name: hexcheck
description: Use when configuring or running hexcheck in a Go repository to enforce hexagonal architecture boundaries, adapter business-logic warnings, and mock discipline.
Hexcheck Configuration Skill
Use hexcheck to lint Go repositories for hexagonal / clean architecture violations.
Core idea
hexcheck does not require folders to have fixed names. It maps project-specific paths to architecture roles through .hexcheck.yaml.
Supported roles:
core — domain entities, value objects, domain services, core business logic
usecase — application services/use cases/orchestration
ports — interfaces/contracts that core/usecases depend on
adapter — infrastructure, persistence, external services, outbound adapters
entrypoint — CLI, HTTP handlers, UI entrypoints, app bootstrap
ignore — generated code, mocks, vendored or ignored paths
Component names are arbitrary. The role is what matters.
Example mappings
A repo with domain, application, and infrastructure:
components:
domain:
role: core
paths:
- internal/domain/**
usecases:
role: usecase
paths:
- internal/application/usecase/**
- internal/application/usecases/**
ports:
role: ports
paths:
- internal/application/port/**
infrastructure:
role: adapter
paths:
- internal/infrastructure/**
cli:
role: entrypoint
paths:
- cmd/**
- internal/cli/**
A repo that uses core and boundaries:
components:
core:
role: core
paths:
- internal/core/**
usecases:
role: usecase
paths:
- internal/usecases/**
inboundBoundaries:
role: entrypoint
paths:
- internal/boundaries/in/**
outboundBoundaries:
role: adapter
paths:
- internal/boundaries/out/**
contracts:
role: ports
paths:
- internal/boundaries/ports/**
Recommended defaults
Start strict on deterministic rules and warning-first on heuristics:
rules:
no-adapter-imports-in-core: error
no-infra-imports-in-usecase: error
no-framework-types-in-core: error
no-infra-types-in-ports: error
no-adapter-to-adapter-imports: warn
suspicious-business-logic-in-adapter: warn
no-local-fakes-for-ports: warn
missing-generated-mock-for-port: warn
prefer-generated-mocks: warn
Business-logic heuristic
suspicious-business-logic-in-adapter is cumulative and package-local. It should not scan the whole repository. It combines strong and weak evidence:
- business keywords such as
Validate, Migrate, Resolve, Score, Restore, Purge, Update
- policy constants and branching
- domain/core mutation or method calls
- multiple port/usecase collaborators when combined with business wording
Use excludePaths for adapter areas where warnings are not useful:
ruleSettings:
suspicious-business-logic-in-adapter:
excludePaths:
- internal/ui/generated/**
Generated code
Always ignore generated code and mocks:
components:
generated:
role: ignore
paths:
- '**/mocks/**'
- '**/generated/**'
- '**/*_templ.go'
- '**/*_gen.go'
hexcheck also ignores files with a standard // Code generated ... DO NOT EDIT. comment.
Mock discipline
Configure generated mock locations so hexcheck can distinguish missing mocks from local fake misuse:
mocking:
generatedMockPaths:
- internal/mocks/**
- internal/application/mocks/**
- internal/application/port/mocks/**
- internal/domain/repository/mocks/**
generatedMockNamePatterns:
- Mock{{Interface}}
- '{{Interface}}Mock'
Expected behavior:
missing-generated-mock-for-port flags mockable interfaces without generated mocks.
no-local-fakes-for-ports flags local fakes only when a generated mock exists.
- Intentional exceptions should use project config
allow entries or linter suppression comments.
Running
Standalone:
hexcheck -hexcheck.config .hexcheck.yaml -hexcheck.root . ./...
With a custom golangci-lint binary, use the module plugin config from examples/custom-gcl.yml and examples/golangci.yml.
Agent checklist
When configuring a new repo:
- Read architecture docs (
AGENTS.md, README, docs) before guessing paths.
- Map local folder names to roles; do not force folder renames.
- Add generated/mocks ignore paths.
- Add mock paths and name patterns.
- Run
hexcheck once and inspect counts by rule.
- Tune
ruleSettings.*.excludePaths for known technical adapters only after reviewing examples.
- Keep deterministic rules as
error; keep heuristic rules as warn until signal is proven.
source
1---
2name: hexcheck
3description: Use when configuring or running hexcheck in a Go repository to enforce hexagonal architecture boundaries, adapter business-logic warnings, and mock discipline.
4---
5
6# Hexcheck Configuration Skill
7
8Use `hexcheck` to lint Go repositories for hexagonal / clean architecture violations.
9
10## Core idea
11
12`hexcheck` does not require folders to have fixed names. It maps project-specific paths to architecture roles through `.hexcheck.yaml`.
13
14Supported roles:
15
16- `core` — domain entities, value objects, domain services, core business logic
17- `usecase` — application services/use cases/orchestration
18- `ports` — interfaces/contracts that core/usecases depend on
19- `adapter` — infrastructure, persistence, external services, outbound adapters
20- `entrypoint` — CLI, HTTP handlers, UI entrypoints, app bootstrap
21- `ignore` — generated code, mocks, vendored or ignored paths
22
23Component names are arbitrary. The `role` is what matters.
24
25## Example mappings
26
27A repo with `domain`, `application`, and `infrastructure`:
28
29```yaml
30components:
31 domain:
32 role: core
33 paths:
34 - internal/domain/**
35 usecases:
36 role: usecase
37 paths:
38 - internal/application/usecase/**
39 - internal/application/usecases/**
40 ports:
41 role: ports
42 paths:
43 - internal/application/port/**
44 infrastructure:
45 role: adapter
46 paths:
47 - internal/infrastructure/**
48 cli:
49 role: entrypoint
50 paths:
51 - cmd/**
52 - internal/cli/**
53```
54
55A repo that uses `core` and `boundaries`:
56
57```yaml
58components:
59 core:
60 role: core
61 paths:
62 - internal/core/**
63 usecases:
64 role: usecase
65 paths:
66 - internal/usecases/**
67 inboundBoundaries:
68 role: entrypoint
69 paths:
70 - internal/boundaries/in/**
71 outboundBoundaries:
72 role: adapter
73 paths:
74 - internal/boundaries/out/**
75 contracts:
76 role: ports
77 paths:
78 - internal/boundaries/ports/**
79```
80
81## Recommended defaults
82
83Start strict on deterministic rules and warning-first on heuristics:
84
85```yaml
86rules:
87 no-adapter-imports-in-core: error
88 no-infra-imports-in-usecase: error
89 no-framework-types-in-core: error
90 no-infra-types-in-ports: error
91 no-adapter-to-adapter-imports: warn
92 suspicious-business-logic-in-adapter: warn
93 no-local-fakes-for-ports: warn
94 missing-generated-mock-for-port: warn
95 prefer-generated-mocks: warn
96```
97
98## Business-logic heuristic
99
100`suspicious-business-logic-in-adapter` is cumulative and package-local. It should not scan the whole repository. It combines strong and weak evidence:
101
102- business keywords such as `Validate`, `Migrate`, `Resolve`, `Score`, `Restore`, `Purge`, `Update`
103- policy constants and branching
104- domain/core mutation or method calls
105- multiple port/usecase collaborators when combined with business wording
106
107Use `excludePaths` for adapter areas where warnings are not useful:
108
109```yaml
110ruleSettings:
111 suspicious-business-logic-in-adapter:
112 excludePaths:
113 - internal/ui/generated/**
114```
115
116## Generated code
117
118Always ignore generated code and mocks:
119
120```yaml
121components:
122 generated:
123 role: ignore
124 paths:
125 - '**/mocks/**'
126 - '**/generated/**'
127 - '**/*_templ.go'
128 - '**/*_gen.go'
129```
130
131`hexcheck` also ignores files with a standard `// Code generated ... DO NOT EDIT.` comment.
132
133## Mock discipline
134
135Configure generated mock locations so `hexcheck` can distinguish missing mocks from local fake misuse:
136
137```yaml
138mocking:
139 generatedMockPaths:
140 - internal/mocks/**
141 - internal/application/mocks/**
142 - internal/application/port/mocks/**
143 - internal/domain/repository/mocks/**
144 generatedMockNamePatterns:
145 - Mock{{Interface}}
146 - '{{Interface}}Mock'
147```
148
149Expected behavior:
150
151- `missing-generated-mock-for-port` flags mockable interfaces without generated mocks.
152- `no-local-fakes-for-ports` flags local fakes only when a generated mock exists.
153- Intentional exceptions should use project config `allow` entries or linter suppression comments.
154
155## Running
156
157Standalone:
158
159```bash
160hexcheck -hexcheck.config .hexcheck.yaml -hexcheck.root . ./...
161```
162
163With a custom golangci-lint binary, use the module plugin config from `examples/custom-gcl.yml` and `examples/golangci.yml`.
164
165## Agent checklist
166
167When configuring a new repo:
168
1691. Read architecture docs (`AGENTS.md`, `README`, docs) before guessing paths.
1702. Map local folder names to roles; do not force folder renames.
1713. Add generated/mocks ignore paths.
1724. Add mock paths and name patterns.
1735. Run `hexcheck` once and inspect counts by rule.
1746. Tune `ruleSettings.*.excludePaths` for known technical adapters only after reviewing examples.
1757. Keep deterministic rules as `error`; keep heuristic rules as `warn` until signal is proven.