Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion libs/ktem/ktem/index/file/ui.py
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,9 @@ def _process_single_file(self, f: FileData) -> NamedString | bytes:
if self.type == "filepath":
if f.orig_name and Path(file_name).name != f.orig_name:
file_name = str(Path(file_name).parent / f.orig_name)
os.rename(f.path, file_name)
# Use shutil.move instead of os.rename to handle the case where
# the target file already exists (FileExistsError on Windows)
shutil.move(f.path, file_name)
file = tempfile.NamedTemporaryFile(delete=False, dir=self.GRADIO_CACHE)
file.name = file_name
return NamedString(file_name)
Expand Down
66 changes: 66 additions & 0 deletions libs/ktem/ktem_tests/test_file_upload.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
"""Tests for file upload functionality."""

import shutil


class TestFileProcessing:
"""Test file processing functions, especially rename handling."""

def test_file_rename_when_target_exists(self, tmp_path):
"""Test that file rename works when target file already exists.

This tests the fix for issue #765 where on Windows, os.rename() fails
with FileExistsError when the target file already exists.
"""
# Create source file
source_file = tmp_path / "source_file.pdf"
source_file.write_text("source content")

# Create target file that already exists
target_file = tmp_path / "target_file.pdf"
target_file.write_text("existing content")

# Verify both files exist
assert source_file.exists()
assert target_file.exists()

# Use shutil.move (as in the fix) which should work even if target exists
shutil.move(str(source_file), str(target_file))

# Verify source is moved and target has new content
assert not source_file.exists()
assert target_file.exists()
assert target_file.read_text() == "source content"

def test_file_rename_when_target_not_exists(self, tmp_path):
"""Test that file rename works when target file does not exist."""
# Create source file
source_file = tmp_path / "source_file.pdf"
source_file.write_text("source content")

# Target file does not exist
target_file = tmp_path / "new_target.pdf"
assert not target_file.exists()

# Use shutil.move
shutil.move(str(source_file), str(target_file))

# Verify source is moved
assert not source_file.exists()
assert target_file.exists()
assert target_file.read_text() == "source content"

def test_file_rename_with_special_characters(self, tmp_path):
"""Test file rename with special characters in filename."""
# Create source file
source_file = tmp_path / "temp_upload_12345.pdf"
source_file.write_text("content")

# Target file with special characters (URL encoded spaces)
target_file = tmp_path / "document%20name.pdf"

# Use shutil.move
shutil.move(str(source_file), str(target_file))

assert not source_file.exists()
assert target_file.exists()