diff --git a/.cargo/config.toml b/.cargo/config.toml index a787f80a929722505eb606fac0698c0d96b3a92d..30e7bb4c8e35b04514c60cd9c809c47ed25835c3 100644 --- a/.cargo/config.toml +++ b/.cargo/config.toml @@ -4,3 +4,5 @@ CXX = "/usr/bin/clang++" [profile.release] strip = true +codegen-units = 1 +opt-level = "z" diff --git a/.gitignore b/.gitignore index 32e03d72558d22a7b82a86d7c0b843ceaf6590d5..1122d4f01002e1f9bf100d16ef74e060cc45caf7 100644 --- a/.gitignore +++ b/.gitignore @@ -30,7 +30,8 @@ pnpm-debug.log* # todo *.todo +*.hcl # jetbrains .idea -.fleet \ No newline at end of file +.fleet diff --git a/Cargo.toml b/Cargo.toml index aba0b3ce712f7619eb78d1082834de41b26ee82e..a5f52152131604a357183684886dbd6f48d91c86 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,12 +6,6 @@ license = "MIT" repository = "https://lab.themackabu.dev/self/pmc" description = "PMC is a simple and easy to use PM2 alternative" -[profile.release] -lto = true -codegen-units = 16 -opt-level = "z" -panic = "abort" - [build-dependencies] tar = "0.4.40" chrono = "0.4.31" diff --git a/build.rs b/build.rs index cbe98d7d3489b25460ed0d15004ae0ed3ee0207c..b629391c3cd2fa875adf1d22b645a4a9a63e744f 100644 --- a/build.rs +++ b/build.rs @@ -132,26 +132,28 @@ fn main() { /* profile matching */ match profile.as_str() { "debug" => println!("cargo:rustc-env=PROFILE=debug"), - "release" => println!("cargo:rustc-env=PROFILE=release"), + "release" => { + println!("cargo:rustc-env=PROFILE=release"); + + /* cleanup */ + fs::remove_dir_all(format!("src/webui/dist")).ok(); + + /* pre-build */ + let path = download_node(); + download_then_build(path); + + /* cc linking */ + cxx_build::bridge("src/lib.rs") + .file("lib/bridge.cc") + .file("lib/process.cc") + .file("lib/fork.cc") + .include("lib/include") + .flag_if_supported("-std=c++17") + .compile("bridge"); + } _ => println!("cargo:rustc-env=PROFILE=none"), } - /* cleanup */ - fs::remove_dir_all(format!("src/webui/dist")).ok(); - - /* pre-build */ - let path = download_node(); - download_then_build(path); - - /* cc linking */ - cxx_build::bridge("src/lib.rs") - .file("lib/bridge.cc") - .file("lib/process.cc") - .file("lib/fork.cc") - .include("lib/include") - .flag_if_supported("-std=c++17") - .compile("bridge"); - let watched = vec![ "lib", "src/lib.rs", diff --git a/src/cli/internal.rs b/src/cli/internal.rs index 986ee43a80fde71c7127bf3d94e8911529f1b86e..d5a871fb9690fec2087f67b7e432b3785667dab4 100644 --- a/src/cli/internal.rs +++ b/src/cli/internal.rs @@ -162,9 +162,26 @@ impl<'i> Internal<'i> { } pub fn flush(&mut self) { + println!("{} Applying {}action flushLogs on ({})", *helpers::SUCCESS, self.kind, self.id); + + if !matches!(self.server_name, "internal" | "local") { + let Some(servers) = config::servers().servers else { + crashln!("{} Failed to read servers", *helpers::FAIL) + }; + + if let Some(server) = servers.get(self.server_name) { + self.runner = match Runner::connect(self.server_name.into(), server.get(), false) { + Some(remote) => remote, + None => crashln!("{} Failed to remove (name={}, address={})", *helpers::FAIL, self.server_name, server.address), + }; + } else { + crashln!("{} Server '{}' does not exist", *helpers::FAIL, self.server_name) + }; + } + self.runner.flush(self.id); - println!("{} Log Flushed {}({}) ✓", *helpers::SUCCESS, self.kind, self.id); - log!("process log flushed (id={})", self.id); + println!("{} Flushed Logs {}({}) ✓", *helpers::SUCCESS, self.kind, self.id); + log!("process logs cleaned (id={})", self.id); } pub fn info(&self, format: &String) { diff --git a/src/cli/mod.rs b/src/cli/mod.rs index 6d2553c6d78397f38a2fa9b81d8f338c891582ad..ae0c64598b02e1d1069eadc9dd7d763101db7210 100644 --- a/src/cli/mod.rs +++ b/src/cli/mod.rs @@ -147,6 +147,7 @@ pub fn logs(item: &Item, lines: &usize, server_name: &String) { } } +// combine into a single function that handles multiple pub fn env(item: &Item, server_name: &String) { let runner: Runner = Runner::new(); let (kind, _) = format(server_name); @@ -171,4 +172,4 @@ pub fn flush(item: &Item, server_name: &String) { None => crashln!("{} Process ({name}) not found", *helpers::FAIL), }, } -} \ No newline at end of file +} diff --git a/src/daemon/api/routes.rs b/src/daemon/api/routes.rs index 384b26098740ad76213619ffed1dbf1d5e331279..e5435de1c3d347fabe4bdcd4175ec8746932f15e 100644 --- a/src/daemon/api/routes.rs +++ b/src/daemon/api/routes.rs @@ -759,13 +759,14 @@ pub async fn action_handler(id: usize, body: Json, _t: Token) -> Res timer.observe_duration(); Ok(Json(attempt(true, method))) } - "flush" => { + "flush" | "clean" => { runner.flush(id); + timer.observe_duration(); Ok(Json(attempt(true, method))) - }, + } _ => { timer.observe_duration(); - Err(not_found("Process was not found")) + Err(not_found("Invalid action attempt")) } } } else { diff --git a/src/main.rs b/src/main.rs index d34660bb5939f8f5720c488b36aedb17380b1171..7de5302a5a34a4e7303bafdba72f6c7eea6f13f9 100644 --- a/src/main.rs +++ b/src/main.rs @@ -31,7 +31,7 @@ struct Cli { #[derive(Subcommand)] enum Daemon { /// Reset process index - #[command(visible_alias = "clean")] + #[command(visible_alias = "reset_position")] Reset, /// Stop daemon #[command(visible_alias = "kill")] @@ -182,7 +182,7 @@ enum Commands { }, /// Flush a process log - #[command(visible_alias = "fl")] + #[command(visible_alias = "clean", visible_alias = "log_rotate")] Flush { #[clap(value_parser = cli::validate::)] item: Item, @@ -191,7 +191,6 @@ enum Commands { server: Option, }, - /// Daemon management #[command(visible_alias = "agent", visible_alias = "bgd")] Daemon { diff --git a/src/process/http.rs b/src/process/http.rs index cbd85423af78f281a9078dda1c2512aaa884f0f6..ffd04c134b9377d3da7329025bb94e1ac6d17577 100644 --- a/src/process/http.rs +++ b/src/process/http.rs @@ -86,6 +86,7 @@ pub fn rename(Remote { address, token, .. }: &Remote, id: usize, name: String) - Ok(client.post(fmtstr!("{address}/process/{id}/rename")).body(name).headers(headers).send()?) } +// merge into one function pub fn stop(Remote { address, token, .. }: &Remote, id: usize) -> Result { let (client, headers) = sync::client(token); let content = ActionBody { method: string!("stop") }; @@ -100,9 +101,9 @@ pub fn remove(Remote { address, token, .. }: &Remote, id: usize) -> Result Result { +pub fn flush(Remote { address, token, .. }: &Remote, id: usize) -> Result { let (client, headers) = sync::client(token); let content = ActionBody { method: string!("flush") }; Ok(client.post(fmtstr!("{address}/process/{id}/action")).json(&content).headers(headers).send()?) -} \ No newline at end of file +} diff --git a/src/process/mod.rs b/src/process/mod.rs index 2cf3f3b8c5ba73414db91abc39bf417a72642b51..cc9dc5d31a8f528f0302d78771e1a0e895ba0c95 100644 --- a/src/process/mod.rs +++ b/src/process/mod.rs @@ -9,6 +9,7 @@ use crate::{ use std::{ env, + fs::File, path::PathBuf, sync::{Arc, Mutex}, }; @@ -173,18 +174,6 @@ impl Status { } } -impl LogInfo { - pub fn flush(&self) { - if let Err(err) = std::fs::remove_file(&self.out) { - crashln!("Failed to remove log {0} file: {err}", self.out); - } - - if let Err(err) = std::fs::remove_file(&self.error) { - crashln!("Failed to remove log {0} file: {err}", self.error); - } - } -} - macro_rules! lock { ($runner:expr) => {{ match $runner.lock() { @@ -410,6 +399,18 @@ impl Runner { return self; } + pub fn flush(&mut self, id: usize) -> &mut Self { + if let Some(remote) = &self.remote { + if let Err(err) = http::flush(remote, id) { + crashln!("{} Failed to flush process {id}\nError: {:#?}", *helpers::FAIL, err); + }; + } else { + self.process(id).logs().flush(); + } + + return self; + } + pub fn rename(&mut self, id: usize, name: String) -> &mut Self { if let Some(remote) = &self.remote { if let Err(err) = http::rename(remote, id, name) { @@ -506,20 +507,19 @@ impl Runner { return processes; } +} - pub fn flush(&mut self, id: usize) -> &mut Self { - if let Some(remote) = &self.remote { - if let Err(err) = http::flush(remote, id) { - crashln!("{} Failed to flush process {id}\nError: {:#?}", *helpers::FAIL, err); - }; - } else { - match self.info(id) { - Some(item) => item.logs().flush(), - None => crashln!("{} Process ({id}) not found", *helpers::FAIL), - }; +impl LogInfo { + pub fn flush(&self) { + if let Err(err) = File::create(&self.out) { + log::debug!("{err}"); + crashln!("{} Failed to purge logs (path={})", *helpers::FAIL, self.error); } - self + if let Err(err) = File::create(&self.error) { + log::debug!("{err}"); + crashln!("{} Failed to purge logs (path={})", *helpers::FAIL, self.error); + } } } diff --git a/src/webui/src/components/react/index.tsx b/src/webui/src/components/react/index.tsx index 65ed5b9f76e69fff1063604794562696fadb4cbc..417ee212d5174991c61f3f9dc01f1a0e19606f7b 100644 --- a/src/webui/src/components/react/index.tsx +++ b/src/webui/src/components/react/index.tsx @@ -1,8 +1,8 @@ import { api } from '@/api'; import Rename from '@/components/react/rename'; import { useEffect, useState, Fragment } from 'react'; -import { Menu, MenuItem, MenuItems, MenuButton, Transition } from '@headlessui/react'; import { EllipsisVerticalIcon } from '@heroicons/react/20/solid'; +import { Menu, MenuItem, MenuItems, MenuButton, Transition } from '@headlessui/react'; const Index = (props: { base: string }) => { const [items, setItems] = useState([]); @@ -59,7 +59,9 @@ const Index = (props: { base: string }) => { leave="transition ease-in duration-75" leaveFrom="transform opacity-100 scale-100" leaveTo="transform opacity-0 scale-95"> - +
{({ focus }) => ( @@ -87,8 +89,15 @@ const Index = (props: { base: string }) => {
diff --git a/src/webui/src/components/react/rename.tsx b/src/webui/src/components/react/rename.tsx index aa4f22c7f97242ae348d1e6272602bc642209cde..43cc6a12153d322d0785dcbde6803a25c3026fc8 100644 --- a/src/webui/src/components/react/rename.tsx +++ b/src/webui/src/components/react/rename.tsx @@ -29,7 +29,7 @@ const Rename = (props: { base: string; process: number; callback: any; old: stri setOpen(close)}>
-
+
-
+
diff --git a/src/webui/src/components/react/view.tsx b/src/webui/src/components/react/view.tsx index 1cfb78f964059d49248bded80f6a87354f27b8e9..783911267f5a497e839014739a77a380190e6558 100644 --- a/src/webui/src/components/react/view.tsx +++ b/src/webui/src/components/react/view.tsx @@ -280,7 +280,7 @@ const View = (props: { id: string; base: string }) => { return ( -
+

@@ -297,7 +297,7 @@ const View = (props: { id: string; base: string }) => {

{item.info.command}

-
+
-
+
{stats.map((stat: any, index: number) => (

{stat.name}

- {stat.value} + {stat.value} {stat.unit ? {stat.unit} : null}

diff --git a/src/webui/src/pages/view.astro b/src/webui/src/pages/view.astro index 52e9b52b7371fac0c44c5b32b2b74cf422eff08a..9462514d48cd02e9b08692fb9a389c31fce15e93 100644 --- a/src/webui/src/pages/view.astro +++ b/src/webui/src/pages/view.astro @@ -5,7 +5,6 @@ import ViewPage from '@/components/react/view'; import { SITE_TITLE, SITE_DESCRIPTION } from '@/consts'; --- -