1use crate::domain::{
4 CodeFileFingerprint, CodeImpactRequest, CodeIndexBatch, CodeIndexCheckpoint, CodeIndexSession,
5 CodeIndexSnapshot, CodeIndexSummary, CodeIndexTaskRecord, CodeRepositoryCrossEdge,
6 CodeRepositoryRegistration, CodeRepositoryReport, CodeRepositorySet, CodeRepositorySetMember,
7 CodeRepositorySetRefreshSummary, CodeRepositorySetRefreshTaskRecord, CodeRepositorySetStatus,
8 CodeRepositoryStatus, CodeRepositoryTotals, CodeRetrievalHit, CodeRetrievalRequest,
9 CodeScopeRetentionSummary,
10};
11
12use super::{StorageError, StorageFuture};
13
14#[derive(Debug, Clone, Default, PartialEq, Eq)]
16pub struct CodeImpactChanges {
17 pub paths: Vec<String>,
18 pub deleted_symbol_names: Vec<String>,
19}
20
21#[derive(Debug, Clone, PartialEq, Eq)]
23pub struct CodeIndexTaskSeed {
24 pub repository_id: String,
25 pub alias: String,
26 pub ref_selector: String,
27 pub resolved_commit_sha: String,
28 pub tree_hash: String,
29 pub source_scope: String,
30 pub path_filters: Vec<String>,
31 pub language_filters: Vec<String>,
32 pub mode: crate::domain::CodeIndexMode,
33 pub input_fingerprint: String,
34 pub resource_budget: crate::domain::CodeIndexResourceBudget,
35 pub payload_json: String,
36 pub now_ms: u64,
37}
38
39#[derive(Debug, Clone, PartialEq, Eq)]
41pub struct CodeIndexTaskClaimRequest {
42 pub task_id: Option<String>,
43 pub lease_owner: String,
44 pub lease_duration_ms: u64,
45 pub max_attempts: u32,
46 pub now_ms: u64,
47}
48
49#[derive(Debug, Clone, PartialEq, Eq)]
51pub struct CodeIndexTaskCompletion {
52 pub task_id: String,
53 pub lease_owner: String,
54 pub attempt_count: u32,
55 pub now_ms: u64,
56}
57
58#[derive(Debug, Clone, PartialEq, Eq)]
60pub struct CodeIndexTaskFailure {
61 pub task_id: String,
62 pub lease_owner: String,
63 pub attempt_count: u32,
64 pub error_kind: String,
65 pub error_message: String,
66 pub retry_backoff_ms: u64,
67 pub max_attempts: u32,
68 pub now_ms: u64,
69}
70
71#[derive(Debug, Clone, PartialEq, Eq)]
73pub struct CodeScopeRetentionRequest {
74 pub repository_id: String,
75 pub active_scope: String,
76 pub retain_recent_successful_scopes: usize,
77}
78
79#[derive(Debug, Clone, PartialEq, Eq)]
81pub struct CodeRepositorySetSeed {
82 pub alias: String,
83 pub description: Option<String>,
84 pub default_ref_policy_json: String,
85 pub now_ms: u64,
86}
87
88#[derive(Debug, Clone, PartialEq, Eq)]
90pub struct CodeRepositorySetMemberSeed {
91 pub set_alias: String,
92 pub repository_id: String,
93 pub repository_alias: String,
94 pub ref_selector: String,
95 pub resolved_commit_sha: String,
96 pub source_scope: String,
97 pub path_filters: Vec<String>,
98 pub language_filters: Vec<String>,
99 pub priority: i32,
100}
101
102#[derive(Debug, Clone, PartialEq, Eq)]
104pub struct CodeRepositorySetRefreshTaskSeed {
105 pub set_id: String,
106 pub set_alias: String,
107 pub input_fingerprint: String,
108 pub now_ms: u64,
109}
110
111#[derive(Debug, Clone, PartialEq, Eq)]
113pub struct CodeRepositorySetRefreshTaskClaimRequest {
114 pub task_id: Option<String>,
115 pub lease_owner: String,
116 pub lease_duration_ms: u64,
117 pub max_attempts: u32,
118 pub now_ms: u64,
119}
120
121#[derive(Debug, Clone, PartialEq, Eq)]
123pub struct CodeRepositorySetRefreshTaskCompletion {
124 pub task_id: String,
125 pub lease_owner: String,
126 pub attempt_count: u32,
127 pub now_ms: u64,
128}
129
130#[derive(Debug, Clone, PartialEq, Eq)]
132pub struct CodeRepositorySetRefreshTaskFailure {
133 pub task_id: String,
134 pub lease_owner: String,
135 pub attempt_count: u32,
136 pub error_kind: String,
137 pub error_message: String,
138 pub retry_backoff_ms: u64,
139 pub max_attempts: u32,
140 pub now_ms: u64,
141}
142
143pub trait CodeRepositoryStore: Send + Sync {
145 fn upsert_code_repository(
146 &self,
147 registration: CodeRepositoryRegistration,
148 ) -> StorageFuture<'_, CodeRepositoryStatus>;
149
150 fn code_repository_status(
151 &self,
152 repository: String,
153 ) -> StorageFuture<'_, Option<CodeRepositoryStatus>>;
154
155 fn code_repository_scope_status(
156 &self,
157 repository: String,
158 resolved_commit_sha: String,
159 path_filters: Vec<String>,
160 language_filters: Vec<String>,
161 ) -> StorageFuture<'_, Option<CodeRepositoryStatus>>;
162
163 fn queue_code_index_task(
164 &self,
165 task: CodeIndexTaskSeed,
166 ) -> StorageFuture<'_, CodeIndexTaskRecord>;
167
168 fn claim_code_index_task(
169 &self,
170 request: CodeIndexTaskClaimRequest,
171 ) -> StorageFuture<'_, Option<CodeIndexTaskRecord>>;
172
173 fn complete_code_index_task(
174 &self,
175 request: CodeIndexTaskCompletion,
176 ) -> StorageFuture<'_, CodeIndexTaskRecord>;
177
178 fn fail_code_index_task(
179 &self,
180 request: CodeIndexTaskFailure,
181 ) -> StorageFuture<'_, CodeIndexTaskRecord>;
182
183 fn code_index_task(&self, task_id: String) -> StorageFuture<'_, Option<CodeIndexTaskRecord>>;
184
185 fn active_code_index_task(
186 &self,
187 repository_id: String,
188 ) -> StorageFuture<'_, Option<CodeIndexTaskRecord>>;
189
190 fn code_index_checkpoint(
191 &self,
192 source_scope: String,
193 ) -> StorageFuture<'_, Option<CodeIndexCheckpoint>>;
194
195 fn code_scope_retention(
196 &self,
197 repository_id: String,
198 ) -> StorageFuture<'_, CodeScopeRetentionSummary>;
199
200 fn prune_code_repository_scopes(
201 &self,
202 request: CodeScopeRetentionRequest,
203 ) -> StorageFuture<'_, CodeScopeRetentionSummary>;
204
205 fn code_file_fingerprints(
206 &self,
207 repository_id: String,
208 ) -> StorageFuture<'_, Vec<CodeFileFingerprint>>;
209
210 fn code_file_fingerprints_for_scope(
211 &self,
212 source_scope: String,
213 ) -> StorageFuture<'_, Vec<CodeFileFingerprint>> {
214 Box::pin(async move {
215 Err(StorageError::InvalidInput(format!(
216 "code file fingerprints for scope '{source_scope}' are unavailable"
217 )))
218 })
219 }
220
221 fn code_file_candidate_paths_for_scope(
222 &self,
223 source_scope: String,
224 _path_filters: Vec<String>,
225 _language_filters: Vec<String>,
226 _limit: usize,
227 ) -> StorageFuture<'_, Vec<String>> {
228 Box::pin(async move {
229 Err(StorageError::InvalidInput(format!(
230 "bounded code file candidate paths for scope '{source_scope}' are unavailable"
231 )))
232 })
233 }
234
235 fn apply_code_index_snapshot(
236 &self,
237 snapshot: CodeIndexSnapshot,
238 ) -> StorageFuture<'_, CodeIndexSummary>;
239
240 fn begin_code_index_session(
241 &self,
242 session: CodeIndexSession,
243 ) -> StorageFuture<'_, CodeIndexCheckpoint> {
244 Box::pin(async move {
245 Err(StorageError::InvalidInput(format!(
246 "checkpointed code index sessions for scope '{}' are unavailable",
247 session.source_scope
248 )))
249 })
250 }
251
252 fn apply_code_index_batch(
253 &self,
254 batch: CodeIndexBatch,
255 ) -> StorageFuture<'_, CodeIndexCheckpoint> {
256 Box::pin(async move {
257 Err(StorageError::InvalidInput(format!(
258 "checkpointed code index batches for scope '{}' are unavailable",
259 batch.source_scope
260 )))
261 })
262 }
263
264 fn finalize_code_index_session(
265 &self,
266 session: CodeIndexSession,
267 ) -> StorageFuture<'_, CodeIndexSummary> {
268 Box::pin(async move {
269 Err(StorageError::InvalidInput(format!(
270 "checkpointed code index finalization for scope '{}' is unavailable",
271 session.source_scope
272 )))
273 })
274 }
275
276 fn search_code(
277 &self,
278 request: CodeRetrievalRequest,
279 ) -> StorageFuture<'_, Vec<CodeRetrievalHit>>;
280
281 fn search_code_scope(
282 &self,
283 source_scope: String,
284 _request: CodeRetrievalRequest,
285 ) -> StorageFuture<'_, Vec<CodeRetrievalHit>> {
286 Box::pin(async move {
287 Err(StorageError::InvalidInput(format!(
288 "code search for source scope '{source_scope}' is unavailable"
289 )))
290 })
291 }
292
293 fn analyze_code_impact(
294 &self,
295 request: CodeImpactRequest,
296 changes: CodeImpactChanges,
297 ) -> StorageFuture<'_, Vec<CodeRetrievalHit>>;
298
299 fn code_repository_totals(&self) -> StorageFuture<'_, CodeRepositoryTotals> {
300 Box::pin(async { Ok(CodeRepositoryTotals::default()) })
301 }
302
303 fn code_repository_report(
304 &self,
305 repository: String,
306 ) -> StorageFuture<'_, CodeRepositoryReport> {
307 Box::pin(async move {
308 Err(StorageError::InvalidInput(format!(
309 "code repository report for '{repository}' is unavailable"
310 )))
311 })
312 }
313
314 fn create_code_repository_set(
315 &self,
316 _seed: CodeRepositorySetSeed,
317 ) -> StorageFuture<'_, CodeRepositorySet> {
318 Box::pin(async {
319 Err(StorageError::InvalidInput(
320 "repository set storage is unavailable".to_owned(),
321 ))
322 })
323 }
324
325 fn add_code_repository_set_member(
326 &self,
327 _seed: CodeRepositorySetMemberSeed,
328 ) -> StorageFuture<'_, CodeRepositorySetMember> {
329 Box::pin(async {
330 Err(StorageError::InvalidInput(
331 "repository set member storage is unavailable".to_owned(),
332 ))
333 })
334 }
335
336 fn remove_code_repository_set_member(
337 &self,
338 _set_alias: String,
339 _repository_alias: String,
340 ) -> StorageFuture<'_, CodeRepositorySetMember> {
341 Box::pin(async {
342 Err(StorageError::InvalidInput(
343 "repository set member storage is unavailable".to_owned(),
344 ))
345 })
346 }
347
348 fn code_repository_set(
349 &self,
350 _set_alias: String,
351 ) -> StorageFuture<'_, Option<CodeRepositorySet>> {
352 Box::pin(async { Ok(None) })
353 }
354
355 fn code_repository_set_status(
356 &self,
357 _set_alias: String,
358 ) -> StorageFuture<'_, Option<CodeRepositorySetStatus>> {
359 Box::pin(async { Ok(None) })
360 }
361
362 fn refresh_code_repository_set_overlay(
363 &self,
364 _set_alias: String,
365 _now_ms: u64,
366 ) -> StorageFuture<'_, CodeRepositorySetRefreshSummary> {
367 Box::pin(async {
368 Err(StorageError::InvalidInput(
369 "repository set overlay refresh is unavailable".to_owned(),
370 ))
371 })
372 }
373
374 fn code_repository_set_cross_edges(
375 &self,
376 _set_id: String,
377 ) -> StorageFuture<'_, Vec<CodeRepositoryCrossEdge>> {
378 Box::pin(async { Ok(Vec::new()) })
379 }
380
381 fn queue_code_repository_set_refresh_task(
382 &self,
383 _task: CodeRepositorySetRefreshTaskSeed,
384 ) -> StorageFuture<'_, CodeRepositorySetRefreshTaskRecord> {
385 Box::pin(async {
386 Err(StorageError::InvalidInput(
387 "repository set refresh task storage is unavailable".to_owned(),
388 ))
389 })
390 }
391
392 fn claim_code_repository_set_refresh_task(
393 &self,
394 _request: CodeRepositorySetRefreshTaskClaimRequest,
395 ) -> StorageFuture<'_, Option<CodeRepositorySetRefreshTaskRecord>> {
396 Box::pin(async { Ok(None) })
397 }
398
399 fn complete_code_repository_set_refresh_task(
400 &self,
401 _request: CodeRepositorySetRefreshTaskCompletion,
402 ) -> StorageFuture<'_, CodeRepositorySetRefreshTaskRecord> {
403 Box::pin(async {
404 Err(StorageError::InvalidInput(
405 "repository set refresh task storage is unavailable".to_owned(),
406 ))
407 })
408 }
409
410 fn fail_code_repository_set_refresh_task(
411 &self,
412 _request: CodeRepositorySetRefreshTaskFailure,
413 ) -> StorageFuture<'_, CodeRepositorySetRefreshTaskRecord> {
414 Box::pin(async {
415 Err(StorageError::InvalidInput(
416 "repository set refresh task storage is unavailable".to_owned(),
417 ))
418 })
419 }
420}