mcp-kb 0.1.0__py3-none-any.whl → 0.2.0__py3-none-any.whl
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.
- mcp_kb/cli/main.py +2 -2
- mcp_kb/cli/reindex.py +3 -2
- mcp_kb/config.py +1 -1
- mcp_kb/data/KNOWLEDBASE_DOC.md +1 -1
- mcp_kb/ingest/chroma.py +19 -14
- mcp_kb/knowledge/bootstrap.py +2 -2
- mcp_kb/knowledge/search.py +2 -2
- mcp_kb/knowledge/store.py +18 -8
- mcp_kb/security/path_validation.py +1 -1
- mcp_kb/server/app.py +3 -3
- mcp_kb/utils/filesystem.py +44 -0
- {mcp_kb-0.1.0.dist-info → mcp_kb-0.2.0.dist-info}/METADATA +3 -3
- mcp_kb-0.2.0.dist-info/RECORD +26 -0
- mcp_kb-0.1.0.dist-info/RECORD +0 -26
- {mcp_kb-0.1.0.dist-info → mcp_kb-0.2.0.dist-info}/WHEEL +0 -0
- {mcp_kb-0.1.0.dist-info → mcp_kb-0.2.0.dist-info}/entry_points.txt +0 -0
- {mcp_kb-0.1.0.dist-info → mcp_kb-0.2.0.dist-info}/top_level.txt +0 -0
mcp_kb/cli/main.py
CHANGED
@@ -8,7 +8,7 @@ import os
|
|
8
8
|
from pathlib import Path
|
9
9
|
from typing import Iterable, List, Optional
|
10
10
|
|
11
|
-
from mcp_kb.config import
|
11
|
+
from mcp_kb.config import DATA_FOLDER_NAME, resolve_knowledge_base_root
|
12
12
|
from mcp_kb.cli.args import add_chroma_arguments, build_chroma_listener, parse_bool
|
13
13
|
from mcp_kb.ingest.chroma import ChromaIngestor
|
14
14
|
from mcp_kb.knowledge.bootstrap import install_default_documentation
|
@@ -79,7 +79,7 @@ def run_server(arguments: Iterable[str] | None = None) -> None:
|
|
79
79
|
parser = _build_argument_parser()
|
80
80
|
options = parser.parse_args(arguments)
|
81
81
|
root_path = resolve_knowledge_base_root(options.root)
|
82
|
-
rules = PathRules(root=root_path, protected_folders=(
|
82
|
+
rules = PathRules(root=root_path, protected_folders=(DATA_FOLDER_NAME,))
|
83
83
|
install_default_documentation(root_path)
|
84
84
|
listeners: List[ChromaIngestor] = []
|
85
85
|
try:
|
mcp_kb/cli/reindex.py
CHANGED
@@ -12,7 +12,7 @@ import logging
|
|
12
12
|
from typing import Iterable, List
|
13
13
|
|
14
14
|
from mcp_kb.cli.args import add_chroma_arguments, build_chroma_listener
|
15
|
-
from mcp_kb.config import
|
15
|
+
from mcp_kb.config import DATA_FOLDER_NAME, resolve_knowledge_base_root
|
16
16
|
from mcp_kb.knowledge.events import KnowledgeBaseReindexListener
|
17
17
|
from mcp_kb.knowledge.store import KnowledgeBase
|
18
18
|
from mcp_kb.security.path_validation import PathRules
|
@@ -58,7 +58,7 @@ def run_reindex(arguments: Iterable[str] | None = None) -> int:
|
|
58
58
|
parser = _build_argument_parser()
|
59
59
|
options = parser.parse_args(arguments)
|
60
60
|
root_path = resolve_knowledge_base_root(options.root)
|
61
|
-
rules = PathRules(root=root_path, protected_folders=(
|
61
|
+
rules = PathRules(root=root_path, protected_folders=(DATA_FOLDER_NAME,))
|
62
62
|
kb = KnowledgeBase(rules)
|
63
63
|
|
64
64
|
listeners: List[KnowledgeBaseReindexListener] = []
|
@@ -71,6 +71,7 @@ def run_reindex(arguments: Iterable[str] | None = None) -> int:
|
|
71
71
|
|
72
72
|
total = 0
|
73
73
|
for listener in listeners:
|
74
|
+
logger.info("Reindexing via %s", listener.__class__.__name__)
|
74
75
|
count = listener.reindex(kb)
|
75
76
|
logger.info("Reindexed %d documents via %s", count, listener.__class__.__name__)
|
76
77
|
total += count
|
mcp_kb/config.py
CHANGED
@@ -16,7 +16,7 @@ import os
|
|
16
16
|
DEFAULT_KNOWLEDGE_BASE_DIR = ".knowledgebase"
|
17
17
|
"""str: Default relative directory for persisting knowledge base documents."""
|
18
18
|
|
19
|
-
|
19
|
+
DATA_FOLDER_NAME = ".data"
|
20
20
|
"""str: Name of the documentation folder inside the knowledge base tree."""
|
21
21
|
|
22
22
|
DOC_FILENAME = "KNOWLEDBASE_DOC.md"
|
mcp_kb/data/KNOWLEDBASE_DOC.md
CHANGED
@@ -8,7 +8,7 @@ operational practices.
|
|
8
8
|
## Structure
|
9
9
|
|
10
10
|
- All knowledge content lives beneath the `.knowledgebase/` root.
|
11
|
-
- Documentation resides under `.
|
11
|
+
- Documentation and other non knowledge resides under `.data/` and is read-only from the MCP tools.
|
12
12
|
- Soft-deleted files are suffixed with `_DELETE_` and ignored by search/overview.
|
13
13
|
|
14
14
|
## Recommended Practices
|
mcp_kb/ingest/chroma.py
CHANGED
@@ -6,7 +6,9 @@ from dataclasses import dataclass
|
|
6
6
|
from pathlib import Path
|
7
7
|
from typing import Any, Dict, List, Mapping, Optional, Set, Tuple, Type, TYPE_CHECKING
|
8
8
|
from langchain_text_splitters import TokenTextSplitter
|
9
|
+
from tqdm import tqdm
|
9
10
|
|
11
|
+
from mcp_kb.config import DATA_FOLDER_NAME
|
10
12
|
from mcp_kb.knowledge.events import (
|
11
13
|
FileDeleteEvent,
|
12
14
|
FileUpsertEvent,
|
@@ -104,7 +106,7 @@ class ChromaConfiguration:
|
|
104
106
|
if data_directory:
|
105
107
|
resolved_directory = Path(data_directory).expanduser().resolve()
|
106
108
|
elif normalized_type == "persistent":
|
107
|
-
resolved_directory = (root / "chroma").resolve()
|
109
|
+
resolved_directory = (root/DATA_FOLDER_NAME / "chroma").resolve()
|
108
110
|
else:
|
109
111
|
resolved_directory = None
|
110
112
|
|
@@ -419,6 +421,7 @@ class ChromaIngestor(KnowledgeBaseListener, KnowledgeBaseReindexListener):
|
|
419
421
|
d.metadata['chunk_number'] = i
|
420
422
|
d.metadata['startline'] = len(content[:d.metadata['start_index']].splitlines())
|
421
423
|
d.metadata['endline'] = d.metadata['startline'] + len(d.page_content.splitlines())-1
|
424
|
+
|
422
425
|
|
423
426
|
self._collection.add(
|
424
427
|
documents=[d.page_content for d in split_docs],
|
@@ -451,19 +454,21 @@ class ChromaIngestor(KnowledgeBaseListener, KnowledgeBaseReindexListener):
|
|
451
454
|
|
452
455
|
count = 0
|
453
456
|
root = kb.rules.root
|
454
|
-
|
455
|
-
|
456
|
-
|
457
|
-
|
458
|
-
|
459
|
-
|
460
|
-
|
461
|
-
|
462
|
-
|
463
|
-
"
|
464
|
-
|
465
|
-
|
466
|
-
|
457
|
+
with tqdm(kb.iter_active_files(include_docs=False), desc="Reindexing Chroma",total=kb.total_active_files(include_docs=False)) as pbar:
|
458
|
+
for path in pbar:
|
459
|
+
pbar.set_description(f"Reindexing Chroma {path.name}")
|
460
|
+
try:
|
461
|
+
content = path.read_text(encoding="utf-8")
|
462
|
+
except FileNotFoundError: # pragma: no cover - race with external edits
|
463
|
+
continue
|
464
|
+
|
465
|
+
relative = str(path.relative_to(root))
|
466
|
+
document_id = f"{self.configuration.id_prefix}{relative}"
|
467
|
+
metadata = {
|
468
|
+
"relative_path": relative,
|
469
|
+
}
|
470
|
+
self._reindex_document(document_id, content, metadata)
|
471
|
+
count += 1
|
467
472
|
|
468
473
|
return count
|
469
474
|
|
mcp_kb/knowledge/bootstrap.py
CHANGED
@@ -4,7 +4,7 @@ from __future__ import annotations
|
|
4
4
|
import importlib.resources as resources
|
5
5
|
from pathlib import Path
|
6
6
|
|
7
|
-
from mcp_kb.config import
|
7
|
+
from mcp_kb.config import DATA_FOLDER_NAME, DOC_FILENAME
|
8
8
|
|
9
9
|
|
10
10
|
def install_default_documentation(root: Path) -> Path:
|
@@ -26,7 +26,7 @@ def install_default_documentation(root: Path) -> Path:
|
|
26
26
|
Path to the documentation file inside the knowledge base tree.
|
27
27
|
"""
|
28
28
|
|
29
|
-
docs_dir = root /
|
29
|
+
docs_dir = root / DATA_FOLDER_NAME
|
30
30
|
doc_path = docs_dir / DOC_FILENAME
|
31
31
|
if doc_path.exists():
|
32
32
|
return doc_path
|
mcp_kb/knowledge/search.py
CHANGED
@@ -11,7 +11,7 @@ from dataclasses import dataclass
|
|
11
11
|
from pathlib import Path
|
12
12
|
from typing import Dict, Iterable, List, Optional
|
13
13
|
|
14
|
-
from mcp_kb.config import
|
14
|
+
from mcp_kb.config import DATA_FOLDER_NAME, DOC_FILENAME
|
15
15
|
from mcp_kb.knowledge.events import KnowledgeBaseSearchListener
|
16
16
|
from mcp_kb.knowledge.store import KnowledgeBase
|
17
17
|
|
@@ -141,7 +141,7 @@ def read_documentation(kb: KnowledgeBase) -> str:
|
|
141
141
|
folder.
|
142
142
|
"""
|
143
143
|
|
144
|
-
doc_path = kb.rules.root /
|
144
|
+
doc_path = kb.rules.root / DATA_FOLDER_NAME / DOC_FILENAME
|
145
145
|
if not doc_path.exists():
|
146
146
|
return ""
|
147
147
|
return doc_path.read_text(encoding="utf-8")
|
mcp_kb/knowledge/store.py
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
|
3
3
|
This module exposes the ``KnowledgeBase`` class, which orchestrates validated
|
4
4
|
filesystem operations for the MCP server. The class encapsulates logic for
|
5
|
-
creating, reading, appending, and modifying
|
5
|
+
creating, reading, appending, and modifying text files while respecting the
|
6
6
|
security constraints defined in the PRD. Each method returns plain Python data
|
7
7
|
structures so that higher-level layers (e.g., JSON-RPC handlers) can focus on
|
8
8
|
protocol serialization rather than filesystem minutiae.
|
@@ -14,7 +14,7 @@ from dataclasses import dataclass
|
|
14
14
|
from pathlib import Path
|
15
15
|
from typing import Iterable, Optional
|
16
16
|
|
17
|
-
from mcp_kb.config import DELETE_SENTINEL,
|
17
|
+
from mcp_kb.config import DELETE_SENTINEL, DATA_FOLDER_NAME
|
18
18
|
from mcp_kb.knowledge.events import FileDeleteEvent, FileUpsertEvent, KnowledgeBaseListener
|
19
19
|
from mcp_kb.security.path_validation import (
|
20
20
|
PathRules,
|
@@ -79,7 +79,7 @@ class KnowledgeBase:
|
|
79
79
|
self.listeners = tuple(listeners or ())
|
80
80
|
|
81
81
|
def create_file(self, relative_path: str, content: str) -> Path:
|
82
|
-
"""Create or overwrite a
|
82
|
+
"""Create or overwrite a text file at ``relative_path``.
|
83
83
|
|
84
84
|
The method validates the path, ensures that the parent directory exists,
|
85
85
|
and writes the provided content as UTF-8 text. Existing files are
|
@@ -185,9 +185,14 @@ class KnowledgeBase:
|
|
185
185
|
original_relative = self._relative_path(normalized)
|
186
186
|
self._notify_delete(target, original_relative)
|
187
187
|
return target
|
188
|
+
|
189
|
+
def total_active_files(self, include_docs: bool = False) -> int:
|
190
|
+
"""Return the total number of non-deleted UTF-8 text files under the root directory.
|
191
|
+
"""
|
192
|
+
return sum(1 for _ in self.iter_active_files(include_docs=include_docs))
|
188
193
|
|
189
194
|
def iter_active_files(self, include_docs: bool = False) -> Iterable[Path]:
|
190
|
-
"""Yield non-deleted
|
195
|
+
"""Yield non-deleted UTF-8 text files under the root directory.
|
191
196
|
|
192
197
|
Parameters
|
193
198
|
----------
|
@@ -197,13 +202,18 @@ class KnowledgeBase:
|
|
197
202
|
the search and overview requirements from the PRD.
|
198
203
|
"""
|
199
204
|
|
200
|
-
|
205
|
+
from mcp_kb.utils.filesystem import is_text_file
|
206
|
+
|
207
|
+
for path in self.rules.root.rglob("*"):
|
208
|
+
if not path.is_file():
|
209
|
+
continue
|
201
210
|
if DELETE_SENTINEL in path.name:
|
202
211
|
continue
|
203
212
|
parts = path.relative_to(self.rules.root).parts
|
204
|
-
if parts and parts[0] ==
|
213
|
+
if parts and parts[0] == DATA_FOLDER_NAME and not include_docs:
|
205
214
|
continue
|
206
|
-
|
215
|
+
if is_text_file(path):
|
216
|
+
yield path
|
207
217
|
|
208
218
|
def _relative_path(self, absolute: Path) -> str:
|
209
219
|
"""Return ``absolute`` rewritten relative to the knowledge base root."""
|
@@ -218,7 +228,7 @@ class KnowledgeBase:
|
|
218
228
|
absolute:
|
219
229
|
Fully resolved path that was modified on disk.
|
220
230
|
content:
|
221
|
-
|
231
|
+
Text payload that should be provided to subscribers.
|
222
232
|
"""
|
223
233
|
|
224
234
|
if not self.listeners:
|
@@ -13,7 +13,7 @@ from dataclasses import dataclass
|
|
13
13
|
from pathlib import Path
|
14
14
|
from typing import Iterable
|
15
15
|
|
16
|
-
from mcp_kb.config import
|
16
|
+
from mcp_kb.config import DATA_FOLDER_NAME, DELETE_SENTINEL
|
17
17
|
|
18
18
|
|
19
19
|
class PathValidationError(ValueError):
|
mcp_kb/server/app.py
CHANGED
@@ -89,7 +89,7 @@ def create_fastmcp_app(
|
|
89
89
|
mcp = FastMCP(
|
90
90
|
"mcp-knowledge-base",
|
91
91
|
instructions=(
|
92
|
-
"You are connected to a local
|
92
|
+
"You are connected to a local text-based knowledge base. Use the provided "
|
93
93
|
"tools to create, inspect, and organize content while respecting the "
|
94
94
|
"soft deletion semantics and the protected documentation folder."
|
95
95
|
),
|
@@ -98,7 +98,7 @@ def create_fastmcp_app(
|
|
98
98
|
|
99
99
|
@mcp.tool(name="create_file", title="Create File")
|
100
100
|
def create_file(path: str, content: str) -> str:
|
101
|
-
"""Create or overwrite a
|
101
|
+
"""Create or overwrite a text file at ``path`` with ``content``."""
|
102
102
|
|
103
103
|
try:
|
104
104
|
created = kb.create_file(path, content)
|
@@ -108,7 +108,7 @@ def create_fastmcp_app(
|
|
108
108
|
|
109
109
|
@mcp.tool(name="read_file", title="Read File", structured_output=True)
|
110
110
|
def read_file(path: str, start_line: int | None = None, end_line: int | None = None) -> ReadFileResult:
|
111
|
-
"""Read a
|
111
|
+
"""Read a text file returning metadata about the extracted segment."""
|
112
112
|
|
113
113
|
try:
|
114
114
|
segment: FileSegment = kb.read_file(path, start_line=start_line, end_line=end_line)
|
mcp_kb/utils/filesystem.py
CHANGED
@@ -81,3 +81,47 @@ def rename(path: Path, target: Path) -> None:
|
|
81
81
|
"""Rename ``path`` to ``target`` using ``Path.rename`` semantics."""
|
82
82
|
|
83
83
|
path.rename(target)
|
84
|
+
|
85
|
+
|
86
|
+
def is_text_file(path: Path, max_bytes: int = 2048) -> bool:
|
87
|
+
"""Heuristically determine whether ``path`` contains UTF-8 text.
|
88
|
+
|
89
|
+
The check is designed to be fast and conservative for use when iterating
|
90
|
+
a directory tree. It reads at most ``max_bytes`` from the file in binary
|
91
|
+
mode and applies two filters:
|
92
|
+
|
93
|
+
- Reject files that contain NUL bytes, which are extremely uncommon in
|
94
|
+
textual formats and a strong indicator of binary content.
|
95
|
+
- Attempt to decode the sampled bytes as UTF-8. If decoding fails, the
|
96
|
+
file is treated as binary.
|
97
|
+
|
98
|
+
Parameters
|
99
|
+
----------
|
100
|
+
path:
|
101
|
+
Absolute path to the file on disk.
|
102
|
+
max_bytes:
|
103
|
+
Upper bound on the number of bytes to sample from the head of the
|
104
|
+
file. A small sample keeps directory scans fast while remaining
|
105
|
+
accurate for typical text formats such as ``.md``, ``.txt``, ``.xml``,
|
106
|
+
and source files.
|
107
|
+
|
108
|
+
Returns
|
109
|
+
-------
|
110
|
+
bool
|
111
|
+
``True`` if the file appears to be UTF-8 text; ``False`` otherwise.
|
112
|
+
"""
|
113
|
+
|
114
|
+
try:
|
115
|
+
with path.open("rb") as handle:
|
116
|
+
sample = handle.read(max_bytes)
|
117
|
+
except (FileNotFoundError, PermissionError): # pragma: no cover - defensive
|
118
|
+
return False
|
119
|
+
|
120
|
+
if b"\x00" in sample:
|
121
|
+
return False
|
122
|
+
|
123
|
+
try:
|
124
|
+
sample.decode("utf-8")
|
125
|
+
return True
|
126
|
+
except UnicodeDecodeError:
|
127
|
+
return False
|
@@ -1,14 +1,14 @@
|
|
1
1
|
Metadata-Version: 2.4
|
2
2
|
Name: mcp-kb
|
3
|
-
Version: 0.
|
3
|
+
Version: 0.2.0
|
4
4
|
Summary: MCP server exposing a local markdown knowledge base
|
5
5
|
Author: LLM Maintainer
|
6
6
|
Requires-Python: >=3.11
|
7
7
|
Description-Content-Type: text/markdown
|
8
|
-
Requires-Dist: chromadb>=1.1.0
|
9
8
|
Requires-Dist: httpx>=0.28.1
|
10
9
|
Requires-Dist: mcp[cli]>=1.15.0
|
11
10
|
Provides-Extra: vector
|
11
|
+
Requires-Dist: chromadb>=1.1.0; extra == "vector"
|
12
12
|
Requires-Dist: tiktoken>=0.11.0; extra == "vector"
|
13
13
|
Requires-Dist: langchain-text-splitters>=0.3.11; extra == "vector"
|
14
14
|
|
@@ -36,7 +36,7 @@ uv run mcp-kb-server --transport http --host 0.0.0.0 --port 9000
|
|
36
36
|
```
|
37
37
|
|
38
38
|
On first launch the server copies a bundled `KNOWLEDBASE_DOC.md` into the
|
39
|
-
`.
|
39
|
+
`.data/` directory if it is missing so that every deployment starts with a
|
40
40
|
baseline usage guide.
|
41
41
|
|
42
42
|
## Optional ChromaDB Mirroring
|
@@ -0,0 +1,26 @@
|
|
1
|
+
mcp_kb/__init__.py,sha256=Ry7qODhfFQF6u6p2m3bwGWhB0-BdWTQcHDJB7NBYAio,74
|
2
|
+
mcp_kb/config.py,sha256=VallCc3_Bjcm2FPElthupvXdbMuXvDkiTkQKj0f4dkQ,2506
|
3
|
+
mcp_kb/cli/__init__.py,sha256=dEIRWFycAfPkha1S1Bj_Y6zkvEZv4eF0qtbF9t74r60,67
|
4
|
+
mcp_kb/cli/args.py,sha256=0yU5lwjjUkgk91ksocqOdpqO_u5JU6xuCaayiOJ-5pQ,5371
|
5
|
+
mcp_kb/cli/main.py,sha256=FMsnWcXmEsXXfETyvPMP2il9jREGFWmR8t23-6QfhMo,3864
|
6
|
+
mcp_kb/cli/reindex.py,sha256=UBBN7_u9rcgGXel5FKnnA3yd7a-AQMwHMwQjt7ZFrSs,3033
|
7
|
+
mcp_kb/data/KNOWLEDBASE_DOC.md,sha256=bkSpdK1W3F0KR6d3q4V_23fnY8Kw2IBjXPvTTRv06AI,1663
|
8
|
+
mcp_kb/data/__init__.py,sha256=UYYuO_n2ikjpwkPSykgleiifYvC0V8_O-atUaRBQUm4,70
|
9
|
+
mcp_kb/ingest/__init__.py,sha256=8obrvfa8nLNLYPbi1MHlFUqfoFHgK9YfdryPzAXQ6kU,77
|
10
|
+
mcp_kb/ingest/chroma.py,sha256=3Kt7or1Z9ng-wBeXeuOPhrVIfjokwkF25jKHdAeYSH8,22170
|
11
|
+
mcp_kb/knowledge/__init__.py,sha256=W_dtRbtnQlrDJ_425vWR8BcoZGJ8gC5-wg1De1E654s,76
|
12
|
+
mcp_kb/knowledge/bootstrap.py,sha256=WlbJUXhxglyWjlvwhUdT20oijLNLaZOePQ6nYwfBCxk,1202
|
13
|
+
mcp_kb/knowledge/events.py,sha256=A7CfD7U5bxo6mCCIic83yE7VPixAN05ssw_HKRF2zxw,3549
|
14
|
+
mcp_kb/knowledge/search.py,sha256=AKsyNipsA8bfRxIJb49tdsU4ICzbHeFrA1Ikvlk1u7w,5901
|
15
|
+
mcp_kb/knowledge/store.py,sha256=urZaLrSRjgqxb_hLC6RQjDeNw8Id14ripQH_6HdWb3o,10002
|
16
|
+
mcp_kb/security/__init__.py,sha256=lF8_XAjzpwhAFresuskXMo0u9v7KFiTJId88wqOAM4Y,62
|
17
|
+
mcp_kb/security/path_validation.py,sha256=21bfKdxjHY-ywDYw0DcGCeXDnvdXDILWVuueUsuuZUM,3617
|
18
|
+
mcp_kb/server/__init__.py,sha256=j9TmxW_WLCoibyQvCsDT1MIuUqSL8sRh2h4u0M4eU0c,74
|
19
|
+
mcp_kb/server/app.py,sha256=7s10UJWFopJ4CZPqZ4briTKsfjDiRo44ZbLAeWb6Lj8,7064
|
20
|
+
mcp_kb/utils/__init__.py,sha256=lKhRsjgnbhye1sSlch1_wsAI3eWKE1M6RVIiNlnsvLI,71
|
21
|
+
mcp_kb/utils/filesystem.py,sha256=0M-Waf2vfqhp8UL__2Emfpwpoqxshti3M7XLjXnpjJw,4026
|
22
|
+
mcp_kb-0.2.0.dist-info/METADATA,sha256=AjAH4xcztes0PzJkjW3J9qyes0VDXS7jfsJFQMq2s1g,5122
|
23
|
+
mcp_kb-0.2.0.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
|
24
|
+
mcp_kb-0.2.0.dist-info/entry_points.txt,sha256=qwJkR3vV7ZeydfS_IYMiDwLv4BdTkrOf4-5neWj25g0,96
|
25
|
+
mcp_kb-0.2.0.dist-info/top_level.txt,sha256=IBiz3TNE3FF3TwkbCZpC1kkk6ohTwtBQNSPJNV3-qGA,7
|
26
|
+
mcp_kb-0.2.0.dist-info/RECORD,,
|
mcp_kb-0.1.0.dist-info/RECORD
DELETED
@@ -1,26 +0,0 @@
|
|
1
|
-
mcp_kb/__init__.py,sha256=Ry7qODhfFQF6u6p2m3bwGWhB0-BdWTQcHDJB7NBYAio,74
|
2
|
-
mcp_kb/config.py,sha256=snbGzbeUf-YXah_F4h2IzHzL_wII966Pf3LZWLKZ-uU,2506
|
3
|
-
mcp_kb/cli/__init__.py,sha256=dEIRWFycAfPkha1S1Bj_Y6zkvEZv4eF0qtbF9t74r60,67
|
4
|
-
mcp_kb/cli/args.py,sha256=0yU5lwjjUkgk91ksocqOdpqO_u5JU6xuCaayiOJ-5pQ,5371
|
5
|
-
mcp_kb/cli/main.py,sha256=07pxHS4FRfhNO4EXWe_9psF7PV6axrY92U7kpZZHkA0,3864
|
6
|
-
mcp_kb/cli/reindex.py,sha256=WxGCTX35ngXO2AjCXSP4TAUJDGcbCzEOIVl6NIFwVu8,2963
|
7
|
-
mcp_kb/data/KNOWLEDBASE_DOC.md,sha256=jrjNdkXNZUIOBZYy9X9ZnRcRWoARJwCKh2pmpiI0oNw,1639
|
8
|
-
mcp_kb/data/__init__.py,sha256=UYYuO_n2ikjpwkPSykgleiifYvC0V8_O-atUaRBQUm4,70
|
9
|
-
mcp_kb/ingest/__init__.py,sha256=8obrvfa8nLNLYPbi1MHlFUqfoFHgK9YfdryPzAXQ6kU,77
|
10
|
-
mcp_kb/ingest/chroma.py,sha256=P3IrPZW3SK3HVayTzyR3KNe_e8aPGiLDfpZswaLmMbE,21849
|
11
|
-
mcp_kb/knowledge/__init__.py,sha256=W_dtRbtnQlrDJ_425vWR8BcoZGJ8gC5-wg1De1E654s,76
|
12
|
-
mcp_kb/knowledge/bootstrap.py,sha256=DitA1x7i4ZMb9IZyWyw1oPh78iHz9VkHe03sBF9042U,1202
|
13
|
-
mcp_kb/knowledge/events.py,sha256=A7CfD7U5bxo6mCCIic83yE7VPixAN05ssw_HKRF2zxw,3549
|
14
|
-
mcp_kb/knowledge/search.py,sha256=_hfN89GPoJn-Y1TEEfnYawkgOGxOn_3-f7-lzdAqbMA,5901
|
15
|
-
mcp_kb/knowledge/store.py,sha256=JP8_vGMzm6HYxg2Y2LUB1fnguIWYokuO1yCRh2pLym4,9598
|
16
|
-
mcp_kb/security/__init__.py,sha256=lF8_XAjzpwhAFresuskXMo0u9v7KFiTJId88wqOAM4Y,62
|
17
|
-
mcp_kb/security/path_validation.py,sha256=lhyL1WUVCb4ypxmJx8drGmR7y_b7nNohz_JFRWJ25MQ,3617
|
18
|
-
mcp_kb/server/__init__.py,sha256=j9TmxW_WLCoibyQvCsDT1MIuUqSL8sRh2h4u0M4eU0c,74
|
19
|
-
mcp_kb/server/app.py,sha256=GnI2z_6C0wwbJd1r-GheQMn1nc4xj71A51_xKLyCUoU,7070
|
20
|
-
mcp_kb/utils/__init__.py,sha256=lKhRsjgnbhye1sSlch1_wsAI3eWKE1M6RVIiNlnsvLI,71
|
21
|
-
mcp_kb/utils/filesystem.py,sha256=Uyo_lHXF35qRxNXsyDkCs6NC0pDqwDt-D6dw0xtYZQE,2632
|
22
|
-
mcp_kb-0.1.0.dist-info/METADATA,sha256=KCfsCIxMSzOzsE7HXtvSmb9d8ouK7ILbab4XNqZjP2Y,5103
|
23
|
-
mcp_kb-0.1.0.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
|
24
|
-
mcp_kb-0.1.0.dist-info/entry_points.txt,sha256=qwJkR3vV7ZeydfS_IYMiDwLv4BdTkrOf4-5neWj25g0,96
|
25
|
-
mcp_kb-0.1.0.dist-info/top_level.txt,sha256=IBiz3TNE3FF3TwkbCZpC1kkk6ohTwtBQNSPJNV3-qGA,7
|
26
|
-
mcp_kb-0.1.0.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|