{"id":13535837,"url":"https://github.com/pcaversaccio/snekmate","last_synced_at":"2025-05-14T17:09:58.233Z","repository":{"id":50595404,"uuid":"519523885","full_name":"pcaversaccio/snekmate","owner":"pcaversaccio","description":"State-of-the-art, highly opinionated, hyper-optimised, and secure 🐍Vyper smart contract building blocks.","archived":false,"fork":false,"pushed_at":"2025-05-07T16:27:39.000Z","size":3196,"stargazers_count":546,"open_issues_count":5,"forks_count":68,"subscribers_count":8,"default_branch":"main","last_synced_at":"2025-05-07T17:30:05.828Z","etag":null,"topics":["ethereum","evm","library","security","smart-contracts","vyper","vyper-contracts"],"latest_commit_sha":null,"homepage":"https://snekmate.com","language":"Solidity","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"agpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/pcaversaccio.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":"audits/ChainSecurity_Curve_Fee_Splitter_September_2024.pdf","citation":null,"codeowners":null,"security":"SECURITY.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null},"funding":{"custom":"https://etherscan.io/address/0xe9Fa0c8B5d7F79DeC36D3F448B1Ac4cEdedE4e69"}},"created_at":"2022-07-30T13:28:30.000Z","updated_at":"2025-05-04T16:13:23.000Z","dependencies_parsed_at":"2024-01-28T20:24:57.845Z","dependency_job_id":"ce7d2cb6-5cfa-4c4e-a00a-28853b06010f","html_url":"https://github.com/pcaversaccio/snekmate","commit_stats":{"total_commits":909,"total_committers":18,"mean_commits":50.5,"dds":0.06820682068206818,"last_synced_commit":"4d564dfdb626389f7446ceee607c4ea839e829c0"},"previous_names":[],"tags_count":7,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pcaversaccio%2Fsnekmate","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pcaversaccio%2Fsnekmate/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pcaversaccio%2Fsnekmate/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/pcaversaccio%2Fsnekmate/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/pcaversaccio","download_url":"https://codeload.github.com/pcaversaccio/snekmate/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":254190395,"owners_count":22029632,"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":["ethereum","evm","library","security","smart-contracts","vyper","vyper-contracts"],"created_at":"2024-08-01T09:00:29.767Z","updated_at":"2025-05-14T17:09:58.225Z","avatar_url":"https://github.com/pcaversaccio.png","language":"Solidity","funding_links":["https://etherscan.io/address/0xe9Fa0c8B5d7F79DeC36D3F448B1Ac4cEdedE4e69"],"categories":["By Language","Smart Contracts","dApps directory","Starter Kits"],"sub_categories":["Solidity","Vyper","Smart Contract Templates","Smart Contract Starter Kits"],"readme":"# 🐍 snekmate \u003c!-- omit from toc --\u003e\n\n[![🕵️‍♂️ Test smart contracts](https://github.com/pcaversaccio/snekmate/actions/workflows/test-contracts.yml/badge.svg)](https://github.com/pcaversaccio/snekmate/actions/workflows/test-contracts.yml)\n[![License: AGPL-3.0-only](https://img.shields.io/badge/License-AGPL--3.0--only-blue)](https://www.gnu.org/licenses/agpl-3.0)\n[![npm package](https://img.shields.io/npm/v/snekmate.svg?color=blue)](https://www.npmjs.com/package/snekmate)\n[![PyPI package](https://img.shields.io/pypi/v/snekmate?color=blue)](https://pypi.org/project/snekmate)\n\n\u003cimg src=https://github.com/pcaversaccio/snekmate/assets/25297591/a899251b-d22b-4cb3-8109-88facba53d6a width=\"1050\"/\u003e\n\n**State-of-the-art**, **highly opinionated**, **hyper-optimised**, and **secure** 🐍Vyper smart contract building blocks.\n\n\u003e [!WARNING]\n\u003e This is **experimental software** and is provided on an \"as is\" and \"as available\" basis. We **do not give any warranties** and **will not be liable for any losses** incurred through any use of this code base.\n\n- [📜 Contracts](#-contracts)\n- [🎛 Installation](#-installation)\n  - [1️⃣ PyPI](#1️⃣-pypi)\n  - [2️⃣ Foundry](#2️⃣-foundry)\n  - [3️⃣ npm](#3️⃣-npm)\n- [🔧 Usage](#-usage)\n- [👩🏼‍⚖️ Tests](#️-tests)\n- [👮‍♀️ Audits](#️-audits)\n- [🙏🏼 Acknowledgements](#-acknowledgements)\n- [🫡 Contributing](#-contributing)\n- [💸 Donation](#-donation)\n- [📄 Licence](#-licence)\n  - [⚖️ Dual-Licensing Option](#️-dual-licensing-option)\n  - [📩 Requesting an MIT License](#-requesting-an-mit-license)\n- [💢 Disclaimer](#-disclaimer)\n\n## 📜 Contracts\n\n```ml\nsrc\n└── snekmate\n    ├── auth\n    │   ├── ownable — \"Owner-Based Access Control Functions\"\n    │   ├── ownable_2step — \"2-Step Ownership Transfer Functions\"\n    │   ├── access_control — \"Multi-Role-Based Access Control Functions\"\n    │   ├── interfaces\n    │   │   └── IAccessControl — \"AccessControl Interface Definition\"\n    │   └── mocks\n    │       ├── ownable_mock — \"`ownable` Module Reference Implementation\"\n    │       ├── ownable_2step_mock — \"`ownable_2step` Module Reference Implementation\"\n    │       └── access_control_mock — \"`access_control` Module Reference Implementation\"\n    ├── extensions\n    │   ├── erc2981 — \"ERC-721 and ERC-1155 Compatible ERC-2981 Reference Implementation\"\n    │   ├── erc4626 — \"Modern and Gas-Efficient ERC-4626 Tokenised Vault Implementation\"\n    │   ├── interfaces\n    │   │   └── IERC2981 — \"EIP-2981 Interface Definition\"\n    │   └── mocks\n    │       ├── erc2981_mock — \"`erc2981` Module Reference Implementation\"\n    │       └── erc4626_mock — \"`erc4626` Module Reference Implementation\"\n    ├── governance\n    │   ├── timelock_controller — \"Multi-Role-Based Timelock Controller Reference Implementation\"\n    │   └── mocks\n    │       └── timelock_controller_mock — \"`timelock_controller` Module Reference Implementation\"\n    ├── tokens\n    │   ├── erc20 — \"Modern and Gas-Efficient ERC-20 + EIP-2612 Implementation\"\n    │   ├── erc721 — \"Modern and Gas-Efficient ERC-721 + EIP-4494 Implementation\"\n    │   ├── erc1155 — \"Modern and Gas-Efficient ERC-1155 Implementation\"\n    │   ├── interfaces\n    │   │   ├── IERC20Permit — \"EIP-2612 Interface Definition\"\n    │   │   ├── IERC721Enumerable — \"EIP-721 Optional Enumeration Interface Definition\"\n    │   │   ├── IERC721Metadata — \"EIP-721 Optional Metadata Interface Definition\"\n    │   │   ├── IERC721Permit — \"EIP-4494 Interface Definition\"\n    │   │   ├── IERC721Receiver — \"EIP-721 Token Receiver Interface Definition\"\n    │   │   ├── IERC1155 — \"EIP-1155 Interface Definition\"\n    │   │   ├── IERC1155MetadataURI — \"EIP-1155 Optional Metadata Interface Definition\"\n    │   │   ├── IERC1155Receiver — \"EIP-1155 Token Receiver Interface Definition\"\n    │   │   └── IERC4906 — \"EIP-4906 Interface Definition\"\n    │   └── mocks\n    │       ├── erc20_mock — \"`erc20` Module Reference Implementation\"\n    │       ├── erc721_mock — \"`erc721` Module Reference Implementation\"\n    │       └── erc1155_mock — \"`erc1155` Module Reference Implementation\"\n    └── utils\n        ├── base64 — \"Base64 Encoding and Decoding Functions\"\n        ├── batch_distributor — \"Batch Sending Both Native and ERC-20 Tokens\"\n        ├── block_hash — \"Utility Functions to Access Historical Block Hashes\"\n        ├── create_address — \"`CREATE` EVM Opcode Utility Function for Address Calculation\"\n        ├── create2_address — \"`CREATE2` EVM Opcode Utility Functions for Address Calculations\"\n        ├── ecdsa — \"Elliptic Curve Digital Signature Algorithm (ECDSA) Secp256k1-Based Functions\"\n        ├── p256 — \"Elliptic Curve Digital Signature Algorithm (ECDSA) Secp256r1-Based Functions\"\n        ├── message_hash_utils — \"Signature Message Hash Utility Functions\"\n        ├── signature_checker — \"ECDSA and EIP-1271 Signature Verification Functions\"\n        ├── eip712_domain_separator — \"EIP-712 Domain Separator\"\n        ├── math — \"Standard Mathematical Utility Functions\"\n        ├── merkle_proof_verification — \"Merkle Tree Proof Verification Functions\"\n        ├── multicall — \"Multicall Functions\"\n        ├── pausable — \"Pausable Functions\"\n        ├── interfaces\n        │   ├── IERC1271 — \"EIP-1271 Interface Definition\"\n        │   └── IERC5267 — \"EIP-5267 Interface Definition\"\n        └── mocks\n            ├── base64_mock — \"`base64` Module Reference Implementation\"\n            ├── batch_distributor_mock — \"`batch_distributor` Module Reference Implementation\"\n            ├── block_hash_mock — \"`block_hash` Module Reference Implementation\"\n            ├── create_address_mock — \"`create_address` Module Reference Implementation\"\n            ├── create2_address_mock — \"`create2_address` Module Reference Implementation\"\n            ├── ecdsa_mock — \"`ecdsa` Module Reference Implementation\"\n            ├── p256_mock — \"`p256` Module Reference Implementation\"\n            ├── message_hash_utils_mock — \"`message_hash_utils` Module Reference Implementation\"\n            ├── signature_checker_mock — \"`signature_checker` Module Reference Implementation\"\n            ├── eip712_domain_separator_mock — \"`eip712_domain_separator` Module Reference Implementation\"\n            ├── math_mock — \"`math` Module Reference Implementation\"\n            ├── merkle_proof_verification_mock — \"`merkle_proof_verification` Module Reference Implementation\"\n            ├── multicall_mock — \"`multicall` Module Reference Implementation\"\n            └── pausable_mock — \"`pausable` Module Reference Implementation\"\n```\n\n## 🎛 Installation\n\n\u003e [!IMPORTANT]  \n\u003e 🐍 snekmate uses a [ZeroVer](https://0ver.org)-based versioning scheme. This means 🐍 snekmate's major version will never exceed the first and most important number in computing: zero.\n\nWe offer three convenient ways to install the 🐍 snekmate contracts:\n\n### 1️⃣ PyPI\n\nYou can install 🐍 snekmate from [PyPI](https://pypi.org/project/snekmate) with:\n\n```console\npip install snekmate\n```\n\n\u003e When using the 🐍Vyper CLI, the search path [defaults](https://docs.vyperlang.org/en/latest/structure-of-a-contract.html#searching-for-imports) to the current working directory and the Python [`sys.path`](https://docs.python.org/3.13/library/sys.html#sys.path). As a result, all imported 🐍 snekmate contracts (e.g. `from snekmate.tokens import erc20`) are seamlessly located during compilation.\n\n### 2️⃣ Foundry\n\nYou can install 🐍 snekmate via submodules using [Foundry](https://github.com/foundry-rs/foundry) with:\n\n```console\nforge install pcaversaccio/snekmate\n```\n\n\u003e [!NOTE]\n\u003e If you want to leverage 🐍 snekmate's [`VyperDeployer`](./lib/utils/VyperDeployer.sol) contract for your own testing, ensure that you compile the 🐍Vyper contracts with the same EVM version as configured in your `foundry.toml` file. The [`VyperDeployer`](./lib/utils/VyperDeployer.sol) contract offers two overloaded `deployContract` functions that allow the configuration of the target EVM version. Please note that since 🐍Vyper version [`0.4.0`](https://github.com/vyperlang/vyper/releases/tag/v0.4.0) the default EVM version is set to `cancun`. Furthermore, the [`VyperDeployer`](./lib/utils/VyperDeployer.sol) contract relies on the Python script [`compile.py`](./lib/utils/compile.py) for successful compilation and deployment. Always use the [`VyperDeployer`](./lib/utils/VyperDeployer.sol) contract alongside with the aforementioned script.\n\n### 3️⃣ npm\n\nYou can install 🐍 snekmate from [npm](https://www.npmjs.com/package/snekmate) with:\n\n```console\nnpm install --save-dev snekmate\n```\n\nOr if you are using [Yarn](https://yarnpkg.com):\n\n```console\nyarn add --dev snekmate\n```\n\nIn case you are using [pnpm](https://pnpm.io), invoke:\n\n```console\npnpm add --save-dev snekmate\n```\n\n\u003e [!CAUTION]\n\u003e It is possible to install the latest versions of `main` or any other branch locally via `pip install git+https://github.com/pcaversaccio/snekmate.git@\u003cbranch\u003e` or `forge install pcaversaccio/snekmate \u0026\u0026 forge update`. Each branch, **including the `main` branch**, must be understood as a development branch that should be avoided in favour of tagged releases. The release process includes security measures that the repository branches do not guarantee.\n\n## 🔧 Usage\n\n🐍Vyper favours code reuse through composition rather than inheritance (Solidity inheritance makes it easy to break the [Liskov Substitution Principle](https://en.wikipedia.org/wiki/Liskov_substitution_principle)). A 🐍Vyper module encapsulates everything required for code reuse, from type and function declarations to state. **All 🐍 snekmate contracts are 🐍Vyper modules.** Thus, many of the 🐍 snekmate contracts do not compile independently, but you must `import` and `initializes` them. Please note that if a module is _stateless_, it does not require the keyword `initializes` (or `uses`) for initialisation (or usage). Each module contract has an associated mock contract in the `mock/` directory, which is part of the associated contract subdirectory. These mock contracts are very illustrative of how 🐍 snekmate contracts can be used as 🐍Vyper modules.\n\n\u003e [!IMPORTANT]\n\u003e All 🐍 snekmate contracts are very well documented in the form of general code and [NatSpec](https://docs.vyperlang.org/en/latest/natspec.html) comments. There are no shortcuts – if you are importing specific logic, read the documentation!\n\nPlease read [here](https://docs.vyperlang.org/en/latest/using-modules.html) to learn more about using 🐍Vyper modules.\n\n## 👩🏼‍⚖️ Tests\n\nThis repository contains [Foundry](https://github.com/foundry-rs/foundry)-based unit tests, property-based tests (i.e. stateless fuzzing), and invariant tests (i.e. stateful fuzzing) for all contracts, if applicable. All tests are run as part of the CI pipeline [`test-contracts`](./.github/workflows/test-contracts.yml).\n\n\u003e [!NOTE]\n\u003e An _invariant_ is a property of a program that should always hold true. Fuzzing is a way of checking whether the invariant is falsifiable.\n\n| **Contract**                | **Unit Tests** | **Property-Based Tests** | **Invariant Tests** |\n| :-------------------------- | :------------: | :----------------------: | :-----------------: |\n| `ownable`                   |       ✅       |            ✅            |         ✅          |\n| `ownable_2step`             |       ✅       |            ✅            |         ✅          |\n| `access_control`            |       ✅       |            ✅            |         ✅          |\n| `erc2981`                   |       ✅       |            ✅            |         ✅          |\n| `erc4626`                   |       ✅       |            ✅            |         ✅          |\n| `timelock_controller`       |       ✅       |            ✅            |         ✅          |\n| `erc20`                     |       ✅       |            ✅            |         ✅          |\n| `erc721`                    |       ✅       |            ✅            |         ✅          |\n| `erc1155`                   |       ✅       |            ✅            |         ✅          |\n| `base64`                    |       ✅       |            ❌            |         ❌          |\n| `batch_distributor`         |       ✅       |            ✅            |         ✅          |\n| `block_hash`                |       ✅       |            ✅            |         ❌          |\n| `create_address`            |       ✅       |            ✅            |         ❌          |\n| `create2_address`           |       ✅       |            ✅            |         ❌          |\n| `ecdsa`                     |       ✅       |            ✅            |         ❌          |\n| `p256`                      |       ✅       |            ✅            |         ❌          |\n| `message_hash_utils`        |       ✅       |            ✅            |         ❌          |\n| `signature_checker`         |       ✅       |            ✅            |         ❌          |\n| `eip712_domain_separator`   |       ✅       |            ✅            |         ❌          |\n| `math`                      |       ✅       |            ✅            |         ❌          |\n| `merkle_proof_verification` |       ✅       |            ✅            |         ❌          |\n| `multicall`                 |       ✅       |            ❌            |         ❌          |\n| `pausable`                  |       ✅       |            ✅            |         ✅          |\n\n✅ Test Type Implemented \u0026emsp; ❌ Test Type Not Implemented\n\nFurthermore, the [`echidna`](https://github.com/crytic/echidna)-based [property](https://github.com/crytic/properties) tests for the [`erc20`](./src/snekmate/tokens/erc20.vy) and [`erc721`](./src/snekmate/tokens/erc721.vy) contracts are available in the [`test/tokens/echidna/`](./test/tokens/echidna) directory. You can run the tests by invoking:\n\n```console\n# Run Echidna ERC-20 property tests.\n~$ FOUNDRY_PROFILE=echidna echidna test/tokens/echidna/ERC20Properties.sol --contract CryticERC20ExternalHarness --config test/echidna.yaml\n\n# Run Echidna ERC-721 property tests.\n~$ FOUNDRY_PROFILE=echidna echidna test/tokens/echidna/ERC721Properties.sol --contract CryticERC721ExternalHarness --config test/echidna.yaml\n```\n\nEventually, the [`halmos`](https://github.com/a16z/halmos)-based symbolic tests for the [`erc20`](./src/snekmate/tokens/erc20.vy), [`erc721`](./src/snekmate/tokens/erc721.vy), [`erc1155`](./src/snekmate/tokens/erc1155.vy), and [`math`](./src/snekmate/utils/math.vy) contracts are available in the [`test/tokens/halmos/`](./test/tokens/halmos) and [`test/utils/halmos/`](./test/utils/halmos) directories. You can run the tests by invoking:\n\n\u003e [!IMPORTANT]\n\u003e You must install the [Yices 2 SMT solver](https://github.com/SRI-CSL/yices2) before invoking the [`halmos`](https://github.com/a16z/halmos)-based symbolic tests.\n\n```console\n# Run Halmos ERC-20 symbolic tests.\n~$ FOUNDRY_PROFILE=halmos halmos --contract ERC20TestHalmos --config test/halmos.toml\n\n# Run Halmos ERC-721 symbolic tests. Be careful, this is a (very!) time-consuming operation.\n~$ FOUNDRY_PROFILE=halmos halmos --contract ERC721TestHalmos --config test/halmos.toml\n\n# Run Halmos ERC-1155 symbolic tests. Be careful, this is a (very!) time-consuming operation.\n~$ FOUNDRY_PROFILE=halmos halmos --contract ERC1155TestHalmos --config test/halmos.toml\n\n# Run Halmos math symbolic tests.\n~$ FOUNDRY_PROFILE=halmos halmos --contract MathTestHalmos --config test/halmos.toml\n```\n\n\u003e [!TIP]\n\u003e If you encounter any issues, please ensure that you have the [latest](https://github.com/vyperlang/vyper/releases) 🐍Vyper version installed locally.\n\n## 👮‍♀️ Audits\n\nAlthough the 🐍 snekmate contracts have not (yet) undergone a full comprehensive audit, selected library modules integrated into specific protocols (such as Curve) have been thoroughly reviewed within the scope of prior audits. The corresponding audit reports are available [here](./audits).\n\n## 🙏🏼 Acknowledgements\n\nThis repository is inspired by or directly modified from many sources, primarily:\n\n- [ApeAcademy](https://github.com/ApeAcademy)\n- [Batch Distributor](https://github.com/pcaversaccio/batch-distributor)\n- [`CREATE` Factory](https://github.com/pcaversaccio/create-util)\n- [Disperse Research](https://github.com/banteg/disperse-research)\n- [Multicall](https://github.com/mds1/multicall)\n- [OpenZeppelin Contracts](https://github.com/OpenZeppelin/openzeppelin-contracts)\n- [Solady](https://github.com/Vectorized/solady)\n- [Solmate](https://github.com/transmissions11/solmate)\n\n## 🫡 Contributing\n\n🐍 snekmate only exists thanks to its [contributors](https://github.com/pcaversaccio/snekmate/graphs/contributors). There are many ways to get involved and contribute to our high-quality and secure smart contracts. Check out our [Contribution Guidelines](./CONTRIBUTING.md)!\n\n## 💸 Donation\n\nI am a strong advocate of the open-source and free software paradigm. However, if you feel my work deserves a donation, you can send it to this address: [`0xe9Fa0c8B5d7F79DeC36D3F448B1Ac4cEdedE4e69`](https://etherscan.io/address/0xe9Fa0c8B5d7F79DeC36D3F448B1Ac4cEdedE4e69). I can pledge that I will use this money to help fix more existing challenges in the Ethereum ecosystem 🤝.\n\n## 📄 Licence\n\nThis software is released under the [GNU Affero General Public License v3.0 only](./LICENSE) (AGPL-3.0-only) **by default**.\n\nWe believe in fostering a collaborative and open ecosystem. The [AGPL-3.0-only](./LICENSE) licence keeps the code free, the knowledge shared, and the doors open. It stands as a quiet rebellion against control, a promise that what is built in the open will remain in the open, owned by no one and available to all.\n\n### ⚖️ Dual-Licensing Option\n\nWe understand that [AGPL-3.0-only](./LICENSE)-licensed software may not be suitable for all use cases, particularly in cases involving:\n\n- Proprietary or closed-source projects,\n- Licence incompatibilities, or\n- Commercial applications with conflicting requirements.\n\nFor such scenarios, we offer an alternative licence under the [MIT License](https://opensource.org/license/mit), granted at our sole discretion.\n\n### 📩 Requesting an MIT License\n\nIf you have **substantial** reasons for requiring a more permissive licence, such as those outlined above, feel free to contact us via [email](mailto:pascal.caversaccio@hotmail.ch) to request access to the software under the [MIT License](https://opensource.org/license/mit).\n\nEach request is evaluated on a case-by-case basis, and we will provide the [MIT License](https://opensource.org/license/mit) if deemed appropriate.\n\n## 💢 Disclaimer\n\n\u003cimg src=https://user-images.githubusercontent.com/25297591/167394075-1813e258-3b03-4bc8-9305-69126a07d57e.png width=\"1050\"/\u003e\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpcaversaccio%2Fsnekmate","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fpcaversaccio%2Fsnekmate","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpcaversaccio%2Fsnekmate/lists"}