Lint rule packs
Introduction
A rule pack is a set of lint rules that ships and installs on its own. Packs exist so that policy can live outside Apache Hop: a company can hold its house style in a pack, a community can share a pack of best practices, and neither has to get their rules accepted into Hop itself to use them.
Hop’s own rules are a pack like any other, with the id hop-core.
Writing a pack needs no Java. A pack is a folder and a YAML file, which is the whole extension mechanism — there is no Java API for individual rules.
Writing a pack
Create a folder under plugins/misc/ in your Hop installation, containing a hop-lint-pack.yml:
pack:
id: acme
name: ACME Standard Lint Rules
owner: VENDOR
priority: 200
rules:
ACME-001:
type: custom
enabled: true
severity: ERROR
target: DATABASE_CONNECTION
targetField: hostname
condition: NO_HARDCODED
name: "Hardcoded Database Hostname"
The rules themselves are written exactly as described in Lint rules.
Give rules tags and a helpUri to carry your own category, owner or policy reference into the SARIF and JSON reports, as described in Tags and help links.
| Key | Meaning |
|---|---|
|
Identifies the pack. Appears in |
|
Display name, shown in Hop Gui. |
|
|
|
Resolution order. Higher priority wins when packs are merged. Hop’s core pack is |
|
Rule ids from another pack that this pack deliberately replaces. |
Rule ids and collisions
Rule ids share one namespace across every installed pack, so prefix yours.
Taking over another pack’s rule id is refused unless the pack declares it:
pack:
id: acme
priority: 200
overrides:
- DB-001 # deliberately replaces the core rule of that name
Without the declaration the incumbent rule stays and the collision is logged. The reason is that a pack could otherwise stand in for Hop’s hardcoded-password rule with something weaker, and nothing would show that it had happened.
Installing a pack
Copy the pack folder into plugins/misc/ in your Hop installation and restart Hop Gui.
The Hop log reports how many packs were discovered.
A pack that cannot be read is left out in Hop Gui, with the error in the Hop log.
hop lint and the Run Linter action fail on it instead, with the pack’s error, so a build never passes without the rules it was meant to check.
Because a pack is a folder of text, it version controls and distributes like any other project: a git repository holding a hop-lint-pack.yml is a complete, shareable rule pack.
Overriding a pack’s rules in a project
A project never edits an installed pack. It overrides the rules it disagrees with in its own hop-lint.yml, which is applied last, on top of every pack:
rules:
ACME-001:
severity: WARNING
This keeps the pack upgradeable: the project’s decisions live with the project, and the pack can be replaced with a newer version without losing them.
Rule ids are matched ignoring case.
An id that no installed pack defines, such as a typo, is reported as a warning in the Hop log and by hop lint, with the closest id as a suggestion, and the override is ignored.
The rule manager in Hop Gui writes these overrides for you.
Editing a pack rule there never changes the pack: a change to its name, description, severity, threshold, enabled state, tags or help URL is written to hop-lint.yml as an override, and the rule goes on following the pack.
A change to what the rule actually looks at, its target, a field or a condition, is written to hop-lint.yml as a complete rule which replaces the pack rule of that id.
So is a changed value in any clause of a composed rule but the first: an override carries one conditionValue, the first clause’s.
From then on, changes to that rule in a newer version of the pack no longer apply, so the rule manager asks before it saves such a change.
The rule is then listed as a project rule, and Restore Pack Rule removes it from hop-lint.yml and brings the pack’s rule back.
Pack rules cannot be deleted, only switched off.