Files
create/docs/src/guide/templates.md
forbes b8cb7ca267
All checks were successful
Build and Test / build (pull_request) Successful in 29m12s
feat(templates): document templating system for .kc files
Add a template system integrated with Silo new-item creation that lets
users create parts from pre-configured .kc templates and save existing
documents as reusable templates.

Changes:
- mods/silo: template discovery, picker UI, Save as Template command,
  3-tier search paths (system, personal, org-shared)
- docs: template guide, SUMMARY.md entry, silo.md command reference
2026-02-21 09:06:36 -06:00

141 lines
5.9 KiB
Markdown

# Document Templates
Templates let you create new parts and assemblies from pre-configured `.kc` files. Instead of starting from a bare `App::Part` or `Assembly::AssemblyObject`, a template can include predefined tree structures, jobs, metadata, and workbench-specific features.
## How templates work
A template is a normal `.kc` file with an extra `silo/template.json` descriptor inside the ZIP archive. When you select a template during **Silo > New**:
1. The template `.kc` is **copied** to the canonical file path
2. `silo/template.json` and `silo/manifest.json` are **stripped** from the copy
3. The document is **opened** in FreeCAD
4. Silo properties (part number, item ID, revision, type) are **stamped** onto the root object
5. On **save**, `kc_format.py` auto-creates a fresh manifest
The original template file is never modified.
## Using templates
### Creating a new item from a template
1. **Silo > New** (Ctrl+N)
2. Select an **Item Type** (Part, Assembly, etc.)
3. The **Template** dropdown shows templates matching the selected type and category
4. Select a template (or leave as "No template" for a blank document)
5. Fill in the remaining fields and click **Create**
The template combo updates automatically when you change the item type or category.
### Saving a document as a template
1. Open the document you want to use as a template
2. **Silo > Save as Template**
3. Fill in the template metadata:
- **Name** — display name shown in the template picker (pre-filled from document label)
- **Description** — what the template is for
- **Item Types** — which types this template applies to (part, assembly, etc.)
- **Categories** — category prefix filter (e.g. `F`, `M01`); leave empty for all categories
- **Author** — pre-filled from your Silo login
- **Tags** — comma-separated search tags
4. Click **Save Template**
5. Optionally upload to Silo for team sharing
The template is saved as a copy to your personal templates directory. The original document is unchanged.
## Template search paths
Templates are discovered from three locations, checked in order. Later paths shadow earlier ones by name (so you can override a system template with a personal one).
| Priority | Path | Purpose |
|----------|------|---------|
| 1 (lowest) | `mods/silo/freecad/templates/` | System templates shipped with the addon |
| 2 | `~/.local/share/FreeCAD/Templates/` | Personal templates (sister to `Macro/`) |
| 3 (highest) | `~/projects/templates/` | Org-shared project templates |
The personal templates directory (`Templates/`) is created automatically when you first save a template. It lives alongside the `Macro/` directory in your FreeCAD user data.
## Template descriptor schema
The `silo/template.json` file inside the `.kc` ZIP has the following structure:
```json
{
"template_version": "1.0",
"name": "Sheet Metal Part",
"description": "Body with SheetMetal base feature and laser-cut job",
"item_types": ["part"],
"categories": [],
"icon": "sheet-metal",
"author": "Kindred Systems",
"tags": ["sheet metal", "fabrication"]
}
```
| Field | Type | Required | Description |
|-------|------|----------|-------------|
| `template_version` | string | yes | Schema version, currently `"1.0"` |
| `name` | string | yes | Display name in the template picker |
| `description` | string | no | Human-readable purpose |
| `item_types` | string[] | yes | Controls visibility — `["part"]`, `["assembly"]`, or both |
| `categories` | string[] | no | Category prefix filter. Empty array means all categories |
| `icon` | string | no | Icon identifier (reserved for future use) |
| `author` | string | no | Template author |
| `tags` | string[] | no | Searchable metadata tags |
### Filtering rules
- **item_types**: The template only appears when the selected item type is in this list
- **categories**: If non-empty, the template only appears when the selected category starts with one of the listed prefixes. An empty list means the template is available for all categories
## Creating templates from the command line
The `inject_template.py` CLI tool can inject `silo/template.json` into any `.kc` file:
```bash
cd mods/silo/freecad/templates/
# Create a template from an existing .kc file
python inject_template.py my-part.kc "My Custom Part" \
--type part \
--description "Part with custom features" \
--author "Your Name" \
--tag "custom"
# Assembly template
python inject_template.py my-assembly.kc "My Assembly" \
--type assembly \
--description "Assembly with predefined joint groups"
# Template with category filtering
python inject_template.py sheet-metal.kc "Sheet Metal Part" \
--type part \
--category S \
--category X \
--tag "sheet metal" \
--tag "fabrication"
```
## Module structure
```
mods/silo/freecad/
├── templates.py # Discovery, filtering, injection helpers
├── templates/
│ └── inject_template.py # CLI tool for injecting template.json
├── schema_form.py # Template combo in New Item form
└── silo_commands.py # SaveAsTemplateDialog, Silo_SaveAsTemplate,
# SiloSync.create_document_from_template()
```
### Key functions
| Function | File | Purpose |
|----------|------|---------|
| `discover_templates()` | `templates.py` | Scan search paths for `.kc` files with `silo/template.json` |
| `filter_templates()` | `templates.py` | Filter by item type and category prefix |
| `inject_template_json()` | `templates.py` | Inject/replace `silo/template.json` in a `.kc` ZIP |
| `get_default_template_dir()` | `templates.py` | Returns `{userAppData}/Templates/`, creating if needed |
| `get_search_paths()` | `templates.py` | Returns the 3-tier search path list |
| `create_document_from_template()` | `silo_commands.py` | Copy template, strip identity, stamp Silo properties |
| `_clean_template_zip()` | `silo_commands.py` | Strip `silo/template.json` and `silo/manifest.json` from a copy |