from pathlib import Path from unittest.mock import patch from private_gpt.components.ingest.ingest_helper import IngestionHelper from private_gpt.components.ingest.progress.errors import IngestionValidationErrors from private_gpt.components.ingest.utils import FileInfo, get_file_info # Mock path to the test files TEST_FOLDER_PATH = Path(__file__).parents[0] TEST_FILE_PATH = TEST_FOLDER_PATH / "test.pdf" def test_get_file_info_valid_pdf(): """Test extracting file info from a valid PDF file.""" with ( patch("private_gpt.components.ingest.utils.get_filesize") as mock_filesize, patch( "private_gpt.components.ingest.utils.get_guest_mime_type" ) as mock_guest_mime, patch( "private_gpt.components.ingest.utils.get_actual_mime_type" ) as mock_actual_mime, patch("private_gpt.components.ingest.utils.detect_encoding") as mock_encoding, patch("private_gpt.components.ingest.utils.extract_config") as mock_config, ): mock_filesize.return_value = 1024 # 1KB mock_guest_mime.return_value = "application/pdf" mock_actual_mime.return_value = "application/pdf" mock_encoding.return_value = "utf-8" mock_config.return_value = { "pages": 10, "is_encrypted": False, "has_images": True, "has_forms": False, "has_annotations": False, "has_attachments": False, "special": False, } file_info = get_file_info(TEST_FILE_PATH, "testfile.pdf") assert isinstance(file_info, FileInfo) assert file_info.file_size == 1024 assert file_info.guest_mime_type == "application/pdf" assert file_info.actual_mime_type == "application/pdf" assert file_info.config["pages"] == 10 assert not file_info.config["is_encrypted"] assert file_info.config["has_images"] is True assert file_info.config["has_forms"] is False assert file_info.config["has_annotations"] is False assert file_info.config["has_attachments"] is False assert not file_info.config["special"] def test_validate_file_info_real_pdf(): """Test validating a real PDF file.""" file_info = get_file_info(TEST_FILE_PATH, "test.pdf") errors, warnings = IngestionHelper.validate_file_info(file_info) assert len(errors) == 0 # Assuming the real test PDF is valid assert len(warnings) == 0 def test_validate_file_info_real_pdf_with_various_pages(): """Test validating a real PDF file removing pages.""" file_info = get_file_info(TEST_FILE_PATH, "test.pdf") # 1. Pages is well-calculated errors, warnings = IngestionHelper.validate_file_info(file_info) assert len(errors) == 0 assert len(warnings) == 0 # 2. Pages is null file_info.config["pages"] = None errors, warnings = IngestionHelper.validate_file_info(file_info) assert len(errors) == 0 assert len(warnings) == 0 # 3. Pages is 0 file_info.config["pages"] = 0 errors, warnings = IngestionHelper.validate_file_info(file_info) assert len(errors) == 0 assert len(warnings) == 0 # 4. Pages is negative file_info.config["pages"] = -5 errors, warnings = IngestionHelper.validate_file_info(file_info) assert len(errors) == 0 assert len(warnings) == 0 # 4. Pages is non-integer file_info.config["pages"] = "non-integer" errors, warnings = IngestionHelper.validate_file_info(file_info) assert len(errors) == 0 assert len(warnings) == 0 def test_validate_file_info_real_encrypted_pdf(): """Test file validation when using an encrypted PDF file.""" # Assuming you provide an encrypted PDF for testing encrypted_pdf_path = TEST_FOLDER_PATH / "pdf_encrypted.pdf" file_info = get_file_info(encrypted_pdf_path, "pdf_encrypted.pdf") errors, warnings = IngestionHelper.validate_file_info(file_info) assert IngestionValidationErrors.SPECIAL_ENCRYPTED_FILE in warnings assert len(errors) == 0 assert len(warnings) == 1 assert file_info.config["is_encrypted"] is True # TODO: disabled due to missing test file # def test_validate_file_info_real_pdf_with_forms(): # """Test file validation when the real PDF contains forms.""" # # Assuming you provide a PDF with forms for testing # forms_pdf_path = TEST_FOLDER_PATH / "pdf_with_forms.pdf" # file_info = get_file_info(forms_pdf_path, "pdf_with_forms.pdf") # # errors, warnings = IngestionHelper.validate_file_info(file_info) # # assert IngestionValidationErrors.SPECIAL_FILE in warnings # assert len(errors) == 0 # assert len(warnings) == 1 # assert file_info.config["has_forms"] is True # # # def test_validate_file_info_real_pdf_with_annotations(): # """Test file validation when the real PDF contains annotations.""" # # Assuming you provide a PDF with annotations for testing # annotations_pdf_path = TEST_FOLDER_PATH / "pdf_with_annotations.pdf" # file_info = get_file_info(annotations_pdf_path, "pdf_with_annotations.pdf") # # errors, warnings = IngestionHelper.validate_file_info(file_info) # # assert IngestionValidationErrors.SPECIAL_FILE in warnings # assert len(errors) == 0 # assert len(warnings) == 1 # assert file_info.config["has_annotations"] is True def test_validate_file_info_encrypted_pdf(): """Test file validation when the PDF is encrypted.""" file_info = FileInfo( file_name="encryptedfile.pdf", extension=".pdf", file_data=TEST_FILE_PATH, guest_mime_type="application/pdf", actual_mime_type="application/pdf", file_size=1024, config={"pages": 5, "is_encrypted": True, "special": False}, ) errors, warnings = IngestionHelper.validate_file_info(file_info) assert IngestionValidationErrors.SPECIAL_ENCRYPTED_FILE in warnings assert len(errors) == 0 assert len(warnings) == 1 def test_validate_file_info_invalid_pdf(): """Test file validation when the PDF is invalid or malformed.""" file_info = FileInfo( file_name="invalidfile.pdf", extension=".pdf", file_data=TEST_FILE_PATH, guest_mime_type="application/pdf", actual_mime_type="application/pdf", file_size=1024, config={"error": "Failed to parse PDF"}, ) errors, warnings = IngestionHelper.validate_file_info(file_info) assert IngestionValidationErrors.MALFORMED_FILE in errors assert len(errors) == 1 assert len(warnings) == 0 # def test_validate_file_info_pdf_with_forms(): # """Test file validation when the PDF contains forms.""" # file_info = FileInfo( # file_name="pdfforms.pdf", # extension=".pdf", # file_data=TEST_FILE_PATH, # guest_mime_type="application/pdf", # actual_mime_type="application/pdf", # file_size=1024, # config={"pages": 5, "special": True, "is_encrypted": False}, # ) # # errors, warnings = IngestionHelper.validate_file_info(file_info) # # assert IngestionValidationErrors.SPECIAL_FILE in warnings # assert len(errors) == 0 # assert len(warnings) == 1 def test_validate_file_info_file_without_extension(): """Test file validation when the file has no extension.""" file_info = FileInfo( file_name="filewithoutextension", extension=None, file_data=TEST_FILE_PATH, guest_mime_type=None, actual_mime_type="application/octet-stream", file_size=1024, config={"pages": 5}, ) errors, warnings = IngestionHelper.validate_file_info(file_info) assert IngestionValidationErrors.UNKNOWN_FILE_EXTENSION in errors assert len(errors) == 1 assert len(warnings) == 0 def test_validate_file_info_empty_file(): """Test file validation when the file is empty.""" file_info = FileInfo( file_name="emptyfile.pdf", extension=".pdf", file_data=TEST_FILE_PATH, guest_mime_type="application/pdf", actual_mime_type="application/pdf", file_size=0, # File size is zero, indicating an empty file config={}, ) errors, warnings = IngestionHelper.validate_file_info(file_info) assert IngestionValidationErrors.INVALID_FILE_SIZE in errors assert len(errors) == 1 assert len(warnings) == 0