From 1acb88017827dd182f19840ad0c3a23e09a0b9da Mon Sep 17 00:00:00 2001 From: Tania Mathern Date: Fri, 6 Mar 2026 15:08:54 -0800 Subject: [PATCH 1/2] fix: Fragment API --- ffi_improvs.md | 11 +++++ src/c2pa/c2pa.py | 62 ++++++++++++++++++++++++- tests/fixtures/dash1.m4s | Bin 0 -> 71111 bytes tests/fixtures/dashinit.mp4 | Bin 0 -> 4765 bytes tests/test_unit_tests.py | 90 +++++++++++++++--------------------- 5 files changed, 110 insertions(+), 53 deletions(-) create mode 100644 ffi_improvs.md create mode 100644 tests/fixtures/dash1.m4s create mode 100644 tests/fixtures/dashinit.mp4 diff --git a/ffi_improvs.md b/ffi_improvs.md new file mode 100644 index 00000000..2e6f2ae9 --- /dev/null +++ b/ffi_improvs.md @@ -0,0 +1,11 @@ +# C FFI Improvement Opportunities + +The Rust C FFI (`c2pa_c_ffi`) exports ~70 functions. The Python layer wraps ~50. This document identifies concrete opportunities to better leverage the FFI. + +### Release Library Verification + +| FFI Function | In Release Library? | Python Status | +|---|---|---| +| `c2pa_builder_with_archive` | YES | Wrapped as `Builder.with_archive()` | +| `c2pa_reader_with_fragment` | YES | Wrapped as `Reader.with_fragment()` | +| `c2pa_reader_with_context_from_manifest_data_and_stream` | NO | — | diff --git a/src/c2pa/c2pa.py b/src/c2pa/c2pa.py index 1e03a108..887cf262 100644 --- a/src/c2pa/c2pa.py +++ b/src/c2pa/c2pa.py @@ -76,6 +76,7 @@ 'c2pa_context_new', 'c2pa_reader_from_context', 'c2pa_reader_with_stream', + 'c2pa_reader_with_fragment', 'c2pa_builder_from_context', 'c2pa_builder_with_definition', 'c2pa_builder_with_archive', @@ -684,6 +685,12 @@ def _setup_function(func, argtypes, restype=None): ctypes.POINTER(C2paStream)], ctypes.POINTER(C2paReader) ) +_setup_function( + _lib.c2pa_reader_with_fragment, + [ctypes.POINTER(C2paReader), ctypes.c_char_p, + ctypes.POINTER(C2paStream), ctypes.POINTER(C2paStream)], + ctypes.POINTER(C2paReader) +) _setup_function( _lib.c2pa_builder_from_context, [ctypes.POINTER(C2paContext)], @@ -2073,7 +2080,8 @@ class Reader(ManagedResource): 'file_error': "Error cleaning up file: {}", 'reader_cleanup_error': "Error cleaning up reader: {}", 'encoding_error': "Invalid UTF-8 characters in input: {}", - 'closed_error': "Reader is closed" + 'closed_error': "Reader is closed", + 'fragment_error': "Failed to process fragment: {}" } @classmethod @@ -2450,6 +2458,58 @@ def _get_cached_manifest_data(self) -> Optional[dict]: return self._manifest_data_cache + def with_fragment(self, format: str, stream, + fragment_stream) -> "Reader": + """Process a BMFF fragment stream with this reader. + + Used for fragmented BMFF media (DASH/HLS streaming) where + content is split into init segments and fragment files. + + Args: + format: MIME type of the media (e.g., "video/mp4") + stream: Stream-like object with the main/init segment data + fragment_stream: Stream-like object with the fragment data + + Returns: + This reader instance, for method chaining. + + Raises: + C2paError: If there was an error processing the fragment + """ + self._ensure_valid_state() + + supported = Reader.get_supported_mime_types() + format_bytes = _validate_and_encode_format( + format, supported, "Reader" + ) + + with Stream(stream) as main_obj, Stream(fragment_stream) as frag_obj: + new_ptr = _lib.c2pa_reader_with_fragment( + self._handle, + format_bytes, + main_obj._stream, + frag_obj._stream, + ) + + if not new_ptr: + self._handle = None + error = _parse_operation_result_for_error( + _lib.c2pa_error() + ) + if error: + raise C2paError(error) + raise C2paError( + Reader._ERROR_MESSAGES[ + 'fragment_error' + ].format("Unknown error")) + self._handle = new_ptr + + # Invalidate caches: fragment may change manifest data + self._manifest_json_str_cache = None + self._manifest_data_cache = None + + return self + def close(self): """Release the reader resources.""" self._manifest_json_str_cache = None diff --git a/tests/fixtures/dash1.m4s b/tests/fixtures/dash1.m4s new file mode 100644 index 0000000000000000000000000000000000000000..1a9a99644b833105a4ee54e958f4a762442ca7b1 GIT binary patch literal 71111 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∋D0KiSPO4Ys;jH*$ELgMQjX-+?)IdIfGAXNI=; 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 literal 0 HcmV?d00001 diff --git a/tests/test_unit_tests.py b/tests/test_unit_tests.py index f81c6652..5aeb44a3 100644 --- a/tests/test_unit_tests.py +++ b/tests/test_unit_tests.py @@ -256,7 +256,7 @@ def test_stream_read_detailed_and_parse(self): title = manifest_store["manifests"][manifest_store["active_manifest"]]["claim"]["dc:title"] self.assertEqual(title, DEFAULT_TEST_FILE_NAME) - def test_stream_read_string_stream(self): + def test_stream_read_string_stream_path_only(self): with Reader(self.testPath) as reader: json_data = reader.json() self.assertIn(DEFAULT_TEST_FILE_NAME, json_data) @@ -4670,7 +4670,7 @@ def test_builder_add_ingredient_from_file_path(self): builder.close() - def test_builder_add_ingredient_from_file_path(self): + def test_builder_add_ingredient_from_file_path_not_found(self): """Test Builder class add_ingredient_from_file_path method.""" # Suppress the specific deprecation warning for this test, as this is a legacy method @@ -4929,56 +4929,6 @@ def test_sign_file_callback_signer(self): finally: shutil.rmtree(temp_dir) - def test_sign_file_callback_signer(self): - """Test signing a file using the sign_file method.""" - - temp_dir = tempfile.mkdtemp() - - try: - output_path = os.path.join(temp_dir, "signed_output.jpg") - - # Use the sign_file method - builder = Builder(self.manifestDefinition) - - # Create signer with callback using create_signer function - signer = create_signer( - callback=self.callback_signer_es256, - alg=SigningAlg.ES256, - certs=self.certs.decode('utf-8'), - tsa_url="http://timestamp.digicert.com" - ) - - manifest_bytes = builder.sign_file( - source_path=self.testPath, - dest_path=output_path, - signer=signer - ) - - # Verify the output file was created - self.assertTrue(os.path.exists(output_path)) - - # Verify results - self.assertIsInstance(manifest_bytes, bytes) - self.assertGreater(len(manifest_bytes), 0) - - # Read the signed file and verify the manifest - with open(output_path, "rb") as file, Reader("image/jpeg", file) as reader: - json_data = reader.json() - # Needs trust configuration to be set up to validate as Trusted - # self.assertNotIn("validation_status", json_data) - - # Parse the JSON and verify the signature algorithm - manifest_data = json.loads(json_data) - active_manifest_id = manifest_data["active_manifest"] - active_manifest = manifest_data["manifests"][active_manifest_id] - - self.assertIn("signature_info", active_manifest) - signature_info = active_manifest["signature_info"] - self.assertEqual(signature_info["alg"], self.callback_signer_alg) - - finally: - shutil.rmtree(temp_dir) - def test_sign_file_callback_signer_managed_single(self): """Test signing a file using the sign_file method with context managers.""" @@ -5492,6 +5442,42 @@ def test_reader_format_and_path_with_ctx(self): reader.close() context.close() + def test_with_fragment_on_closed_reader_raises(self): + context = Context() + reader = Reader(DEFAULT_TEST_FILE, context=context) + reader.close() + with self.assertRaises(Error): + reader.with_fragment( + "video/mp4", + io.BytesIO(b"\x00" * 100), + io.BytesIO(b"\x00" * 100), + ) + context.close() + + def test_with_fragment_unsupported_format_raises(self): + context = Context() + reader = Reader(DEFAULT_TEST_FILE, context=context) + with self.assertRaises(Error): + reader.with_fragment( + "text/plain", + io.BytesIO(b"\x00" * 100), + io.BytesIO(b"\x00" * 100), + ) + reader.close() + context.close() + + def test_with_fragment_with_dash_fixtures(self): + context = Context() + init_path = os.path.join(FIXTURES_DIR, "dashinit.mp4") + with open(init_path, "rb") as init_fragment: + reader = Reader("video/mp4", init_fragment, context=context) + frag_path = os.path.join(FIXTURES_DIR, "dash1.m4s") + with open(init_path, "rb") as init_fragment, \ + open(frag_path, "rb") as next_fragment: + reader.with_fragment("video/mp4", init_fragment, next_fragment) + reader.close() + context.close() + class TestBuilderWithContext(TestContextAPIs): From 0ec60a7b5111a0bf0385dfce20f653b1e083eb3c Mon Sep 17 00:00:00 2001 From: tmathern <60901087+tmathern@users.noreply.github.com> Date: Mon, 9 Mar 2026 11:24:16 -0700 Subject: [PATCH 2/2] Delete ffi_improvs.md --- ffi_improvs.md | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 ffi_improvs.md diff --git a/ffi_improvs.md b/ffi_improvs.md deleted file mode 100644 index 2e6f2ae9..00000000 --- a/ffi_improvs.md +++ /dev/null @@ -1,11 +0,0 @@ -# C FFI Improvement Opportunities - -The Rust C FFI (`c2pa_c_ffi`) exports ~70 functions. The Python layer wraps ~50. This document identifies concrete opportunities to better leverage the FFI. - -### Release Library Verification - -| FFI Function | In Release Library? | Python Status | -|---|---|---| -| `c2pa_builder_with_archive` | YES | Wrapped as `Builder.with_archive()` | -| `c2pa_reader_with_fragment` | YES | Wrapped as `Reader.with_fragment()` | -| `c2pa_reader_with_context_from_manifest_data_and_stream` | NO | — |