-
Notifications
You must be signed in to change notification settings - Fork 5
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
101 changed files
with
951 additions
and
351 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,19 +1,48 @@ | ||
{ | ||
"extends": "stylelint-config-recommended-scss", | ||
"extends": [ | ||
"stylelint-config-recommended-scss", | ||
"stylelint-config-standard-scss" | ||
], | ||
"ignoreFiles": [ | ||
"**/*.js", | ||
"**/*.snap", | ||
"**/*.vars.pcss" | ||
"**/*.js", | ||
"**/*.snap", | ||
"**/*.vars.pcss" | ||
], | ||
"plugins": [ | ||
"stylelint-scss" | ||
"stylelint-scss" | ||
], | ||
"rules": { | ||
"at-rule-disallowed-list": ["debug"], | ||
"no-empty-source": null, | ||
"no-descending-specificity": null, | ||
"selector-pseudo-class-no-unknown": [true, { | ||
"ignorePseudoClasses": ["global"] | ||
}] | ||
"at-rule-disallowed-list": ["debug"], | ||
"no-empty-source": null, | ||
"no-descending-specificity": null, | ||
"selector-pseudo-class-no-unknown": [ | ||
true, | ||
{ | ||
"ignorePseudoClasses": ["global"] | ||
} | ||
], | ||
"scss/at-extend-no-missing-placeholder": true, | ||
"scss/comment-no-loud": null, | ||
"scss/function-color-relative": true, | ||
"scss/at-if-no-null": true, | ||
"scss/dollar-variable-no-missing-interpolation": true, | ||
"scss/selector-no-redundant-nesting-selector": true, | ||
"scss/at-import-partial-extension": null, | ||
"scss/at-mixin-pattern": null, | ||
"scss/at-function-pattern": null, | ||
"scss/dollar-variable-pattern": null, | ||
"scss/percent-placeholder-pattern": null, | ||
"function-disallowed-list": null, | ||
"color-function-notation": null, | ||
"alpha-value-notation": null, | ||
"color-hex-length": null, | ||
"custom-property-pattern": null, | ||
"selector-class-pattern": [ | ||
"^[a-z0-9]+(?:-[a-z0-9]+)*(?:__(?:[a-z0-9]+(?:-[a-z0-9]+)*))?(?:--(?:[a-z0-9]+(?:-[a-z0-9]+)*))?$", | ||
{ | ||
"message": "Expected class selector to follow BEM naming convention (selector-class-pattern)" | ||
} | ||
] | ||
} | ||
} | ||
} | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,148 @@ | ||
/* eslint-env node */ | ||
|
||
// lint-report-generator.mjs | ||
import stylelint from 'stylelint'; | ||
import fs from 'fs'; | ||
import { join, relative } from 'path'; | ||
import { fileURLToPath } from 'url'; | ||
import { dirname } from 'path'; | ||
|
||
const __filename = fileURLToPath(import.meta.url); | ||
const __dirname = dirname(__filename); | ||
|
||
/** | ||
* Formats the current date as YYYY-MM-DD | ||
*/ | ||
const getFormattedDate = () => { | ||
const date = new Date(); | ||
return date.toISOString().split('T')[0]; | ||
}; | ||
|
||
/** | ||
* Creates directory if it doesn't exist | ||
*/ | ||
const ensureDirectoryExists = (dirPath) => { | ||
if (!fs.existsSync(dirPath)) { | ||
fs.mkdirSync(dirPath, { recursive: true }); | ||
} | ||
}; | ||
|
||
/** | ||
* Processes stylelint results into a structured format | ||
*/ | ||
const processStylelintResults = (styleResults) => { | ||
return styleResults.results.reduce((acc, file) => { | ||
if (file.warnings.length > 0) { | ||
const relativePath = relative(process.cwd(), file.source); | ||
acc.push({ | ||
file: relativePath, | ||
warnings: file.warnings.map(w => ({ | ||
line: w.line, | ||
column: w.column, | ||
rule: w.rule, | ||
text: w.text, | ||
severity: w.severity | ||
})) | ||
}); | ||
} | ||
return acc; | ||
}, []); | ||
}; | ||
|
||
/** | ||
* Generates markdown content from warnings | ||
*/ | ||
const generateMarkdownContent = (styleWarnings, reportDate) => { | ||
let mdReport = `# Stylelint Warning Report (${reportDate})\n\n`; | ||
mdReport += `## Summary\n\n`; | ||
|
||
const totalWarnings = styleWarnings.reduce((sum, file) => | ||
sum + file.warnings.length, 0); | ||
|
||
mdReport += `- Total files with warnings: ${styleWarnings.length}\n`; | ||
mdReport += `- Total warnings: ${totalWarnings}\n\n`; | ||
|
||
if (styleWarnings.length === 0) { | ||
mdReport += 'No style warnings found.\n\n'; | ||
return mdReport; | ||
} | ||
|
||
mdReport += `## Detailed Warnings\n\n`; | ||
styleWarnings.forEach(file => { | ||
mdReport += `### ${file.file}\n\n`; | ||
mdReport += '| Line:Col | Rule | Message |\n'; | ||
mdReport += '|----------|------|---------||\n'; | ||
file.warnings.forEach(warning => { | ||
const escapedText = warning.text.replace(/\|/g, '\\|'); | ||
mdReport += ` | ||
| ${warning.line}:${warning.column} | ||
| \`${warning.rule}\` | ||
| ${escapedText} |\n`; | ||
}); | ||
mdReport += '\n'; | ||
}); | ||
|
||
return mdReport; | ||
}; | ||
|
||
/** | ||
* Main function to generate lint reports | ||
*/ | ||
const generateLintReport = async () => { | ||
try { | ||
const reportDate = getFormattedDate(); | ||
const reportDir = join(process.cwd(), 'reports'); | ||
|
||
ensureDirectoryExists(reportDir); | ||
|
||
const styleResults = await stylelint.lint({ | ||
files: 'src/**/*.scss', | ||
formatter: 'json' | ||
}); | ||
|
||
const styleWarnings = processStylelintResults(styleResults); | ||
const mdReport = generateMarkdownContent(styleWarnings, reportDate); | ||
|
||
const reportPath = join(reportDir, `stylelint-report-${reportDate}.md`); | ||
const jsonReportPath = join(reportDir, `stylelint-report-${reportDate}.json`); | ||
|
||
fs.writeFileSync(reportPath, mdReport); | ||
fs.writeFileSync(jsonReportPath, JSON.stringify({ | ||
date: reportDate, | ||
styleWarnings | ||
}, null, 2)); | ||
|
||
const summary = { | ||
totalFiles: styleWarnings.length, | ||
totalWarnings: styleWarnings.reduce((sum, file) => | ||
sum + file.warnings.length, 0), | ||
reportPath, | ||
jsonReportPath | ||
}; | ||
|
||
console.log(` | ||
Reports generated successfully: | ||
- Markdown: ${summary.reportPath} | ||
- JSON: ${summary.jsonReportPath} | ||
Summary: | ||
- Total files with warnings: ${summary.totalFiles} | ||
- Total warnings: ${summary.totalWarnings} | ||
`); | ||
|
||
return summary; | ||
|
||
} catch (error) { | ||
console.error('Error generating lint report:', error); | ||
throw error; | ||
} | ||
}; | ||
|
||
// Execute if called directly | ||
if (import.meta.url === `file://${__filename}`) { | ||
generateLintReport().catch(error => { | ||
console.error('An error occurred:', error); | ||
process.exit(1); | ||
}); | ||
} | ||
|
||
export default generateLintReport; |
Oops, something went wrong.