Skip to content

Commit 39777c1

Browse files
committed
blocklock agent
0 parents  commit 39777c1

File tree

2,268 files changed

+428072
-0
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

2,268 files changed

+428072
-0
lines changed

.dockerignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
node_modules
2+
**/node_modules
3+
out
Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
name: build-and-push
2+
on:
3+
push:
4+
branches:
5+
# all branches, docker image is only pushed on main
6+
- "*"
7+
tags:
8+
- 'v[0-9]+.[0-9]+.[0-9]+*'
9+
pull_request:
10+
11+
env:
12+
SERVICE_ACCOUNT: [email protected]
13+
DOCKER_REGISTRY: europe-west1-docker.pkg.dev/randamu-prod/candyland
14+
IMAGE_MAINTAINER: "Randamu"
15+
IMAGE_VENDOR: "Randamu"
16+
17+
jobs:
18+
build-and-push:
19+
runs-on: "ubuntu-latest"
20+
steps:
21+
- name: Checkout code
22+
uses: actions/checkout@v4
23+
with:
24+
fetch-depth: 0
25+
submodules: 'true'
26+
27+
- name: Update submodules
28+
run: git submodule update --init --recursive --remote
29+
30+
- name: Set up Node.js
31+
uses: actions/setup-node@v4
32+
with:
33+
node-version: '>=22.5.0'
34+
35+
- name: Login to Artifact Registry
36+
uses: docker/login-action@v3
37+
with:
38+
registry: europe-west1-docker.pkg.dev
39+
username: _json_key
40+
password: ${{ secrets.GCP_SERVICE_ACCOUNT_TOKEN }}
41+
42+
- name: Install
43+
run: npm install && npm install -g yarn
44+
45+
- name: Install Foundry
46+
uses: foundry-rs/foundry-toolchain@v1
47+
48+
- name: Build
49+
run: yarn build
50+
51+
- name: Docker meta
52+
id: meta
53+
uses: docker/metadata-action@v5
54+
with:
55+
images: ${{ env.DOCKER_REGISTRY }}/blocklock-agent
56+
labels: |
57+
maintainer=${{ env.IMAGE_MAINTAINER }}
58+
org.opencontainers.image.title=blocklock-agent
59+
org.opencontainers.image.description="an agent for uploading signatures to blockchains"
60+
org.opencontainers.image.vendor=${{ env.IMAGE_VENDOR }}
61+
flavor: |
62+
latest=false
63+
prefix=
64+
suffix=
65+
tags: |
66+
type=sha,prefix=
67+
type=ref,event=branch,suffix=-latest,enable=${{ startsWith(github.ref, 'refs/heads/') }}
68+
type=semver,pattern={{version}},event=tag,enable=${{ startsWith(github.ref, 'refs/tags/') }}
69+
70+
- name: Set up Docker Buildx
71+
uses: docker/setup-buildx-action@v3
72+
with:
73+
# this might not work at all, but might work and
74+
# allow us to bypass dockerhub ratelimit
75+
buildkitd-config-inline: |
76+
[registry."docker.io"]
77+
mirrors = ["mirror.gcr.io"]
78+
## this does work to avoid the dockerhub ratelimit
79+
driver-opts: |
80+
image=mirror.gcr.io/moby/buildkit:buildx-stable-1
81+
network=host
82+
83+
- id: docker-push-tagged
84+
name: Tag Docker image and push to Google Artifact Registry
85+
uses: docker/build-push-action@v6
86+
with:
87+
push: ${{ github.ref == 'refs/heads/main' }}
88+
tags: ${{ steps.meta.outputs.tags }}
89+
labels: ${{ steps.meta.outputs.labels }}
90+
cache-from: |
91+
type=registry,ref=${{ env.DOCKER_REGISTRY }}/blocklock-agent-cache:${{ steps.meta.outputs.version }}
92+
type=registry,ref=${{ env.DOCKER_REGISTRY }}/blocklock-agent-cache:main-latest
93+
cache-to: type=registry,ref=${{ env.DOCKER_REGISTRY }}/blocklock-agent-cache:${{ steps.meta.outputs.version }},mode=max
94+

.gitignore

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
index.js
2+
index.cjs
3+
index.d.ts
4+
src/generated/**
5+
node_modules
6+
state.json

.gitmodules

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
[submodule "blocklock-solidity"]
2+
path = blocklock-solidity
3+
url = https://github.com/randa-mu/blocklock-solidity.git

Dockerfile

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
# Set ARG for Node.js version
2+
ARG ARCH=linux/amd64
3+
ARG NODE_VERSION=22.3
4+
5+
# TODO: install foundry on our node images
6+
FROM --platform=${ARCH} node:${NODE_VERSION} AS node
7+
8+
FROM --platform=${ARCH} ghcr.io/foundry-rs/foundry:latest AS build
9+
10+
# foundry recently changed their dockerfile permissions so we need this to build now
11+
USER root
12+
13+
# we copy the bin from the node image to foundry (which uses alpine)
14+
COPY --from=node /usr/lib /usr/lib
15+
COPY --from=node /usr/local/lib /usr/local/lib
16+
COPY --from=node /usr/local/include /usr/local/include
17+
COPY --from=node /usr/local/bin /usr/local/bin
18+
19+
WORKDIR /app
20+
21+
COPY . .
22+
23+
RUN npm install
24+
RUN npm run build
25+
26+
FROM --platform=${ARCH} node:${NODE_VERSION} AS runner
27+
# Define the command to run the application
28+
WORKDIR /app
29+
COPY --from=build /app/index.cjs .
30+
CMD ["node", "/app/index.cjs"]

LICENSE

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
MIT License
2+
3+
Copyright (c) 2025 Randamu
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is
10+
furnished to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21+
SOFTWARE.

README.md

Lines changed: 122 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,122 @@
1+
## @randamu/blocklock-agent
2+
3+
The `blocklock-agent` is a blockchain-based timelock decryption and signature agent leveraging BLS signatures and blocklock mechanisms on the Ethereum-compatible Filecoin network. This agent listens for decryption requests and processes them based on predefined conditions.
4+
5+
### Features
6+
7+
- **Event Listener**: Listens for `DecryptionRequested` events from the `DecryptionSender` smart contract.
8+
- **BLS Cryptography**: Utilizes BLS signatures for secure and efficient cryptographic operations.
9+
- **IBE Decryption**: Implements identity-based encryption (IBE) to handle requests securely.
10+
- **Health Check**: Provides an HTTP health-check endpoint.
11+
- **Event Replay**: Replays past unfulfilled decryption requests upon startup.
12+
13+
### Requirements
14+
15+
- Node.js version 16+.
16+
- An Ethereum-compatible blockchain node (e.g., Filecoin calibration network).
17+
- Access to the deployed `DecryptionSender` contract address.
18+
19+
### Installation
20+
21+
1. Clone the repository:
22+
```bash
23+
git clone <repository-url>
24+
cd blocklock-agent
25+
```
26+
27+
2. Install dependencies:
28+
```bash
29+
npm install
30+
```
31+
32+
### Configuration
33+
34+
The agent can be configured using command-line arguments, environment variables, or a combination of both. Below are the available options:
35+
36+
| Option | Default Value | Environment Variable | Description |
37+
|--------------------------|-----------------------------------------------|------------------------------------------------|--------------------------------------------------------------------------------------------------------------------|
38+
| `--port` | `8080` | `BLOCKLOCK_PORT` | The port to host the health-check HTTP server. |
39+
| `--rpc-url` | `https://api.calibration.node.glif.io/rpc/v1` | `BLOCKLOCK_RPC_URL` | Blockchain RPC URL. |
40+
| `--private-key` | `<Default Private Key>` | `BLOCKLOCK_PRIVATE_KEY` | Private key for transaction signing. |
41+
| `--bls-key` | `<Default BLS Key>` | `BLOCKLOCK_BLS_PRIVATE_KEY` | BLS private key for signing. |
42+
| `--decryptionSenderAddr` | `<Deployed Contract Address>` | `BLOCKLOCK_DECRYPTION_SENDER_CONTRACT_ADDRESS` | Address of the deployed `DecryptionSender` contract. |
43+
| `--state-path` | `./state.json` | `BLOCKLOCK_STATE_PATH` | A JSON file containing the `chainHeight` at which to start processing events. Empty will start from current block. |
44+
| `--polling-interval` | 1000 | `BLOCKLOCK_POLLING_INTERVAL` | How frequently in milliseconds to call the RPC for the latest events/state. |
45+
| `--log-level` | info | `BLOCKLOCK_LOG_LEVEL` | The logging level for structured JSON logging. Can be "info", "debug", "error", or "trace". |
46+
47+
### Usage
48+
49+
To start the `blocklock-agent`, run the following command:
50+
51+
```bash
52+
npm run start [options]
53+
```
54+
55+
For example, to specify a custom RPC URL and state file, run:
56+
57+
```bash
58+
npm run start --rpc-url http://localhost:8545 --state-file /home/cooluser/state.json
59+
```
60+
61+
The agent will store its state periodically to the provided state file. If a state file doesn't exist, it will start from the current chain height.
62+
If you wish to bootstrap it with a custom state file, an example format is the following:
63+
```{ "chainHeight": 123456 }```
64+
65+
### How It Works
66+
67+
1. **Initialization**:
68+
- Connects to the specified RPC URL.
69+
- Configures the agent with the provided private and BLS keys.
70+
- Loads the state file to determine which chain height to start from,
71+
- Retrieves past `DecryptionRequested` events from the `chainHeight` specified in the state file
72+
- Listens for future `DecryptionRequested` events
73+
74+
2. **Event Processing**:
75+
- For each `DecryptionRequested` event:
76+
- Verifies the scheme ID (`BN254-BLS-BLOCKLOCK`).
77+
- Computes the BLS signature for the request condition.
78+
- Processes the ciphertext and fulfills the request via the `DecryptionSender` contract.
79+
80+
3. **Health Check**:
81+
- Hosts a lightweight HTTP server on the configured port to indicate the agent's health.
82+
83+
4. **Keep Alive**:
84+
- The agent remains active, continuously listening for new events and processing them in real-time.
85+
86+
### Development
87+
88+
#### Scripts
89+
90+
- Build the project:
91+
```bash
92+
npm run build
93+
```
94+
95+
### Directory Structure
96+
97+
- **`crypto/`**: Contains cryptographic implementations (BLS and IBE).
98+
- **`generated/`**: Auto-generated smart contract TypeScript bindings / factories and type definitions.
99+
- **`provider.ts`**: Utilities for blockchain provider creation and retry logic.
100+
- **`index.ts`**: Entry point of the application.
101+
102+
### Testing
103+
104+
To test the agent, you can simulate `DecryptionRequested` events on a local blockchain, e.g., [Anvil](https://book.getfoundry.sh/reference/anvil/).
105+
Note that the required smart contracts will need to be deployed on the local chain, i.e., DecryptionSender, BlocklockSender and the user contract from where the on-chain timelock encryption / decryption requests will be made.
106+
See the [blocklock-solidity repository](github.com/randa-mu/blocklock-solidity.git) for more.
107+
108+
### Troubleshooting
109+
110+
- **Error: `missing revert data`**:
111+
Ensure the contract address, private key, and RPC URL are correctly configured. Ensure that the Ciphertext is correctly generated. There's an example [here](github.com/randa-mu/blocklock-solidity/blob/main/scripts/chain-interaction.ts)
112+
113+
- **Unhandled Exception**:
114+
Check the blockchain node for connectivity issues or misconfigured start block.
115+
116+
### Contributing
117+
118+
Contributions are welcome! Please submit issues or pull requests to improve the project.
119+
120+
### License
121+
122+
This project is licensed under the MIT License. See the [LICENSE](LICENSE) file for details.

blocklock-solidity/.env.example

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# Private key for contract deployment and interaction
2+
PRIVATE_KEY=
3+
4+
# RPC
5+
RPC_URL=
6+
7+
# Threshold network BLS Point G2 public key x and y coordinates (all uints) used to construct the public key as a G2 point
8+
BLS_PUBLIC_KEY_X0=
9+
BLS_PUBLIC_KEY_X1=
10+
BLS_PUBLIC_KEY_Y0=
11+
BLS_PUBLIC_KEY_Y1=
12+
13+
# Contract upgrades
14+
IS_UPGRADE=
15+
16+
# Contract verification
17+
ETHERSCAN_API_KEY=
18+
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
name: Foundry
2+
3+
on:
4+
push:
5+
pull_request:
6+
workflow_dispatch:
7+
8+
jobs:
9+
check:
10+
strategy:
11+
fail-fast: true
12+
13+
name: Foundry project
14+
runs-on: ubuntu-latest
15+
16+
steps:
17+
- uses: actions/checkout@v4
18+
with:
19+
submodules: recursive
20+
21+
- name: Install Foundry
22+
uses: foundry-rs/foundry-toolchain@v1
23+
24+
- name: Install hardhat
25+
run: |
26+
yarn add --dev hardhat
27+
id: hardhat-install
28+
29+
- name: Show Forge version
30+
run: |
31+
forge --version
32+
33+
- name: Run Forge fmt
34+
run: |
35+
forge fmt --check
36+
id: fmt
37+
38+
- name: Run Forge build
39+
run: |
40+
forge build --force --skip test --sizes
41+
id: build
42+
43+
- name: Run Forge tests
44+
run: |
45+
FOUNDRY_PROFILE=test forge test --gas-report
46+
id: forge-test
47+
48+
- name: Run foundry coverage
49+
run: FOUNDRY_PROFILE=coverage forge coverage --report summary
50+
51+
- name: Run Hardhat tests
52+
run: |
53+
npx hardhat test
54+
id: hardhat-test

0 commit comments

Comments
 (0)