diff --git a/src/basic/keywords/create_site.rs b/src/basic/keywords/create_site.rs index 6cfaa2e4..ff6bb626 100644 --- a/src/basic/keywords/create_site.rs +++ b/src/basic/keywords/create_site.rs @@ -78,7 +78,7 @@ async fn create_site( ); info!("Asking LLM to create site."); - let llm_result = utils::call_llm(&full_prompt, &config.ai).await?; + let llm_result = utils::call_llm(&full_prompt, &config.llm).await?; let index_path = alias_path.join("index.html"); fs::write(index_path, llm_result).map_err(|e| e.to_string())?; diff --git a/src/bootstrap/mod.rs b/src/bootstrap/mod.rs index c07cc49b..9c91fed7 100644 --- a/src/bootstrap/mod.rs +++ b/src/bootstrap/mod.rs @@ -544,13 +544,14 @@ impl BootstrapManager { let temp_path = std::env::temp_dir().join("config.csv"); std::fs::write(&temp_path, csv_content)?; + // First sync the CSV to database config_manager.sync_gbot_config(&default_bot_id, temp_path.to_str().unwrap()) .map_err(|e| anyhow::anyhow!("Failed to sync gbot config: {}", e))?; - // Load config from database which now has the CSV values - let mut config_conn = establish_pg_connection()?; - let config = AppConfig::from_database(&mut config_conn); - info!("Successfully loaded config from CSV"); + // Create fresh connection for final config load + let mut final_conn = establish_pg_connection()?; + let config = AppConfig::from_database(&mut final_conn); + info!("Successfully loaded config from CSV with LLM settings"); Ok(config) } Err(e) => { diff --git a/src/config/mod.rs b/src/config/mod.rs index 06eae187..d2e32362 100644 --- a/src/config/mod.rs +++ b/src/config/mod.rs @@ -8,6 +8,13 @@ use std::io::Write; use std::path::PathBuf; use std::sync::{Arc, Mutex}; +#[derive(Clone)] +pub struct LLMConfig { + pub url: String, + pub key: String, + pub model: String, +} + #[derive(Clone)] pub struct AppConfig { pub drive: DriveConfig, @@ -15,7 +22,8 @@ pub struct AppConfig { pub database: DatabaseConfig, pub database_custom: DatabaseConfig, pub email: EmailConfig, - pub ai: AIConfig, + pub llm: LLMConfig, + pub embedding: LLMConfig, pub site_path: String, pub stack_path: PathBuf, pub db_conn: Option>>, @@ -54,14 +62,6 @@ pub struct EmailConfig { pub password: String, } -#[derive(Clone)] -pub struct AIConfig { - pub instance: String, - pub key: String, - pub version: String, - pub endpoint: String, -} - #[derive(Debug, Clone, Serialize, Deserialize, QueryableByName)] pub struct ServerConfigRow { #[diesel(sql_type = Text)] @@ -218,13 +218,6 @@ impl AppConfig { password: get_str("EMAIL_PASS", "pass"), }; - let ai = AIConfig { - instance: get_str("AI_INSTANCE", "gpt-4"), - key: get_str("AI_KEY", ""), - version: get_str("AI_VERSION", "2023-12-01-preview"), - endpoint: get_str("AI_ENDPOINT", "https://api.openai.com"), - }; - // Write drive config to .env file if let Err(e) = write_drive_config_to_env(&minio) { warn!("Failed to write drive config to .env: {}", e); @@ -239,7 +232,16 @@ impl AppConfig { database, database_custom, email, - ai, + llm: LLMConfig { + url: get_str("LLM_URL", "http://localhost:8081"), + key: get_str("LLM_KEY", ""), + model: get_str("LLM_MODEL", "gpt-4"), + }, + embedding: LLMConfig { + url: get_str("EMBEDDING_URL", "http://localhost:8082"), + key: get_str("EMBEDDING_KEY", ""), + model: get_str("EMBEDDING_MODEL", "text-embedding-ada-002"), + }, site_path: get_str("SITES_ROOT", "./botserver-stack/sites"), stack_path, db_conn: None, @@ -302,15 +304,6 @@ impl AppConfig { password: std::env::var("EMAIL_PASS").unwrap_or_else(|_| "pass".to_string()), }; - let ai = AIConfig { - instance: std::env::var("AI_INSTANCE").unwrap_or_else(|_| "gpt-4".to_string()), - key: std::env::var("AI_KEY").unwrap_or_else(|_| "".to_string()), - version: std::env::var("AI_VERSION") - .unwrap_or_else(|_| "2023-12-01-preview".to_string()), - endpoint: std::env::var("AI_ENDPOINT") - .unwrap_or_else(|_| "https://api.openai.com".to_string()), - }; - AppConfig { drive: minio, server: ServerConfig { @@ -323,7 +316,16 @@ impl AppConfig { database, database_custom, email, - ai, + llm: LLMConfig { + url: std::env::var("LLM_URL").unwrap_or_else(|_| "http://localhost:8081".to_string()), + key: std::env::var("LLM_KEY").unwrap_or_else(|_| "".to_string()), + model: std::env::var("LLM_MODEL").unwrap_or_else(|_| "gpt-4".to_string()), + }, + embedding: LLMConfig { + url: std::env::var("EMBEDDING_URL").unwrap_or_else(|_| "http://localhost:8082".to_string()), + key: std::env::var("EMBEDDING_KEY").unwrap_or_else(|_| "".to_string()), + model: std::env::var("EMBEDDING_MODEL").unwrap_or_else(|_| "text-embedding-ada-002".to_string()), + }, site_path: std::env::var("SITES_ROOT") .unwrap_or_else(|_| "./botserver-stack/sites".to_string()), stack_path: PathBuf::from(stack_path), diff --git a/src/main.rs b/src/main.rs index a16bf34d..90a6283a 100644 --- a/src/main.rs +++ b/src/main.rs @@ -190,7 +190,7 @@ async fn main() -> std::io::Result<()> { let tool_manager = Arc::new(tools::ToolManager::new()); let llm_provider = Arc::new(crate::llm::OpenAIClient::new( "empty".to_string(), - Some(cfg.ai.endpoint.clone()), + Some(cfg.llm.url.clone()), )); let web_adapter = Arc::new(WebChannelAdapter::new()); let voice_adapter = Arc::new(VoiceAdapter::new( diff --git a/src/package_manager/installer.rs b/src/package_manager/installer.rs index f52dbefe..08da77a4 100644 --- a/src/package_manager/installer.rs +++ b/src/package_manager/installer.rs @@ -241,7 +241,7 @@ post_install_cmds_linux: vec![ post_install_cmds_windows: vec![], env_vars: HashMap::new(), data_download_list: Vec::new(), - exec_cmd: "{{BIN_PATH}}/bin/valkey-server --port 6379 --dir {{DATA_PATH}}".to_string(), + exec_cmd: "nohup {{BIN_PATH}}/bin/valkey-server --port 6379 --dir {{DATA_PATH}} > {{LOGS_PATH}}/valkey.log 2>&1 &".to_string(), }, ); } @@ -841,4 +841,4 @@ post_install_cmds_linux: vec![ hasher.update(password.as_bytes()); format!("{:x}", hasher.finalize()) } -} \ No newline at end of file +} diff --git a/src/shared/utils.rs b/src/shared/utils.rs index 31cc27f4..abb39c01 100644 --- a/src/shared/utils.rs +++ b/src/shared/utils.rs @@ -1,4 +1,3 @@ -use crate::config::AIConfig; use anyhow::{Context, Result}; use diesel::{Connection, PgConnection}; use futures_util::StreamExt; @@ -175,7 +174,7 @@ pub fn parse_filter_with_offset( pub async fn call_llm( prompt: &str, - _ai_config: &AIConfig, + _llm_config: &crate::config::LLMConfig, ) -> Result> { Ok(format!("Generated response for: {}", prompt)) } diff --git a/templates/default.gbai/default.gbot/config.csv b/templates/default.gbai/default.gbot/config.csv index 4ac4a5da..340ca8f2 100644 --- a/templates/default.gbai/default.gbot/config.csv +++ b/templates/default.gbai/default.gbot/config.csv @@ -9,7 +9,7 @@ llm-url,http://localhost:8080/v1 llm-model,botserver-stack/data/llm/DeepSeek-R1-Distill-Qwen-1.5B-Q3_K_M.gguf embedding-url,http://localhost:8082 -embedding-model-path,botserver-stack/data/llm/bge-small-en-v1.5-f32.gguf +embedding-model,botserver-stack/data/llm/bge-small-en-v1.5-f32.gguf llm-server,false llm-server-path,botserver-stack/bin/llm/