Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 6 additions & 1 deletion .github/workflows/docs-tests.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ jobs:
config: .markdownlint.yaml
globs: |
docs/**/*.md
cookbook/**/*.md
Comment thread
DmitryAnansky marked this conversation as resolved.

vale:
name: vale action
Expand All @@ -31,7 +32,11 @@ jobs:
steps:
- name: Checkout Repository
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- name: Markup Link Checker (mlc)
- name: Markup Link Checker (mlc) - docs
uses: becheran/mlc@7ec24825cefe0c9c8c6bac48430e1f69e3ec356e # v1.2.0
with:
args: ./docs
- name: Markup Link Checker (mlc) - cookbook
uses: becheran/mlc@7ec24825cefe0c9c8c6bac48430e1f69e3ec356e # v1.2.0
with:
args: ./cookbook
30 changes: 30 additions & 0 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ Issue comments and discussion replies are expected to be written in the contribu
- [Local source code usage](#local-source-code-usage)
- [Tests](#tests)
- [Contribute documentation](#contribute-documentation)
- [Contribute to the cookbook](#contribute-to-the-cookbook)
- [Project structure](#project-structure)
- [Release flow](#release-flow)

Expand Down Expand Up @@ -342,6 +343,33 @@ mlc docs/
The tool only checks links within the local docs (it can't check links to other docs sections that are present when we publish all products under https://redocly.com/docs), and doesn't currently check anchors.
Take care when renaming pages or titles.

## Contribute to the cookbook

The [cookbook](./cookbook) is a community collection of rulesets, configuration, custom plugins, and other Redocly CLI additions.
Unlike the packages, it is not built or tested as part of the CLI — treat every entry as a shared example that people use at their own risk.
A cookbook-only change does not affect the published packages, so it does not need a changeset; add the `no changeset needed` label to the pull request instead.

To add an entry:

1. Pick the top-level category under `cookbook/` that fits best (`rulesets`, `configurable-rules`, `custom-plugins`, `custom-plugin-decorators`, `custom-plugin-rules`, or `miscellaneous`), and create a directory inside it named for what you are adding.
Comment thread
Daryna-del marked this conversation as resolved.
Give it a meaningful name — people browse the collection this way.

```text
cookbook
└── configurable-rules
└── endpoints-are-tagged-cupcake
```

1. Put the file or files you want to share into the new directory, and name them so others can reuse and understand them.

1. Add a `README.md` to the directory that explains the problem the entry solves and any context a reader needs to reuse it successfully.
Follow the structure of the existing entries.

1. List your entry in the relevant section of the [cookbook catalog](./cookbook/README.md).

1. Open a pull request.
Someone from Redocly will review it, suggest changes if needed, and merge it once it is ready.

## Project structure

- **`tests/e2e`**: contains e2e tests.
Expand Down Expand Up @@ -371,6 +399,8 @@ Take care when renaming pages or titles.

- **`resources`**: contains some example API descriptions and configuration files that might be useful for testing.

- **`cookbook`**: contains the community cookbook — shared rulesets, configuration, custom plugins, and other Redocly CLI additions. It is not part of the build or test suite.

## Release flow

We use [Changesets](https://github.com/changesets/changesets) flow.
Expand Down
88 changes: 88 additions & 0 deletions cookbook/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
# Redocly CLI Cookbook

A community collection of rulesets, configuration, custom plugins and other additions for [Redocly CLI](https://github.com/Redocly/redocly-cli). We know our users have some great tips, examples, and code to share, and this is the place to do just that. We would love to have your [contributions](#contributing) here too!

> [!IMPORTANT]
> Redocly are the repository maintainers, but we can't thoroughly test everything here. Please browse, share, and use what you find at your own risk.

If you're new to Redocly CLI, start with the [documentation](https://redocly.com/docs/cli/) to get up and running, then come back here to pick out any elements you would like to re-use yourself. To keep up with new developments, either subscribe to the project repository, or [sign up for the Redocly product newsletter](https://redocly.com/product-updates/).

## Usage

Use the content here as a starting point for your own work.

1. Take a look at what's available in each category, and pick any that you think apply to your situation.

2. Each section links to the documentation for that feature, in case you need an introduction or refresher.

3. Copy and paste the examples you want to use into your own setup, then edit them to fit your own needs.

If you come up with something new, please consider sharing it here by opening a pull request.

## Categories

### Rulesets

Combine existing [built-in rules](https://redocly.com/docs/cli/rules/built-in-rules/) in ways that serve a specific purpose, and make a [reusable ruleset](https://redocly.com/docs/cli/guides/configure-rules/#create-a-reusable-ruleset).

- [Spec-compliant ruleset](rulesets/spec-compliant/)
- [Spot common mistakes](rulesets/common-mistakes)
- [Security ruleset](rulesets/security) adds some defensive rules to your description.

### Configurable rules

There are some fantastic examples of [configurable rules](https://redocly.com/docs/cli/rules/configurable-rules/) in the wild, we hope the list here inspires you to share more of your own!

- [Ban certain words from descriptions](configurable-rules/description-banned-words/)
- [Require `items` field for schemas of type `array`](configurable-rules/required-items-for-array-schemas/)
- [Ensure sentence case in operation summaries](configurable-rules/operation-summary-sentence-case)
- [`POST` SHOULD define `requestBody` schema](configurable-rules/operation-post-should-define-request-body/)
- [`GET` SHOULD NOT define `requestBody` schema](configurable-rules/operation-get-should-not-define-requestBody/)
- [`DELETE` SHOULD NOT define `requestBody` schema](configurable-rules/operation-delete-should-not-define-requestBody/)
- [Info section must have a description](configurable-rules/info-description)
- [No `<script>` tags in descriptions](configurable-rules/no-script)
- [Paths should not match a pattern](configurable-rules/path-excludes-pattern/)
- [API healthcheck rules](configurable-rules/api-health/)
- [String schemas length defined](configurable-rules/string-schemas-length-defined/)
- [JSON Schema misconfigurations](configurable-rules/json-schema-misconfigurations/)
- [Azure APIM unsupported keywords](configurable-rules/azure-apim-unsupported-keyword/)
- [Operation-deprecated-response-headers](configurable-rules/operation-deprecated-response-headers/)
- [`operation-operationId` variant that excludes `OPTIONS`](configurable-rules/operation-operationId-exclude-OPTIONS/)

### Custom plugins

The [custom plugin](https://redocly.com/docs/cli/custom-plugins/) is the ultimate in extensibility, but it's an advanced feature. Try these plugins for inspiration and to get you started. Rather than including the whole plugin, there are also sections for individual rules and decorators further down.

- [Sorting plugin](./custom-plugins/sorting) - rules to check sort order and decorators to transform an API description into the correct order. Includes sorting for tags, methods, properties and enum values.

#### Decorators (for custom plugins)

- [Tag sorting](./custom-plugin-decorators/tag-sorting) - put your tags list in alphabetical order.
- [Substitute datetime placeholders in an API description](./custom-plugin-decorators/update-example-dates) - update dates in examples to the current date.
- [OpenAI isConsequential](./custom-plugin-decorators/openai-is-consequential) - add `x-openai-isConsequential: true` specification extension to GET operations.
- [Remove extensions](./custom-plugin-decorators/remove-extensions) - remove any given [OpenAPI Extensions](https://spec.openapis.org/oas/v3.1.0#specification-extensions) from an OpenAPI document.
- [Remove unused tags](./custom-plugin-decorators/remove-unused-tags) - remove tags that are declared but not used by any operations.
- [Azure APIM](./custom-plugin-decorators/azure-apim) - remove features unsupported by Azure APIM such as examples.
- [Swap summary and description](./custom-plugin-decorators/swap-summary-description) - swap the contents of summary and description fields if they are the wrong way round.
- [Apply root-level security](./custom-plugin-decorators/apply-root-security) - re-apply root-level `security` to operations that lose it after `redocly join`.
- [Set servers URLs](./custom-plugin-decorators/set-servers-urls) - set or overwrite the API `servers` URLs, even when the source description has none.

#### Rules (for custom plugins)

- [Validate Markdown](./custom-plugin-rules/markdown-validator) - check Markdown in description fields is valid.
- [Check code samples](./custom-plugin-rules/code-sample-checks) - check that an expected list of code samples is present in `x-code-samples` for every operation.
- [Default is an enum](./custom-plugin-rules/default-enum-match) - check that a schema's `default` is one of its `enum` values.

### Miscellaneous (including tips and tricks)

Share anything that didn't fit the existing categories here.

- [Script to re-order an API description](./miscellaneous/reorder-bundled-description-properties/) and put the top-level properties in a particular order.

## Contributing

Please share your best Redocly CLI usage with us! Each item should be shared in its own pull request, following the existing directory structure and including a `README.md` in each folder. Full instructions are in the [contributing guide](../CONTRIBUTING.md#contribute-to-the-cookbook).

## Requests

If there's something you think should be in the collection and it isn't, let us know! Open an issue, and describe the problem you'd like to see solved with Redocly CLI. We can't make promises, but we are pretty sure someone out there will know the answer.
134 changes: 134 additions & 0 deletions cookbook/configurable-rules/api-health/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
# API Health

Authors:

- [`adamaltman`](https://github.com/adamaltman) Adam Altman (Redocly)

## What this does and why

This set of configurable rules checks that an API conforms to expected health check standards.
Three rules are included and they check the following:

- `/health` endpoint is defined
- The `200` and `400` responses use the `application/health+json` media type
- The response contains the mandatory `status` property

Source: [Proposed Health Check Response Format for HTTP APIs](https://datatracker.ietf.org/doc/html/draft-inadarei-api-health-check-06).

## Code

The first rule checks that a health path is defined.

```yaml
rule/health-endpoint:
subject:
type: Paths
assertions:
required:
- '/health'
message: API must have a health endpoint.
```

The second rule checks that the response uses the `application/health+json` media type.

It uses a `where` clause to target the check to the successful health response.

```yaml
rule/health-media-type:
subject:
type: MediaTypesMap
assertions:
const: application/health+json
where:
- subject:
type: PathItem
matchParentKeys: '/health'
assertions:
defined: true
- subject:
type: Response
filterInParentKeys:
- '200'
- '400'
assertions:
defined: true
message: API Health response has media type `application/health+json`
severity: error
```

The final rule checks that the response has the required `status` property.

It uses a `where` clause to target the check to the successful health response.

```yaml
rule/health-schema-status:
where:
- subject:
type: PathItem
matchParentKeys: '/health'
assertions:
defined: true
- subject:
type: Response
filterInParentKeys:
- '200'
- '400'
assertions:
defined: true
subject:
type: SchemaProperties
assertions:
required:
- status
message: API Health response must have a required property `status`
severity: error
```

## Examples

The following OpenAPI passes the configurable rules.

```yaml
openapi: 3.1.0
info:
title: Sample health check
version: demo
paths:
/health:
get:
summary: Health check
description: Check the health of our API.
operationId: Health
responses:
'200':
description: Pass or warn
content:
application/health+json:
schema:
type: object
properties:
status:
type: string
description: The status of the API.
enum:
- pass
- warn
'400':
description: Fail
content:
application/health+json:
schema:
type: object
properties:
status:
type: string
description: The status of the API.
enum:
- fail
```

Not having the `/health` path defined or not have the `status` property or `application/health+json` response media type defined result in problems.

## References

Inspired by the expired draft of a health check standard: https://datatracker.ietf.org/doc/html/draft-inadarei-api-health-check-06
36 changes: 36 additions & 0 deletions cookbook/configurable-rules/api-health/openapi.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
openapi: 3.1.0
info:
title: Sample health check
version: demo
paths:
/health:
get:
summary: Health check
description: Check the health of our API.
operationId: Health
responses:
'200':
description: Pass or warn
content:
application/health+json:
schema:
type: object
properties:
status:
type: string
description: The status of the API.
enum:
- pass
- warn
'400':
description: Fail
content:
application/health+json:
schema:
type: object
properties:
status:
type: string
description: The status of the API.
enum:
- fail
52 changes: 52 additions & 0 deletions cookbook/configurable-rules/api-health/redocly.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
# Reference: https://datatracker.ietf.org/doc/html/draft-inadarei-api-health-check-06
rules:
rule/health-endpoint:
subject:
type: Paths
assertions:
required:
- '/health'
message: API must have a health endpoint.

rule/health-media-type:
subject:
type: MediaTypesMap
assertions:
const: application/health+json
where:
- subject:
type: PathItem
matchParentKeys: '/health'
assertions:
defined: true
- subject:
type: Response
filterInParentKeys:
- '200'
- '400'
assertions:
defined: true
message: API Health response has media type `application/health+json`
severity: error

rule/health-schema-status:
where:
- subject:
type: PathItem
matchParentKeys: '/health'
assertions:
defined: true
- subject:
type: Response
filterInParentKeys:
- '200'
- '400'
assertions:
defined: true
subject:
type: SchemaProperties
assertions:
required:
- status
message: API Health response must have a required property `status`
severity: error
Comment thread
DmitryAnansky marked this conversation as resolved.
Loading
Loading