logmind 0.1.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.
- logmind-0.1.0/LICENSE +21 -0
- logmind-0.1.0/MANIFEST.in +11 -0
- logmind-0.1.0/PKG-INFO +219 -0
- logmind-0.1.0/README.md +178 -0
- logmind-0.1.0/pyproject.toml +94 -0
- logmind-0.1.0/setup.cfg +4 -0
- logmind-0.1.0/src/logmind/__init__.py +8 -0
- logmind-0.1.0/src/logmind/actions/__init__.py +5 -0
- logmind-0.1.0/src/logmind/actions/aggregate.py +108 -0
- logmind-0.1.0/src/logmind/actions/link_check.py +193 -0
- logmind-0.1.0/src/logmind/cli.py +1224 -0
- logmind-0.1.0/src/logmind/core/__init__.py +1 -0
- logmind-0.1.0/src/logmind/core/aggregator.py +78 -0
- logmind-0.1.0/src/logmind/core/analytics.py +97 -0
- logmind-0.1.0/src/logmind/core/config.py +233 -0
- logmind-0.1.0/src/logmind/core/decision_templates.py +86 -0
- logmind-0.1.0/src/logmind/core/git_handler.py +277 -0
- logmind-0.1.0/src/logmind/core/gitignore.py +60 -0
- logmind-0.1.0/src/logmind/core/inserter.py +623 -0
- logmind-0.1.0/src/logmind/core/logger.py +323 -0
- logmind-0.1.0/src/logmind/core/parser.py +22 -0
- logmind-0.1.0/src/logmind/core/search.py +192 -0
- logmind-0.1.0/src/logmind/core/skill_install.py +68 -0
- logmind-0.1.0/src/logmind/core/tree_gen.py +208 -0
- logmind-0.1.0/src/logmind/decorators.py +181 -0
- logmind-0.1.0/src/logmind/integrations/__init__.py +5 -0
- logmind-0.1.0/src/logmind/integrations/base.py +43 -0
- logmind-0.1.0/src/logmind/integrations/langchain.py +79 -0
- logmind-0.1.0/src/logmind/templates/AGENTS.md.template +81 -0
- logmind-0.1.0/src/logmind/templates/CLAUDE.md.template +53 -0
- logmind-0.1.0/src/logmind/templates/agent-stub.md +3 -0
- logmind-0.1.0/src/logmind/templates/config.yml.template +61 -0
- logmind-0.1.0/src/logmind/templates/decisions-archive.md.template +7 -0
- logmind-0.1.0/src/logmind/templates/decisions.md.template +5 -0
- logmind-0.1.0/src/logmind/templates/file-structure.md.template +9 -0
- logmind-0.1.0/src/logmind/templates/github/check-doc-links.yml.template +31 -0
- logmind-0.1.0/src/logmind/templates/github/logmind-aggregate.yml.template +49 -0
- logmind-0.1.0/src/logmind/templates/logmind-section.md +68 -0
- logmind-0.1.0/src/logmind.egg-info/PKG-INFO +219 -0
- logmind-0.1.0/src/logmind.egg-info/SOURCES.txt +62 -0
- logmind-0.1.0/src/logmind.egg-info/dependency_links.txt +1 -0
- logmind-0.1.0/src/logmind.egg-info/entry_points.txt +2 -0
- logmind-0.1.0/src/logmind.egg-info/requires.txt +13 -0
- logmind-0.1.0/src/logmind.egg-info/top_level.txt +1 -0
- logmind-0.1.0/tests/test_action_aggregate.py +126 -0
- logmind-0.1.0/tests/test_agents_consolidation.py +235 -0
- logmind-0.1.0/tests/test_aggregator.py +315 -0
- logmind-0.1.0/tests/test_analytics.py +363 -0
- logmind-0.1.0/tests/test_branch_aware_logging.py +257 -0
- logmind-0.1.0/tests/test_cli.py +1029 -0
- logmind-0.1.0/tests/test_config.py +232 -0
- logmind-0.1.0/tests/test_decision_templates.py +282 -0
- logmind-0.1.0/tests/test_decorators.py +392 -0
- logmind-0.1.0/tests/test_file_structure_updates.py +155 -0
- logmind-0.1.0/tests/test_git_handler.py +140 -0
- logmind-0.1.0/tests/test_gitignore_management.py +86 -0
- logmind-0.1.0/tests/test_inserter.py +723 -0
- logmind-0.1.0/tests/test_integrations.py +293 -0
- logmind-0.1.0/tests/test_link_check.py +150 -0
- logmind-0.1.0/tests/test_logger.py +253 -0
- logmind-0.1.0/tests/test_parser.py +252 -0
- logmind-0.1.0/tests/test_search.py +409 -0
- logmind-0.1.0/tests/test_skill_install.py +100 -0
- logmind-0.1.0/tests/test_tree_gen.py +101 -0
logmind-0.1.0/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 logmind contributors
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
include README.md
|
|
2
|
+
include LICENSE
|
|
3
|
+
include pyproject.toml
|
|
4
|
+
|
|
5
|
+
# Include all template files
|
|
6
|
+
recursive-include src/logmind/templates *.template *.md
|
|
7
|
+
|
|
8
|
+
# Exclude test files and cache
|
|
9
|
+
global-exclude __pycache__
|
|
10
|
+
global-exclude *.py[co]
|
|
11
|
+
global-exclude .DS_Store
|
logmind-0.1.0/PKG-INFO
ADDED
|
@@ -0,0 +1,219 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: logmind
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Decision logging for AI-assisted development - automatic tracking, git integration, and context for AI agents
|
|
5
|
+
Author: logmind contributors
|
|
6
|
+
License: MIT
|
|
7
|
+
Project-URL: Homepage, https://github.com/thrillmot/logmind
|
|
8
|
+
Project-URL: Documentation, https://github.com/thrillmot/logmind#readme
|
|
9
|
+
Project-URL: Repository, https://github.com/thrillmot/logmind
|
|
10
|
+
Project-URL: Bug Tracker, https://github.com/thrillmot/logmind/issues
|
|
11
|
+
Project-URL: Changelog, https://github.com/thrillmot/logmind/blob/main/CHANGELOG.md
|
|
12
|
+
Keywords: ai,decision-logging,documentation,development,llm,ai-agents,decision-tracking,git-integration,claude,gpt,copilot
|
|
13
|
+
Classifier: Development Status :: 4 - Beta
|
|
14
|
+
Classifier: Intended Audience :: Developers
|
|
15
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
16
|
+
Classifier: Programming Language :: Python :: 3
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.8
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.9
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
23
|
+
Classifier: Topic :: Software Development :: Documentation
|
|
24
|
+
Classifier: Topic :: Software Development :: Version Control :: Git
|
|
25
|
+
Classifier: Topic :: Text Processing :: Markup :: Markdown
|
|
26
|
+
Requires-Python: >=3.8
|
|
27
|
+
Description-Content-Type: text/markdown
|
|
28
|
+
License-File: LICENSE
|
|
29
|
+
Requires-Dist: click>=8.0.0
|
|
30
|
+
Requires-Dist: pyyaml>=6.0.0
|
|
31
|
+
Provides-Extra: dev
|
|
32
|
+
Requires-Dist: pytest>=7.0.0; extra == "dev"
|
|
33
|
+
Requires-Dist: black>=23.0.0; extra == "dev"
|
|
34
|
+
Requires-Dist: mypy>=1.0.0; extra == "dev"
|
|
35
|
+
Requires-Dist: ruff>=0.5.0; extra == "dev"
|
|
36
|
+
Requires-Dist: pre-commit>=3.5.0; extra == "dev"
|
|
37
|
+
Requires-Dist: build>=1.0.0; extra == "dev"
|
|
38
|
+
Provides-Extra: langchain
|
|
39
|
+
Requires-Dist: langchain-core>=0.1.0; extra == "langchain"
|
|
40
|
+
Dynamic: license-file
|
|
41
|
+
|
|
42
|
+
# logmind
|
|
43
|
+
|
|
44
|
+
[](https://pypi.org/project/logmind/)
|
|
45
|
+
[](https://pypi.org/project/logmind/)
|
|
46
|
+
[](https://github.com/thrillmot/logmind/actions/workflows/test.yml)
|
|
47
|
+
[](LICENSE)
|
|
48
|
+
|
|
49
|
+
AI decision logging for development projects — branch-aware by default.
|
|
50
|
+
|
|
51
|
+
## Why logmind
|
|
52
|
+
|
|
53
|
+
Codebases lose the *why* behind their code faster than the *what*. logmind
|
|
54
|
+
captures architectural and implementation decisions as you make them,
|
|
55
|
+
attaches them to the relevant git branch, and surfaces them to the next
|
|
56
|
+
human or AI that works in the repo. One CLI command per decision; the
|
|
57
|
+
package handles the docs, the branch routing, and the merge-time
|
|
58
|
+
aggregation.
|
|
59
|
+
|
|
60
|
+
**Key concept:** Install once, init anywhere, log everything. Feature
|
|
61
|
+
branches get their own decision file; on PR merge a GitHub Action appends
|
|
62
|
+
a one-line summary to `docs/decisions.md` linking the PR + the branch
|
|
63
|
+
detail. AGENTS.md is the canonical agent-instruction file; per-tool files
|
|
64
|
+
(CLAUDE.md, .cursorrules, ...) are 2-line stubs pointing to it.
|
|
65
|
+
|
|
66
|
+
## Installation
|
|
67
|
+
|
|
68
|
+
```bash
|
|
69
|
+
# Using pipx (recommended)
|
|
70
|
+
pipx install logmind
|
|
71
|
+
|
|
72
|
+
# Using Homebrew (macOS/Linux)
|
|
73
|
+
brew tap thrillmot/logmind
|
|
74
|
+
brew install logmind
|
|
75
|
+
|
|
76
|
+
# Using pip
|
|
77
|
+
pip install logmind
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
## Quick Start
|
|
81
|
+
|
|
82
|
+
```bash
|
|
83
|
+
# If installed via pipx/brew, it's already available globally
|
|
84
|
+
|
|
85
|
+
# Initialize in your project
|
|
86
|
+
cd your-project
|
|
87
|
+
logmind init
|
|
88
|
+
|
|
89
|
+
# Log decisions - Python API
|
|
90
|
+
from logmind import log
|
|
91
|
+
log("Chose FastAPI over Flask",
|
|
92
|
+
reasoning="Need async/await for WebSocket handling")
|
|
93
|
+
|
|
94
|
+
# Or use CLI
|
|
95
|
+
logmind log "Use PostgreSQL for database" \
|
|
96
|
+
-r "Need ACID compliance" \
|
|
97
|
+
-a "MongoDB" -a "SQLite"
|
|
98
|
+
|
|
99
|
+
# View and search decisions
|
|
100
|
+
logmind show
|
|
101
|
+
logmind search "postgres"
|
|
102
|
+
|
|
103
|
+
# Log with a built-in template (pre-fills reasoning, alternatives, implications)
|
|
104
|
+
logmind log --template database "Use PostgreSQL"
|
|
105
|
+
logmind templates # list all available templates
|
|
106
|
+
|
|
107
|
+
# Analytics and stats
|
|
108
|
+
logmind stats
|
|
109
|
+
logmind stats --months 6
|
|
110
|
+
|
|
111
|
+
# Aggregate decisions across multiple projects
|
|
112
|
+
logmind aggregate ~/projects/api ~/projects/frontend
|
|
113
|
+
logmind aggregate --summary ~/work/*/
|
|
114
|
+
|
|
115
|
+
# Enforce decision logging with a pre-commit hook
|
|
116
|
+
logmind install-hook # installs .git/hooks/pre-commit
|
|
117
|
+
logmind check-decisions # run manually or in CI
|
|
118
|
+
|
|
119
|
+
# Manage AI agents
|
|
120
|
+
logmind agents list
|
|
121
|
+
logmind agents add windsurf
|
|
122
|
+
|
|
123
|
+
# View and modify configuration
|
|
124
|
+
logmind config list
|
|
125
|
+
logmind config get git.auto_push
|
|
126
|
+
logmind config set git.auto_push false
|
|
127
|
+
|
|
128
|
+
# Upgrade logmind
|
|
129
|
+
logmind update
|
|
130
|
+
|
|
131
|
+
# Auto-log with decorators
|
|
132
|
+
from logmind import log_decision, log_choice
|
|
133
|
+
|
|
134
|
+
@log_decision(
|
|
135
|
+
decision="Authenticate user with {method}",
|
|
136
|
+
reasoning="Security checkpoint"
|
|
137
|
+
)
|
|
138
|
+
def authenticate(method="oauth"):
|
|
139
|
+
# Your auth code
|
|
140
|
+
return True
|
|
141
|
+
|
|
142
|
+
@log_choice(
|
|
143
|
+
choices={
|
|
144
|
+
"redis": "Use Redis for caching",
|
|
145
|
+
"memory": "Use in-memory caching",
|
|
146
|
+
}
|
|
147
|
+
)
|
|
148
|
+
def select_cache():
|
|
149
|
+
return "redis" if is_production() else "memory"
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
## Contributing / Development Setup
|
|
153
|
+
|
|
154
|
+
Working on logmind itself? Set it up like any CLI tool:
|
|
155
|
+
|
|
156
|
+
```bash
|
|
157
|
+
# Clone the repo
|
|
158
|
+
git clone https://github.com/thrillmot/logmind.git
|
|
159
|
+
cd logmind
|
|
160
|
+
|
|
161
|
+
# Install globally in editable mode (like npm, git, docker)
|
|
162
|
+
pipx install -e .
|
|
163
|
+
|
|
164
|
+
# Now just use it!
|
|
165
|
+
logmind log "Add new feature" -r "Reasoning here"
|
|
166
|
+
logmind show
|
|
167
|
+
logmind search "keyword"
|
|
168
|
+
|
|
169
|
+
# Run tests
|
|
170
|
+
python3 -m venv venv
|
|
171
|
+
source venv/bin/activate
|
|
172
|
+
pip install -e ".[dev]"
|
|
173
|
+
pytest
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
**Why pipx?** logmind is a CLI tool, not a library. It should be globally available like `git` or `npm`.
|
|
177
|
+
|
|
178
|
+
## Framework Integrations
|
|
179
|
+
|
|
180
|
+
```python
|
|
181
|
+
# LangChain — auto-log agent decisions (pip install logmind[langchain])
|
|
182
|
+
from logmind.integrations import LangChainLogger
|
|
183
|
+
|
|
184
|
+
chain = LLMChain(llm=llm, callbacks=[LangChainLogger()])
|
|
185
|
+
|
|
186
|
+
# Custom framework — subclass BaseIntegration
|
|
187
|
+
from logmind.integrations.base import BaseIntegration
|
|
188
|
+
|
|
189
|
+
class MyLogger(BaseIntegration):
|
|
190
|
+
def on_decision(self, output):
|
|
191
|
+
self.log(f"Chose: {output}", reasoning="My framework decided")
|
|
192
|
+
```
|
|
193
|
+
|
|
194
|
+
See [docs/custom-integrations.md](docs/custom-integrations.md) for patterns, examples, and publishing guide.
|
|
195
|
+
|
|
196
|
+
## Documentation
|
|
197
|
+
|
|
198
|
+
- **[Plan & Architecture](docs/plan.md)** - Vision, approach, and technical details
|
|
199
|
+
- **[AI Agent Files](docs/ai-agent-files.md)** - How logmind integrates with AI instruction files
|
|
200
|
+
- **[Custom Integrations](docs/custom-integrations.md)** - Build integrations for any AI framework
|
|
201
|
+
- **[First Decision Example](docs/first-decision-example.md)** - What the initial decision looks like
|
|
202
|
+
- **Development Status** - All phases complete ✅
|
|
203
|
+
|
|
204
|
+
## How It Works
|
|
205
|
+
|
|
206
|
+
1. **Install** logmind as a package
|
|
207
|
+
2. **Init** creates `docs/` folder and inserts instructions into `CLAUDE.md` (preserving existing content)
|
|
208
|
+
3. **Log** a decision - appends, archives old ones (keeps 20 recent), regenerates tree, commits, and pushes
|
|
209
|
+
4. **Context** AI agents read the 20 most recent decisions and current file structure
|
|
210
|
+
|
|
211
|
+
## Why logmind?
|
|
212
|
+
|
|
213
|
+
- **Simple:** Two markdown files (recent + archive), no database
|
|
214
|
+
- **Focused:** Only 20 most recent decisions for relevant AI context
|
|
215
|
+
- **Git-native:** Every decision is a commit, git history is your audit trail
|
|
216
|
+
- **AI-friendly:** Recent decisions + file structure = complete context
|
|
217
|
+
- **Automatic:** Commits and pushes on every log
|
|
218
|
+
|
|
219
|
+
See [docs/plan.md](docs/plan.md) for complete architecture and roadmap.
|
logmind-0.1.0/README.md
ADDED
|
@@ -0,0 +1,178 @@
|
|
|
1
|
+
# logmind
|
|
2
|
+
|
|
3
|
+
[](https://pypi.org/project/logmind/)
|
|
4
|
+
[](https://pypi.org/project/logmind/)
|
|
5
|
+
[](https://github.com/thrillmot/logmind/actions/workflows/test.yml)
|
|
6
|
+
[](LICENSE)
|
|
7
|
+
|
|
8
|
+
AI decision logging for development projects — branch-aware by default.
|
|
9
|
+
|
|
10
|
+
## Why logmind
|
|
11
|
+
|
|
12
|
+
Codebases lose the *why* behind their code faster than the *what*. logmind
|
|
13
|
+
captures architectural and implementation decisions as you make them,
|
|
14
|
+
attaches them to the relevant git branch, and surfaces them to the next
|
|
15
|
+
human or AI that works in the repo. One CLI command per decision; the
|
|
16
|
+
package handles the docs, the branch routing, and the merge-time
|
|
17
|
+
aggregation.
|
|
18
|
+
|
|
19
|
+
**Key concept:** Install once, init anywhere, log everything. Feature
|
|
20
|
+
branches get their own decision file; on PR merge a GitHub Action appends
|
|
21
|
+
a one-line summary to `docs/decisions.md` linking the PR + the branch
|
|
22
|
+
detail. AGENTS.md is the canonical agent-instruction file; per-tool files
|
|
23
|
+
(CLAUDE.md, .cursorrules, ...) are 2-line stubs pointing to it.
|
|
24
|
+
|
|
25
|
+
## Installation
|
|
26
|
+
|
|
27
|
+
```bash
|
|
28
|
+
# Using pipx (recommended)
|
|
29
|
+
pipx install logmind
|
|
30
|
+
|
|
31
|
+
# Using Homebrew (macOS/Linux)
|
|
32
|
+
brew tap thrillmot/logmind
|
|
33
|
+
brew install logmind
|
|
34
|
+
|
|
35
|
+
# Using pip
|
|
36
|
+
pip install logmind
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
## Quick Start
|
|
40
|
+
|
|
41
|
+
```bash
|
|
42
|
+
# If installed via pipx/brew, it's already available globally
|
|
43
|
+
|
|
44
|
+
# Initialize in your project
|
|
45
|
+
cd your-project
|
|
46
|
+
logmind init
|
|
47
|
+
|
|
48
|
+
# Log decisions - Python API
|
|
49
|
+
from logmind import log
|
|
50
|
+
log("Chose FastAPI over Flask",
|
|
51
|
+
reasoning="Need async/await for WebSocket handling")
|
|
52
|
+
|
|
53
|
+
# Or use CLI
|
|
54
|
+
logmind log "Use PostgreSQL for database" \
|
|
55
|
+
-r "Need ACID compliance" \
|
|
56
|
+
-a "MongoDB" -a "SQLite"
|
|
57
|
+
|
|
58
|
+
# View and search decisions
|
|
59
|
+
logmind show
|
|
60
|
+
logmind search "postgres"
|
|
61
|
+
|
|
62
|
+
# Log with a built-in template (pre-fills reasoning, alternatives, implications)
|
|
63
|
+
logmind log --template database "Use PostgreSQL"
|
|
64
|
+
logmind templates # list all available templates
|
|
65
|
+
|
|
66
|
+
# Analytics and stats
|
|
67
|
+
logmind stats
|
|
68
|
+
logmind stats --months 6
|
|
69
|
+
|
|
70
|
+
# Aggregate decisions across multiple projects
|
|
71
|
+
logmind aggregate ~/projects/api ~/projects/frontend
|
|
72
|
+
logmind aggregate --summary ~/work/*/
|
|
73
|
+
|
|
74
|
+
# Enforce decision logging with a pre-commit hook
|
|
75
|
+
logmind install-hook # installs .git/hooks/pre-commit
|
|
76
|
+
logmind check-decisions # run manually or in CI
|
|
77
|
+
|
|
78
|
+
# Manage AI agents
|
|
79
|
+
logmind agents list
|
|
80
|
+
logmind agents add windsurf
|
|
81
|
+
|
|
82
|
+
# View and modify configuration
|
|
83
|
+
logmind config list
|
|
84
|
+
logmind config get git.auto_push
|
|
85
|
+
logmind config set git.auto_push false
|
|
86
|
+
|
|
87
|
+
# Upgrade logmind
|
|
88
|
+
logmind update
|
|
89
|
+
|
|
90
|
+
# Auto-log with decorators
|
|
91
|
+
from logmind import log_decision, log_choice
|
|
92
|
+
|
|
93
|
+
@log_decision(
|
|
94
|
+
decision="Authenticate user with {method}",
|
|
95
|
+
reasoning="Security checkpoint"
|
|
96
|
+
)
|
|
97
|
+
def authenticate(method="oauth"):
|
|
98
|
+
# Your auth code
|
|
99
|
+
return True
|
|
100
|
+
|
|
101
|
+
@log_choice(
|
|
102
|
+
choices={
|
|
103
|
+
"redis": "Use Redis for caching",
|
|
104
|
+
"memory": "Use in-memory caching",
|
|
105
|
+
}
|
|
106
|
+
)
|
|
107
|
+
def select_cache():
|
|
108
|
+
return "redis" if is_production() else "memory"
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
## Contributing / Development Setup
|
|
112
|
+
|
|
113
|
+
Working on logmind itself? Set it up like any CLI tool:
|
|
114
|
+
|
|
115
|
+
```bash
|
|
116
|
+
# Clone the repo
|
|
117
|
+
git clone https://github.com/thrillmot/logmind.git
|
|
118
|
+
cd logmind
|
|
119
|
+
|
|
120
|
+
# Install globally in editable mode (like npm, git, docker)
|
|
121
|
+
pipx install -e .
|
|
122
|
+
|
|
123
|
+
# Now just use it!
|
|
124
|
+
logmind log "Add new feature" -r "Reasoning here"
|
|
125
|
+
logmind show
|
|
126
|
+
logmind search "keyword"
|
|
127
|
+
|
|
128
|
+
# Run tests
|
|
129
|
+
python3 -m venv venv
|
|
130
|
+
source venv/bin/activate
|
|
131
|
+
pip install -e ".[dev]"
|
|
132
|
+
pytest
|
|
133
|
+
```
|
|
134
|
+
|
|
135
|
+
**Why pipx?** logmind is a CLI tool, not a library. It should be globally available like `git` or `npm`.
|
|
136
|
+
|
|
137
|
+
## Framework Integrations
|
|
138
|
+
|
|
139
|
+
```python
|
|
140
|
+
# LangChain — auto-log agent decisions (pip install logmind[langchain])
|
|
141
|
+
from logmind.integrations import LangChainLogger
|
|
142
|
+
|
|
143
|
+
chain = LLMChain(llm=llm, callbacks=[LangChainLogger()])
|
|
144
|
+
|
|
145
|
+
# Custom framework — subclass BaseIntegration
|
|
146
|
+
from logmind.integrations.base import BaseIntegration
|
|
147
|
+
|
|
148
|
+
class MyLogger(BaseIntegration):
|
|
149
|
+
def on_decision(self, output):
|
|
150
|
+
self.log(f"Chose: {output}", reasoning="My framework decided")
|
|
151
|
+
```
|
|
152
|
+
|
|
153
|
+
See [docs/custom-integrations.md](docs/custom-integrations.md) for patterns, examples, and publishing guide.
|
|
154
|
+
|
|
155
|
+
## Documentation
|
|
156
|
+
|
|
157
|
+
- **[Plan & Architecture](docs/plan.md)** - Vision, approach, and technical details
|
|
158
|
+
- **[AI Agent Files](docs/ai-agent-files.md)** - How logmind integrates with AI instruction files
|
|
159
|
+
- **[Custom Integrations](docs/custom-integrations.md)** - Build integrations for any AI framework
|
|
160
|
+
- **[First Decision Example](docs/first-decision-example.md)** - What the initial decision looks like
|
|
161
|
+
- **Development Status** - All phases complete ✅
|
|
162
|
+
|
|
163
|
+
## How It Works
|
|
164
|
+
|
|
165
|
+
1. **Install** logmind as a package
|
|
166
|
+
2. **Init** creates `docs/` folder and inserts instructions into `CLAUDE.md` (preserving existing content)
|
|
167
|
+
3. **Log** a decision - appends, archives old ones (keeps 20 recent), regenerates tree, commits, and pushes
|
|
168
|
+
4. **Context** AI agents read the 20 most recent decisions and current file structure
|
|
169
|
+
|
|
170
|
+
## Why logmind?
|
|
171
|
+
|
|
172
|
+
- **Simple:** Two markdown files (recent + archive), no database
|
|
173
|
+
- **Focused:** Only 20 most recent decisions for relevant AI context
|
|
174
|
+
- **Git-native:** Every decision is a commit, git history is your audit trail
|
|
175
|
+
- **AI-friendly:** Recent decisions + file structure = complete context
|
|
176
|
+
- **Automatic:** Commits and pushes on every log
|
|
177
|
+
|
|
178
|
+
See [docs/plan.md](docs/plan.md) for complete architecture and roadmap.
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["setuptools>=61.0", "wheel"]
|
|
3
|
+
build-backend = "setuptools.build_meta"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "logmind"
|
|
7
|
+
version = "0.1.0"
|
|
8
|
+
description = "Decision logging for AI-assisted development - automatic tracking, git integration, and context for AI agents"
|
|
9
|
+
readme = "README.md"
|
|
10
|
+
requires-python = ">=3.8"
|
|
11
|
+
license = {text = "MIT"}
|
|
12
|
+
authors = [
|
|
13
|
+
{name = "logmind contributors"}
|
|
14
|
+
]
|
|
15
|
+
keywords = [
|
|
16
|
+
"ai", "decision-logging", "documentation", "development",
|
|
17
|
+
"llm", "ai-agents", "decision-tracking", "git-integration",
|
|
18
|
+
"claude", "gpt", "copilot"
|
|
19
|
+
]
|
|
20
|
+
classifiers = [
|
|
21
|
+
"Development Status :: 4 - Beta",
|
|
22
|
+
"Intended Audience :: Developers",
|
|
23
|
+
"License :: OSI Approved :: MIT License",
|
|
24
|
+
"Programming Language :: Python :: 3",
|
|
25
|
+
"Programming Language :: Python :: 3.8",
|
|
26
|
+
"Programming Language :: Python :: 3.9",
|
|
27
|
+
"Programming Language :: Python :: 3.10",
|
|
28
|
+
"Programming Language :: Python :: 3.11",
|
|
29
|
+
"Programming Language :: Python :: 3.12",
|
|
30
|
+
"Programming Language :: Python :: 3.13",
|
|
31
|
+
"Topic :: Software Development :: Documentation",
|
|
32
|
+
"Topic :: Software Development :: Version Control :: Git",
|
|
33
|
+
"Topic :: Text Processing :: Markup :: Markdown",
|
|
34
|
+
]
|
|
35
|
+
|
|
36
|
+
dependencies = [
|
|
37
|
+
"click>=8.0.0",
|
|
38
|
+
"pyyaml>=6.0.0",
|
|
39
|
+
]
|
|
40
|
+
|
|
41
|
+
[project.optional-dependencies]
|
|
42
|
+
dev = [
|
|
43
|
+
"pytest>=7.0.0",
|
|
44
|
+
"black>=23.0.0",
|
|
45
|
+
"mypy>=1.0.0",
|
|
46
|
+
"ruff>=0.5.0",
|
|
47
|
+
"pre-commit>=3.5.0",
|
|
48
|
+
"build>=1.0.0",
|
|
49
|
+
]
|
|
50
|
+
langchain = [
|
|
51
|
+
"langchain-core>=0.1.0",
|
|
52
|
+
]
|
|
53
|
+
|
|
54
|
+
[project.scripts]
|
|
55
|
+
logmind = "logmind.cli:main"
|
|
56
|
+
|
|
57
|
+
[project.urls]
|
|
58
|
+
Homepage = "https://github.com/thrillmot/logmind"
|
|
59
|
+
Documentation = "https://github.com/thrillmot/logmind#readme"
|
|
60
|
+
Repository = "https://github.com/thrillmot/logmind"
|
|
61
|
+
"Bug Tracker" = "https://github.com/thrillmot/logmind/issues"
|
|
62
|
+
Changelog = "https://github.com/thrillmot/logmind/blob/main/CHANGELOG.md"
|
|
63
|
+
|
|
64
|
+
[tool.setuptools.packages.find]
|
|
65
|
+
where = ["src"]
|
|
66
|
+
|
|
67
|
+
[tool.setuptools.package-data]
|
|
68
|
+
logmind = [
|
|
69
|
+
"templates/*.template",
|
|
70
|
+
"templates/*.md",
|
|
71
|
+
"templates/github/*.template",
|
|
72
|
+
]
|
|
73
|
+
|
|
74
|
+
[tool.black]
|
|
75
|
+
line-length = 100
|
|
76
|
+
target-version = ['py38']
|
|
77
|
+
|
|
78
|
+
[tool.ruff]
|
|
79
|
+
line-length = 100
|
|
80
|
+
target-version = "py38"
|
|
81
|
+
|
|
82
|
+
[tool.ruff.lint]
|
|
83
|
+
select = ["E", "F", "W", "I", "B", "UP"]
|
|
84
|
+
ignore = ["E501"] # line length handled by black
|
|
85
|
+
|
|
86
|
+
[tool.ruff.lint.per-file-ignores]
|
|
87
|
+
"tests/*" = ["B011"] # allow asserts
|
|
88
|
+
|
|
89
|
+
[tool.mypy]
|
|
90
|
+
python_version = "3.8"
|
|
91
|
+
warn_return_any = true
|
|
92
|
+
warn_unused_configs = true
|
|
93
|
+
disallow_untyped_defs = false
|
|
94
|
+
ignore_missing_imports = true
|
logmind-0.1.0/setup.cfg
ADDED
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
"""Aggregate per-branch decision logs into docs/decisions.md on PR merge.
|
|
2
|
+
|
|
3
|
+
Designed to be invoked by ``.github/workflows/logmind-aggregate.yml`` after a
|
|
4
|
+
pull request is merged. Reads the per-branch decisions file written by Phase 5
|
|
5
|
+
and appends a single summary entry to the canonical decisions log so the
|
|
6
|
+
default branch's history shows merged work alongside its detail link.
|
|
7
|
+
|
|
8
|
+
Importable for unit testing; ``main()`` adapts environment variables for use
|
|
9
|
+
with ``python -m logmind.actions.aggregate``.
|
|
10
|
+
"""
|
|
11
|
+
|
|
12
|
+
from __future__ import annotations
|
|
13
|
+
|
|
14
|
+
import os
|
|
15
|
+
import sys
|
|
16
|
+
from datetime import datetime
|
|
17
|
+
from pathlib import Path
|
|
18
|
+
from typing import Optional
|
|
19
|
+
|
|
20
|
+
from logmind.core.logger import _sanitize_branch
|
|
21
|
+
from logmind.core.parser import iter_decisions
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
def aggregate(
|
|
25
|
+
branch: str,
|
|
26
|
+
pr_number: int,
|
|
27
|
+
pr_url: str,
|
|
28
|
+
docs_path: Path,
|
|
29
|
+
timestamp: Optional[datetime] = None,
|
|
30
|
+
) -> Optional[Path]:
|
|
31
|
+
"""
|
|
32
|
+
Append a merge-summary entry to ``docs/decisions.md``.
|
|
33
|
+
|
|
34
|
+
Returns the path to the updated file, or ``None`` if the per-branch file is
|
|
35
|
+
missing / empty (in which case there is nothing to summarise and the main
|
|
36
|
+
log is left untouched).
|
|
37
|
+
"""
|
|
38
|
+
if timestamp is None:
|
|
39
|
+
timestamp = datetime.now()
|
|
40
|
+
|
|
41
|
+
sanitized = _sanitize_branch(branch)
|
|
42
|
+
branch_file = docs_path / "decisions-branches" / f"{sanitized}.md"
|
|
43
|
+
if not branch_file.exists():
|
|
44
|
+
return None
|
|
45
|
+
|
|
46
|
+
decision_count = sum(1 for _ in iter_decisions(branch_file))
|
|
47
|
+
if decision_count == 0:
|
|
48
|
+
return None
|
|
49
|
+
|
|
50
|
+
rel_link = f"decisions-branches/{sanitized}.md"
|
|
51
|
+
entry = (
|
|
52
|
+
f"## {timestamp.strftime('%Y-%m-%d %H:%M')} - "
|
|
53
|
+
f"Merged: {branch} (#{pr_number})\n"
|
|
54
|
+
"\n"
|
|
55
|
+
f"- **PR:** {pr_url}\n"
|
|
56
|
+
f"- **Decisions:** {decision_count} from this branch\n"
|
|
57
|
+
f"- **Detail:** [{rel_link}]({rel_link})\n"
|
|
58
|
+
"\n"
|
|
59
|
+
"---\n"
|
|
60
|
+
)
|
|
61
|
+
|
|
62
|
+
decisions_path = docs_path / "decisions.md"
|
|
63
|
+
existing = decisions_path.read_text(encoding="utf-8") if decisions_path.exists() else ""
|
|
64
|
+
decisions_path.write_text(existing + entry, encoding="utf-8")
|
|
65
|
+
return decisions_path
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
def main() -> int:
|
|
69
|
+
"""Entry point for ``python -m logmind.actions.aggregate``."""
|
|
70
|
+
branch = os.environ.get("BRANCH_NAME") or os.environ.get("GITHUB_HEAD_REF")
|
|
71
|
+
pr_number_str = os.environ.get("PR_NUMBER")
|
|
72
|
+
pr_url = os.environ.get("PR_URL")
|
|
73
|
+
|
|
74
|
+
if not branch or not pr_number_str or not pr_url:
|
|
75
|
+
print(
|
|
76
|
+
"logmind aggregate: BRANCH_NAME, PR_NUMBER, and PR_URL must be set",
|
|
77
|
+
file=sys.stderr,
|
|
78
|
+
)
|
|
79
|
+
return 2
|
|
80
|
+
|
|
81
|
+
try:
|
|
82
|
+
pr_number = int(pr_number_str)
|
|
83
|
+
except ValueError:
|
|
84
|
+
print(f"logmind aggregate: PR_NUMBER must be an integer, got {pr_number_str!r}",
|
|
85
|
+
file=sys.stderr)
|
|
86
|
+
return 2
|
|
87
|
+
|
|
88
|
+
docs_path = Path(os.environ.get("LOGMIND_DOCS", "docs"))
|
|
89
|
+
if not docs_path.is_absolute():
|
|
90
|
+
docs_path = Path.cwd() / docs_path
|
|
91
|
+
|
|
92
|
+
result = aggregate(
|
|
93
|
+
branch=branch,
|
|
94
|
+
pr_number=pr_number,
|
|
95
|
+
pr_url=pr_url,
|
|
96
|
+
docs_path=docs_path,
|
|
97
|
+
)
|
|
98
|
+
|
|
99
|
+
if result is None:
|
|
100
|
+
print(f"logmind aggregate: no per-branch decisions for {branch}; nothing to do.")
|
|
101
|
+
return 0
|
|
102
|
+
|
|
103
|
+
print(f"logmind aggregate: appended merge summary for {branch} to {result}")
|
|
104
|
+
return 0
|
|
105
|
+
|
|
106
|
+
|
|
107
|
+
if __name__ == "__main__": # pragma: no cover
|
|
108
|
+
sys.exit(main())
|