Code Quality Help

SVG Icon Generation and Maintenance Mechanism

1. Purpose

This document describes the recommended mechanism for maintaining SVG icons in the Angular application.

The application uses dedicated Angular components to render icons. Each generated icon component contains an inline SVG template. The list of available icons is maintained in a central registry called ICON_REGISTRY.

The goal of this mechanism is to make icon maintenance predictable, repeatable, and safe:

  • analysts or designers can review and update SVG assets as regular files;

  • developers do not manually edit generated Angular icon components;

  • generated icon components and ICON_REGISTRY are always synchronized;

  • monochrome icons support application-level size and color control;

  • multicolor icons can preserve their original colors;

  • icon names remain stable and meaningful across the application.

2. Scope

This mechanism covers:

  • storing source SVG files in a dedicated project folder;

  • sharing SVG files with analysts or designers;

  • updating existing SVG icons;

  • adding new SVG icons;

  • removing obsolete SVG icons;

  • generating Angular icon components;

  • regenerating the central icon registry;

  • normalizing SVG size attributes;

  • handling monochrome and multicolor SVG files.

This mechanism does not cover:

  • runtime loading of SVG files from the assets folder;

  • dynamic icon loading from a backend service;

  • manual editing of generated icon component files;

  • automatic design approval of SVG content.

3. Current Icon Architecture

The application uses a component-based icon system.

Each icon is represented by a dedicated Angular standalone component.

Example structure:

src/app/shared/components/icons/ icon/ icon.component.ts icon.component.html icon.component.scss components/ icon-add/ icon-add.ts icon-add.html icon-delete/ icon-delete.ts icon-delete.html icons.ts

The file icons.ts contains the global registry of available icons and their names.

Conceptually:

export const ICON_REGISTRY = { add: IconAdd, delete: IconDelete, edit: IconEdit }; export type IconRegistryKey = 'add' | 'delete' | 'edit';

A common icon host component can use this registry to resolve and render the required icon by name.

Example usage:

<app-icon name="delete"></app-icon>

4. Target Process Overview

The project should contain a dedicated SVG source folder.

Recommended folder:

icons-source/

This folder is the source of truth for SVG icon files.

The generation script reads SVG files from this folder, removes previously generated icon components, creates new Angular components, and rebuilds ICON_REGISTRY.

High-level process:

  1. The developer provides the current SVG set to an analyst or designer.

  2. The analyst or designer reviews, modifies, adds, or removes SVG files.

  3. The developer places the approved SVG files into icons-source/.

  4. The developer runs the icon generation script.

  5. The script regenerates Angular components and the icon registry.

  6. The developer reviews generated changes and commits them.

5. Roles and Responsibilities

Role

Responsibility

Business Analyst / Designer

Reviews existing SVG files, updates SVG files, provides new SVG files with approved names.

Developer

Maintains the generation script, updates icons-source/, runs generation, verifies generated application changes.

Reviewer

Checks naming consistency, generated files, and visual correctness during pull request review.

CI/CD Pipeline

Optionally validates that generated icon files are up to date.

project-root/ icons-source/ add.svg delete.svg edit.svg logo.color.svg scripts/ generate-icons.js src/ app/ shared/ components/ icons/ icon/ icon.component.ts icon.component.html icon.component.scss components/ icon-add/ icon-add.ts icon-add.html icon-delete/ icon-delete.ts icon-delete.html icons.ts

7. Source Folder

7.1 Folder Location

The recommended folder is:

icons-source/

This folder should be located outside the Angular src/assets directory.

It should not be referenced by the Angular build configuration as an application asset.

The folder is used only by the generation script.

7.2 Source Folder Purpose

The icons-source/ folder is used for:

  • storing source SVG files;

  • exchanging icons between developers and analysts or designers;

  • maintaining stable icon names;

  • regenerating Angular icon components;

  • ensuring that the generated icon registry reflects the current SVG set.

The folder should be treated as the source of truth.

Generated Angular component files should be treated as derived artifacts.

8. Naming Rules

8.1 General Naming Rule

The SVG file name defines the icon name.

Recommended file naming convention:

kebab-case.svg

Examples:

SVG file

Icon name

Angular component

add.svg

add

IconAdd

delete.svg

delete

IconDelete

arrow-down.svg

arrow_down

IconArrowDown

theme-light.svg

theme_light

IconThemeLight

user-permissions.svg

user_permissions

IconUserPermissions

Recommended registry key convention:

kebab-case file name -> snake-case registry key

This keeps icon usage natural in TypeScript and Angular templates.

Example:

<app-icon name="arrow_down"></app-icon>

8.2 Allowed File Name Pattern

Recommended file name pattern:

[a-z0-9]+(-[a-z0-9]+)*.svg

Valid examples:

add.svg delete.svg arrow-down.svg theme-light.svg user-permissions.svg

Discouraged examples:

Add.svg arrow down.svg arrow_down.svg icon-delete.svg delete-final-v2.svg

Reasons:

  • spaces may cause scripting and tooling issues;

  • uppercase names create inconsistent generated code;

  • underscores make the convention less predictable if kebab-case is expected;

  • the icon- prefix duplicates the generated component folder prefix;

  • temporary names such as final-v2 are unclear and tend to become permanent.

8.3 Multicolor Icon Naming

Multicolor icons must use the .color.svg suffix.

Examples:

logo.color.svg country-flag.color.svg brand-marker.color.svg theme-light.color.svg theme-dark.color.svg

The .color marker means:

  • original SVG colors must be preserved;

  • automatic monochrome color replacement must not be applied;

  • size normalization still applies.

The generated registry key ignores the .color suffix.

Examples:

SVG file

Registry key

Component

logo.color.svg

logo

IconLogo

country-flag.color.svg

country_flag

IconCountryFlag

theme-dark.color.svg

theme_dark

IconThemeDark

9. SVG Normalization Rules

The generation script must normalize SVG files before writing them into Angular templates.

9.1 Size Normalization

All generated SVG templates should use CSS-controlled icon sizing.

The root svg element should contain:

height="var(--icon-size)"

Example generated SVG:

<svg viewBox="0 0 24 24" height="var(--icon-size)" xmlns="http://www.w3.org/2000/svg"> <path d="..." fill="var(--icon-color, var(--clr-accent-6))"/> </svg>

This allows the icon size to be controlled with CSS.

Example:

.small-action { --icon-size: 16px; } .large-action { --icon-size: 24px; }

9.2 ViewBox Preservation

The generation script must preserve the original viewBox.

Example:

<svg viewBox="0 0 24 24">

The viewBox defines the SVG coordinate system and is required for correct scaling.

The script should not remove or recalculate viewBox unless a separate SVG optimization step is explicitly introduced and documented.

9.3 Width and Height Replacement

If the source SVG contains fixed dimensions, they must be replaced.

Source:

<svg width="32" height="32" viewBox="0 0 32 32">

Generated:

<svg viewBox="0 0 32 32" height="var(--icon-size)">

The purpose is to avoid hardcoded icon dimensions in generated Angular templates.

9.4 XML Header and DOCTYPE Removal

The script may remove XML declarations and document type declarations.

Source:

<?xml version="1.0" encoding="UTF-8"?> <svg viewBox="0 0 24 24"> ... </svg>

Generated:

<svg viewBox="0 0 24 24" width="var(--icon-size)" height="var(--icon-size)"> ... </svg>

Inline SVG inside Angular templates does not require XML headers.

10. Color Handling

Color handling is the most important part of the mechanism.

There are two supported icon types:

  1. monochrome icons;

  2. multicolor icons.

10.1 Monochrome Icons

Monochrome icons are regular SVG files without the .color.svg suffix.

Examples:

delete.svg edit.svg arrow-down.svg

For monochrome icons, the generation script should replace black fill and stroke values with:

var(--icon-color,var(--clr-accent-6))

This allows icons to follow the application theme.

Source SVG:

<svg viewBox="0 0 24 24"> <path d="..." fill="#000000"/> </svg>

Generated SVG:

<svg viewBox="0 0 24 24" height="var(--icon-size)"> <path d="..." fill="var(--icon-color, var(--clr-accent-6))"/> </svg>

The icon color can then be controlled with CSS.

Example:

.danger-action { --icon-color: var(--clr-danger-6); } .secondary-action { --icon-color: var(--clr-neutral-7); }

10.2 Supported Monochrome Color Replacements

The script should replace common black color formats.

Recommended replacement list:

#000 #000000 black rgb(0, 0, 0)

Properties to process:

fill stroke

Supported forms:

<path fill="#000000"/> <path stroke="#000"/> <path style="fill: #000000; stroke: black"/>

10.3 Values That Must Not Be Replaced

The script must not replace structural or special SVG values.

Examples:

none transparent currentColor url(...)

Examples:

<path fill="none" stroke="#000000"/> <path fill="url(#gradient1)"/> <path fill="currentColor"/>

fill="none" must remain unchanged because it is a structural SVG instruction, not a visible color.

10.4 Multicolor Icons

Multicolor icons must be named with the .color.svg suffix.

Examples:

logo.color.svg map-layer.color.svg country-flag.color.svg

For these files, the generation script must preserve original colors.

Source:

<svg viewBox="0 0 24 24"> <path d="..." fill="#136AEC"/> <path d="..." fill="#F9D65C"/> </svg>

Generated:

<svg viewBox="0 0 24 24" height="var(--icon-size)"> <path d="..." fill="#136AEC"/> <path d="..." fill="#F9D65C"/> </svg>

Only size normalization is applied.

10.5 Why Explicit Multicolor Marking Is Required

Automatic multicolor detection is risky.

Example:

<path fill="#000000"/> <path fill="#111111"/>

This may represent:

  • a monochrome icon exported with slightly different shades;

  • a deliberately multicolor icon;

  • an export artifact from a design tool.

The generator should avoid guessing design intent.

Therefore, .color.svg is used as an explicit and predictable marker.

11. Generated Angular Component Rules

For each source SVG file, the script generates one Angular standalone component.

Example source file:

icons-source/delete.svg

Generated folder:

src/app/shared/components/icons/components/icon-delete/

Generated files:

icon-delete.ts icon-delete.html

11.1 Generated HTML Template

The generated .html file contains the normalized inline SVG.

Example:

<svg viewBox="0 0 24 24" width="var(--icon-size)" height="var(--icon-size)" xmlns="http://www.w3.org/2000/svg"> <path d="..." fill="var(--icon-color, var(--clr-accent-6))"/> </svg>

11.2 Generated TypeScript Component

The generated .ts file contains a minimal Angular standalone component.

Example:

import {ChangeDetectionStrategy, Component} from '@angular/core'; @Component({ selector: 'app-icon-delete', standalone: true, templateUrl: './icon-delete.html', changeDetection: ChangeDetectionStrategy.OnPush }) export class IconDelete { }

11.3 Generated Component Naming

Source file

Folder

Component class

Selector

delete.svg

icon-delete

IconDelete

app-icon-delete

arrow-down.svg

icon-arrow-down

IconArrowDown

app-icon-arrow-down

theme-light.svg

icon-theme-light

IconThemeLight

app-icon-theme-light

logo.color.svg

icon-logo

IconLogo

app-icon-logo

12. Generated Registry Rules

The script regenerates the registry file:

src/app/shared/components/icons/icons.ts

The file should contain:

  • imports for all generated icon components;

  • the ICON_REGISTRY object;

  • optionally, a generated union type for available icon names.

Recommended generated structure:

import {Type} from '@angular/core'; import {IconAdd} from './components/icon-add/icon-add'; import {IconDelete} from './components/icon-delete/icon-delete'; import {IconArrowDown} from './components/icon-arrow-down/icon-arrow-down'; export const ICON_REGISTRY = { add: IconAdd, delete: IconDelete, arrowDown: IconArrowDown } as const; export type IconName = keyof typeof ICON_REGISTRY;

Using as const allows TypeScript to infer a strict list of available icon names.

13. Runtime Usage

A generic icon component can accept an icon name and render the corresponding generated component dynamically.

Example:

<app-icon name="delete"></app-icon> <app-icon name="arrowDown"></app-icon>

CSS variables control icon size and color.

Example:

<button class="delete-button"> <app-icon name="delete"></app-icon> Delete </button>
.delete-button { --icon-size: 16px; --icon-color: var(--clr-danger-6); }

For multicolor icons, --icon-color is not expected to affect internal SVG colors.

14. Developer Workflow

14.1 Updating Existing Icons

Updating Existing IconsAnalystAnalystDeveloperDevelopericons-source/icons-source/Generation ScriptGeneration ScriptGenerated Icon ComponentsGenerated Icon ComponentsICON_REGISTRYICON_REGISTRYGitGitProvide current SVG filesShare SVG packageReview and modify SVG filesReturn updated SVG filesReplace existing SVG filesRun icon generation commandDelete old generated componentsGenerate new componentsRegenerate ICON_REGISTRYReview generated changesCommit changes

14.2 Adding a New Icon

Adding a New IconAnalystAnalystDeveloperDevelopericons-source/icons-source/Generation ScriptGeneration ScriptAngular ApplicationAngular ApplicationProvide new SVG file with approved nameAdd SVG fileRun generation commandValidate file nameNormalize SVGCreate icon componentRegister icon in ICON_REGISTRYUse icon by registry name

14.3 Replacing the Full Icon Set

Replacing the Full Icon SetAnalystAnalystDeveloperDevelopericons-source/icons-source/Generation ScriptGeneration ScriptGenerated Components FolderGenerated Components Foldericons.tsicons.tsProvide approved SVG packageClear existing SVG source filesCopy received SVG packageRun generation commandRemove all generated icon componentsClear previous registry contentloop[For each SVG file]Read SVGNormalize sizeProcess colors according to file typeGenerate Angular componentAdd registry entryReport generation resultBuild and test application

15. Generation Algorithm

The script should follow this algorithm.

Icon Generation AlgorithmRead SVG files from icons-source/Stop with errornoicons-source/ exists?yesSort SVG files by file nameDelete generated components directoryCreate empty generated components directoryTake next SVG fileValidate file nameDetermine icon nameDetermine whether file is multicolorRead SVG contentRemove XML header if presentRemove DOCTYPE if presentNormalize root SVG width and heightPreserve viewBoxMulticolor icon?yesnoPreserve original fill and stroke colorsReplace black fill and stroke with CSS variableGenerate Angular HTML templateGenerate Angular TypeScript componentAdd entry to registry modelMore SVG files?yesGenerate icons.tsPrint generation summary

16. Component Generation Mapping

SVG File to Angular Component Mappingicons-source/delete.svgfileName = delete.svgicon-delete.htmlnormalized inline SVGicon-delete.tsAngular standalone componentclass IconDeleteicons.tsICON_REGISTRY.delete = IconDeletenormalized intocomponent generated asregistered in

17. Color Handling Decision Tree

SVG Color Handling Decision TreeRead SVG file nameFile name ends with .color.svg?yesnoMark as multicolorPreserve original colorsNormalize width and height onlyMark as monochromeReplace black fill/stroke valuesUse var(--icon-color, var(--clr-accent-6))Generate Angular icon template

18. Build Integration

The icon generation script can be run manually or integrated into package scripts.

Recommended command:

{ "scripts": { "generate:icons": "node scripts/generate-icons.js" } }

Manual execution:

npm run generate:icons

Optional CI validation command:

npm run generate:icons git diff --exit-code

If generated files are outdated, the CI job fails because git diff --exit-code detects changes.

19. Pull Request Checklist

Before merging icon changes, reviewers should verify:

  • [ ] SVG files are placed in icons-source/.

  • [ ] File names follow the naming convention.

  • [ ] Multicolor icons use the .color.svg suffix.

  • [ ] Generated components were updated.

  • [ ] ICON_REGISTRY was regenerated.

  • [ ] IconRegistryKey was regenerated.

  • [ ] No manual edits were made inside generated icon components.

  • [ ] The application builds successfully.

  • [ ] Icons are visually checked in relevant UI screens.

  • [ ] No unexpected hardcoded dimensions remain in generated SVG files.

  • [ ] Monochrome icons use var(--icon-color, var(--clr-accent-6)).

20. Validation Rules

The generation script should validate SVG files before generation.

Validation

Severity

Description

Invalid file name

Error

File name does not match the naming convention.

Missing svg root

Error

File is not a valid SVG document.

Missing viewBox

Warning or Error

Icon may not scale correctly.

Duplicate registry key

Error

Two files resolve to the same icon name.

Unsupported extension

Ignored

Only .svg files are processed.

Monochrome icon contains non-black colors

Warning

The file may need .color.svg.

Multicolor icon has .color.svg suffix

OK

Colors are preserved.

21. Handling Potential Issues

21.1 Missing ViewBox

Problem:

<svg width="24" height="24">

Without viewBox, scaling may be incorrect.

Recommended action:

  • ask the analyst or designer to export SVG with viewBox;

  • or manually fix the source SVG before generation.

The generator may stop with an error if viewBox is missing.

21.2 Incorrect Multicolor Icon Processing

Problem:

A multicolor logo was named:

logo.svg

As a result, black paths may be replaced with the theme color.

Correct file name:

logo.color.svg

Then rerun:

npm run generate:icons

21.3 Icon Color Does Not Change in UI

Possible reasons:

  1. The source SVG was marked as multicolor by using .color.svg.

  2. The SVG uses a color value that is not included in the replacement list.

  3. The SVG uses gradients, masks, or embedded styles.

  4. CSS variable --icon-color is not set in the expected scope.

Recommended check:

.some-container { --icon-color: red; }

If the icon color changes, the generation worked correctly.

21.4 Icon Size Does Not Change in UI

Possible reasons:

  1. The generated SVG still contains fixed dimensions.

  2. CSS variable --icon-size is not set.

  3. Parent layout restricts icon dimensions.

Recommended check:

.some-container { --icon-size: 32px; }

22. Generated Files Policy

Generated files should not be edited manually.

This includes:

src/app/shared/components/icons/components/** src/app/shared/components/icons/icons.ts

Any changes to generated files must be made by updating SVG files in:

icons-source/

and rerunning:

npm run generate:icons

Manual edits are likely to be overwritten by the next generation.

The following README.md may be placed into the source folder.

# Icon Source Folder This folder contains source SVG files for application icons. ## Rules - The file name defines the icon name. - Use kebab-case file names. - Do not use spaces or uppercase letters. - Monochrome icons should use black fill/stroke in the source SVG. - Monochrome black fill/stroke values are replaced during generation with: `var(--icon-color, var(--clr-accent-6))` - Multicolor icons must use the `.color.svg` suffix. - Example: `logo.color.svg` - SVG files must contain a valid `viewBox`. - Do not edit generated Angular icon components manually. ## Generation Run: ```bash npm run generate:icons

The generator should:

  1. read SVG files from icons-source/;

  2. validate file names;

  3. detect multicolor icons by .color.svg;

  4. remove old generated components;

  5. normalize SVG size attributes;

  6. preserve viewBox;

  7. replace black colors for monochrome icons;

  8. preserve colors for multicolor icons;

  9. create one Angular component per icon;

  10. regenerate ICON_REGISTRY;

  11. print a summary.

25. End-to-End Process

End-to-End Icon Maintenance ProcessBusiness Analyst / DesignerBusiness Analyst / DesignerDeveloperDevelopericons-source/icons-source/generate-icons.jsgenerate-icons.jsGenerated Angular ComponentsGenerated Angular ComponentsICON_REGISTRYICON_REGISTRYAngular UIAngular UIPull RequestPull RequestExport or provide current SVG source filesSend SVG files for reviewReview, update, add, or remove iconsReturn approved SVG packageUpdate source SVG filesRun npm run generate:iconsRead SVG filesRecreate icon componentsRegenerate ICON_REGISTRY&IconRegistryKeyBuild and test applicationCreate pull requestReview source SVG changesReview generated filesVerify naming and color rules

26. Key Design Decisions

Decision

Rationale

Use icons-source/ as the source of truth

Simple exchange format for analysts/designers and developers.

Generate Angular components

Keeps runtime icon rendering consistent with the existing architecture.

Regenerate ICON_REGISTRY

Prevents missing or stale registry entries.

Use width and height with var(--icon-size)

Enables CSS-based size control.

Replace black colors in monochrome icons

Enables theme-aware icon coloring.

Use .color.svg for multicolor icons

Avoids unreliable automatic color detection.

Do not manually edit generated files

Prevents losing changes during regeneration.

Validate file names

Keeps generated code predictable and stable.

Possible future improvements:

  • add SVG optimization with SVGO;

  • add a dry-run mode;

  • add a validation-only mode for CI;

  • generate an icon catalog page for QA and analysts;

  • add visual regression tests for icon changes;

  • add a reverse export script if generated components must be converted back to SVG files.

28. Glossary

Term

Meaning

Source SVG

SVG file stored in icons-source/.

Generated component

Angular component generated from a source SVG.

Registry

The ICON_REGISTRY object that maps icon names to Angular components.

Monochrome icon

Icon whose color is controlled by application CSS variables.

Multicolor icon

Icon whose original SVG colors must be preserved.

.color.svg

File suffix used to mark multicolor icons.

--icon-size

CSS variable controlling generated icon size.

--icon-color

CSS variable controlling monochrome icon color.

--clr-accent-6

Default fallback color for monochrome icons.

10 August 2026