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

Proxy eth_sendRawTransaction to builder #22

Merged
merged 2 commits into from
Oct 25, 2024
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: 3 additions & 1 deletion src/proxy.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ use std::{future::Future, pin::Pin};
use tower::{Layer, Service};
use tracing::debug;

const MULTIPLEX_METHODS: [&str; 2] = ["engine_", "eth_sendRawTransaction"];

#[derive(Debug, Clone)]
pub struct ProxyLayer {
target_url: Uri,
Expand Down Expand Up @@ -84,7 +86,7 @@ where
message = "received json rpc request for",
method = method.method
);
if method.method.starts_with("engine_") {
if PROXY_METHODS.iter().any(|&m| method.method.starts_with(m)) {
// let rpc server handle engine rpc requests
let res = inner.call(req).await.map_err(|e| e.into())?;
Ok(res)
Expand Down
39 changes: 38 additions & 1 deletion src/server.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use alloy::primitives::B256;
use alloy_primitives::Bytes;
use alloy_rpc_types_engine::{
ExecutionPayload, ExecutionPayloadV3, ForkchoiceState, ForkchoiceUpdated, PayloadId,
PayloadStatus,
Expand All @@ -14,7 +15,7 @@ use op_alloy_rpc_types_engine::{
};
use reth_rpc_layer::AuthClientService;
use std::sync::Arc;
use tracing::{error, info};
use tracing::{debug, error, info};

#[rpc(server, client, namespace = "engine")]
pub trait EngineApi {
Expand All @@ -40,6 +41,12 @@ pub trait EngineApi {
) -> RpcResult<PayloadStatus>;
}

#[rpc(server, client, namespace = "eth")]
pub trait EthApi {
#[method(name = "sendRawTransaction")]
async fn send_raw_transaction(&self, bytes: Bytes) -> RpcResult<B256>;
}

pub struct EthEngineApi<S = AuthClientService<HttpBackend>> {
l2_client: Arc<HttpClient<S>>,
builder_client: Arc<HttpClient<S>>,
Expand All @@ -60,6 +67,36 @@ impl<S> EthEngineApi<S> {
}
}

#[async_trait]
impl EthApiServer for EthEngineApi {
async fn send_raw_transaction(&self, bytes: Bytes) -> RpcResult<B256> {
debug!(
message = "received send_raw_transaction",
"bytes_len" = bytes.len()
);
let builder = self.builder_client.clone();
let tx_bytes = bytes.clone();
tokio::spawn(async move {
builder.send_raw_transaction(tx_bytes).await.map_err(|e| {
error!(message = "error calling send_raw_transaction for builder", "error" = %e);
})
});
self.l2_client
.send_raw_transaction(bytes)
.await
.map_err(|e| match e {
ClientError::Call(err) => err, // Already an ErrorObjectOwned, so just return it
other_error => {
error!(
message = "error calling send_raw_transaction for l2 client",
"error" = %other_error,
);
ErrorCode::InternalError.into()
}
})
}
}

#[async_trait]
impl EngineApiServer for EthEngineApi {
async fn fork_choice_updated_v3(
Expand Down
Loading