镜像站点 · 本页由第三方 GitHub 只读镜像提供,非 GitHub 官方站点,不接受任何登录或凭据输入。前往 github.com
Skip to content

Input formats for translation and language detection #60

Open

Description

@tomayac

While the spec doesn't seem to say anything about supported formats, in practice, inputting HTML seems to work just fine (and surprisingly fine even) for translations:

const translator = await Translator.create({
  sourceLanguage: 'en',
  targetLanguage: 'es',
});

await translator.translate('<p>Hello, or should I say <strong>good morning</strong>?</p>');
// '<p>Hola, o debería decir <strong>Buenos días</strong>?</p>'

However, the same can't be said for language detection:

const languageDetector = await LanguageDetector.create();
await languageDetector.detect('<strong>Guten Morgen</strong>');
/*
[
  {confidence: 0.4321225881576538, detectedLanguage: 'en'},
  {confidence: 0.20436188578605652, detectedLanguage: 'de'}, // 👈 Correct
  …
]
*/

Test-wise stripping the HTML from the input string correctly results in the language to be detected as German.

Do we need something like SummarizerFormat but for the Translator and Language Detector APIs to, for example, set expectations that corresponding words like the <strong>good morning</strong> would also be contained in the output (<strong>Buenos días</strong>) and to make sure the developer doesn't need to do an innerText dance to strip HTML formatting for language detection?

The three to-be-supported formats ideally would be the same as for the Writing Assistance APIs, that is, plain text and Markdown.

As a developer, I'd also wish for direct HTML support, as this avoids a to-Markdown dance, which may lose styling like classes that were in the original HTML.

Activity

  1. domenic commented on Sep 13, 2025

    @domenic
    Collaborator

    It'd be neat if we could mandate that all implementations support HTML and Markdown. In particular if Chrome could fix their language detection.

    But otherwise, I agree that a supported formats input at the spec level is probably the way to solve this.

  2. tomayac commented on Jan 27, 2026

    @tomayac
    Author

    Some good discussion with @jakearchibald over on mozilla/standards-positions#1015 (starting at mozilla/standards-positions#1015 (comment)) about this feature request.

    One idea would be to add a mimeType parameter to the options bag that would allow the API to enter into a safe mode where it sanitizes when the input is HTML. If developers send HTML without the proper MIME type, the API could escape the HTML automatically in such cases to make it harmless. Another option would be to simply use a DOM tree as the input. In all cases proper sanitizing would be needed, but we have the Sanitizer API now.

  3. jakearchibald commented on Jan 27, 2026

    @jakearchibald

    In all cases proper sanitizing would be needed,

    That shouldn't be the case if the transform is DOM-to-DOM. We would need to specify which content is expected to be handled by the translator, but otherwise it shouldn't create new elements, change element types, or change attribute values that are not intended to be human-readable.

  4. sandstrom commented on Jan 27, 2026

    @sandstrom

    Just a small data point from a developer.

    In our existing translation pipeline using LLMs, we have issues with interpolation (similar to HTML tags).

    Something like hello world #{count} might translate as Hallo Welt #{wortzahl} or even just Hallo Welt {wortzahl} (broken syntax). This is an issue with variable interpolation, but an LLM would have the same problem with HTML tags too.

    This could be left to the developer to cleanup afterwards, or handled by the browser. But good if the spec is clear on what guarantees are given with regards to html tags, i.e. does it guarantee that tags or might them be broken.

  5. jakearchibald commented on Jan 27, 2026

    @jakearchibald

    Yeah, that's a good point. I'm hoping that we could define a system where if the system was fed the DOM:

    <p>hello world <span class="count">0</span></p>

    …then it would know not to change the class attribute value, although it may change title attribute values. If we would have it preserve the span element, even better.

    But the important thing is we define the expectations, so the result is interoperable, even if the human language part of the translation is subjective.

  6. tomayac commented on Jan 27, 2026

    @tomayac
    Author

    although it may change title attribute values.

    That's a good point. Other attributes like aria-label come to mind, too. There's likely someone (you, @jakearchibald?) who knows by heart all the ones that would qualify.

  7. jakearchibald commented on Jan 27, 2026

    @jakearchibald

    I don't know them off the top of my head, but it should be an allow-list defined by the spec.

    There are some tricky edge cases where content is displayed to the user but isn't in the DOM tree. Such as input values and pseudo elements. I guess shadow DOM would need to be taken into consideration too, but there are patterns for that already.

  8. xM8WVqaG commented on Jan 27, 2026

    @xM8WVqaG

    (this is also a reply to mozilla/standards-positions#1015, as this line of discussion appears to have migrated to this issue).

    One idea would be to add a mimeType parameter to the options bag that would allow the API to enter into a safe mode where it sanitizes when the input is HTML. If developers send HTML without the proper MIME type, the API could escape the HTML automatically in such cases to make it harmless. Another option would be to simply use a DOM tree as the input. In all cases proper sanitizing would be needed, but we have the Sanitizer API now.

    I like the idea of setting the mimeType to text/html might make the translator behave differently, but IMO automatically doing any transformation to the input when the mimetype is set to text/plain would be unhelpful and confusing. If I tell the API to treat my input as plain text it should do just that. What happens if my input happens to include text that looks like HTML? Like the string "Is Foo / Bar > Alice & Bob?", it would be strange to have the response HTML encoded. I might be outputting the API response into a form field rather than injecting it into the DOM where the escaped characters wouldn't be unescaped and rendered.

    If input needs to be sanitised before it can be translated then developers should have the tools to do that before calling the Transformation API, rather than making assumptions on the "simple" text/plain code path.

  9. reillyeon commented on Jun 2, 2026

    @reillyeon
    Collaborator

    The fact that browsers have built-in page translation features seems to indicate that "translate the human-readable content of the DOM without changing the machine-readable content" is a solved problem and is what we want here. As I see it there would be two versions of this API: one which is string-to-string and can be used for general-purpose translation of human-readable text and one which is (HTMLElement or TrustedHTML)-to-TrustedHTML which is used for translating content that intended to be used with an HTML sink. We can't stop developers from passing HTML to the text-to-text API but we can provide a safe alternative which, by integrating with Trusted Types, would be easier to use.

  10. sandstrom commented on Jun 3, 2026

    @sandstrom

    Another approach to solve the hassle of html in translations, might be to just raise an exception if any <, >, & etc character is detected. And let developers clean them out ahead of time (a simple fix is to replace them with unicode-equivalents).

    That would fairly clearly signal that it's not supposed to be used for translating raw HTML, thereby side-stepping the security issues around that use-case.

    I think in practice, translating raw HTML isn't a major use-case anyway.

  11. toreini commented on Jun 4, 2026

    @toreini
    Collaborator

    there have been some discussions with @nordzilla which might be good to have his opinion here.

  12. nordzilla commented on Jun 4, 2026

    @nordzilla

    @toreini thanks for the ping. I'm catching up on this thread.


    @tomayac

    although it may change title attribute values.

    That's a good point. Other attributes like aria-label come to mind, too. There's likely someone (you, @jakearchibald?) who knows by heart all the ones that would qualify.

    @jakearchibald
    I don't know them off the top of my head, but it should be an allow-list defined by the spec.

    There are some tricky edge cases where content is displayed to the user but isn't in the DOM tree. Such as input values and pseudo elements. I guess shadow DOM would need to be taken into consideration too, but there are patterns for that already.

    There are some attributes that are defined as translatable by the HTML spec:

    This list is non-exhaustive. It says:

    "Other specifications may define other attributes that are also translatable attributes. For example, ARIA would define the aria-label attribute as translatable."

    The ARIA spec does define its own translatable attributes here:

    Firefox attempts to abide by these specs, and its implementation at the time of writing is here:


    In general, I see value in having both a plain-text API and a DOM-to-DOM API.

    The former is much more straightforward, and will likely be sufficient for a vast number of use cases.

    However, I share the concern that if a plain-text API is the only API that exists, then it opens the door to be used in alarming ways with no reasonable alternative, such as this example that Jake brought up in another thread.

  13. toreini commented on Aug 19, 2026

    @toreini
    Collaborator

    Proposed resolution / Call for consensus

    Thanks all for the discussion here and in mozilla/standards-positions#1015. We seem to be circling because this issue bundles several independent questions, and comments tend to answer different ones. This comment tries to (a) separate them, (b) agree evaluation criteria, and (c) propose a concrete set of decisions to react to in separate issues. If there are no sustained objections by 1 Month, I'll land these as provisional and we'll iterate via PR.

    Provisional / non-blocking: interpolation-placeholder preservation (@sandstrom) is not a v1 guarantee for free-text input; DOM-to-DOM naturally protects real tags, but placeholder tokens embedded in text are a documented known limitation for now.

    Editorial note: this is a proposal for the group to shoot at, not a decision. Please object explicitly to any decision (explictely mentioned in the bottom of this comment, as separate threads).

    Use cases (inferred from this thread)

    1. Translate a rich-text snippet while preserving inline structure (e.g. <strong>, links) and author intent (class, id, aria-*).
    2. Translate user-generated / untrusted content without creating an injection sink.
    3. Detect the language of a string that may contain markup, without the developer doing an innerText dance.
    4. Don't damage interpolation placeholders (e.g. #{count}): raised by @sandstrom as a real LLM failure mode that also applies to tags.

    Evaluation criteria

    • Determinism & interop: behavior is defined, not "whatever the model tolerates."
    • Safety: the design does not add a new injection surface.
    • Preserves author intent: non-human-readable attributes and structure survive.
    • Simplicity: smallest thing that meets the use cases (avoid scope creep).
    • Feature-detectable: authors can detect support and fall back.
    • Consistency with the Writing Assistance APIs.

    What I need from reviewers

    Here are the questions we're actually deciding (derived from the threat). I'd like us to resolve these in order and separately, rather than voting on a whole API shape at once.

  14. sushraja-msft commented on Aug 31, 2026

    @sushraja-msft

    On the topic of supporting HTML in language detection.

    In the case of Edge, language detection performs preprocessing that removes tags like <,> so for the example
    <strong>Guten Morgen</strong>, we do detect German 75%.
    https://microsoftedge.github.io/Demos/built-in-ai/playgrounds/languagedetector-api/

    However, the presence of HTML tags can skew language detection especially when the tag name is valid English. For example - <strong>Guten Morgen</strong><strong></strong><strong></strong><strong></strong> is classified as English.
    <div>Guten Morgen</div><div></div><div></div><div></div> is classified as German.

    For translation I agree there is a primitive that is missing in the API to represent a sequence of text in the same translation context that needs to be translated. My issue #85 is asking about collection of text with different translation context which is a counterpart to this.

    For input text like I ran <b>out</b> of time., without this primitive a web developer is left having to translate each chunk independently resulting in

    translate("I ran ") → "Ich rannte "
    translate("out") → "hinaus"
    translate(" of time.") → " der Zeit."

    instead of "Mir ging die Zeit aus."

    Therefore, it does seem to me that we should support HTML as input type for both APIs where the browser performs requisite preprocessing/post processing, to retain the words and separators in context.

    Now thinking about this a bit broader for a use case where a web developer wants to translate markdown
    Please turn off the light.
    the same problems as with HTML reappear.

    So instead of supporting HTML as input, I think accepting a collection of strings may be a better choice in this case. I did want to use a collection of strings as the API shape for batched inputs, if we go down this path - we need to figure out how to represent these two concepts at the API level - Sequence of same context text (processed together for semantic context), Sequence of independent context text (batched for performance).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions