mirror of
https://github.com/grafana/grafana.git
synced 2025-07-28 03:12:07 +08:00
97 lines
2.8 KiB
JavaScript
97 lines
2.8 KiB
JavaScript
// @ts-check
|
|
const { AST_NODE_TYPES } = require('@typescript-eslint/utils');
|
|
const { upperFirst } = require('lodash');
|
|
|
|
/** @typedef {import('@typescript-eslint/utils/ts-eslint').RuleContext<'publicImg' | 'importImage' | 'useBuildFolder', []>} RuleContextWithOptions */
|
|
|
|
/**
|
|
* @param {string} str
|
|
*/
|
|
const camelCase = (str) => {
|
|
return str
|
|
.replace(/[-_]/g, ' ')
|
|
.split(' ')
|
|
.map((word, index) => (index === 0 ? word : upperFirst(word)))
|
|
.join('');
|
|
};
|
|
|
|
/**
|
|
* @param {string} value
|
|
* @returns {string}
|
|
*/
|
|
const convertPathToImportName = (value) => {
|
|
const fullFileName = value.split('/').pop() || '';
|
|
const fileType = fullFileName.split('.').pop();
|
|
const fileName = fullFileName.replace(`.${fileType}`, '');
|
|
return camelCase(fileName) + upperFirst(fileType);
|
|
};
|
|
|
|
/**
|
|
* @param {import('@typescript-eslint/utils/ts-eslint').RuleFixer} fixer
|
|
* @param {import('@typescript-eslint/utils').TSESTree.StringLiteral} node
|
|
* @param {RuleContextWithOptions} context
|
|
*/
|
|
function getImageImportFixers(fixer, node, context) {
|
|
const { value: importPath } = node;
|
|
const pathWithoutPublic = importPath.replace('public/', '');
|
|
|
|
/** e.g. public/img/checkbox.png -> checkboxPng */
|
|
const imageImportName = convertPathToImportName(importPath);
|
|
|
|
const body = context.sourceCode.ast.body;
|
|
|
|
const existingImport = body.find(
|
|
(node) => node.type === AST_NODE_TYPES.ImportDeclaration && node.source.value === pathWithoutPublic
|
|
);
|
|
|
|
const fixers = [];
|
|
|
|
// If there's no existing import at all, add a fixer for this
|
|
if (!existingImport) {
|
|
const importStatementFixer = fixer.insertTextBefore(
|
|
body[0],
|
|
`import ${imageImportName} from '${pathWithoutPublic}';\n`
|
|
);
|
|
fixers.push(importStatementFixer);
|
|
}
|
|
|
|
const isInAttribute = node.parent.type === AST_NODE_TYPES.JSXAttribute;
|
|
const variableReplacement = isInAttribute ? `{${imageImportName}}` : imageImportName;
|
|
const variableFixer = fixer.replaceText(node, variableReplacement);
|
|
fixers.push(variableFixer);
|
|
|
|
return fixers;
|
|
}
|
|
|
|
/**
|
|
* @param {import('@typescript-eslint/utils/ts-eslint').RuleFixer} fixer
|
|
* @param {import('@typescript-eslint/utils').TSESTree.StringLiteral} node
|
|
*/
|
|
const replaceWithPublicBuild = (fixer, node) => {
|
|
const { value } = node;
|
|
|
|
const startingQuote = node.raw.startsWith('"') ? '"' : "'";
|
|
return fixer.replaceText(
|
|
node,
|
|
`${startingQuote}${value.replace('public/img/', 'public/build/img/')}${startingQuote}`
|
|
);
|
|
};
|
|
|
|
/**
|
|
* @param {string} value
|
|
*/
|
|
const isInvalidImageLocation = (value) => {
|
|
return (
|
|
value.startsWith('public/img/') ||
|
|
(!value.startsWith('public/build/') &&
|
|
!value.startsWith('public/plugins/') &&
|
|
/public.*(\.svg|\.png|\.jpg|\.jpeg|\.gif)$/.test(value))
|
|
);
|
|
};
|
|
|
|
module.exports = {
|
|
getImageImportFixers,
|
|
replaceWithPublicBuild,
|
|
isInvalidImageLocation,
|
|
};
|