plotly/plotly.js · warning
Invalid color specifier: "${cstr}". Defaulting to "#000"
Error message
Invalid color specifier: "${cstr}". Defaulting to "#000" What it means
plotly.js parses all color-like strings through culori-based `parse`. When the string cannot be converted to an RGB color, it warns 'Invalid color specifier' and falls back to black (#000). It exists because plotting silently using undefined colors is confusing; the warning points at the malformed input.
Source
Thrown at src/components/color/index.js:77
// 8-bit step first. Six decimals absorb the float error and still leave a
// genuine value such as 122.45 alone.
const snap01 = (v) => Math.round(v * 255e6) / 255e6;
const snap = (c) => ({ ...c, r: snap01(c.r), g: snap01(c.g), b: snap01(c.b) });
const formatRgb = (c) => culoriFormatRgb(snap(c));
const formatHex = (c) => culoriFormatHex(snap(c));
/**
* Parse a color specifier string and return it as a culori rgb color object.
*
* @param {*} cstr - Color specifier
* @param {Boolean} [silent] - Skip the warning, for callers that run per data point
* @return {Object} A culori rgb color ({ mode: 'rgb', r: _, g: _, b: _, alpha: _ })
*/
const parse = (cstr, silent) => {
const c = toColor(cstr);
if (!c) {
if (!silent && cstr != null) warn(`Invalid color specifier: "${cstr}". Defaulting to "#000"`);
return BLACK;
}
// `toRgb` omits alpha when it's 1; make sure it's added since we expect it
c.alpha ??= 1;
return c;
};
// TODO: rename to `rgbString` to better describe return value
/**
* Convert any color specifier to a normalized `rgb(r, g, b)` string.
* Force alpha to 1 so that it gets dropped in the result.
*
* @param {*} cstr - Color specifier
* @return {String}
*/
const rgb = (cstr) => formatRgb({ ...parse(cstr), alpha: 1 });
View on GitHub (pinned to 1d090e0b5f)
Solutions
- Log the cstr value in the warning and correct the offending data at its source.
- Use parse-silent-friendly inputs: hex (#rgb, #rrggbb, #rrggbbaa), rgb()/rgba()/hsl()/hsla() strings, or valid CSS named colors.
- Validate colors before assignment with a regex or the browser (e.g. assigning to a temporary element's style.color and comparing).
- Use a colorscale object/array for per-point coloring instead of raw strings from data.
- Guard optional attributes: only set color when the value is a non-empty string.
Example fix
// before
Plotly.restyle(gd, 'marker.color', trace.color || 'auto'); // 'auto' is invalid
// after
const color = /^#([0-9a-f]{3,8})$/i.test(trace.color || '') ? trace.color : '#000000';
Plotly.restyle(gd, 'marker.color', color); Defensive patterns
Strategy: validation
Validate before calling
function isValidColor(c) {
if (typeof c !== 'string') return false;
const s = new Option().style;
s.color = '';
s.color = c;
return s.color !== '';
} Type guard
function isColorString(v) {
return typeof v === 'string' && isValidColor(v);
} Try / catch
// plotly only warns (no throw), so prefer pre-validation
if (!isValidColor(color)) {
console.warn('rejecting bad color', color);
color = '#000000';
}
Plotly.restyle(gd, 'marker.color', color); Prevention
- Only pass hex, rgb()/rgba()/hsl()/hsla() strings, or valid CSS named colors.
- Never trust colors from user input or APIs — validate before assignment.
- Test suspicious colors with a temporary DOM element's style.color round-trip.
- For per-point colors, prefer arrays of valid strings or a colorscale + cmin/cmax.
When it happens
Trigger: Setting any color attribute (marker.color, line.color, layout colorway, font color, colorscale stop values) to a string culori cannot parse — e.g. 'not-a-color', a misspelled keyword ('rebeccapurplee'), an out-of-gamut CSS4 color, an rgba() string with the wrong argument count, or a number where a string is expected.
Common situations: Colors coming from user data or API responses that were assumed valid; typos in CSS color names; using 'rgb(r,g,b)' with percentages mixed with numbers; passing a hex string missing the '#' or with 5 digits.
Related errors
- Invalid GeoJSON type ${type}. Traces with locationmode *geoj
- Unrecognized full object edit value
- Circular Sankey diagrams do not support the "input" <type>.s
AI-assisted analysis of plotly/plotly.js@1d090e0b5f (2026-09-02).
Data as JSON: /api/errors/c8f6866e01c987e4.
Report an issue: GitHub.