Migrating from Jev
Use this checklist before switching traffic:
- Set
TYPESAFE_BASE_URLto your Laya Cloud origin andTYPESAFE_API_KEYto a Laya key. Keep your existingsystemOneorsystem_onecall. - Use
jev-latest(the SDK default),jev-preview,jev-1.13.0, orlaya-latestfor language routing. English resolves tolaya-0.3.5; detected non-English resolves tolaya-multilingual-0.3.9. To select a checkpoint explicitly uselaya-0.3.5,laya-multilingual, orlaya-multilingual-0.3.9. See models. - Measure every question's state room. English has a 512-token sequence; the exact room is
511 − len(head + options sequence)for that question. The simple choice and noul questions in the plan leave 476 state tokens. Multilingual has a 1024-token window and about 951–990 state tokens of room. Longer instructions and options reduce either limit. - Split long state into smaller, self-contained chunks and send only the relevant chunk per call. Laya Cloud rejects state that would truncate; it never silently cuts it.
- Keep each call at or below 32 questions and the selected model's processed-token cap: 3,500 English or 6,000 multilingual. The processed cost is
number of questions × longest per-question Laya sequence length, so many questions with long states hit the cap sooner. A 32-question call can exceed the SDK's 10-second default timeout on a busy CPU worker; prefer smaller batches. - Handle 402 monthly free allowance exhaustion by checking
/app/usageand waiting for the UTC reset or contacting support. Jev does not have this response. - Handle 429 account rate/in-flight limits and 529 worker busy/startup with
Retry-Afterandretry-after-ms; branch onx-laya-error-code. The SDK retries these by default, so set an overall deadline. - Compare outputs: Laya strips
actionand noulconfidence. Multilingual confidence is uncalibrated, and its English quality was lower in a 12-case check. The two checkpoints use different tokenizers, so token counts and state limits differ. The model card evaluates about 50 languages; its “100+” claim is unverified. - Pin SDK versions while migrating: Python
typesafe-sdk==0.7.1; JavaScript@typesafe-ai/[email protected]. Roll back by restoring the previous Jev base URL and Jev key; keep keys separate.
The snippet below uses the repository's laya_compat counter and the model tokenizer only; it does not load torch or model weights. Run it from the repository root after uv sync --project worker. Downloading the tokenizer requires Hugging Face access the first time.
import sys
sys.path.insert(0, "worker")
from huggingface_hub import hf_hub_download
from runtime import MODEL_ID, REVISION, Tokenizer
from laya_compat import inspect_request
tokenizer = Tokenizer(hf_hub_download(MODEL_ID, "tokenizer/tokenizer.json", revision=REVISION))
state = "I was billed twice for March."
questions = {
"department": {"type": "choice", "instructions": "Which team should handle this?", "criteria": {"billing": "Payment issues", "technical": "Bugs"}},
}
for qid, q in questions.items():
_, errors = inspect_request(tokenizer, "word " * 2500, {qid: q})
room = next(e["m"] for e in errors if e["code"] == "state_too_long")
print(qid, "state room:", room)
counts, errors = inspect_request(tokenizer, state, questions)
print("processed tokens:", counts.processed, "validation errors:", errors)
Try the migrated request locally:
curl --fail --silent "$TYPESAFE_BASE_URL/v1/systemone" -H "Authorization: Bearer $TYPESAFE_API_KEY" -H 'Content-Type: application/json' -d '{"model":"jev-latest","state":"I was billed twice for March.","questions":{"department":{"type":"choice","instructions":"Which team should handle this?","criteria":{"billing":"Payment issues","technical":"Bugs"}}}}' | python3 -c 'import json,sys; r=json.load(sys.stdin); assert r["model"] == "laya-0.3.5" and "department" in r["answers"]'