Skip to content

Commit

Permalink
Update errors in client + update logic
Browse files Browse the repository at this point in the history
  • Loading branch information
Dzejkop committed Feb 27, 2024
1 parent 305730d commit 20fe3ad
Show file tree
Hide file tree
Showing 4 changed files with 75 additions and 26 deletions.
57 changes: 42 additions & 15 deletions src/client.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use reqwest::Response;
use thiserror::Error;

use crate::api_key::ApiKey;
use crate::server::routes::network::NewNetworkInfo;
Expand All @@ -8,13 +9,29 @@ use crate::server::routes::relayer::{
use crate::server::routes::transaction::{
GetTxResponse, SendTxRequest, SendTxResponse,
};
use crate::server::ApiError;
use crate::types::RelayerUpdate;

pub struct TxSitterClient {
client: reqwest::Client,
url: String,
}

#[derive(Debug, Error)]
pub enum ClientError {
#[error("Reqwest error: {0}")]
Reqwest(#[from] reqwest::Error),

#[error("Serialization error: {0}")]
Serde(#[from] serde_json::Error),

#[error("API error: {0}")]
TxSitter(#[from] ApiError),

#[error("Invalid API key: {0}")]
InvalidApiKey(eyre::Error),
}

impl TxSitterClient {
pub fn new(url: impl ToString) -> Self {
Self {
Expand All @@ -23,7 +40,7 @@ impl TxSitterClient {
}
}

async fn post<R>(&self, url: &str) -> eyre::Result<R>
async fn post<R>(&self, url: &str) -> Result<R, ClientError>
where
R: serde::de::DeserializeOwned,
{
Expand All @@ -34,7 +51,11 @@ impl TxSitterClient {
Ok(response.json().await?)
}

async fn json_post<T, R>(&self, url: &str, body: T) -> eyre::Result<R>
async fn json_post<T, R>(
&self,
url: &str,
body: T,
) -> Result<R, ClientError>
where
T: serde::Serialize,
R: serde::de::DeserializeOwned,
Expand All @@ -46,7 +67,7 @@ impl TxSitterClient {
Ok(response.json().await?)
}

async fn json_get<R>(&self, url: &str) -> eyre::Result<R>
async fn json_get<R>(&self, url: &str) -> Result<R, ClientError>
where
R: serde::de::DeserializeOwned,
{
Expand All @@ -57,27 +78,29 @@ impl TxSitterClient {
Ok(response.json().await?)
}

async fn validate_response(response: Response) -> eyre::Result<Response> {
async fn validate_response(
response: Response,
) -> Result<Response, ClientError> {
if !response.status().is_success() {
let body = response.text().await?;

return Err(eyre::eyre!("{body}"));
let body: ApiError = response.json().await?;
return Err(ClientError::TxSitter(body));
}

Ok(response)
}

pub async fn create_relayer(
&self,
req: &CreateRelayerRequest,
) -> eyre::Result<CreateRelayerResponse> {
) -> Result<CreateRelayerResponse, ClientError> {
self.json_post(&format!("{}/1/admin/relayer", self.url), req)
.await
}

pub async fn create_relayer_api_key(
&self,
relayer_id: &str,
) -> eyre::Result<CreateApiKeyResponse> {
) -> Result<CreateApiKeyResponse, ClientError> {
self.post(&format!("{}/1/admin/relayer/{relayer_id}/key", self.url,))
.await
}
Expand All @@ -86,7 +109,7 @@ impl TxSitterClient {
&self,
relayer_id: &str,
relayer_update: RelayerUpdate,
) -> eyre::Result<()> {
) -> Result<(), ClientError> {
self.json_post(
&format!("{}/1/admin/relayer/{relayer_id}", self.url),
relayer_update,
Expand All @@ -98,9 +121,13 @@ impl TxSitterClient {
&self,
api_key: &ApiKey,
req: &SendTxRequest,
) -> eyre::Result<SendTxResponse> {
) -> Result<SendTxResponse, ClientError> {
self.json_post(
&format!("{}/1/api/{}/tx", self.url, api_key.reveal()?),
&format!(
"{}/1/api/{}/tx",
self.url,
api_key.reveal().map_err(ClientError::InvalidApiKey)?
),
req,
)
.await
Expand All @@ -110,11 +137,11 @@ impl TxSitterClient {
&self,
api_key: &ApiKey,
tx_id: &str,
) -> eyre::Result<GetTxResponse> {
) -> Result<GetTxResponse, ClientError> {
self.json_get(&format!(
"{}/1/api/{}/tx/{tx_id}",
self.url,
api_key.reveal()?,
api_key.reveal().map_err(ClientError::InvalidApiKey)?,
tx_id = tx_id
))
.await
Expand All @@ -124,7 +151,7 @@ impl TxSitterClient {
&self,
chain_id: u64,
req: &NewNetworkInfo,
) -> eyre::Result<()> {
) -> Result<(), ClientError> {
let response = self
.client
.post(&format!("{}/1/admin/network/{}", self.url, chain_id))
Expand Down
34 changes: 28 additions & 6 deletions src/db.rs
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,15 @@ impl Database {
) -> eyre::Result<()> {
let mut tx = self.pool.begin().await?;

if let Some(name) = &update.relayer_name {
let RelayerUpdate {
relayer_name,
max_inflight_txs,
max_queued_txs,
gas_price_limits,
enabled,
} = update;

if let Some(name) = relayer_name {
sqlx::query(
r#"
UPDATE relayers
Expand All @@ -88,7 +96,7 @@ impl Database {
.await?;
}

if let Some(max_inflight_txs) = update.max_inflight_txs {
if let Some(max_inflight_txs) = max_inflight_txs {
sqlx::query(
r#"
UPDATE relayers
Expand All @@ -97,12 +105,12 @@ impl Database {
"#,
)
.bind(id)
.bind(max_inflight_txs as i64)
.bind(*max_inflight_txs as i64)
.execute(tx.as_mut())
.await?;
}

if let Some(max_queued_txs) = update.max_queued_txs {
if let Some(max_queued_txs) = max_queued_txs {
sqlx::query(
r#"
UPDATE relayers
Expand All @@ -111,12 +119,12 @@ impl Database {
"#,
)
.bind(id)
.bind(max_queued_txs as i64)
.bind(*max_queued_txs as i64)
.execute(tx.as_mut())
.await?;
}

if let Some(gas_price_limits) = &update.gas_price_limits {
if let Some(gas_price_limits) = gas_price_limits {
sqlx::query(
r#"
UPDATE relayers
Expand All @@ -130,6 +138,20 @@ impl Database {
.await?;
}

if let Some(enabled) = enabled {
sqlx::query(
r#"
UPDATE relayers
SET enabled = $2
WHERE id = $1
"#,
)
.bind(id)
.bind(*enabled)
.execute(tx.as_mut())
.await?;
}

tx.commit().await?;

Ok(())
Expand Down
2 changes: 1 addition & 1 deletion src/server.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,10 @@ use self::routes::transaction::{get_tx, get_txs, send_tx};
use self::trace_layer::MatchedPathMakeSpan;
use crate::app::App;

mod error;
mod middleware;
pub mod routes;
mod trace_layer;
mod error;

pub use self::error::ApiError;

Expand Down
8 changes: 4 additions & 4 deletions src/server/routes/relayer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -83,10 +83,10 @@ pub async fn update_relayer(
State(app): State<Arc<App>>,
Path(relayer_id): Path<String>,
Json(req): Json<RelayerUpdate>,
) -> Result<(), ApiError> {
) -> Result<Json<()>, ApiError> {
app.db.update_relayer(&relayer_id, &req).await?;

Ok(())
Ok(Json(()))
}

#[tracing::instrument(skip(app))]
Expand Down Expand Up @@ -115,10 +115,10 @@ pub async fn get_relayer(
pub async fn purge_unsent_txs(
State(app): State<Arc<App>>,
Path(relayer_id): Path<String>,
) -> Result<(), ApiError> {
) -> Result<Json<()>, ApiError> {
app.db.purge_unsent_txs(&relayer_id).await?;

Ok(())
Ok(Json(()))
}

#[tracing::instrument(skip(app, api_token))]
Expand Down

0 comments on commit 20fe3ad

Please sign in to comment.