Author high-quality Markdown documentation with deterministic structure, lint compliance, and CI integration. Use when writing README files, creating docs pages, fixing markdownlint failures, defining style rules, or wiring markdown checks into pre-commit and pipelines. Keywords: markdown, markdownlint, readme, docs, headings, lists, code fences, links, images, lint config, ci, documentation style.
Overall
score
100%
Does it follow best practices?
Validation for skill structure
name: Markdown Lint
on:
push:
branches: [main, develop]
pull_request:
branches: [main, develop]
jobs:
markdown-lint:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: '20'
cache: 'npm'
- name: Install dependencies
run: npm ci
- name: Lint markdown files
run: npm run lint:mdname: Markdown Lint
on: [push, pull_request]
jobs:
markdown-lint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Lint markdown
uses: DavidAnson/markdownlint-cli2-action@v16
with:
globs: |
**/*.md
#node_modulesname: Markdown Lint & Fix
on:
pull_request:
branches: [main]
jobs:
markdown-lint-fix:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
ref: ${{ github.head_ref }}
- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: '20'
- name: Install dependencies
run: npm ci
- name: Fix markdown issues
run: npm run lint:md:fix
- name: Commit changes
uses: stefanzweifel/git-auto-commit-action@v5
with:
commit_message: 'docs: auto-fix markdown lint issues'
file_pattern: '*.md'name: Markdown Lint
on: [push, pull_request]
jobs:
markdown-lint:
runs-on: ${{ matrix.os }}
strategy:
matrix:
os: [ubuntu-latest, windows-latest, macos-latest]
node-version: [18, 20]
steps:
- uses: actions/checkout@v4
- name: Setup Node.js ${{ matrix.node-version }}
uses: actions/setup-node@v4
with:
node-version: ${{ matrix.node-version }}
- run: npm ci
- run: npm run lint:mdstages:
- test
markdown-lint:
stage: test
image: node:20
before_script:
- npm ci
script:
- npm run lint:md
only:
- merge_requests
- main
- developmarkdown-lint:
stage: test
image: node:20
cache:
key: ${CI_COMMIT_REF_SLUG}
paths:
- node_modules/
before_script:
- npm ci
script:
- npm run lint:md
artifacts:
reports:
junit: markdown-lint-report.xml
when: alwaysmarkdown-lint-fix:
stage: test
image: node:20
before_script:
- npm ci
- git config user.name "GitLab CI"
- git config user.email "ci@gitlab.com"
script:
- npm run lint:md:fix
- |
if [[ -n $(git status -s) ]]; then
git add "*.md"
git commit -m "docs: auto-fix markdown lint issues [skip ci]"
git push "https://oauth2:${CI_JOB_TOKEN}@${CI_SERVER_HOST}/${CI_PROJECT_PATH}.git" HEAD:${CI_COMMIT_REF_NAME}
fi
only:
- merge_requestsversion: 2.1
executors:
node-executor:
docker:
- image: cimg/node:20.0
jobs:
markdown-lint:
executor: node-executor
steps:
- checkout
- restore_cache:
keys:
- node-deps-{{ checksum "package-lock.json" }}
- run:
name: Install dependencies
command: npm ci
- save_cache:
key: node-deps-{{ checksum "package-lock.json" }}
paths:
- node_modules
- run:
name: Lint markdown
command: npm run lint:md
workflows:
version: 2
test:
jobs:
- markdown-lintpipeline {
agent any
tools {
nodejs 'NodeJS 20'
}
stages {
stage('Install') {
steps {
sh 'npm ci'
}
}
stage('Lint Markdown') {
steps {
sh 'npm run lint:md'
}
}
}
post {
always {
cleanWs()
}
failure {
emailext(
subject: "Markdown Lint Failed: ${env.JOB_NAME} #${env.BUILD_NUMBER}",
body: "Check console output at ${env.BUILD_URL}",
to: "team@example.com"
)
}
}
}node {
stage('Checkout') {
checkout scm
}
stage('Install') {
nodejs(nodeJSInstallationName: 'NodeJS 20') {
sh 'npm ci'
}
}
stage('Lint Markdown') {
nodejs(nodeJSInstallationName: 'NodeJS 20') {
sh 'npm run lint:md'
}
}
}trigger:
- main
- develop
pool:
vmImage: 'ubuntu-latest'
steps:
- task: NodeTool@0
inputs:
versionSpec: '20.x'
displayName: 'Install Node.js'
- script: npm ci
displayName: 'Install dependencies'
- script: npm run lint:md
displayName: 'Lint markdown files'
- task: PublishTestResults@2
condition: always()
inputs:
testResultsFormat: 'JUnit'
testResultsFiles: '**/markdown-lint-report.xml'
failTaskOnFailedTests: truepackage.json:
{
"scripts": {
"prepare": "husky install"
},
"lint-staged": {
"*.md": [
"markdownlint-cli2 --fix",
"git add"
]
},
"devDependencies": {
"husky": "^9.0.0",
"lint-staged": "^15.0.0",
"markdownlint-cli2": "^0.12.0"
}
}.husky/pre-commit:
#!/usr/bin/env sh
. "$(dirname -- "$0")/_/husky.sh"
npx lint-stagedSetup:
npm install -D husky lint-staged
npx husky install
npx husky add .husky/pre-commit "npx lint-staged".pre-commit-config.yaml:
repos:
- repo: https://github.com/DavidAnson/markdownlint-cli2
rev: v0.12.1
hooks:
- id: markdownlint-cli2
args: ['--fix']Setup:
pip install pre-commit
pre-commit installFROM node:20-alpine
WORKDIR /app
COPY package*.json ./
RUN npm ci --only=production
COPY . .
RUN npm run lint:mdversion: '3.8'
services:
markdown-lint:
image: node:20-alpine
working_dir: /app
volumes:
- .:/app
command: sh -c "npm ci && npm run lint:md"Usage:
docker-compose run markdown-lintturbo.json:
{
"pipeline": {
"lint:md": {
"outputs": [],
"cache": true
}
}
}package.json (root):
{
"scripts": {
"lint:md": "turbo run lint:md"
}
}packages/docs/package.json:
{
"scripts": {
"lint:md": "markdownlint-cli2 \"**/*.md\""
}
}lerna.json:
{
"version": "independent",
"npmClient": "npm",
"command": {
"run": {
"stream": true
}
}
}package.json (root):
{
"scripts": {
"lint:md": "lerna run lint:md"
}
}// scripts/markdown-lint-report.js
const { markdownlint } = require('markdownlint/promise');
const fs = require('fs').promises;
async function generateReport() {
const result = await markdownlint({
files: ['**/*.md'],
config: { default: true }
});
let html = '<html><body><h1>Markdown Lint Report</h1>';
Object.keys(result).forEach(file => {
const errors = result[file];
if (errors.length > 0) {
html += `<h2>${file}</h2><ul>`;
errors.forEach(err => {
html += `<li>Line ${err.lineNumber}: ${err.ruleDescription}</li>`;
});
html += '</ul>';
}
});
html += '</body></html>';
await fs.writeFile('markdown-lint-report.html', html);
}
generateReport();package.json:
{
"scripts": {
"lint:md:json": "markdownlint-cli2 --config .markdownlint-cli2.jsonc \"**/*.md\""
}
}.markdownlint-cli2.jsonc:
{
"outputFormatters": [
["markdownlint-cli2-formatter-json", { "path": "markdown-lint-report.json" }]
]
}--fix locally, not in CInode_modules, dist, etc.node_modules--fix in CI can cause unexpected commitsInstall with Tessl CLI
npx tessl i pantheon-ai/markdown-authoring@0.1.1