feat: update project
This commit is contained in:
79
Cargo.lock
generated
79
Cargo.lock
generated
@@ -215,6 +215,9 @@ name = "bitflags"
|
||||
version = "2.9.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1b8e56985ec62d17e9c1001dc89c88ecd7dc08e47eba5ec7c29c7b5eeecde967"
|
||||
dependencies = [
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bollard"
|
||||
@@ -369,6 +372,27 @@ version = "0.1.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "56254986775e3233ffa9c4d7d3faaf6d36a2c09d30b20687e9f88bc8bafc16c8"
|
||||
|
||||
[[package]]
|
||||
name = "dirs"
|
||||
version = "6.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c3e8aa94d75141228480295a7d0e7feb620b1a5ad9f12bc40be62411e38cce4e"
|
||||
dependencies = [
|
||||
"dirs-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dirs-sys"
|
||||
version = "0.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e01a3366d27ee9890022452ee61b2b63a67e6f13f58900b651ff5665f0bb1fab"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"option-ext",
|
||||
"redox_users",
|
||||
"windows-sys 0.59.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "displaydoc"
|
||||
version = "0.2.5"
|
||||
@@ -912,6 +936,16 @@ version = "0.2.174"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1171693293099992e19cddea4e8b849964e9846f4acee11b3948bcc337be8776"
|
||||
|
||||
[[package]]
|
||||
name = "libredox"
|
||||
version = "0.1.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "391290121bad3d37fbddad76d8f5d1c1c314cfc646d143d7e07a3086ddff0ce3"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "litemap"
|
||||
version = "0.8.0"
|
||||
@@ -990,12 +1024,14 @@ dependencies = [
|
||||
"bollard",
|
||||
"bytes",
|
||||
"clap",
|
||||
"dirs",
|
||||
"futures-util",
|
||||
"norun-grpc-interface",
|
||||
"notmad",
|
||||
"pretty_assertions",
|
||||
"prost",
|
||||
"prost-types",
|
||||
"ron",
|
||||
"serde",
|
||||
"tokio",
|
||||
"tokio-util",
|
||||
@@ -1003,6 +1039,7 @@ dependencies = [
|
||||
"tonic",
|
||||
"tracing",
|
||||
"tracing-subscriber",
|
||||
"uuid",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1079,6 +1116,12 @@ version = "1.70.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a4895175b425cb1f87721b59f0f286c2092bd4af812243672510e1ac53e2e0ad"
|
||||
|
||||
[[package]]
|
||||
name = "option-ext"
|
||||
version = "0.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "04744f49eae99ab78e0d5c0b603ab218f515ea8cfe5a456d7629ad883a3b6e7d"
|
||||
|
||||
[[package]]
|
||||
name = "overload"
|
||||
version = "0.1.1"
|
||||
@@ -1304,6 +1347,17 @@ dependencies = [
|
||||
"bitflags",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "redox_users"
|
||||
version = "0.5.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a4e608c6638b9c18977b00b475ac1f28d14e84b27d8d42f70e0bf1e3dec127ac"
|
||||
dependencies = [
|
||||
"getrandom 0.2.16",
|
||||
"libredox",
|
||||
"thiserror",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ref-cast"
|
||||
version = "1.0.24"
|
||||
@@ -1368,6 +1422,19 @@ version = "0.8.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2b15c43186be67a4fd63bee50d0303afffcef381492ebe2c5d87f324e1b8815c"
|
||||
|
||||
[[package]]
|
||||
name = "ron"
|
||||
version = "0.10.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "beceb6f7bf81c73e73aeef6dd1356d9a1b2b4909e1f0fc3e59b034f9572d7b7f"
|
||||
dependencies = [
|
||||
"base64",
|
||||
"bitflags",
|
||||
"serde",
|
||||
"serde_derive",
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustc-demangle"
|
||||
version = "0.1.25"
|
||||
@@ -1924,6 +1991,18 @@ version = "0.2.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "06abde3611657adf66d383f00b093d7faecc7fa57071cce2578660c9f1010821"
|
||||
|
||||
[[package]]
|
||||
name = "uuid"
|
||||
version = "1.17.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3cf4199d1e5d15ddd86a694e4d0dffa9c323ce759fea589f00fef9d81cc1931d"
|
||||
dependencies = [
|
||||
"getrandom 0.3.3",
|
||||
"js-sys",
|
||||
"serde",
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "valuable"
|
||||
version = "0.1.1"
|
||||
|
@@ -3,42 +3,41 @@
|
||||
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||
pub struct PublishRequest {
|
||||
#[prost(message, optional, tag="1")]
|
||||
#[prost(message, optional, tag = "1")]
|
||||
pub project: ::core::option::Option<Project>,
|
||||
}
|
||||
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||
#[derive(Clone, Copy, PartialEq, ::prost::Message)]
|
||||
pub struct PublishResponse {
|
||||
}
|
||||
pub struct PublishResponse {}
|
||||
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||
pub struct GetTopicRequest {
|
||||
#[prost(string, tag="1")]
|
||||
#[prost(string, tag = "1")]
|
||||
pub topic: ::prost::alloc::string::String,
|
||||
}
|
||||
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||
pub struct GetTopicResponse {
|
||||
#[prost(message, optional, tag="1")]
|
||||
#[prost(message, optional, tag = "1")]
|
||||
pub projects: ::core::option::Option<Projects>,
|
||||
}
|
||||
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||
pub struct Projects {
|
||||
#[prost(message, repeated, tag="1")]
|
||||
#[prost(message, repeated, tag = "1")]
|
||||
pub projects: ::prost::alloc::vec::Vec<Project>,
|
||||
}
|
||||
#[allow(clippy::derive_partial_eq_without_eq)]
|
||||
#[derive(Clone, PartialEq, ::prost::Message)]
|
||||
pub struct Project {
|
||||
#[prost(string, tag="1")]
|
||||
#[prost(string, tag = "1")]
|
||||
pub name: ::prost::alloc::string::String,
|
||||
#[prost(string, tag="2")]
|
||||
#[prost(string, tag = "2")]
|
||||
pub image: ::prost::alloc::string::String,
|
||||
#[prost(string, tag="3")]
|
||||
#[prost(string, tag = "3")]
|
||||
pub version: ::prost::alloc::string::String,
|
||||
#[prost(uint32, optional, tag="4")]
|
||||
#[prost(uint32, optional, tag = "4")]
|
||||
pub port: ::core::option::Option<u32>,
|
||||
}
|
||||
include!("norun.v1.tonic.rs");
|
||||
// @@protoc_insertion_point(module)
|
||||
// @@protoc_insertion_point(module)
|
||||
|
@@ -23,6 +23,9 @@ async-trait = "0.1.88"
|
||||
notmad = "0.7.2"
|
||||
bollard = "0.19.1"
|
||||
futures-util = "0.3.31"
|
||||
dirs = "6.0.0"
|
||||
uuid = { version = "1.17.0", features = ["serde", "v4"] }
|
||||
ron = "0.10.1"
|
||||
|
||||
[dev-dependencies]
|
||||
pretty_assertions = "1.4.1"
|
||||
|
@@ -7,6 +7,8 @@ mod state;
|
||||
|
||||
mod server;
|
||||
|
||||
mod services;
|
||||
|
||||
mod grpc_client;
|
||||
mod grpc_server;
|
||||
|
||||
|
@@ -1,5 +1,7 @@
|
||||
pub mod project_tag;
|
||||
pub use project_tag::*;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use uuid::Uuid;
|
||||
|
||||
pub mod port {
|
||||
#[derive(Clone, Debug, PartialEq)]
|
||||
@@ -8,3 +10,15 @@ pub mod port {
|
||||
pub container_port: usize,
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)]
|
||||
pub struct Project {
|
||||
pub id: Uuid,
|
||||
pub spec: ProjectSpec,
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)]
|
||||
pub enum ProjectSpec {
|
||||
Compose {},
|
||||
Container {},
|
||||
}
|
||||
|
1
crates/norun/src/services.rs
Normal file
1
crates/norun/src/services.rs
Normal file
@@ -0,0 +1 @@
|
||||
pub mod project_registry;
|
104
crates/norun/src/services/project_registry.rs
Normal file
104
crates/norun/src/services/project_registry.rs
Normal file
@@ -0,0 +1,104 @@
|
||||
use std::path::PathBuf;
|
||||
|
||||
use anyhow::Context;
|
||||
use tokio::io::AsyncWriteExt;
|
||||
|
||||
use crate::{models::Project, state::ClientState};
|
||||
|
||||
pub struct ProjectRegistry {
|
||||
state_dir: PathBuf,
|
||||
}
|
||||
|
||||
impl ProjectRegistry {
|
||||
pub async fn get_project(&self, project: &Project) -> anyhow::Result<Option<Project>> {
|
||||
let project_dir = self.project_file(project)?;
|
||||
|
||||
if !project_dir.exists() {
|
||||
return Ok(None);
|
||||
}
|
||||
|
||||
let project_content = tokio::fs::read_to_string(&project_dir)
|
||||
.await
|
||||
.context("failed to read ron file")?;
|
||||
|
||||
let project: Project = ron::from_str(&project_content)
|
||||
.context(format!("failed to read: '{}'", project_dir.display()))?;
|
||||
|
||||
Ok(Some(project))
|
||||
}
|
||||
|
||||
pub async fn create_project(&self, project: &Project) -> anyhow::Result<()> {
|
||||
match self.get_project(project).await {
|
||||
Ok(_) => anyhow::bail!("project already exists"),
|
||||
Err(_) => {
|
||||
// continue
|
||||
}
|
||||
}
|
||||
|
||||
let project_file_path = self.project_file(project)?;
|
||||
if let Some(project_file) = project_file_path.parent() {
|
||||
tokio::fs::create_dir_all(project_file)
|
||||
.await
|
||||
.context("create ron project dir")?;
|
||||
}
|
||||
|
||||
let mut project_file = tokio::fs::File::create_new(&project_file_path)
|
||||
.await
|
||||
.context("create project file")?;
|
||||
|
||||
let project_content = ron::to_string(project)?;
|
||||
|
||||
project_file
|
||||
.write_all(&project_content.as_bytes())
|
||||
.await
|
||||
.context("write project file")?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub async fn update_project(&self, project: &Project) -> anyhow::Result<()> {
|
||||
let project_file_path = self.project_file(project)?;
|
||||
if let Some(project_file) = project_file_path.parent() {
|
||||
tokio::fs::create_dir_all(project_file)
|
||||
.await
|
||||
.context("update ron project dir")?;
|
||||
}
|
||||
|
||||
let mut project_file = tokio::fs::File::create_new(&project_file_path)
|
||||
.await
|
||||
.context("update project file")?;
|
||||
|
||||
let project_content = ron::to_string(project)?;
|
||||
|
||||
project_file
|
||||
.write_all(project_content.as_bytes())
|
||||
.await
|
||||
.context("update project file")?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn project_file(&self, project: &Project) -> anyhow::Result<PathBuf> {
|
||||
let project_dir = self
|
||||
.state_dir
|
||||
.join(project.id.to_string())
|
||||
.join("project.ron");
|
||||
|
||||
Ok(project_dir)
|
||||
}
|
||||
}
|
||||
|
||||
pub trait ProjectRegistryState {
|
||||
fn project_registry(&self) -> ProjectRegistry;
|
||||
}
|
||||
|
||||
impl ProjectRegistryState for ClientState {
|
||||
fn project_registry(&self) -> ProjectRegistry {
|
||||
ProjectRegistry {
|
||||
state_dir: dirs::state_dir()
|
||||
.expect("to be able to find state")
|
||||
.join("norun")
|
||||
.join("projects"),
|
||||
}
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user