Skip to main content
Glama
incremental_utils_test.py24.1 kB
# Copyright (c) Meta Platforms, Inc. and affiliates. # # This source code is licensed under both the MIT license found in the # LICENSE-MIT file in the root directory of this source tree and the Apache # License, Version 2.0 found in the LICENSE-APACHE file in the root directory # of this source tree. import os import tempfile import unittest from pathlib import Path from typing import Generator from apple.tools.code_signing.codesign_bundle import CodesignConfiguration from .assemble_bundle_types import BundleSpecItem from .incremental_state import CodesignedOnCopy, IncrementalState, IncrementalStateItem from .incremental_utils import ( calculate_incremental_state, IncrementalContext, should_assemble_incrementally, ) try: from contextlib import chdir # pyre-ignore[21], Python 3.11+ except ImportError: from contextlib import contextmanager @contextmanager def chdir(path: os.PathLike) -> Generator[None, None, None]: cwd = os.getcwd() try: os.chdir(path) yield finally: os.chdir(cwd) class TestIncrementalUtils(unittest.TestCase): maxDiff = None def test_not_run_incrementally_when_previous_build_not_incremental(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=False, ) ] incremental_context = IncrementalContext( metadata={Path("foo"): "digest"}, state=None, codesigned=False, codesign_configuration=None, codesign_identity=None, codesign_arguments=[], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) def test_run_incrementally_when_previous_build_not_codesigned(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=False, ) ] incremental_context = IncrementalContext( metadata={Path("foo"): "digest"}, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=False, codesign_configuration=None, codesigned_on_copy=[], codesign_identity=None, codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=None, codesign_identity=None, codesign_arguments=[], versioned_if_macos=True, ) self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_previous_build_codesigned_and_current_is_not( self, ): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=False, ) ] incremental_context = IncrementalContext( metadata={Path("foo"): "digest"}, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, codesign_configuration=None, codesigned_on_copy=[], codesign_identity=None, codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=False, codesign_configuration=None, codesign_identity=None, codesign_arguments=[], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) # Check that behavior changes when both builds are codesigned incremental_context.codesigned = True self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_previous_build_codesigned_with_different_identity( self, ): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=False, ) ] incremental_context = IncrementalContext( metadata={Path("foo"): "digest"}, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, codesign_configuration=None, codesigned_on_copy=[], codesign_identity="old_identity", codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=None, codesign_identity="new_identity", codesign_arguments=[], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) # Check that behavior changes when identities are same incremental_context.state.codesign_identity = "same_identity" incremental_context.codesign_identity = "same_identity" self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_run_incrementally_when_codesign_on_copy_paths_match(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=True, ), BundleSpecItem( src="src/bar", dst="bar", codesign_on_copy=True, ), BundleSpecItem( src="src/baz", dst="baz", codesign_on_copy=True, codesign_entitlements="entitlements.plist", ), ] incremental_context = IncrementalContext( metadata={ Path("src/foo"): "digest", Path("src/baz"): "digest2", Path("entitlements.plist"): "entitlements_digest", }, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ), IncrementalStateItem( source=Path("src/baz"), destination_relative_to_bundle=Path("baz"), digest="digest2", resolved_symlink=None, ), ], codesigned=True, codesign_configuration=None, codesigned_on_copy=[ CodesignedOnCopy( path=Path("foo"), entitlements_digest=None, codesign_flags_override=None, extra_codesign_paths=None, ), CodesignedOnCopy( path=Path("baz"), entitlements_digest="entitlements_digest", codesign_flags_override=None, extra_codesign_paths=None, ), ], codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=None, codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, ) self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_codesign_on_copy_paths_mismatch(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", # want it to be not codesigned in new build codesign_on_copy=False, ) ] incremental_context = IncrementalContext( metadata={Path("src/foo"): "digest"}, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, codesign_configuration=None, # but it was codesigned in old build codesigned_on_copy=[ CodesignedOnCopy( path=Path("foo"), entitlements_digest=None, codesign_flags_override=None, extra_codesign_paths=None, ) ], codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=None, codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) spec[0].codesign_on_copy = True self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_codesign_on_copy_entitlements_mismatch(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=True, codesign_entitlements="baz/entitlements.plist", ) ] incremental_context = IncrementalContext( metadata={ Path("src/foo"): "digest", Path("baz/entitlements.plist"): "new_digest", }, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, codesign_configuration=None, codesigned_on_copy=[ CodesignedOnCopy( path=Path("foo"), entitlements_digest="old_digest", codesign_flags_override=None, extra_codesign_paths=None, ) ], codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=None, codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) incremental_context.metadata[Path("baz/entitlements.plist")] = "old_digest" self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_codesign_on_copy_flags_mismatch(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=True, codesign_flags_override=["--force"], ) ] incremental_context = IncrementalContext( metadata={ Path("src/foo"): "digest", }, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, codesign_configuration=None, codesigned_on_copy=[ CodesignedOnCopy( path=Path("foo"), entitlements_digest=None, codesign_flags_override=["--force", "--deep"], extra_codesign_paths=None, ) ], codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=None, codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) incremental_context.state.codesigned_on_copy[0].codesign_flags_override = [ "--force" ] self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_extra_codesign_paths_mismatch(self): extra_codesign_paths_before = ["Frameworks/Base.framework"] extra_codesign_paths_after = [ "Frameworks/Base.framework", "Frameworks/Extra.framework", ] spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=True, extra_codesign_paths=extra_codesign_paths_after, ) ] incremental_context = IncrementalContext( metadata={ Path("src/foo"): "digest", }, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, codesign_configuration=None, codesigned_on_copy=[ CodesignedOnCopy( path=Path("foo"), entitlements_digest=None, codesign_flags_override=None, extra_codesign_paths=extra_codesign_paths_before, ) ], codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=None, codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) incremental_context.state.codesigned_on_copy[ 0 ].extra_codesign_paths = extra_codesign_paths_after self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_codesign_arguments_mismatch(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", ) ] incremental_context = IncrementalContext( metadata={ Path("src/foo"): "digest", }, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, codesign_configuration=None, codesigned_on_copy=[], codesign_identity="same_identity", codesign_arguments=["--force"], swift_stdlib_paths=[], versioned_if_macos=True, ), codesigned=True, codesign_configuration=None, codesign_identity="same_identity", codesign_arguments=["--force", "--deep"], versioned_if_macos=True, ) self.assertFalse(should_assemble_incrementally(spec, incremental_context)) incremental_context.codesign_arguments = ["--force"] self.assertTrue(should_assemble_incrementally(spec, incremental_context)) def test_not_run_incrementally_when_codesign_configurations_mismatch(self): spec = [ BundleSpecItem( src="src/foo", dst="foo", codesign_on_copy=True, ) ] incremental_context = IncrementalContext( metadata={Path("src/foo"): "digest"}, state=IncrementalState( items=[ IncrementalStateItem( source=Path("src/foo"), destination_relative_to_bundle=Path("foo"), digest="digest", resolved_symlink=None, ) ], codesigned=True, # Dry codesigned in old build codesign_configuration=CodesignConfiguration.dryRun, codesigned_on_copy=[ CodesignedOnCopy( path=Path("foo"), entitlements_digest=None, codesign_flags_override=None, extra_codesign_paths=None, ) ], codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, swift_stdlib_paths=[], ), codesigned=True, codesign_configuration=CodesignConfiguration.dryRun, codesign_identity="same_identity", codesign_arguments=[], versioned_if_macos=True, ) # Canary self.assertTrue(should_assemble_incrementally(spec, incremental_context)) # Now we want a regular signing in new build incremental_context.codesign_configuration = None self.assertFalse(should_assemble_incrementally(spec, incremental_context)) def test_calculate_incremental_state(self): with tempfile.TemporaryDirectory() as project_root, chdir(project_root): # project_root # ├── foo # ├── bar # │ ├── baz # │ └── qux -> baz # ├── abc # │ └── def # └── ghi -> abc Path("foo").write_text("hello") bar_path = Path("bar") bar_path.mkdir() (bar_path / "baz").write_text("world") (bar_path / "qux").symlink_to("baz") abc_path = Path("abc") abc_path.mkdir() (abc_path / "def").write_text("yo") Path("ghi").symlink_to("abc") action_metadata = { Path("foo"): "hash(foo)", Path("bar/baz"): "hash(baz)", Path("abc/def"): "hash(def)", } spec = [ BundleSpecItem( src="foo", dst="foo", codesign_on_copy=False, ), BundleSpecItem( src="bar", dst="tux", codesign_on_copy=True, ), BundleSpecItem( src="ghi", dst="ghi", codesign_on_copy=True, ), ] state = calculate_incremental_state(spec, action_metadata) self.assertEqual( state, [ IncrementalStateItem( source=Path("foo"), destination_relative_to_bundle=Path("foo"), digest="hash(foo)", resolved_symlink=None, ), IncrementalStateItem( source=Path("bar/baz"), destination_relative_to_bundle=Path("tux/baz"), digest="hash(baz)", resolved_symlink=None, ), IncrementalStateItem( source=Path("bar/qux"), destination_relative_to_bundle=Path("tux/qux"), digest=None, resolved_symlink=Path("baz"), ), IncrementalStateItem( source=Path("ghi/def"), destination_relative_to_bundle=Path("ghi/def"), digest="hash(def)", resolved_symlink=None, ), ], ) def test_calculate_incremental_state_with_ds_store(self) -> None: with tempfile.TemporaryDirectory() as project_root, chdir(project_root): # project_root # ├── foo # └── bar # ├── baz # └── .DS_Store Path("foo").write_text("hello") bar_path = Path("bar") bar_path.mkdir() (bar_path / "baz").write_text("world") (bar_path / ".DS_Store").touch() action_metadata = { Path("foo"): "hash(foo)", Path("bar/baz"): "hash(baz)", } spec = [ BundleSpecItem( src="foo", dst="foo", codesign_on_copy=False, ), BundleSpecItem( src="bar", dst="bar", codesign_on_copy=True, ), ] state = calculate_incremental_state(spec, action_metadata) self.assertEqual( state, [ IncrementalStateItem( source=Path("foo"), destination_relative_to_bundle=Path("foo"), digest="hash(foo)", resolved_symlink=None, ), IncrementalStateItem( source=Path("bar/baz"), destination_relative_to_bundle=Path("bar/baz"), digest="hash(baz)", resolved_symlink=None, ), ], )

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/systeminit/si'

If you have feedback or need assistance with the MCP directory API, please join our Discord server