dotmd-parser 0.6.2__tar.gz → 0.7.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.
- {dotmd_parser-0.6.2/src/dotmd_parser.egg-info → dotmd_parser-0.7.0}/PKG-INFO +1 -1
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/pyproject.toml +1 -1
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/__init__.py +1 -1
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/parser.py +11 -3
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0/src/dotmd_parser.egg-info}/PKG-INFO +1 -1
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser.egg-info/SOURCES.txt +1 -0
- dotmd_parser-0.7.0/tests/test_orchestrator_detection.py +72 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_skill_integration.py +1 -1
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/LICENSE +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/README.md +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/setup.cfg +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/analyze.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/cli.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/digest.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/index.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/index_md.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/inventory.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/openrag.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/SKILL.md +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/__init__.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/dotmd_index/SKILL.md +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/dotmd_index/__init__.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/prompts/__init__.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/prompts/analyze-dependencies.md +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser.egg-info/dependency_links.txt +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser.egg-info/entry_points.txt +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser.egg-info/requires.txt +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser.egg-info/top_level.txt +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_aggregate.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_analyze.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_cli_dotmd_index.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_cost_estimate.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_empty_warnings.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_host_agent_plan.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_index_md.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_index_scope.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_inventory.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_openrag_push.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_parser.py +0 -0
- {dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/tests/test_token_savings.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: dotmd-parser
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.7.0
|
|
4
4
|
Summary: Dependency graph parser, single-file folder index (dotmd-index.md), and AI analyzer for .md skill files — parse @include/@delegate/@ref directives, build graphs, resolve templates, generate RAG-friendly overviews, and ingest into OpenRAG
|
|
5
5
|
Author: dotmd-projects
|
|
6
6
|
License-Expression: MIT
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "dotmd-parser"
|
|
3
|
-
version = "0.
|
|
3
|
+
version = "0.7.0"
|
|
4
4
|
description = "Dependency graph parser, single-file folder index (dotmd-index.md), and AI analyzer for .md skill files — parse @include/@delegate/@ref directives, build graphs, resolve templates, generate RAG-friendly overviews, and ingest into OpenRAG"
|
|
5
5
|
requires-python = ">=3.10"
|
|
6
6
|
license = "MIT"
|
|
@@ -244,14 +244,22 @@ def build_graph(root_path: str, type_map: list[tuple[str, str]] | None = None) -
|
|
|
244
244
|
if root.is_dir():
|
|
245
245
|
candidate = root / "SKILL.md"
|
|
246
246
|
if not candidate.exists():
|
|
247
|
-
# Case-insensitive search
|
|
247
|
+
# Case-insensitive search at root
|
|
248
248
|
candidates = list(root.glob("*.md"))
|
|
249
249
|
skill_files = [f for f in candidates if f.name.upper() == "SKILL.MD"]
|
|
250
250
|
if skill_files:
|
|
251
251
|
candidate = skill_files[0]
|
|
252
252
|
else:
|
|
253
|
-
|
|
254
|
-
|
|
253
|
+
# Sprint 13 Phase 36: Claude Code plugin convention fallback
|
|
254
|
+
# .claude/skills/<name>/skill.md パターンを検出
|
|
255
|
+
plugin_skills = list(root.glob(".claude/skills/*/skill.md"))
|
|
256
|
+
if plugin_skills:
|
|
257
|
+
# 最初の plugin skill を採用 (複数ある場合は名前順)
|
|
258
|
+
plugin_skills.sort()
|
|
259
|
+
candidate = plugin_skills[0]
|
|
260
|
+
else:
|
|
261
|
+
has_skill_md = False
|
|
262
|
+
candidate = None
|
|
255
263
|
|
|
256
264
|
if candidate:
|
|
257
265
|
root = candidate
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: dotmd-parser
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.7.0
|
|
4
4
|
Summary: Dependency graph parser, single-file folder index (dotmd-index.md), and AI analyzer for .md skill files — parse @include/@delegate/@ref directives, build graphs, resolve templates, generate RAG-friendly overviews, and ingest into OpenRAG
|
|
5
5
|
Author: dotmd-projects
|
|
6
6
|
License-Expression: MIT
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
"""Sprint 13 Phase 36: orchestrator のマルチシグナル検出テスト.
|
|
2
|
+
|
|
3
|
+
dotmd-parser の build_graph が以下 3 パターンの orchestrator を検出できることを確認:
|
|
4
|
+
- root SKILL.md (大文字、既存)
|
|
5
|
+
- subdirectory SKILL.md (claude-ads, TradingAgents)
|
|
6
|
+
- .claude/skills/<name>/skill.md (Claude Code plugin convention, freee-ads-skills)
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
from __future__ import annotations
|
|
10
|
+
|
|
11
|
+
from pathlib import Path
|
|
12
|
+
|
|
13
|
+
import pytest
|
|
14
|
+
|
|
15
|
+
from dotmd_parser.parser import build_graph
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
@pytest.fixture
|
|
19
|
+
def temp_repo(tmp_path: Path) -> Path:
|
|
20
|
+
"""テスト用の最小リポジトリ構造を作る."""
|
|
21
|
+
(tmp_path / "references").mkdir()
|
|
22
|
+
(tmp_path / "references" / "target.md").write_text("# target")
|
|
23
|
+
return tmp_path
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
class TestOrchestratorDetection:
|
|
27
|
+
def test_detects_claude_code_plugin_skill(self, temp_repo: Path) -> None:
|
|
28
|
+
"""`.claude/skills/<name>/skill.md` が directory 引数で auto-detect される."""
|
|
29
|
+
plugin_dir = temp_repo / ".claude" / "skills" / "ads"
|
|
30
|
+
plugin_dir.mkdir(parents=True)
|
|
31
|
+
skill_file = plugin_dir / "skill.md"
|
|
32
|
+
skill_file.write_text(
|
|
33
|
+
"# orchestrator\n\n@delegate ../../../references/target.md\n"
|
|
34
|
+
)
|
|
35
|
+
|
|
36
|
+
graph = build_graph(str(temp_repo))
|
|
37
|
+
|
|
38
|
+
node_ids = [n["id"] for n in graph["nodes"]]
|
|
39
|
+
assert any("skill.md" in nid for nid in node_ids), (
|
|
40
|
+
f"plugin skill.md not detected. nodes={node_ids}"
|
|
41
|
+
)
|
|
42
|
+
assert any("target.md" in nid for nid in node_ids), (
|
|
43
|
+
f"@delegate target not resolved. nodes={node_ids}"
|
|
44
|
+
)
|
|
45
|
+
|
|
46
|
+
def test_root_skill_md_still_works(self, temp_repo: Path) -> None:
|
|
47
|
+
"""既存の root SKILL.md (大文字) 検出が回帰していない."""
|
|
48
|
+
(temp_repo / "SKILL.md").write_text(
|
|
49
|
+
"# top\n\n@delegate references/target.md\n"
|
|
50
|
+
)
|
|
51
|
+
|
|
52
|
+
graph = build_graph(str(temp_repo))
|
|
53
|
+
node_ids = [n["id"] for n in graph["nodes"]]
|
|
54
|
+
assert any("SKILL.md" in nid for nid in node_ids)
|
|
55
|
+
assert any("target.md" in nid for nid in node_ids)
|
|
56
|
+
|
|
57
|
+
def test_root_skill_md_preferred_over_plugin(self, temp_repo: Path) -> None:
|
|
58
|
+
"""root SKILL.md が存在する場合は plugin より優先される (後方互換)."""
|
|
59
|
+
(temp_repo / "SKILL.md").write_text("# root\n")
|
|
60
|
+
plugin_dir = temp_repo / ".claude" / "skills" / "ads"
|
|
61
|
+
plugin_dir.mkdir(parents=True)
|
|
62
|
+
(plugin_dir / "skill.md").write_text("# plugin\n")
|
|
63
|
+
|
|
64
|
+
graph = build_graph(str(temp_repo))
|
|
65
|
+
node_ids = [n["id"] for n in graph["nodes"]]
|
|
66
|
+
assert any(nid.endswith("/SKILL.md") or nid.endswith("SKILL.md") for nid in node_ids)
|
|
67
|
+
|
|
68
|
+
def test_no_skill_anywhere_returns_warning(self, temp_repo: Path) -> None:
|
|
69
|
+
"""SKILL.md も plugin skill.md もない場合は既存 warning を返す."""
|
|
70
|
+
graph = build_graph(str(temp_repo))
|
|
71
|
+
warnings = graph.get("warnings", [])
|
|
72
|
+
assert any(w.get("type") == "missing" for w in warnings)
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/dotmd_index/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
{dotmd_parser-0.6.2 → dotmd_parser-0.7.0}/src/dotmd_parser/templates/prompts/analyze-dependencies.md
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|