|
| 1 | +use actix_web::{ |
| 2 | + web::{self, Data}, |
| 3 | + App, HttpRequest, HttpResponse, HttpServer, Responder, |
| 4 | +}; |
| 5 | + |
| 6 | +use super::types::AppResponse; |
| 7 | + |
| 8 | +use crate::{config::Config, db::Db}; |
| 9 | + |
| 10 | +#[derive(Clone, Debug)] |
| 11 | +pub struct BatcherServer { |
| 12 | + db: Db, |
| 13 | + config: Config, |
| 14 | +} |
| 15 | + |
| 16 | +impl BatcherServer { |
| 17 | + pub fn new(db: Db, config: Config) -> Self { |
| 18 | + Self { db, config } |
| 19 | + } |
| 20 | + |
| 21 | + pub async fn start(&self) -> Result<(), std::io::Error> { |
| 22 | + // Note: BatcherServer is thread safe so we can just clone it (no need to add mutexes) |
| 23 | + let port = self.config.port; |
| 24 | + let state = self.clone(); |
| 25 | + |
| 26 | + HttpServer::new(move || { |
| 27 | + App::new() |
| 28 | + .app_data(Data::new(state.clone())) |
| 29 | + .route("/nonce/{address}", web::get().to(Self::get_nonce)) |
| 30 | + .route( |
| 31 | + "/proof/merkle/:receipt", |
| 32 | + web::get().to(Self::get_proof_merkle_path), |
| 33 | + ) |
| 34 | + .route("/proof", web::post().to(Self::post_proof)) |
| 35 | + }) |
| 36 | + .bind(("127.0.0.1", port))? |
| 37 | + .run() |
| 38 | + .await |
| 39 | + } |
| 40 | + |
| 41 | + async fn get_nonce(req: HttpRequest) -> impl Responder { |
| 42 | + let Some(address) = req.match_info().get("address") else { |
| 43 | + return HttpResponse::BadRequest() |
| 44 | + .json(AppResponse::new_unsucessfull("Missing address", 400)); |
| 45 | + }; |
| 46 | + |
| 47 | + // TODO: validate valid ethereum address |
| 48 | + |
| 49 | + let Some(state) = req.app_data::<Data<BatcherServer>>() else { |
| 50 | + return HttpResponse::InternalServerError() |
| 51 | + .json(AppResponse::new_unsucessfull("Internal server error", 500)); |
| 52 | + }; |
| 53 | + |
| 54 | + let state = state.get_ref(); |
| 55 | + match state.db.count_proofs_by_address(address).await { |
| 56 | + Ok(count) => HttpResponse::Ok().json(AppResponse::new_sucessfull(serde_json::json!( |
| 57 | + { |
| 58 | + "nonce": count |
| 59 | + } |
| 60 | + ))), |
| 61 | + Err(err) => { |
| 62 | + tracing::error!(error = ?err, "failed to count proofs"); |
| 63 | + HttpResponse::InternalServerError().finish() |
| 64 | + } |
| 65 | + } |
| 66 | + } |
| 67 | + |
| 68 | + // TODO: receive the proof and 1. decode it, 2. verify it, 3. add to the db |
| 69 | + async fn post_proof(req: HttpRequest) -> impl Responder { |
| 70 | + HttpResponse::Ok() |
| 71 | + } |
| 72 | + |
| 73 | + // TODO: get the proof merkle path for the receipt id (proof commitment) |
| 74 | + async fn get_proof_merkle_path(req: HttpRequest) -> impl Responder { |
| 75 | + HttpResponse::Ok() |
| 76 | + } |
| 77 | +} |
0 commit comments