pub mod env;
pub mod fs;
pub mod history_layout;
pub mod http;
pub use env::{
BrowserEnvBackend, BrowserEnvironment, ENV_PERSIST_PATH,
};
pub use fs::{
BrowserFileSystem, BrowserFsBackend, BROWSER_HOME_DIR, BROWSER_WORKSPACE_DIR,
};
pub use history_layout::{
config_persist_path, conv_id_for_group, group_clawft_md_path, group_dir, resolve_group_id,
sessions_dir, validate_group_id, BROWSER_CHANNEL, DEFAULT_GROUP_ID, GROUP_CLAWFT_MD,
};
pub use http::BrowserHttpClient;
use std::sync::Arc;
use async_trait::async_trait;
use crate::Platform;
pub struct BrowserPlatform {
http: BrowserHttpClient,
fs: BrowserFileSystem,
env: Arc<BrowserEnvironment>,
}
impl BrowserPlatform {
pub fn new() -> Self {
Self {
http: BrowserHttpClient::new(),
fs: BrowserFileSystem::new(),
env: Arc::new(BrowserEnvironment::new()),
}
}
pub async fn open() -> Self {
Self {
http: BrowserHttpClient::new(),
fs: BrowserFileSystem::open().await,
env: Arc::new(BrowserEnvironment::open().await),
}
}
pub fn with_env(env: BrowserEnvironment) -> Self {
Self {
http: BrowserHttpClient::new(),
fs: BrowserFileSystem::new(),
env: Arc::new(env),
}
}
pub fn with_env_arc(env: Arc<BrowserEnvironment>) -> Self {
Self {
http: BrowserHttpClient::new(),
fs: BrowserFileSystem::new(),
env,
}
}
pub async fn with_env_arc_open(env: Arc<BrowserEnvironment>) -> Self {
Self {
http: BrowserHttpClient::new(),
fs: BrowserFileSystem::open().await,
env,
}
}
pub fn with_env_arc_and_fs(env: Arc<BrowserEnvironment>, fs: BrowserFileSystem) -> Self {
Self {
http: BrowserHttpClient::new(),
fs,
env,
}
}
pub fn env_arc(&self) -> Arc<BrowserEnvironment> {
Arc::clone(&self.env)
}
pub fn fs_backend(&self) -> BrowserFsBackend {
self.fs.backend()
}
pub fn env_backend(&self) -> BrowserEnvBackend {
self.env.backend()
}
}
impl Default for BrowserPlatform {
fn default() -> Self {
Self::new()
}
}
#[async_trait(?Send)]
impl Platform for BrowserPlatform {
fn http(&self) -> &dyn crate::http::HttpClient {
&self.http
}
fn fs(&self) -> &dyn crate::fs::FileSystem {
&self.fs
}
fn env(&self) -> &dyn crate::env::Environment {
self.env.as_ref()
}
fn process(&self) -> Option<&dyn crate::process::ProcessSpawner> {
None
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::env::Environment;
use crate::Platform;
#[test]
fn set_env_via_arc_visible_through_platform_env() {
let env = Arc::new(BrowserEnvironment::new());
let platform = BrowserPlatform::with_env_arc(Arc::clone(&env));
env.set_var("CLAWFT_WEFT391_KEY", "live-value");
assert_eq!(
platform.env().get_var("CLAWFT_WEFT391_KEY"),
Some("live-value".to_string())
);
assert_eq!(
platform.env_arc().get_var("CLAWFT_WEFT391_KEY"),
Some("live-value".to_string())
);
platform.env().set_var("CLAWFT_WEFT391_KEY", "updated");
assert_eq!(
env.get_var("CLAWFT_WEFT391_KEY"),
Some("updated".to_string())
);
}
#[test]
fn with_env_pre_seeds_vars() {
let mut vars = std::collections::HashMap::new();
vars.insert("FOO".to_string(), "bar".to_string());
let platform = BrowserPlatform::with_env(BrowserEnvironment::with_vars(vars));
assert_eq!(
platform.env().get_var("FOO"),
Some("bar".to_string())
);
}
#[test]
fn process_spawner_is_none() {
let platform = BrowserPlatform::new();
assert!(platform.process().is_none());
}
}