Repository navigation
Conversation
POST /v1/characters makes a Character's lines in a voice from the new
characters/voices.tsv (GET /v1/voices): with the user's own key for the
voice's provider, 16 kHz PCM straight from ElevenLabs or Volcano Engine;
otherwise from the voice service with "for":"character". Lines with
{address} are made once per form of address, named and laid out as
tools/make-character.sh does. Each line is trimmed, normalized to -1 dBFS
and packed with the box's ADPCM encoder into pack.bin and
address/<form>.bin under config_dir()/characters/<id>/, byte for byte as
tools/character_pack.py packs them. A refusal stops the job and keeps the
lines made; making the same id again resumes. Progress is `making` in
/v1/status.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
There was a problem hiding this comment.
Copilot was unable to review this pull request because the user who requested the review has insufficient remaining quota.
An organization owner can choose the repository organization as the billing source for reviews requested by members with a paid Copilot license. Learn about Copilot code review billing.
…ve a panic GET /v1/characters lists the Characters made here from their manifests, with whether their packs are made. A box wearing a made Character's pack gets spoken replies in the voice it was made with, not Jessica. A job that panics ends as failed with reason "internal" instead of making forever. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Builds on #187 (own keys).
Changes
characters/voices.tsv: id, provider, voice, language, gender, display name. It holds the presets' voices (robot is skipped) and Jessica, and it is compiled into the daemon.GET /v1/voiceslists it.POST /v1/characters {id?, name, base, voice, lines:[{occasion,text}]}starts a background job, one at a time (409 while one is running). It answers 202.makingin/v1/statusreports{id, name, state, done, total, reason, error}.voicemust be avoices.tsvid,basea preset with lines, and there can be at most 110 lines (what a pack with a look holds).pcm_16000witheleven_flash_v2_5, or the Volcano Engine V3 stream withformat:"pcm", sample_rate:16000. Without a key, it goes to/v1/voice/speakwith"for":"character"and the session. The reasons areplan,monthly,global_cap,signed_out(401 forgets the session), andown_keywhen a provider refuses the user's key.{address}lines, naming and layout followtools/make-character.sh:audio/<occasion>/<prefix>-<sha1[:10]>.pcm(+.txt) andaudio-address/<form>/....0-<row>, all other lines get1.without_addressare ported.firmware-rs/core'sEncoder. That crate moves from dev- to normal dependencies. It is already a workspace member, so the license bundle is unchanged.config_dir()/characters/<id>/:pack.binandaddress/<form>.binare v1 packs with no look, byte for byte whatcharacter_pack.pybuilds. The App takes them as it takes a preset's (withAddress/withLook,Pack::parse/with_address/with_look).manifest.jsonholds{name, base, voice, lines}.idagain resumes it; if its voice changed, the old audio is dropped.synthesis.rs: the Volcano Engine JSON stream reader is split out (read_volc) so PCM can share it, and a few constants are nowpub(crate).docs/app.md(the local API),docs/characters.md("Making a Character"),characters/README.md.Verification
cargo test --workspace --locked: all pass (daemon 356).cargo clippy --workspace --all-targets: no warnings in the touched files.shasum) and its comma rules;monthly) stopping the job, then a resume that makes each line exactly once and the packs parsing with the firmware's parser;plan,global_capand 401 reasons;voices.tsvvoices accepted, and every preset'svoice_forvoice present;id;character_pack.py,daemon/src/fixtures/character/holds three PCM lines (odd lengths included) and thepack.binthattools/character_pack.pybuilt from them. The daemon's pack must match it byte for byte. A checked-in fixture keepscargo testindependent of Python, and it pins the format: a drift on either side shows up as a diff.Follow-ups in the second commit:
GET /v1/characterslists made Characters: id, name, base, voice, lines, andcomplete. Starting a job removes the old packs, socompletealways matches the lines the Character has now.voice_forknows made Characters. When the box reports a made Character's id, the reply uses the voice from its manifest. This needs the App to keep the made Character'sidas the pack id.failedwith reasoninternal, throughcatch_unwind. A lock left poisoned by the panic doesn't stop the next job.Not done here: the App UI (#184).
Closes #183
🤖 Generated with Claude Code