Skip to content

Commit 6a995b1

Browse files
committed
fix: A bunch of compilation errors by using Arcs
1 parent 2d4fe51 commit 6a995b1

File tree

4 files changed

+51
-81
lines changed

4 files changed

+51
-81
lines changed

src/builder.rs

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
11
use crate::config::*;
2-
use crate::handler::{LazyClient, RocketHandler};
2+
use crate::handler::RocketHandler;
33
use lamedh_http::handler;
44
use lamedh_runtime::run;
5+
use rocket::local::blocking::Client;
56
use rocket::Rocket;
7+
use std::sync::Arc;
68

79
/// A builder to create and configure a [RocketHandler](RocketHandler).
810
pub struct RocketHandlerBuilder {
@@ -42,9 +44,11 @@ impl RocketHandlerBuilder {
4244
/// run(handler(rocket_handler));
4345
/// ```
4446
pub fn into_handler(self) -> RocketHandler {
47+
// TODO: Change this to async Client?
48+
let client = Arc::new(Client::untracked(self.rocket).unwrap());
4549
RocketHandler {
46-
client: LazyClient::Uninitialized(self.rocket),
47-
config: self.config,
50+
client,
51+
config: Arc::new(self.config),
4852
}
4953
}
5054

@@ -64,8 +68,8 @@ impl RocketHandlerBuilder {
6468
///
6569
/// rocket::ignite().lambda().launch();
6670
/// ```
67-
pub fn launch(self) -> ! {
68-
run(handler(self.into_handler()));
71+
pub async fn launch(self) -> ! {
72+
run(handler(self.into_handler())).await.unwrap();
6973
unreachable!("lambda! should loop forever (or panic)")
7074
}
7175

src/handler.rs

Lines changed: 35 additions & 70 deletions
Original file line numberDiff line numberDiff line change
@@ -6,21 +6,14 @@ use lamedh_http::{Handler, Request, RequestExt, Response};
66
use lamedh_runtime::Context;
77
use rocket::http::{uri::Uri, Header};
88
use rocket::local::blocking::{Client, LocalRequest, LocalResponse};
9-
use rocket::{Rocket, Route};
109
use std::future::Future;
11-
use std::mem;
1210
use std::pin::Pin;
11+
use std::sync::Arc;
1312

1413
/// A Lambda handler for API Gateway events that processes requests using a [Rocket](rocket::Rocket) instance.
1514
pub struct RocketHandler {
16-
pub(super) client: LazyClient,
17-
pub(super) config: Config,
18-
}
19-
20-
pub(super) enum LazyClient {
21-
Placeholder,
22-
Uninitialized(Rocket),
23-
Ready(Client),
15+
pub(super) client: Arc<Client>,
16+
pub(super) config: Arc<Config>,
2417
}
2518

2619
impl Handler for RocketHandler {
@@ -29,9 +22,10 @@ impl Handler for RocketHandler {
2922
type Fut = Pin<Box<dyn Future<Output = Result<Self::Response, Self::Error>> + 'static>>;
3023

3124
fn call(&mut self, req: Request, _ctx: Context) -> Self::Fut {
32-
self.ensure_client_ready(&req);
25+
let client = Arc::clone(&self.client);
26+
let config = Arc::clone(&self.config);
3327
let fut = async {
34-
process_request(self, req)
28+
process_request(client, config, req)
3529
.await
3630
.map_err(failure::Error::from)
3731
.map_err(failure::Error::into)
@@ -40,76 +34,47 @@ impl Handler for RocketHandler {
4034
}
4135
}
4236

43-
impl RocketHandler {
44-
fn ensure_client_ready(&mut self, req: &Request) {
45-
match self.client {
46-
ref mut lazy_client @ LazyClient::Uninitialized(_) => {
47-
let uninitialized_client = mem::replace(lazy_client, LazyClient::Placeholder);
48-
let mut rocket = match uninitialized_client {
49-
LazyClient::Uninitialized(rocket) => rocket,
50-
_ => unreachable!("LazyClient must be uninitialized at this point."),
51-
};
52-
if self.config.base_path_behaviour == BasePathBehaviour::RemountAndInclude {
53-
let base_path = req.base_path();
54-
if !base_path.is_empty() {
55-
let routes: Vec<Route> = rocket.routes().cloned().collect();
56-
rocket = rocket.mount(&base_path, routes);
57-
}
58-
}
59-
let client = Client::untracked(rocket).unwrap();
60-
self.client = LazyClient::Ready(client);
61-
}
62-
LazyClient::Ready(_) => {}
63-
LazyClient::Placeholder => panic!("LazyClient has previously begun initialiation."),
64-
}
65-
}
66-
67-
fn client(&self) -> &Client {
68-
match &self.client {
69-
LazyClient::Ready(client) => client,
70-
_ => panic!("Rocket client wasn't ready. ensure_client_ready should have been called!"),
71-
}
72-
}
73-
74-
fn get_path_and_query(&self, req: &Request) -> String {
75-
let mut uri = match self.config.base_path_behaviour {
76-
BasePathBehaviour::Include | BasePathBehaviour::RemountAndInclude => req.full_path(),
77-
BasePathBehaviour::Exclude => req.api_path().to_owned(),
78-
};
79-
let query = req.query_string_parameters();
37+
fn get_path_and_query(config: &Config, req: &Request) -> String {
38+
// TODO: Figure out base path behavior per request since the client doesn't have it now
39+
let mut uri = match config.base_path_behaviour {
40+
BasePathBehaviour::Include | BasePathBehaviour::RemountAndInclude => req.full_path(),
41+
BasePathBehaviour::Exclude => req.api_path().to_owned(),
42+
};
43+
let query = req.query_string_parameters();
8044

81-
let mut separator = '?';
82-
for (key, _) in query.iter() {
83-
for value in query.get_all(key).unwrap() {
84-
uri.push_str(&format!(
85-
"{}{}={}",
86-
separator,
87-
Uri::percent_encode(key),
88-
Uri::percent_encode(value)
89-
));
90-
separator = '&';
91-
}
45+
let mut separator = '?';
46+
for (key, _) in query.iter() {
47+
for value in query.get_all(key).unwrap() {
48+
uri.push_str(&format!(
49+
"{}{}={}",
50+
separator,
51+
Uri::percent_encode(key),
52+
Uri::percent_encode(value)
53+
));
54+
separator = '&';
9255
}
93-
uri
9456
}
57+
uri
9558
}
9659

9760
async fn process_request(
98-
handler: &RocketHandler,
61+
client: Arc<Client>,
62+
config: Arc<Config>,
9963
req: Request,
10064
) -> Result<Response<Body>, RocketLambError> {
101-
let local_req = create_rocket_request(handler, req)?;
65+
let local_req = create_rocket_request(&client, Arc::clone(&config), req)?;
10266
let local_res = local_req.dispatch();
103-
create_lambda_response(handler, local_res).await
67+
create_lambda_response(config, local_res).await
10468
}
10569

10670
fn create_rocket_request(
107-
handler: &RocketHandler,
71+
client: &Client,
72+
config: Arc<Config>,
10873
req: Request,
10974
) -> Result<LocalRequest, RocketLambError> {
11075
let method = to_rocket_method(req.method())?;
111-
let uri = handler.get_path_and_query(&req);
112-
let mut local_req = handler.client().req(method, uri);
76+
let uri = get_path_and_query(&config, &req);
77+
let mut local_req = client.req(method, uri);
11378
for (name, value) in req.headers() {
11479
match value.to_str() {
11580
Ok(v) => local_req.add_header(Header::new(name.to_string(), v.to_string())),
@@ -121,7 +86,7 @@ fn create_rocket_request(
12186
}
12287

12388
async fn create_lambda_response(
124-
handler: &RocketHandler,
89+
config: Arc<Config>,
12590
local_res: LocalResponse<'_>,
12691
) -> Result<Response<Body>, RocketLambError> {
12792
let mut builder = Response::builder();
@@ -136,9 +101,9 @@ async fn create_lambda_response(
136101
.unwrap_or_default()
137102
.split(';')
138103
.next()
139-
.and_then(|ct| handler.config.response_types.get(&ct.to_lowercase()))
104+
.and_then(|ct| config.response_types.get(&ct.to_lowercase()))
140105
.copied()
141-
.unwrap_or(handler.config.default_response_type);
106+
.unwrap_or(config.default_response_type);
142107
let body = match local_res.into_bytes() {
143108
Some(b) => match response_type {
144109
ResponseType::Auto => match String::from_utf8(b) {

tests/path_tests.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ macro_rules! test_case {
4444
.into_handler();
4545

4646
let req = get_request($file)?;
47-
let res = handler.run(req, Context::default())?;
47+
let res = handler.call(req, Context::default())?;
4848

4949
assert_eq!(res.status(), $status);
5050
assert_eq!(*res.body(), Body::Text($path.to_string()));

tests/rocket_tests.rs

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ extern crate rocket;
55

66
use lambda_http::{Body, Handler, Request, Response};
77
use lambda_runtime::Context;
8+
use lamedh_http::Handler;
89
use rocket_lamb::{ResponseType, RocketExt};
910
use std::error::Error;
1011
use std::fs::File;
@@ -43,7 +44,7 @@ fn ok_auto_text() -> Result<(), Box<dyn Error>> {
4344
let mut handler = make_rocket().lambda().into_handler();
4445

4546
let req = get_request("upper")?;
46-
let res = handler.run(req, Context::default())?;
47+
let res = handler.call(req, Context::default())?;
4748

4849
assert_eq!(res.status(), 200);
4950
assert_header(&res, "content-type", "text/plain; charset=utf-8");
@@ -56,7 +57,7 @@ fn ok_auto_binary() -> Result<(), Box<dyn Error>> {
5657
let mut handler = make_rocket().lambda().into_handler();
5758

5859
let req = get_request("binary")?;
59-
let res = handler.run(req, Context::default())?;
60+
let res = handler.call(req, Context::default())?;
6061

6162
assert_eq!(res.status(), 200);
6263
assert_header(&res, "content-type", "application/octet-stream");
@@ -72,7 +73,7 @@ fn ok_default_binary() -> Result<(), Box<dyn Error>> {
7273
.into_handler();
7374

7475
let req = get_request("upper")?;
75-
let res = handler.run(req, Context::default())?;
76+
let res = handler.call(req, Context::default())?;
7677

7778
assert_eq!(res.status(), 200);
7879
assert_header(&res, "content-type", "text/plain; charset=utf-8");
@@ -91,7 +92,7 @@ fn ok_type_binary() -> Result<(), Box<dyn Error>> {
9192
.into_handler();
9293

9394
let req = get_request("upper")?;
94-
let res = handler.run(req, Context::default())?;
95+
let res = handler.call(req, Context::default())?;
9596

9697
assert_eq!(res.status(), 200);
9798
assert_header(&res, "content-type", "text/plain; charset=utf-8");
@@ -107,7 +108,7 @@ fn request_not_found() -> Result<(), Box<dyn Error>> {
107108
let mut handler = make_rocket().lambda().into_handler();
108109

109110
let req = get_request("not_found")?;
110-
let res = handler.run(req, Context::default())?;
111+
let res = handler.call(req, Context::default())?;
111112

112113
assert_eq!(res.status(), 404);
113114
assert_eq!(res.headers().contains_key("content-type"), false);

0 commit comments

Comments
 (0)