{"id":14041784,"url":"https://github.com/sigstore/model-transparency","last_synced_at":"2025-07-27T15:30:54.692Z","repository":{"id":190242427,"uuid":"682178126","full_name":"sigstore/model-transparency","owner":"sigstore","description":"Supply chain security for ML","archived":false,"fork":false,"pushed_at":"2025-07-19T17:49:39.000Z","size":2370,"stargazers_count":176,"open_issues_count":28,"forks_count":36,"subscribers_count":9,"default_branch":"main","last_synced_at":"2025-07-19T21:00:00.170Z","etag":null,"topics":["machine-learning","security","sigstore","supply-chain"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/sigstore.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":"CODEOWNERS","security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2023-08-23T15:57:02.000Z","updated_at":"2025-07-19T17:49:43.000Z","dependencies_parsed_at":"2023-08-23T20:10:18.955Z","dependency_job_id":"35f485a0-904e-4498-bf8e-42aca0b0e4e8","html_url":"https://github.com/sigstore/model-transparency","commit_stats":null,"previous_names":["google/model-transparency","sigstore/model-transparency"],"tags_count":8,"template":false,"template_full_name":null,"purl":"pkg:github/sigstore/model-transparency","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sigstore%2Fmodel-transparency","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sigstore%2Fmodel-transparency/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sigstore%2Fmodel-transparency/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sigstore%2Fmodel-transparency/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/sigstore","download_url":"https://codeload.github.com/sigstore/model-transparency/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sigstore%2Fmodel-transparency/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":266027664,"owners_count":23866051,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["machine-learning","security","sigstore","supply-chain"],"created_at":"2024-08-12T08:00:37.679Z","updated_at":"2025-07-27T15:30:54.687Z","avatar_url":"https://github.com/sigstore.png","language":"Python","funding_links":[],"categories":["Open Source Security Tools","Tools","LLM SECURITY / AI SECURITY","Python","Identity, signing and provenance"],"sub_categories":["Model Verification","AI/ML Dataset Security","Supply chain beyond libraries"],"readme":"# Model Transparency\n\n\u003c!-- markdown-toc --bullets=\"-\" -i README.md --\u003e\n\n\u003c!-- toc --\u003e\n\n- [Overview](#overview)\n- [Model Signing](#model-signing)\n  - [Model Signing CLI](#model-signing-cli)\n  - [Model Signing API](#model-signing-api)\n  - [Model Signing Format](#model-signing-format)\n- [SLSA for ML](#slsa-for-ml)\n- [Status](#status)\n- [Contributing](#contributing)\n\n\u003c!-- tocstop --\u003e\n\n## Overview\n\nThere is currently significant growth in the number of ML-powered applications.\nThis brings benefits, but it also provides grounds for attackers to exploit\nunsuspecting ML users.\n\nBuilding on the work with [Open Source Security Foundation][openssf], we are\ncreating this collection of projects to strengthen the ML supply chain in\n_the same way_ as the traditional software supply chain.\n\nThe focus is on providing *verifiable* claims about the integrity and provenance\nof the resulting models, meaning users can check for themselves that these\nclaims are true rather than having to just trust the model trainer.\n\n## Model Signing\n\nThis project demonstrates how to protect the integrity of a model by signing it.\nWe support generating signatures via [Sigstore](https://www.sigstore.dev/), a\ntool for making code signatures transparent without requiring management of\ncryptographic key material. But we also support traditional signing methods, so\nmodels can be signed with public keys or signing certificates as well as\nPKCS #11 enabled devices *(install with `pip install model-signing[pkcs11]` to enable this functionality)*.\n\nThe signing part creates a\n[sigstore bundle](https://github.com/sigstore/protobuf-specs/blob/main/protos/sigstore_bundle.proto)\nprotobuf that is stored as in JSON format. The bundle contains the verification\nmaterial necessary to check the payload and a payload as a\n[DSSE envelope](https://github.com/sigstore/protobuf-specs/blob/main/protos/envelope.proto).\nFurther the DSSE envelope contains an in-toto statment and the signature over\nthat statement. The signature format and how the the signature is computed can\nbe seen\n[here](https://github.com/secure-systems-lab/dsse/blob/v1.0.0/protocol.md).\n\nFinally, the statement itself contains subjects which are a list of (file path,\ndigest) pairs a predicate type set to `https://model_signing/signature/v1.0` and\na dictionary of predicates. The idea is to use the predicates to store (and\ntherefor sign) model card information in the future.\n\nThe verification part reads the sigstore bundle file and firstly verifies that the\nsignature is valid and secondly compute the model's file hashes again to compare\nagainst the signed ones.\n\nWhen users download a given version of a signed model they can check that the\nsignature comes from a known or trusted identity and thus that the model hasn't\nbeen tampered with after training.\n\nWhen using Sigstore, signing events are recorded to Sigstore's append-only\ntransparency log.  Transparency logs make signing events discoverable: Model\nverifiers can validate that the models they are looking at exist in the\ntransparency log by checking a proof of inclusion (which is handled by the model\nsigning library).  Furthermore, model signers that monitor the log can check for\nany unexpected signing events.\n\nModel signers should monitor for occurences of their signing identity in the\nlog. Sigstore is actively developing a [log\nmonitor](https://github.com/sigstore/rekor-monitor) that runs on GitHub Actions.\n\n![Signing models with Sigstore](docs/images/sigstore-model-diagram.png)\n\n### Model Signing CLI\n\nAfter installing the package, the CLI can be used via either `python -m\nmodel_signing \u003cargs\u003e` or by calling the binary directly, `model_signing \u003cargs\u003e`.\n\nUsers that don't want to install the package, but want to test this using the\nrepository can do the same using [Hatch](https://hatch.pypa.io/latest/) via\n`hatch run python -m model_signing \u003cargs\u003e`.\n\nFor the remainder of the section, we would use `model_signing \u003cargs\u003e` method.\n\nThe CLI has two subcommands: `sign` for signing and `verify` for verification.\nEach subcommand has another level of subcommands to select the signing method\n(`sigstore` -- the default, can be skipped --, `key`, `certificate`). Then, each\nof these subcommands has several flags to configure parameters for\nsigning/verification.\n\nFor the demo, we will use the `bert-base-uncased` model, which can be obtained\nvia:\n\n```bash\n[...]$ git clone --depth=1 \"https://huggingface.co/bert-base-uncased\"\n```\n\nWe remove the `.git` directory since that should not be included in the\nsignature:\n\n```bash\n[...]$ rm -rf bert-base-uncased/.git\n```\n\nBy default, the code also ignores git related paths.\n\nThe simplest example of the CLI is to sign a model using Sigstore:\n\n```bash\n[...]$ model_signing sign bert-base-uncased\n```\n\nThis will open an OIDC flow to obtain a short lived token for the certificate.\nThe identity used during signing and the provider must be reused during\nverification.\n\nAs another example, here is how we can sign with private keys. First, we\ngenerate the key pair:\n\n```bash\n[...]$ openssl ecparam -name prime256v1 -genkey -noout -out key.priv\n[...]$ openssl ec -in key.priv -pubout \u003e key.pub\n```\n\nAnd then we use the private key to sign.\n\n```bash\n[...]$ model_signing sign key bert-base-uncased --private_key key.priv\n```\n\nAll signing methods support changing the signature name and location via the\n`--signature` flag:\n\n```bash\n[...]$ model_signing sign bert-base-uncased --signature model.sig\n```\n\nConsult the help for a list of all flags (`model_signing --help`, or directly\n`model_signing` with no arguments)\n\nOn verification we use the `verify` subcommand. To verify a Sigstore signed\nmodel we use\n\n```bash\n[...]$ model_signing verify bert-base-uncased \\\n      --signature model.sig \\\n      --identity \"$identity\" \\\n      --identity_provider \"$oidc_provider\"\n```\n\nWhere `$identity` and `$oidc_provider` are those set up during the signing flow\nand `--signature` must point to the signature to verify.\n\nFor developers signing models with Sigstore, there are three identity providers\nthat can be used at the moment:\n\n* Google's provider is `https://accounts.google.com`.\n* GitHub's provider is `https://github.com/login/oauth`.\n  * GitHub Actions uses `https://token.actions.githubusercontent.com`\n* Microsoft's provider is `https://login.microsoftonline.com`.\n\nFor automated signing using a workload identity, the following platforms\nare currently supported, shown with their expected identities:\n\n* GitHub Actions\n  (`https://github.com/octo-org/octo-automation/.github/workflows/oidc.yml@refs/heads/main`)\n* GitLab CI\n  (`https://gitlab.com/my-group/my-project//path/to/.gitlab-ci.yml@refs/heads/main`)\n* Google Cloud Platform (`SERVICE_ACCOUNT_NAME@PROJECT_ID.iam.gserviceaccount.com`)\n* Buildkite CI (`https://buildkite.com/ORGANIZATION_SLUG/PIPELINE_SLUG`)\n\nSimilarly, for key verification, we can use\n\n```bash\n[...]$ model_signing verify key bert-base-uncased \\\n       --signature resnet.sig --public_key key.pub\n```\n\n#### Signing with PKCS #11 URIs\n\nSigning with PKCS #11 enabled crypto devices is supported through RFC 7512\ncompliant PKCS #11 URIs. The URI can be used in place of the private key\nwhen siging with a private key or certificate.\n\nThe following features are supported/required:\n\n    - The PKCS #11 URI must either provide the module through the query\n      parameter 'module-path', or the query parameter 'module-name' must\n      describe the name of a module that can be found in well-known\n      directories of Linux distributions.\n    - A token can be selected based on a provided 'slot-id' path parameter.\n      The first token that matches the given slot-id will be used. If a\n      'token' path parameter is also provided, then it will be used for\n      selecting the appropriate token by its label.\n    - When no 'slot-id' is given then all slots are searched for by the\n      name of the given 'token'.\n    - A PIN may be provided as 'pin-value' query parameter or may be read\n      from a file described by the 'pin-source' query parameter.\n    - An 'id' path parameter and/or key label (path parameter 'object') must\n      be provided to select the signing key.\n    - The public key on the PKCS #11 device will also be accessed during\n      signing.\n    - The signing key must be of type NIST P256/384/521 (secp256/384/512r1).\n\nWith a PKCS #11 URI describing the private key, we can use the following\nfor signing:\n\n```bash\n[...]$ model_signing sign pkcs11-key --signature model.sig \\\n       --private_key \"pkcs11:...\" /path/to/your/model\n```\n\nFor signature verification it is necessary to retrieve the public key from\nthe PKCS #11 device and store it in a file in PEM format. With can then use:\n\n```bash\n[...]$ model_signing verify key --signature model.sig\\\n       --public_key key.pub  /path/to/your/model\n```\n\n### Model Signing API\n\nWe offer an API which can be used in integrations with ML frameworks, ML\npipelins and ML model hubs libraries. The CLI wraps around the API.\n\nThe API is split into 3 main components:\n\n- `model_signing.hashing`: responsible with generating a list of hashes for\n  every component of the model. A component could be a file, a file shard, a\n  tensor, etc., depending on the method used. We currently support only files\n  and file shards. The result of hashing is a manifest, a listing of hashes for\n  every object in the model.\n- `model_signing.signing`: responsible with taking the manifest and generating a\n  signature, based on a signing configuration. The signing configuration can\n  select the method used to sign as well as the parameters.\n- `model_signing.verifying`: responsible with taking a signature and verifying\n  it. If the cryptographic parts of the signature can be validated, the\n  verification layer would return an expanded manifest which can then be\n  compared agains a manifest obtained from hashing the existing model. If the\n  two manifest don't match then the model integrity was compromised and the\n  `model_signing` package detected that.\n\nThe first two of these components allows configurability but can also be used\ndirectly, with a default configuration. The only difference is for the\nverification component where we need to configure the verification method since\nthere are no sensible defaults that can be used.\n\nThe simplest way to generate a signature using Sigstore is:\n\n```python\nimport model_signing\n\nmodel_signing.signing.sign(\"bert-base-uncased\", \"model.sig\")\n```\n\nThis will run the same OIDC flow as when signing with Sigstore from the CLI.\n\nWe can use explicit configurations to configure more about the signing:\n\n```python\nimport model_signing\n\nmodel_signing.signing.Config().use_elliptic_key_signer(\n    private_key=\"key.priv\"\n).sign(\n    \"finbert\", \"finbert.sig\"\n)\n```\n\nThe same signing configuration can be used to sign multiple models:\n\n```python\nimport model_signing\n\nsigning_config = model_signing.signing.Config().use_elliptic_key_signer(\n    private_key=\"key.priv\"\n)\n\nfor model in all_models:\n    signing_config.sign(model, f\"{model}_sharded.sig\")\n```\n\nVerification needs a configuration. To verify using Sigstore:\n\n```python\nimport model_signing\n\nmodel_signing.verifying.Config().use_sigstore_verifier(\n    identity=identity, oidc_issuer=oidc_provider\n).verify(\"finbert\", \"finbert.sig\")\n```\n\nThe same verification configuration can be used to verify multiple models:\n\n```python\nimport model_signing\n\nverifying_config = model_signing.signing.Config().use_elliptic_key_verifier(\n    public_key=\"key.pub\"\n)\n\nfor model in all_models:\n    verifying_config.verify(model, f\"{model}_sharded.sig\")\n```\n\nConsult the\n[official documentation](https://sigstore.github.io/model-transparency/model_signing.html)\nfor more details.\n\n### Model Signing Format\n\nFor a diagram showing the model signing format as well as an explanation of the\nlayers, see the [model signing format](docs/model_signing_format.md) document.\n\n## SLSA for ML\n\nThis is a separate project from the `model_signing` package, aimed at generating\n[SLSA][slsa] provenance for ML models, using either Github Actions or Google\nCloud Platform.\n\nSee [slsa_for_models/README.md](slsa_for_models/README.md) for more information.\n\n## Contributing\n\nPlease see the [Contributor Guide](CONTRIBUTING.md) for more information.\n\n[slsa]: https://slsa.dev/\n[saif]: https://blog.google/technology/safety-security/introducing-googles-secure-ai-framework/\n[openssf]: https://openssf.org/\n[slsa-generator]: https://github.com/slsa-framework/slsa-github-generator\n[solarwinds]: https://www.techtarget.com/whatis/feature/SolarWinds-hack-explained-Everything-you-need-to-know\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsigstore%2Fmodel-transparency","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsigstore%2Fmodel-transparency","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsigstore%2Fmodel-transparency/lists"}