feat: add basic

Signed-off-by: kjuulh <contact@kjuulh.io>
This commit is contained in:
Kasper Juul Hermansen 2024-05-20 19:25:59 +02:00
commit fe48259d06
Signed by: kjuulh
GPG Key ID: 9AA7BC13CE474394
18 changed files with 2608 additions and 0 deletions

2
.drone.yml Normal file
View File

@ -0,0 +1,2 @@
kind: template
load: cuddle-rust-cli-plan.yaml

2
.gitignore vendored Normal file
View File

@ -0,0 +1,2 @@
target/
.cuddle/

2367
Cargo.lock generated Normal file

File diff suppressed because it is too large Load Diff

13
Cargo.toml Normal file
View File

@ -0,0 +1,13 @@
[workspace]
members = ["crates/*"]
resolver = "2"
[workspace.dependencies]
anyhow = { version = "1" }
tokio = { version = "1", features = ["full"] }
tracing = { version = "0.1", features = ["log"] }
tracing-subscriber = { version = "0.3.18" }
clap = { version = "4", features = ["derive", "env"] }
dotenv = { version = "0.15" }
axum = { version = "0.7" }

16
README.md Normal file
View File

@ -0,0 +1,16 @@
# cuddle-clusters
Stage 1:
Pick up templates from:
```yaml
some-service/:
templates/:
clusters/:
deployment.yaml.jinja2:
raw/
some-crdb.yaml
```
For each env chosen, run code with own set of variables

1
crates/cuddle-clusters/.gitignore vendored Normal file
View File

@ -0,0 +1 @@
/target

View File

@ -0,0 +1,33 @@
[package]
name = "cuddle-clusters"
version = "0.1.0"
edition = "2021"
autotests = false
[dependencies]
anyhow.workspace = true
tokio.workspace = true
tracing.workspace = true
tracing-subscriber.workspace = true
clap.workspace = true
dotenv.workspace = true
axum.workspace = true
serde = { version = "1.0.197", features = ["derive"] }
sqlx = { version = "0.7.3", features = [
"runtime-tokio",
"tls-rustls",
"postgres",
"uuid",
"time",
] }
uuid = { version = "1.7.0", features = ["v4"] }
tower-http = { version = "0.5.2", features = ["cors", "trace"] }
serde_yaml = "0.9.34"
[[test]]
name = "integration"
path = "tests/tests.rs"
[dev-dependencies]
tracing-test = "0.2.4"

View File

@ -0,0 +1,3 @@
pub mod process;
pub use process::{process, process_opts};

View File

@ -0,0 +1,29 @@
use anyhow::Context;
use clap::{Parser, Subcommand};
#[derive(Parser)]
#[command(author, version, about, long_about = None, subcommand_required = true)]
struct Command {
#[command(subcommand)]
command: Option<Commands>,
}
#[derive(Subcommand)]
enum Commands {
Hello {},
}
#[tokio::main]
async fn main() -> anyhow::Result<()> {
dotenv::dotenv().ok();
tracing_subscriber::fmt::init();
let cli = Command::parse();
tracing::debug!("Starting cli");
if let Some(Commands::Hello {}) = cli.command {
println!("Hello!")
}
Ok(())
}

View File

@ -0,0 +1,68 @@
use std::{
collections::HashMap,
path::{Path, PathBuf},
};
use anyhow::Context;
pub async fn process() -> anyhow::Result<()> {
process_opts(ProcessOpts::default()).await
}
pub struct ProcessOpts {
pub path: PathBuf,
}
impl Default for ProcessOpts {
fn default() -> Self {
Self {
path: std::env::current_dir().expect("to be able to get current dir"),
}
}
}
pub async fn process_opts(opts: ProcessOpts) -> anyhow::Result<()> {
let path = opts.path.canonicalize().context("failed to find folder")?;
let cuddle_path = path.join("cuddle.yaml");
let template = path.join("templates").join("clusters");
tracing::debug!(
"searching for templates in: {} with cuddle: {}",
template.display(),
cuddle_path.display()
);
let clusters = read_cuddle_section(&cuddle_path).await?;
tracing::debug!("found clusters: {:?}", clusters);
load_template_files(&template).await?;
Ok(())
}
#[derive(serde::Deserialize, Default, Debug, Clone)]
struct CuddleClusters(HashMap<String, serde_yaml::Value>);
async fn read_cuddle_section(path: &Path) -> anyhow::Result<CuddleClusters> {
let cuddle_file = tokio::fs::read(path).await?;
let value: serde_yaml::Value = serde_yaml::from_slice(&cuddle_file)?;
let mut cuddle_clusters = CuddleClusters::default();
if let Some(clusters) = value.get("cuddle/clusters") {
if let Some(mapping) = clusters.as_mapping() {
for (key, value) in mapping.iter() {
if let Some(key) = key.as_str() {
cuddle_clusters.0.insert(key.to_string(), value.clone());
}
}
}
}
Ok(cuddle_clusters)
}
async fn load_template_files(path: &Path) -> anyhow::Result<()> {
Ok(())
}

View File

@ -0,0 +1,8 @@
use crate::common::run_test;
#[tokio::test]
async fn can_run_for_env() -> anyhow::Result<()> {
run_test("can_run_for_env").await?;
Ok(())
}

View File

@ -0,0 +1,2 @@
cuddle/clusters:
dev:

View File

@ -0,0 +1,6 @@
{
hello = "world",
some = {
thing = "some"
}
}

View File

@ -0,0 +1,16 @@
use cuddle_clusters::process::ProcessOpts;
pub(crate) async fn run_test(name: &str) -> anyhow::Result<()> {
let _ = tracing_subscriber::fmt::try_init();
println!("running for: {name}");
let current_dir = std::env::current_dir()?;
cuddle_clusters::process_opts(ProcessOpts {
path: current_dir.join("tests").join(name),
})
.await?;
Ok(())
}

View File

@ -0,0 +1,3 @@
pub mod common;
mod can_run_for_env;

21
cuddle.yaml Normal file
View File

@ -0,0 +1,21 @@
# yaml-language-server: $schema=https://git.front.kjuulh.io/kjuulh/cuddle/raw/branch/main/schemas/base.json
base: "git@git.front.kjuulh.io:kjuulh/cuddle-rust-cli-plan.git"
vars:
service: "cuddle-clusters"
registry: kasperhermansen
clusters:
clank-prod:
replicas: "3"
namespace: prod
deployment:
registry: git@git.front.kjuulh.io:kjuulh/clank-clusters
env:
prod:
clusters:
- clank-prod

3
renovate.json Normal file
View File

@ -0,0 +1,3 @@
{
"$schema": "https://docs.renovatebot.com/renovate-schema.json"
}

View File

@ -0,0 +1,15 @@
version: "3"
services:
crdb:
restart: 'always'
image: 'cockroachdb/cockroach:v23.1.14'
command: 'start-single-node --advertise-addr 0.0.0.0 --insecure'
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:8080/health?ready=1"]
interval: '10s'
timeout: '30s'
retries: 5
start_period: '20s'
ports:
- 8080:8080
- '26257:26257'