Skip to content
CodeLifter Forum

How do I stop a coding assistant from using innerHTML?

Staff answerWritten by CodeLifter editors · 0 replies

Short answer

Name the ban and its replacement in the prompt itself, for example "write text with textContent, never innerHTML", and say how to build structure instead. Repeat the rule in the rules file your tool reads, such as AGENTS.md, then back it with a lint rule, because an instruction alone guarantees nothing. Search every answer before you paste it.

CiteCodeLifter Forum, "How do I stop a coding assistant from using innerHTML?", https://forum.codelifter.com/posts/how-do-i-stop-a-coding-assistant-from-using-innerhtml/, accessed 2026-10-16.
Written by CodeLifter editors · Staff, CodeLifter ·
  1. Staff, CodeLifter ·

    Why innerHTML is the one to ban

    Assigning a string to innerHTML parses that string as HTML. MDN's innerHTML reference calls the property "probably the most common vector for cross-site scripting (XSS) attacks", where unsafe strings from a user reach the DOM without being sanitized. The same page gives the plain alternative: Node.textContent should be used when you know the content should be plain text, because that prevents it being parsed as HTML.

    Most snippets an assistant writes for a small page only need to show text, set an attribute or add an element. None of those needs HTML parsing, so a ban costs you nothing and removes a whole class of bug.

    The prompt lines that do the work

    A bare "don't use innerHTML" leaves the assistant to guess what to do instead. Name the replacement for each job. These lines are copied from the CodeLifter prompt pages, where the editors tested the code each prompt asks for:

    Job in the code Prompt line What it produces
    Show changing text "Write with textContent, never innerHTML" (mouse position) el.textContent = value
    Add a link or other markup "build the link with createElement, never innerHTML" (random quote generator) document.createElement("a"), then set href and text
    Set an image "Set the large image's src and alt as properties, never by writing HTML" (image popup) img.src = url; img.alt = text

    Two things make these lines work better than a general warning. First, each one pairs the ban with the method to use, which is what the Gemini prompting guide means when it says you can tell the model what to do and not to do. Second, they sit next to the task they apply to, so the instruction is still in view when the model writes that part.

    Close the side doors too. outerHTML, insertAdjacentHTML() and document.write() parse strings in the same way, and Mozilla's lint plugin, below, treats them as the same family. Add one line such as "Do not use innerHTML, outerHTML, insertAdjacentHTML or document.write" if you are prompting for anything larger than a snippet.

    The CodeLifter prompts have not been run against a named assistant, so treat every line here as a request that you still verify. For how a full prompt is put together, see How to write a coding prompt.

    Put the rule where every session reads it

    Typing the same line into every chat is easy to forget. Most coding agents read a standing rules file from the repository.

    1. Create AGENTS.md in the root of your repository.

    2. Add a short section, for example:

      ## Code
      - Write text with textContent, never innerHTML.
      - Build elements with createElement; set attributes as properties.
      - Do not use outerHTML, insertAdjacentHTML or document.write.
      
    3. If your tool reads a different file by default, point it at the same rules. The file names differ by tool:

    Tool File it reads
    GitHub Copilot .github/copilot-instructions.md, and AGENTS.md
    Cursor .cursor/rules, and AGENTS.md
    Claude Code CLAUDE.md, or AGENTS.md when there is no CLAUDE.md
    Gemini CLI GEMINI.md, or AGENTS.md once set as context.fileName in .gemini/settings.json
    Aider CONVENTIONS.md loaded with aider --read CONVENTIONS.md

    GitHub documents that the nearest AGENTS.md in the directory tree takes precedence, so a file in a subfolder can override the root one. The full list, with links to each vendor's page, is in the coding agents directory.

    Make it fail the build

    A rule in a Markdown file is advice. A lint error is a gate. Mozilla publishes eslint-plugin-no-unsanitized, which disallows assignments to innerHTML and calls such as insertAdjacentHTML() unless the value goes through an escaping function.

    1. Install it: npm install --save-dev eslint-plugin-no-unsanitized

    2. In eslint.config.mjs, add the recommended config (adapted from the README):

      import nounsanitized from "eslint-plugin-no-unsanitized";
      export default [nounsanitized.configs.recommended];
      
    3. Run npx eslint . before each commit, or in CI.

    Know its limits. The README lists foo.innerHTML = 5 and a fixed string literal as allowed, because neither can carry user input. If you want a total ban, add a plain search as well:

    grep -rnE "innerHTML|outerHTML|insertAdjacentHTML|document\.write" src/
    

    An empty result means none of those names appears in src/.

    When you really need markup

    Sometimes you are rendering HTML from a source you control, such as your own Markdown converter. MDN's advice for that case is to sanitize the input and assign a TrustedHTML object rather than a string, with Trusted Types enforced by a Content Security Policy. If you go that way, say so in the prompt and name the sanitizer, or the assistant will pick one for you. Otherwise keep the ban.

    Check every answer

    1. Search the answer for the four names above before you paste it.
    2. Where you find one, ask for the replacement by name: "Rewrite this with textContent and createElement."
    3. Run the lint rule and fix what it reports.
    4. Test the result with the keyboard as well; the keyboard prompting thread has the lines for that.

    If you run a local model, the same checks apply, and the local models thread covers what differs there.

    0
    ReplyLink

Write a reply

Plain text or simple Markdown. Links are nofollow. Your email is never shown.