From 831125bdf0e1af344a457d5b81dff03987769d4a Mon Sep 17 00:00:00 2001 From: Sebastian Moser Date: Sun, 4 Feb 2024 21:15:18 +0100 Subject: [PATCH] towards the next try of mize... --- .gitignore | 2 +- Cargo.lock | 1571 +++++++++++++++++++++++++++++++++ Cargo.toml | 31 +- flake.lock | 61 ++ flake.nix | 17 + src/cli/call.rs | 4 + src/cli/daemon.rs | 63 ++ src/cli/get.rs | 23 + src/cli/mod.rs | 16 + src/cli/mount.rs | 4 + src/cli/print.rs | 4 + src/cli/serve.rs | 4 + src/cli/set.rs | 4 + src/error.rs | 271 ++++++ src/instance/connection.rs | 74 ++ src/instance/mod.rs | 213 +++++ src/instance/peer.rs | 1 + src/instance/web.rs | 239 +++++ src/item.rs | 234 +++++ src/itemstore.rs | 267 ++++++ src/lib.rs | 16 + src/main.rs | 325 +++++++ src/proto.rs | 7 + types/mize/instance/item.json | 7 + 24 files changed, 3445 insertions(+), 13 deletions(-) create mode 100644 Cargo.lock create mode 100644 flake.lock create mode 100644 flake.nix create mode 100644 src/cli/call.rs create mode 100644 src/cli/daemon.rs create mode 100644 src/cli/get.rs create mode 100644 src/cli/mod.rs create mode 100644 src/cli/mount.rs create mode 100644 src/cli/print.rs create mode 100644 src/cli/serve.rs create mode 100644 src/cli/set.rs create mode 100644 src/error.rs create mode 100644 src/instance/connection.rs create mode 100644 src/instance/mod.rs create mode 100644 src/instance/peer.rs create mode 100644 src/instance/web.rs create mode 100644 src/item.rs create mode 100644 src/itemstore.rs create mode 100644 src/lib.rs create mode 100644 src/main.rs create mode 100644 src/proto.rs create mode 100644 types/mize/instance/item.json diff --git a/.gitignore b/.gitignore index 776ee59..3f969db 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,6 @@ /target -/mize-folder +/folder # I put testing stuff for this projekt that I don't want to push to github into a folder called gitignore /gitignore diff --git a/Cargo.lock b/Cargo.lock new file mode 100644 index 0000000..50865c0 --- /dev/null +++ b/Cargo.lock @@ -0,0 +1,1571 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "addr2line" +version = "0.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb" +dependencies = [ + "gimli", +] + +[[package]] +name = "adler" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" + +[[package]] +name = "aho-corasick" +version = "1.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b2969dcb958b36655471fc61f7e416fa76033bdd4bfed0678d8fee1e2d07a1f0" +dependencies = [ + "memchr", +] + +[[package]] +name = "anstream" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d664a92ecae85fd0a7392615844904654d1d5f5514837f471ddef4a057aba1b6" +dependencies = [ + "anstyle", + "anstyle-parse", + "anstyle-query", + "anstyle-wincon", + "colorchoice", + "utf8parse", +] + +[[package]] +name = "anstyle" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7079075b41f533b8c61d2a4d073c4676e1f8b249ff94a393b0595db304e0dd87" + +[[package]] +name = "anstyle-parse" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c75ac65da39e5fe5ab759307499ddad880d724eed2f6ce5b5e8a26f4f387928c" +dependencies = [ + "utf8parse", +] + +[[package]] +name = "anstyle-query" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e28923312444cdd728e4738b3f9c9cac739500909bb3d3c94b43551b16517648" +dependencies = [ + "windows-sys 0.52.0", +] + +[[package]] +name = "anstyle-wincon" +version = "3.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1cd54b81ec8d6180e24654d0b371ad22fc3dd083b6ff8ba325b72e00c87660a7" +dependencies = [ + "anstyle", + "windows-sys 0.52.0", +] + +[[package]] +name = "async-trait" +version = "0.1.75" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fdf6721fb0140e4f897002dd086c06f6c27775df19cfe1fccb21181a48fd2c98" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.42", +] + +[[package]] +name = "autocfg" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" + +[[package]] +name = "axum" +version = "0.6.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b829e4e32b91e643de6eafe82b1d90675f5874230191a4ffbc1b336dec4d6bf" +dependencies = [ + "async-trait", + "axum-core", + "base64", + "bitflags 1.3.2", + "bytes", + "futures-util", + "headers", + "http", + "http-body", + "hyper", + "itoa", + "matchit", + "memchr", + "mime", + "percent-encoding", + "pin-project-lite", + "rustversion", + "serde", + "serde_json", + "serde_path_to_error", + "serde_urlencoded", + "sha1", + "sync_wrapper", + "tokio", + "tokio-tungstenite", + "tower", + "tower-layer", + "tower-service", +] + +[[package]] +name = "axum-core" +version = "0.3.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "759fa577a247914fd3f7f76d62972792636412fbfd634cd452f6a385a74d2d2c" +dependencies = [ + "async-trait", + "bytes", + "futures-util", + "http", + "http-body", + "mime", + "rustversion", + "tower-layer", + "tower-service", +] + +[[package]] +name = "axum-extra" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f9a320103719de37b7b4da4c8eb629d4573f6bcfd3dfe80d3208806895ccf81d" +dependencies = [ + "axum", + "bytes", + "futures-util", + "http", + "mime", + "pin-project-lite", + "tokio", + "tower", + "tower-http", + "tower-layer", + "tower-service", +] + +[[package]] +name = "axum-macros" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cdca6a10ecad987bda04e95606ef85a5417dcaac1a78455242d72e031e2b6b62" +dependencies = [ + "heck", + "proc-macro2", + "quote", + "syn 2.0.42", +] + +[[package]] +name = "backtrace" +version = "0.3.69" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2089b7e3f35b9dd2d0ed921ead4f6d318c27680d4a5bd167b3ee120edb105837" +dependencies = [ + "addr2line", + "cc", + "cfg-if", + "libc", + "miniz_oxide", + "object", + "rustc-demangle", +] + +[[package]] +name = "base64" +version = "0.21.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "35636a1494ede3b646cc98f74f8e62c773a38a659ebc777a2cf26b9b74171df9" + +[[package]] +name = "bitflags" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" + +[[package]] +name = "bitflags" +version = "2.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "327762f6e5a765692301e5bb513e0d9fef63be86bbc14528052b1cd3e6f03e07" + +[[package]] +name = "block-buffer" +version = "0.10.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3078c7629b62d3f0439517fa394996acacc5cbc91c5a20d8c658e77abd503a71" +dependencies = [ + "generic-array", +] + +[[package]] +name = "byteorder" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" + +[[package]] +name = "bytes" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2bd12c1caf447e69cd4528f47f94d203fd2582878ecb9e9465484c4148a8223" + +[[package]] +name = "cc" +version = "1.0.83" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1174fb0b6ec23863f8b971027804a42614e347eafb0a95bf0b12cdae21fc4d0" +dependencies = [ + "libc", +] + +[[package]] +name = "cfg-if" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" + +[[package]] +name = "clap" +version = "4.4.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfaff671f6b22ca62406885ece523383b9b64022e341e53e009a62ebc47a45f2" +dependencies = [ + "clap_builder", +] + +[[package]] +name = "clap_builder" +version = "4.4.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a216b506622bb1d316cd51328dce24e07bdff4a6128a47c7e7fad11878d5adbb" +dependencies = [ + "anstream", + "anstyle", + "clap_lex", + "strsim", +] + +[[package]] +name = "clap_lex" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "702fc72eb24e5a1e48ce58027a675bc24edd52096d5397d4aea7c6dd9eca0bd1" + +[[package]] +name = "colorchoice" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7" + +[[package]] +name = "colored" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cbf2150cce219b664a8a70df7a1f933836724b503f8a413af9365b4dcc4d90b8" +dependencies = [ + "lazy_static", + "windows-sys 0.48.0", +] + +[[package]] +name = "convert_case" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6245d59a3e82a7fc217c5828a6692dbc6dfb63a0c8c90495621f7b9d79704a0e" + +[[package]] +name = "cpufeatures" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce420fe07aecd3e67c5f910618fe65e94158f6dcc0adf44e00d69ce2bdfe0fd0" +dependencies = [ + "libc", +] + +[[package]] +name = "crypto-common" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1bfb12502f3fc46cca1bb51ac28df9d618d813cdc3d2f25b9fe775a34af26bb3" +dependencies = [ + "generic-array", + "typenum", +] + +[[package]] +name = "daemonize" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ab8bfdaacb3c887a54d41bdf48d3af8873b3f5566469f8ba21b92057509f116e" +dependencies = [ + "libc", +] + +[[package]] +name = "data-encoding" +version = "2.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7e962a19be5cfc3f3bf6dd8f61eb50107f356ad6270fbb3ed41476571db78be5" + +[[package]] +name = "derive_more" +version = "0.99.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4fb810d30a7c1953f91334de7244731fc3f3c10d7fe163338a35b9f640960321" +dependencies = [ + "convert_case", + "proc-macro2", + "quote", + "rustc_version", + "syn 1.0.109", +] + +[[package]] +name = "digest" +version = "0.10.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ed9a281f7bc9b7576e61468ba615a66a5c8cfdff42420a70aa82701a3b1e292" +dependencies = [ + "block-buffer", + "crypto-common", +] + +[[package]] +name = "env_logger" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "95b3f3e67048839cb0d0781f445682a35113da7121f7c949db0e2be96a4fbece" +dependencies = [ + "humantime", + "is-terminal", + "log", + "regex", + "termcolor", +] + +[[package]] +name = "errno" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a258e46cdc063eb8519c00b9fc845fc47bcfca4130e2f08e88665ceda8474245" +dependencies = [ + "libc", + "windows-sys 0.52.0", +] + +[[package]] +name = "fnv" +version = "1.0.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" + +[[package]] +name = "form_urlencoded" +version = "1.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e13624c2627564efccf4934284bdd98cbaa14e79b0b5a141218e507b3a823456" +dependencies = [ + "percent-encoding", +] + +[[package]] +name = "futures-channel" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff4dd66668b557604244583e3e1e1eada8c5c2e96a6d0d6653ede395b78bbacb" +dependencies = [ + "futures-core", +] + +[[package]] +name = "futures-core" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eb1d22c66e66d9d72e1758f0bd7d4fd0bee04cad842ee34587d68c07e45d088c" + +[[package]] +name = "futures-macro" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "53b153fd91e4b0147f4aced87be237c98248656bb01050b96bf3ee89220a8ddb" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.42", +] + +[[package]] +name = "futures-sink" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e36d3378ee38c2a36ad710c5d30c2911d752cb941c00c72dbabfb786a7970817" + +[[package]] +name = "futures-task" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "efd193069b0ddadc69c46389b740bbccdd97203899b48d09c5f7969591d6bae2" + +[[package]] +name = "futures-util" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a19526d624e703a3179b3d322efec918b6246ea0fa51d41124525f00f1cc8104" +dependencies = [ + "futures-core", + "futures-macro", + "futures-sink", + "futures-task", + "pin-project-lite", + "pin-utils", + "slab", +] + +[[package]] +name = "generic-array" +version = "0.14.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85649ca51fd72272d7821adaf274ad91c288277713d9c18820d8499a7ff69e9a" +dependencies = [ + "typenum", + "version_check", +] + +[[package]] +name = "getrandom" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fe9006bed769170c11f845cf00c7c1e9092aeb3f268e007c3e760ac68008070f" +dependencies = [ + "cfg-if", + "libc", + "wasi", +] + +[[package]] +name = "gimli" +version = "0.28.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4271d37baee1b8c7e4b708028c57d816cf9d2434acb33a549475f78c181f6253" + +[[package]] +name = "half" +version = "1.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eabb4a44450da02c90444cf74558da904edde8fb4e9035a9a6a4e15445af0bd7" + +[[package]] +name = "headers" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "06683b93020a07e3dbcf5f8c0f6d40080d725bea7936fc01ad345c01b97dc270" +dependencies = [ + "base64", + "bytes", + "headers-core", + "http", + "httpdate", + "mime", + "sha1", +] + +[[package]] +name = "headers-core" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7f66481bfee273957b1f20485a4ff3362987f85b2c236580d81b4eb7a326429" +dependencies = [ + "http", +] + +[[package]] +name = "heck" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8" + +[[package]] +name = "hermit-abi" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d77f7ec81a6d05a3abb01ab6eb7590f6083d08449fe5a1c8b1e620283546ccb7" + +[[package]] +name = "home" +version = "0.5.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3d1354bf6b7235cb4a0576c2619fd4ed18183f689b12b006a0ee7329eeff9a5" +dependencies = [ + "windows-sys 0.52.0", +] + +[[package]] +name = "http" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8947b1a6fad4393052c7ba1f4cd97bed3e953a95c79c92ad9b051a04611d9fbb" +dependencies = [ + "bytes", + "fnv", + "itoa", +] + +[[package]] +name = "http-body" +version = "0.4.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7ceab25649e9960c0311ea418d17bee82c0dcec1bd053b5f9a66e265a693bed2" +dependencies = [ + "bytes", + "http", + "pin-project-lite", +] + +[[package]] +name = "http-range-header" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "add0ab9360ddbd88cfeb3bd9574a1d85cfdfa14db10b3e21d3700dbc4328758f" + +[[package]] +name = "httparse" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d897f394bad6a705d5f4104762e116a75639e470d80901eed05a860a95cb1904" + +[[package]] +name = "httpdate" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df3b46402a9d5adb4c86a0cf463f42e19994e3ee891101b1841f30a545cb49a9" + +[[package]] +name = "humantime" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4" + +[[package]] +name = "hyper" +version = "0.14.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bf96e135eb83a2a8ddf766e426a841d8ddd7449d5f00d34ea02b41d2f19eef80" +dependencies = [ + "bytes", + "futures-channel", + "futures-core", + "futures-util", + "http", + "http-body", + "httparse", + "httpdate", + "itoa", + "pin-project-lite", + "socket2", + "tokio", + "tower-service", + "tracing", + "want", +] + +[[package]] +name = "idna" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "634d9b1461af396cad843f47fdba5597a4f9e6ddd4bfb6ff5d85028c25cb12f6" +dependencies = [ + "unicode-bidi", + "unicode-normalization", +] + +[[package]] +name = "is-terminal" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b" +dependencies = [ + "hermit-abi", + "rustix", + "windows-sys 0.48.0", +] + +[[package]] +name = "itoa" +version = "1.0.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b1a46d1a171d865aa5f83f92695765caa047a9b4cbae2cbf37dbd613a793fd4c" + +[[package]] +name = "lazy_static" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" + +[[package]] +name = "libc" +version = "0.2.151" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "302d7ab3130588088d277783b1e2d2e10c9e9e4a16dd9050e6ec93fb3e7048f4" + +[[package]] +name = "linux-raw-sys" +version = "0.4.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c4cd1a83af159aa67994778be9070f0ae1bd732942279cabb14f86f986a21456" + +[[package]] +name = "lock_api" +version = "0.4.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c168f8615b12bc01f9c17e2eb0cc07dcae1940121185446edc3744920e8ef45" +dependencies = [ + "autocfg", + "scopeguard", +] + +[[package]] +name = "log" +version = "0.4.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b5e6163cb8c49088c2c36f57875e58ccd8c87c7427f7fbd50ea6710b2f3f2e8f" + +[[package]] +name = "matchit" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0e7465ac9959cc2b1404e8e2367b43684a6d13790fe23056cc8c6c5a6b7bcb94" + +[[package]] +name = "memchr" +version = "2.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f665ee40bc4a3c5590afb1e9677db74a508659dfd71e126420da8274909a0167" + +[[package]] +name = "mime" +version = "0.3.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6877bb514081ee2a7ff5ef9de3281f14a4dd4bceac4c09388074a6b5df8a139a" + +[[package]] +name = "mime_guess" +version = "2.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4192263c238a5f0d0c6bfd21f336a313a4ce1c450542449ca191bb657b4642ef" +dependencies = [ + "mime", + "unicase", +] + +[[package]] +name = "miniz_oxide" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7810e0be55b428ada41041c41f32c9f1a42817901b4ccf45fa3d4b6561e74c7" +dependencies = [ + "adler", +] + +[[package]] +name = "mio" +version = "0.8.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f3d0b296e374a4e6f3c7b0a1f5a51d748a0d34c85e7dc48fc3fa9a87657fe09" +dependencies = [ + "libc", + "wasi", + "windows-sys 0.48.0", +] + +[[package]] +name = "mize" +version = "0.1.1" +dependencies = [ + "axum", + "axum-extra", + "axum-macros", + "clap", + "colored", + "daemonize", + "derive_more", + "env_logger", + "futures-util", + "home", + "log", + "nix", + "serde", + "serde_cbor", + "serde_json", + "tokio", + "tokio-stream", + "toml", + "uuid", +] + +[[package]] +name = "nix" +version = "0.27.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2eb04e9c688eff1c89d72b407f168cf79bb9e867a9d3323ed6c01519eb9cc053" +dependencies = [ + "bitflags 2.4.1", + "cfg-if", + "libc", +] + +[[package]] +name = "num_cpus" +version = "1.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +dependencies = [ + "hermit-abi", + "libc", +] + +[[package]] +name = "object" +version = "0.32.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9cf5f9dd3933bd50a9e1f149ec995f39ae2c496d31fd772c1fd45ebc27e902b0" +dependencies = [ + "memchr", +] + +[[package]] +name = "once_cell" +version = "1.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3fdb12b2476b595f9358c5161aa467c2438859caa136dec86c26fdd2efe17b92" + +[[package]] +name = "parking_lot" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" +dependencies = [ + "lock_api", + "parking_lot_core", +] + +[[package]] +name = "parking_lot_core" +version = "0.9.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4c42a9226546d68acdd9c0a280d17ce19bfe27a46bf68784e4066115788d008e" +dependencies = [ + "cfg-if", + "libc", + "redox_syscall", + "smallvec", + "windows-targets 0.48.5", +] + +[[package]] +name = "percent-encoding" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" + +[[package]] +name = "pin-project" +version = "1.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fda4ed1c6c173e3fc7a83629421152e01d7b1f9b7f65fb301e490e8cfc656422" +dependencies = [ + "pin-project-internal", +] + +[[package]] +name = "pin-project-internal" +version = "1.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4359fd9c9171ec6e8c62926d6faaf553a8dc3f64e1507e76da7911b4f6a04405" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.42", +] + +[[package]] +name = "pin-project-lite" +version = "0.2.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8afb450f006bf6385ca15ef45d71d2288452bc3683ce2e2cacc0d18e4be60b58" + +[[package]] +name = "pin-utils" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" + +[[package]] +name = "ppv-lite86" +version = "0.2.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de" + +[[package]] +name = "proc-macro2" +version = "1.0.71" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "75cb1540fadbd5b8fbccc4dddad2734eba435053f725621c070711a14bb5f4b8" +dependencies = [ + "unicode-ident", +] + +[[package]] +name = "quote" +version = "1.0.33" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5267fca4496028628a95160fc423a33e8b2e6af8a5302579e322e4b520293cae" +dependencies = [ + "proc-macro2", +] + +[[package]] +name = "rand" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" +dependencies = [ + "libc", + "rand_chacha", + "rand_core", +] + +[[package]] +name = "rand_chacha" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" +dependencies = [ + "ppv-lite86", + "rand_core", +] + +[[package]] +name = "rand_core" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" +dependencies = [ + "getrandom", +] + +[[package]] +name = "redox_syscall" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4722d768eff46b75989dd134e5c353f0d6296e5aaa3132e776cbdb56be7731aa" +dependencies = [ + "bitflags 1.3.2", +] + +[[package]] +name = "regex" +version = "1.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "380b951a9c5e80ddfd6136919eef32310721aa4aacd4889a8d39124b026ab343" +dependencies = [ + "aho-corasick", + "memchr", + "regex-automata", + "regex-syntax", +] + +[[package]] +name = "regex-automata" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f804c7828047e88b2d32e2d7fe5a105da8ee3264f01902f796c8e067dc2483f" +dependencies = [ + "aho-corasick", + "memchr", + "regex-syntax", +] + +[[package]] +name = "regex-syntax" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c08c74e62047bb2de4ff487b251e4a92e24f48745648451635cec7d591162d9f" + +[[package]] +name = "rustc-demangle" +version = "0.1.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" + +[[package]] +name = "rustc_version" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366" +dependencies = [ + "semver", +] + +[[package]] +name = "rustix" +version = "0.38.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72e572a5e8ca657d7366229cdde4bd14c4eb5499a9573d4d366fe1b599daa316" +dependencies = [ + "bitflags 2.4.1", + "errno", + "libc", + "linux-raw-sys", + "windows-sys 0.52.0", +] + +[[package]] +name = "rustversion" +version = "1.0.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7ffc183a10b4478d04cbbbfc96d0873219d962dd5accaff2ffbd4ceb7df837f4" + +[[package]] +name = "ryu" +version = "1.0.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f98d2aa92eebf49b69786be48e4477826b256916e84a57ff2a4f21923b48eb4c" + +[[package]] +name = "scopeguard" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" + +[[package]] +name = "semver" +version = "1.0.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "836fa6a3e1e547f9a2c4040802ec865b5d85f4014efe00555d7090a3dcaa1090" + +[[package]] +name = "serde" +version = "1.0.193" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25dd9975e68d0cb5aa1120c288333fc98731bd1dd12f561e468ea4728c042b89" +dependencies = [ + "serde_derive", +] + +[[package]] +name = "serde_cbor" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2bef2ebfde456fb76bbcf9f59315333decc4fda0b2b44b420243c11e0f5ec1f5" +dependencies = [ + "half", + "serde", +] + +[[package]] +name = "serde_derive" +version = "1.0.193" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "43576ca501357b9b071ac53cdc7da8ef0cbd9493d8df094cd821777ea6e894d3" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.42", +] + +[[package]] +name = "serde_json" +version = "1.0.108" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d1c7e3eac408d115102c4c24ad393e0821bb3a5df4d506a80f85f7a742a526b" +dependencies = [ + "itoa", + "ryu", + "serde", +] + +[[package]] +name = "serde_path_to_error" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4beec8bce849d58d06238cb50db2e1c417cfeafa4c63f692b15c82b7c80f8335" +dependencies = [ + "itoa", + "serde", +] + +[[package]] +name = "serde_urlencoded" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" +dependencies = [ + "form_urlencoded", + "itoa", + "ryu", + "serde", +] + +[[package]] +name = "sha1" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3bf829a2d51ab4a5ddf1352d8470c140cadc8301b2ae1789db023f01cedd6ba" +dependencies = [ + "cfg-if", + "cpufeatures", + "digest", +] + +[[package]] +name = "signal-hook-registry" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d8229b473baa5980ac72ef434c4415e70c4b5e71b423043adb4ba059f89c99a1" +dependencies = [ + "libc", +] + +[[package]] +name = "slab" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67" +dependencies = [ + "autocfg", +] + +[[package]] +name = "smallvec" +version = "1.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4dccd0940a2dcdf68d092b8cbab7dc0ad8fa938bf95787e1b916b0e3d0e8e970" + +[[package]] +name = "socket2" +version = "0.5.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b5fac59a5cb5dd637972e5fca70daf0523c9067fcdc4842f053dae04a18f8e9" +dependencies = [ + "libc", + "windows-sys 0.48.0", +] + +[[package]] +name = "strsim" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" + +[[package]] +name = "syn" +version = "1.0.109" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" +dependencies = [ + "proc-macro2", + "quote", + "unicode-ident", +] + +[[package]] +name = "syn" +version = "2.0.42" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b7d0a2c048d661a1a59fcd7355baa232f7ed34e0ee4df2eef3c1c1c0d3852d8" +dependencies = [ + "proc-macro2", + "quote", + "unicode-ident", +] + +[[package]] +name = "sync_wrapper" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2047c6ded9c721764247e62cd3b03c09ffc529b2ba5b10ec482ae507a4a70160" + +[[package]] +name = "termcolor" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff1bc3d3f05aff0403e8ac0d92ced918ec05b666a43f83297ccef5bea8a3d449" +dependencies = [ + "winapi-util", +] + +[[package]] +name = "thiserror" +version = "1.0.51" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f11c217e1416d6f036b870f14e0413d480dbf28edbee1f877abaf0206af43bb7" +dependencies = [ + "thiserror-impl", +] + +[[package]] +name = "thiserror-impl" +version = "1.0.51" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "01742297787513b79cf8e29d1056ede1313e2420b7b3b15d0a768b4921f549df" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.42", +] + +[[package]] +name = "tinyvec" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" +dependencies = [ + "tinyvec_macros", +] + +[[package]] +name = "tinyvec_macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" + +[[package]] +name = "tokio" +version = "1.35.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c89b4efa943be685f629b149f53829423f8f5531ea21249408e8e2f8671ec104" +dependencies = [ + "backtrace", + "bytes", + "libc", + "mio", + "num_cpus", + "parking_lot", + "pin-project-lite", + "signal-hook-registry", + "socket2", + "tokio-macros", + "windows-sys 0.48.0", +] + +[[package]] +name = "tokio-macros" +version = "2.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b8a1e28f2deaa14e508979454cb3a223b10b938b45af148bc0986de36f1923b" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.42", +] + +[[package]] +name = "tokio-stream" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "397c988d37662c7dda6d2208364a706264bf3d6138b11d436cbac0ad38832842" +dependencies = [ + "futures-core", + "pin-project-lite", + "tokio", +] + +[[package]] +name = "tokio-tungstenite" +version = "0.20.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "212d5dcb2a1ce06d81107c3d0ffa3121fe974b73f068c8282cb1c32328113b6c" +dependencies = [ + "futures-util", + "log", + "tokio", + "tungstenite", +] + +[[package]] +name = "tokio-util" +version = "0.7.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5419f34732d9eb6ee4c3578b7989078579b7f039cbbb9ca2c4da015749371e15" +dependencies = [ + "bytes", + "futures-core", + "futures-sink", + "pin-project-lite", + "tokio", +] + +[[package]] +name = "toml" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f4f7f0dd8d50a853a531c426359045b1998f04219d88799810762cd4ad314234" +dependencies = [ + "serde", +] + +[[package]] +name = "tower" +version = "0.4.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b8fa9be0de6cf49e536ce1851f987bd21a43b771b09473c3549a6c853db37c1c" +dependencies = [ + "futures-core", + "futures-util", + "pin-project", + "pin-project-lite", + "tokio", + "tower-layer", + "tower-service", + "tracing", +] + +[[package]] +name = "tower-http" +version = "0.3.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f873044bf02dd1e8239e9c1293ea39dad76dc594ec16185d0a1bf31d8dc8d858" +dependencies = [ + "bitflags 1.3.2", + "bytes", + "futures-core", + "futures-util", + "http", + "http-body", + "http-range-header", + "httpdate", + "mime", + "mime_guess", + "percent-encoding", + "pin-project-lite", + "tokio", + "tokio-util", + "tower-layer", + "tower-service", +] + +[[package]] +name = "tower-layer" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c20c8dbed6283a09604c3e69b4b7eeb54e298b8a600d4d5ecb5ad39de609f1d0" + +[[package]] +name = "tower-service" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" + +[[package]] +name = "tracing" +version = "0.1.40" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3523ab5a71916ccf420eebdf5521fcef02141234bbc0b8a49f2fdc4544364ef" +dependencies = [ + "log", + "pin-project-lite", + "tracing-core", +] + +[[package]] +name = "tracing-core" +version = "0.1.32" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c06d3da6113f116aaee68e4d601191614c9053067f9ab7f6edbcb161237daa54" +dependencies = [ + "once_cell", +] + +[[package]] +name = "try-lock" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e421abadd41a4225275504ea4d6566923418b7f05506fbc9c0fe86ba7396114b" + +[[package]] +name = "tungstenite" +version = "0.20.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e3dac10fd62eaf6617d3a904ae222845979aec67c615d1c842b4002c7666fb9" +dependencies = [ + "byteorder", + "bytes", + "data-encoding", + "http", + "httparse", + "log", + "rand", + "sha1", + "thiserror", + "url", + "utf-8", +] + +[[package]] +name = "typenum" +version = "1.17.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42ff0bf0c66b8238c6f3b578df37d0b7848e55df8577b3f74f92a69acceeb825" + +[[package]] +name = "unicase" +version = "2.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f7d2d4dafb69621809a81864c9c1b864479e1235c0dd4e199924b9742439ed89" +dependencies = [ + "version_check", +] + +[[package]] +name = "unicode-bidi" +version = "0.3.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6f2528f27a9eb2b21e69c95319b30bd0efd85d09c379741b0f78ea1d86be2416" + +[[package]] +name = "unicode-ident" +version = "1.0.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b" + +[[package]] +name = "unicode-normalization" +version = "0.1.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921" +dependencies = [ + "tinyvec", +] + +[[package]] +name = "url" +version = "2.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "31e6302e3bb753d46e83516cae55ae196fc0c309407cf11ab35cc51a4c2a4633" +dependencies = [ + "form_urlencoded", + "idna", + "percent-encoding", +] + +[[package]] +name = "utf-8" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" + +[[package]] +name = "utf8parse" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a" + +[[package]] +name = "uuid" +version = "1.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5e395fcf16a7a3d8127ec99782007af141946b4795001f876d54fb0d55978560" + +[[package]] +name = "version_check" +version = "0.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" + +[[package]] +name = "want" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa7760aed19e106de2c7c0b581b509f2f25d3dacaf737cb82ac61bc6d760b0e" +dependencies = [ + "try-lock", +] + +[[package]] +name = "wasi" +version = "0.11.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" + +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-util" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f29e6f9198ba0d26b4c9f07dbe6f9ed633e1f3d5b8b414090084349e46a52596" +dependencies = [ + "winapi", +] + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + +[[package]] +name = "windows-sys" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" +dependencies = [ + "windows-targets 0.48.5", +] + +[[package]] +name = "windows-sys" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d" +dependencies = [ + "windows-targets 0.52.0", +] + +[[package]] +name = "windows-targets" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c" +dependencies = [ + "windows_aarch64_gnullvm 0.48.5", + "windows_aarch64_msvc 0.48.5", + "windows_i686_gnu 0.48.5", + "windows_i686_msvc 0.48.5", + "windows_x86_64_gnu 0.48.5", + "windows_x86_64_gnullvm 0.48.5", + "windows_x86_64_msvc 0.48.5", +] + +[[package]] +name = "windows-targets" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a18201040b24831fbb9e4eb208f8892e1f50a37feb53cc7ff887feb8f50e7cd" +dependencies = [ + "windows_aarch64_gnullvm 0.52.0", + "windows_aarch64_msvc 0.52.0", + "windows_i686_gnu 0.52.0", + "windows_i686_msvc 0.52.0", + "windows_x86_64_gnu 0.52.0", + "windows_x86_64_gnullvm 0.52.0", + "windows_x86_64_msvc 0.52.0", +] + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8" + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb7764e35d4db8a7921e09562a0304bf2f93e0a51bfccee0bd0bb0b666b015ea" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbaa0368d4f1d2aaefc55b6fcfee13f41544ddf36801e793edbbfd7d7df075ef" + +[[package]] +name = "windows_i686_gnu" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e" + +[[package]] +name = "windows_i686_gnu" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a28637cb1fa3560a16915793afb20081aba2c92ee8af57b4d5f28e4b3e7df313" + +[[package]] +name = "windows_i686_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406" + +[[package]] +name = "windows_i686_msvc" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ffe5e8e31046ce6230cc7215707b816e339ff4d4d67c65dffa206fd0f7aa7b9a" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d6fa32db2bc4a2f5abeacf2b69f7992cd09dca97498da74a151a3132c26befd" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a657e1e9d3f514745a572a6846d3c7aa7dbe1658c056ed9c3344c4109a6949e" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dff9641d1cd4be8d1a070daf9e3773c5f67e78b4d9d42263020c057706765c04" diff --git a/Cargo.toml b/Cargo.toml index c779f04..b048cb3 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -4,20 +4,27 @@ version = "0.1.1" edition = "2021" [dependencies] -#axum = { version = "0.6.1", features = ["ws", "headers"] } -#axum-extra = { version = "0.4.2", features = ["spa"] } -#axum-macros = "0.3.0" -#colored = "2.0.0" -#derive_more = "0.99.17" -#futures-util = "0.3.24" +clap = { version = "4.4.11", features = ["cargo"] } +home = "0.5.9" +serde = { version = "1.0.152", features = ["derive"] } +serde_json = "1.0.91" +axum = { version = "0.6.1", features = ["ws", "headers"] } +axum-extra = { version = "0.4.2", features = ["spa"] } +axum-macros = "0.3.0" +colored = "2.0.0" +derive_more = "0.99.17" +futures-util = "0.3.24" #itertools = "0.10.5" #lazy_static = "1.4.0" #rmp-serde = "1.1.1" #rmpv = { version = "1.0.0", features = ["serde", "with-serde"] } -#serde = "1.0.152" -#serde_json = "1.0.91" -#tokio = {version = "1.21.0", features = ["full"]} -#tokio-stream = "0.1.9" -#toml = "0.5.10" +tokio = { version = "1.21.0", features = ["full", "net"] } +tokio-stream = "0.1.9" +toml = "0.5.10" #tower-http = "0.3.5" -#uuid = "1.3.0" +uuid = "1.3.0" +log = "0.4.20" +env_logger = "0.10.1" +daemonize = "0.5.0" +nix = { version = "0.27.1", features = ["signal"] } +serde_cbor = "0.11.2" diff --git a/flake.lock b/flake.lock new file mode 100644 index 0000000..92eead7 --- /dev/null +++ b/flake.lock @@ -0,0 +1,61 @@ +{ + "nodes": { + "flake-utils": { + "inputs": { + "systems": "systems" + }, + "locked": { + "lastModified": 1701680307, + "narHash": "sha256-kAuep2h5ajznlPMD9rnQyffWG8EM/C73lejGofXvdM8=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "4022d587cbbfd70fe950c1e2083a02621806a725", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1703637592, + "narHash": "sha256-8MXjxU0RfFfzl57Zy3OfXCITS0qWDNLzlBAdwxGZwfY=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "cfc3698c31b1fb9cdcf10f36c9643460264d0ca8", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "root": { + "inputs": { + "flake-utils": "flake-utils", + "nixpkgs": "nixpkgs" + } + }, + "systems": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 0000000..efbe7d0 --- /dev/null +++ b/flake.nix @@ -0,0 +1,17 @@ +{ + inputs = { + # nixpkgs 35.11 still contains rust 1.73 + nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; + + flake-utils.url = "github:numtide/flake-utils"; + }; + outputs = { flake-utils, nixpkgs, ... }@inputs: flake-utils.lib.eachDefaultSystem (system: let pkgs = nixpkgs.legacyPackages.${system}; in { + + + #packages.default = + devShells.default = pkgs.mkShell { + buildInputs = with pkgs; [ cargo rustc ]; + }; + }); +} + diff --git a/src/cli/call.rs b/src/cli/call.rs new file mode 100644 index 0000000..0e0c4c7 --- /dev/null +++ b/src/cli/call.rs @@ -0,0 +1,4 @@ +use clap::ArgMatches; + +pub async fn call(sub_matches: &ArgMatches) { +} diff --git a/src/cli/daemon.rs b/src/cli/daemon.rs new file mode 100644 index 0000000..f7a550c --- /dev/null +++ b/src/cli/daemon.rs @@ -0,0 +1,63 @@ +use std::path::PathBuf; + +use clap::ArgMatches; +use home::home_dir; +use std::fs::File; +use log::{trace, debug, info, warn, error}; +use nix::sys::signal::{self, Signal}; + +use crate::error::{MizeResultTrait, IntoMizeResult, MizeError}; +use crate::instance::Instance; + + +pub async fn daemon(sub_matches: &ArgMatches) { + let instance_path = match sub_matches.get_one::("store") { + Some(a) => PathBuf::from(a), + None => { + let mut home_dir = home_dir() + .ok_or(MizeError::new().category("io").category("env").msg("could not get the home directory, where the mize store is by default")).critical(); + home_dir.push(".mize"); + home_dir + }, + }; + + let instance = Instance::new(instance_path.clone()).await.critical(); + + info!("Opened Instance at \"{}\"", instance_path.clone().display()); + + match sub_matches.subcommand() { + // stop the daemon + Some(("stop", _)) => { + if instance.daemon_is_running().await.critical() { + //instance.stop_daemon(); + println!("Todo") + } else { + warn!("Daemon is already not running."); + }; + }, + Some(("status", _)) => { + if instance.daemon_is_running().await.critical() { + eprintln!("Daemon is running"); + } else { + eprintln!("Daemon is not running"); + }; + }, + + Some(("kill", _)) => { + signal::kill(instance.get_daemon_pid().await.critical(), Signal::SIGTERM).mize_result_msg("Could not kill daemon").critical(); + }, + + Some((cmd, _)) => { + error!("Unknown Command: {}", cmd); + } + + // just start the daemon + None => { + if !instance.daemon_is_running().await.critical() { + debug!("Daemon is not running. starting..."); + instance.start_deamon().await.critical(); + info!("Daemon Started"); + }; + }, + } +} diff --git a/src/cli/get.rs b/src/cli/get.rs new file mode 100644 index 0000000..3adeb15 --- /dev/null +++ b/src/cli/get.rs @@ -0,0 +1,23 @@ +use std::path::PathBuf; + +use clap::ArgMatches; +use home::home_dir; + +use crate::error::{MizeResultTrait, IntoMizeResult, MizeError}; +use crate::instance::Instance; + + + +pub async fn get(sub_matches: &ArgMatches) { + let instance_folder_path = match sub_matches.get_one::("store") { + Some(a) => PathBuf::from(a), + None => { + let mut home_dir = home_dir() + .ok_or(MizeError::new().category("io").category("env").msg("could not get the home directory, where the mize store is by default")).critical(); + home_dir.push(".mize"); + home_dir + }, + }; + let instance = Instance::new(instance_folder_path); +} + diff --git a/src/cli/mod.rs b/src/cli/mod.rs new file mode 100644 index 0000000..aac64fc --- /dev/null +++ b/src/cli/mod.rs @@ -0,0 +1,16 @@ + +pub mod daemon; +pub mod serve; +pub mod get; +pub mod set; +pub mod mount; +pub mod print; +pub mod call; + +pub use daemon::daemon; +pub use serve::serve; +pub use get::get; +pub use set::set; +pub use mount::mount; +pub use print::print; +pub use call::call; diff --git a/src/cli/mount.rs b/src/cli/mount.rs new file mode 100644 index 0000000..dfa3538 --- /dev/null +++ b/src/cli/mount.rs @@ -0,0 +1,4 @@ +use clap::ArgMatches; + +pub async fn mount(sub_matches: &ArgMatches) { +} diff --git a/src/cli/print.rs b/src/cli/print.rs new file mode 100644 index 0000000..e652cd3 --- /dev/null +++ b/src/cli/print.rs @@ -0,0 +1,4 @@ +use clap::ArgMatches; + +pub async fn print(sub_matches: &ArgMatches) { +} diff --git a/src/cli/serve.rs b/src/cli/serve.rs new file mode 100644 index 0000000..4846dc9 --- /dev/null +++ b/src/cli/serve.rs @@ -0,0 +1,4 @@ +use clap::ArgMatches; + +pub async fn serve(sub_matches: &ArgMatches) { +} diff --git a/src/cli/set.rs b/src/cli/set.rs new file mode 100644 index 0000000..0b8596e --- /dev/null +++ b/src/cli/set.rs @@ -0,0 +1,4 @@ +use clap::ArgMatches; + +pub async fn set(sub_matches: &ArgMatches) { +} diff --git a/src/error.rs b/src/error.rs new file mode 100644 index 0000000..ddaa874 --- /dev/null +++ b/src/error.rs @@ -0,0 +1,271 @@ + +use std::collections::HashMap; +use std::fmt::Debug; +use std::fmt::Display; +use std::fmt::format; +use std::string::FromUtf8Error; +use toml::Value; +use colored::Colorize; +use std::io; +use log::{trace, debug, info, warn, error}; + +use serde_json::Value as JsonValue; +use toml; + +use crate::instance::Connection; +use crate::proto::MizeMessage; + +pub type MizeResult = Result; + +pub trait MizeResultTrait { + fn critical(self) -> T; +} +pub trait IntoMizeResult { + fn mize_result(self) -> MizeResult; + fn mize_result_msg(self, msg: S) -> MizeResult where S: std::fmt::Display ; +} + +#[derive(Debug, Clone)] +pub struct MizeError { + pub category: Vec, + pub code: u32, + pub messages: Vec, + pub caused_by_msg: Option, + pub code_location: Option, +} + +#[derive(Debug, Clone)] +pub struct CausedByMessage { + // peer: &Connection, // TODO: add later + msg: Box, +} + +#[derive(Debug, Clone)] +pub struct MizeCodeLocation { + file: String, + line: u32, + column: u32, +} + +impl Display for MizeCodeLocation { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + write!(f, "file: {} line: {} column: {}", self.file, self.line, self.column) + } +} + +impl From<&std::panic::Location <'_>> for MizeCodeLocation { + fn from(panic_location: &std::panic::Location) -> MizeCodeLocation { + let file = panic_location.file().to_string(); + let line = panic_location.line(); + let column = panic_location.column(); + MizeCodeLocation {file, line, column} + } +} + +impl MizeError { + #[track_caller] + pub fn code(code: u32) -> MizeError { + let caller_location = std::panic::Location::caller(); + + get_error_by_code(code, caller_location) + } + + pub fn set_code(mut self, code: u32) -> MizeError { + self.code = code; + return self; + } + + #[track_caller] + pub fn new() -> MizeError { + let caller_location = std::panic::Location::caller(); + + return MizeError { + category: Vec::new(), + code: 0, + messages: Vec::new(), + caused_by_msg: None, + code_location: Some(caller_location.into()), + } + } + + pub fn msg(mut self, msg: E) -> MizeError + where E: std::fmt::Display + { + self.messages.push(format!("{}", msg)); + return self; + } + + pub fn category(mut self, category: T) -> MizeError where T: Into { + self.category.push(category.into()); + return self; + } + + fn send(self) -> MizeError{ + self + } + + fn add_to_err_item(self) -> MizeError { + self + } + + pub fn log(self) -> MizeError { + error!("MizeError encountered: {}", self.messages.join("\n")); + self + } + + pub fn handle(self) -> MizeError { + return self.send().add_to_err_item().log(); + } + + pub fn critical(self){ + let mut msg_iter = self.messages.iter(); + match msg_iter.next() { + None => { + error!("{} MizeError with code: {}", "CRITICAL".red(), self.code); + }, + Some(msg) => { + error!("{} MizeError with code: {} - {}", "CRITICAL".red(), self.code, msg); + }, + } + for msg in msg_iter { + error!("{} {}", "MSG".red(), msg) + } + if let Some(location) = self.code_location { + error!("{} {}", "LOCATION".red(), location) + } + if let Some(caused_by_msg) = self.caused_by_msg { + error!("{} {:?}", "CAUSED_BY_MESSAGE".red(), caused_by_msg) + } + panic!(); + } + +} + +/* +pub trait MizeResultExtension { + fn extra_msg(self, msg: E) -> Result + where E: std::fmt::Display + ; + fn handle(self) -> Result; + + fn is_critical(self) -> T; +} + +impl MizeResultExtension for Result { + fn msg(mut self, msg: E) -> Result + where E: std::fmt::Display + { + match self { + Err(ref mut e) => { + e.msg.push(format!("{}", msg)); + return self; + }, + Ok(something) => Ok(something), + } + } + fn handle(self) -> Result { + match self { + Err(e) => { + Err(e.send().add_to_err_item().write_to_stderr()) + }, + Ok(something) => Ok(something) + } + } + fn is_critical(self) -> T { + self.expect("Aborting because of a critical Error") + } +} +*/ + +/* +impl From for MizeError { + #[track_caller] + fn from(utf_err: FromUtf8Error) -> MizeError{ + let caller_location = std::panic::Location::caller(); + + let mut err = MizeError::code(109).msg(format!("From std::string::FromUtf8Error: {}", utf_err)); + err.code_location = Some(caller_location.into()); + return err; + } +} +*/ + +impl From for MizeError where E: std::fmt::Display { + fn from(e: E) -> MizeError { + MizeError::new().msg(format!("From generic Rust error: {}", e)) + } +} + +impl MizeResultTrait for MizeResult { + fn critical(self) -> T { + match self { + Ok(val) => val, + Err(err) => { + err.critical(); + unreachable!() + }, + } + } +} + +impl IntoMizeResult for Result where E: std::fmt::Display { + #[track_caller] + fn mize_result(self) -> MizeResult { + let caller_location = std::panic::Location::caller(); + + match self { + Ok(val) => MizeResult::Ok(val), + Err(err) => MizeResult::Err(MizeError::new().category("misc").msg(format!("From any Error: {}", err))), + } + } + #[track_caller] + fn mize_result_msg(self, msg: S) -> MizeResult where S: std::fmt::Display { + let caller_location = std::panic::Location::caller(); + match self { + Ok(val) => MizeResult::Ok(val), + Err(err) => MizeResult::Err(MizeError::new().category("misc").msg(format!("{}", msg)).msg(format!("From any Error: {}", err))), + } + } +} + +/* +impl IntoMizeResult for io::Result { + #[track_caller] + fn mize_result(self) -> MizeResult { + let caller_location = std::panic::Location::caller(); + + match self { + Ok(val) => MizeResult::Ok(val), + Err(io_err) => MizeResult::Err(MizeError::new().category("io").msg(format!("From an io::Error: {}", io_err))), + } + } + #[track_caller] + fn mize_result_msg(self, msg: dyn Into<&str>) -> MizeResult { + let caller_location = std::panic::Location::caller(); + match self { + Ok(val) => MizeResult::Ok(val), + Err(io_err) => MizeResult::Err(MizeError::new().category("io").msg(msg).msg(format!("From an io::Error: {}", io_err))), + } + } +} +*/ + + +fn get_error_by_code(code: u32, caller_location: &std::panic::Location) -> MizeError { + let err = MizeError { + category: Vec::new(), + code: 0, + messages: Vec::new(), + caused_by_msg: None, + code_location: Some(caller_location.into()), + }; + + match code { + 109 => err.set_code(109).category("decoding").msg("conversion from utf8 failed"), + 108 => err.set_code(108).category("decoding").msg("serde deserialisation failed"), + _ => err, + } +} + + + diff --git a/src/instance/connection.rs b/src/instance/connection.rs new file mode 100644 index 0000000..d8d20ce --- /dev/null +++ b/src/instance/connection.rs @@ -0,0 +1,74 @@ +use log::{trace, debug, info, warn, error}; +use tokio::{sync::mpsc::{Sender, Receiver}, net::UnixStream}; +use tokio::net::unix::{OwnedReadHalf, OwnedWriteHalf}; +use tokio::io::{self, Interest}; + +use crate::proto::MizeMessage; +use crate::error::{MizeError, MizeResult, IntoMizeResult}; + +#[derive(Debug)] +pub struct Connection { + tx: Sender, + rx: Receiver, +} + +impl Connection { + pub fn from_unix(unix_sock: UnixStream) -> Connection { + + let (recieve_tx, recieve_rx) = tokio::sync::mpsc::channel(crate::instance::UNIX_SOCKET_CHANNEL_SIZE); + let (send_tx, send_rx) = tokio::sync::mpsc::channel(crate::instance::UNIX_SOCKET_CHANNEL_SIZE); + let (unix_read, unix_write) = unix_sock.into_split(); + + // TODO: error handling and close con on error + tokio::spawn(unix_send(unix_write, send_rx)); + tokio::spawn(unix_recieve(unix_read, recieve_tx)); + + return Connection { tx: send_tx, rx: recieve_rx } + + } +} + +async fn unix_send(unix_write: OwnedWriteHalf, send_rx: Receiver) -> MizeResult<()> { + loop { + let ready = unix_write.ready(Interest::WRITABLE).await.mize_result_msg("hi")?; + if ready.is_writable() { + // Try to write data, this may still fail with `WouldBlock` + // if the readiness event is a false positive. + match unix_write.try_write(b"hello world") { + Ok(n) => { + println!("wrote {} bytes to unix sock", n); + } + Err(ref e) if e.kind() == io::ErrorKind::WouldBlock => { + continue; + } + Err(e) => { + return Err(e.into()); + } + } + } + } +} + +async fn unix_recieve(unix_read: OwnedReadHalf, recieve_tx: Sender) -> MizeResult<()> { + loop { + let ready = unix_read.ready(Interest::READABLE).await.mize_result_msg("hi")?; + + if ready.is_readable() { + let mut data = vec![0; 1024]; + // Try to read data, this may still fail with `WouldBlock` + // if the readiness event is a false positive. + match unix_read.try_read(&mut data) { + Ok(n) => { + println!("read {} bytes from unix sock", n); + } + Err(ref e) if e.kind() == io::ErrorKind::WouldBlock => { + continue; + } + Err(e) => { + return Err(e.into()); + } + } + + } + } +} diff --git a/src/instance/mod.rs b/src/instance/mod.rs new file mode 100644 index 0000000..4ff46c6 --- /dev/null +++ b/src/instance/mod.rs @@ -0,0 +1,213 @@ +use std::collections::HashMap; +use std::path::PathBuf; +use std::fs::create_dir; +use colored::Colorize; +use log::{trace, debug, info, warn, error}; +use tokio::net::{UnixListener, UnixStream}; +use uuid::Uuid; +use std::fs::File; +use std::path::Path; +use daemonize::Daemonize; +use nix::unistd::Pid; + +use crate::error::{MizeError, MizeResult, IntoMizeResult, MizeResultTrait}; +use crate::itemstore::{Itemstore, self}; +use crate::item::{Item, MizeId, ItemGeneral}; + +pub mod peer; +pub mod connection; + +pub use connection::Connection; + +static UNIX_SOCKET_CHANNEL_SIZE: usize = 200; +static WEB_SOCKET_CHANNEL_SIZE: usize = 200; +static TCP_SOCKET_CHANNEL_SIZE: usize = 200; +static UPDATE_CHANNEL_SIZE: usize = 200; + + +pub struct Instance { + store: Itemstore, + peers: Vec, + realm_instance: Option<(RealmId, Vec)>, +} + +pub enum RealmId { + Uuid(Uuid), + Local(Vec), + Tld(Vec), +} + +impl Instance { + pub async fn new(instance_path: PathBuf) -> MizeResult { + trace!("[ {} ] Instance::new()", "CALL".yellow()); + trace!("[ {} ] instance_path: {:?}", "ARG".yellow(), instance_path); + + // if path does not exist, create it + if instance_path.exists() == false { + debug!("instance path \"{}\" does not exist, so creating it", instance_path.clone().display()); + File::create(&instance_path) + .mize_result_msg(format!("Could not create Instance at: {}", &instance_path.display())).critical(); + } + + // if a daemon is running, return instance with memory store + // with realm_instance at that daemon + let mut instance = match find_running_ademon(instance_path.clone()).await { + Ok(con) => { + Instance { + store: Itemstore::Memory(itemstore::new_memory_store()?), + peers: vec![con], + realm_instance: None, + } + }, + + // else open the itemstore + Err(err) => { + Instance { + store: Itemstore::Folder(itemstore::new_folder_store(instance_path)?), + peers: vec![], + realm_instance: None, + } + }, + }; + + if !instance.store.has_item(MizeId::main(1)).await? { + // create first item ... which is this instance + let mut instance_item = ItemGeneral { + id: MizeId::main(1), + kind: vec!["instance".to_owned()], + value: Vec::new(), + map: HashMap::new(), + }; + instance_item.map.insert("daemon".to_owned(), MizeId::main(1).join("daemon")); + instance.store.set_item(Item::General(instance_item)).await?; + + let mut daemon_item = ItemGeneral { + id: MizeId::main(1).join("daemon"), + kind: vec!["instance/daemon".to_owned()], + value: Vec::new(), + map: HashMap::new(), + }; + daemon_item.map.insert("log".to_owned(), MizeId::main(1).join("daemon").join("log")); + daemon_item.map.insert("pid".to_owned(), MizeId::main(1).join("daemon").join("pid")); + instance.store.set_item(Item::General(daemon_item)).await?; + + let log_item = ItemGeneral { + id: MizeId::main(1).join("daemon").join("log"), + kind: vec!["blob".to_owned()], + value: Vec::new(), + map: HashMap::new(), + }; + instance.store.set_item(Item::General(log_item)).await?; + + let pid_item = ItemGeneral { + id: MizeId::main(1).join("daemon").join("pid"), + kind: vec!["int".to_owned()], + value: Vec::new(), + map: HashMap::new(), + }; + instance.store.set_item(Item::General(pid_item)).await?; + }; + + return Ok(instance); + + } + + pub async fn start_deamon(mut self) -> MizeResult<()> { + trace!("[ {} ] Instance::start_deamon()", "CALL".yellow()); + // daemonize + let stdout = self.get_item(MizeId::main(1).join("daemon").join("log")).await?.value_as_file()?; + + let pid_file = self.get_item(MizeId::main(1).join("daemon").join("pid")).await?.value_as_path()?; + + let daemonize = Daemonize::new() + .pid_file(pid_file) + //.chown_pid_file(true) // is optional, see `Daemonize` documentation + //.working_directory("/tmp") // for default behaviour. + //.user("nobody") + //.group("daemon") // Group name + //.group(2) // or group id. + //.umask(0o777) // Set umask, `0o027` by default. + .stdout(stdout); // Redirect stdout to `/tmp/daemon.out`. + //.privileged_action(|| "Executed before drop privileges"); + + daemonize.start().mize_result_msg("Error daemonizing")?; + + info!("Succesfuly Daemonized"); + + // listen on unix socket + let sock_path = self.get_item(MizeId::main(1).join("daemon").join("sock")).await?.value_as_path()?; + let listener = UnixListener::bind(&sock_path) + .mize_result_msg(format!("Could not bind to unix Socket at: {}", sock_path.display())).critical(); + loop { + match listener.accept().await { + Ok((unix_sock, _addr)) => { + self.peers.push(Connection::from_unix(unix_sock)) + }, + Err(e) => { MizeError::new().msg("New Peer failed").msg(format!("{}", e)).log(); }, + }; + } + } + + pub async fn get_daemon_pid(self) -> MizeResult { + trace!("[ {} ] Instance::get_daemon_pid()", "CALL".yellow()); + todo!() + } + + pub async fn daemon_is_running(&self) -> MizeResult { + trace!("[ {} ] Instance::daemon_is_running()", "CALL".yellow()); + let sock_path = self.get_item(MizeId::main(1).join("daemon").join("sock")).await?.value_as_path()?; + match find_running_ademon(sock_path).await { + Ok(_) => Ok(true), + Err(_) => Ok(false), + } + } + + + // item funcs + pub async fn get_item(&self, id: MizeId) -> MizeResult { + self.store.get_item(id).await + } + pub async fn set_item(&mut self, item: Item) -> MizeResult<()> { + self.store.set_item(item).await + } + pub async fn create_item(&mut self) -> MizeResult { + self.store.create_item().await + } + + //pub fn update_item(self) -> MizeResult { + //todo!() + //} + //pub fn on_item_update(self) -> MizeResult { + //todo!() + //} +} + +async fn find_running_ademon(path: PathBuf) -> MizeResult { + match UnixStream::connect(path).await { + Ok(val) => Ok(Connection::from_unix(val)), + Err(err) => Err(MizeError::new().msg("No Daemon found to connect")), + } +} + + +fn handle_connection() { + todo!() +} + +/* +fn get_instance_type() -> MizeResult { + + let mut types_item = Item::new("types"); + + // instance + let instance_str = include_str!("../../types/mize/instance/item.json"); + let instance = Item::new("type").load_json(instance_str)?; + types_item.set("instance", instance); + + return Ok(types_item); +} +*/ + + + + diff --git a/src/instance/peer.rs b/src/instance/peer.rs new file mode 100644 index 0000000..8b13789 --- /dev/null +++ b/src/instance/peer.rs @@ -0,0 +1 @@ + diff --git a/src/instance/web.rs b/src/instance/web.rs new file mode 100644 index 0000000..8587e0a --- /dev/null +++ b/src/instance/web.rs @@ -0,0 +1,239 @@ + +static SERVER_PORT: u16 = 3000; +static API_ENDPOINT: &str = "@mize"; + + +pub fn run() -> Result { + /* + * - Run a Webserver + * + * + * + */ + + + // I will deal with renders later. cli only for now + // let renders = + +// for render in &*renders { +// match render.render_type { +// RenderType::JsonUi => {}, +// RenderType::WebComponent => { +// let url_path = String::from("/api/render/") + &render.name + "/webroot"; +// let file_path = mutexes.mize_folder.clone() + "/mr/" + &render.folder[..] + "/" + &render.webroot.clone()[..]; +// let serve_dir = get_service(ServeDir::new(&file_path)).handle_error(handle_error); + +// app = app.nest_service(&url_path, serve_dir); +// }, +// } +// } + + + // let serve_client = get_service(ServeDir::new("js-client/src")).handle_error(handle_error); + + let mut app = Router::new() + .route(format!("/{}/socket", API_ENDPOINT), get(websocket_handler)) +// .route(format!("/{}/render/:id", API_ENDPOINT), get(get_render_main)) +// .route(format!("/{}/file", API_ENDPOINT), get(get_file_handler)) +// .merge(SpaRouter::new(format!("/{}/client", API_ENDPOINT), "js-client/src").index_file("main.html")) +// .nest_service(format!("/{}/client", API_ENDPOINT), serve_client) + .with_state(main) + .fallback(render_item); + + let addr = SocketAddr::from(([0, 0, 0, 0], SERVER_PORT)); + // tracing::debug!("listening on {}", addr); + + axum::Server::bind(&addr) + .serve(app.into_make_service()) + .await + .expect(format!("Unable to bind axum::Server to {}", addr)); +} + +pub struct Web { +} + +impl Web { + +} + + +async fn handle_error(_err: std::io::Error) -> impl IntoResponse { + MizeError::new(0).msg("internal server error").handle() + (StatusCode::INTERNAL_SERVER_ERROR, "Something went wrong...") +} + +async fn render_item(uri: Uri) -> impl IntoResponse { + Html(fs::read_to_string("js-client/src/main.html").unwrap()) +} + +//#[axum_macros::debug_handler] +//async fn get_render_main(extract::Path(id): extract::Path, State(mutexes): State) -> http::Response { +// let renders = &*mutexes.renders.lock().await; + +// let render = renders.iter().filter(|&render| render.name == id).nth(0) +// .unwrap_or(renders.iter().filter(|&render| render.name == "mize-mmejs").nth(0).expect("mize-mmejs")); + +// let file_path = mutexes.mize_folder.clone() + "/mr/" + &render.folder + "/" + &render.main; + +// match render.render_type { +// RenderType::JsonUi => { +// return Response::builder() +// .header("content-type", "application/json") +// .status(StatusCode::OK) +// .body(fs::read_to_string(file_path).unwrap()).unwrap(); +// }, +// RenderType::WebComponent => { +// return Response::builder() +// .header("content-type", "application/javascript") +// .status(StatusCode::OK) +// .body(fs::read_to_string(file_path).unwrap()).unwrap(); +// }, +// } +//} + +async fn websocket_handler( + ws: WebSocketUpgrade, + State(main): State<&Main>, + headers: HeaderMap, +) -> impl IntoResponse { + ws.on_upgrade(|socket| handle_websocket_connection(socket, main, headers)) +} + +async fn handle_websocket_connection( + socket: WebSocket, + main: &Main, + headers: HeaderMap, +){ + //TODO: auth + + //socket_tx.send() ... send out the socket + //socket_rx.read() ... read a message from the socket + let (mut socket_tx, mut socket_rx) = socket.split(); + + // msg_tx.send() ... send a MizeMessage to a Peer. should be in a Peer struct + // msg_rx.read() ... read MizeMessages that should be sent to the Peer that this ws connection is to + let (msg_tx, msg_rx): (Sender, Receiver) = mpsc::channel(SOCKET_CHANNEL_SIZE); + + // why is this actually + let mut msg_rx = ReceiverStream::new(msg_rx); + + // check if mize-module header exists +// let origin = if let Some(mod_header_val) = headers.get("mize-module"){ + +// let mut mods = mutexes.modules.lock().await; +// let mut client_id = mutexes.next_free_client_id.lock().await; +// let mut module = Module{ +// tx: msg_tx.clone(), +// client_id: *client_id, +// name: String::from("tmp"), +// kind: ModuleKind::Extern(), +// registered_types: Vec::new(), +// }; + +// *client_id += 1; + +// if let Ok(name) = mod_header_val.to_str() { +// module.name = name.to_string(); +// } else { +// let err = MizeError::new(113) +// .extra_msg("The mize-module Header could not be decoded into a String."); + +// msg_tx.send(proto::MizeMessage::Json(err.to_json_message())).await; +// return; +// }; +// println!("module {} connected", module.name); +// mods.push(module.clone()); +// drop(mods); +// Peer::Module(module) + +// } else { +// }; + + // Forwarding messages + tokio::spawn(async move { + while let Some(msg) = msg_rx.next().await { + match msg { + proto::MizeMessage::Json(json_msg) => { + if let Ok(msg) = serde_json::to_string(&json_msg) { + let result = socket_tx.send(Message::Text(msg.clone())).await; + if let Err(e) = result { + println!("Client no longer Connected: {:?}", e); + remove_peer(myorigin.clone(), mymutexes.clone()).await; + } else { + println!("SENDING: {}", msg); + } + } else { + let err: MizeError = MizeError::new(11).extra_msg("error while serializing a json message").handle(); + if let Ok(text) = serde_json::to_string(&err.to_json()){ + socket_tx.send(Message::Text(text)); + } else { + MizeError::new(11).extra_msg("not even being able to serialize an error, while failing to serializing a message").handle(); + } + } + } + proto::MizeMessage::Bin(bin_msg) => { + socket_tx.send(Message::Binary(bin_msg.raw)).await; + } + proto::MizeMessage::Pong() => { + socket_tx.send(Message::Pong(Vec::new())).await; + } + proto::MizeMessage::Close((num, reason)) => { + println!("SENDING Close message"); + socket_tx.send(Message::Close(Some(CloseFrame{code: num, reason: Cow::Owned(reason)}))).await; + } + } + } + }); + + // Reading messages + while let Some(result) = socket_rx.next().await { + let msg = if let Ok(msg) = result {msg} else { + let err = MizeError::new(115).extra_msg("TCP Connection Closed"); + remove_peer(origin.clone(), mutexes.clone()); + return; + }; + match msg { + Message::Binary(b) => { + println!("Recieved a Binary Message. Those are not implemented yet.") + }, + + + Message::Text(text) => { + println!("GOT: {}", text); + let json_msg: proto::JsonMessage = serde_json::from_str(&text).expect("error parsing json"); + if let Err(err) = proto::handle_json_msg(json_msg, origin.clone(), mutexes.clone()).await { + let err_msg: MizeMessage = err.handle().into(); + origin.send(err_msg).await; + }; + }, + + Message::Close(inner) => { + match inner { + Some(CloseFrame{code, reason}) => { + origin.send(MizeMessage::Close((code, reason.into_owned()))).await; + }, + None => { + origin.send(MizeMessage::Close((1000, "You didn't send a Close Reason".to_owned()))).await; + } + }; + + println!("Close from Client"); + remove_peer(origin.clone(), mutexes.clone()).await; + } + + + Message::Ping(_) => { + msg_tx.send(MizeMessage::Pong()); + }, + + + Message::Pong(_) => { + let err = MizeError::new(11) + .extra_msg("unhandeld WebSocket-Message type: Pong") + .handle(); + msg_tx.send(proto::MizeMessage::Json(err.to_json_message())).await; + }, + + }; + }; +} diff --git a/src/item.rs b/src/item.rs new file mode 100644 index 0000000..b605661 --- /dev/null +++ b/src/item.rs @@ -0,0 +1,234 @@ +use log::{trace, debug, info, warn, error}; +use std::{collections::HashMap, path::PathBuf, io::Cursor, fmt::Display}; +use serde_cbor::Value as CborValue; +use std::fs::File; +use tokio::sync::Mutex; + +use crate::error::{MizeError, MizeResult, IntoMizeResult}; + + +#[derive(Debug)] +pub enum Item { + Cbor(ItemCbor), + Folder(ItemFolder), + Ref(ItemRef), +} + +#[derive(Clone, Debug)] +pub struct ItemCbor { + pub inner: CborValue, + pub id: MizeId, +} + +#[derive(Debug)] +pub struct ItemFolder { + pub path: PathBuf, + pub id: MizeId, +} + +#[derive(Debug)] +pub struct ItemRef { + pub store: Mutex>, + pub id: MizeId, +} + +#[derive(Clone, Debug, Hash, PartialEq, Eq)] +pub struct MizeId { + pub main: u64, + pub path: Option> +} + +pub struct MizeType { +} + + +////////////////////////////////////////////////////////////////////////////////////////////// + + +impl Display for MizeId { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + if let Some(path) = &self.path { + write!(f, "{}/{}", self.main, path.join("/")) + } else { + write!(f, "{}", self.main) + } + } +} + +impl MizeId { + pub fn main(main: u64) -> MizeId { + MizeId { main, path: None } + } + pub fn join(self, segment: &str) -> MizeId { + let mut new = self.clone(); + match new.path { + None => { + new.path = Some(vec![segment.to_owned()]); + } + Some(ref mut val) => { + val.push(segment.to_owned()); + } + } + return new; + } +} + + + +////////////////////////////////////////////////////////////////////////////////////////////// + +impl ItemCbor { + fn value_as_file(&self) -> MizeResult { + /* sadly does not work like that + let cbor_c = self.inner.get("v").ok_or(MizeError::new() + .msg(format!("The ItemCbor ({}) does not have a \"c\" field ... so can't get it as a file", self.id()?)))?; + match cbor_c { + Cbor::Bytes(val) => { + return Ok(Cursor::new(val.clone()).into()); + }, + _ => { + return Err(MizeError::new().msg(format!("The value fo item ({}) is not of type Cbor::Bytes", self.id()?))); + }, + } + */ + return File::open(self.value_as_path()?).mize_result_msg("Could not open file"); + } + + fn value_as_path(&self) -> MizeResult { + todo!() + } + + /* an old way of getting the id this + fn id(self) -> MizeResult { + let cbor_item = self.inner.get("item".to_owned()).ok_or(MizeError::new() + .msg("ItemCbor had no path: \"item\""))?; + + let cbor_id = match cbor_item { + Cbor::Map(map) => { + map.get("id").ok_or(MizeError::new().msg("ItemCbor had no path \"item/id\"")) + }, + _ => { + return Err(MizeError::new().msg("ItemCbor path \"item\" was not of type Cbor::Map")); + }, + }; + + let id = match cbor_id { + Cbor::Unsigned(val) => val.into_u64(), + _ => { + return Err(MizeError::new().msg("ItemCbor path \"item/id\" was not of type Cbor::Unsigned")); + }, + + }; + + return Ok(MizeId { inner: id }); + } + // */ + + fn id(&self) -> MizeResult { + Ok(self.id.clone()) + } + fn as_cbor(&self) -> MizeResult { + Ok(self.clone()) + } + fn write_to_path(&self, path: PathBuf) -> MizeResult<()> { + todo!() + //let cbor_content = + //std::fs::write(path.join(format!("{}", self.id)), ); + } +} + +impl ItemFolder { + fn value_as_file(&self) -> MizeResult { + let file = File::open(self.path.join("v")) + .mize_result_msg(format!("Could not open the value file of item ({})", self.id()?)); + return file; + } + + fn value_as_path(&self) -> MizeResult { + return Ok(self.path.clone()); + } + + fn id(&self) -> MizeResult { + Ok(self.id.clone()) + } + + fn as_cbor(&self) -> MizeResult { + todo!() + } + + fn write_to_path(&self, path: PathBuf) -> MizeResult<()> { + Ok(()) + } +} + +impl ItemRef { + fn value_as_file(&self) -> MizeResult { + todo!() + } + + fn value_as_path(&self) -> MizeResult { + todo!() + } + + fn id(&self) -> MizeResult { + return Ok(self.id.clone()); + } + + fn as_cbor(&self) -> MizeResult { + todo!() + } + + fn write_to_path(&self, path: PathBuf) -> MizeResult<()> { + let store = self.store.lock().await; + for (key, value) in self.map.iter() { + // TODO right here!!!! + } + todo!() + } +} + +impl Item { + pub fn value_as_file(&self) -> MizeResult { + match self { + Item::Cbor(val) => val.value_as_file(), + Item::Ref(val) => val.value_as_file(), + Item::Folder(val) => val.value_as_file(), + } + } + + pub fn value_as_path(&self) -> MizeResult { + match self { + Item::Cbor(val) => val.value_as_path(), + Item::Ref(val) => val.value_as_path(), + Item::Folder(val) => val.value_as_path(), + } + } + + pub fn id(&self) -> MizeResult { + match self { + Item::Cbor(val) => val.id(), + Item::Ref(val) => val.id(), + Item::Folder(val) => val.id(), + } + } + + pub fn as_cbor(&self) -> MizeResult { + match self { + Item::Cbor(val) => val.as_cbor(), + Item::Ref(val) => val.as_cbor(), + Item::Folder(val) => val.as_cbor(), + } + } + + pub fn write_to_path(&self, path: PathBuf) -> MizeResult<()> { + match self { + Item::Cbor(val) => val.write_to_path(path), + Item::Ref(val) => val.write_to_path(path), + Item::Folder(val) => val.write_to_path(path), + } + } + pub fn load_json(json_str: &str) -> MizeResult { + todo!() + } +} + diff --git a/src/itemstore.rs b/src/itemstore.rs new file mode 100644 index 0000000..5767464 --- /dev/null +++ b/src/itemstore.rs @@ -0,0 +1,267 @@ +use log::{trace, debug, info, warn, error}; +use std::fs::{self, File}; +use std::path::{PathBuf, Path}; +use std::collections::HashMap; +use std::io::{Read, Write}; +use colored::Colorize; + +use crate::item::{Item, MizeId, ItemCbor, ItemDescriptor}; +use crate::error::{MizeError, MizeResult, IntoMizeResult}; + +pub enum Itemstore { + Folder(FolderItemstore), + Memory(MemoryItemstore), +} + +pub struct FolderItemstore { + path: PathBuf, + next_id: u64, +} + +pub struct MemoryItemstore { + inner: HashMap, + next_id: u64, +} + + +/////////////////////////////////////////////////////////////////////////////////////////// + + +pub fn new_memory_store() -> MizeResult { + Ok(MemoryItemstore { + inner: HashMap::new(), + next_id: 100, + }) +} + +pub fn new_folder_store(path: PathBuf) -> MizeResult { + if path.join("store_open").exists() { + let pid_str = fs::read_to_string(path.join("store_open")) + .mize_result_msg("Could not read the store_open file to check which process has the store opened")?; + let pid = pid_str.parse::() + .mize_result_msg("Could not Parse the content of the store_open file into a u32")?; + + if Path::new("/proc").join(format!("{}", pid)).exists() { + return Err(MizeError::new().msg( + format!("the store at {} is already open by process with pid: {}", path.display(), pid) + )); + } else { + warn!("An Instance was not closed properly. (store_open file contained a not running PID)"); + std::fs::remove_file(path.join("store_open")) + .mize_result_msg("Could not remove the store_open file")?; + } + } + + let mut store_open_file = File::create(path.join("store_open")) + .mize_result_msg("Could not create the store_open file")?; + + store_open_file.write_all(format!("{}", std::process::id()).as_bytes()) + .mize_result_msg("Could not write my pid to the store_open file")?; + + // if no store_next_id exists write it with the default 100 + let mut next_id: u64 = 100; // as a default + if !path.join("store_next_id").exists() { + fs::write(path.join("store_next_id"), format!("{}", next_id).as_bytes()) + .mize_result_msg("Could not write the default next_id to store_next_id")?; + } else { + let next_id_string = fs::read_to_string(path.join("store_next_id")) + .mize_result_msg("Could not read store_next_id of this store")?; + + next_id = next_id_string.parse() + .mize_result_msg("Could not parse contents of store_next_id into u64")?; + } + + return Ok(FolderItemstore{ path, next_id}); + +} + + +/////////////////////////////////////////////////////////////////////////////////////////// + + +impl FolderItemstore { + pub async fn write_next_id(&self) -> MizeResult<()> { + fs::write(self.path.join("store_next_id"), format!("{}", self.next_id).as_bytes()) + .mize_result_msg(format!("Could not write the next_id: \"{}\" to \"{}\"", self.next_id, self.path.join("store_next_id").display()))?; + return Ok(()); + } +} + + +/////////////////////////////////////////////////////////////////////////////////////////// + + +impl MemoryItemstore { + // item funcs + async fn get_item(&self, id: MizeId) -> MizeResult { + match self.inner.get(&id) { + None => { + Err(MizeError::new().msg(format!("there was no item with id ({}) in this store", id))) + }, + Some(item) => { + Ok(Item::Cbor(item.as_cbor()?)) + }, + } + } + + async fn set_item(&mut self, item: Item) -> MizeResult<()> { + self.inner.insert(item.id()?, item) + .ok_or(MizeError::new().msg("Could not set an item in a MemoryStore"))?; + return Ok(()); + } + + + async fn create_item(&mut self) -> MizeResult { + // advance the next_id + self.next_id += 1; + return Ok(MizeId::main(self.next_id)) + } + + //fn update_item(self) -> MizeResult; + + // other funcs + async fn close(&self) -> MizeResult<()> { + return Ok(()); + } + + async fn next_id(&self) -> u64 { + self.next_id + } + + async fn has_item(&self, id: MizeId) -> MizeResult { + Ok(self.inner.contains_key(&id)) + } +} + +impl FolderItemstore { + // item funcs + async fn get_item(&self, id: MizeId) -> MizeResult { + let id_string = format!("{}", id.main); + let mut final_path = self.path.join("store"); + if id_string.len() < 2 { + // use path 00 for ids under 10 + final_path.push("00") + } else { + // will not panic, because of prior check if string is more than two long + final_path.push(id_string[..2].to_owned()); + }; + + return Ok(Item::Descriptor(ItemDescriptor { path: final_path, id})); + } + + async fn set_item(&self, item: Item) -> MizeResult<()> { + item.write_to_path(self.get_path_of_item(&item.id()?)?) + } + + async fn create_item(&mut self) -> MizeResult { + // advance the next_id + self.next_id += 1; + match self.write_next_id().await { + // on error revert to old next_id + Ok(_) => {}, + Err(err) => { + self.next_id -= 1; + return Err(err); + }, + } + return Ok(MizeId::main(self.next_id)); + } + + //fn update_item(self) -> MizeResult; + + // other funcs + async fn close(&self) -> MizeResult<()> { + if self.path.join("store_open").exists() { + std::fs::remove_file(self.path.join("store_open")) + .mize_result_msg("Could not remove the store_open file")?; + } + return Ok(()); + } + + async fn next_id(&self) -> u64 { + self.next_id + } + async fn has_item(&self, id: MizeId) -> MizeResult { + Ok(self.get_path_of_item(&id)?.exists()) + } + + fn get_path_of_item(&self, id: &MizeId) -> MizeResult { + // get path of item + let id_string = format!("{}", id.main); + let mut final_path = self.path.join("store"); + if id_string.len() < 2 { + // use path 00 for ids under 10 + final_path.push("00") + } else { + // will not panic, because of prior check if string is more than two long + final_path.push(id_string[..2].to_owned()); + }; + return Ok(final_path); + } +} + +impl Itemstore { + // item funcs + pub async fn get_item(&self, id: MizeId) -> MizeResult { + trace!("[ {} ] Itemstore::get_item()", "CALL".yellow()); + trace!("[ {} ] id: {}", "ARG".yellow(), id); + + match self { + Itemstore::Folder(val) => val.get_item(id).await, + Itemstore::Memory(val) => val.get_item(id).await, + } + } + + pub async fn set_item(&mut self, item: Item) -> MizeResult<()> { + trace!("[ {} ] Itemstore::set_item()", "CALL".yellow()); + trace!("[ {} ] item: {:?}", "ARG".yellow(), item); + + match self { + Itemstore::Folder(val) => val.set_item(item).await, + Itemstore::Memory(val) => val.set_item(item).await, + } + } + + pub async fn create_item(&mut self) -> MizeResult { + trace!("[ {} ] Itemstore::create_item()", "CALL".yellow()); + + match self { + Itemstore::Folder(val) => val.create_item().await, + Itemstore::Memory(val) => val.create_item().await, + } + } + + //pub fn update_item(self) -> MizeResult; + + // other funcs + pub async fn close(&self) -> MizeResult<()> { + trace!("[ {} ] Itemstore::close()", "CALL".yellow()); + match self { + Itemstore::Folder(val) => val.close().await, + Itemstore::Memory(val) => val.close().await, + } + } + + pub async fn next_id(&self) -> u64 { + trace!("[ {} ] Itemstore::next_id()", "CALL".yellow()); + + match self { + Itemstore::Folder(val) => val.next_id().await, + Itemstore::Memory(val) => val.next_id().await, + } + } + pub async fn has_item(&self, id: MizeId) -> MizeResult { + trace!("[ {} ] Itemstore::has_item()", "CAL".yellow()); + trace!("[ {} ] id: {}", "ARG".yellow(), id); + + let ret = match self { + Itemstore::Folder(val) => val.has_item(id).await, + Itemstore::Memory(val) => val.has_item(id).await, + }; + + if let Ok(val) = ret {trace!("[ {} ] Itemstore::has_item(): {}", "RET".yellow(), val)}; + + return ret; + } +} + diff --git a/src/lib.rs b/src/lib.rs new file mode 100644 index 0000000..2de16d5 --- /dev/null +++ b/src/lib.rs @@ -0,0 +1,16 @@ + +#![ allow( warnings ) ] + +static PROTO_VERSION: u8 = 1; + + +// pub mod types; + +pub mod error; +mod instance; +mod proto; +mod item; +mod itemstore; + + + diff --git a/src/main.rs b/src/main.rs new file mode 100644 index 0000000..b7b1592 --- /dev/null +++ b/src/main.rs @@ -0,0 +1,325 @@ + +#![ allow( warnings ) ] + +use std::path::PathBuf; +use clap::{ArgAction, ArgMatches}; +use clap::{Arg, crate_version, Command}; + +use tokio::sync::{Mutex, mpsc}; +use std::sync::Arc; +use log::Level; +use log::LevelFilter; +use env_logger::{Builder, Env}; +use std::io::Write; +use colored::Colorize; +use std::env; + +use log::{trace, debug, info, warn, error}; + +mod cli; +mod error; +// mod types; +mod instance; +mod item; +mod itemstore; +mod proto; + +static APPNAME: &str = "mize"; +static DEFAULT_LOG_LEVEL: LevelFilter = LevelFilter::Warn; + +#[tokio::main] +async fn main() { + + let cli_matches = cli_matches(); + + init_logger(&cli_matches); + + // log a message of every level, to test loging + // test_logger(); + + + // match command + match cli_matches.subcommand() { + // mi daemon + Some(("daemon", sub_matches)) => cli::daemon(sub_matches).await, + + // mi serve + Some(("serve", sub_matches)) => cli::serve(sub_matches).await, + + // mi mount + Some(("mount", sub_matches)) => cli::mount(sub_matches).await, + + // mi get + Some(("get", sub_matches)) => cli::get(sub_matches).await, + + // mi set + Some(("set", sub_matches)) => cli::set(sub_matches).await, + + // mi print + Some(("print", sub_matches)) => cli::print(sub_matches).await, + + // mi call + Some(("call", sub_matches)) => cli::call(sub_matches).await, + + // some unknown command passed + Some((cmd, sub_matches)) => error!("The subcommand: {} is not known. use --help to list availavle commands", cmd), + + None => error!("No subcommand was passed. use --help to list availavle comamnds."), + } + + +} + +fn init_logger(cli_matches: &ArgMatches) { + + // to save log messages, before the logger is setup + let mut log_messages: Vec<(Level, String)> = Vec::new(); + + log_messages.push((Level::Info, "Starting Mize".to_owned())); + + // builder with DEFAULT_LOG_LEVEL + let mut builder = Builder::new(); + builder.format_indent(Some(8)); + + + + // set loglevel + let mut log_level = DEFAULT_LOG_LEVEL; + log_messages.push((Level::Trace, format!("set log level from DEFAULT_LOG_LEVEL to {}", DEFAULT_LOG_LEVEL))); + + // check env RUST_LOG + let mut val_rust_log = level_from_env("RUST_LOG", log_level); + if let Some(level_rust_log) = val_rust_log.0 { + log_level = level_rust_log; + log_messages.push((Level::Trace, format!("set log level from the Variable RUST_LOG to {}", level_rust_log))); + } + log_messages.append(&mut val_rust_log.1); + + // check env MIZE_LOG + let mut val_mize_log = level_from_env("MIZE_LOG", log_level); + if let Some(level_mize_log) = val_mize_log.0 { + log_level = level_mize_log; + log_messages.push((Level::Trace, format!("set log level from the Variable MIZE_LOG to {}", level_mize_log))); + } + log_messages.append(&mut val_mize_log.1); + + // check -vvvvv flags + let v_flag_count = cli_matches.get_count("verbose"); + let default_log_level_as_num = match DEFAULT_LOG_LEVEL { + LevelFilter::Off => 0, + LevelFilter::Error => 1, + LevelFilter::Warn => 2, + LevelFilter::Info => 3, + LevelFilter::Debug => 4, + LevelFilter::Trace => 5, + }; + let new_log_level_num = default_log_level_as_num + v_flag_count; + log_level = match new_log_level_num { + 0 => LevelFilter::Off, + 1 => LevelFilter::Error, + 2 => LevelFilter::Warn, + 3 => LevelFilter::Info, + 4 => LevelFilter::Debug, + 5 => LevelFilter::Trace, + _ => { + log_messages.push((Level::Trace, format!("the number of verbose (-v) flags passed ({}) exeeds the maximumg log_level", v_flag_count))); + LevelFilter::Trace + }, + }; + log_messages.push((Level::Trace, format!("set log level from the verbose flags to {}", log_level))); + + // check --log-level arg + if let Some(log_level_arg_string) = cli_matches.get_one::<&str>("log-level") { + let log_level_from_arg = match log_level_arg_string.to_lowercase().as_str() { + "none" => LevelFilter::Off, + "trace" => LevelFilter::Trace, + "debug" => LevelFilter::Debug, + "info" => LevelFilter::Info, + "warn" => LevelFilter::Warn, + "error" => LevelFilter::Error, + _ => { + log_messages.push((Level::Warn, format!( + "The argument to --log-level \"{}\" is not a valid log-level. loglevel stays at: {}" + , log_level_arg_string + , log_level + ))); + log_level + } + }; + log_level = log_level_from_arg; + log_messages.push((Level::Trace, format!("set log level from the --log-level arg to {}", log_level_from_arg))); + } + + // check --silent flag + if cli_matches.get_flag("silent") { + if log_level != DEFAULT_LOG_LEVEL { + log_messages.push((Level::Warn, format!( + "The loglevel was set by some method (it's not the DEFAULT_LOG_LEVEL) and is now overwritten by the --siltne to be OFF" + ))) + } + log_level = LevelFilter::Off; + } + + // actually set the log_level on the builder + builder.filter_level(log_level); + log_messages.push((Level::Info, format!("loglevel is now {}", log_level))); + + + // set format + builder.format(|buf, record| { + match record.level() { + Level::Trace => writeln!(buf, "[ {} ] {}", format!("{}", record.level()).yellow(), record.args()), + Level::Debug => writeln!(buf, "[ {} ] {}", format!("{}", record.level()).green(), record.args()), + Level::Info => writeln!(buf, "[ {} ] {}", format!("{}", record.level()).blue(), record.args()), + Level::Warn => writeln!(buf, "[ {} ] {}", format!("{}", record.level()).truecolor(245, 164, 66), record.args()), + Level::Error => writeln!(buf, "[ {} ] {}", format!("{}", record.level()).red(), record.args()), + } + }); + + builder.init(); + + + // write out all log messages from log_messages + for (level, msg) in log_messages { + match level { + Level::Error => error!("{}", msg), + Level::Warn => warn!("{}", msg), + Level::Info => info!("{}", msg), + Level::Debug => debug!("{}", msg), + Level::Trace => trace!("{}", msg), + } + } +} + +fn test_logger() { + error!("hi from error"); + warn!("hi from warn"); + info!("hi from info"); + debug!("hi from debug"); + trace!("hi from trace"); +} + +fn level_from_env(var_name: &str, log_level: LevelFilter) -> (Option, Vec<(Level, String)>) { + let mut log_messages: Vec<(Level, String)> = Vec::new(); + let var_value = env::var(var_name); + match var_value { + Ok(val) => { + // set loglevel acording to RUST_LOG + let level = match val.to_lowercase().as_str() { + "none" => LevelFilter::Off, + "trace" => LevelFilter::Trace, + "debug" => LevelFilter::Debug, + "info" => LevelFilter::Info, + "warn" => LevelFilter::Warn, + "error" => LevelFilter::Error, + _ => { + log_messages.push((Level::Warn, format!( + "The value of Environment Variable {}: \"{}\" is not a valid log-level. loglevel stays at: {}" + , var_name + , val + , log_level + ))); + log_level + } + }; + return (Some(level), log_messages) + }, + Err(env::VarError::NotPresent) => {}, + Err(env::VarError::NotUnicode(os_string)) => { + + let os_string_as_hex : String = os_string.clone().into_encoded_bytes().iter() + .map(|b| format!("{:02x}", b).to_string()) + .collect::>() + .join(""); + log_messages.push((Level::Debug, format!( + "value of Environment Variable {} was not a unicode valid string. Therefore ignoring it. + \n value with replacement char U+FFFD: {} + \n the WTF-8 raw bytes as hex: {}" + , var_name + , os_string.to_string_lossy(), os_string_as_hex + ))); + }, + }; + return (None, log_messages); +} + +fn cli_matches() -> clap::ArgMatches { + + let store_arg = Arg::new("store") + .short('s') + .long("store") + .help("The folder used as the Itemstore"); + + let main = Command::new(APPNAME) + .version(crate_version!()) + .author("Sebastian Moser") + .about("The MiZe Command line tool") + .arg(Arg::new("verbose") + .long("verbose") + .short('v') + .action(ArgAction::Count) + ) + .arg(Arg::new("log-level") + .long("log-level") + .value_name("LOGLEVEL") + .help("set the log-level to one of OFF, ERROR, WARN, INFO, DEBUG, TRACE") + ) + .arg(Arg::new("silent") + .long("silent") + .action(ArgAction::SetTrue) + .help("set the log-level to OFF") + ) + .subcommand( + Command::new("daemon") + .aliases(["da"]) + .arg(&store_arg) + .about("Starts the mize daemon. Has subcommands to stop, etc") + .subcommand(Command::new("stop") + .about("Stops the mize daemon if one is running") + ) + .subcommand(Command::new("kill")) + .about("Stops the mize daemon with a signal") + .alias("k") + .subcommand(Command::new("status") + .alias("st") + ) + ) + .subcommand( + Command::new("serve") + .aliases(["se"]) + .arg(&store_arg) + ) + .subcommand( + Command::new("mount") + .aliases(["m"]) + .arg(&store_arg) + ) + .subcommand( + Command::new("get") + .aliases(["g"]) + .arg(&store_arg) + .arg(Arg::new("id").help("The id or path to get")) + ) + .subcommand( + Command::new("set") + .aliases(["s"]) + .arg(&store_arg) + .arg(Arg::new("id").help("The id or path to set")) + ) + .subcommand( + Command::new("print") + .aliases(["p"]) + .arg(&store_arg) + .arg(Arg::new("id").help("The id or path to print")) + ) + .subcommand( + Command::new("call") + .aliases(["c"]) + .arg(&store_arg) + ) + .arg_required_else_help(true); + + return main.get_matches(); +} + + diff --git a/src/proto.rs b/src/proto.rs new file mode 100644 index 0000000..e4505b2 --- /dev/null +++ b/src/proto.rs @@ -0,0 +1,7 @@ +use serde_cbor::Value as CborValue; + + +#[derive(Debug, Clone)] +pub struct MizeMessage { + value: CborValue, +} diff --git a/types/mize/instance/item.json b/types/mize/instance/item.json new file mode 100644 index 0000000..9ebb0f1 --- /dev/null +++ b/types/mize/instance/item.json @@ -0,0 +1,7 @@ +{ + "name": "instance", + "paths": [ + [["daemon", "pid"], "int"], + [["daemon", "log", "blob"]] + ] +}