1pub mod ranking;
2pub mod suggestions;
3
4pub use ranking::SuggestionRanker;
5pub use suggestions::CompletionSuggestion;
6
7use crate::code::code_completion::context::CompletionContext;
8use crate::code::code_completion::learning::CompletionLearningData;
9use hashbrown::HashMap;
10use serde::{Deserialize, Serialize};
11use std::sync::Arc;
12use tokio::sync::RwLock;
13
14#[derive(Debug, Clone, Serialize, Deserialize, PartialEq)]
16pub enum CompletionKind {
17 Function,
18 Method,
19 Variable,
20 Class,
21 Struct,
22 Enum,
23 Trait,
24 Module,
25 Keyword,
26 Snippet,
27 Import,
28 Type,
29}
30
31pub struct CompletionEngine {
33 suggestion_cache: Arc<RwLock<HashMap<String, Arc<Vec<CompletionSuggestion>>>>>,
34 learning_data: Arc<RwLock<CompletionLearningData>>,
35 performance_stats: Arc<RwLock<CompletionStats>>,
36}
37
38#[derive(Debug, Clone, Default)]
40pub struct CompletionStats {
41 pub total_requests: usize,
42 pub cache_hits: usize,
43 pub average_response_time_ms: f64,
44 pub acceptance_rate: f64,
45}
46
47impl CompletionEngine {
48 pub fn new() -> Self {
49 Self {
50 suggestion_cache: Arc::new(RwLock::new(HashMap::new())),
51 learning_data: Arc::new(RwLock::new(CompletionLearningData::default())),
52 performance_stats: Arc::new(RwLock::new(CompletionStats::default())),
53 }
54 }
55
56 pub async fn complete(&self, context: &CompletionContext) -> Vec<CompletionSuggestion> {
58 let arc = self.complete_shared(context).await;
59 (*arc).clone()
60 }
61
62 pub async fn complete_shared(
65 &self,
66 context: &CompletionContext,
67 ) -> Arc<Vec<CompletionSuggestion>> {
68 let cache_key = format!("{}:{}:{}", context.language, context.line, context.column);
69
70 {
71 let cache = self.suggestion_cache.read().await;
72 if let Some(cached) = cache.get(&cache_key) {
73 return Arc::clone(cached);
74 }
75 }
76
77 let mut suggestions = Vec::new();
79 let keywords = self.get_language_keywords(&context.language);
80 for keyword in keywords {
81 if keyword.starts_with(&context.prefix) {
82 suggestions.push(CompletionSuggestion {
83 text: keyword.to_string(),
84 kind: CompletionKind::Keyword,
85 confidence: 0.8,
86 context: context.clone(),
87 metadata: HashMap::new(),
88 acceptance_rate: 0.0,
89 learning_data: CompletionLearningData::default(),
90 accepted_count: 0,
91 rejected_count: 0,
92 });
93 }
94 }
95
96 let snippets = self.get_language_snippets(&context.language);
97 for snippet in snippets {
98 if snippet.label.starts_with(&context.prefix) {
99 suggestions.push(CompletionSuggestion {
100 text: snippet.template,
101 kind: CompletionKind::Snippet,
102 confidence: 0.7,
103 context: context.clone(),
104 metadata: HashMap::from([
105 ("label".to_owned(), snippet.label),
106 ("description".to_owned(), snippet.description),
107 ]),
108 acceptance_rate: 0.0,
109 learning_data: CompletionLearningData::default(),
110 accepted_count: 0,
111 rejected_count: 0,
112 });
113 }
114 }
115
116 let arc = Arc::new(suggestions);
118 {
119 let mut cache = self.suggestion_cache.write().await;
120 cache.insert(cache_key, Arc::clone(&arc));
121 }
122
123 arc
124 }
125
126 pub async fn record_feedback(&self, suggestion_id: &str, accepted: bool) {
128 let mut learning_data = self.learning_data.write().await;
129
130 let current_rate = learning_data
132 .pattern_acceptance
133 .get(suggestion_id)
134 .copied()
135 .unwrap_or(0.0);
136 let new_rate = if accepted {
137 (current_rate + 1.0) / 2.0
138 } else {
139 current_rate * 0.9
140 };
141 learning_data
142 .pattern_acceptance
143 .insert(suggestion_id.to_string(), new_rate);
144
145 let mut stats = self.performance_stats.write().await;
147 stats.total_requests += 1;
148 if accepted {
149 stats.acceptance_rate = (stats.acceptance_rate * (stats.total_requests - 1) as f64
150 + 1.0)
151 / stats.total_requests as f64;
152 }
153 }
154
155 fn get_language_keywords(&self, language: &str) -> Vec<&'static str> {
157 match language {
158 "rust" => vec![
159 "fn", "let", "mut", "const", "static", "struct", "enum", "impl", "trait", "mod",
160 "use", "pub", "crate", "super", "self", "Self", "async", "await", "move", "if",
161 "else", "match", "loop", "while", "for", "in", "break", "continue", "return", "as",
162 "dyn", "where", "unsafe",
163 ],
164 "python" => vec![
165 "def", "class", "if", "elif", "else", "for", "while", "try", "except", "finally",
166 "with", "as", "import", "from", "return", "yield", "lambda", "and", "or", "not",
167 "in", "is", "None", "True", "False", "self", "super",
168 ],
169 "javascript" => vec![
170 "function",
171 "const",
172 "let",
173 "var",
174 "if",
175 "else",
176 "for",
177 "while",
178 "try",
179 "catch",
180 "finally",
181 "return",
182 "async",
183 "await",
184 "class",
185 "extends",
186 "import",
187 "export",
188 "from",
189 "as",
190 "this",
191 "super",
192 "new",
193 "typeof",
194 "instanceof",
195 ],
196 _ => vec![],
197 }
198 }
199
200 fn get_language_snippets(&self, language: &str) -> Vec<CodeSnippet> {
202 match language {
203 "rust" => vec![
204 CodeSnippet {
205 label: "fn".to_string(),
206 template: "fn ${1:name}(${2:params}) -> ${3:ReturnType} {\n\t${0:// body}\n}".to_string(),
207 description: "Function declaration".to_string(),
208 },
209 CodeSnippet {
210 label: "impl".to_string(),
211 template: "impl ${1:Trait} for ${2:Type} {\n\t${0:// implementation}\n}".to_string(),
212 description: "Implementation block".to_string(),
213 },
214 ],
215 "python" => vec![
216 CodeSnippet {
217 label: "def".to_string(),
218 template: "def ${1:name}(${2:params}):\n\t${0:# body}".to_string(),
219 description: "Function definition".to_string(),
220 },
221 CodeSnippet {
222 label: "class".to_string(),
223 template: "class ${1:Name}:\n\tdef __init__(self${2:params}):\n\t\t${0:# initialization}".to_string(),
224 description: "Class definition".to_string(),
225 },
226 ],
227 "javascript" => vec![
228 CodeSnippet {
229 label: "func".to_string(),
230 template: "function ${1:name}(${2:params}) {\n\t${0:// body}\n}".to_string(),
231 description: "Function declaration".to_string(),
232 },
233 CodeSnippet {
234 label: "class".to_string(),
235 template: "class ${1:Name} {\n\tconstructor(${2:params}) {\n\t\t${0:// initialization}\n\t}\n}".to_string(),
236 description: "Class declaration".to_string(),
237 },
238 ],
239 _ => vec![],
240 }
241 }
242}
243
244impl Default for CompletionEngine {
245 fn default() -> Self {
246 Self::new()
247 }
248}
249
250#[derive(Debug, Clone)]
252pub struct CodeSnippet {
253 pub label: String,
254 pub template: String,
255 pub description: String,
256}