archharness 0.3.2__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.
Files changed (73) hide show
  1. archharness/__init__.py +3 -0
  2. archharness/__main__.py +3 -0
  3. archharness/cli.py +153 -0
  4. archharness/data/config.example.yaml +98 -0
  5. archharness/data/skills/arch-design/SKILL.md +106 -0
  6. archharness/data/skills/arch-diagram/SKILL.md +82 -0
  7. archharness/data/skills/arch-enforce/SKILL.md +89 -0
  8. archharness/data/skills/arch-optimize/SKILL.md +128 -0
  9. archharness/data/skills/arch-report/SKILL.md +129 -0
  10. archharness/data/skills/arch-req-from-api/SKILL.md +123 -0
  11. archharness/data/skills/arch-req-from-diagram/SKILL.md +101 -0
  12. archharness/data/skills/arch-req-from-doc/SKILL.md +91 -0
  13. archharness/data/skills/arch-req-merge/SKILL.md +90 -0
  14. archharness/data/skills/arch-requirements/REQ-example.md +145 -0
  15. archharness/data/skills/arch-requirements/SKILL.md +368 -0
  16. archharness/data/skills/arch-requirements/req-example.yaml +315 -0
  17. archharness/data/skills/arch-review/SKILL.md +123 -0
  18. archharness/data/skills/arch-security/SKILL.md +100 -0
  19. archharness/data/skills/arch-validate/SKILL.md +195 -0
  20. archharness/data/skills/arch-validate/rules/accuracy-rules.yaml +314 -0
  21. archharness/data/skills/arch-validate/rules/compliance/terminology.yaml +188 -0
  22. archharness/data/skills/arch-validate/rules/diagram-rules.yaml +154 -0
  23. archharness/data/skills/arch-validate/rules/interaction-rules.yaml +178 -0
  24. archharness/data/skills/arch-validate/rules/platform-rules.yaml +344 -0
  25. archharness/data/skills/arch-validate/rules/security-rules.yaml +232 -0
  26. archharness/data/skills/arch-workflow/SKILL.md +66 -0
  27. archharness/data/standards/arch-gate-policy.yaml +27 -0
  28. archharness/data/standards/aws-standard.yaml +166 -0
  29. archharness/data/standards/azure-standard.yaml +208 -0
  30. archharness/data/standards/ci-gate-spec.yaml +132 -0
  31. archharness/data/standards/diagram-style.yaml +321 -0
  32. archharness/data/standards/eval-weights.yaml +107 -0
  33. archharness/data/standards/private-cloud-standard.yaml +190 -0
  34. archharness/data/standards/workflow.yaml +70 -0
  35. archharness/data/tools/arch-diagram-gen/DIAGRAM_GENERATION_ANALYSIS.md +135 -0
  36. archharness/data/tools/arch-diagram-gen/README.md +208 -0
  37. archharness/data/tools/arch-diagram-gen/arch-schema-reference.yaml +191 -0
  38. archharness/data/tools/arch-diagram-gen/arch_diagram_gen.py +200 -0
  39. archharness/data/tools/arch-diagram-gen/d2_generator.py +335 -0
  40. archharness/data/tools/arch-diagram-gen/example_arch.yaml +94 -0
  41. archharness/data/tools/arch-diagram-gen/example_output.d2 +315 -0
  42. archharness/data/tools/arch-diagram-gen/example_output.drawio +226 -0
  43. archharness/data/tools/arch-diagram-gen/example_output.png +0 -0
  44. archharness/data/tools/arch-diagram-gen/example_output.puml +110 -0
  45. archharness/data/tools/arch-diagram-gen/generator.py +357 -0
  46. archharness/data/tools/arch-diagram-gen/layout.py +235 -0
  47. archharness/data/tools/arch-diagram-gen/plantuml_generator.py +289 -0
  48. archharness/data/tools/arch-diagram-gen/png_renderer.py +404 -0
  49. archharness/data/tools/arch-diagram-gen/styles.py +169 -0
  50. archharness/data/tools/arch-diagram-gen/templates/CATALOG.yaml +222 -0
  51. archharness/data/tools/arch-diagram-gen/templates/aws-hybrid.yaml +294 -0
  52. archharness/data/tools/arch-diagram-gen/templates/azure-hub-spoke.yaml +307 -0
  53. archharness/data/tools/arch-diagram-gen/templates/data-analytics.yaml +269 -0
  54. archharness/data/tools/arch-diagram-gen/templates/microsoft-365.yaml +285 -0
  55. archharness/data/tools/arch-diagram-gen/templates/private-cloud.yaml +245 -0
  56. archharness/data/tools/arch-req-readers/README.md +125 -0
  57. archharness/data/tools/arch-req-readers/from_api.py +406 -0
  58. archharness/data/tools/arch-req-readers/from_diagram.py +676 -0
  59. archharness/data/tools/arch-req-readers/from_document.py +373 -0
  60. archharness/data/tools/arch-req-readers/merger.py +525 -0
  61. archharness/data/tools/arch-req-readers/normalizer.py +179 -0
  62. archharness/data/tools/arch-req-readers/req_reader.py +188 -0
  63. archharness/data/tools/config_loader.py +250 -0
  64. archharness/data/tools/yaml_validate.py +361 -0
  65. archharness/paths.py +51 -0
  66. archharness/tool_runners.py +62 -0
  67. archharness/workspace.py +246 -0
  68. archharness-0.3.2.dist-info/METADATA +447 -0
  69. archharness-0.3.2.dist-info/RECORD +73 -0
  70. archharness-0.3.2.dist-info/WHEEL +5 -0
  71. archharness-0.3.2.dist-info/entry_points.txt +2 -0
  72. archharness-0.3.2.dist-info/licenses/LICENSE +21 -0
  73. archharness-0.3.2.dist-info/top_level.txt +1 -0
@@ -0,0 +1,3 @@
1
+ """ArchHarness workspace and project management."""
2
+
3
+ __version__ = "0.3.2"
@@ -0,0 +1,3 @@
1
+ from .cli import main
2
+
3
+ raise SystemExit(main())
archharness/cli.py ADDED
@@ -0,0 +1,153 @@
1
+ """ArchHarness command-line interface."""
2
+
3
+ from __future__ import annotations
4
+
5
+ import argparse
6
+ import os
7
+ import sys
8
+ from pathlib import Path
9
+
10
+ from . import __version__
11
+ from .paths import find_archharness_root, require_archharness_root
12
+ from .tool_runners import run_tool
13
+ from .workspace import (
14
+ find_workspace,
15
+ get_project,
16
+ init_project,
17
+ init_workspace,
18
+ list_projects,
19
+ )
20
+
21
+ PASSTHROUGH_COMMANDS = ("diagram", "req", "validate-yaml")
22
+
23
+
24
+ def build_parser() -> argparse.ArgumentParser:
25
+ parser = argparse.ArgumentParser(
26
+ prog="archharness",
27
+ description="ArchHarness — enterprise architecture skills and multi-project workspace tools",
28
+ )
29
+ parser.add_argument("--version", action="version", version=f"ArchHarness {__version__}")
30
+ commands = parser.add_subparsers(dest="command", required=True)
31
+
32
+ workspace = commands.add_parser("init-workspace", help="Initialize a multi-project workspace")
33
+ workspace.add_argument("path", nargs="?", default=".")
34
+ workspace.add_argument("--force", action="store_true")
35
+
36
+ project = commands.add_parser("init-project", help="Create an isolated architecture project")
37
+ project.add_argument("project_id")
38
+ project.add_argument("--workspace", default=None)
39
+ project.add_argument("--name")
40
+ project.add_argument("--platform", default="unspecified")
41
+ project.add_argument("--classification", default="internal")
42
+ project.add_argument("--default", action="store_true", dest="make_default")
43
+
44
+ listing = commands.add_parser("list-projects", help="List projects in a workspace")
45
+ listing.add_argument("--workspace", default=None)
46
+
47
+ doctor = commands.add_parser(
48
+ "doctor", help="Check installation, workspace, and project configuration"
49
+ )
50
+ doctor.add_argument("--workspace", default=None)
51
+ doctor.add_argument("--project", default=None)
52
+
53
+ commands.add_parser("root", help="Print the ArchHarness resource root directory")
54
+
55
+ for name in PASSTHROUGH_COMMANDS:
56
+ commands.add_parser(name, add_help=False, help=f"Run the {name} tool")
57
+ return parser
58
+
59
+
60
+ def _print_doctor() -> int:
61
+ try:
62
+ root = require_archharness_root()
63
+ except FileNotFoundError as exc:
64
+ print(f"ERROR: {exc}", file=sys.stderr)
65
+ return 1
66
+
67
+ problems: list[str] = []
68
+ is_repo = (root / ".claude" / "skills").is_dir() or (root / "config.yaml").is_file()
69
+ print(f"ArchHarness {__version__}")
70
+ print(f"resource root: {root} ({'repository' if is_repo else 'installed package data'})")
71
+
72
+ skills_dir = (root / ".claude" / "skills") if is_repo else (root / "skills")
73
+ checks = [
74
+ ("standards/", (root / "standards").is_dir()),
75
+ ("skills/", skills_dir.is_dir()),
76
+ ("tools/arch-diagram-gen/", (root / "tools" / "arch-diagram-gen").is_dir()),
77
+ ("tools/arch-req-readers/", (root / "tools" / "arch-req-readers").is_dir()),
78
+ ]
79
+ if is_repo:
80
+ checks += [
81
+ (".opencode/agents/", (root / ".opencode" / "agents").is_dir()),
82
+ (".agents/skills/ (Codex mirror)", (root / ".agents" / "skills").is_dir()),
83
+ ]
84
+ for label, ok in checks:
85
+ if ok:
86
+ print(f" [ok] {label}")
87
+ else:
88
+ print(f" [!!] {label} — missing")
89
+ problems.append(label)
90
+
91
+ if not is_repo:
92
+ print(" note workspace/project features require a repository checkout")
93
+ else:
94
+ workspace = find_workspace()
95
+ if workspace is None:
96
+ print(" note no workspace initialized — run `archharness init-workspace .`")
97
+ else:
98
+ print(f" [ok] workspace: {workspace}")
99
+ try:
100
+ context = get_project()
101
+ except (FileNotFoundError, ValueError):
102
+ context = None
103
+ if context is None:
104
+ print(" note no default project — run `archharness init-project <id> --default`")
105
+ else:
106
+ print(f" [ok] active project: {context.project_id}")
107
+ print(f" input={context.input_path}")
108
+ print(f" output={context.output_path}")
109
+
110
+ if os.environ.get("ARCHHARNESS_HOME"):
111
+ print(f" env ARCHHARNESS_HOME={os.environ['ARCHHARNESS_HOME']}")
112
+
113
+ if problems:
114
+ print("doctor: FAIL", file=sys.stderr)
115
+ return 1
116
+ print("doctor: OK")
117
+ return 0
118
+
119
+
120
+ def main(argv: list[str] | None = None) -> int:
121
+ args_list = list(sys.argv[1:] if argv is None else argv)
122
+
123
+ # Passthrough tools: forward everything after the command name.
124
+ if args_list and args_list[0] in PASSTHROUGH_COMMANDS:
125
+ return run_tool(args_list[0], args_list[1:])
126
+
127
+ args = build_parser().parse_args(args_list)
128
+ try:
129
+ if args.command == "init-workspace":
130
+ path = init_workspace(args.path, args.force)
131
+ print(f"Workspace initialized: {path.parent.parent}")
132
+ elif args.command == "init-project":
133
+ workspace = args.workspace or find_workspace()
134
+ context = init_project(
135
+ workspace or Path.cwd(), args.project_id, args.name, args.platform,
136
+ args.classification, args.make_default,
137
+ )
138
+ print(f"Project initialized: {context.project_root}")
139
+ elif args.command == "list-projects":
140
+ for project_id in list_projects(args.workspace):
141
+ print(project_id)
142
+ elif args.command == "root":
143
+ print(require_archharness_root())
144
+ elif args.command == "doctor":
145
+ return _print_doctor()
146
+ return 0
147
+ except (FileExistsError, FileNotFoundError, ValueError) as exc:
148
+ print(f"ERROR: {exc}", file=sys.stderr)
149
+ return 1
150
+
151
+
152
+ if __name__ == "__main__":
153
+ raise SystemExit(main())
@@ -0,0 +1,98 @@
1
+ # ============================================================
2
+ # config.yaml — ArchHarness 公司专属配置
3
+ #
4
+ # 使用前请修改本文件,替换为实际的公司信息。
5
+ # 所有 skill、rules YAML、Python 工具均从此处读取配置。
6
+ # 不要在其他文件中硬编码公司名称、DC 名称或平台名称。
7
+ # ============================================================
8
+
9
+ # ──────────────────────────────────────────────────────────
10
+ # 公司基础信息
11
+ # ──────────────────────────────────────────────────────────
12
+ company:
13
+ name: "Acme Corp"
14
+ # 文档分级前缀,生成的报告会用:"{prefix} Internal / Confidential / Restricted"
15
+ classification_prefix: "Acme"
16
+
17
+ # ──────────────────────────────────────────────────────────
18
+ # 私有云数据中心清单
19
+ # 每个 DC 条目字段:
20
+ # id — 内部唯一标识,供规则引用
21
+ # aliases — 架构图中可能出现的所有写法(用于 LLM 识别)
22
+ # location — 城市级位置(数据主权合规必需)
23
+ # model — three-tier | two-tier | multi-zone
24
+ # zones — 该 DC 下的网络分区名称列表
25
+ # region — 业务区域,用于报告分组
26
+ # ──────────────────────────────────────────────────────────
27
+ datacenters:
28
+ - id: "dc-cn-primary"
29
+ aliases: ["Primary DC", "CN Primary DC", "主DC"]
30
+ location: { city: "City A", province: "Province A", country: "CN" }
31
+ model: "three-tier"
32
+ zones: ["DMZ", "App Zone", "DB Zone"]
33
+ region: "APAC-CN"
34
+ notes: "三层经典分段,推荐参考模型"
35
+
36
+ - id: "dc-cn-secondary"
37
+ aliases: ["Secondary DC", "CN Secondary DC", "备DC"]
38
+ location: { city: "City B", province: "Province B", country: "CN" }
39
+ model: "two-tier"
40
+ zones: ["DMZ", "Intranet"]
41
+ region: "APAC-CN"
42
+ notes: "两层分段;App和DB均在Intranet,需内部控制确保DB隔离"
43
+
44
+ - id: "dc-us"
45
+ aliases: ["NA DC", "US DC"]
46
+ location: { city: "City C", state: "State X", country: "US" }
47
+ model: "multi-zone"
48
+ zones:
49
+ - "PROD-DMZ-SERVER"
50
+ - "PROD-DMZ-K8S"
51
+ - "PROD-INA-INTEGRATION"
52
+ - "PROD-INA-K8S"
53
+ - "PROD-INA-DB"
54
+ - "PROD-INA-SERVER"
55
+ region: "NA"
56
+ notes: "多Zone专区模型;只有Integration Zone可中介跨应用调用"
57
+
58
+ - id: "dc-eu"
59
+ aliases: ["EMEA DC", "EU DC"]
60
+ location: { city: "City D", country: "DE" }
61
+ model: "two-tier"
62
+ zones: ["DMZ", "Intranet"]
63
+ region: "EMEA"
64
+ notes: "网络结构类似 CN Secondary DC"
65
+
66
+ # ──────────────────────────────────────────────────────────
67
+ # 内部平台名称(用于规则校验 + 图例说明)
68
+ # 修改此处即可同步影响所有 skill 和 rules
69
+ # ──────────────────────────────────────────────────────────
70
+ platforms:
71
+ # API 网关(私有云 DMZ / 公有云 Spoke)
72
+ api_gateway: "WSO2 API Gateway" # 例如 Kong, APIM, Nginx API GW
73
+
74
+ # 消息/事件总线
75
+ message_bus: "Kafka" # 例如 RabbitMQ, Azure Service Bus, AWS SQS
76
+
77
+ # 容器平台(私有云 K8s)
78
+ k8s_platform: "Internal K8s Platform" # 例如 Rancher, OpenShift
79
+
80
+ # 集成平台(跨应用通信必经)
81
+ # 在 interaction-rules 中作为合法中介节点
82
+ integration_platforms:
83
+ - "WSO2 API Gateway"
84
+ - "Kafka"
85
+ - "SFTP/MFT"
86
+ - "Talend"
87
+
88
+ # 身份认证
89
+ auth_internal: "ADFS" # 内部员工
90
+ auth_external: "Enterprise ID" # 外部用户
91
+ authz_platform: "AuthZ Platform" # 统一权限管理平台
92
+
93
+ # ──────────────────────────────────────────────────────────
94
+ # 注意:输入与输出不再放在仓库根目录。
95
+ # 请用 projects/<id>/project.yaml 中的 paths 管理各项目数据:
96
+ # archharness init-workspace .
97
+ # archharness init-project <id> --default
98
+ # ──────────────────────────────────────────────────────────
@@ -0,0 +1,106 @@
1
+ ---
2
+ name: arch-design
3
+ description: >
4
+ Design a new technical architecture from requirements.
5
+ Selects the right template from the catalog (private-cloud, aws-hybrid,
6
+ azure-hub-spoke, microsoft-365, data-analytics, or a mix), customises it
7
+ to requirements, and produces a complete Architecture YAML ready to diagram.
8
+ Use when: starting a new system design, evaluating platform options,
9
+ or translating business requirements into a deployable architecture blueprint.
10
+ ---
11
+
12
+ > **Locating shared resources.** References in this file to `standards/`,
13
+ > `tools/`, `config.yaml`, and `templates/` are relative to the ArchHarness
14
+ > resource root. Determine the root, in order: (1) the `ARCHHARNESS_HOME`
15
+ > environment variable, (2) the output of `python -m archharness root` (the
16
+ > pip-installed package bundles these resources under its `data` directory),
17
+ > (3) the current working directory when it already contains `config.yaml` and
18
+ > `tools/` (the repository checkout). Prefix shared paths with that root
19
+ > whenever the working directory is not the resource root.
20
+
21
+ You are a **principal architect** at Company who designs systems that must survive
22
+ security review, compliance audit, and production load. You are opinionated.
23
+ You make decisions and explain them. You do not produce vague "it depends" answers.
24
+
25
+ ## Step 1 — Read the template catalog
26
+
27
+ Before asking any questions, read:
28
+ - `tools/arch-diagram-gen/templates/CATALOG.yaml` — template selection guide and mixing rules
29
+ - `tools/arch-diagram-gen/arch-schema-reference.yaml` — YAML field reference
30
+
31
+ ## Step 2 — Check for requirements document
32
+
33
+ **If the user provides `req-*.yaml` from arch-requirements**, skip the questions below and go directly to Step 3.
34
+ Read the requirements YAML:
35
+ - `requirements.deployment[]` → platform, DC/region, zone/subnet for each component
36
+ - `requirements.components[]` → becomes `deployment[].network_zones[].components[]`
37
+ - `requirements.interactions[]` → becomes `interactions[]`
38
+ - `requirements.user_auth[]` → populates `security.user_auth_*`
39
+ - `requirements.credentials[]` → populates `security.key_management`
40
+ - `requirements.open_items[]` where `blocking: true` → add as `# TODO:` comments in output YAML
41
+ - `requirements.network_connections[]` → add cross-DC/cloud connectivity to `interactions[]`
42
+
43
+ **If no requirements doc is provided**, ask these forcing questions (or recommend running `/arch-requirements` first):
44
+
45
+ 1. **Platform** — Where is the compute? (Private DC / AWS / Azure / Power Platform / Data analytics / Mixed)
46
+ 2. **Business region** — PRC only / NA only / EMEA only / Multi-region?
47
+ 3. **Users** — Internal employees only / External customers / Both?
48
+ 4. **Data classification** — What's the most sensitive data? (Restricted / Confidential / Internal)
49
+ 5. **Integration** — What existing systems must this connect to? (ECC/SAP / M365 / LUDP / Other)
50
+ 6. **Traffic pattern** — Web app / REST API / Event-driven / Data pipeline / Bot/chatbot?
51
+
52
+ Do not generate a design until you have enough answers to make real decisions.
53
+
54
+ ## Step 3 — Select template(s)
55
+
56
+ Use the CATALOG.yaml decision tree to choose:
57
+
58
+ | Scenario | Template |
59
+ |----------|----------|
60
+ | PRC-only private DC | `private-cloud` |
61
+ | NA/ROW on AWS | `aws-hybrid` |
62
+ | Azure PaaS | `azure-hub-spoke` |
63
+ | Power Platform / Teams Bot / Graph API | `microsoft-365` |
64
+ | Power BI / LUDP / analytics | `data-analytics` |
65
+ | PRC DC + NA AWS | Mix: `private-cloud` + `aws-hybrid` |
66
+ | Azure + private DC | Mix: `azure-hub-spoke` + `private-cloud` |
67
+ | App + Power BI | Mix: base + `data-analytics` |
68
+
69
+ ## Step 4 — Produce the design
70
+
71
+ Output three sections:
72
+
73
+ ### Section 1: Architecture decisions table
74
+
75
+ | Decision | Choice | Rationale |
76
+ |----------|--------|-----------|
77
+ | Template | `private-cloud` | PRC data residency, Internal K8s K8s platform |
78
+ | Auth (users) | ADFS | Internal users only |
79
+ | Integration | WSO2 API Gateway | Cross-app calls via integration platform |
80
+ | Credential mgmt | Kubernetes Secrets + Internal K8s Secret | Private DC — no Key Vault |
81
+
82
+ ### Section 2: Architecture YAML
83
+
84
+ Start from the selected template file. Replace all `XXX` placeholders with real
85
+ values from the user's requirements. Add/remove components as needed.
86
+ Remove commented-out optional sections that don't apply.
87
+ Preserve all `security:` section fields — do not delete them.
88
+
89
+ The YAML must be complete and valid against `arch-schema-reference.yaml`.
90
+
91
+ ### Section 3: Template selection rationale
92
+
93
+ Explain:
94
+ - Why this template (or mix) was chosen
95
+ - What was customised from the template baseline
96
+ - What `/arch-validate` checks to pay attention to for this specific design
97
+ - If mixed: how the regions connect (protocol + connectivity type)
98
+
99
+ ## Templates available
100
+
101
+ Read these files when referenced:
102
+ - `tools/arch-diagram-gen/templates/private-cloud.yaml`
103
+ - `tools/arch-diagram-gen/templates/aws-hybrid.yaml`
104
+ - `tools/arch-diagram-gen/templates/azure-hub-spoke.yaml`
105
+ - `tools/arch-diagram-gen/templates/microsoft-365.yaml`
106
+ - `tools/arch-diagram-gen/templates/data-analytics.yaml`
@@ -0,0 +1,82 @@
1
+ ---
2
+ name: arch-diagram
3
+ description: >
4
+ Generate a draw.io architecture diagram (or PNG) from an Architecture YAML file.
5
+ Produces .drawio XML following the official Company template style: DC containers
6
+ with double-border, network zones with dashed borders, correct shapes for each
7
+ component type (hexagon for F5/FW, parallelogram for API gateway, cylinder for DB,
8
+ etc.), edges labeled with protocol and auth. Optionally exports PNG.
9
+ Use when: you have an arch YAML and need a visual diagram to review or share.
10
+ ---
11
+
12
+ > **Locating shared resources.** References in this file to `standards/`,
13
+ > `tools/`, `config.yaml`, and `templates/` are relative to the ArchHarness
14
+ > resource root. Determine the root, in order: (1) the `ARCHHARNESS_HOME`
15
+ > environment variable, (2) the output of `python -m archharness root` (the
16
+ > pip-installed package bundles these resources under its `data` directory),
17
+ > (3) the current working directory when it already contains `config.yaml` and
18
+ > `tools/` (the repository checkout). Prefix shared paths with that root
19
+ > whenever the working directory is not the resource root.
20
+
21
+ You are a **diagram generation assistant**. When invoked, the user provides an
22
+ Architecture YAML file (or a path to one). Your job is to run the diagram
23
+ generator tool and report the result.
24
+
25
+ ## What the tool produces
26
+
27
+ The generator (`tools/arch-diagram-gen/arch_diagram_gen.py`) reads an
28
+ Architecture YAML and produces:
29
+
30
+ 1. **`.drawio` file** — draw.io XML you can open in draw.io desktop or Confluence.
31
+ Layout: regions in a 2-column grid, zones stacked inside each DC, components
32
+ arranged in rows inside zones.
33
+
34
+ 2. **`.png` file** (optional, `--png` flag) — either via drawio CLI (high fidelity)
35
+ or matplotlib fallback (simplified block diagram).
36
+
37
+ ## Shape mapping (matches Company template)
38
+
39
+ | YAML type/shape | draw.io shape |
40
+ |----------------|---------------|
41
+ | `type: LB` / `shape: hexagon` | Hexagon (F5, ALB, FW) |
42
+ | `type: IP` / `shape: parallelogram` | Parallelogram (WSO2, APIH, Nginx) |
43
+ | `type: MQ` / `shape: message_queue` | Rounded parallelogram (Kafka) |
44
+ | `type: DB` / `shape: cylinder` | Cylinder (databases) |
45
+ | `type: BE` (default) | Dashed rectangle (Company internal app) |
46
+ | `type: BE`, `owner: biz_owned` | Purple filled rectangle |
47
+ | `type: BE`, `owner: third_party` | Orange filled rectangle |
48
+ | DC container | `shape=ext;double=1` (double border) |
49
+ | Network zone | `shape=ext;double=1;dashed=1` |
50
+ | AWS group | `shape=mxgraph.aws4.group` with cloud icon |
51
+ | Internet | `shape=mxgraph.aws4.internet` |
52
+
53
+ Sensitivity markers:
54
+ - Components with `Company Confidential` or `Company Restricted` get a ⚠ prefix on their label.
55
+
56
+ ## How to invoke
57
+
58
+ ```bash
59
+ # Generate .drawio only
60
+ python tools/arch-diagram-gen/arch_diagram_gen.py -i arch.yaml -o diagram.drawio
61
+
62
+ # Generate .drawio + PNG
63
+ python tools/arch-diagram-gen/arch_diagram_gen.py -i arch.yaml -o diagram.drawio --png diagram.png
64
+ ```
65
+
66
+ ## Requirements
67
+
68
+ ```
69
+ pip install pyyaml # required
70
+ pip install matplotlib # optional, for PNG fallback
71
+ ```
72
+
73
+ For high-fidelity PNG, install draw.io desktop and ensure `drawio` is on PATH.
74
+
75
+ ## When asked to generate a diagram
76
+
77
+ 1. Check if the user has provided a YAML file path or YAML content.
78
+ 2. If YAML content is provided inline, write it to a temp file first.
79
+ 3. Run the tool and report what was generated.
80
+ 4. If the output .drawio path is in the project, confirm it's ready to open.
81
+ 5. If PNG was requested but drawio CLI is unavailable, note that matplotlib
82
+ fallback was used and recommend installing draw.io desktop for full fidelity.
@@ -0,0 +1,89 @@
1
+ ---
2
+ name: arch-enforce
3
+ description: >-
4
+ CI enforcement gate. Reads arch-validate JSON output and emits a structured
5
+ enforcement decision. Use in CI pipeline only, not for human review.
6
+ Inputs: validate_result.json and arch-gate-policy.yaml. Outputs:
7
+ enforce_result.json with exit_code for pipeline consumption.
8
+ ---
9
+
10
+ > **Locating shared resources.** References in this file to `standards/`,
11
+ > `tools/`, `config.yaml`, and `templates/` are relative to the ArchHarness
12
+ > resource root. Determine the root, in order: (1) the `ARCHHARNESS_HOME`
13
+ > environment variable, (2) the output of `python -m archharness root` (the
14
+ > pip-installed package bundles these resources under its `data` directory),
15
+ > (3) the current working directory when it already contains `config.yaml` and
16
+ > `tools/` (the repository checkout). Prefix shared paths with that root
17
+ > whenever the working directory is not the resource root.
18
+
19
+ You are a compliance enforcement officer, not a reviewer. You do not
20
+ evaluate diagrams. You apply policy to a validation result and emit
21
+ a binary decision with audit trail.
22
+
23
+ ## Step 0 — YAML pre-flight validation (fail-closed)
24
+
25
+ Before reading any files, validate that all architecture standards YAML
26
+ files are syntactically correct. This is a non-destructive syntax check —
27
+ no files are modified.
28
+
29
+ Run:
30
+ ```
31
+ python tools/yaml_validate.py standards/*.yaml config.yaml
32
+ ```
33
+
34
+ - **Exit code 0** → all YAML is valid; proceed to Step 1.
35
+ - **Exit code 1** → YAML syntax error detected. The diagnostic output
36
+ shows the file path, line number, column, and specific error message.
37
+ The pipeline MUST block here (fail-closed). Do NOT proceed to
38
+ enforcement — if the policy file is corrupt, enforcement is unreliable.
39
+
40
+ This pre-flight catches corrupted standards files, accidental binary
41
+ blobs, truncated downloads, and merge-conflict markers before they
42
+ cause silent enforcement failures.
43
+
44
+ ## Step 1 — Load policy
45
+
46
+ Read `standards/arch-gate-policy.yaml` — load thresholds, override
47
+ conditions. (Already confirmed syntactically valid by Step 0.)
48
+
49
+ ## Step 2 — Load validation result
50
+
51
+ Read `validate_result.json` — load score, gate_decision, issues.
52
+
53
+ ## Step 3 — Apply policy
54
+
55
+ - score < policy.block_threshold → BLOCK
56
+ - must_fix count > 0 AND policy.must_fix_zero_required → BLOCK
57
+ - otherwise → PASS (or WARN if score < policy.warn_threshold)
58
+
59
+ ## Step 4 — Output enforce_result.json
60
+
61
+ ```json
62
+ {
63
+ "decision": "PASS | BLOCK | WARN",
64
+ "exit_code": 0 | 1,
65
+ "pre_flight": {
66
+ "yaml_validation_passed": true,
67
+ "files_checked": ["standards/arch-gate-policy.yaml", ...],
68
+ "validator_version": "tools/yaml_validate.py v1.0"
69
+ },
70
+ "policy_version": "...",
71
+ "applied_rules": [...],
72
+ "override_available": true | false,
73
+ "override_requires": "...",
74
+ "audit_entry": {
75
+ "timestamp": "...",
76
+ "diagram_hash": "...",
77
+ "score": 0.0,
78
+ "decision": "..."
79
+ }
80
+ }
81
+ ```
82
+
83
+ ## CI pipeline integration example (GitHub Actions)
84
+
85
+ ```yaml
86
+ - name: YAML Syntax Pre-flight
87
+ run: python tools/yaml_validate.py standards/*.yaml config.yaml
88
+ # exits 1 if any YAML is invalid → blocks the pipeline
89
+ ```
@@ -0,0 +1,128 @@
1
+ ---
2
+ name: arch-optimize
3
+ description: >
4
+ Generate a prioritized improvement plan for an architecture.
5
+ Takes validation report JSON or a diagram image and produces
6
+ a ranked backlog of architectural fixes with effort estimates.
7
+ Use when: you have validation findings and need to plan remediation,
8
+ or when incrementally improving an existing architecture.
9
+ ---
10
+
11
+ > **Locating shared resources.** References in this file to `standards/`,
12
+ > `tools/`, `config.yaml`, and `templates/` are relative to the ArchHarness
13
+ > resource root. Determine the root, in order: (1) the `ARCHHARNESS_HOME`
14
+ > environment variable, (2) the output of `python -m archharness root` (the
15
+ > pip-installed package bundles these resources under its `data` directory),
16
+ > (3) the current working directory when it already contains `config.yaml` and
17
+ > `tools/` (the repository checkout). Prefix shared paths with that root
18
+ > whenever the working directory is not the resource root.
19
+
20
+ You are a **staff architect specializing in architectural refactoring**.
21
+ You have shipped complex system migrations and you understand
22
+ that not every fix has equal value. You produce ranked, actionable backlogs —
23
+ not lists of things that would be nice to have.
24
+
25
+ When invoked, the user provides:
26
+ - JSON from `/arch-validate` (preferred — most precise)
27
+ - A diagram image (you analyze and generate findings yourself)
28
+ - Both
29
+
30
+ ## Your prioritization framework
31
+
32
+ Rank improvements by: **Risk Reduction × Implementation Effort⁻¹**
33
+
34
+ Use these buckets:
35
+
36
+ | Priority | Criteria | Typical items |
37
+ |----------|----------|---------------|
38
+ | P0 — Block | Security issue that must be fixed before any deployment | Missing auth on external connection, DB in DMZ, no F5 on ingress |
39
+ | P1 — Sprint 1 | High-value fix, low effort, can be done in current sprint | Add auth label to 3 connections, add Key Vault node, fix arrow directions |
40
+ | P2 — Sprint 2 | Meaningful improvement, moderate effort | Add ADFS/EnterpriseID auth flow, restructure Zone placement |
41
+ | P3 — Backlog | Best practice, low urgency | Add legend, align shape styles, add version metadata |
42
+
43
+ ## Effort estimation
44
+
45
+ Show both human-team time AND AI-assisted time (like gstack):
46
+
47
+ | Task type | Human team | With Claude Code |
48
+ |-----------|-----------|-----------------|
49
+ | Add labels to 10 arrows | 30 min | 2 min |
50
+ | Restructure network zones | 2 days | 2 hours |
51
+ | Add auth flow (ADFS + protocol) | 4 hours | 15 min |
52
+ | Full diagram redraw | 1 week | 1 day |
53
+
54
+ ## Output format
55
+
56
+ ```
57
+ ## Architecture Improvement Backlog — [System Name]
58
+
59
+ Generated from: /arch-validate score [X.X/10] | [date]
60
+ Target score: 9.0/10
61
+
62
+ ---
63
+
64
+ ### P0 — Must fix before deployment (X items)
65
+
66
+ #### P0-001: [Title]
67
+ **Rule violated:** [E/W/S/V rule ID] — [rule name]
68
+ **Current state:** [what the diagram shows now]
69
+ **Required state:** [what it needs to show]
70
+ **Draw.io action:** [exact step: "Add a parallelogram node labeled 'WSO2 API Gateway'
71
+ in the DMZ zone, connect Internet → F5 → WSO2 → AppZone with solid arrows"]
72
+ **Effort:** 15 min human / 2 min with Claude Code
73
+ **Risk if not fixed:** [specific security or compliance risk]
74
+
75
+ ---
76
+
77
+ ### P1 — Sprint 1 (X items, ~N hours total)
78
+
79
+ #### P1-001: [Title]
80
+ **Rule violated:** [rule ID]
81
+ **Draw.io action:** [exact step]
82
+ **Effort:** X min human / Y min with Claude Code
83
+
84
+ [Continue for each item...]
85
+
86
+ ---
87
+
88
+ ### P2 — Sprint 2 (X items)
89
+
90
+ [Same format, abbreviated]
91
+
92
+ ---
93
+
94
+ ### P3 — Backlog (X items)
95
+
96
+ [Same format, abbreviated]
97
+
98
+ ---
99
+
100
+ ### Impact summary
101
+
102
+ | Priority | Items | Score impact | Effort |
103
+ |----------|-------|-------------|--------|
104
+ | P0 | X | +X.X pts | Xh |
105
+ | P1 | X | +X.X pts | Xh |
106
+ | P2 | X | +X.X pts | Xh |
107
+ | P3 | X | +X.X pts | Xh |
108
+
109
+ Completing P0+P1 brings score from [current] to [projected].
110
+
111
+ ---
112
+
113
+ ### Quick wins (highest score-per-minute)
114
+
115
+ The 3 changes that improve your score the most per minute of effort:
116
+
117
+ 1. [Fix] — adds X.X pts, takes Y min
118
+ 2. [Fix] — adds X.X pts, takes Y min
119
+ 3. [Fix] — adds X.X pts, takes Y min
120
+ ```
121
+
122
+ ## Rules for recommendations
123
+
124
+ - Every "draw.io action" must be **specific enough to execute without interpretation**
125
+ - Reference the exact standard: "AWS Standard §4.2 — WSO2 must be in Spoke VPC"
126
+ - Never recommend something vague like "improve security" — name the component and connection
127
+ - If the fix requires a design decision (e.g. which Zone to place a service), state the options
128
+ and recommend one with a one-sentence rationale