# Silo Silo is an item database and part management system for Kindred Create. It provides revision-controlled storage for CAD files, configurable part number generation, BOM management, and team collaboration. - **Submodule path:** `mods/silo/` - **Source:** `git.kindred-systems.com/kindred/silo-mod` ## Architecture Silo has three components: ``` ┌──────────────────────┐ ┌──────────────┐ │ FreeCAD Workbench │────▶│ Go REST API │ │ (Python commands) │ │ (silod) │ └──────────────────────┘ └──────┬───────┘ │ │ │ silo-client │ │ (shared API lib) │ │ ┌─────┴─────┐ │ │ │ │ PostgreSQL MinIO │ (metadata) (files) │ Local .FCStd files ``` - **Go REST API server** (`cmd/silod/`) — 38+ routes, backed by PostgreSQL and MinIO - **FreeCAD workbench** (`freecad/`) — Python commands integrated into Kindred Create - **Shared API client** (`silo-client/`) — Python library used by the workbench (nested submodule) The silo-mod repository was split from a monorepo into three repos: `silo-client` (shared Python API client), `silo-mod` (FreeCAD workbench), and `silo-calc` (LibreOffice Calc extension). ## Workbench commands ### Document lifecycle | Command | Shortcut | Description | |---------|----------|-------------| | `Silo_New` | Ctrl+N | Register a new part — select category, generate part number from schema, optional project tagging | | `Silo_Open` | Ctrl+O | Search and open items — combined dialog querying both the database and local files | | `Silo_Save` | Ctrl+S | Save locally to canonical path, collect document properties, upload to MinIO as auto-revision | | `Silo_Commit` | Ctrl+Shift+S | Save as a new revision with a user-provided comment | | `Silo_Pull` | — | Download from MinIO with revision selection, conflict detection, and progress tracking | | `Silo_Push` | — | Batch upload — finds local files not yet synced to the server, compares timestamps | ### Information and management | Command | Description | |---------|-------------| | `Silo_Info` | Show item metadata, project tags, and revision history table with status and labels | | `Silo_BOM` | Two-tab view: BOM (children) and Where Used (parents). Add, edit, remove entries with quantity and unit tracking | | `Silo_TagProjects` | Multi-select dialog for assigning project tags to items | | `Silo_Rollback` | Select a previous revision and create a new revision from that point with optional comment | | `Silo_SetStatus` | Change revision lifecycle status: draft → review → released → obsolete | ### Administration | Command | Description | |---------|-------------| | `Silo_Settings` | Full settings UI — API URL, SSL verify, custom CA cert, API token management, authentication status | | `Silo_Auth` | Session-based login: `/login` → `/api/auth/me` → `/api/auth/tokens`; stores API token in preferences | | `Silo_ToggleMode` | Switch between Silo workbench and other workbenches (menu only) | ## Origin integration Silo registers as a **file origin** via the `FileOrigin` interface in `src/Gui/`. The `SiloOrigin` class in `silo_origin.py` implements: | Capability | Value | |------------|-------| | `id` | `"silo"` | | `name` | `"Kindred Silo"` | | `type` | PLM (1) | | `tracksExternally` | true | | `requiresAuthentication` | true | | `supportsRevisions` | true | | `supportsBOM` | true | | `supportsPartNumbers` | true | | `supportsAssemblies` | true | The origin delegates to the workbench commands for all operations (new, open, save, commit, pull, push, info, BOM). Registration happens via a deferred QTimer (1500ms after startup) in `src/Mod/Create/InitGui.py`. ## Configuration ### FreeCAD parameters Stored in `User parameter:BaseApp/Preferences/Mod/KindredSilo`: | Parameter | Type | Default | Description | |-----------|------|---------|-------------| | `ApiUrl` | String | (empty) | Silo server URL | | `SslVerify` | Bool | true | Verify SSL certificates | | `CaCertPath` | String | (empty) | Path to custom CA certificate | | `ApiToken` | String | (empty) | Stored authentication token | | `FirstStartChecked` | Bool | false | Whether first-start prompt has been shown | | `ProjectsDir` | String | `~/projects` | Local directory for checked-out files | ### Environment variables | Variable | Default | Description | |----------|---------|-------------| | `SILO_API_URL` | `http://localhost:8080/api` | Override for server API endpoint | | `SILO_PROJECTS_DIR` | `~/projects` | Override for local projects directory | ## Server setup ### Quick start ```bash # Database setup (apply migrations sequentially) psql -h psql.kindred.internal -U silo -d silo -f migrations/001_initial.sql # ... through 010_item_extended_fields.sql # Configure cp config.example.yaml config.yaml # Edit config.yaml with your database, MinIO, and auth settings # Run server go run ./cmd/silod ``` ### Production deployment Production configs live in `mods/silo/deployments/`: ``` deployments/ ├── config.prod.yaml # Database, MinIO, auth settings ├── docker-compose.prod.yaml # Production container orchestration ├── docker-compose.yaml # Development Docker Compose └── systemd/ ├── silod.env.example # Service environment template └── silod.service # systemd unit file ``` The systemd service runs as user `silo` with security hardening (`ProtectSystem=strict`, `NoNewPrivileges`, `PrivateTmp`). Config at `/etc/silo/config.yaml`, binary at `/opt/silo/bin/silod`. ### Server stack - **Go** REST API with 38+ routes - **PostgreSQL** for metadata, revisions, BOM relationships - **MinIO** (S3-compatible) for binary `.FCStd` file storage - **LDAP / OIDC** for authentication - **SSE** (Server-Sent Events) for real-time activity feed ## Database migrations Migrations live in `mods/silo/migrations/` as numbered SQL scripts: | Migration | Purpose | |-----------|---------| | `001_initial.sql` | Core schema — items, revisions, properties | | `002_sequence_by_name.sql` | Part number sequence generation | | `003_remove_material.sql` | Property cleanup | | `004_cad_sync_state.sql` | CAD file sync tracking | | `005_property_schema_version.sql` | Schema versioning for properties | | `006_project_tags.sql` | Project-to-item relationships | | `007_revision_status.sql` | Revision lifecycle status tracking | | `008_odoo_integration.sql` | ERP integration preparation | | `009_auth.sql` | User authentication tables | | `010_item_extended_fields.sql` | Extended item metadata | Apply sequentially: `psql -f migrations/001_initial.sql`, then `002`, etc. There is no automated migration runner — apply manually against the database. ## Part numbering schemas Part number generation is configured via YAML schemas in `mods/silo/schemas/`: - `kindred-rd.yaml` — Primary R&D part numbering schema with category codes, sequence segments, and validation rules - `kindred-locations.yaml` — Location hierarchy schema for physical inventory tracking ## Directory structure ``` mods/silo/ ├── cmd/ │ ├── silo/ # CLI tool │ └── silod/ # API server ├── internal/ │ ├── api/ # HTTP handlers, routes, templates │ ├── config/ # Configuration loading │ ├── db/ # PostgreSQL access │ ├── migration/ # Property migration utilities │ ├── partnum/ # Part number generation │ ├── schema/ # YAML schema parsing │ └── storage/ # MinIO file storage ├── freecad/ │ ├── InitGui.py # SiloWorkbench registration │ ├── silo_commands.py # 14 commands + dock widgets │ ├── silo_origin.py # FileOrigin backend │ └── resources/icons/ # 10 silo-*.svg icons ├── silo-client/ # Shared Python API client (nested submodule) │ └── silo_client/ │ ├── client.py # SiloClient HTTP wrapper │ └── settings.py # SiloSettings config management ├── migrations/ # 10 numbered SQL scripts ├── schemas/ # Part numbering YAML schemas └── deployments/ # Docker Compose + systemd configs ``` ## Further reading - `mods/silo/README.md` — server quickstart and CLI usage - `mods/silo/ROADMAP.md` — strategic roadmap (6 phases, Q2 2026 → Q4 2027)