iflytek/astron-agent · warning · ValueError
API requires Chinese (cn) as either source or target…
Error message
API requires Chinese (cn) as either source or target language. Current combination: {source_language} → {target_language} is not supported. What it means
The `validate_language_combination` model_validator (mode="after") enforces that at least one of source_language/target_language is Chinese ("cn"), because the underlying iFlytek translation API only supports pairs involving Chinese. `is_valid_language_pair` returning False triggers this ValueError, wrapped by pydantic into a ValidationError. The message shows the exact offending pair.
Solutions
- Route non-Chinese pairs to a different translation backend that supports them.
- For a pair like en→ja, translate in two hops through Chinese (en→cn then cn→ja) if acceptable quality-wise.
- Constrain the UI so target_language options depend on the chosen source (or vice versa) such that one side is always cn.
- Check pair validity client-side with the same rule (source=='cn' || target=='cn') before calling.
Example fix
// before
await translate({ text, source_language: 'en', target_language: 'ja' }); // rejected
// after
if (source !== 'cn' && target !== 'cn') {
const mid = await translate({ text, source_language: source, target_language: 'cn' });
return translate({ text: mid, source_language: 'cn', target_language: target });
}
return translate({ text, source_language: source, target_language: target }); Defensive patterns
Strategy: validation
Validate before calling
function isSupportedPair(source, target) {
return source === 'cn' || target === 'cn';
} Try / catch
try:
inp = TranslationInput(**payload)
except ValidationError as e:
if 'Chinese (cn)' in str(e):
return error_response('该翻译接口要求源语言或目标语言为中文(cn)', 400)
raise Prevention
- Constrain UI options so one side is always Chinese, or offer a pivot-translation path for non-Chinese pairs.
- Document the cn-involving-pair requirement wherever the endpoint is consumed.
- Validate the pair client-side with the same rule as the model validator.
When it happens
Trigger: Constructing TranslationInput with a pair like en→ja, fr→de, or any combination where neither side is "cn" — even when both codes are individually valid.
Common situations: Users pick two non-Chinese languages in the UI; generic translation clients reuse the endpoint for arbitrary pairs; routing all traffic to this API without checking pair support first.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- Invalid source language
- Invalid target language
- Translation text cannot be empty
- Translation text cannot exceed 5000 characters
- 21600
AI-assisted analysis of iflytek/astron-agent@5e758547a8 (2026-09-12).
Data as JSON: /api/errors/6a5bed05001dab60.
Report an issue: GitHub.
Appendix: source
Thrown at core/plugin/aitools/service/translation/translation_service.py:79
)
return value
@field_validator("source_language")
@classmethod
def validate_source_language(cls, value: str) -> str:
"""validate source language"""
if value not in VALID_LANGUAGE_CODES:
raise ValueError(
f"Invalid source language: {value}.\n"
f"Valid options: {list(VALID_LANGUAGE_CODES)}"
)
return value
@model_validator(mode="after")
def validate_language_combination(self) -> "TranslationInput":
"""Validate that at least one language is Chinese (cn)"""
if not is_valid_language_pair(self.source_language, self.target_language):
raise ValueError(
"API requires Chinese (cn) as either source or target language. "
f"Current combination: {self.source_language} → {self.target_language} "
"is not supported."
)
return self
@api_service(
method="POST",
path="/aitools/v1/translation",
query=None,
body=TranslationInput,
response=BaseResponse,
summary="Translate text from Chinese (cn) to other languages",
description="Translate text from Chinese (cn) to other languages",
tags=["public_cn"],
deprecated=True,
)View on GitHub (pinned to 5e758547a8)