Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Reputation #43

Merged
merged 20 commits into from
Feb 1, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,9 @@ jobs:
with:
toolchain: stable
components: rustfmt, clippy
- name: Setup third party dependencies
- name: Setup third-party dependencies
run: |
make fetch-thirdparty
make setup-thirdparty
- name: Install Geth and solc
run: |
sudo add-apt-repository ppa:ethereum/ethereum
Expand Down
16 changes: 7 additions & 9 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,34 +1,32 @@
build:
make fetch-thirdparty
cd thirdparty/account-abstraction && yarn install && yarn compile && cd ../..
cargo build

run-bundler:
cargo run -- --mnemonic-file ${HOME}/.aa-bundler/0x129D197b2a989C6798601A49D89a4AEC822A17a3 --beneficiary 0x690B9A9E9aa1C9dB991C7721a92d351Db4FaC990 --gas-factor 600 --min-balance 1 --entry-points 0x0000000000000000000000000000000000000000 --chain-id 5 --helper 0x0000000000000000000000000000000000000000

run-bundler-uopool:
cargo run --bin bundler-uopool -- --entry-points 0x0000000000000000000000000000000000000000 --chain-id 5
cargo run --bin bundler-uopool -- --entry-points 0x0000000000000000000000000000000000000000 --chain-id 5 --min-stake 1 --min-unstake-delay 0

run-bundler-rpc:
cargo run --bin bundler-rpc

run-create-wallet:
cargo run --bin create-wallet -- --output-path ${HOME}/.aa-bundler

fetch-thirdparty:
git submodule update --init

test:
setup-thirdparty:
git submodule update --init
cd thirdparty/account-abstraction && yarn install && yarn compile && cd ../..
cd thirdparty/bundler && yarn install && yarn preprocess && cd ../..

test:
cargo test

format:
cargo fmt --all

lint:
cd thirdparty/bundler && yarn install && yarn preprocess && cd ../..
cargo fmt --all -- --check
cargo clippy -- -D warnings -A clippy::derive_partial_eq_without_eq -D clippy::unwrap_used
cargo clippy -- -D warnings -A clippy::derive_partial_eq_without_eq -D clippy::unwrap_used -D clippy::uninlined_format_args

clean:
cd thirdparty/account-abstraction && yarn clean && cd ../..
Expand Down
8 changes: 7 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,12 @@ For more information: https://hackmd.io/@Vid201/aa-bundler-rust

## How to run?

Set up third-party dependencies (EIP-4337 smart contracts and bundler tests):

```bash
make setup-thirdparty
```

Create wallet for bundler:

```bash
Expand All @@ -32,7 +38,7 @@ cargo run -- --mnemonic-file ${HOME}/.aa-bundler/0x129D197b2a989C6798601A49D89a4
Run only user operation pool:

```bash
cargo run --bin bundler-uopool -- --entry-points 0x0000000000000000000000000000000000000000 --chain-id 5
cargo run --bin bundler-uopool -- --entry-points 0x0000000000000000000000000000000000000000 --chain-id 5 --min-stake 1 --min-unstake-delay 0
```

Run only JSON-RPC API:
Expand Down
13 changes: 12 additions & 1 deletion bin/bundler-rpc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,10 @@ use jsonrpsee::{core::server::rpc_module::Methods, server::ServerBuilder, tracin
use std::future::pending;

use aa_bundler::{
rpc::{eth::EthApiServerImpl, eth_api::EthApiServer},
rpc::{
debug::DebugApiServerImpl, debug_api::DebugApiServer, eth::EthApiServerImpl,
eth_api::EthApiServer,
},
uopool::server::uopool::uo_pool_client::UoPoolClient,
};

Expand Down Expand Up @@ -34,6 +37,14 @@ async fn main() -> Result<()> {
let mut api = Methods::new();
let uopool_grpc_client =
UoPoolClient::connect(format!("http://{}", opt.uopool_grpc_listen_address)).await?;

#[cfg(debug_assertions)]
zsluedem marked this conversation as resolved.
Show resolved Hide resolved
api.merge(
DebugApiServerImpl {
uopool_grpc_client: uopool_grpc_client.clone(),
}
.into_rpc(),
)?;
api.merge(
EthApiServerImpl {
call_gas_limit: 100_000_000,
Expand Down
12 changes: 11 additions & 1 deletion bin/bundler.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
use aa_bundler::{
bundler::Bundler,
models::wallet::Wallet,
rpc::{eth::EthApiServerImpl, eth_api::EthApiServer},
rpc::{
debug::DebugApiServerImpl, debug_api::DebugApiServer, eth::EthApiServerImpl,
eth_api::EthApiServer,
},
uopool::server::uopool::uo_pool_client::UoPoolClient,
utils::{parse_address, parse_u256},
};
Expand Down Expand Up @@ -87,6 +90,13 @@ fn main() -> Result<()> {
))
.await?;

#[cfg(debug_assertions)]
zsluedem marked this conversation as resolved.
Show resolved Hide resolved
api.merge(
DebugApiServerImpl {
uopool_grpc_client: uopool_grpc_client.clone(),
}
.into_rpc(),
)?;
api.merge(
EthApiServerImpl {
call_gas_limit: 100_000_000,
Expand Down
13 changes: 13 additions & 0 deletions src/proto/types/types.proto
Original file line number Diff line number Diff line change
Expand Up @@ -34,3 +34,16 @@ message UserOperation {
bytes paymaster_and_data = 10;
bytes signature = 11;
}

enum ReputationStatus {
OK = 0;
THROTTLED = 1;
BANNED = 2;
}

message ReputationEntry {
types.H160 address = 1;
uint64 uo_seen = 2;
uint64 uo_included = 3;
ReputationStatus status = 4;
}
61 changes: 56 additions & 5 deletions src/proto/uopool/uopool.proto
Original file line number Diff line number Diff line change
Expand Up @@ -30,17 +30,68 @@ enum RemoveResult {

message RemoveResponse {
RemoveResult result = 1;
string data = 2;
}

message AllRequest {}
enum GetAllResult {
GOT_ALL = 0;
NOT_GOT_ALL = 1;
}

message GetAllRequest {
types.H160 ep = 1;
}

message GetAllResponse {
GetAllResult result = 1;
repeated types.UserOperation uos = 2;
}

enum ClearResult {
CLEARED = 0;
NOT_CLEARED = 1;
}

message ClearRequest {}

message AllResponse {
repeated types.UserOperation uos = 1;
message ClearResponse {
ClearResult result = 1;
}

enum GetAllReputationResult {
GOT_ALL_REPUTATION = 0;
NOT_GOT_ALL_REPUTATION = 1;
}

message GetAllReputationRequest {
types.H160 ep = 1;
}

message GetAllReputationResponse {
GetAllReputationResult result = 1;
repeated types.ReputationEntry res = 2;
}

enum SetReputationResult {
SET_REPUTATION = 0;
NOT_SET_REPUTATION = 1;
}

message SetReputationRequest {
repeated types.ReputationEntry res = 1;
types.H160 ep = 2;
}

message SetReputationResponse {
SetReputationResult result = 1;
}

service UoPool {
rpc Add(AddRequest) returns (AddResponse);
rpc Remove(RemoveRequest) returns (RemoveResponse);
rpc All(AllRequest) returns (AllResponse);

// debug
rpc GetAll(GetAllRequest) returns (GetAllResponse);
rpc Clear(ClearRequest) returns (ClearResponse);
rpc GetAllReputation(GetAllReputationRequest) returns (GetAllReputationResponse);
rpc SetReputation(SetReputationRequest) returns (SetReputationResponse);
}
113 changes: 113 additions & 0 deletions src/rpc/debug.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
use super::debug_api::DebugApiServer;
use crate::{
types::{reputation::ReputationEntry, user_operation::UserOperation},
uopool::server::uopool::{
uo_pool_client::UoPoolClient, ClearRequest, ClearResult, GetAllReputationRequest,
GetAllReputationResult, GetAllRequest, GetAllResult, SetReputationRequest,
SetReputationResult,
},
};
use anyhow::format_err;
use async_trait::async_trait;
use ethers::types::Address;
use jsonrpsee::core::RpcResult;

#[cfg(debug_assertions)]
pub struct DebugApiServerImpl {
pub uopool_grpc_client: UoPoolClient<tonic::transport::Channel>,
}

#[cfg(debug_assertions)]
#[async_trait]
impl DebugApiServer for DebugApiServerImpl {
async fn clear_state(&self) -> RpcResult<()> {
let mut uopool_grpc_client = self.uopool_grpc_client.clone();

let request = tonic::Request::new(ClearRequest {});

let response = uopool_grpc_client
.clear(request)
.await
.map_err(|status| format_err!("GRPC error (uopool): {}", status.message()))?
.into_inner();

if response.result == ClearResult::Cleared as i32 {
return Ok(());
}

Err(jsonrpsee::core::Error::Custom(
"error clearing state".to_string(),
))
}

async fn dump_mempool(&self, entry_point: Address) -> RpcResult<Vec<UserOperation>> {
let mut uopool_grpc_client = self.uopool_grpc_client.clone();

let request = tonic::Request::new(GetAllRequest {
ep: Some(entry_point.into()),
});

let response = uopool_grpc_client
.get_all(request)
.await
.map_err(|status| format_err!("GRPC error (uopool): {}", status.message()))?
.into_inner();

if response.result == GetAllResult::GotAll as i32 {
return Ok(response.uos.iter().map(|uo| uo.clone().into()).collect());
}

Err(jsonrpsee::core::Error::Custom(
"error getting mempool".to_string(),
))
}

async fn set_reputation(
&self,
reputation_entries: Vec<ReputationEntry>,
entry_point: Address,
) -> RpcResult<()> {
let mut uopool_grpc_client = self.uopool_grpc_client.clone();

let request = tonic::Request::new(SetReputationRequest {
res: reputation_entries.iter().map(|re| (*re).into()).collect(),
ep: Some(entry_point.into()),
});

let response = uopool_grpc_client
.set_reputation(request)
.await
.map_err(|status| format_err!("GRPC error (uopool): {}", status.message()))?
.into_inner();

if response.result == SetReputationResult::SetReputation as i32 {
return Ok(());
}

Err(jsonrpsee::core::Error::Custom(
"error setting reputation".to_string(),
))
}

async fn dump_reputation(&self, entry_point: Address) -> RpcResult<Vec<ReputationEntry>> {
let mut uopool_grpc_client = self.uopool_grpc_client.clone();

let request = tonic::Request::new(GetAllReputationRequest {
ep: Some(entry_point.into()),
});

let response = uopool_grpc_client
.get_all_reputation(request)
.await
.map_err(|status| format_err!("GRPC error (uopool): {}", status.message()))?
.into_inner();

if response.result == GetAllReputationResult::GotAllReputation as i32 {
return Ok(response.res.iter().map(|re| re.clone().into()).collect());
}

Err(jsonrpsee::core::Error::Custom(
"error getting reputation".to_string(),
))
}
}
23 changes: 23 additions & 0 deletions src/rpc/debug_api.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
use crate::types::{reputation::ReputationEntry, user_operation::UserOperation};
use ethers::types::Address;
use jsonrpsee::{core::RpcResult, proc_macros::rpc};

#[cfg(debug_assertions)]
#[rpc(server, namespace = "debug_bundler")]
pub trait DebugApi {
#[method(name = "clearState")]
async fn clear_state(&self) -> RpcResult<()>;

#[method(name = "dumpMempool")]
async fn dump_mempool(&self, entry_point: Address) -> RpcResult<Vec<UserOperation>>;

#[method(name = "setReputation")]
async fn set_reputation(
&self,
reputation_entries: Vec<ReputationEntry>,
entry_point: Address,
) -> RpcResult<()>;

#[method(name = "dumpReputation")]
async fn dump_reputation(&self, entry_point: Address) -> RpcResult<Vec<ReputationEntry>>;
}
4 changes: 4 additions & 0 deletions src/rpc/eth_api.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,24 @@ pub struct EstimateUserOperationGasResponse {
pub trait EthApi {
#[method(name = "chainId")]
async fn chain_id(&self) -> RpcResult<U64>;

#[method(name = "supportedEntryPoints")]
async fn supported_entry_points(&self) -> RpcResult<Vec<Address>>;

#[method(name = "sendUserOperation")]
async fn send_user_operation(
&self,
user_operation: UserOperation,
entry_point: Address,
) -> RpcResult<UserOperationHash>;

#[method(name = "estimateUserOperationGas")]
async fn estimate_user_operation_gas(
&self,
user_operation: UserOperation,
entry_point: Address,
) -> RpcResult<EstimateUserOperationGasResponse>;

#[method(name = "getUserOperationReceipt")]
async fn get_user_operation_receipt(
&self,
Expand Down
2 changes: 2 additions & 0 deletions src/rpc/mod.rs
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
pub mod debug;
pub mod debug_api;
pub mod eth;
pub mod eth_api;
1 change: 1 addition & 0 deletions src/types/mod.rs
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
pub mod reputation;
pub mod user_operation;
Loading