contextly 0.1.4__tar.gz → 1.0.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (92) hide show
  1. contextly-1.0.0/PKG-INFO +161 -0
  2. contextly-1.0.0/README.md +139 -0
  3. contextly-1.0.0/contextly/__init__.py +1 -0
  4. contextly-1.0.0/contextly/commands/__init__.py +1 -0
  5. contextly-1.0.0/contextly/commands/analyze.py +49 -0
  6. contextly-1.0.0/contextly/commands/discover.py +51 -0
  7. contextly-1.0.0/contextly/commands/export.py +42 -0
  8. contextly-1.0.0/contextly/commands/init.py +24 -0
  9. contextly-1.0.0/contextly/commands/inspect.py +39 -0
  10. contextly-1.0.0/contextly/commands/learn.py +61 -0
  11. contextly-1.0.0/contextly/commands/memory.py +47 -0
  12. contextly-1.0.0/contextly/commands/pack.py +57 -0
  13. contextly-1.0.0/contextly/core/__init__.py +1 -0
  14. contextly-1.0.0/contextly/core/analyzer/__init__.py +1 -0
  15. contextly-1.0.0/contextly/core/analyzer/engine.py +53 -0
  16. contextly-1.0.0/contextly/core/discovery/__init__.py +1 -0
  17. contextly-1.0.0/contextly/core/discovery/engine.py +22 -0
  18. contextly-1.0.0/contextly/core/exporter/__init__.py +1 -0
  19. contextly-1.0.0/contextly/core/exporter/engine.py +68 -0
  20. contextly-1.0.0/contextly/core/initializer/__init__.py +1 -0
  21. contextly-1.0.0/contextly/core/initializer/engine.py +49 -0
  22. contextly-1.0.0/contextly/core/inspector/__init__.py +1 -0
  23. contextly-1.0.0/contextly/core/inspector/engine.py +28 -0
  24. contextly-1.0.0/contextly/core/learner/__init__.py +1 -0
  25. contextly-1.0.0/contextly/core/learner/engine.py +34 -0
  26. contextly-1.0.0/contextly/core/memory/__init__.py +1 -0
  27. contextly-1.0.0/contextly/core/memory/engine.py +70 -0
  28. contextly-1.0.0/contextly/core/packer/__init__.py +1 -0
  29. contextly-1.0.0/contextly/core/packer/engine.py +84 -0
  30. contextly-1.0.0/contextly/generators/__init__.py +1 -0
  31. contextly-1.0.0/contextly/generators/base.py +63 -0
  32. contextly-1.0.0/contextly/generators/chatgpt.py +63 -0
  33. contextly-1.0.0/contextly/generators/claude.py +69 -0
  34. contextly-1.0.0/contextly/main.py +42 -0
  35. contextly-1.0.0/contextly/scanners/__init__.py +4 -0
  36. contextly-1.0.0/contextly/scanners/base.py +28 -0
  37. contextly-1.0.0/contextly/scanners/dependencies.py +91 -0
  38. contextly-1.0.0/contextly/scanners/framework.py +53 -0
  39. contextly-1.0.0/contextly/scanners/language.py +51 -0
  40. contextly-1.0.0/contextly/scanners/patterns.py +79 -0
  41. contextly-1.0.0/contextly/types/__init__.py +1 -0
  42. contextly-1.0.0/contextly/types/models.py +42 -0
  43. contextly-1.0.0/contextly/utils/__init__.py +1 -0
  44. contextly-1.0.0/contextly/utils/console.py +3 -0
  45. contextly-1.0.0/contextly/utils/exceptions.py +15 -0
  46. contextly-1.0.0/contextly/utils/ignore.py +74 -0
  47. contextly-1.0.0/contextly/utils/validation.py +26 -0
  48. contextly-1.0.0/contextly.egg-info/PKG-INFO +161 -0
  49. contextly-1.0.0/contextly.egg-info/SOURCES.txt +68 -0
  50. contextly-1.0.0/contextly.egg-info/dependency_links.txt +1 -0
  51. contextly-1.0.0/contextly.egg-info/entry_points.txt +2 -0
  52. contextly-1.0.0/contextly.egg-info/requires.txt +12 -0
  53. contextly-1.0.0/contextly.egg-info/top_level.txt +1 -0
  54. contextly-1.0.0/pyproject.toml +37 -0
  55. contextly-1.0.0/setup.cfg +4 -0
  56. contextly-1.0.0/tests/test_analyze.py +111 -0
  57. contextly-1.0.0/tests/test_core.py +77 -0
  58. contextly-1.0.0/tests/test_discover.py +110 -0
  59. contextly-1.0.0/tests/test_export.py +132 -0
  60. contextly-1.0.0/tests/test_generators.py +147 -0
  61. contextly-1.0.0/tests/test_init.py +42 -0
  62. contextly-1.0.0/tests/test_inspect.py +100 -0
  63. contextly-1.0.0/tests/test_learn.py +126 -0
  64. contextly-1.0.0/tests/test_memory.py +103 -0
  65. contextly-1.0.0/tests/test_pack.py +162 -0
  66. contextly-1.0.0/tests/test_scanner_base.py +22 -0
  67. contextly-1.0.0/tests/test_scanner_dependencies.py +163 -0
  68. contextly-1.0.0/tests/test_scanner_framework.py +40 -0
  69. contextly-1.0.0/tests/test_scanner_language.py +64 -0
  70. contextly-1.0.0/tests/test_scanner_patterns.py +50 -0
  71. contextly-0.1.4/.gitignore +0 -42
  72. contextly-0.1.4/LICENSE +0 -21
  73. contextly-0.1.4/PKG-INFO +0 -209
  74. contextly-0.1.4/README.md +0 -150
  75. contextly-0.1.4/pyproject.toml +0 -110
  76. contextly-0.1.4/src/contextly/__init__.py +0 -5
  77. contextly-0.1.4/src/contextly/app.py +0 -111
  78. contextly-0.1.4/src/contextly/cli.py +0 -201
  79. contextly-0.1.4/src/contextly/core/analyzer.py +0 -118
  80. contextly-0.1.4/src/contextly/core/embeddings.py +0 -129
  81. contextly-0.1.4/src/contextly/core/sync.py +0 -66
  82. contextly-0.1.4/src/contextly/llm/__init__.py +0 -13
  83. contextly-0.1.4/src/contextly/llm/base.py +0 -19
  84. contextly-0.1.4/src/contextly/llm/manager.py +0 -126
  85. contextly-0.1.4/src/contextly/llm/models.py +0 -213
  86. contextly-0.1.4/src/contextly/llm/ollama.py +0 -73
  87. contextly-0.1.4/src/contextly/llm/openai.py +0 -41
  88. contextly-0.1.4/src/contextly/parsers/base.py +0 -39
  89. contextly-0.1.4/src/contextly/parsers/config.py +0 -79
  90. contextly-0.1.4/src/contextly/parsers/javascript.py +0 -122
  91. contextly-0.1.4/src/contextly/parsers/python.py +0 -60
  92. contextly-0.1.4/tests/test_core.py +0 -156
@@ -0,0 +1,161 @@
1
+ Metadata-Version: 2.4
2
+ Name: contextly
3
+ Version: 1.0.0
4
+ Summary: The ultimate context-engineering workspace CLI for LLMs.
5
+ Author: Contextly Team
6
+ Project-URL: Homepage, https://github.com/vutikurishanmukha9/Contextly
7
+ Project-URL: Repository, https://github.com/vutikurishanmukha9/Contextly.git
8
+ Project-URL: Changelog, https://github.com/vutikurishanmukha9/Contextly/blob/main/cli/CHANGELOG.md
9
+ Requires-Python: >=3.9
10
+ Description-Content-Type: text/markdown
11
+ Requires-Dist: typer>=0.12.0
12
+ Requires-Dist: rich>=13.7.0
13
+ Requires-Dist: pyyaml>=6.0.1
14
+ Requires-Dist: pydantic>=2.0.0
15
+ Requires-Dist: pathspec>=0.12.0
16
+ Requires-Dist: pyperclip>=1.8.2
17
+ Requires-Dist: tomli>=2.0.1
18
+ Requires-Dist: tiktoken>=0.7.0
19
+ Provides-Extra: dev
20
+ Requires-Dist: pytest>=8.0.0; extra == "dev"
21
+ Requires-Dist: pytest-cov>=4.1.0; extra == "dev"
22
+
23
+ # Context-Ly
24
+
25
+ **Imagine trying to hire a new employee, but instead of giving them an employee handbook, a map of the office, and a list of company rules, you just dump 10,000 loose papers on their desk and say, "figure it out."**
26
+
27
+ That is how most people use AI today. They dump raw files into ChatGPT or Claude and hope for the best. The AI gets confused, makes mistakes, and wastes time.
28
+
29
+ **Context-Ly fixes this.**
30
+
31
+ Context-Ly is a tool that automatically reads your project, figures out your unwritten rules, maps out how everything is connected, and packages it perfectly for AI. When you use Context-Ly, the AI instantly understands your project exactly like a senior engineer would—saving you hours of typing, explaining, and correcting.
32
+
33
+ ---
34
+
35
+ ## Overview
36
+
37
+ Modern AI applications often suffer from "token waste" - providing either too little context (requiring repeated clarifications) or too much irrelevant context (diluting the model's focus). Context-Ly solves this by introducing a structured methodology for building context packs.
38
+
39
+ The application sits between the user's raw thoughts and the AI model, enforcing best practices in prompt engineering through an intuitive interface and a real-time heuristic scoring engine.
40
+
41
+ ## Core Features
42
+
43
+ ### 1. Context Builder
44
+ The Context Builder allows users to break down their prompts into distinct, manageable blocks:
45
+ - **Goal**: The primary objective or task (What does success look like?).
46
+ - **Background**: Necessary prerequisite information for the model.
47
+ - **Constraints**: Strict boundaries, desired tone, and format restrictions.
48
+ - **Examples**: Few-shot examples, gold standards, or anti-examples to guide the model.
49
+ - **Files**: Supporting reference materials such as code snippets or documentation.
50
+
51
+ ### 2. Real-Time Context Scoring
52
+ Every context pack is graded algorithmically before it touches an LLM. The scoring engine evaluates the context across four axes:
53
+ - **Relevance**: Analyzes the word overlap ratio between the Goal block and all supporting blocks to ensure every token serves the primary objective.
54
+ - **Completeness**: Verifies the presence of necessary structural components (e.g., heavily penalizing the absence of a defined Goal or Constraints).
55
+ - **Redundancy**: Utilizes Jaccard similarity to detect and penalize repetitive information across different blocks.
56
+ - **Clarity**: Evaluates sentence complexity (penalizing average sentence lengths over 25 words) and detects the excessive use of ambiguous pronouns ("it", "that", "those").
57
+
58
+ ### 3. Prompt Generator
59
+ The generator compiles the active context blocks into a clean, markdown-structured system prompt. It clearly separates the permanent system context (Audience, Tech Stack, Output Style) from the temporary task context, ensuring the output is perfectly formatted for direct integration into tools like ChatGPT, Claude, or API requests.
60
+
61
+ ## Technical Architecture
62
+
63
+ The application is designed with strict separation of concerns, ensuring that the core business logic remains framework-agnostic.
64
+
65
+ - **Frontend Framework**: React with TanStack Start
66
+ - **Styling**: Tailwind CSS and Radix UI (Shadcn components)
67
+ - **State Management**: Zustand with `localStorage` persistence module
68
+ - **Core Engine**: Pure TypeScript logic (`scoring.ts` and `prompt-generator.ts`) completely decoupled from the DOM and React ecosystem, ensuring straightforward migration to alternative interfaces (such as a CLI) in the future.
69
+
70
+ ## Local Development
71
+
72
+ The web application resides entirely within the `frontend` directory.
73
+
74
+ ### Prerequisites
75
+ - Node.js (v20 or higher recommended)
76
+ - npm
77
+
78
+ ### Installation
79
+
80
+ 1. Clone the repository and navigate to the frontend directory:
81
+ ```bash
82
+ cd frontend
83
+ ```
84
+
85
+ 2. Install the project dependencies:
86
+ ```bash
87
+ npm install
88
+ ```
89
+
90
+ 3. Start the development server:
91
+ ```bash
92
+ npm run dev
93
+ ```
94
+
95
+ 4. Open your browser and navigate to the provided local address (typically `http://localhost:5173`).
96
+
97
+ ## Project Structure
98
+
99
+ ```text
100
+ frontend/
101
+ ├── src/
102
+ │ ├── components/ # Reusable UI components (AppShell, Canvas, Optimizer)
103
+ │ ├── lib/
104
+ │ │ ├── prompt-generator.ts # Logic for formatting the final markdown prompt
105
+ │ │ ├── scoring.ts # Heuristic mathematical scoring engine
106
+ │ │ └── store.ts # Zustand state management and persistence
107
+ │ └── routes/ # TanStack Start routing layer
108
+ ```
109
+
110
+ ## Context-Ly CLI: The Intelligence Layer
111
+
112
+ The true value of Context-Ly lies in its command-line interface, which transforms the tool from a simple prompt formatter into a persistent **Context Memory Layer** for your entire repository.
113
+
114
+ The CLI acts as a static analysis tool that discovers team conventions, evaluates repository complexity, and generates highly-optimized, token-efficient system prompts (`PROJECT_CONTEXT.md`) tailored to your exact stack.
115
+
116
+ ### Setup
117
+
118
+ To begin using the CLI, activate the Python virtual environment located in the `cli` directory:
119
+
120
+ ```bash
121
+ cd cli
122
+ .\venv\Scripts\activate
123
+ ```
124
+
125
+ ### Commands
126
+
127
+ #### 1. `contextly init`
128
+ Initializes Context-as-Code in the current directory. It creates a `.contextly` configuration folder and sets up your environment.
129
+
130
+ #### 2. `contextly analyze`
131
+ The ultimate context generator. This command automatically:
132
+ - Reads your `README.md`.
133
+ - Scans your entire project tree to build an ASCII architecture map.
134
+ - Inspects your dependencies to determine your language and framework (e.g. TypeScript, React).
135
+ - Pulls in both manually saved rules and statically inferred conventions.
136
+ - Merges everything into a massive, LLM-ready system prompt named `PROJECT_CONTEXT.md`.
137
+
138
+ #### 3. `contextly discover`
139
+ Runs the Pattern Discovery Engine. It statically analyzes the codebase using dependency heuristics and file-tree structures to figure out your team's unwritten conventions (e.g. "Uses Zustand", "Uses TailwindCSS", "Service Layer Hint").
140
+
141
+ #### 4. `contextly learn --auto`
142
+ The interactive gatekeeper to the True Memory Engine. It triggers the Discovery Engine and interactively asks if you want to save the discovered conventions:
143
+ ```text
144
+ Save convention: TailwindCSS (Uses TailwindCSS for styling.)? [y/N]
145
+ ```
146
+ Confirmed conventions are saved permanently to `.contextly/memory/rules.yaml`.
147
+
148
+ #### 5. `contextly memory`
149
+ Trust requires visibility. Use this command to inspect all rules and conventions that have been permanently saved to the project's memory.
150
+
151
+ #### 6. `contextly pack <dir>`
152
+ Bundles a specific directory (e.g., `src/components`) into an LLM-ready Context Pack. It reads all files, counts their tokens, and bundles them into `.contextly/packs/` so you can effortlessly copy-paste large portions of your codebase into an LLM without clutter.
153
+
154
+ #### 7. `contextly inspect`
155
+ Performs a deep-dive analysis on your repository complexity, warning you about excessively large files that will act as "Token Hogs" and consume too much context window.
156
+
157
+ ---
158
+
159
+ ## Changelog
160
+
161
+ For all release notes and version history, please see the [CHANGELOG.md](CHANGELOG.md).
@@ -0,0 +1,139 @@
1
+ # Context-Ly
2
+
3
+ **Imagine trying to hire a new employee, but instead of giving them an employee handbook, a map of the office, and a list of company rules, you just dump 10,000 loose papers on their desk and say, "figure it out."**
4
+
5
+ That is how most people use AI today. They dump raw files into ChatGPT or Claude and hope for the best. The AI gets confused, makes mistakes, and wastes time.
6
+
7
+ **Context-Ly fixes this.**
8
+
9
+ Context-Ly is a tool that automatically reads your project, figures out your unwritten rules, maps out how everything is connected, and packages it perfectly for AI. When you use Context-Ly, the AI instantly understands your project exactly like a senior engineer would—saving you hours of typing, explaining, and correcting.
10
+
11
+ ---
12
+
13
+ ## Overview
14
+
15
+ Modern AI applications often suffer from "token waste" - providing either too little context (requiring repeated clarifications) or too much irrelevant context (diluting the model's focus). Context-Ly solves this by introducing a structured methodology for building context packs.
16
+
17
+ The application sits between the user's raw thoughts and the AI model, enforcing best practices in prompt engineering through an intuitive interface and a real-time heuristic scoring engine.
18
+
19
+ ## Core Features
20
+
21
+ ### 1. Context Builder
22
+ The Context Builder allows users to break down their prompts into distinct, manageable blocks:
23
+ - **Goal**: The primary objective or task (What does success look like?).
24
+ - **Background**: Necessary prerequisite information for the model.
25
+ - **Constraints**: Strict boundaries, desired tone, and format restrictions.
26
+ - **Examples**: Few-shot examples, gold standards, or anti-examples to guide the model.
27
+ - **Files**: Supporting reference materials such as code snippets or documentation.
28
+
29
+ ### 2. Real-Time Context Scoring
30
+ Every context pack is graded algorithmically before it touches an LLM. The scoring engine evaluates the context across four axes:
31
+ - **Relevance**: Analyzes the word overlap ratio between the Goal block and all supporting blocks to ensure every token serves the primary objective.
32
+ - **Completeness**: Verifies the presence of necessary structural components (e.g., heavily penalizing the absence of a defined Goal or Constraints).
33
+ - **Redundancy**: Utilizes Jaccard similarity to detect and penalize repetitive information across different blocks.
34
+ - **Clarity**: Evaluates sentence complexity (penalizing average sentence lengths over 25 words) and detects the excessive use of ambiguous pronouns ("it", "that", "those").
35
+
36
+ ### 3. Prompt Generator
37
+ The generator compiles the active context blocks into a clean, markdown-structured system prompt. It clearly separates the permanent system context (Audience, Tech Stack, Output Style) from the temporary task context, ensuring the output is perfectly formatted for direct integration into tools like ChatGPT, Claude, or API requests.
38
+
39
+ ## Technical Architecture
40
+
41
+ The application is designed with strict separation of concerns, ensuring that the core business logic remains framework-agnostic.
42
+
43
+ - **Frontend Framework**: React with TanStack Start
44
+ - **Styling**: Tailwind CSS and Radix UI (Shadcn components)
45
+ - **State Management**: Zustand with `localStorage` persistence module
46
+ - **Core Engine**: Pure TypeScript logic (`scoring.ts` and `prompt-generator.ts`) completely decoupled from the DOM and React ecosystem, ensuring straightforward migration to alternative interfaces (such as a CLI) in the future.
47
+
48
+ ## Local Development
49
+
50
+ The web application resides entirely within the `frontend` directory.
51
+
52
+ ### Prerequisites
53
+ - Node.js (v20 or higher recommended)
54
+ - npm
55
+
56
+ ### Installation
57
+
58
+ 1. Clone the repository and navigate to the frontend directory:
59
+ ```bash
60
+ cd frontend
61
+ ```
62
+
63
+ 2. Install the project dependencies:
64
+ ```bash
65
+ npm install
66
+ ```
67
+
68
+ 3. Start the development server:
69
+ ```bash
70
+ npm run dev
71
+ ```
72
+
73
+ 4. Open your browser and navigate to the provided local address (typically `http://localhost:5173`).
74
+
75
+ ## Project Structure
76
+
77
+ ```text
78
+ frontend/
79
+ ├── src/
80
+ │ ├── components/ # Reusable UI components (AppShell, Canvas, Optimizer)
81
+ │ ├── lib/
82
+ │ │ ├── prompt-generator.ts # Logic for formatting the final markdown prompt
83
+ │ │ ├── scoring.ts # Heuristic mathematical scoring engine
84
+ │ │ └── store.ts # Zustand state management and persistence
85
+ │ └── routes/ # TanStack Start routing layer
86
+ ```
87
+
88
+ ## Context-Ly CLI: The Intelligence Layer
89
+
90
+ The true value of Context-Ly lies in its command-line interface, which transforms the tool from a simple prompt formatter into a persistent **Context Memory Layer** for your entire repository.
91
+
92
+ The CLI acts as a static analysis tool that discovers team conventions, evaluates repository complexity, and generates highly-optimized, token-efficient system prompts (`PROJECT_CONTEXT.md`) tailored to your exact stack.
93
+
94
+ ### Setup
95
+
96
+ To begin using the CLI, activate the Python virtual environment located in the `cli` directory:
97
+
98
+ ```bash
99
+ cd cli
100
+ .\venv\Scripts\activate
101
+ ```
102
+
103
+ ### Commands
104
+
105
+ #### 1. `contextly init`
106
+ Initializes Context-as-Code in the current directory. It creates a `.contextly` configuration folder and sets up your environment.
107
+
108
+ #### 2. `contextly analyze`
109
+ The ultimate context generator. This command automatically:
110
+ - Reads your `README.md`.
111
+ - Scans your entire project tree to build an ASCII architecture map.
112
+ - Inspects your dependencies to determine your language and framework (e.g. TypeScript, React).
113
+ - Pulls in both manually saved rules and statically inferred conventions.
114
+ - Merges everything into a massive, LLM-ready system prompt named `PROJECT_CONTEXT.md`.
115
+
116
+ #### 3. `contextly discover`
117
+ Runs the Pattern Discovery Engine. It statically analyzes the codebase using dependency heuristics and file-tree structures to figure out your team's unwritten conventions (e.g. "Uses Zustand", "Uses TailwindCSS", "Service Layer Hint").
118
+
119
+ #### 4. `contextly learn --auto`
120
+ The interactive gatekeeper to the True Memory Engine. It triggers the Discovery Engine and interactively asks if you want to save the discovered conventions:
121
+ ```text
122
+ Save convention: TailwindCSS (Uses TailwindCSS for styling.)? [y/N]
123
+ ```
124
+ Confirmed conventions are saved permanently to `.contextly/memory/rules.yaml`.
125
+
126
+ #### 5. `contextly memory`
127
+ Trust requires visibility. Use this command to inspect all rules and conventions that have been permanently saved to the project's memory.
128
+
129
+ #### 6. `contextly pack <dir>`
130
+ Bundles a specific directory (e.g., `src/components`) into an LLM-ready Context Pack. It reads all files, counts their tokens, and bundles them into `.contextly/packs/` so you can effortlessly copy-paste large portions of your codebase into an LLM without clutter.
131
+
132
+ #### 7. `contextly inspect`
133
+ Performs a deep-dive analysis on your repository complexity, warning you about excessively large files that will act as "Token Hogs" and consume too much context window.
134
+
135
+ ---
136
+
137
+ ## Changelog
138
+
139
+ For all release notes and version history, please see the [CHANGELOG.md](CHANGELOG.md).
@@ -0,0 +1 @@
1
+ # Contextly CLI Package
@@ -0,0 +1 @@
1
+ # Init commands
@@ -0,0 +1,49 @@
1
+ from pathlib import Path
2
+ from rich.table import Table
3
+ import typer
4
+
5
+ from ..utils.console import console
6
+ from ..scanners.base import ScannerError
7
+ from ..utils.exceptions import ContextlyError
8
+ from ..core.analyzer.engine import AnalyzerEngine
9
+
10
+ def analyze_cmd(model: str = typer.Option("chatgpt", "--model", "-m", help="Target LLM format ('chatgpt' or 'claude')")):
11
+ """Automatically analyze and map the repository"""
12
+ root_dir = Path.cwd()
13
+ engine = AnalyzerEngine(root_dir)
14
+
15
+ with console.status("[bold blue]Scanning repository intelligence (Max Level)...", spinner="dots"):
16
+ try:
17
+ intelligence = engine.analyze(model)
18
+ except ScannerError as e:
19
+ console.print(f"\n[bold red]Scanner Error:[/bold red] {e}")
20
+ raise typer.Exit(1)
21
+ except ContextlyError as e:
22
+ console.print(f"\n[bold red]Context-Ly Error:[/bold red] {e}")
23
+ raise typer.Exit(1)
24
+ except Exception as e:
25
+ console.print(f"\n[bold red]Unexpected Error:[/bold red] {e}")
26
+ raise typer.Exit(1)
27
+
28
+ console.print("\n[bold green][OK][/bold green] Repository scan complete!\n")
29
+
30
+ table = Table(title="Repository Intelligence (Max Level)", show_header=False, box=None)
31
+ table.add_column("Category", style="cyan", justify="right")
32
+ table.add_column("Value", style="magenta")
33
+
34
+ table.add_row("Primary Language", f"[bold]{intelligence.language.primary}[/bold]")
35
+ table.add_row("Frontend Framework", intelligence.frameworks.frontend)
36
+ table.add_row("Backend/Tooling", intelligence.frameworks.backend)
37
+
38
+ npm_count = len(intelligence.dependencies.npm)
39
+ py_count = len(intelligence.dependencies.python)
40
+
41
+ if npm_count > 0:
42
+ table.add_row("NPM Dependencies", str(npm_count))
43
+ if py_count > 0:
44
+ table.add_row("Python Dependencies", str(py_count))
45
+
46
+ console.print(table)
47
+ console.print()
48
+ console.print(f"[dim]Generated advanced PROJECT_CONTEXT.md ({model.lower()} format) in current directory.[/dim]")
49
+
@@ -0,0 +1,51 @@
1
+ from pathlib import Path
2
+ import typer
3
+
4
+ from ..utils.console import console
5
+ from ..core.discovery.engine import DiscoveryEngine
6
+ from ..scanners.base import ScannerError
7
+ from ..utils.exceptions import ValidationError, ContextlyError
8
+ from ..utils.validation import require_contextly_initialized
9
+
10
+ def discover_cmd():
11
+ """Statically analyze the repository to discover architectural patterns and conventions"""
12
+ root_dir = Path.cwd()
13
+
14
+ try:
15
+ require_contextly_initialized(root_dir)
16
+ except ValidationError as e:
17
+ console.print(f"[bold red]Error:[/bold red] {e}")
18
+ raise typer.Exit(code=1)
19
+
20
+ engine = DiscoveryEngine(root_dir)
21
+
22
+ with console.status("[bold blue]Running Pattern Discovery Engine...", spinner="dots"):
23
+ try:
24
+ patterns_result = engine.discover()
25
+ except ScannerError as e:
26
+ console.print(f"\n[bold red]Scanner Error:[/bold red] {e}")
27
+ raise typer.Exit(code=1)
28
+ except ContextlyError as e:
29
+ console.print(f"\n[bold red]Context-Ly Error:[/bold red] {e}")
30
+ raise typer.Exit(code=1)
31
+
32
+ console.print("[bold green][OK][/bold green] Pattern Discovery Complete:\n")
33
+
34
+ if not patterns_result.patterns:
35
+ console.print("[yellow]No recognizable architectural patterns or conventions discovered.[/yellow]")
36
+ return
37
+
38
+ # Group by category
39
+ categories = {}
40
+ for p in patterns_result.patterns:
41
+ if p.category not in categories:
42
+ categories[p.category] = []
43
+ categories[p.category].append(p)
44
+
45
+ for category, patterns in sorted(categories.items()):
46
+ console.print(f"[bold cyan]{category}:[/bold cyan]")
47
+ # Sort by confidence descending (High -> Medium -> Low)
48
+ sorted_patterns = sorted(patterns, key=lambda p: {"high": 0, "medium": 1, "low": 2}.get(p.confidence.lower(), 3))
49
+ for p in sorted_patterns:
50
+ console.print(f" [green]\\[OK][/green] [bold]{p.name}[/bold] ({p.description})")
51
+ console.print()
@@ -0,0 +1,42 @@
1
+ import typer
2
+ from pathlib import Path
3
+ from ..utils.console import console
4
+ from ..core.exporter.engine import ExporterEngine
5
+ from ..utils.validation import require_contextly_initialized
6
+ from ..utils.exceptions import ValidationError, ContextlyError
7
+
8
+ def export_cmd(
9
+ pack_name: str = typer.Argument(..., help="The name of the context pack to export (e.g., 'frontend')")
10
+ ):
11
+ """Fuses intelligence and context packs, copying the result to your clipboard."""
12
+ root_dir = Path.cwd()
13
+
14
+ try:
15
+ require_contextly_initialized(root_dir)
16
+ except ValidationError as e:
17
+ console.print(f"[bold red]Error:[/bold red] {e}")
18
+ raise typer.Exit(code=1)
19
+
20
+ engine = ExporterEngine(root_dir)
21
+
22
+ try:
23
+ export_path, clipboard_success = engine.export(pack_name)
24
+ except ContextlyError as e:
25
+ console.print(f"[bold red]Error:[/bold red] {e}")
26
+ raise typer.Exit(code=1)
27
+
28
+ if clipboard_success:
29
+ clipboard_status = "[green]Successfully copied to clipboard![/green]"
30
+ else:
31
+ clipboard_status = "[yellow]Could not copy to clipboard. The export file was saved successfully.[/yellow]"
32
+
33
+ console.print(f"\n[bold green][OK][/bold green] Export Generation Complete!")
34
+ console.print(f" - [cyan]Intelligence:[/cyan] PROJECT_CONTEXT.md")
35
+ console.print(f" - [cyan]Context Pack:[/cyan] {pack_name}")
36
+ console.print(f" - [cyan]Local Export:[/cyan] {export_path.relative_to(root_dir)}")
37
+ console.print(f"\n{clipboard_status}")
38
+ if clipboard_success:
39
+ console.print("\nYou can now paste the contents directly into Claude or ChatGPT.")
40
+ else:
41
+ console.print("\nOpen the local export file to copy the contents manually.")
42
+
@@ -0,0 +1,24 @@
1
+ import typer
2
+ from pathlib import Path
3
+ from ..utils.console import console
4
+ from ..core.initializer.engine import InitEngine
5
+ from ..utils.exceptions import ContextlyError
6
+
7
+ def init_cmd():
8
+ """Initialize Context-as-Code in the current directory"""
9
+ root_dir = Path.cwd()
10
+ engine = InitEngine(root_dir)
11
+
12
+ try:
13
+ success = engine.initialize()
14
+ if not success:
15
+ console.print("[yellow]Contextly is already initialized in this repository.[/yellow]")
16
+ return
17
+
18
+ console.print("[bold green][OK][/bold green] Contextly initialized successfully!")
19
+ console.print(f"Created configuration at [cyan].contextly/config.yaml[/cyan]")
20
+ console.print("Edit this file to define your Context-as-Code rules.")
21
+
22
+ except ContextlyError as e:
23
+ console.print(f"[bold red]Error initializing Contextly:[/bold red] {str(e)}")
24
+ raise typer.Exit(code=1)
@@ -0,0 +1,39 @@
1
+ from pathlib import Path
2
+ from rich.table import Table
3
+ from ..utils.console import console
4
+ from ..utils.exceptions import ValidationError
5
+ from ..utils.validation import require_directory_exists
6
+ from ..core.inspector.engine import InspectorEngine
7
+ import typer
8
+
9
+ def inspect_cmd():
10
+ """Deep dive into repository complexity and structure"""
11
+ try:
12
+ root_dir = require_directory_exists(str(Path.cwd()))
13
+ except ValidationError as e:
14
+ console.print(f"[bold red]Error:[/bold red] {e}")
15
+ raise typer.Exit(code=1)
16
+
17
+ engine = InspectorEngine(root_dir)
18
+
19
+ with console.status("[bold blue]Inspecting repository file tree...", spinner="bouncingBar"):
20
+ file_sizes = engine.inspect()
21
+
22
+ console.print("\n[bold green][OK][/bold green] Inspection complete!\n")
23
+
24
+ table = Table(title="Top 5 Largest Files (Potential Token Hogs)")
25
+ table.add_column("Size (KB)", justify="right", style="cyan")
26
+ table.add_column("File Path", style="magenta")
27
+
28
+ for size, path in file_sizes[:5]:
29
+ rel_path = path.relative_to(root_dir)
30
+ kb_size = size / 1024
31
+
32
+ # Highlight massive files that shouldn't go to LLMs
33
+ style = "red" if kb_size > 100 else "yellow" if kb_size > 50 else "white"
34
+
35
+ table.add_row(f"{kb_size:.1f}", f"[{style}]{rel_path}[/{style}]")
36
+
37
+ console.print(table)
38
+ console.print("\n[dim]Tip: Files over 50KB (yellow) or 100KB (red) consume massive LLM context windows. Keep them out of your Context Packs if possible.[/dim]\n")
39
+
@@ -0,0 +1,61 @@
1
+ import typer
2
+ from pathlib import Path
3
+ from rich.prompt import Confirm
4
+ from ..utils.console import console
5
+ from ..core.learner.engine import LearnEngine
6
+ from ..scanners.base import ScannerError
7
+ from ..utils.exceptions import ValidationError, ContextlyError
8
+ from ..utils.validation import require_contextly_initialized
9
+
10
+ def learn_cmd(
11
+ auto: bool = typer.Option(False, "--auto", help="Automatically discover and interactively learn conventions.")
12
+ ):
13
+ """Teach Context-Ly new conventions, or use --auto to discover them."""
14
+ root_dir = Path.cwd()
15
+ try:
16
+ require_contextly_initialized(root_dir)
17
+ except ValidationError as e:
18
+ console.print(f"[bold red]Error:[/bold red] {e}")
19
+ raise typer.Exit(code=1)
20
+
21
+ engine = LearnEngine(root_dir)
22
+
23
+ if not auto:
24
+ console.print("[yellow]Manual learning is currently disabled in favor of automated discovery.[/yellow]")
25
+ console.print("Please use [bold cyan]contextly learn --auto[/bold cyan]")
26
+ return
27
+
28
+ with console.status("[bold blue]Running Pattern Discovery Engine...", spinner="dots"):
29
+ try:
30
+ sorted_patterns = engine.discover_conventions()
31
+ except ScannerError as e:
32
+ console.print(f"\n[bold red]Scanner Error:[/bold red] {e}")
33
+ raise typer.Exit(code=1)
34
+ except ContextlyError as e:
35
+ console.print(f"\n[bold red]Context-Ly Error:[/bold red] {e}")
36
+ raise typer.Exit(code=1)
37
+
38
+ if not sorted_patterns:
39
+ console.print("[yellow]No new recognizable conventions discovered to learn.[/yellow]")
40
+ return
41
+
42
+ console.print("\n[bold green]Discovered Conventions:[/bold green]\n")
43
+
44
+ saved_count = 0
45
+ for p in sorted_patterns:
46
+ if Confirm.ask(f"Save convention: [cyan]{p.name}[/cyan] ({p.description})?"):
47
+ added = engine.save_convention(p)
48
+ if added:
49
+ saved_count += 1
50
+ console.print(f" [green]\\[OK][/green] Saved to memory.")
51
+ else:
52
+ console.print(f" [dim]Skipped (Already in memory).[/dim]")
53
+ else:
54
+ console.print(f" [dim]Skipped.[/dim]")
55
+
56
+ if saved_count > 0:
57
+ console.print(f"\n[bold green][OK][/bold green] Successfully saved {saved_count} rules to persistent memory!")
58
+ console.print("Run [bold cyan]contextly memory[/bold cyan] to view them.")
59
+ else:
60
+ console.print("\n[dim]No new rules were saved.[/dim]")
61
+
@@ -0,0 +1,47 @@
1
+ from pathlib import Path
2
+ from rich.table import Table
3
+ from ..utils.console import console
4
+ from ..core.memory import MemoryEngine
5
+ from ..utils.exceptions import ValidationError
6
+ from ..utils.validation import require_contextly_initialized
7
+ import typer
8
+
9
+ def memory_cmd():
10
+ """Inspect the persistently stored team memory and conventions."""
11
+ root_dir = Path.cwd()
12
+
13
+ try:
14
+ require_contextly_initialized(root_dir)
15
+ except ValidationError as e:
16
+ console.print(f"[bold red]Error:[/bold red] {e}")
17
+ raise typer.Exit(code=1)
18
+
19
+ engine = MemoryEngine(root_dir)
20
+
21
+ memory = engine.load_memory()
22
+
23
+ if not memory.rules:
24
+ console.print("[yellow]Context-Ly memory is currently empty.[/yellow]")
25
+ console.print("Run [bold cyan]contextly learn --auto[/bold cyan] to discover and save team conventions.")
26
+ return
27
+
28
+ console.print(f"[bold green]Stored Memory[/bold green] (Found {len(memory.rules)} rules)\n")
29
+
30
+ # Group by category
31
+ categories = {}
32
+ for rule in memory.rules:
33
+ if rule.category not in categories:
34
+ categories[rule.category] = []
35
+ categories[rule.category].append(rule)
36
+
37
+ for category, rules in sorted(categories.items()):
38
+ console.print(f"[bold cyan]{category}[/bold cyan]")
39
+ # Sort by confidence descending (High -> Medium -> Low)
40
+ sorted_rules = sorted(rules, key=lambda r: {"high": 0, "medium": 1, "low": 2}.get(r.confidence.lower(), 3))
41
+ for rule in sorted_rules:
42
+ source_tag = f"[dim]({rule.source})[/dim]"
43
+ conf_color = "green" if rule.confidence.lower() == "high" else "yellow"
44
+ conf_tag = f"[{conf_color}][{rule.confidence}][/{conf_color}]"
45
+
46
+ console.print(f" - [dim]\\[{rule.id}][/dim] {rule.rule} {conf_tag} {source_tag}")
47
+ console.print()