Skip to content

Commit 6d1396b

Browse files
committed
Fix inconsistent content-type headers for JSON responses
1 parent 7af4855 commit 6d1396b

7 files changed

Lines changed: 88 additions & 11 deletions

File tree

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,20 @@
11
use rapid_web::actix::HttpResponse;
2+
use rapid_web::json_response;
23
use rapid_web::rapid_web_codegen::rapid_handler;
4+
use serde::Serialize;
35

46
pub const ROUTE_KEY: &str = "hello";
5-
pub type RapidOutput = String;
7+
pub type RapidOutput = HelloResponse;
8+
9+
#[derive(Serialize)]
10+
pub struct HelloResponse {
11+
message: String,
12+
}
613

714
#[rapid_handler]
815
pub async fn query() -> HttpResponse {
9-
HttpResponse::Ok().body("Hello from a RAPID rust endpoint!")
16+
let response = HelloResponse {
17+
message: String::from("Hello from a RAPID rust endpoint!"),
18+
};
19+
json_response(response)
1020
}
Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,20 @@
11
use rapid_web::actix::HttpResponse;
2+
use rapid_web::json_response;
23
use rapid_web::rapid_web_codegen::rapid_handler;
4+
use serde::Serialize;
35

46
pub const ROUTE_KEY: &str = "hello";
5-
pub type RapidOutput = String;
7+
pub type RapidOutput = HelloResponse;
8+
9+
#[derive(Serialize)]
10+
pub struct HelloResponse {
11+
message: String,
12+
}
613

714
#[rapid_handler]
815
pub async fn query() -> HttpResponse {
9-
HttpResponse::Ok().body("Hello from a RAPID rust endpoint!")
16+
let response = HelloResponse {
17+
message: String::from("Hello from a RAPID rust endpoint!"),
18+
};
19+
json_response(response)
1020
}
Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,20 @@
11
use rapid_web::actix::HttpResponse;
2+
use rapid_web::json_response;
23
use rapid_web::rapid_web_codegen::rapid_handler;
4+
use serde::Serialize;
35

46
pub const ROUTE_KEY: &str = "hello";
5-
pub type RapidOutput = String;
7+
pub type RapidOutput = HelloResponse;
8+
9+
#[derive(Serialize)]
10+
pub struct HelloResponse {
11+
message: String,
12+
}
613

714
#[rapid_handler]
815
pub async fn query() -> HttpResponse {
9-
HttpResponse::Ok().body("Hello from a RAPID rust endpoint!")
16+
let response = HelloResponse {
17+
message: String::from("Hello from a RAPID rust endpoint!"),
18+
};
19+
json_response(response)
1020
}

crates/rapid-web/src/lib.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,14 @@ pub use actix_web as actix;
44
pub use actix_web_httpauth as auth;
55
pub use default_routes::templates::WELCOME_TEMPLATE as welcome_view;
66
pub use rapid_web_codegen;
7+
pub use util::json_response;
78
pub(crate) mod default_routes;
89
pub mod logger;
910
pub mod server;
1011
pub mod shift; // TODO: shift needs to be abstracted out into its own crate
1112
pub(crate) mod tui;
1213
pub mod types;
13-
pub(crate) mod util;
14+
pub mod util;
1415

1516
// Create new namings for every actix extractor (this is so that Shift can easily parse new route files and generate the correct typescript types)
1617
pub mod request {

crates/rapid-web/src/util.rs

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ use rapid_cli::rapid_config::config::{RapidConfig, ServerConfig};
66
use std::{env::current_dir, fs::File, io::Read, path::PathBuf};
77
use syn::{parse_file, parse_str, File as SynFile, Item};
88
use walkdir::WalkDir;
9+
use super::actix::{web, HttpResponse};
910

1011
pub const REMIX_ROUTE_PATH: &'static str = "app/api/routes";
1112
pub const NEXTJS_ROUTE_PATH: &'static str = "pages/api/routes";
@@ -237,6 +238,31 @@ pub fn is_serving_static_files() -> bool {
237238
}
238239
}
239240

241+
/// Creates an HTTP response with JSON data and the correct content-type header.
242+
///
243+
/// This function ensures that all JSON responses consistently use the
244+
/// "application/json; charset=utf-8" content-type header.
245+
///
246+
/// # Examples
247+
///
248+
/// ```
249+
/// use rapid_web::util::json_response;
250+
///
251+
/// #[rapid_handler]
252+
/// async fn query() -> HttpResponse {
253+
/// let data = serde_json::json!({ "message": "Hello world!" });
254+
/// json_response(data)
255+
/// }
256+
/// ```
257+
pub fn json_response<T>(data: T) -> HttpResponse
258+
where
259+
T: serde::Serialize,
260+
{
261+
HttpResponse::Ok()
262+
.content_type("application/json; charset=utf-8")
263+
.json(data)
264+
}
265+
240266
#[cfg(test)]
241267
mod tests {
242268
use super::*;
Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,20 @@
11
use rapid_web::actix::HttpResponse;
2+
use rapid_web::json_response;
23
use rapid_web::rapid_web_codegen::rapid_handler;
4+
use serde::Serialize;
35

46
pub const ROUTE_KEY: &str = "hello";
5-
pub type RapidOutput = String;
7+
pub type RapidOutput = HelloResponse;
8+
9+
#[derive(Serialize)]
10+
pub struct HelloResponse {
11+
message: String,
12+
}
613

714
#[rapid_handler]
815
pub async fn query() -> HttpResponse {
9-
HttpResponse::Ok().body("Hello from a RAPID rust endpoint!")
16+
let response = HelloResponse {
17+
message: String::from("Hello from a RAPID rust endpoint!"),
18+
};
19+
json_response(response)
1020
}
Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,20 @@
11
use rapid_web::actix::HttpResponse;
2+
use rapid_web::json_response;
23
use rapid_web::rapid_web_codegen::rapid_handler;
4+
use serde::Serialize;
35

46
pub const ROUTE_KEY: &str = "hello";
5-
pub type RapidOutput = String;
7+
pub type RapidOutput = HelloResponse;
8+
9+
#[derive(Serialize)]
10+
pub struct HelloResponse {
11+
message: String,
12+
}
613

714
#[rapid_handler]
815
pub async fn query() -> HttpResponse {
9-
HttpResponse::Ok().body("Hello from a RAPID rust endpoint!")
16+
let response = HelloResponse {
17+
message: String::from("Hello from a RAPID rust endpoint!"),
18+
};
19+
json_response(response)
1020
}

0 commit comments

Comments
 (0)