summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/api/auth.rs2
-rw-r--r--src/api/pages.rs1
-rw-r--r--src/api/posts.rs8
-rw-r--r--src/console.rs13
-rw-r--r--src/main.rs38
-rw-r--r--src/types/extract.rs29
6 files changed, 69 insertions, 22 deletions
diff --git a/src/api/auth.rs b/src/api/auth.rs
index b469d4d..54c4e06 100644
--- a/src/api/auth.rs
+++ b/src/api/auth.rs
@@ -26,7 +26,7 @@ impl Check for RegistrationRequet {
Self::assert_length(&self.gender, 1, 100, "Gender can only by 1-100 characters long")?;
Self::assert_range(self.day as u64, 1, 255, "Birthday day can only be between 1-255")?;
Self::assert_range(self.month as u64, 1, 255, "Birthday month can only be between 1-255")?;
- Self::assert_range(self.year as u64, 1, 2147483647, "Birthday year can only be between 1-2147483647")?;
+ Self::assert_range(self.year as u64, 1, 4294967295, "Birthday year can only be between 1-4294967295")?;
Ok(())
}
}
diff --git a/src/api/pages.rs b/src/api/pages.rs
index 749a686..4701795 100644
--- a/src/api/pages.rs
+++ b/src/api/pages.rs
@@ -3,7 +3,6 @@ use axum::{Router, response::{Response, Redirect, IntoResponse}, routing::get};
use crate::types::{extract::AuthorizedUser, response::ResponseCode};
async fn root(user: Option<AuthorizedUser>) -> Response {
- println!("{}", user.is_some());
if user.is_some() {
return Redirect::to("/home").into_response()
} else {
diff --git a/src/api/posts.rs b/src/api/posts.rs
index 85ff2b2..6830c1a 100644
--- a/src/api/posts.rs
+++ b/src/api/posts.rs
@@ -18,11 +18,15 @@ impl Check for PostCreateRequest {
async fn create(AuthorizedUser(user): AuthorizedUser, Json(body): Json<PostCreateRequest>) -> Response {
- let Ok(_post) = Post::new(user.user_id, body.content) else {
+ let Ok(post) = Post::new(user.user_id, body.content) else {
return ResponseCode::InternalServerError.msg("Failed to create post")
};
- ResponseCode::Created.msg("Successfully created new post")
+ let Ok(json) = serde_json::to_string(&post) else {
+ return ResponseCode::InternalServerError.msg("Failed to create post")
+ };
+
+ ResponseCode::Created.json(&json)
}
#[derive(Deserialize)]
diff --git a/src/console.rs b/src/console.rs
new file mode 100644
index 0000000..5a3c60b
--- /dev/null
+++ b/src/console.rs
@@ -0,0 +1,13 @@
+use std::net::IpAddr;
+use axum::http::{Method, Uri};
+
+pub async fn log(ip: &IpAddr, method: &Method, uri: &Uri, path: Option<&str>, body: Option<&str>) {
+
+ if path.is_some() && body.is_some() {
+ println!("{} {} {}{} {}", ip, method, path.unwrap(), uri, body.unwrap());
+ } else {
+ println!("{} {} {}", ip, method, uri);
+ }
+
+
+} \ No newline at end of file
diff --git a/src/main.rs b/src/main.rs
index 9ad772d..64abf68 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -1,13 +1,14 @@
use std::net::SocketAddr;
-use axum::{Router, response::Response, http::Request, middleware::{Next, self}};
+use axum::{Router, response::Response, http::Request, middleware::{Next, self}, extract::ConnectInfo, RequestExt, body::HttpBody, Extension};
use tower_cookies::CookieManagerLayer;
-use types::response::ResponseCode;
+use types::{response::ResponseCode};
-use crate::api::{pages, auth, users, posts};
+use crate::{api::{pages, auth, users, posts}, types::extract::RouterURI};
mod api;
mod database;
mod types;
+mod console;
async fn serve<B>(req: Request<B>, next: Next<B>) -> Response {
let Ok(file) = ResponseCode::Success.file(&req.uri().to_string()).await else {
@@ -16,6 +17,19 @@ async fn serve<B>(req: Request<B>, next: Next<B>) -> Response {
file
}
+async fn log<B>(mut req: Request<B>, next: Next<B>) -> Response where
+ B: Send + Sync + 'static + HttpBody,
+{
+
+ let Ok(ConnectInfo(info)) = req.extract_parts::<ConnectInfo<SocketAddr>>().await else {
+ return next.run(req).await
+ };
+
+ console::log(&info.ip(), req.method(), req.uri(), None, None).await;
+
+ return next.run(req).await
+}
+
async fn not_found() -> Response {
match ResponseCode::NotFound.file("/404.html").await {
Ok(file) => file,
@@ -30,18 +44,22 @@ async fn main() {
let app = Router::new()
.fallback(not_found)
- .layer(middleware::from_fn(serve))
.nest("/", pages::router())
- .nest("/api/auth", auth::router())
- .nest("/api/users", users::router())
- .nest("/api/posts", posts::router())
- .layer(CookieManagerLayer::new());
+ .layer(middleware::from_fn(log))
+ .layer(middleware::from_fn(serve))
+ .nest("/api/auth", auth::router()
+ .layer(Extension(RouterURI("/api/auth")))
+ ).nest("/api/users", users::router()
+ .layer(Extension(RouterURI("/api/users")))
+ ).nest("/api/posts", posts::router()
+ .layer(Extension(RouterURI("/api/posts")))
+ ).layer(CookieManagerLayer::new());
- let addr = SocketAddr::from(([127, 0, 0, 1], 8080));
+ let addr = "[::]:8080".parse::<std::net::SocketAddr>().unwrap();
println!("Listening on {}", addr);
axum::Server::bind(&addr)
- .serve(app.into_make_service())
+ .serve(app.into_make_service_with_connect_info::<SocketAddr>())
.await
.unwrap();
diff --git a/src/types/extract.rs b/src/types/extract.rs
index bb50aa7..1379828 100644
--- a/src/types/extract.rs
+++ b/src/types/extract.rs
@@ -1,10 +1,10 @@
-use std::io::Read;
+use std::{io::Read, net::SocketAddr};
-use axum::{extract::{FromRequestParts, FromRequest}, async_trait, response::Response, http::{request::Parts, Request}, TypedHeader, headers::Cookie, body::HttpBody, BoxError};
+use axum::{extract::{FromRequestParts, FromRequest, ConnectInfo}, async_trait, response::Response, http::{request::Parts, Request}, TypedHeader, headers::Cookie, body::HttpBody, BoxError, RequestExt};
use bytes::Bytes;
use serde::de::DeserializeOwned;
-use crate::types::{user::User, response::{ResponseCode, Result}, session::Session};
+use crate::{types::{user::User, response::{ResponseCode, Result}, session::Session}, console};
pub struct AuthorizedUser(pub User);
@@ -39,24 +39,33 @@ pub struct Json<T>(pub T);
#[async_trait]
impl<T, S, B> FromRequest<S, B> for Json<T> where
T: DeserializeOwned + Check,
- B: HttpBody + Send + 'static,
+ B: HttpBody + Sync + Send + 'static,
B::Data: Send,
B::Error: Into<BoxError>,
S: Send + Sync,
{
type Rejection = Response;
- async fn from_request(req: Request<B>, state: &S) -> Result<Self> {
+ async fn from_request(mut req: Request<B>, state: &S) -> Result<Self> {
+
+ let Ok(ConnectInfo(info)) = req.extract_parts::<ConnectInfo<SocketAddr>>().await else {
+ return Err(ResponseCode::InternalServerError.msg("Failed to read connection info"));
+ };
+ let method = req.method().clone();
+ let path = req.extensions().get::<RouterURI>().unwrap().0;
+ let uri = req.uri().clone();
let Ok(bytes) = Bytes::from_request(req, state).await else {
return Err(ResponseCode::InternalServerError.msg("Failed to read request body"));
};
- let Ok(string) = String::from_utf8(bytes.bytes().flatten().collect()) else {
+ let Ok(body) = String::from_utf8(bytes.bytes().flatten().collect()) else {
return Err(ResponseCode::BadRequest.msg("Invalid utf8 body"))
};
+
+ console::log(&info.ip(), &method, &uri, Some(path), Some(&body)).await;
- let Ok(value) = serde_json::from_str::<T>(&string) else {
+ let Ok(value) = serde_json::from_str::<T>(&body) else {
return Err(ResponseCode::BadRequest.msg("Invalid request body"))
};
@@ -87,4 +96,8 @@ pub trait Check {
}
Ok(())
}
-} \ No newline at end of file
+}
+
+#[derive(Clone)]
+pub struct RouterURI(pub &'static str);
+