feat: add environment configuration for database and authentication, update router setup
This commit is contained in:
3
.env.example
Normal file
3
.env.example
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
POSTGRES_USER=thoughts_user
|
||||||
|
POSTGRES_PASSWORD=postgres
|
||||||
|
POSTGRES_DB=thoughts_db
|
1
.gitignore
vendored
1
.gitignore
vendored
@@ -1,2 +1,3 @@
|
|||||||
backend-codebase.txt
|
backend-codebase.txt
|
||||||
frontend-codebase.txt
|
frontend-codebase.txt
|
||||||
|
.env
|
@@ -3,3 +3,5 @@ PORT=3000
|
|||||||
DATABASE_URL="sqlite://dev.db"
|
DATABASE_URL="sqlite://dev.db"
|
||||||
# DATABASE_URL="postgresql://postgres:postgres@localhost/clean-axum"
|
# DATABASE_URL="postgresql://postgres:postgres@localhost/clean-axum"
|
||||||
PREFORK=1
|
PREFORK=1
|
||||||
|
AUTH_SECRET=your_secret_key_here
|
||||||
|
BASE_URL=http://localhost:3000
|
1
thoughts-backend/.gitignore
vendored
1
thoughts-backend/.gitignore
vendored
@@ -1 +1,2 @@
|
|||||||
/target
|
/target
|
||||||
|
.env
|
@@ -25,9 +25,8 @@ pub async fn federate_thought(
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
let base_url = "http://localhost:3000"; // Replace in production
|
let thought_url = format!("{}/thoughts/{}", &state.base_url, thought.id);
|
||||||
let thought_url = format!("{}/thoughts/{}", base_url, thought.id);
|
let author_url = format!("{}/users/{}", &state.base_url, author.username);
|
||||||
let author_url = format!("{}/users/{}", base_url, author.username);
|
|
||||||
|
|
||||||
// Construct the "Create" activity containing the "Note" object
|
// Construct the "Create" activity containing the "Note" object
|
||||||
let activity = json!({
|
let activity = json!({
|
||||||
@@ -59,7 +58,7 @@ pub async fn federate_thought(
|
|||||||
|
|
||||||
let client = reqwest::Client::new();
|
let client = reqwest::Client::new();
|
||||||
for follower in followers {
|
for follower in followers {
|
||||||
let inbox_url = format!("{}/users/{}/inbox", base_url, follower.username);
|
let inbox_url = format!("{}/users/{}/inbox", &state.base_url, follower.username);
|
||||||
tracing::info!("Federating post {} to {}", thought.id, inbox_url);
|
tracing::info!("Federating post {} to {}", thought.id, inbox_url);
|
||||||
|
|
||||||
let res = client.post(&inbox_url).json(&activity).send().await;
|
let res = client.post(&inbox_url).json(&activity).send().await;
|
||||||
|
@@ -9,8 +9,11 @@ use app::state::AppState;
|
|||||||
use crate::routers::create_router;
|
use crate::routers::create_router;
|
||||||
|
|
||||||
// TODO: middleware, logging, authentication
|
// TODO: middleware, logging, authentication
|
||||||
pub fn setup_router(conn: DatabaseConnection) -> Router {
|
pub fn setup_router(conn: DatabaseConnection, config: &Config) -> Router {
|
||||||
create_router(AppState { conn })
|
create_router(AppState {
|
||||||
|
conn,
|
||||||
|
base_url: config.base_url.clone(),
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn setup_config() -> Config {
|
pub fn setup_config() -> Config {
|
||||||
|
@@ -220,8 +220,7 @@ async fn get_user_by_param(
|
|||||||
// This is the logic from `user_actor_get`.
|
// This is the logic from `user_actor_get`.
|
||||||
match get_user_by_username(&state.conn, &username).await {
|
match get_user_by_username(&state.conn, &username).await {
|
||||||
Ok(Some(user)) => {
|
Ok(Some(user)) => {
|
||||||
let base_url = "http://localhost:3000";
|
let user_url = format!("{}/users/{}", &state.base_url, user.username);
|
||||||
let user_url = format!("{}/users/{}", base_url, user.username);
|
|
||||||
let actor = json!({
|
let actor = json!({
|
||||||
"@context": [
|
"@context": [
|
||||||
"https://www.w3.org/ns/activitystreams",
|
"https://www.w3.org/ns/activitystreams",
|
||||||
@@ -272,13 +271,12 @@ async fn user_outbox_get(
|
|||||||
let thoughts = get_thoughts_by_user(&state.conn, user.id).await?;
|
let thoughts = get_thoughts_by_user(&state.conn, user.id).await?;
|
||||||
|
|
||||||
// Format the outbox as an ActivityPub OrderedCollection
|
// Format the outbox as an ActivityPub OrderedCollection
|
||||||
let base_url = "http://localhost:3000";
|
let outbox_url = format!("{}/users/{}/outbox", &state.base_url, username);
|
||||||
let outbox_url = format!("{}/users/{}/outbox", base_url, username);
|
|
||||||
let items: Vec<Value> = thoughts
|
let items: Vec<Value> = thoughts
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|thought| {
|
.map(|thought| {
|
||||||
let thought_url = format!("{}/thoughts/{}", base_url, thought.id);
|
let thought_url = format!("{}/thoughts/{}", &state.base_url, thought.id);
|
||||||
let author_url = format!("{}/users/{}", base_url, thought.author_username);
|
let author_url = format!("{}/users/{}", &state.base_url, thought.author_username);
|
||||||
json!({
|
json!({
|
||||||
"id": format!("{}/activity", thought_url),
|
"id": format!("{}/activity", thought_url),
|
||||||
"type": "Create",
|
"type": "Create",
|
||||||
|
@@ -45,8 +45,7 @@ pub async fn webfinger(
|
|||||||
_ => return Err((axum::http::StatusCode::NOT_FOUND, "User not found")),
|
_ => return Err((axum::http::StatusCode::NOT_FOUND, "User not found")),
|
||||||
};
|
};
|
||||||
|
|
||||||
let base_url = "http://localhost:3000";
|
let user_url = Url::parse(&format!("{}/users/{}", &state.base_url, user.username)).unwrap();
|
||||||
let user_url = Url::parse(&format!("{}/users/{}", base_url, user.username)).unwrap();
|
|
||||||
|
|
||||||
let response = WebFingerResponse {
|
let response = WebFingerResponse {
|
||||||
subject: query.resource,
|
subject: query.resource,
|
||||||
|
@@ -4,6 +4,7 @@ pub struct Config {
|
|||||||
pub port: u32,
|
pub port: u32,
|
||||||
pub prefork: bool,
|
pub prefork: bool,
|
||||||
pub auth_secret: String,
|
pub auth_secret: String,
|
||||||
|
pub base_url: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Config {
|
impl Config {
|
||||||
@@ -16,7 +17,8 @@ impl Config {
|
|||||||
.parse()
|
.parse()
|
||||||
.expect("PORT is not a number"),
|
.expect("PORT is not a number"),
|
||||||
prefork: std::env::var("PREFORK").is_ok_and(|v| v == "1"),
|
prefork: std::env::var("PREFORK").is_ok_and(|v| v == "1"),
|
||||||
auth_secret: std::env::var("AUTH_SECRET").unwrap_or_else(|_| "secret".into()),
|
auth_secret: std::env::var("AUTH_SECRET").expect("AUTH_SECRET is not set in .env file"),
|
||||||
|
base_url: std::env::var("BASE_URL").expect("BASE_URL is not set in .env file"),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -3,4 +3,5 @@ use sea_orm::DatabaseConnection;
|
|||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub struct AppState {
|
pub struct AppState {
|
||||||
pub conn: DatabaseConnection,
|
pub conn: DatabaseConnection,
|
||||||
|
pub base_url: String,
|
||||||
}
|
}
|
||||||
|
@@ -11,7 +11,9 @@ async fn worker(child_num: u32, db_url: &str, prefork: bool, listener: std::net:
|
|||||||
migrate(&conn).await.expect("Migration failed!");
|
migrate(&conn).await.expect("Migration failed!");
|
||||||
}
|
}
|
||||||
|
|
||||||
let router = setup_router(conn).attach_doc();
|
let config = setup_config();
|
||||||
|
|
||||||
|
let router = setup_router(conn, &config).attach_doc();
|
||||||
|
|
||||||
let listener = tokio::net::TcpListener::from_std(listener).expect("bind to port");
|
let listener = tokio::net::TcpListener::from_std(listener).expect("bind to port");
|
||||||
axum::serve(listener, router).await.expect("start server");
|
axum::serve(listener, router).await.expect("start server");
|
||||||
|
@@ -13,10 +13,17 @@ pub struct TestApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub async fn setup() -> TestApp {
|
pub async fn setup() -> TestApp {
|
||||||
|
std::env::set_var("DATABASE_URL", "sqlite::memory:");
|
||||||
|
std::env::set_var("AUTH_SECRET", "test_secret");
|
||||||
|
std::env::set_var("BASE_URL", "http://localhost:3000");
|
||||||
|
std::env::set_var("HOST", "localhost");
|
||||||
|
std::env::set_var("PORT", "3000");
|
||||||
|
std::env::set_var("LOG_LEVEL", "debug");
|
||||||
|
|
||||||
let db = setup_test_db("sqlite::memory:")
|
let db = setup_test_db("sqlite::memory:")
|
||||||
.await
|
.await
|
||||||
.expect("Failed to set up test db");
|
.expect("Failed to set up test db");
|
||||||
let router = setup_router(db.clone());
|
let router = setup_router(db.clone(), &app::config::Config::from_env());
|
||||||
TestApp { router, db }
|
TestApp { router, db }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user