Begin implementing unshell_lib::manager functionality in server

This commit is contained in:
Michael Mikovsky
2025-12-03 10:15:20 -07:00
parent 7fb9aaf534
commit 11d9454f8c
10 changed files with 85 additions and 146 deletions
+17 -17
View File
@@ -9,10 +9,10 @@ use unshell_lib::{debug, info};
use crate::{
api::{auth, structs::CurrentUser},
database::Database,
server::Server,
};
pub async fn start_api(address: &str, database: Database) {
pub async fn start_api(address: &str, server: Server) {
let listener = TcpListener::bind(address)
.await
.expect("Unable to start listener");
@@ -25,19 +25,19 @@ pub async fn start_api(address: &str, database: Database) {
router = route_get_tree_keys(router);
router = route_trees(router);
axum::serve(listener, router.with_state(database))
axum::serve(listener, router.with_state(server))
.await
.expect("Error serving application");
}
// Route the "keys" api for each tree
fn route_get_trees(router: Router<Database>) -> Router<Database> {
fn route_get_trees(router: Router<Server>) -> Router<Server> {
router.route(
"/api/trees",
get(
async |State(database): State<Database>, Extension(_): Extension<CurrentUser>| {
async |State(server): State<Server>, Extension(_): Extension<CurrentUser>| {
debug!("GET /api/trees");
let result = database.get_trees();
let result = server.get_trees();
Json(serde_json::to_value(result).unwrap())
},
@@ -47,15 +47,15 @@ fn route_get_trees(router: Router<Database>) -> Router<Database> {
}
// Route the "keys" api for each tree
fn route_get_tree_keys(router: Router<Database>) -> Router<Database> {
fn route_get_tree_keys(router: Router<Server>) -> Router<Server> {
router.route(
"/api/keys/{*path}",
get(
async |State(database): State<Database>,
async |State(server): State<Server>,
Path(path): Path<String>,
Extension(_): Extension<CurrentUser>| {
debug!("GET /api/keys/{}", path);
let result = database.get_keys(&path);
let result = server.get_keys(&path);
Json(serde_json::to_value(result).unwrap())
},
@@ -65,15 +65,15 @@ fn route_get_tree_keys(router: Router<Database>) -> Router<Database> {
}
// Route the "values" api to get all the values for each tree
fn route_get_all_tree_values(router: Router<Database>) -> Router<Database> {
fn route_get_all_tree_values(router: Router<Server>) -> Router<Server> {
router.route(
"/api/values/{*path}",
get(
async |State(database): State<Database>,
async |State(server): State<Server>,
Path(path): Path<String>,
Extension(_): Extension<CurrentUser>| {
debug!("GET /api/values/{}", path);
let result = database.all_tree_values(&path);
let result = server.all_tree_values(&path);
Json(serde_json::to_value(result).unwrap())
},
@@ -83,17 +83,17 @@ fn route_get_all_tree_values(router: Router<Database>) -> Router<Database> {
}
// Loop through all trees and add /api/<tree>/<path> POST aand GET listeners for them
fn route_trees(mut router: Router<Database>) -> Router<Database> {
fn route_trees(mut router: Router<Server>) -> Router<Server> {
for tree in crate::DATABASE_TREES.iter() {
router = router
// Route GET requests to this tree
.route(
&format!("/api/{}/{{*path}}", tree),
get(
async |State(database): State<Database>,
async |State(server): State<Server>,
Path(path): Path<String>,
Extension(_): Extension<CurrentUser>| {
let result = database.get_value(tree, &path);
let result = server.get_value(tree, &path);
debug!("GET /api/{}/{}", tree.to_string(), path);
Json(serde_json::to_value(result).unwrap())
@@ -105,11 +105,11 @@ fn route_trees(mut router: Router<Database>) -> Router<Database> {
.route(
&format!("/api/{}/{{*path}}", tree),
post(
async |State(database): State<Database>,
async |State(server): State<Server>,
Path(path): Path<String>,
Extension(_): Extension<CurrentUser>,
body: String| {
let result = database.put_value(tree, &path, &body);
let result = server.put_value(tree, &path, &body);
debug!("POST /api/{}/{}", tree.to_string(), path);
Json(serde_json::to_value(result).unwrap())
+16 -2
View File
@@ -1,8 +1,22 @@
// #![macro_use]
mod api;
pub mod database;
mod server;
pub use api::app::start_api;
pub use server::Server;
#[static_init::dynamic]
static DATABASE_TREES: Vec<&'static str> = vec!["users"];
pub static DATABASE_TREES: Vec<&'static str> = vec!["users"];
#[static_init::dynamic]
pub static DEFAULT_HOST: String = "localhost".to_string();
#[static_init::dynamic]
pub static DATABASE_NAME: String = "database".to_string();
#[static_init::dynamic]
pub static SERVER_CONFIG: unshell_lib::config::PayloadConfig = unshell_lib::config::PayloadConfig {
id: "Server",
components: unshell_lib::get_components(),
runtime_config: Vec::new(),
};
+3 -8
View File
@@ -1,12 +1,7 @@
use unshell_server::{database::Database, start_api};
use unshell_server::{Server, start_api};
use clap::Parser;
use static_init::dynamic;
#[dynamic]
static DEFAULT_HOST: String = "localhost".to_string();
#[dynamic]
static DATABASE_NAME: String = "database".to_string();
use unshell_server::{DATABASE_NAME, DEFAULT_HOST};
/// A fictional versioning CLI
#[derive(Debug, Parser)]
@@ -32,7 +27,7 @@ async fn main() {
unshell_lib::logger::PrettyLogger::init();
let database = Database::new(args.database_name);
let database = Server::new(args.database_name);
start_api(&format!("{}:{}", args.host, args.port), database).await;
}
@@ -3,18 +3,14 @@ use std::collections::HashMap;
use sled::Tree;
use unshell_lib::error;
#[derive(Clone)]
pub struct Database {
db: sled::Db,
}
use crate::server::Server;
impl Database {
pub fn new(database: String) -> Self {
Self {
db: sled::open(database).expect("Failed to open database"),
}
}
// #[derive(Clone)]
// pub struct Database {
// db: sled::Db,
// }
impl Server {
fn get_tree(&self, tree_name: &str) -> Result<Tree, String> {
self.db.open_tree(tree_name).map_err(|e| {
error!("DB Failed to open tree: {}", e);
@@ -77,9 +73,3 @@ impl Database {
.collect::<HashMap<String, String>>())
}
}
impl Drop for Database {
fn drop(&mut self) {
self.db.flush().expect("Failed to flush database on drop");
}
}
+30
View File
@@ -0,0 +1,30 @@
mod database;
mod manager;
use std::sync::{Arc, Mutex};
use unshell_lib::module::Manager;
use crate::SERVER_CONFIG;
#[derive(Clone)]
pub struct Server {
pub manager: Arc<Mutex<Manager>>,
pub db: sled::Db,
}
impl Server {
pub fn new(database: String) -> Self {
Self {
manager: Manager::start(&SERVER_CONFIG, Vec::new()),
db: sled::open(database).expect("Failed to open database"),
}
}
}
impl Drop for Server {
fn drop(&mut self) {
self.db.flush().expect("Failed to flush database on drop");
Manager::join(self.manager.clone());
}
}