DenverCoder1/github-readme-streak-stats · error · AssertionError

Invalid color: " . $color

Error message

Invalid color: " . $color

What it means

convertHexColor() accepts 3/4/6/8-digit hex color strings and throws AssertionError for anything else. This library throws it when a color value passed into the SVG color-conversion pipeline is not valid hex notation.

Solutions

  1. Convert the input color to 6-digit hex format (e.g. '#ff0000') before passing it in
  2. Ensure the color is a plain hex string without '#' being stripped by URL encoding
  3. Add pre-validation that matches /^[0-9a-fA-F]{3,4}$|^[0-9a-fA-F]{6}$|^[0-9a-fA-F]{8}$/
  4. If using named colors, map them to hex first

Example fix

// before
convertHexColor("red");
// after
convertHexColor("#ff0000");
Defensive patterns

Strategy: validation

Validate before calling

if (!preg_match('/^(?:[0-9a-fA-F]{3,4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$/', $color)) { throw new InvalidArgumentException("Not a hex color: $color"); }

Type guard

function isHexColor(?string $c): bool { return $c !== null && preg_match('/^(?:[0-9a-fA-F]{3,4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$/', $c) === 1; }

Prevention

When it happens

Trigger: Passing a named CSS color (e.g. 'red'), an 'rgb(...)' string, a color missing the '#' prefix, an empty string, or a hex string of any length other than 3, 4, 6, or 8 into convertHexColors/convertHexColor.

Common situations: Users supplying custom theme colors via query parameters or config that aren't hex; copying colors from design tools that output rgb() or hsl() notation; truncating a hex string by mistake.

Understand the failure class

Background: "Invalid ... format", "must be in format X", "does not look like a ..." — invalid argument format errors across CLI tools and libraries — this error's family across 17 libraries.

Related errors


AI-assisted analysis of DenverCoder1/github-readme-streak-stats@70dd50f921 (2026-09-15). Data as JSON: /api/errors/217d43762a62965f. Report an issue: GitHub.

Appendix: source

Thrown at src/card.php:730

        $color = "{$chars[0]}{$chars[0]}{$chars[1]}{$chars[1]}{$chars[2]}{$chars[2]}";
    } elseif (strlen($color) === 4) {
        $chars = str_split($color);
        $color = "{$chars[0]}{$chars[0]}{$chars[1]}{$chars[1]}{$chars[2]}{$chars[2]}{$chars[3]}{$chars[3]}";
    }

    // convert to 6 digit hex and opacity
    if (strlen($color) === 6) {
        return [
            "color" => "#{$color}",
            "opacity" => 1,
        ];
    } elseif (strlen($color) === 8) {
        return [
            "color" => "#" . substr($color, 0, 6),
            "opacity" => hexdec(substr($color, 6, 2)) / 255,
        ];
    }
    throw new AssertionError("Invalid color: " . $color);
}

/**
 * Convert transparent hex colors (4/8 digits) in an SVG to hex 6 digits and corresponding opacity attribute (0-1)
 *
 * @param string $svg The SVG for the card as a string
 * @return string The SVG with converted colors
 */
function convertHexColors(string $svg): string
{
    // convert "transparent" to "#0000"
    $svg = preg_replace("/(fill|stroke)=['\"]transparent['\"]/m", '\1="#0000"', $svg);

    // convert hex colors to 6 digits and corresponding opacity attribute
    $svg = preg_replace_callback(
        "/(fill|stroke|stop-color)=['\"]#([0-9a-fA-F]{4}|[0-9a-fA-F]{8})['\"]/m",
        function ($matches) {
            $attribute = $matches[1];

View on GitHub (pinned to 70dd50f921)