garrytan/gstack · warning · Error
Invalid CSS property name: ${property}. Only letters and hyp
Error message
Invalid CSS property name: ${property}. Only letters and hyphens allowed. What it means
Thrown by `browse style` when the property name fails the regex `/^[a-zA-Z-]+$/`. The command only accepts standard CSS property names composed of ASCII letters and hyphens (e.g. `color`, `background-color`, `font-size`). This guards the subsequent `modifyStyle` call which interpolates the property into a CSS rule string, preventing injection of arbitrary CSS or JS-triggers via the property slot. Note CSS custom properties (`--my-var`) are NOT accepted because the regex requires at least one letter and allows hyphens but the leading `--` form has no letter before the first hyphen segment — actually `--my-var` contains letters so it PASSES; the real rejection targets underscores, digits-leading tokens, and non-ASCII.
Source
Thrown at browse/src/write-commands.ts:780
case 'style': {
// style --undo [N] → revert modification
if (args[0] === '--undo') {
const idx = args[1] ? parseInt(args[1], 10) : undefined;
await undoModification(page, idx);
return idx !== undefined ? `Reverted modification #${idx}` : 'Reverted last modification';
}
// style <selector> <property> <value>
const [selector, property, ...valueParts] = args;
const value = valueParts.join(' ');
if (!selector || !property || !value) {
throw new Error('Usage: browse style <sel> <prop> <value> | style --undo [N]');
}
// Validate CSS property name
if (!/^[a-zA-Z-]+$/.test(property)) {
throw new Error(`Invalid CSS property name: ${property}. Only letters and hyphens allowed.`);
}
// Validate CSS value — block data exfiltration patterns
const DANGEROUS_CSS = /url\s*\(|expression\s*\(|@import|javascript:|data:/i;
if (DANGEROUS_CSS.test(value)) {
throw new Error('CSS value rejected: contains potentially dangerous pattern.');
}
const mod = await modifyStyle(page, selector, property, value);
return `Style modified: ${selector} { ${property}: ${mod.oldValue || '(none)'} → ${value} } (${mod.method})`;
}
case 'cleanup': {
// Parse flags
let doAds = false, doCookies = false, doSticky = false, doSocial = false;
let doOverlays = false, doClutter = false;
let doAll = false;
View on GitHub (pinned to 94993f7401)
Solutions
- Use the CSS kebab-case property name: `background-color`, not `backgroundColor` or `background_color`.
- Ensure the property contains only ASCII letters and hyphens — no underscores, digits at the start, or punctuation.
- Custom properties (`--my-var`) are accepted as they contain letters and hyphens.
- If you need to set a property the regex rejects, verify it is a real CSS property; non-standard or invented names are intentionally blocked.
Example fix
// before await runBrowseCommand(['style', 'body', 'background_color', 'red']); // after await runBrowseCommand(['style', 'body', 'background-color', 'red']);
Defensive patterns
Strategy: validation
Validate before calling
function validateCssProperty(property: string): void {
if (!/^[a-zA-Z-]+$/.test(property)) {
throw new Error(`Invalid CSS property name: ${property}. Only ASCII letters and hyphens allowed.`);
}
} Type guard
function isCssPropertyName(s: string): boolean {
return /^[a-zA-Z-]+$/.test(s);
} Prevention
- Use CSS kebab-case property names (background-color, not background_color).
- Avoid underscores, leading digits, and non-ASCII in property names.
- Custom properties (--my-var) are accepted since they contain letters and hyphens.
When it happens
Trigger: Passing `background_color` (underscore not allowed), `backgroundColor` (camelCase — no hyphen, but the letters pass... actually camelCase like `backgroundColor` matches `[a-zA-Z-]+` since it is all letters with no hyphen, so it PASSES the regex but may not be a valid CSS property in that form); `1color` (leading digit rejected); `color!` (punctuation rejected); a property name with a trailing space that survived trim.
Common situations: User passes a JavaScript CSSOM camelCase name (`backgroundColor`) instead of the CSS kebab-case (`background-color`) — note this passes the regex but `modifyStyle` may still mis-handle it; user passes a vendor-prefixed property with an underscore typo; an LLM emits `--custom` with a leading space; a property name copied from a minified CSS source contained an escape character.
Related errors
- Usage: browse style <sel> <prop> <value> | style --undo [N]
- Invalid skill name "${name}". Must be lowercase letters/digi
- Invalid file path in stageSkill: "${relPath}".
- State name must be alphanumeric (a-z, 0-9, _, -)
- Usage: browse viewport [<WxH>] [--scale <n>] (e.g. 375x812,
AI-assisted analysis of garrytan/gstack@94993f7401 (2026-08-12).
Data as JSON: /api/errors/ad9d8ef7511b82ff.
Report an issue: GitHub.