Establishes the framework's foundation as a multi-site adoptable platform. ADRs (migrations/adr/): - ADR-001 (ACCEPTED): Asset is the platform contract; Machine retires. Three relationship types (partof, controls, connectedto) with free-text label, position-resolution chain (asset > related > location), hierarchical locations, sibling-bay propagation. - ADR-002 (ACCEPTED): Plugin contract semver via __contract_version__. - ADR-003 (ACCEPTED): Hybrid plugin distribution (in-tree bundled + filesystem-based external). - ADR-004 (ACCEPTED): Per-site instances, not multi-tenant. - ADR-005 (ACCEPTED): Equipment plugin (manufacturing) split from measuringtools plugin (metrology). Subtype-table pattern for protocol data (FOCAS, CLM, MTConnect). - ADR-006 (ACCEPTED): Plugin collector contract via get_collector_schema hook with API-key auth and identity-based upsert. Naming convention v1 (CONTRIBUTING.md): - DB tables/columns: lowercase concatenated, no underscores or dashes - DB-mirrored Python/JS variables match column names exactly; pure code follows host-language convention (PEP 8 / camelCase) - Closed acronym allowlist (universal + shop-floor domain), banned shorthand list with suffix exception (printers_bp etc allowed) - Plain ASCII everywhere: chat, docs, comments, string literals Style enforcement (scripts/check-naming-and-style.sh): - Pre-commit-runnable check script: non-ASCII, banned shorthand, snake_case DB names, snake_case API params in frontend - Fixes 14 violations across 11 files (Unicode arrows, snake_case params, ctx -> canvasContext, res -> response, req -> request_obj) Project state (CLAUDE.md, README.md, frontend/CLAUDE.md): - De-staled CLAUDE.md to reflect actual current state - README unifies DB story (MySQL canonical, SQLite test-only) - frontend/CLAUDE.md points at root convention Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
150 lines
6.9 KiB
Markdown
150 lines
6.9 KiB
Markdown
# ADR-005: Equipment plugin scope vs measuringtools plugin
|
|
|
|
- **Status:** ACCEPTED
|
|
- **Date:** 2026-05-08
|
|
- **Deciders:** cproudlock
|
|
- **Supersedes:** none
|
|
|
|
## Context
|
|
|
|
ADR-001 narrowed the migration to physical manufacturing equipment with a `machinenumber`. In practice, the legacy `category='Equipment'` rows contain two distinct asset classes:
|
|
|
|
1. **Manufacturing machinery** (5-axis mills, lathes, broachers, heat treatment ovens). These produce parts.
|
|
2. **Metrology and inspection instruments** (CMMs, Keyence vision systems, wax-and-trace surface profilometers, GenSpec instruments). These measure parts.
|
|
|
|
Both share `Asset` properties (vendor, model, location, controller). They differ in domain fields (axes vs measurement accuracy, cycle time vs calibration interval, controller protocol vs measurement software).
|
|
|
|
Mixing them under one plugin pollutes the schema and confuses cross-plugin queries ("show me all measuring tools" requires an enumeration of measuring-instrument equipmenttype values, which scales badly).
|
|
|
|
## Decision
|
|
|
|
Two plugins, separate concerns, shared platform contract.
|
|
|
|
### `equipment` plugin
|
|
|
|
Tracks manufacturing machinery. Bundled, in-tree.
|
|
|
|
Schema (per ADR-001 contract):
|
|
|
|
```
|
|
equipment
|
|
- assetid FK to assets, PK
|
|
- equipmenttypeid FK to equipmenttypes (5-axis mill, lathe, broacher, heat treat, ...)
|
|
- vendorid FK to vendors (platform)
|
|
- modelid FK to models (platform)
|
|
- controllertypeid FK to controllertypes (equipment plugin)
|
|
- controllerosid FK to controlleros (equipment plugin)
|
|
- (other shared fields: spindle count, axes, max workpiece size, ...)
|
|
|
|
equipmenttypes (lookup, equipment plugin)
|
|
- equipmenttypeid, name (5-axis mill, lathe, broacher, heat treat, ...)
|
|
|
|
controllertypes (lookup, equipment plugin)
|
|
- controllertypeid, name (Fanuc 31i, Siemens 840D, Mitsubishi M70, Heidenhain TNC640, ...)
|
|
- vendorid (FK to vendors)
|
|
|
|
controlleros (lookup, equipment plugin - separate from PC OS)
|
|
- controllerosid, name (FAPT, VxWorks, embedded Windows, Linux RT, ...)
|
|
|
|
equipmentfocas (subtype, optional, present only when FOCAS-equipped)
|
|
- assetid PK, FK to equipment
|
|
- focasipaddress text
|
|
- focasport integer
|
|
- focasversion text
|
|
- focasmachinenumber text
|
|
|
|
equipmentclm (subtype, optional, present only when CLM-equipped)
|
|
- assetid PK, FK to equipment
|
|
- (CLM-specific: address, port, station ID - finalize when plugin is built)
|
|
|
|
equipmentmtconnect (subtype, optional, present only when MTConnect-equipped)
|
|
- assetid PK, FK to equipment
|
|
- mtconnectagenturl text
|
|
- mtconnectdevicename text
|
|
```
|
|
|
|
The `equipment.protocol` enum field is deliberately **not** included. Presence or absence of a subtype row indicates which protocol applies. Avoids a denormalized field that can drift out of sync.
|
|
|
|
### `measuringtools` plugin
|
|
|
|
Tracks metrology and inspection instruments. Bundled, in-tree (built in Phase 3-4 of the refactor as the first new plugin built using the framework scaffold).
|
|
|
|
Schema (initial draft, refined when plugin is built):
|
|
|
|
```
|
|
measuringtools
|
|
- assetid FK to assets, PK
|
|
- measuringtooltypeid FK to measuringtooltypes (CMM, vision system, profilometer, surface tester, ...)
|
|
- vendorid FK to vendors (platform)
|
|
- modelid FK to models (platform)
|
|
- measurementaxes integer (e.g., 3 for a 3-axis CMM)
|
|
- accuracyspec text (e.g., "+/-0.5um")
|
|
- calibrationintervaldays integer
|
|
- lastcalibrationdate date
|
|
- nextcalibrationdate date (computed)
|
|
- (other domain fields as needed)
|
|
|
|
measuringtooltypes (lookup, measuringtools plugin)
|
|
- measuringtooltypeid, name (CMM, vision system, surface profilometer, gage block, ...)
|
|
```
|
|
|
|
Future extension: subtype tables for measurement-software integrations (PC-DMIS, Keyence, GenSpec). Same pattern as equipment subtype tables.
|
|
|
|
### Subtype-table pattern (general)
|
|
|
|
Both plugins use the same pattern for protocol- or software-specific fields:
|
|
|
|
- Core plugin table carries shared, common fields
|
|
- Optional subtype tables (one per protocol or software) hold extension fields
|
|
- Each subtype table is keyed by `assetid` (PK), one-to-one with the parent
|
|
- Subtype row exists if and only if the asset uses that protocol or software
|
|
- Sister sites add new subtype tables for their own integrations without touching core
|
|
|
|
## Reclassification of legacy data
|
|
|
|
ADR-001's migration moves all legacy `category='Equipment' AND machinenumber IS NOT NULL` rows to `assets` with `assettype='Equipment'` and into the equipment plugin's `equipment` table. This includes both manufacturing machinery and measuring tools.
|
|
|
|
After the equipment migration, when the measuringtools plugin is built:
|
|
|
|
1. Build a mapping table: legacy `machinetypeid` values that are measuring tools (CMM type, Keyence type, etc.)
|
|
2. Run a reclassification script:
|
|
- For each `assets` row where the original `machinetypeid` is in the measuring-tool mapping
|
|
- Change `assets.assettype` to `'MeasuringTool'`
|
|
- Move the row from `equipment` to `measuringtools`
|
|
- Map domain fields where they differ (e.g., legacy `axes` field maps to `measurementaxes`)
|
|
3. Verify counts pre- and post-reclassification
|
|
4. Audit log entry per reclassified row
|
|
|
|
Reclassification is one-shot, run once, archived. Like the original migration script.
|
|
|
|
## Consequences
|
|
|
|
### Positive
|
|
|
|
- Manufacturing machinery and measuring tools are first-class plugins, each with appropriate domain fields
|
|
- Sister sites can install one or both depending on what they track
|
|
- Subtype-table pattern is the canonical example for protocol-specific data and extends naturally to other plugins
|
|
- Building `measuringtools` mid-refactor validates the plugin scaffold tooling against a real new plugin
|
|
|
|
### Negative
|
|
|
|
- Reclassification is a second migration step. Lower risk than the initial migration because it is data-only (no schema change beyond moving rows between two tables that share the same `assetid` link).
|
|
- Sites that adopt the framework before `measuringtools` ships need to either keep measuring tools in `equipment` (workable but suboptimal) or wait for the plugin
|
|
|
|
### Neutral
|
|
|
|
- Legacy `machinetypeid` is preserved on the equipment row during migration to enable reclassification
|
|
|
|
## Alternatives considered
|
|
|
|
1. **Single equipment plugin with sub-typed assets.** Use `equipment.equipmenttypeid` to discriminate manufacturing vs metrology. Rejected: domain fields differ enough that a single table is wide and full of NULLs.
|
|
2. **Migrate split (build mapping before initial migration).** Cleaner end state but requires the `measuringtools` plugin to exist before the migration runs, which delays Phase 5. Rejected.
|
|
3. **JSON blob for protocol data instead of subtype tables.** Considered for both plugins. Rejected: weak typing, awkward queries, no schema validation.
|
|
|
|
## References
|
|
|
|
- ADR-001 (Asset is platform contract)
|
|
- ADR-002 (versioning of the surface)
|
|
- `plugins/equipment/` (current placeholder)
|
|
- `plugins/computers/` (existing example of plugin pattern)
|