Implement api to store the state of the frontend

Signed-off-by: trivernis <trivernis@protonmail.com>
pull/4/head
trivernis 3 years ago
parent 4f631511de
commit c201e3f3d6

@ -963,8 +963,8 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f"
[[package]] [[package]]
name = "mediarepo-api" name = "mediarepo-api"
version = "0.14.0" version = "0.16.0"
source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=14f2675f5fe1a11ea3302a623d040e77dcc78080#14f2675f5fe1a11ea3302a623d040e77dcc78080" source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=9599020726eb9db47b9be7a6c41c2942a477ba09#9599020726eb9db47b9be7a6c41c2942a477ba09"
dependencies = [ dependencies = [
"bromine", "bromine",
"chrono", "chrono",

@ -832,8 +832,8 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f"
[[package]] [[package]]
name = "mediarepo-api" name = "mediarepo-api"
version = "0.14.0" version = "0.16.0"
source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=14f2675f5fe1a11ea3302a623d040e77dcc78080#14f2675f5fe1a11ea3302a623d040e77dcc78080" source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=9599020726eb9db47b9be7a6c41c2942a477ba09#9599020726eb9db47b9be7a6c41c2942a477ba09"
dependencies = [ dependencies = [
"bromine", "bromine",
"chrono", "chrono",

@ -36,7 +36,7 @@ features = ["fs", "io-util", "io-std"]
[dependencies.mediarepo-api] [dependencies.mediarepo-api]
git = "https://github.com/Trivernis/mediarepo-api.git" git = "https://github.com/Trivernis/mediarepo-api.git"
rev = "14f2675f5fe1a11ea3302a623d040e77dcc78080" rev = "9599020726eb9db47b9be7a6c41c2942a477ba09"
features = ["bromine"] features = ["bromine"]
[features] [features]

@ -1,4 +1,5 @@
use crate::settings::Settings; use crate::settings::Settings;
use std::path::PathBuf;
use typemap_rev::TypeMapKey; use typemap_rev::TypeMapKey;
pub struct SettingsKey; pub struct SettingsKey;
@ -6,3 +7,9 @@ pub struct SettingsKey;
impl TypeMapKey for SettingsKey { impl TypeMapKey for SettingsKey {
type Value = Settings; type Value = Settings;
} }
pub struct RepoPathKey;
impl TypeMapKey for RepoPathKey {
type Value = PathBuf;
}

@ -887,8 +887,8 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f"
[[package]] [[package]]
name = "mediarepo-api" name = "mediarepo-api"
version = "0.14.0" version = "0.16.0"
source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=14f2675f5fe1a11ea3302a623d040e77dcc78080#14f2675f5fe1a11ea3302a623d040e77dcc78080" source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=9599020726eb9db47b9be7a6c41c2942a477ba09#9599020726eb9db47b9be7a6c41c2942a477ba09"
dependencies = [ dependencies = [
"bromine", "bromine",
"chrono", "chrono",

@ -829,8 +829,8 @@ checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f"
[[package]] [[package]]
name = "mediarepo-api" name = "mediarepo-api"
version = "0.14.0" version = "0.16.0"
source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=14f2675f5fe1a11ea3302a623d040e77dcc78080#14f2675f5fe1a11ea3302a623d040e77dcc78080" source = "git+https://github.com/Trivernis/mediarepo-api.git?rev=9599020726eb9db47b9be7a6c41c2942a477ba09#9599020726eb9db47b9be7a6c41c2942a477ba09"
dependencies = [ dependencies = [
"bromine", "bromine",
"chrono", "chrono",

@ -2,10 +2,11 @@ use mediarepo_core::bromine::prelude::*;
use mediarepo_core::error::{RepoError, RepoResult}; use mediarepo_core::error::{RepoError, RepoResult};
use mediarepo_core::mediarepo_api::types::misc::InfoResponse; use mediarepo_core::mediarepo_api::types::misc::InfoResponse;
use mediarepo_core::settings::Settings; use mediarepo_core::settings::Settings;
use mediarepo_core::type_keys::SettingsKey; use mediarepo_core::type_keys::{RepoPathKey, SettingsKey};
use mediarepo_model::repo::Repo; use mediarepo_model::repo::Repo;
use mediarepo_model::type_keys::RepoKey; use mediarepo_model::type_keys::RepoKey;
use std::net::{IpAddr, SocketAddr}; use std::net::{IpAddr, SocketAddr};
use std::path::PathBuf;
use std::sync::Arc; use std::sync::Arc;
use tokio::net::TcpListener; use tokio::net::TcpListener;
use tokio::task::JoinHandle; use tokio::task::JoinHandle;
@ -18,6 +19,7 @@ mod utils;
pub fn start_tcp_server( pub fn start_tcp_server(
ip: IpAddr, ip: IpAddr,
port_range: (u16, u16), port_range: (u16, u16),
repo_path: PathBuf,
settings: Settings, settings: Settings,
repo: Repo, repo: Repo,
) -> RepoResult<(String, JoinHandle<()>)> { ) -> RepoResult<(String, JoinHandle<()>)> {
@ -30,6 +32,7 @@ pub fn start_tcp_server(
get_builder::<TcpListener>(address) get_builder::<TcpListener>(address)
.insert::<RepoKey>(Arc::new(repo)) .insert::<RepoKey>(Arc::new(repo))
.insert::<SettingsKey>(settings) .insert::<SettingsKey>(settings)
.insert::<RepoPathKey>(repo_path)
.build_server() .build_server()
.await .await
.expect("Failed to start tcp server") .expect("Failed to start tcp server")
@ -42,6 +45,7 @@ pub fn start_tcp_server(
#[tracing::instrument(skip(settings, repo))] #[tracing::instrument(skip(settings, repo))]
pub fn create_unix_socket( pub fn create_unix_socket(
path: std::path::PathBuf, path: std::path::PathBuf,
repo_path: PathBuf,
settings: Settings, settings: Settings,
repo: Repo, repo: Repo,
) -> RepoResult<JoinHandle<()>> { ) -> RepoResult<JoinHandle<()>> {
@ -55,6 +59,7 @@ pub fn create_unix_socket(
get_builder::<UnixListener>(path) get_builder::<UnixListener>(path)
.insert::<RepoKey>(Arc::new(repo)) .insert::<RepoKey>(Arc::new(repo))
.insert::<SettingsKey>(settings) .insert::<SettingsKey>(settings)
.insert::<RepoPathKey>(repo_path)
.build_server() .build_server()
.await .await
.expect("Failed to create unix domain socket"); .expect("Failed to create unix domain socket");

@ -2,10 +2,12 @@ use mediarepo_core::bromine::prelude::AsyncStreamProtocolListener;
use mediarepo_core::bromine::{namespace, namespace::Namespace, IPCBuilder}; use mediarepo_core::bromine::{namespace, namespace::Namespace, IPCBuilder};
pub mod files; pub mod files;
pub mod repo;
pub mod tags; pub mod tags;
pub fn build_namespaces<L: AsyncStreamProtocolListener>(builder: IPCBuilder<L>) -> IPCBuilder<L> { pub fn build_namespaces<L: AsyncStreamProtocolListener>(builder: IPCBuilder<L>) -> IPCBuilder<L> {
builder builder
.add_namespace(namespace!(files::FilesNamespace)) .add_namespace(namespace!(files::FilesNamespace))
.add_namespace(namespace!(tags::TagsNamespace)) .add_namespace(namespace!(tags::TagsNamespace))
.add_namespace(namespace!(repo::RepoNamespace))
} }

@ -0,0 +1,66 @@
use mediarepo_core::bromine::prelude::*;
use mediarepo_core::mediarepo_api::types::repo::FrontendState;
use mediarepo_core::type_keys::{RepoPathKey, SettingsKey};
use std::path::PathBuf;
use tokio::fs;
pub struct RepoNamespace;
impl NamespaceProvider for RepoNamespace {
fn name() -> &'static str {
"repo"
}
fn register(handler: &mut EventHandler) {
events!(handler,
"frontend_state" => Self::frontend_state,
"set_frontend_state" => Self::set_frontend_state
);
}
}
impl RepoNamespace {
#[tracing::instrument(skip_all)]
async fn frontend_state(ctx: &Context, _: Event) -> IPCResult<()> {
let path = get_frontend_state_path(ctx).await?;
let state_string = if path.exists() {
Some(fs::read_to_string(path).await?)
} else {
None
};
ctx.emit_to(
Self::name(),
"frontend_state",
FrontendState {
state: state_string,
},
)
.await?;
Ok(())
}
#[tracing::instrument(skip_all)]
async fn set_frontend_state(ctx: &Context, event: Event) -> IPCResult<()> {
let path = get_frontend_state_path(ctx).await?;
let state = event.payload::<FrontendState>()?.state;
if let Some(state_string) = state {
fs::write(path, state_string.into_bytes()).await?;
} else {
fs::remove_file(path).await?;
}
Ok(())
}
}
async fn get_frontend_state_path(ctx: &Context) -> IPCResult<PathBuf> {
let data = ctx.data.read().await;
let settings = data.get::<SettingsKey>().unwrap();
let repo_path = data.get::<RepoPathKey>().unwrap();
let state_path = repo_path
.join(PathBuf::from(&settings.database_path).parent().unwrap())
.join("frontend-state.json");
Ok(state_path)
}

@ -127,14 +127,19 @@ async fn start_server(opt: Opt) -> RepoResult<()> {
#[cfg(unix)] #[cfg(unix)]
{ {
let socket_path = opt.repo.join("repo.sock"); let socket_path = opt.repo.join("repo.sock");
let handle = let handle = mediarepo_socket::create_unix_socket(
mediarepo_socket::create_unix_socket(socket_path, settings.clone(), repo.clone())?; socket_path,
opt.repo.clone(),
settings.clone(),
repo.clone(),
)?;
handles.push(handle); handles.push(handle);
} }
let (address, tcp_handle) = start_tcp_server( let (address, tcp_handle) = start_tcp_server(
settings.listen_address.clone(), settings.listen_address.clone(),
settings.port_range, settings.port_range,
opt.repo.clone(),
settings, settings,
repo, repo,
)?; )?;

Loading…
Cancel
Save