{"record":{"id":"c426e6e323b86656","repo":"SeleniumHQ/selenium","slug":"expected-exactly-one-where-in-bzl-file-name-f","errorCode":null,"errorMessage":"Expected exactly one {where} in {BZL_FILE.name}, found {n}","messagePattern":"Expected exactly one (.+?) in (.+?), found (.+?)","errorType":"exception","errorClass":"RuntimeError","httpStatus":null,"severity":"error","filePath":"scripts/update_cddl.py","lineNumber":155,"sourceCode":"    return json.loads(r.data)[\"sha\"]\n\n\ndef existing_repo_names(content):\n    return set(re.findall(r'\\(\\s*\"([a-z0-9_]+)\"\\s*,\\s*\"[^\"]+\\.cddl\"', content))\n\n\ndef render_files(var, entries):\n    lines = [f\"{var} = [\"]\n    for name, filename, sha256 in entries:\n        lines.append(f'    (\"{name}\", \"{filename}\", \"{sha256}\"),')\n    lines.append(\"]\")\n    return \"\\n\".join(lines)\n\n\ndef sub_once(content, pattern, replacement, where):\n    content, n = re.subn(pattern, replacement, content, flags=re.S)\n    if n != 1:\n        raise RuntimeError(f\"Expected exactly one {where} in {BZL_FILE.name}, found {n}\")\n    return content\n\n\ndef update_pin(commit, cddl_entries, dfns_entries, bidi_commit, bidi_sha256):\n    content = BZL_FILE.read_text()\n\n    # Anchor so this does not also match the tail of `_BIDI_SPEC_HTML_COMMIT = \"…\"`.\n    content = sub_once(content, r'(?<![A-Z_])_COMMIT = \"[0-9a-f]+\"', f'_COMMIT = \"{commit}\"', \"_COMMIT assignment\")\n    content = sub_once(\n        content, r\"_CDDL_FILES = \\[.*?\\n\\]\", lambda _: render_files(\"_CDDL_FILES\", cddl_entries), \"_CDDL_FILES block\"\n    )\n    content = sub_once(\n        content, r\"_DFNS_FILES = \\[.*?\\n\\]\", lambda _: render_files(\"_DFNS_FILES\", dfns_entries), \"_DFNS_FILES block\"\n    )\n    content = sub_once(\n        content,\n        r'_BIDI_SPEC_HTML_COMMIT = \"[0-9a-f]+\"',\n        f'_BIDI_SPEC_HTML_COMMIT = \"{bidi_commit}\"',","sourceCodeStart":137,"sourceCodeEnd":173,"githubUrl":"https://github.com/SeleniumHQ/selenium/blob/aa36b38e696a0909e973bdf5e2f9031ffe842c4b/scripts/update_cddl.py#L137-L173","documentation":"Raised by sub_once() in scripts/update_cddl.py when a regex substitution in common/webref_cddl.bzl does not match exactly once. The function uses re.subn() with re.S (dotall) and asserts n == 1. If n == 0, the expected pattern (e.g., _COMMIT assignment, _CDDL_FILES block, _DFNS_FILES block, _BIDI_SPEC_HTML_* assignments) is missing from the .bzl file. If n > 1, there are duplicate patterns and the script cannot determine which to replace.","triggerScenarios":"Running update_cddl.py after the webref_cddl.bzl file was manually edited, reformatted, or restructured such that the anchored regex patterns no longer match. Also triggered if someone added a duplicate variable assignment, or if the file was regenerated from scratch without the expected structure.","commonSituations":"Manual edits to webref_cddl.bzl that changed variable names, formatting, or block structure; merge conflict resolution that altered the file; the .bzl file was deleted or partially truncated; a variable was renamed (e.g., _COMMIT to _WEBREF_COMMIT) making the regex stale.","solutions":["Inspect common/webref_cddl.bzl to verify the expected patterns exist: _COMMIT = \"...\", _CDDL_FILES = [...], _DFNS_FILES = [...], _BIDI_SPEC_HTML_COMMIT = \"...\", _BIDI_SPEC_HTML_SHA256 = \"...\".","If a variable was renamed, update the regex patterns in sub_once() calls in update_cddl.py to match the new names.","If the file is corrupted, restore it from git (git checkout common/webref_cddl.bzl) and re-run.","Ensure there is exactly one occurrence of each pattern — remove any duplicates."],"exampleFix":"null","handlingStrategy":"validation","validationCode":"import re\n\ncontent = open('common/webref_cddl.bzl').read()\nfor label, pattern in [\n    ('_COMMIT', r'(?<![A-Z_])_COMMIT = \"[0-9a-f]+\"'),\n    ('_CDDL_FILES', r'_CDDL_FILES = \\[.*?\\n\\]'),\n    ('_DFNS_FILES', r'_DFNS_FILES = \\[.*?\\n\\]'),\n]:\n    matches = re.findall(pattern, content, flags=re.S)\n    if len(matches) != 1:\n        print(f'WARNING: {label} has {len(matches)} matches, expected 1')","typeGuard":"null","tryCatchPattern":"null","preventionTips":["Do not manually reformat webref_cddl.bzl — the update script relies on specific patterns.","Run update_cddl.py regularly so the .bzl file stays in sync with the script's expectations.","If you must edit the .bzl, preserve the variable names and block structure the regexes expect."],"tags":["selenium","build-script","update-cddl","regex","bazel","ci","file-structure"],"backgroundTag":null,"analyzedSha":"aa36b38e696a0909e973bdf5e2f9031ffe842c4b","analyzedAt":"2026-08-14T02:32:32.244Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}