diff --git a/.gitattributes b/.gitattributes
new file mode 100644
index 0000000..faa3394
--- /dev/null
+++ b/.gitattributes
@@ -0,0 +1 @@
+RULES.md linguist-generated=true
\ No newline at end of file
diff --git a/.github/workflows/update-rules.yml b/.github/workflows/update-rules.yml
new file mode 100644
index 0000000..4442f74
--- /dev/null
+++ b/.github/workflows/update-rules.yml
@@ -0,0 +1,39 @@
+name: Update Rules Page
+
+on:
+ pull_request:
+ branches: [main]
+ paths:
+ - 'styles/**'
+ - '.github/workflows/update-rules.yml'
+
+jobs:
+ generate_markdown:
+ runs-on: ubuntu-latest
+
+ steps:
+ - uses: actions/checkout@v3
+
+ - name: Set up Python
+ uses: actions/setup-python@v4
+ with:
+ python-version: 3.x
+
+ - name: Install dependencies
+ run: |
+ python -m pip install --upgrade pip
+ pip install pyyaml
+
+ - name: Run script to generate Markdown
+ run: python scripts/update-rules-page.py
+
+ - name: Commit and push changes
+ run: |
+ git config --local user.email "action@github.com"
+ git config --local user.name "GitHub Action"
+ git add -f RULES.md
+ TIMESTAMP=$(date -u +"%Y-%m-%d")
+ git commit -m "Update RULES.md - $TIMESTAMP." || echo "No changes to commit."
+ git config pull.rebase true
+ git pull origin ${{ github.head_ref }}
+ git push origin HEAD:${{ github.head_ref }}
diff --git a/.gitignore b/.gitignore
index 1461f1b..4c138c0 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,2 +1,4 @@
Docshtml.zip
Docsmd.zip
+.DS_Store
+/RULES.md
\ No newline at end of file
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 8b0473d..ae81cc9 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -16,7 +16,7 @@ Are you interested in contributing your team's product-specific terminology and
1. Create a folder such as `[Product Name]-Names` and add it to the [`Styles/Datadog` folder][4].
2. Update the [CODEOWNERS file][5] with your team's GitHub handle.
-3. Update the `StylesPath` to point to the approriate directory in your team repository's [`.vale.ini` file][6].
+3. Update the `StylesPath` to point to the appropriate directory in your team repository's [`.vale.ini` file][6].
In order to ease and speed up our review, here are some items you can check for when submitting your pull request:
diff --git a/RULES.md b/RULES.md
new file mode 100644
index 0000000..6669c73
--- /dev/null
+++ b/RULES.md
@@ -0,0 +1,848 @@
+# Vale Rules Overview
+
+This page provides a comprehensive list of the Vale linter rules used in Datadog documentation.
+
+Last Updated: 2024-03-20
+
+## Table of Contents
+- [Vocab](#vocab)
+- [CWS-Descriptions](#cws-descriptions)
+- [SIEM-Names](#siem-names)
+- [Datadog](#datadog)
+- [CWS-Names](#cws-names)
+
+## Vocab
+
+
+## CWS-Descriptions
+
+### Refer to the 'Datadog %s' instead of the 'Datadog %s'
+
+**Level:** *error*
+
+**Swap:**
+- `agent` -> `Agent`
+
+**Ignore Case:** False
+
+
+## SIEM-Names
+
+### Rule names should use sentence case
+
+**Level:** *error*
+
+
+Exceptions:
+
+- `1Password`
+- `Advanced Protection`
+- `Autoscaling Group`
+- `Amazon EC2 Instance`
+- `Amazon S3`
+- `API calls`
+- `Auth0 Attack Protection`
+- `Auth0 Breached Password Detection`
+- `Auth0 Brute Force Protection`
+- `Auth0 Guardian MFA`
+- `Auth0 Suspicious IP Throttling`
+- `AWS Cloudtrail GetCallerIdentity`
+- `AWS DescribeInstances`
+- `AWS IAM User created with AdministratorAccess policy attached`
+- `AWS ConsoleLogin`
+- `AWS Console login without MFA`
+- `AWS GuardDuty`
+- `AWS IAM Roles Anywhere`
+- `AWS Kinesis Firehose`
+- `AWS Lambda`
+- `AWS Network Gateway`
+- `AWS Secrets Manager`
+- `AWS Systems Manager`
+- `AWS Verified Access`
+- `AWS VPC Flow Log`
+- `Azure Active Directory`
+- `Azure AD Identity Protection`
+- `Azure AD Privileged Identity Management`
+- `CloudTrail`
+- `Cloudflare`
+- `Cloudflare CASB Finding`
+- `Cloudflare L7 DDOS`
+- `Crowdstrike Alerts`
+- `Enterprise Organization`
+- `GitHub`
+- `GitHub Advanced Security`
+- `GitHub Dependabot`
+- `GitHub Personal Access Token`
+- `GitHub Secret Scanning`
+- `Google App Engine`
+- `Google Cloud`
+- `Google Cloud IAM Role updated`
+- `Google Cloud Storage`
+- `Google Cloud Storage Bucket`
+- `Google Compute`
+- `Google Compute Engine`
+- `Google Drive`
+- `Google Security Command Center`
+- `Google Workspace`
+- `IdP configuration changed`
+- `Impossible Travel Auth0`
+- `IoC`
+- `Jamf Protect`
+- `Microsoft 365 Application Impersonation`
+- `Microsoft 365 Default or Anonymous`
+- `Microsoft 365 E-Discovery`
+- `Microsoft 365 Exchange`
+- `Microsoft 365 Full Access`
+- `Microsoft 365 Inbound Connector`
+- `Microsoft 365 OneDrive`
+- `Microsoft 365 Security and Compliance`
+- `Microsoft 365 SendAs`
+- `Microsoft Defender for Cloud`
+- `Microsoft Intune Enterprise MDM`
+- `Microsoft Teams`
+- `Okta`
+- `Okta Identity Provider`
+- `Palo Alto Networks Firewall`
+- `RDS Snapshot`
+- `Scout Suite`
+- `Sqreen`
+- `Tor`
+- `TruffleHog`
+- `Zendesk Automatic Redaction`
+
+
+
+## Datadog
+
+### Use inclusive language
+
+**Level:** *error*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#inclusive-language)
+
+**Swap:**
+- `black ?list` -> `disallow list|exclude list`
+- `master` -> `primary`
+- `slave` -> `secondary`
+- `white ?list` -> `allow list|include list`
+
+**Ignore Case:** True
+
+### Avoid vague text in links like '%s' unless you can pair it with more descriptive text
+
+**Level:** *warning*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#links)
+
+**Swap:**
+- `\[here\]\(.*?\)` -> `here`
+- `\s*here\s*` -> `here`
+- `\[this\]\(.*?\)` -> `this`
+- `\s*this\s*` -> `this`
+- `\[page\]\(.*?\)` -> `page`
+- `\s*page\s*` -> `page`
+- `\[this page\]\(.*?\)` -> `this page`
+- `\s*this page\s*` -> `this page`
+
+**Ignore Case:** True
+
+### Use '%s' instead of '%s'
+
+**Level:** *warning*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#words-and-phrases)
+
+**Swap:**
+- `a number of` -> `few|several|many`
+- `acknowledgement` -> `acknowledgment`
+- `App Analytics` -> `Tracing without Limits™`
+- `auto(?:\s|-)complete` -> `autocomplete`
+- `auto(?:\s|-)completion` -> `autocompletion`
+- `Availability Zone` -> `availability zone`
+- `Availability Zones` -> `availability zones`
+- `back(?:\s|-)end` -> `backend`
+- `back(?:\s|-)ends` -> `backends`
+- `bear in mind` -> `keep in mind`
+- `boolean` -> `Boolean`
+- `booleans` -> `Booleans`
+- `cheat sheet` -> `cheatsheet`
+- `command line interface` -> `command-line interface`
+- `Create a new` -> `Create a|Create an`
+- `culprit` -> `cause`
+- `data are` -> `data is`
+- `data(?:\s|-)point` -> `datapoint`
+- `data(?:\s|-)points` -> `datapoints`
+- `data(?:\s|-)set` -> `dataset`
+- `data(?:\s|-)sets` -> `datasets`
+- `data-?center` -> `data center`
+- `data-?centers` -> `data centers`
+- `Datadog (?:app|application)` -> `Datadog|Datadog site`
+- `Datadog product` -> `Datadog|Datadog service`
+- `data-?source` -> `data source`
+- `data-?sources` -> `data sources`
+- `default (?:dash|screen)board` -> `out-of-the-box dashboard`
+- `default (?:dash|screen)boards` -> `out-of-the-box dashboards`
+- `(?:Dev/?ops|dev/?ops|Dev/Ops)` -> `DevOps|DevSecOps`
+- `drill (?:down|into)` -> `examine|investigate|analyze`
+- `drilling (?:down|into)` -> `examining|investigating|analyzing`
+- `Distributed Tracing` -> `distributed tracing`
+- `(?:easy|easily)` -> ``
+- `e-?book` -> `eBook`
+- `e-?books` -> `eBooks`
+- `e-mail` -> `email`
+- `e-mailing` -> `emailing`
+- `e-mails` -> `emails`
+- `end(?:\s|-)point` -> `endpoint`
+- `end(?:\s|-)points` -> `endpoints`
+- `event (?:stream|streem)` -> `Event Stream`
+- `flame-?graph` -> `flame graph`
+- `flame-?graphs` -> `flame graphs`
+- `figure out` -> `determine`
+- `figuring out` -> `determining`
+- `file(?:\s|-)name` -> `filename`
+- `file(?:\s|-)names` -> `filenames`
+- `filesystem` -> `file system`
+- `filesystems` -> `file systems`
+- `fine\s?-?tune` -> `customize|optimize|refine`
+- `for the most part` -> `generally|usually`
+- `front(?:\s|-)end` -> `frontend`
+- `health-?check` -> `heath check`
+- `health-?checks` -> `heath checks`
+- `(?:heat-?map|Heat Map)` -> `heat map`
+- `(?:heat-?maps|Heat Maps)` -> `heat maps`
+- `(?:host-?map|Host Map)` -> `host map`
+- `(?:host-?maps|Host Maps)` -> `host maps`
+- `hone in` -> `home in`
+- `hones in` -> `homes in`
+- `honing in` -> `homing in`
+- `highly` -> ``
+- `hit` -> `click|select`
+- `in order to` -> `to`
+- `in sync` -> `in-sync`
+- `In sync` -> `In-sync`
+- `indices` -> `indexes`
+- `indexation` -> `indexing`
+- `infrastructures` -> `infrastructure`
+- `install command` -> `installation command`
+- `Internet` -> `internet`
+- `(?:i/?-?o|I-?O)` -> `I/O`
+- `(?:i/?ops|I/OPS)` -> `IOPS`
+- `just` -> ``
+- `keep in mind` -> `consider`
+- `left up to` -> `determined by`
+- `let's assume` -> `assuming|for example, if`
+- `load-?balancing` -> `load balancing`
+- `machine-?learning` -> `machine learning`
+- `micro(?:\s|-)service` -> `microservice`
+- `micro(?:\s|-)services` -> `microservices`
+- `multi-?alert` -> `multi alert`
+- `multicloud` -> `multi-cloud`
+- `multiline` -> `multi-line`
+- `Note that` -> `**Note**:`
+- `(?:obvious|obviously|Obviously)` -> ``
+- `off-line` -> `offline`
+- `on the fly` -> `real-time|in real time`
+- `Once` -> `After`
+- `open-?source` -> `open source`
+- `page view` -> `pageview`
+- `page views` -> `pageviews`
+- `play a hand` -> `influence`
+- `please` -> ``
+- `pre-connect` -> `preconnect`
+- `quick|quickly` -> ``
+- `screen(?:\s|-)board` -> `screenboard`
+- `simple|simply` -> ``
+- `single pane of glass` -> `single view|single place|single page`
+- `slice and dice` -> `filter and group`
+- `stand for` -> `represent|mean`
+- `Synthetics` -> `Synthetic Monitoring`
+- `reenable` -> `re-enable`
+- `run(?:\s|-)time` -> `runtime`
+- `refer to|visit` -> `see|read|follow`
+- `time board` -> `timeboard`
+- `time(?:\s|-)series` -> `timeseries`
+- `time-?frame` -> `time frame`
+- `time-?frames` -> `time frames`
+- `top-?list` -> `top list`
+- `trade(?:\s|-)off` -> `trade-off`
+- `Trace Search and Analytics` -> `Tracing without Limits™`
+- `turnkey` -> `ready to use`
+- `under the hood` -> ``
+- `utilize` -> `use`
+- `very` -> ``
+- `via` -> `with|through`
+- `visit` -> `see|read`
+- `webserver` -> `web server`
+- `web site` -> `website`
+- `X-axis` -> `x-axis`
+- `Y-axis` -> `y-axis`
+- `(?:github|Github)` -> `GitHub`
+- `(?:kubernetes|k8s|K8s|K8S)` -> `Kubernetes`
+- `(?:Mapreduce|mapreduce|Map reduce|Map Reduce)` -> `MapReduce`
+- `memcached` -> `Memcached`
+- `(?:nginx|Nginx)` -> `NGINX`
+- `(?:node.js|nodeJS|NodeJS|node.JS|Node.JS)` -> `Node.js`
+- `(?:pagerduty|pager duty|Pagerduty|Pager duty)` -> `PagerDuty`
+- `prometheus` -> `Prometheus`
+- `(?:sql|Sql)` -> `SQL`
+- `(?:statsd|statsD|Statsd)` -> `StatsD`
+- `(?:unix|Unix)` -> `UNIX`
+
+**Ignore Case:** False
+
+### Do not use Latin abbreviations
+
+**Level:** *warning*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#abbreviations)
+
+**Swap:**
+- `\b(?:eg|e\.g\.|eg\.)[\s,]` -> `for example`
+- `\b(?:ie|i\.e\.|ie\.)[\s,]` -> `that is`
+
+**Ignore Case:** True
+
+### '%s' should use sentence-style capitalization
+
+**Level:** *warning*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#headers)
+
+
+Exceptions:
+
+- `ACLs`
+- `ActiveMQ XML Integration`
+- `Agent`
+- `Agentless`
+- `Agents`
+- `Airflow`
+- `Amazon`
+- `Amazon Web Services`
+- `APCu`
+- `APIs`
+- `APM`
+- `Application Performance Monitoring`
+- `APM & Continuous Profiler`
+- `App Analytics`
+- `App Service`
+- `AppVeyor`
+- `Application Security Management`
+- `Application Vulnerability Management`
+- `AuthN`
+- `Autodiscovery`
+- `AWS Step Functions`
+- `AWS Systems Manager`
+- `Azure`
+- `Azure App Service`
+- `Azure App Service Plan`
+- `Azure Blob Storage`
+- `Azure Event Hub`
+- `Audit Trail`
+- `BitBucket`
+- `BuildKite`
+- `Browser Monitoring`
+- `CakePHP`
+- `Cassandra Nodetool`
+- `Cassandra Nodetool Integration`
+- `CentOS`
+- `Chef`
+- `CircleCI`
+- `CI/CD`
+- `CI Visibility`
+- `Clipboard`
+- `Cloud Cost Management`
+- `Cloud Pub Sub`
+- `Cloud Security Management`
+- `Cloud Security Posture Management`
+- `Cloud SIEM`
+- `Cloud Workload Security`
+- `CloudFormation`
+- `CloudSQL`
+- `CloudTrail`
+- `CloudWatch`
+- `Cluster Agent`
+- `Continuous Profiler`
+- `Continuous Testing`
+- `DaemonSet`
+- `Data Collected`
+- `Database Monitoring`
+- `Datadog`
+- `DatadogMetric`
+- `Datadog Agent Manager`
+- `Datadog for Government`
+- `Datadog Forwarder`
+- `Datadog Lambda Extension`
+- `Datadog Operator`
+- `Datadog Plugin`
+- `Datadog Watchdog`
+- `DatadogHook`
+- `Debian`
+- `Detection Rules`
+- `Docker`
+- `Docker Compose`
+- `Docker Swarm`
+- `Dockerfile`
+- `DogStatsD`
+- `Envoy`
+- `Fargate`
+- `FastCGI`
+- `Firehose Nozzle`
+- `FireLens`
+- `Fluent Bit`
+- `Fluentd`
+- `FreeBSD`
+- `FreeSwitch`
+- `Further Reading`
+- `GeoIP`
+- `Git`
+- `GitHub`
+- `GitHub Actions`
+- `GitLab`
+- `GitLab Runner Integration`
+- `Google`
+- `Google Analytics`
+- `Google Cloud`
+- `Google Cloud Functions`
+- `GraphQL`
+- `Gunicorn`
+- `HAProxy`
+- `HBase RegionServer Integration`
+- `HDFS DataNode Integration`
+- `HDFS NameNode Integration`
+- `Helm`
+- `Heroku`
+- `HipChat`
+- `HostPort`
+- `I`
+- `IdP`
+- `IDs`
+- `iLert`
+- `Incident Management`
+- `Infrastructure Monitoring`
+- `Ingress Controller`
+- `Internet Information Services`
+- `IoT`
+- `IPs`
+- `Java`
+- `JavaScript`
+- `JBoss`
+- `Jenkins`
+- `JFrog`
+- `JFrog Artifactory`
+- `Jira`
+- `JMXFetch`
+- `Journald`
+- `Kafka`
+- `Kafka Consumer Integration`
+- `Kubernetes`
+- `Kubernetes Engine`
+- `Kubernetes Pod`
+- `Kubernetes Service`
+- `Lambda`
+- `Lambda Layer`
+- `Lambda@Edge`
+- `LaunchDarkly`
+- `Linux`
+- `Live Analytics`
+- `Live Search`
+- `Live Tail`
+- `Log Explorer`
+- `Log Management`
+- `Log Rehydration`
+- `Logback`
+- `macOS`
+- `Marketplace`
+- `MarkLogic`
+- `Meraki`
+- `Mesos Slave Integration`
+- `Metrics Explorer`
+- `Metrics without Limits`
+- `Mobile Monitoring`
+- `MongoDB`
+- `MsTest`
+- `MySQL`
+- `Network Address Translation`
+- `Network Device Monitoring`
+- `Network Performance Monitoring`
+- `New Relic`
+- `NGINX Plus`
+- `NixOS`
+- `Node`
+- `Notebook`
+- `Notebook List`
+- `npm`
+- `NXLog`
+- `Observability Pipelines`
+- `OkHttp`
+- `OneLogin`
+- `OPcache`
+- `OpenLDAP`
+- `OpenMetrics`
+- `OpenShift`
+- `OpenStack`
+- `openSUSE`
+- `OpenTelemetry`
+- `OpenTracing`
+- `OpenVPN`
+- `OpsGenie`
+- `OpsWorks`
+- `Oracle Instant Client`
+- `Phusion Passenger`
+- `Pipeline Visibility`
+- `Pivotal Platform`
+- `Postgres`
+- `PostgreSQL`
+- `PowerDNS`
+- `Prometheus`
+- `Prometheus Alertmanager`
+- `Puppet`
+- `Python`
+- `RabbitMQ`
+- `Rails`
+- `Rancher`
+- `Real User Monitoring`
+- `Red Hat`
+- `Redis`
+- `ReplicaSet`
+- `RocketPants`
+- `Roku Monitoring`
+- `Root Cause Analysis`
+- `Route53`
+- `RSpec`
+- `Ruby`
+- `RUM`
+- `RumMonitor`
+- `SafeNet`
+- `SaltStack`
+- `Security Monitoring`
+- `Security Signal`
+- `Security Signals`
+- `SELinux`
+- `Sensitive Data Scanner`
+- `Serverless APM`
+- `Serverless Framework`
+- `Serverless Monitoring`
+- `Serverless Workload Monitoring`
+- `Service Checks`
+- `Session Replay`
+- `Siri`
+- `Slack`
+- `SLIs`
+- `SLOs`
+- `socat`
+- `Social Security`
+- `SQL Server`
+- `SQLDelight`
+- `SQLite`
+- `Stackdriver`
+- `StackPulse`
+- `StackStorm`
+- `StatsD`
+- `Sumo Logic`
+- `Swift`
+- `Synthetic Monitoring`
+- `Syslog`
+- `sysOID`
+- `System Core`
+- `System Swap`
+- `Teamcity`
+- `Terraform`
+- `Testing Visibility`
+- `TokuMX`
+- `Tracing Without Limits`
+- `Trello`
+- `Twilio`
+- `TypeScript`
+- `Ubuntu`
+- `Unified Service Tagging`
+- `Unix`
+- `Unix Domain Socket`
+- `URLs`
+- `User Datagram Protocol`
+- `USM`
+- `Universal Service Monitoring`
+- `Varnish`
+- `Vector`
+- `Vertica`
+- `VMWare`
+- `vSphere`
+- `Watchdog`
+- `Watchdog Insights`
+- `Webhook`
+- `WildFly`
+- `Windows`
+- `Xray`
+- `ZooKeeper`
+
+
+### Missing ™ on phrase '%s'
+
+**Level:** *error*
+
+[Link](https://www.datadoghq.com)
+
+**Tokens:**
+- `(?
+Exceptions:
+
+- `(?:A|a)dvertise`
+- `(?:A|a)dvise`
+- `(?:A|a)ppraise`
+- `(?:A|a)pprise`
+- `(?:A|a)rise`
+- `(?:C|c)hastise`
+- `(?:C|c)ircumcise`
+- `(?:C|c)lockwise`
+- `(?:C|c)omprise`
+- `(?:C|c)ompromise`
+- `(?:C|c)oncise`
+- `(?:C|c)ounterclockwise`
+- `(?:D|d)emise`
+- `(?:D|d)espise`
+- `(?:D|d)evise`
+- `(?:D|d)isguise`
+- `(?:E|e)nterprise`
+- `(?:E|e)xcise`
+- `(?:E|e)xercise`
+- `(?:E|e)xpertise`
+- `(?:F|f)ranchise`
+- `(?:I|i)mprecise`
+- `(?:I|i)mprovise`
+- `(?:I|i)ncise`
+- `(?:L|l)ikewise`
+- `(?:M|m)erchandise`
+- `(?:N|n)oise`
+- `(?:O|o)therwise`
+- `(?:P|p)aradise`
+- `(?:P|p)oise`
+- `(?:P|p)raise`
+- `(?:P|p)recise`
+- `(?:P|p)remise`
+- `(?:P|p)romise`
+- `(?:R|r)evise`
+- `(?:R|r)ise`
+- `(?:S|s)upervise`
+- `(?:S|s)urmise`
+- `(?:S|s)urprise`
+- `(?:T|t)elevise`
+- `(?:W|w)ise`
+- `(?:d|D)etours?`
+- `(?:c|C)ontours?`
+- `(?:g|G)lamour`
+- `(?:o|O)utpour`
+- `(?:s|S)cours?`
+- `(?:t|T)roubadours?`
+- `(?:p|P)ompadour`
+
+
+**Ignore Case:** True
+
+### Avoid first-person pronouns such as '%s'
+
+**Level:** *warning*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#pronouns)
+
+**Tokens:**
+- `(?<=^|\s)I(?=\s)`
+- `(?<=^|\s)I,(?=\s)`
+- `\bI'm\b`
+- `(?<=\s)[Mm]e\b`
+- `(?<=\s)[Mm]y\b`
+- `(?<=\s)[Mm]ine\b`
+- `(?<=\s)[Ww]e\b`
+- `we'(?:ve|re)`
+- `(?<=\s)[Uu]s\b`
+- `(?<=\s)[Oo]ur\b`
+- `\blet's\b`
+
+### Avoid en dashes ('–'). For hyphenated words, use a hyphen ('-').
+For parenthesis, use an em dash ('—')
+
+**Level:** *error*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#dashes)
+
+**Tokens:**
+- `–`
+
+### Use %s (the former, to refer to Datadog's mechanism for applying integration configurations to containers; the latter, to refer to automatic discovery IN GENERAL) instead of '%s'
+
+**Level:** *warning*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#words-and-phrases)
+
+**Swap:**
+- `{'(?:autodiscovery|auto-discovery|Auto-discovery)': 'Autodiscovery|automatic detection'}`
+- `{'(?:autodiscover|auto-discover|Auto-discover)': 'Autodiscover|automatically detect'}`
+- `{'(?:autodiscovered|auto-discovered|Auto-discovered)': 'Autodiscovered|automatically detected'}`
+
+**Ignore Case:** False
+
+### Use gender-neutral pronouns
+
+**Level:** *error*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#gender)
+
+**Tokens:**
+- `he/she`
+- `s/he`
+- `\(s\)he`
+- `\bhe\b`
+- `\bhim\b`
+- `\bhis\b`
+- `\bshe\b`
+- `\bher\b`
+
+**Ignore Case:** True
+
+### Use only one space between words and sentences (not two)
+
+**Level:** *error*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#spaces)
+
+**Tokens:**
+- `[\w.?!,\(\)\-":] {2,}[\w.?!,\(\)\-":]`
+
+### Use straight quotes instead of smart quotes
+
+**Level:** *error*
+
+**Tokens:**
+- `“`
+- `”`
+- `‘`
+- `’`
+
+### Format times as 'HOUR:MINUTE a.m.' or HOUR:MINUTE p.m.' instead of '%s'
+
+**Level:** *warning*
+
+[Link](https://datadoghq.atlassian.net/wiki/spaces/WRIT/pages/2732523547/Style+guide#%s)
+
+**Tokens:**
+- `(1[012]|[1-9]):[0-5][0-9] (A\.M\.|P\.M\.)`
+- `(1[012]|[1-9]):[0-5][0-9] (?i)(a\.m[^\.]|p\.m[^\.])`
+- `(1[012]|[1-9]):[0-5][0-9][ ]?(?i)(am|pm)`
+
+### Use the Oxford comma in '%s'
+
+**Level:** *suggestion*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#commas)
+
+**Tokens:**
+- `(?:[^,]+,){1,}\s\w+\s(?:and|or)`
+
+### Don't put a space before or after a dash
+
+**Level:** *warning*
+
+[Link](https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#dashes)
+
+**Tokens:**
+- `\s[—–]\s`
+
+### Try to keep your sentence length to 25 words or fewer
+
+**Level:** *suggestion*
+
+**Ignore Case:** False
+
+
+## CWS-Names
+
+### Rule names should not start with '%s'
+
+**Level:** *error*
+
+**Tokens:**
+- `A`
+- `An`
+- `The`
+
+**Ignore Case:** False
+
+### Rule names should avoid weak works like '%s'
+
+**Level:** *error*
+
+[Link](https://developers.google.com/tech-writing/one/clear-sentences)
+
+**Tokens:**
+- `was`
+- `were`
+- `is`
+- `are`
+
+**Ignore Case:** True
+
+### Rule names should use sentence case
+
+**Level:** *error*
+
+
+Exceptions:
+
+- `OverlayFS`
+- `DNS`
+- `TXT`
+- `Kubernetes`
+
+
+### New Value rules should use '%s' instead of '%s'
+
+**Level:** *error*
+
+**Swap:**
+- `unrecognized` -> `unfamiliar`
+- `unusual` -> `unfamiliar`
+- `new` -> `unfamiliar`
+
+**Ignore Case:** True
+
+### Rule names should not be longer than 10 words
+
+**Level:** *error*
+
+**Ignore Case:** False
+
diff --git a/scripts/update-rules-page.py b/scripts/update-rules-page.py
new file mode 100644
index 0000000..85956ec
--- /dev/null
+++ b/scripts/update-rules-page.py
@@ -0,0 +1,78 @@
+import os
+import yaml
+from datetime import datetime
+
+def generate_rule_markdown(rule_data):
+
+ ## Use description field if it exists; if not, use message field
+ description = rule_data.get('description', rule_data['message'].rstrip('.'))
+ markdown = f"### {description}\n\n"
+ markdown += f"**Level:** *{rule_data['level']}*\n\n"
+
+ if 'link' in rule_data:
+ markdown += f"[Link]({rule_data['link']})\n\n"
+
+ for field in ['tokens']:
+ if field in rule_data:
+ markdown += f"**{field.capitalize()}:**\n"
+ for item in rule_data[field]:
+ markdown += f"- `{item}`\n"
+ markdown += "\n"
+
+ if 'exceptions' in rule_data:
+ markdown += "\nExceptions:
\n\n"
+ for exception in rule_data['exceptions']:
+ markdown += f"- `{exception}`\n"
+ markdown += " \n\n"
+
+ if 'swap' in rule_data:
+ markdown += "**Swap:**\n"
+ if isinstance(rule_data['swap'], dict):
+ for key, value in rule_data['swap'].items():
+ markdown += f"- `{key}` -> `{value}`\n"
+ elif isinstance(rule_data['swap'], list):
+ for item in rule_data['swap']:
+ markdown += f"- `{item}`\n"
+ markdown += "\n"
+
+ if 'ignorecase' in rule_data:
+ markdown += f"**Ignore Case:** {rule_data['ignorecase']}\n\n"
+
+ return markdown
+
+def process_subfolder(subfolder_path):
+ markdown_content = ""
+ for root, _, files in os.walk(subfolder_path):
+ for file in files:
+ if file.endswith('.yml'):
+ with open(os.path.join(root, file), 'r') as f:
+ rule_data = yaml.safe_load(f)
+ markdown_content += generate_rule_markdown(rule_data)
+ return markdown_content
+
+def generate_table_of_contents(style_folders):
+ toc = "## Table of Contents\n"
+ for folder in style_folders:
+ toc += f"- [{folder}](#{folder.lower()})\n"
+ return toc
+
+def main():
+ styles_folder = 'styles'
+ style_folders = [folder for folder in os.listdir(styles_folder)
+ if os.path.isdir(os.path.join(styles_folder, folder))]
+
+ markdown_content = "# Vale Rules Overview\n\n"
+ markdown_content += "This page provides a comprehensive list of the Vale linter rules used in Datadog documentation.\n\n"
+ markdown_content += f"Last Updated: {datetime.now().strftime('%Y-%m-%d')}\n\n"
+ markdown_content += generate_table_of_contents(style_folders)
+
+ for style_folder in style_folders:
+ subfolder_path = os.path.join(styles_folder, style_folder)
+ markdown_content += f"\n## {style_folder}\n\n"
+ markdown_content += process_subfolder(subfolder_path)
+
+ with open('RULES.md', 'w') as file:
+ file.write(markdown_content)
+
+if __name__ == '__main__':
+ main()
\ No newline at end of file
diff --git a/styles/Datadog/abbreviations.yml b/styles/Datadog/abbreviations.yml
index bcd2163..356d424 100644
--- a/styles/Datadog/abbreviations.yml
+++ b/styles/Datadog/abbreviations.yml
@@ -1,4 +1,5 @@
extends: substitution
+description: Do not use Latin abbreviations
message: "Use '%s' instead of abbreviations like '%s'."
link: "https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#abbreviations"
ignorecase: true
diff --git a/styles/Datadog/americanspelling.yml b/styles/Datadog/americanspelling.yml
index 415b8e6..9618399 100644
--- a/styles/Datadog/americanspelling.yml
+++ b/styles/Datadog/americanspelling.yml
@@ -1,4 +1,5 @@
extends: existence
+description: Use American spelling
message: "In general, use American spelling instead of '%s'."
link: 'https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md'
ignorecase: true
diff --git a/styles/Datadog/gender.yml b/styles/Datadog/gender.yml
index b2b19b7..cc0a570 100644
--- a/styles/Datadog/gender.yml
+++ b/styles/Datadog/gender.yml
@@ -1,4 +1,5 @@
extends: existence
+description: Use gender-neutral pronouns
message: "Use a gender-neutral pronoun instead of '%s'."
link: "https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#gender"
level: error
diff --git a/styles/Datadog/inclusive.yml b/styles/Datadog/inclusive.yml
index bc1a9df..8a815f0 100644
--- a/styles/Datadog/inclusive.yml
+++ b/styles/Datadog/inclusive.yml
@@ -1,4 +1,5 @@
extends: substitution
+description: Use inclusive language
message: "Use '%s' instead of '%s'."
link: "https://github.com/DataDog/documentation/blob/master/CONTRIBUTING.md#inclusive-language"
ignorecase: true