mockforge_collab/
config.rs1use serde::{Deserialize, Serialize};
4use std::time::Duration;
5
6#[derive(Debug, Clone, Serialize, Deserialize)]
8pub struct CollabConfig {
9 pub jwt_secret: String,
11 pub database_url: String,
13 pub bind_address: String,
15 pub max_connections_per_workspace: usize,
17 pub event_bus_capacity: usize,
19 pub auto_commit: bool,
21 pub session_timeout: Duration,
23 pub websocket_ping_interval: Duration,
25 pub max_message_size: usize,
27 pub workspace_dir: Option<String>,
29 pub backup_dir: Option<String>,
31}
32
33impl Default for CollabConfig {
34 fn default() -> Self {
35 Self {
36 jwt_secret: "change-me-in-production".to_string(),
37 database_url: "sqlite://mockforge-collab.db".to_string(),
38 bind_address: "127.0.0.1:8080".to_string(),
39 max_connections_per_workspace: 100,
40 event_bus_capacity: 1000,
41 auto_commit: true,
42 session_timeout: Duration::from_secs(24 * 3600), websocket_ping_interval: Duration::from_secs(30),
44 max_message_size: 1024 * 1024, workspace_dir: Some("./workspaces".to_string()),
46 backup_dir: Some("./backups".to_string()),
47 }
48 }
49}
50
51impl CollabConfig {
52 #[must_use]
54 pub fn from_env() -> Self {
55 Self {
56 jwt_secret: std::env::var("MOCKFORGE_JWT_SECRET")
57 .unwrap_or_else(|_| "change-me-in-production".to_string()),
58 database_url: std::env::var("MOCKFORGE_DATABASE_URL")
59 .unwrap_or_else(|_| "sqlite://mockforge-collab.db".to_string()),
60 bind_address: std::env::var("MOCKFORGE_BIND_ADDRESS")
61 .unwrap_or_else(|_| "127.0.0.1:8080".to_string()),
62 ..Default::default()
63 }
64 }
65}
66
67#[cfg(test)]
68mod tests {
69 use super::*;
70
71 #[test]
72 fn test_default_config() {
73 let config = CollabConfig::default();
74
75 assert_eq!(config.jwt_secret, "change-me-in-production");
76 assert_eq!(config.database_url, "sqlite://mockforge-collab.db");
77 assert_eq!(config.bind_address, "127.0.0.1:8080");
78 assert_eq!(config.max_connections_per_workspace, 100);
79 assert_eq!(config.event_bus_capacity, 1000);
80 assert!(config.auto_commit);
81 assert_eq!(config.session_timeout, Duration::from_secs(24 * 3600));
82 assert_eq!(config.websocket_ping_interval, Duration::from_secs(30));
83 assert_eq!(config.max_message_size, 1024 * 1024);
84 assert_eq!(config.workspace_dir, Some("./workspaces".to_string()));
85 assert_eq!(config.backup_dir, Some("./backups".to_string()));
86 }
87
88 #[test]
89 fn test_from_env_defaults() {
90 std::env::remove_var("MOCKFORGE_JWT_SECRET");
92 std::env::remove_var("MOCKFORGE_DATABASE_URL");
93 std::env::remove_var("MOCKFORGE_BIND_ADDRESS");
94
95 let config = CollabConfig::from_env();
96
97 assert_eq!(config.jwt_secret, "change-me-in-production");
98 assert_eq!(config.database_url, "sqlite://mockforge-collab.db");
99 assert_eq!(config.bind_address, "127.0.0.1:8080");
100 }
101
102 #[test]
103 fn test_from_env_with_values() {
104 std::env::set_var("MOCKFORGE_JWT_SECRET", "test-secret");
106 std::env::set_var("MOCKFORGE_DATABASE_URL", "postgres://localhost/test");
107 std::env::set_var("MOCKFORGE_BIND_ADDRESS", "0.0.0.0:9090");
108
109 let config = CollabConfig::from_env();
110
111 assert_eq!(config.jwt_secret, "test-secret");
112 assert_eq!(config.database_url, "postgres://localhost/test");
113 assert_eq!(config.bind_address, "0.0.0.0:9090");
114
115 std::env::remove_var("MOCKFORGE_JWT_SECRET");
117 std::env::remove_var("MOCKFORGE_DATABASE_URL");
118 std::env::remove_var("MOCKFORGE_BIND_ADDRESS");
119 }
120
121 #[test]
122 fn test_config_serialization() {
123 let config = CollabConfig::default();
124 let serialized = serde_json::to_string(&config).unwrap();
125 let deserialized: CollabConfig = serde_json::from_str(&serialized).unwrap();
126
127 assert_eq!(config.jwt_secret, deserialized.jwt_secret);
128 assert_eq!(config.database_url, deserialized.database_url);
129 assert_eq!(config.bind_address, deserialized.bind_address);
130 }
131
132 #[test]
133 fn test_config_clone() {
134 let config = CollabConfig::default();
135 let cloned = config.clone();
136
137 assert_eq!(config.jwt_secret, cloned.jwt_secret);
138 assert_eq!(config.max_connections_per_workspace, cloned.max_connections_per_workspace);
139 }
140
141 #[test]
142 fn test_config_debug() {
143 let config = CollabConfig::default();
144 let debug_str = format!("{:?}", config);
145
146 assert!(debug_str.contains("CollabConfig"));
147 assert!(debug_str.contains("jwt_secret"));
148 }
149}