denoland/deno · error · Error

Multiple selectors not allowed here

Error message

Multiple selectors not allowed here

What it means

Thrown by popSelector() in cli/js/40_lint_selector.js when a finished selector group must attach to the last node of the enclosing selector, but that node is not one of the node types that accept selector arguments (:nth-child, :has, :is, :not). It is the parser rejecting a selector list placed after an ordinary node.

Source

Thrown at cli/js/40_lint_selector.js:789

    const prev = /** @type {Selector} */ (stack.at(-1));
    if (prev.length === 0) {
      throw new Error(`Empty selector`);
    }

    const node = prev.at(-1);
    if (node === undefined) {
      throw new Error(`Empty node`);
    }

    if (node.type === PSEUDO_NTH_CHILD) {
      node.of = sel;
    } else if (
      node.type === PSEUDO_HAS || node.type === PSEUDO_IS ||
      node.type === PSEUDO_NOT
    ) {
      node.selectors.push(sel);
    } else {
      throw new Error(`Multiple selectors not allowed here`);
    }
  }
}

const TRUE_FN = () => {
  return true;
};

/**
 * @param {Selector} selector
 * @returns {MatcherFn}
 */
export function compileSelector(selector) {
  /** @type {MatcherFn} */
  let fn = TRUE_FN;

  for (let i = 0; i < selector.length; i++) {
    const node = selector[i];

View on GitHub (pinned to 89f33cbef2)

Solutions

  1. Use a grouping pseudo for the list: wrap it in :is(...) or :has(...)
  2. Split the visitor key into one key per selector and share the callback via a helper

Example fix

// before
"VariableDeclarator > (ArrayPattern, ObjectPattern)"(node) {},

// after
"VariableDeclarator > :is(ArrayPattern, ObjectPattern)"(node) {},
Defensive patterns

Strategy: validation

Validate before calling

function groupingOnlyInPseudos(sel) {
  // reject bare parenthesized groups and lists attached to plain nodes
  if (/(?<![a-z-]):?(?:[A-Za-z]+)?\s*\([^()]*,/.test(sel) && !/:\w+\(/.test(sel)) {
    throw new Error(`selector list must sit inside :is()/:has()/:not(): '${sel}'`);
  }
}

Prevention

When it happens

Trigger: Grammar that puts a comma-separated group where only a plain selector chain is legal — e.g. malformed nesting like "Foo > (Bar, Baz)" or a selector group landing after an element/attribute/relation node. Bounded constructs like :has()/:is()/:not()/:nth-child() accept the group; anything else throws.

Common situations: Over-nesting selectors assuming parenthesized grouping works like CSS; malformed hand-written compound selectors after an edit; selector text that survived a bad copy-paste with stray commas.

Related errors


AI-assisted analysis of denoland/deno@89f33cbef2 (2026-08-16). Data as JSON: /api/errors/fcffde37c8fb4a7e. Report an issue: GitHub.