Skip to content

Commit

Permalink
WIP cli (#21)
Browse files Browse the repository at this point in the history
  • Loading branch information
Dzejkop authored Oct 4, 2024
1 parent a81cea7 commit a73c198
Show file tree
Hide file tree
Showing 16 changed files with 1,911 additions and 747 deletions.
1,955 changes: 1,433 additions & 522 deletions world-chain-builder/Cargo.lock

Large diffs are not rendered by default.

26 changes: 16 additions & 10 deletions world-chain-builder/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,9 @@ edition = "2021"

default-run = "world-chain-builder"

[workspace]
members = ["crates/*"]

[dependencies]
# reth
reth-primitives = { git = "https://github.com/ewoolsey/reth", rev = "b2848f", features = [
Expand Down Expand Up @@ -67,19 +70,24 @@ alloy-rpc-types = "0.3"
alloy-rlp = "0.3"
alloy-eips = "0.3"

# other
revm = "14"
# revm
revm = "=14.0.2"
revm-interpreter = "=10.0.2"
revm-inspectors = "=0.7.4"
revm-precompile = "=11.0.2"
revm-primitives = { version = "=9.0.2", default-features = false, features = [
"std",
] }

# 3rd party
tokio = { version = "1", features = ["full"] }
futures = "0.3"
chrono = "0.4"
thiserror = "1"
strum = "0.26"
strum_macros = "0.26"
bytemuck = "1"
revm-primitives = { version = "9.0.0", default-features = false, features = [
"std",
] }
semaphore = { git = "https://github.com/worldcoin/semaphore-rs", rev = "f44b7934", features = [
semaphore = { git = "https://github.com/worldcoin/semaphore-rs", rev = "d0d1f899add7116ccc1228f5e5e5ee2e2e233768", features = [
"depth_30",
] }
clap = { version = "4", features = ["derive", "env"] }
Expand All @@ -90,6 +98,8 @@ parking_lot = "0.12"
derive_more = "1"
dotenvy = "0.15.7"
tikv-jemallocator = { version = "0.6.0", optional = true }
bytes = "1.7.2"
hex = "0.4.3"

[dev-dependencies]
tempfile = "3"
Expand All @@ -114,7 +124,3 @@ jemalloc = ["tikv-jemallocator"]
[[bin]]
name = "world-chain-builder"
path = "bin/world-chain-builder.rs"

[[bin]]
name = "toolkit"
path = "bin/toolkit.rs"
28 changes: 0 additions & 28 deletions world-chain-builder/bin/toolkit.rs

This file was deleted.

27 changes: 27 additions & 0 deletions world-chain-builder/crates/toolkit/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
[package]
name = "toolkit"
version = "0.1.0"
edition = "2021"

[dependencies]
semaphore = { git = "https://github.com/worldcoin/semaphore-rs", rev = "d0d1f899add7116ccc1228f5e5e5ee2e2e233768", features = [
"depth_30",
] }
world-chain-builder = { path = "../.." }

# Alloy
alloy-consensus = "0.3"
alloy-network = "0.3"
alloy-primitives = "0.8"
alloy-rlp = "0.3"

# 3rd party
bytes = "1.7.2"
clap = { version = "4", features = ["derive", "env"] }
eyre = { version = "0.6", package = "color-eyre" }
hex = "0.4.3"
serde = { version = "1", features = ["derive"] }
serde_json = "1.0"
tokio = { version = "1", features = ["full"] }
dotenvy = "0.15.7"
chrono = "0.4"
55 changes: 55 additions & 0 deletions world-chain-builder/crates/toolkit/src/cli.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
use bytes::{Bytes, BytesMut};
use chrono::NaiveDate;
use clap::Parser;
use identity_source::IdentitySource;
use inclusion_proof_source::InclusionProofSource;

pub mod identity_source;
pub mod inclusion_proof_source;
mod utils;

#[derive(Debug, Clone, Parser)]
pub struct Opt {
#[clap(subcommand)]
pub cmd: Cmd,
}

#[derive(Debug, Clone, Parser)]
pub enum Cmd {
Prove(ProveArgs),

Send(SendArgs),
}

#[derive(Debug, Clone, Parser)]
pub struct ProveArgs {
/// Raw tx
///
/// can be constructed with `cast mktx`
#[clap(short, long)]
#[clap(value_parser = utils::bytes_parse_hex)]
pub tx: Bytes,

/// The PBH nonce for the priority tx
///
/// should be in range 0-30 otherwise the tx will be discarded as invalid
#[clap(short = 'N', long)]
#[clap(alias = "nonce")]
pub pbh_nonce: u16,

/// Overrides the current date for PBH proof generation
/// Format: "YYYY-MM-DD"
///
/// Dates are always assumed to be in UTC
#[clap(short = 'D', long)]
pub custom_date: Option<NaiveDate>,

#[command(flatten)]
pub identity_source: IdentitySource,

#[command(flatten)]
pub inclusion_proof_source: InclusionProofSource,
}

#[derive(Debug, Clone, Parser)]
pub struct SendArgs {}
43 changes: 43 additions & 0 deletions world-chain-builder/crates/toolkit/src/cli/identity_source.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
use std::path::PathBuf;

use bytes::BytesMut;
use clap::Args;
use semaphore::identity::Identity;

use super::utils::bytes_mut_parse_hex;

#[derive(Debug, Clone, Args)]
pub struct IdentitySource {
/// Hex encoded identity secret
#[clap(
short = 'I',
long,
conflicts_with = "identity_file",
required_unless_present = "identity_file",
value_parser = bytes_mut_parse_hex
)]
pub identity: Option<BytesMut>,

/// Path to a file containing the identity secret
#[clap(
long,
conflicts_with = "identity",
required_unless_present = "identity"
)]
pub identity_file: Option<PathBuf>,
}

impl IdentitySource {
pub fn load(&self) -> Identity {
if let Some(mut identity) = self.identity.clone() {
return Identity::from_secret(identity.as_mut(), None);
}

if let Some(identity_file) = &self.identity_file {
let mut identity = std::fs::read(identity_file).unwrap();
return Identity::from_secret(identity.as_mut(), None);
}

unreachable!()
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
use std::path::PathBuf;

use clap::Args;
use semaphore::poseidon_tree::Proof;

use super::utils::parse_from_json;

#[derive(Debug, Clone, Args)]
pub struct InclusionProofSource {
/// Inclusion proof in JSON format
#[clap(
short = 'P',
long,
value_parser = parse_from_json::<Proof>,
conflicts_with = "inclusion_proof_file",
required_unless_present = "inclusion_proof_file"
)]
pub inclusion_proof: Option<Proof>,

#[clap(
long,
conflicts_with = "inclusion_proof",
required_unless_present = "inclusion_proof"
)]
pub inclusion_proof_file: Option<PathBuf>,

// TODO: Add fetching from signup-sequencer/world-tree
// TODO: Add fetching from smart contract via RPC
}

impl InclusionProofSource {
pub fn load(&self) -> Proof {
if let Some(inclusion_proof) = self.inclusion_proof.clone() {
return inclusion_proof;
}

if let Some(inclusion_proof_file) = &self.inclusion_proof_file {
let inclusion_proof = std::fs::read(inclusion_proof_file).unwrap();
return serde_json::from_slice(&inclusion_proof).unwrap();
}

unreachable!()
}
}
21 changes: 21 additions & 0 deletions world-chain-builder/crates/toolkit/src/cli/utils.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
use bytes::{Bytes, BytesMut};
use serde::de::DeserializeOwned;

pub fn bytes_mut_parse_hex(s: &str) -> eyre::Result<BytesMut> {
Ok(BytesMut::from(
&hex::decode(s.trim_start_matches("0x"))?[..],
))
}

pub fn bytes_parse_hex(s: &str) -> eyre::Result<Bytes> {
Ok(Bytes::from(
hex::decode(s.trim_start_matches("0x"))?,
))
}

pub fn parse_from_json<'a, T>(s: &'a str) -> eyre::Result<T>
where
T: DeserializeOwned,
{
Ok(serde_json::from_str(s)?)
}
48 changes: 48 additions & 0 deletions world-chain-builder/crates/toolkit/src/main.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
use alloy_consensus::TxEnvelope;
use alloy_rlp::Decodable;
use clap::Parser;
use cli::{Cmd, Opt};
use semaphore::hash_to_field;
use world_chain_builder::date_marker::DateMarker;
use world_chain_builder::external_nullifier::ExternalNullifier;

mod cli;

#[tokio::main]
async fn main() -> eyre::Result<()> {
dotenvy::dotenv().ok();

let args = Opt::parse();
println!("{:#?}", args);

match args.cmd {
Cmd::Prove(prove_args) => {
let tx: TxEnvelope = TxEnvelope::decode(&mut prove_args.tx.as_ref())?;

let tx_hash = tx.tx_hash();
let signal_hash = hash_to_field(tx_hash.as_ref());

let identity = prove_args.identity_source.load();
let merkle_proof = prove_args.inclusion_proof_source.load();

let date = prove_args
.custom_date
.unwrap_or_else(|| chrono::Utc::now().naive_utc().date());

let month = DateMarker::from(date);

let external_nullifier = ExternalNullifier::new(month, prove_args.pbh_nonce);
let external_nullifier_hash = external_nullifier.hash();

let semaphore_proof = semaphore::protocol::generate_proof(
&identity,
&merkle_proof,
external_nullifier_hash,
signal_hash,
)?;
}
_ => unimplemented!(),
}

Ok(())
}
Loading

0 comments on commit a73c198

Please sign in to comment.