{"id":29436126,"url":"https://github.com/Enigma-Dark/runes","last_synced_at":"2025-07-13T05:02:43.613Z","repository":{"id":298596268,"uuid":"992830591","full_name":"Enigma-Dark/runes","owner":"Enigma-Dark","description":"A CLI tool that converts Echidna fuzzer reproducer .txt files into executable Foundry test files.","archived":false,"fork":false,"pushed_at":"2025-06-22T01:16:27.000Z","size":156,"stargazers_count":7,"open_issues_count":0,"forks_count":1,"subscribers_count":0,"default_branch":"main","last_synced_at":"2025-06-22T02:26:59.600Z","etag":null,"topics":["developer-tools","echidna","ethereum","foundry","fuzzing"],"latest_commit_sha":null,"homepage":"https://enigmadark.com","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Enigma-Dark.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2025-05-29T19:27:50.000Z","updated_at":"2025-06-22T01:12:34.000Z","dependencies_parsed_at":"2025-06-11T23:29:48.822Z","dependency_job_id":"c75b9840-2162-4c0d-9cfd-b9625c87e7bd","html_url":"https://github.com/Enigma-Dark/runes","commit_stats":null,"previous_names":["enigma-dark/runes"],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/Enigma-Dark/runes","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Enigma-Dark%2Frunes","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Enigma-Dark%2Frunes/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Enigma-Dark%2Frunes/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Enigma-Dark%2Frunes/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Enigma-Dark","download_url":"https://codeload.github.com/Enigma-Dark/runes/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Enigma-Dark%2Frunes/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":265091733,"owners_count":23710033,"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":["developer-tools","echidna","ethereum","foundry","fuzzing"],"created_at":"2025-07-13T05:01:22.912Z","updated_at":"2025-07-13T05:02:43.586Z","avatar_url":"https://github.com/Enigma-Dark.png","language":"Go","funding_links":[],"categories":["Tooling"],"sub_categories":["Utils"],"readme":"\u003cp\u003e\n  \u003cimg src=\"assets/logo.png\" width=\"150\" /\u003e\n\u003c/p\u003e\n\n# Runes\n\nA CLI tool that converts Echidna fuzzer reproducer files to executable Foundry test files.\n\n## Overview\n\nEchidna generates reproducer files in JSON format when it finds bugs or property violations. This tool parses those reproducer files and generates corresponding Foundry test files that can be executed with `forge test` to reproduce the exact same sequence of function calls.\n\n## Features\n\n- **JSON Parsing**: Parses Echidna reproducer files with complex ABI parameter encoding\n- **Type Conversion**: Converts ABI types (AbiUInt, AbiInt, AbiBool, etc.) to proper Solidity types\n- **Template Generation**: Uses Go templates to generate clean, readable Foundry test files\n- **CLI Interface**: Simple command-line interface with sensible defaults\n- **Directory Support**: Automatically finds and uses the oldest .txt file when given a directory\n- **Actor Management**: Generates `_setUpActor()` calls for different users\n- **Time Delays**: Includes `_delay()` calls for time-based testing\n- **Configurable Output**: Customize contract names, test function names, and output paths\n\n## Installation\n\n### Prerequisites\n\n- Go 1.21 or higher\n\n### Install with Go\n\n```bash\ngo install github.com/Enigma-Dark/runes@latest\n```\n\n### Build from source\n\n```bash\ngit clone https://github.com/Enigma-Dark/runes.git\ncd runes\ngo mod tidy\nmake build\n```\n\nThe binary will be available at `build/runes`.\n\n## Usage\n\n### Basic Usage\n\nConvert an Echidna reproducer file to a Foundry test:\n\n```bash\n./runes convert reproducer.txt\n```\n\nConvert all reproducer files in a directory (automatically selects oldest):\n\n```bash\n./runes convert /path/to/reproducers/\n```\n\n### Advanced Usage\n\nCustomize the output:\n\n```bash\n./runes convert reproducer.txt \\\n  --output MyTest.t.sol \\\n  --contract MyTestContract \\\n  --test testBugReproduction\n```\n\n### Command-line Options\n\n- `--output, -o`: Output file path (default: `[input-name]_replay.t.sol`)\n- `--contract, -c`: Contract name (default: `[input-name]Replay`)\n- `--test, -t`: Test function name (default: `testReplay`)\n- `--config`: Config file (default: `$HOME/.runes.yaml`)\n\n## Input Format\n\nThe tool accepts:\n1. **Single file**: A specific .txt reproducer file\n2. **Directory**: A folder containing .txt files (automatically selects the oldest)\n\nEchidna reproducer files are in JSON format and contain an array of transaction objects:\n\n```json\n[\n  {\n    \"call\": {\n      \"contents\": [\n        \"deposit\",\n        [\n          {\"contents\": [256, \"3625\"], \"tag\": \"AbiUInt\"},\n          {\"contents\": [8, \"0\"], \"tag\": \"AbiUInt\"}\n        ]\n      ],\n      \"tag\": \"SolCall\"\n    },\n    \"dst\": \"0x7FA9385bE102ac3EAc297483Dd6233D62b3e1496\",\n    \"delay\": [\"0x0000000000000000000000000000000000000000000000000000000000000000\", \"0x0000000000000000000000000000000000000000000000000000000000000000\"],\n    \"gas\": 1000000000,\n    \"value\": \"0x0000000000000000000000000000000000000000000000000000000000000000\"\n  }\n]\n```\n\n## Output Format\n\nThe tool generates clean, readable Foundry test files in the style of modern property-based testing:\n\n```solidity\n// SPDX-License-Identifier: MIT\npragma solidity ^0.8.0;\n\nimport {Test} from \"forge-std/Test.sol\";\n\ncontract TestReplay is Test {\n    // Actor addresses (adjust these to match your test setup)\n    address constant USER1 = 0x0000000000000000000000000000000000010000;\n    address constant USER2 = 0x0000000000000000000000000000000000020000;\n    address constant USER3 = 0x0000000000000000000000000000000000030000;\n    \n    // TODO: Replace with your actual contract instance\n    // YourContract Tester;\n    \n    function setUp() public {\n        // TODO: Initialize your contract here\n        // Tester = new YourContract();\n    }\n    \n    function test_replay() public {\n        _setUpActor(USER1);\n        _delay(2);\n        Tester.deposit(3625, 0, 1);\n        _setUpActor(USER3);\n        _delay(840);\n        Tester.donateEulerOnlyEVaultToTargetEVault(109, 1, 11);\n        Tester.setPrice(1, 0);\n        Tester.borrowCV(115792089237316195423570985008687907853269984665640564039457584007913129639935, 0);\n    }\n    \n    function _setUpActor(address actor) internal {\n        vm.startPrank(actor);\n        // Add any additional actor setup here if needed\n    }\n    \n    function _delay(uint256 timeInSeconds) internal {\n        vm.warp(block.timestamp + timeInSeconds);\n    }\n}\n```\n\n## Supported ABI Types\n\n- `AbiUInt` - Unsigned integers (uint8, uint16, uint256, etc.)\n- `AbiInt` - Signed integers (int8, int16, int256, etc.)\n- `AbiAddress` - Ethereum addresses\n- `AbiBool` - Boolean values (supports both array and direct boolean formats)\n- `AbiBytes` - Fixed and dynamic byte arrays\n- `AbiString` - String values\n\n## Examples\n\n### Example 1: Single File Conversion\n\n```bash\n./runes convert reproducer.txt\n```\n\nOutput: `reproducer_replay.t.sol`\n\n### Example 2: Directory Processing\n\n```bash\n./runes convert /path/to/reproducers/\n```\n\nAutomatically finds the oldest .txt file and converts it.\n\n### Example 3: Custom Output\n\n```bash\n./runes convert reproducer.txt \\\n  --output BugReproduction.t.sol \\\n  --contract BugReproduction \\\n  --test test_reproduce_bug\n```\n\n## Directory Processing\n\nWhen you provide a directory path:\n\n1. **Scans for .txt files**: Finds all .txt files in the directory\n2. **Selects oldest**: Automatically selects the file with the oldest modification time\n3. **Processes**: Converts the selected file to a Foundry test\n\nThis is particularly useful when working with Echidna corpus directories that contain multiple reproducer files.\n\n## Development\n\n### Project Structure\n\n```\nrunes/\n├── cmd/                 # CLI commands (cobra)\n│   ├── root.go         # Root command setup\n│   └── convert.go      # Convert command implementation\n├── internal/\n│   ├── types/          # Type definitions\n│   ├── parser/         # JSON parsing logic\n│   └── generator/      # Test file generation\n├── main.go             # Entry point\n├── go.mod              # Go module definition\n└── README.md           # This file\n```\n\n### Running Tests\n\n```bash\ngo test ./...\n```\n\n### Contributing\n\nSee [CONTRIBUTING.md](CONTRIBUTING.md) for detailed guidelines.\n\n### Testing\n\n```bash\nmake test          # Run all tests\nmake test-verbose  # Run tests with verbose output\n```\n\n## TODO \u0026 Roadmap\n\n### Near-term improvements\n- [ ] Add example reproducer files in `/examples`\n- [ ] Support for more ABI types (AbiArray, AbiTuple)\n- [ ] Better error messages with line numbers\n\n### Future enhancements\n- [ ] Support for multi-file test generation\n- [ ] Integration with more fuzzing tools, like [Medusa](https://github.com/crytic/medusa)\n\n### Known limitations\n- Complex nested ABI types may need manual adjustment\n- Generated tests require manual contract initialization\n\n## License\n\nMIT License - see [LICENSE](LICENSE) file for details. ","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FEnigma-Dark%2Frunes","html_url":"https://awesome.ecosyste.ms/projects/github.com%2FEnigma-Dark%2Frunes","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FEnigma-Dark%2Frunes/lists"}