All files / packages/design-system/scripts/gulp/plugins lint-icons.js

0% Statements 0/52
0% Branches 0/10
0% Functions 0/10
0% Lines 0/51

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114                                                                                                                                                                                                                                   
import paths from './../../helpers/paths';
const path = require('path');
const yaml = require('js-yaml');
const map = require('map-stream');
const _ = require('lodash');
const gutil = require('gulp-util');
const sdsColorPalette = require(`${path.resolve(paths.sdsStylingAliases, 'color-palettes.json')}`).aliases;
const recommendedIconColors = require(path.resolve(__dirname, '../../../assets/icon-colors/icon-colors.json'));
 
const recommendedColorsHexCodes = recommendedIconColors.recommendedColors
                                    .map(color => `PALETTE_${color.replace(/-/g, '_').toUpperCase()}`)
                                    .map(color => sdsColorPalette[color].toUpperCase());
const ICONS_COLORS = [...recommendedColorsHexCodes, ...recommendedIconColors.specialColors];
const ICON_TYPES_TO_CHECK = ["standard", "actions"];
 
const verboseReporter = (lint, file) =>
  lint.errors.forEach(error => {
    const errors = Array.from(error.error).map(err => `\t❌ ${err}`).join('\n');
    const icon = error.icon;
    const filePath = file.path;
    const message = `${icon} in ${filePath} has following error(s): \n${errors}`;
 
    gutil.log('iconlint: ', `${message}`);
  });
 
const IconLint = function (icons, pluginOptions = {}) {
  let self = this;
 
  if (!(self instanceof IconLint)) {
    return new IconLint(icons, pluginOptions);
  }
 
  self.errors = [];
 
  _.keys(icons).forEach(icon => {
    const iconName = icon;
    const iconColor = icons[icon].value;
    try {
      self.iconColorAndCaseLint(iconName, iconColor, pluginOptions.type);
    } catch (e) {
      self.errors.push({
        icon: iconName,
        error: e
      });
    }
  });
 
  return {
    errors: self.errors
  };
};
 
IconLint.prototype.iconColorAndCaseLint = function (iconName, iconColor, iconType) {
  const errors = [];
 
  if (!iconName || iconName.trim().length === 0 || !iconColor || iconColor.trim().length === 0) {
    errors.push('Icon name or color cannot be empty');
  }
 
  if (iconName.toUpperCase() !== iconName) {
    errors.push('Icon names should be in uppercase');
  }
 
  if (iconColor.toUpperCase() !== iconColor) {
    errors.push('Icon color code should be in uppercase');
  }
 
  if (!_.includes(ICONS_COLORS, iconColor.toUpperCase())) {
    errors.push(`Icon color should be part of recommended colors - [${ICONS_COLORS}]`,
      `Please add the icon color to the recommended list if it is meant to be included`
      );
  }
 
  if (errors.length) {
    throw errors;
  }
};
 
const iconlintPlugin = (pluginOptions = {}) =>
  map(function (file, cb) {
    const iconType = path.parse(file.path).name.replace('bg-', '');
    if (ICON_TYPES_TO_CHECK.includes(iconType)) {
      pluginOptions.type = iconType;
      const icons = yaml.safeLoad(file.contents.toString('utf8'));
      const iconList = icons.props ? icons.props : [];
      const result = IconLint(iconList, pluginOptions);
      file.iconlint = {
        errors: result.errors
      };
    }
 
    // Pass file
    cb(null, file);
  });
 
iconlintPlugin.report = _ =>
  map(function (file, cb) {
    let error = null;
    const iconlintErrors = file.iconlint ? file.iconlint.errors : null;
    if (iconlintErrors) {
      if (iconlintErrors.length) {
        error = new gutil.PluginError(
          'iconlint', `Found ${iconlintErrors.length} linting error(s)`
        );
      }
      verboseReporter(file.iconlint, file);
    }
 
    // Pass file
    cb(error, file);
  });
 
module.exports = iconlintPlugin;