# Label templates

> One printer command file of the Labels library: its name and encoding, the printer commands editor and file import, the marker grammar, the installed Windows queue and the test send.

A label template is one row of the **Labels** library (Process > Templates > Labels): a
printer command file (ZPL, EPL, CPCL or any other RAW command language) with `{{NAME}}`
markers where a run value belongs. Ganter Lab sends the bytes to a Windows RAW queue and
substitutes the markers; it never parses, renders or previews the printer language, so the
layout itself is designed in the printer vendor's tool. Editing takes **Manage process**;
the whole page is inert while a unit is running, and a test send is refused while the
runtime is stopped. A new template is born empty, named "Label" ("Label 2", and so on),
and prints nothing until it holds commands: every path that renders or sends refuses an
empty template.

The page is five cards, in the order the work is done: the identity and encoding, the
commands, the markers found in them, how to prepare a file in a designer, and the test
send.

## Template {#template}

| Field | What it is | Values / default | Effect |
| --- | --- | --- | --- |
| Name | The name the library and every label command show. | Text; commits when the field is left. | An empty name is refused ("A label template needs a name.") and the previous name stays. |
| Encoding | How the stored bytes are read back as text, and how every substituted value is encoded. | UTF-8 (default), Latin-1, ASCII. | Changing it rewrites editable commands in the new encoding; a character the new encoding cannot represent is refused ("The commands stay in UTF-8. Line 3 contains 'é', which ASCII cannot represent.") and the encoding stays. Opaque commands keep their bytes and are simply read again under the new declaration. |

## Printer commands {#printer-commands}

| Control | What it does |
| --- | --- |
| The editor | A monospaced text field holding the commands, with a ZPL shape as placeholder. Typing validates as you go (the marker list and any refusal follow the text); leaving the field saves. A refused draft stays on screen with its reason and is not saved; opening another template discards it. Saving a text identical to the stored bytes changes nothing. |
| Import file… / Replace file… | Brings a printer command file in (`.zpl`, `.epl`, `.epl2`, `.cpcl`, `.prn`, `.lbl`, `.txt`). The bytes are copied into the configuration and the file name is kept for traceability: moving or deleting the original does not affect the template. An empty file and a file over 2 MiB are refused, and so is a file whose markers are malformed. |

Commands are editable as text only while they survive the round trip byte for byte: they
decode under the declared encoding, re-encode to the same bytes, end every line the same
way (all LF or all CR LF; an imported CR LF style is put back on every save) and carry no
control character beyond tab and the line ending. Commands that fail any of those tests
stay **opaque**: the editor is replaced by the reason ("Byte 0x1B at offset 12 is not UTF-8
text.", "The line endings are mixed: some lines end with CR LF and others with LF alone.")
and the bytes change only by replacing the file. A line under the card says what is
stored: "Nothing is stored yet.", "Imported from labels.zpl · 1.2 KiB · CR LF line endings
are preserved" or "Written here · 240 B".

## Detected markers {#detected-markers}

The markers found in the stored commands, in first-occurrence order. A marker is a strict
ASCII `{{NAME}}`: the name starts with A to Z, continues with A to Z, 0 to 9 or underscore,
is at most 64 characters long and closes with `}}`. Anything that opens with `{{` and does
not follow the grammar is refused with its byte offset and the rule it broke ("Malformed
label marker at byte offset 40: the name may contain only A-Z, 0-9, or underscore."). Every
byte outside a marker is preserved, and substitution happens once and never recursively.

A template with no commands reads "No commands yet. Write the printer commands above, or
import a file exported from a label designer. Until then this template prints nothing."; a
template with commands and no markers reads "No markers were found: this fixed label sends
the same bytes every time and uses no run data." and is a valid template. Each distinct
marker needs one source in every label command that uses the template; a repeated marker
receives the same value. The card closes with the standing rule: Ganter Lab validates
marker syntax, not vendor commands. Store only commands you trust; they may change printer
behavior.

## Prepare a template in a label designer {#prepare-a-template-in-a-label-designer}

A collapsed reminder of the workflow:

1. Create the label design in the printer vendor's tool, such as ZebraDesigner.
2. Put Ganter Lab markers such as `{{SERIAL}}` or `{{RESULT}}` inside text or barcode content.
3. Export the printer-ready command file, such as ZPL. Do not import the designer's project file.
4. Import that file here (or paste its contents into the commands field) and verify the detected markers.
5. Enter representative values below and test against an installed Windows queue.

The same flow applies to EPL, CPCL and other printer command languages.

## Test send {#test-send}

| Control | What it does |
| --- | --- |
| Refresh queues | Re-reads the printer queues installed for the interactive Windows user. A failure to read them is said beside the picker. |
| One value box per marker | The sample text substituted for that marker in this send only. A fixed template reads "This fixed template needs no sample values."; an empty one "There is nothing to send until this template has printer commands." |
| Installed Windows queue | The queue the test goes to ("(choose a queue)" or "(no installed queues)"). |
| Send test | Renders the stored commands with the sample values and submits them as a RAW document named `Ganter Lab test · <template>`. No run and no artifact is created. The outcome lands in the action feed ("Test label sent to 'Q'." or "Test send failed: reason"). |

Send test is greyed with no commands stored, no queue chosen, while sending, and while the
page is inert. A value a marker cannot carry in the declared encoding is refused by the
renderer. Success means the Windows queue accepted the RAW document; it does not confirm
that a physical label was printed.

## Where the values come from {#where-the-values-come-from}

The sample values above are for the test only. In a run, every distinct marker of the
template is mapped to one finite source on the label command that uses it
([Actions](process-actions)): the frozen metadata, the model name and revision, the unit
name and code, the procedure name and code, the run identifier, the start instant, the run
state, and at Completion also the finish instant, the duration, the verdict, the
termination reason and one named criterion result with an explicit cycle. Date and time
sources take a format (station date and time, station date, station time, ISO 8601) and
numeric sources an optional fixed number of decimal places (0 to 9). A number is written for
the machine that reads it and not the way the station displays numbers on screen: never a group
separator, which inside a barcode breaks the receiving system, always the invariant decimal
point, and a whole number, such as a count or a duration in seconds, written whole. A value that
holds a control character, a line break included, or a character that starts a printer command
(`^`, `~`) is refused naming its marker: it would split the line it sits in, or print a different
label. What each boundary
offers, how the artifact is frozen and how a send is recorded is [Emitting labels and
reports](process-emission); mapping a template by hand against a recorded run is [Labels
and reports](histories-documents#labels).

## What this page does not do {#what-this-page-does-not-do}

It draws no preview of the label and validates nothing about the printer language. It maps
no marker to a value: that is the label command's job. It does not print a label for a
run: the artifacts of a run are printed from its record in Histories. And deleting the
template (the bar's **Delete label template**) leaves every recorded artifact untouched;
only the commands still naming it stop generating.
