MOSS-TTS Load Tokens
Point At a File, Skip the Encode Entirely
- tokens
- frames
This is the other half of the encode-once trick. You encoded a voice reference, saved the codes, and now you want them back - without a model load, without an encode, without feeding MOSS the same 15-second WAV for the four hundredth time.
MOSS-TTS Load Tokens reads a .moss_tokens.pt file back into MOSS_TOKENS and hands you frames alongside it. Note what's missing from that sentence: there's no model input. You can load and inspect token files with nothing loaded in VRAM. That's convenient for a bit of housekeeping, and it's also why the pack validates n_vq later, when the codes are actually used - the loader has no model to check them against.
How you pick a file
Two inputs, and the second one wins whenever it isn't empty:
path- a dropdown, not a text field. It lists every.moss_tokens.ptfound by recursively scanning ComfyUI's input and output directories (Save Tokens writes into a subfolder likeoutput/moss_tokens/, so the scan has to be recursive to be useful). Files from the output directory are prefixedoutput/so that two files with the same basename in different directories don't collapse into one entry. A file written after the page loaded shows up on reload - reload the browser, not ComfyUI.path_override(optional) - a STRING. When non-empty it replaces the dropdown selection. Relative paths resolve against ComfyUI's input directory with the output directory as fallback; absolute paths are used as-is. This is the one that takes a link, because a dropdown can't: convert it to an input and wireMOSS-TTS Save Tokens'pathoutput straight in.
Outputs: tokens (MOSS_TOKENS, shape [frames, n_vq]) and frames (INT, divide by 12.5 for seconds). Wire tokens into Voice Clone.reference_tokens, Voice Continue.prev_tokens, Concat Tokens, Decode Tokens, or straight back into Save Tokens.
Why the split between dropdown and override exists
The dropdown is for you, sitting at the canvas picking a voice from a list. The override is for machines: a headless pipeline saves the base voice in one prompt, reads the path out of /history, and every later prompt carries it. The UI can't express "whatever Save Tokens wrote last time" - a STRING input can.
Two details in the code you'll only notice when they save you:
- Overwriting is detected. The node re-reads the file when its mtime or size changed, so a re-encode that overwrites an existing token file is picked up instead of being served from cache.
- Old workflows still load. When
pathwas a plain STRING in earlier builds, saved values that aren't in the current dropdown are still accepted and resolved the way they always were - a path that has since moved fails at load time with a real message, not at graph-load time with a combo error.
What goes wrong
(no token files found). The dropdown has exactly one entry when neither directory holds a token file, and running with it selected fails on purpose with a plain explanation instead of a confusing "file not found". Either run MOSS-TTS Save Tokens once and reload the page, or use path_override.
Codes from the wrong model. A base voice encoded on the default Local-Transformer will not work on the 8B. The pack checks n_vq when the codes are used and stops with a clear error - annoying, but far better than the alternative, which would be noise you'd spend an hour trying to fix in the sampler settings.
A relative path_override that escapes the input/output directories is refused. Absolute paths are fine.
The file sounds wrong once decoded. That's the loader being honest upstream of you: if Load Tokens → Decode Tokens doesn't sound like the voice you meant, the encode was wrong and every clone off it would be too. Check the prefix once, then run the batch.
Installing it
ComfyUI-Manager: search MOSS-TTS 1.5 by enrico - there are other packs with "MOSS-TTS" in the title. Or:
cd ComfyUI/custom_nodes
git clone https://github.com/eehrich/ComfyUI-MOSS-TTS-1.5.git
Restart ComfyUI. The pack ships with no pip dependencies on purpose (its pyproject.toml is explicit), leaning on the torch, torchaudio and transformers your install already has. Model weights are a separate download - ~9 GB plus ~8.5 GB of audio tokenizer for the default model - but since this node doesn't need a model, you can organise and audition token files before that download has finished.
Troubleshooting
- Edited the file and the node didn't notice - mtime and size are watched, so an edit that preserves both is genuinely invisible. Touch the file or change its content.
- Renamed a token file and it vanished from the dropdown - the scan matches the
.moss_tokens.ptsuffix. Pointpath_overrideat it directly instead. - Loading a token file from someone else - it's read with
weights_only=True, tensors only, so it can't execute code. That's a real security property of the format, and worth remembering next to anytorch.loadyou write yourself. non-default argument 'sampling_rate' follows default argumentlater in the graph - transformers 5.4.0/5.5.0, the pack's one genuine install gotcha.python -m pip install -U "transformers>=5.5.1"in ComfyUI's environment.
Paired with Save Tokens, this is the difference between a voice that lives in your session and a voice that lives in your library.
Inputs (2)
| Name | Type | Default | Description |
|---|---|---|---|
| path | COMBO | Token file to load. Scanned recursively from ComfyUI's input and output directory; entries from the output directory -- where Save Tokens writes -- carry an 'output/' prefix. Files written after the page was loaded appear on reload. A path stored by an older workflow that is not in this list still resolves the way it always did. | |
| path_overrideopt | STRING | Explicit path; when non-empty it REPLACES the dropdown selection. Relative to ComfyUI's input directory (output directory as fallback), or absolute. Convert it to an input and wire the 'path' output of MOSS-TTS Save Tokens into it to load in a later run what an earlier one wrote -- a dropdown cannot take a link, this can. |
Outputs (2)
| Name | Type | Description |
|---|---|---|
| tokens | MOSS_TOKENS | Audio codes, shape [frames, n_vq]. Must come from the same model you generate with (n_vq is validated when it is used). |
| frames | INT | Number of code frames. Divide by 12.5 for seconds. |