jellytau_lib/commands/
device.rs1use std::sync::Arc;
7
8use log::info;
9use tauri::State;
10use uuid::Uuid;
11
12use crate::commands::storage::DatabaseWrapper;
13use crate::storage::db_service::{DatabaseService, Query, QueryParam};
14
15#[tauri::command]
26#[specta::specta]
27pub async fn device_get_id(db: State<'_, DatabaseWrapper>) -> Result<String, String> {
28 let db_service = {
29 let database = db.0.lock().map_err(|e| e.to_string())?;
30 Arc::new(database.service())
31 };
32
33 let query = Query::with_params(
35 "SELECT value FROM app_settings WHERE key = ?",
36 vec![QueryParam::String("device_id".to_string())],
37 );
38
39 let existing_id: Option<String> = db_service
40 .query_one(query, |row| row.get(0))
41 .await
42 .ok()
43 .flatten();
44
45 if let Some(device_id) = existing_id {
46 info!("[Device] Retrieved existing device ID");
47 return Ok(device_id);
48 }
49
50 let device_id = Uuid::new_v4().to_string();
52
53 let insert_query = Query::with_params(
55 "INSERT INTO app_settings (key, value) VALUES (?, ?)",
56 vec![
57 QueryParam::String("device_id".to_string()),
58 QueryParam::String(device_id.clone()),
59 ],
60 );
61
62 db_service
63 .execute(insert_query)
64 .await
65 .map_err(|e| e.to_string())?;
66
67 info!("[Device] Generated and stored new device ID");
68 Ok(device_id)
69}
70
71#[tauri::command]
83#[specta::specta]
84pub async fn device_set_id(
85 device_id: String,
86 db: State<'_, DatabaseWrapper>,
87) -> Result<(), String> {
88 let db_service = {
89 let database = db.0.lock().map_err(|e| e.to_string())?;
90 Arc::new(database.service())
91 };
92
93 let query = Query::with_params(
94 "INSERT OR REPLACE INTO app_settings (key, value) VALUES (?, ?)",
95 vec![
96 QueryParam::String("device_id".to_string()),
97 QueryParam::String(device_id),
98 ],
99 );
100
101 db_service.execute(query).await.map_err(|e| e.to_string())?;
102
103 info!("[Device] Device ID set");
104 Ok(())
105}
106
107#[cfg(test)]
108mod tests {
109 use super::*;
110
111 #[test]
112 fn test_device_id_is_valid_uuid() {
113 let id = Uuid::new_v4().to_string();
114 let parsed = Uuid::parse_str(&id);
116 assert!(parsed.is_ok(), "Device ID should be a valid UUID");
117 }
118
119 #[test]
120 fn test_device_id_format() {
121 let id = Uuid::new_v4().to_string();
122 assert_eq!(id.len(), 36, "Device ID should be 36 characters");
124 assert!(id.contains('-'), "Device ID should contain hyphens");
125 }
126
127 #[test]
128 fn test_device_ids_are_unique() {
129 let id1 = Uuid::new_v4().to_string();
130 let id2 = Uuid::new_v4().to_string();
131 assert_ne!(id1, id2, "Generated device IDs should be unique");
132 }
133}