1use super::{LanguageFrameworkDetector, TechnologyRule, FrameworkDetectionUtils};
2use crate::analyzer::{DetectedTechnology, DetectedLanguage, TechnologyCategory, LibraryType};
3use crate::error::Result;
4
5pub struct PythonFrameworkDetector;
6
7impl LanguageFrameworkDetector for PythonFrameworkDetector {
8 fn detect_frameworks(&self, language: &DetectedLanguage) -> Result<Vec<DetectedTechnology>> {
9 let rules = get_python_technology_rules();
10
11 let all_deps: Vec<String> = language.main_dependencies.iter()
13 .chain(language.dev_dependencies.iter())
14 .cloned()
15 .collect();
16
17 let technologies = FrameworkDetectionUtils::detect_technologies_by_dependencies(
18 &rules, &all_deps, language.confidence
19 );
20
21 Ok(technologies)
22 }
23
24 fn supported_languages(&self) -> Vec<&'static str> {
25 vec!["Python"]
26 }
27}
28
29fn get_python_technology_rules() -> Vec<TechnologyRule> {
31 vec![
32 TechnologyRule {
34 name: "Django".to_string(),
35 category: TechnologyCategory::BackendFramework,
36 confidence: 0.95,
37 dependency_patterns: vec!["django".to_string(), "Django".to_string()],
38 requires: vec![],
39 conflicts_with: vec![],
40 is_primary_indicator: true,
41 alternative_names: vec![],
42 file_indicators: vec![],
43 },
44 TechnologyRule {
45 name: "Django REST Framework".to_string(),
46 category: TechnologyCategory::BackendFramework,
47 confidence: 0.90,
48 dependency_patterns: vec!["djangorestframework".to_string(), "rest_framework".to_string()],
49 requires: vec!["Django".to_string()],
50 conflicts_with: vec![],
51 is_primary_indicator: false,
52 alternative_names: vec!["DRF".to_string()],
53 file_indicators: vec![],
54 },
55
56 TechnologyRule {
58 name: "Flask".to_string(),
59 category: TechnologyCategory::BackendFramework,
60 confidence: 0.95,
61 dependency_patterns: vec!["flask".to_string(), "Flask".to_string()],
62 requires: vec![],
63 conflicts_with: vec![],
64 is_primary_indicator: true,
65 alternative_names: vec![],
66 file_indicators: vec![],
67 },
68 TechnologyRule {
69 name: "FastAPI".to_string(),
70 category: TechnologyCategory::BackendFramework,
71 confidence: 0.95,
72 dependency_patterns: vec!["fastapi".to_string(), "FastAPI".to_string()],
73 requires: vec![],
74 conflicts_with: vec![],
75 is_primary_indicator: true,
76 alternative_names: vec![],
77 file_indicators: vec![],
78 },
79 TechnologyRule {
80 name: "Starlette".to_string(),
81 category: TechnologyCategory::BackendFramework,
82 confidence: 0.90,
83 dependency_patterns: vec!["starlette".to_string(), "Starlette".to_string()],
84 requires: vec![],
85 conflicts_with: vec![],
86 is_primary_indicator: true,
87 alternative_names: vec![],
88 file_indicators: vec![],
89 },
90 TechnologyRule {
91 name: "Quart".to_string(),
92 category: TechnologyCategory::BackendFramework,
93 confidence: 0.90,
94 dependency_patterns: vec!["quart".to_string(), "Quart".to_string()],
95 requires: vec![],
96 conflicts_with: vec![],
97 is_primary_indicator: true,
98 alternative_names: vec![],
99 file_indicators: vec![],
100 },
101 TechnologyRule {
102 name: "Sanic".to_string(),
103 category: TechnologyCategory::BackendFramework,
104 confidence: 0.90,
105 dependency_patterns: vec!["sanic".to_string(), "Sanic".to_string()],
106 requires: vec![],
107 conflicts_with: vec![],
108 is_primary_indicator: true,
109 alternative_names: vec![],
110 file_indicators: vec![],
111 },
112 TechnologyRule {
113 name: "Bottle".to_string(),
114 category: TechnologyCategory::BackendFramework,
115 confidence: 0.85,
116 dependency_patterns: vec!["bottle".to_string(), "Bottle".to_string()],
117 requires: vec![],
118 conflicts_with: vec![],
119 is_primary_indicator: true,
120 alternative_names: vec![],
121 file_indicators: vec![],
122 },
123 TechnologyRule {
124 name: "Falcon".to_string(),
125 category: TechnologyCategory::BackendFramework,
126 confidence: 0.85,
127 dependency_patterns: vec!["falcon".to_string(), "Falcon".to_string()],
128 requires: vec![],
129 conflicts_with: vec![],
130 is_primary_indicator: true,
131 alternative_names: vec![],
132 file_indicators: vec![],
133 },
134 TechnologyRule {
135 name: "Hug".to_string(),
136 category: TechnologyCategory::BackendFramework,
137 confidence: 0.85,
138 dependency_patterns: vec!["hug".to_string(), "Hug".to_string()],
139 requires: vec![],
140 conflicts_with: vec![],
141 is_primary_indicator: true,
142 alternative_names: vec![],
143 file_indicators: vec![],
144 },
145 TechnologyRule {
146 name: "Molten".to_string(),
147 category: TechnologyCategory::BackendFramework,
148 confidence: 0.85,
149 dependency_patterns: vec!["molten".to_string(), "Molten".to_string()],
150 requires: vec![],
151 conflicts_with: vec![],
152 is_primary_indicator: true,
153 alternative_names: vec![],
154 file_indicators: vec![],
155 },
156 TechnologyRule {
157 name: "Responder".to_string(),
158 category: TechnologyCategory::BackendFramework,
159 confidence: 0.85,
160 dependency_patterns: vec!["responder".to_string(), "Responder".to_string()],
161 requires: vec![],
162 conflicts_with: vec![],
163 is_primary_indicator: true,
164 alternative_names: vec![],
165 file_indicators: vec![],
166 },
167 TechnologyRule {
168 name: "Vibora".to_string(),
169 category: TechnologyCategory::BackendFramework,
170 confidence: 0.85,
171 dependency_patterns: vec!["vibora".to_string(), "Vibora".to_string()],
172 requires: vec![],
173 conflicts_with: vec![],
174 is_primary_indicator: true,
175 alternative_names: vec![],
176 file_indicators: vec![],
177 },
178 TechnologyRule {
179 name: "Asgi".to_string(),
180 category: TechnologyCategory::BackendFramework,
181 confidence: 0.85,
182 dependency_patterns: vec!["asgi".to_string(), "Asgi".to_string()],
183 requires: vec![],
184 conflicts_with: vec![],
185 is_primary_indicator: true,
186 alternative_names: vec![],
187 file_indicators: vec![],
188 },
189 TechnologyRule {
190 name: "Tornado".to_string(),
191 category: TechnologyCategory::BackendFramework,
192 confidence: 0.90,
193 dependency_patterns: vec!["tornado".to_string(), "Tornado".to_string()],
194 requires: vec![],
195 conflicts_with: vec![],
196 is_primary_indicator: true,
197 alternative_names: vec![],
198 file_indicators: vec![],
199 },
200 TechnologyRule {
201 name: "CherryPy".to_string(),
202 category: TechnologyCategory::BackendFramework,
203 confidence: 0.85,
204 dependency_patterns: vec!["cherrypy".to_string(), "CherryPy".to_string()],
205 requires: vec![],
206 conflicts_with: vec![],
207 is_primary_indicator: true,
208 alternative_names: vec![],
209 file_indicators: vec![],
210 },
211 TechnologyRule {
212 name: "Web2py".to_string(),
213 category: TechnologyCategory::BackendFramework,
214 confidence: 0.85,
215 dependency_patterns: vec!["web2py".to_string(), "Web2py".to_string()],
216 requires: vec![],
217 conflicts_with: vec![],
218 is_primary_indicator: true,
219 alternative_names: vec![],
220 file_indicators: vec![],
221 },
222 TechnologyRule {
223 name: "Pyramid".to_string(),
224 category: TechnologyCategory::BackendFramework,
225 confidence: 0.90,
226 dependency_patterns: vec!["pyramid".to_string(), "Pyramid".to_string()],
227 requires: vec![],
228 conflicts_with: vec![],
229 is_primary_indicator: true,
230 alternative_names: vec![],
231 file_indicators: vec![],
232 },
233 TechnologyRule {
234 name: "TurboGears".to_string(),
235 category: TechnologyCategory::BackendFramework,
236 confidence: 0.85,
237 dependency_patterns: vec!["tg".to_string(), "TurboGears".to_string()],
238 requires: vec![],
239 conflicts_with: vec![],
240 is_primary_indicator: true,
241 alternative_names: vec![],
242 file_indicators: vec![],
243 },
244 TechnologyRule {
245 name: "Klein".to_string(),
246 category: TechnologyCategory::BackendFramework,
247 confidence: 0.85,
248 dependency_patterns: vec!["klein".to_string(), "Klein".to_string()],
249 requires: vec![],
250 conflicts_with: vec![],
251 is_primary_indicator: true,
252 alternative_names: vec![],
253 file_indicators: vec![],
254 },
255 TechnologyRule {
256 name: "Morepath".to_string(),
257 category: TechnologyCategory::BackendFramework,
258 confidence: 0.85,
259 dependency_patterns: vec!["morepath".to_string(), "Morepath".to_string()],
260 requires: vec![],
261 conflicts_with: vec![],
262 is_primary_indicator: true,
263 alternative_names: vec![],
264 file_indicators: vec![],
265 },
266 TechnologyRule {
267 name: "Masonite".to_string(),
268 category: TechnologyCategory::BackendFramework,
269 confidence: 0.85,
270 dependency_patterns: vec!["masonite".to_string(), "Masonite".to_string()],
271 requires: vec![],
272 conflicts_with: vec![],
273 is_primary_indicator: true,
274 alternative_names: vec![],
275 file_indicators: vec![],
276 },
277 TechnologyRule {
278 name: "Litestar".to_string(),
279 category: TechnologyCategory::BackendFramework,
280 confidence: 0.90,
281 dependency_patterns: vec!["litestar".to_string(), "Litestar".to_string()],
282 requires: vec![],
283 conflicts_with: vec![],
284 is_primary_indicator: true,
285 alternative_names: vec!["Starlite".to_string()],
286 file_indicators: vec![],
287 },
288 TechnologyRule {
289 name: "Connexion".to_string(),
290 category: TechnologyCategory::BackendFramework,
291 confidence: 0.85,
292 dependency_patterns: vec!["connexion".to_string(), "Connexion".to_string()],
293 requires: vec![],
294 conflicts_with: vec![],
295 is_primary_indicator: true,
296 alternative_names: vec![],
297 file_indicators: vec![],
298 },
299 TechnologyRule {
300 name: "Nameko".to_string(),
301 category: TechnologyCategory::BackendFramework,
302 confidence: 0.85,
303 dependency_patterns: vec!["nameko".to_string(), "Nameko".to_string()],
304 requires: vec![],
305 conflicts_with: vec![],
306 is_primary_indicator: true,
307 alternative_names: vec![],
308 file_indicators: vec![],
309 },
310 TechnologyRule {
311 name: "Aiohttp".to_string(),
312 category: TechnologyCategory::BackendFramework,
313 confidence: 0.90,
314 dependency_patterns: vec!["aiohttp".to_string(), "Aiohttp".to_string()],
315 requires: vec![],
316 conflicts_with: vec![],
317 is_primary_indicator: true,
318 alternative_names: vec![],
319 file_indicators: vec![],
320 },
321
322 TechnologyRule {
324 name: "asyncio".to_string(),
325 category: TechnologyCategory::Runtime,
326 confidence: 0.85,
327 dependency_patterns: vec!["asyncio".to_string()],
328 requires: vec![],
329 conflicts_with: vec![],
330 is_primary_indicator: false,
331 alternative_names: vec![],
332 file_indicators: vec![],
333 },
334 TechnologyRule {
335 name: "Trio".to_string(),
336 category: TechnologyCategory::Runtime,
337 confidence: 0.85,
338 dependency_patterns: vec!["trio".to_string()],
339 requires: vec![],
340 conflicts_with: vec![],
341 is_primary_indicator: false,
342 alternative_names: vec![],
343 file_indicators: vec![],
344 },
345 TechnologyRule {
346 name: "Curio".to_string(),
347 category: TechnologyCategory::Runtime,
348 confidence: 0.85,
349 dependency_patterns: vec!["curio".to_string()],
350 requires: vec![],
351 conflicts_with: vec![],
352 is_primary_indicator: false,
353 alternative_names: vec![],
354 file_indicators: vec![],
355 },
356
357 TechnologyRule {
359 name: "Streamlit".to_string(),
360 category: TechnologyCategory::FrontendFramework,
361 confidence: 0.95,
362 dependency_patterns: vec!["streamlit".to_string(), "Streamlit".to_string()],
363 requires: vec![],
364 conflicts_with: vec![],
365 is_primary_indicator: true,
366 alternative_names: vec![],
367 file_indicators: vec![],
368 },
369 TechnologyRule {
370 name: "Gradio".to_string(),
371 category: TechnologyCategory::FrontendFramework,
372 confidence: 0.95,
373 dependency_patterns: vec!["gradio".to_string(), "Gradio".to_string()],
374 requires: vec![],
375 conflicts_with: vec![],
376 is_primary_indicator: true,
377 alternative_names: vec![],
378 file_indicators: vec![],
379 },
380 TechnologyRule {
381 name: "Dash".to_string(),
382 category: TechnologyCategory::FrontendFramework,
383 confidence: 0.90,
384 dependency_patterns: vec!["dash".to_string(), "Dash".to_string()],
385 requires: vec!["Flask".to_string()],
386 conflicts_with: vec![],
387 is_primary_indicator: true,
388 alternative_names: vec![],
389 file_indicators: vec![],
390 },
391 TechnologyRule {
392 name: "Panel".to_string(),
393 category: TechnologyCategory::FrontendFramework,
394 confidence: 0.90,
395 dependency_patterns: vec!["panel".to_string(), "Panel".to_string()],
396 requires: vec!["Bokeh".to_string()],
397 conflicts_with: vec![],
398 is_primary_indicator: true,
399 alternative_names: vec![],
400 file_indicators: vec![],
401 },
402 TechnologyRule {
403 name: "NiceGUI".to_string(),
404 category: TechnologyCategory::FrontendFramework,
405 confidence: 0.90,
406 dependency_patterns: vec!["nicegui".to_string(), "NiceGUI".to_string()],
407 requires: vec![],
408 conflicts_with: vec![],
409 is_primary_indicator: true,
410 alternative_names: vec![],
411 file_indicators: vec![],
412 },
413 TechnologyRule {
414 name: "Reflex".to_string(),
415 category: TechnologyCategory::FrontendFramework,
416 confidence: 0.90,
417 dependency_patterns: vec!["reflex".to_string(), "Reflex".to_string()],
418 requires: vec![],
419 conflicts_with: vec![],
420 is_primary_indicator: true,
421 alternative_names: vec!["pynecone".to_string()],
422 file_indicators: vec![],
423 },
424 TechnologyRule {
425 name: "PyWebIO".to_string(),
426 category: TechnologyCategory::FrontendFramework,
427 confidence: 0.85,
428 dependency_patterns: vec!["pywebio".to_string(), "PyWebIO".to_string()],
429 requires: vec![],
430 conflicts_with: vec![],
431 is_primary_indicator: true,
432 alternative_names: vec![],
433 file_indicators: vec![],
434 },
435 TechnologyRule {
436 name: "Anvil".to_string(),
437 category: TechnologyCategory::FrontendFramework,
438 confidence: 0.85,
439 dependency_patterns: vec!["anvil".to_string(), "Anvil".to_string()],
440 requires: vec![],
441 conflicts_with: vec![],
442 is_primary_indicator: true,
443 alternative_names: vec![],
444 file_indicators: vec![],
445 },
446
447 TechnologyRule {
449 name: "NumPy".to_string(),
450 category: TechnologyCategory::Library(LibraryType::Utility),
451 confidence: 0.90,
452 dependency_patterns: vec!["numpy".to_string(), "NumPy".to_string()],
453 requires: vec![],
454 conflicts_with: vec![],
455 is_primary_indicator: false,
456 alternative_names: vec![],
457 file_indicators: vec![],
458 },
459 TechnologyRule {
460 name: "SciPy".to_string(),
461 category: TechnologyCategory::Library(LibraryType::Utility),
462 confidence: 0.90,
463 dependency_patterns: vec!["scipy".to_string(), "SciPy".to_string()],
464 requires: vec!["NumPy".to_string()],
465 conflicts_with: vec![],
466 is_primary_indicator: false,
467 alternative_names: vec![],
468 file_indicators: vec![],
469 },
470 TechnologyRule {
471 name: "Pandas".to_string(),
472 category: TechnologyCategory::Library(LibraryType::Utility),
473 confidence: 0.90,
474 dependency_patterns: vec!["pandas".to_string(), "Pandas".to_string()],
475 requires: vec!["NumPy".to_string()],
476 conflicts_with: vec![],
477 is_primary_indicator: false,
478 alternative_names: vec![],
479 file_indicators: vec![],
480 },
481 TechnologyRule {
482 name: "Matplotlib".to_string(),
483 category: TechnologyCategory::Library(LibraryType::Utility),
484 confidence: 0.85,
485 dependency_patterns: vec!["matplotlib".to_string(), "Matplotlib".to_string()],
486 requires: vec![],
487 conflicts_with: vec![],
488 is_primary_indicator: false,
489 alternative_names: vec![],
490 file_indicators: vec![],
491 },
492 TechnologyRule {
493 name: "Seaborn".to_string(),
494 category: TechnologyCategory::Library(LibraryType::Utility),
495 confidence: 0.85,
496 dependency_patterns: vec!["seaborn".to_string(), "Seaborn".to_string()],
497 requires: vec!["Matplotlib".to_string(), "Pandas".to_string()],
498 conflicts_with: vec![],
499 is_primary_indicator: false,
500 alternative_names: vec![],
501 file_indicators: vec![],
502 },
503 TechnologyRule {
504 name: "Plotly".to_string(),
505 category: TechnologyCategory::Library(LibraryType::Utility),
506 confidence: 0.85,
507 dependency_patterns: vec!["plotly".to_string(), "Plotly".to_string()],
508 requires: vec![],
509 conflicts_with: vec![],
510 is_primary_indicator: false,
511 alternative_names: vec![],
512 file_indicators: vec![],
513 },
514 TechnologyRule {
515 name: "Bokeh".to_string(),
516 category: TechnologyCategory::Library(LibraryType::Utility),
517 confidence: 0.85,
518 dependency_patterns: vec!["bokeh".to_string(), "Bokeh".to_string()],
519 requires: vec![],
520 conflicts_with: vec![],
521 is_primary_indicator: false,
522 alternative_names: vec![],
523 file_indicators: vec![],
524 },
525
526 TechnologyRule {
528 name: "TensorFlow".to_string(),
529 category: TechnologyCategory::Library(LibraryType::Utility),
530 confidence: 0.95,
531 dependency_patterns: vec!["tensorflow".to_string(), "TensorFlow".to_string()],
532 requires: vec![],
533 conflicts_with: vec![],
534 is_primary_indicator: false,
535 alternative_names: vec![],
536 file_indicators: vec![],
537 },
538 TechnologyRule {
539 name: "PyTorch".to_string(),
540 category: TechnologyCategory::Library(LibraryType::Utility),
541 confidence: 0.95,
542 dependency_patterns: vec!["torch".to_string(), "PyTorch".to_string()],
543 requires: vec![],
544 conflicts_with: vec![],
545 is_primary_indicator: false,
546 alternative_names: vec![],
547 file_indicators: vec![],
548 },
549 TechnologyRule {
550 name: "Scikit-learn".to_string(),
551 category: TechnologyCategory::Library(LibraryType::Utility),
552 confidence: 0.90,
553 dependency_patterns: vec!["scikit-learn".to_string(), "sklearn".to_string()],
554 requires: vec!["NumPy".to_string(), "SciPy".to_string()],
555 conflicts_with: vec![],
556 is_primary_indicator: false,
557 alternative_names: vec!["sklearn".to_string()],
558 file_indicators: vec![],
559 },
560 TechnologyRule {
561 name: "Keras".to_string(),
562 category: TechnologyCategory::Library(LibraryType::Utility),
563 confidence: 0.90,
564 dependency_patterns: vec!["keras".to_string(), "Keras".to_string()],
565 requires: vec!["TensorFlow".to_string()],
566 conflicts_with: vec![],
567 is_primary_indicator: false,
568 alternative_names: vec![],
569 file_indicators: vec![],
570 },
571 TechnologyRule {
572 name: "XGBoost".to_string(),
573 category: TechnologyCategory::Library(LibraryType::Utility),
574 confidence: 0.85,
575 dependency_patterns: vec!["xgboost".to_string(), "XGBoost".to_string()],
576 requires: vec![],
577 conflicts_with: vec![],
578 is_primary_indicator: false,
579 alternative_names: vec![],
580 file_indicators: vec![],
581 },
582 TechnologyRule {
583 name: "LightGBM".to_string(),
584 category: TechnologyCategory::Library(LibraryType::Utility),
585 confidence: 0.85,
586 dependency_patterns: vec!["lightgbm".to_string(), "LightGBM".to_string()],
587 requires: vec![],
588 conflicts_with: vec![],
589 is_primary_indicator: false,
590 alternative_names: vec![],
591 file_indicators: vec![],
592 },
593 TechnologyRule {
594 name: "CatBoost".to_string(),
595 category: TechnologyCategory::Library(LibraryType::Utility),
596 confidence: 0.85,
597 dependency_patterns: vec!["catboost".to_string(), "CatBoost".to_string()],
598 requires: vec![],
599 conflicts_with: vec![],
600 is_primary_indicator: false,
601 alternative_names: vec![],
602 file_indicators: vec![],
603 },
604
605 TechnologyRule {
607 name: "SQLAlchemy".to_string(),
608 category: TechnologyCategory::Database,
609 confidence: 0.90,
610 dependency_patterns: vec!["sqlalchemy".to_string(), "SQLAlchemy".to_string()],
611 requires: vec![],
612 conflicts_with: vec![],
613 is_primary_indicator: false,
614 alternative_names: vec![],
615 file_indicators: vec![],
616 },
617 TechnologyRule {
618 name: "Peewee".to_string(),
619 category: TechnologyCategory::Database,
620 confidence: 0.85,
621 dependency_patterns: vec!["peewee".to_string(), "Peewee".to_string()],
622 requires: vec![],
623 conflicts_with: vec![],
624 is_primary_indicator: false,
625 alternative_names: vec![],
626 file_indicators: vec![],
627 },
628 TechnologyRule {
629 name: "Tortoise ORM".to_string(),
630 category: TechnologyCategory::Database,
631 confidence: 0.85,
632 dependency_patterns: vec!["tortoise-orm".to_string(), "tortoise".to_string()],
633 requires: vec![],
634 conflicts_with: vec![],
635 is_primary_indicator: false,
636 alternative_names: vec!["tortoise".to_string()],
637 file_indicators: vec![],
638 },
639 TechnologyRule {
640 name: "Django ORM".to_string(),
641 category: TechnologyCategory::Database,
642 confidence: 0.90,
643 dependency_patterns: vec!["django".to_string()],
644 requires: vec!["Django".to_string()],
645 conflicts_with: vec![],
646 is_primary_indicator: false,
647 alternative_names: vec![],
648 file_indicators: vec![],
649 },
650 TechnologyRule {
651 name: "MongoEngine".to_string(),
652 category: TechnologyCategory::Database,
653 confidence: 0.85,
654 dependency_patterns: vec!["mongoengine".to_string(), "MongoEngine".to_string()],
655 requires: vec![],
656 conflicts_with: vec![],
657 is_primary_indicator: false,
658 alternative_names: vec![],
659 file_indicators: vec![],
660 },
661 TechnologyRule {
662 name: "Pymongo".to_string(),
663 category: TechnologyCategory::Database,
664 confidence: 0.85,
665 dependency_patterns: vec!["pymongo".to_string(), "Pymongo".to_string()],
666 requires: vec![],
667 conflicts_with: vec![],
668 is_primary_indicator: false,
669 alternative_names: vec![],
670 file_indicators: vec![],
671 },
672
673 TechnologyRule {
675 name: "Pytest".to_string(),
676 category: TechnologyCategory::Testing,
677 confidence: 0.90,
678 dependency_patterns: vec!["pytest".to_string(), "Pytest".to_string()],
679 requires: vec![],
680 conflicts_with: vec![],
681 is_primary_indicator: false,
682 alternative_names: vec![],
683 file_indicators: vec![],
684 },
685 TechnologyRule {
686 name: "Unittest".to_string(),
687 category: TechnologyCategory::Testing,
688 confidence: 0.80,
689 dependency_patterns: vec!["unittest".to_string()],
690 requires: vec![],
691 conflicts_with: vec![],
692 is_primary_indicator: false,
693 alternative_names: vec![],
694 file_indicators: vec![],
695 },
696 TechnologyRule {
697 name: "Tox".to_string(),
698 category: TechnologyCategory::Testing,
699 confidence: 0.80,
700 dependency_patterns: vec!["tox".to_string()],
701 requires: vec![],
702 conflicts_with: vec![],
703 is_primary_indicator: false,
704 alternative_names: vec![],
705 file_indicators: vec![],
706 },
707 TechnologyRule {
708 name: "Nose".to_string(),
709 category: TechnologyCategory::Testing,
710 confidence: 0.75,
711 dependency_patterns: vec!["nose".to_string(), "nose2".to_string()],
712 requires: vec![],
713 conflicts_with: vec![],
714 is_primary_indicator: false,
715 alternative_names: vec!["nose2".to_string()],
716 file_indicators: vec![],
717 },
718 TechnologyRule {
719 name: "Behave".to_string(),
720 category: TechnologyCategory::Testing,
721 confidence: 0.85,
722 dependency_patterns: vec!["behave".to_string()],
723 requires: vec![],
724 conflicts_with: vec![],
725 is_primary_indicator: false,
726 alternative_names: vec![],
727 file_indicators: vec![],
728 },
729 TechnologyRule {
730 name: "Hypothesis".to_string(),
731 category: TechnologyCategory::Testing,
732 confidence: 0.85,
733 dependency_patterns: vec!["hypothesis".to_string()],
734 requires: vec![],
735 conflicts_with: vec![],
736 is_primary_indicator: false,
737 alternative_names: vec![],
738 file_indicators: vec![],
739 },
740
741 TechnologyRule {
743 name: "Click".to_string(),
744 category: TechnologyCategory::Library(LibraryType::CLI),
745 confidence: 0.90,
746 dependency_patterns: vec!["click".to_string(), "Click".to_string()],
747 requires: vec![],
748 conflicts_with: vec![],
749 is_primary_indicator: true,
750 alternative_names: vec![],
751 file_indicators: vec![],
752 },
753 TechnologyRule {
754 name: "Argparse".to_string(),
755 category: TechnologyCategory::Library(LibraryType::CLI),
756 confidence: 0.80,
757 dependency_patterns: vec!["argparse".to_string()],
758 requires: vec![],
759 conflicts_with: vec![],
760 is_primary_indicator: true,
761 alternative_names: vec![],
762 file_indicators: vec![],
763 },
764 TechnologyRule {
765 name: "Fire".to_string(),
766 category: TechnologyCategory::Library(LibraryType::CLI),
767 confidence: 0.85,
768 dependency_patterns: vec!["fire".to_string(), "Fire".to_string()],
769 requires: vec![],
770 conflicts_with: vec![],
771 is_primary_indicator: true,
772 alternative_names: vec![],
773 file_indicators: vec![],
774 },
775 TechnologyRule {
776 name: "Typer".to_string(),
777 category: TechnologyCategory::Library(LibraryType::CLI),
778 confidence: 0.85,
779 dependency_patterns: vec!["typer".to_string(), "Typer".to_string()],
780 requires: vec!["Click".to_string()],
781 conflicts_with: vec![],
782 is_primary_indicator: true,
783 alternative_names: vec![],
784 file_indicators: vec![],
785 },
786 TechnologyRule {
787 name: "Docopt".to_string(),
788 category: TechnologyCategory::Library(LibraryType::CLI),
789 confidence: 0.80,
790 dependency_patterns: vec!["docopt".to_string(), "Docopt".to_string()],
791 requires: vec![],
792 conflicts_with: vec![],
793 is_primary_indicator: true,
794 alternative_names: vec![],
795 file_indicators: vec![],
796 },
797 TechnologyRule {
798 name: "Plac".to_string(),
799 category: TechnologyCategory::Library(LibraryType::CLI),
800 confidence: 0.80,
801 dependency_patterns: vec!["plac".to_string(), "Plac".to_string()],
802 requires: vec![],
803 conflicts_with: vec![],
804 is_primary_indicator: true,
805 alternative_names: vec![],
806 file_indicators: vec![],
807 },
808
809 TechnologyRule {
811 name: "Celery".to_string(),
812 category: TechnologyCategory::Library(LibraryType::Utility),
813 confidence: 0.90,
814 dependency_patterns: vec!["celery".to_string(), "Celery".to_string()],
815 requires: vec![],
816 conflicts_with: vec![],
817 is_primary_indicator: false,
818 alternative_names: vec![],
819 file_indicators: vec![],
820 },
821 TechnologyRule {
822 name: "RQ".to_string(),
823 category: TechnologyCategory::Library(LibraryType::Utility),
824 confidence: 0.85,
825 dependency_patterns: vec!["rq".to_string(), "RQ".to_string()],
826 requires: vec![],
827 conflicts_with: vec![],
828 is_primary_indicator: false,
829 alternative_names: vec![],
830 file_indicators: vec![],
831 },
832 TechnologyRule {
833 name: "Dramatiq".to_string(),
834 category: TechnologyCategory::Library(LibraryType::Utility),
835 confidence: 0.85,
836 dependency_patterns: vec!["dramatiq".to_string(), "Dramatiq".to_string()],
837 requires: vec![],
838 conflicts_with: vec![],
839 is_primary_indicator: false,
840 alternative_names: vec![],
841 file_indicators: vec![],
842 },
843 TechnologyRule {
844 name: "Huey".to_string(),
845 category: TechnologyCategory::Library(LibraryType::Utility),
846 confidence: 0.85,
847 dependency_patterns: vec!["huey".to_string(), "Huey".to_string()],
848 requires: vec![],
849 conflicts_with: vec![],
850 is_primary_indicator: false,
851 alternative_names: vec![],
852 file_indicators: vec![],
853 },
854
855 TechnologyRule {
857 name: "Pydantic".to_string(),
858 category: TechnologyCategory::Library(LibraryType::Utility),
859 confidence: 0.90,
860 dependency_patterns: vec!["pydantic".to_string(), "Pydantic".to_string()],
861 requires: vec![],
862 conflicts_with: vec![],
863 is_primary_indicator: false,
864 alternative_names: vec![],
865 file_indicators: vec![],
866 },
867 TechnologyRule {
868 name: "ConfigParser".to_string(),
869 category: TechnologyCategory::Library(LibraryType::Utility),
870 confidence: 0.80,
871 dependency_patterns: vec!["configparser".to_string()],
872 requires: vec![],
873 conflicts_with: vec![],
874 is_primary_indicator: false,
875 alternative_names: vec![],
876 file_indicators: vec![],
877 },
878 TechnologyRule {
879 name: "PyYAML".to_string(),
880 category: TechnologyCategory::Library(LibraryType::Utility),
881 confidence: 0.85,
882 dependency_patterns: vec!["pyyaml".to_string(), "PyYAML".to_string()],
883 requires: vec![],
884 conflicts_with: vec![],
885 is_primary_indicator: false,
886 alternative_names: vec!["yaml".to_string()],
887 file_indicators: vec![],
888 },
889 TechnologyRule {
890 name: "Toml".to_string(),
891 category: TechnologyCategory::Library(LibraryType::Utility),
892 confidence: 0.85,
893 dependency_patterns: vec!["toml".to_string(), "Toml".to_string()],
894 requires: vec![],
895 conflicts_with: vec![],
896 is_primary_indicator: false,
897 alternative_names: vec![],
898 file_indicators: vec![],
899 },
900
901 TechnologyRule {
903 name: "Requests".to_string(),
904 category: TechnologyCategory::Library(LibraryType::HttpClient),
905 confidence: 0.90,
906 dependency_patterns: vec!["requests".to_string(), "Requests".to_string()],
907 requires: vec![],
908 conflicts_with: vec![],
909 is_primary_indicator: false,
910 alternative_names: vec![],
911 file_indicators: vec![],
912 },
913 TechnologyRule {
914 name: "Httpx".to_string(),
915 category: TechnologyCategory::Library(LibraryType::HttpClient),
916 confidence: 0.85,
917 dependency_patterns: vec!["httpx".to_string(), "Httpx".to_string()],
918 requires: vec![],
919 conflicts_with: vec![],
920 is_primary_indicator: false,
921 alternative_names: vec![],
922 file_indicators: vec![],
923 },
924 TechnologyRule {
925 name: "Aiohttp Client".to_string(),
926 category: TechnologyCategory::Library(LibraryType::HttpClient),
927 confidence: 0.85,
928 dependency_patterns: vec!["aiohttp".to_string()],
929 requires: vec![],
930 conflicts_with: vec![],
931 is_primary_indicator: false,
932 alternative_names: vec![],
933 file_indicators: vec![],
934 },
935 TechnologyRule {
936 name: "Urllib3".to_string(),
937 category: TechnologyCategory::Library(LibraryType::HttpClient),
938 confidence: 0.80,
939 dependency_patterns: vec!["urllib3".to_string(), "Urllib3".to_string()],
940 requires: vec![],
941 conflicts_with: vec![],
942 is_primary_indicator: false,
943 alternative_names: vec![],
944 file_indicators: vec![],
945 },
946 ]
947}