Repository: Redocly/redocly-cli
Pull request #1656 (2024-08-02 15:11:44)

chore: remap arazzo schema to our internal type
## What/Why/How?

- Remap Arazzo JSON schema to our internal type 
- Add Spot rule sample
- Change makeConfig test util

## Reference

## Testing

## Screenshots (optional)

## Check yourself

- [ ] Code changed? - Tested with redoc/reference-docs/workflows (internal)
- [x] All new/updated code is covered with tests
- [ ] New package installed? - Tested in different environments (browser/node)

## Security

- [x] Security impact of change has been considered
- [x] Code follows company security practices and guidelines


changeset-bot[bot]: ###  ⚠️  No Changeset found

Latest commit: 5b757494d05bca5da18a5e4bbf8d4069eba99b69

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. **If these changes should result in a version bump, you need to add a changeset.**

<details><summary>This PR includes no changesets</summary>

  When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

</details>

[Click here to learn what changesets are, and how to add one](https://github.com/changesets/changesets/blob/main/docs/adding-a-changeset.md).

[Click here if you're a maintainer who wants to add a changeset to this PR](https://github.com/Redocly/redocly-cli/new/feat/updating-arazzo-types?filename=.changeset/eighty-fishes-grab.md&value=---%0A%22%40redocly%2Fopenapi-core%22%3A%20patch%0A---%0A%0Afeat%3A%20remap%20arazzo%20schema%20to%20our%20internal%20type%0A)


github-actions[bot]: | Command | Mean [s] | Min [s] | Max [s] | Relative |
|:---|---:|---:|---:|---:|
| `redocly lint packages/core/src/benchmark/benches/rebilly.yaml` | 1.011 ± 0.036 | 0.974 | 1.105 | 1.03 ± 0.05 |
| `redocly-next lint packages/core/src/benchmark/benches/rebilly.yaml` | 0.984 ± 0.025 | 0.966 | 1.053 | 1.00 |

<!-- thollander/actions-comment-pull-request "latest-vs-next-comparison" -->
github-actions[bot]: <!-- jest coverage report action for options with hash 3339ae53a38c44382c0fb4491bdb282d -->

## Coverage report 



| <div title="Status of coverage:&#10; 🟢 - ok&#10; 🟡 - slightly more than threshold&#10; 🔴 - under the threshold">St.<sup>:grey_question:</sup></div> | Category   | Percentage | Covered / Total |
| :----------------------------------------------------------------------------------------------------------------------------------------------------: | :--------- | :--------- | :-------------: |
|                                                                           🟡                                                                           | Statements | 77.38%     |    4699/6073    |
|                                                                           🟡                                                                           | Branches   | 65.58%     |    1938/2955    |
|                                                                           🟡                                                                           | Functions  | 71.04%     |     763/1074    |
|                                                                           🟡                                                                           | Lines      | 77.58%     |    4436/5718    |


<details><summary>Show files with reduced coverage 🔻</summary>
<br/>

| <div title="Status of coverage:&#10; 🟢 - ok&#10; 🟡 - slightly more than threshold&#10; 🔴 - under the threshold">St.<sup>:grey_question:</sup></div> | File                                                          | Statements                                                    | Branches                                                | Functions                                               | Lines                                                         |
| :----------------------------------------------------------------------------------------------------------------------------------------------------: | :------------------------------------------------------------ | :------------------------------------------------------------ | :------------------------------------------------------ | :------------------------------------------------------ | :------------------------------------------------------------ |
|                                                                           🟡                                                                           | <div title="core/src/types/arazzo.ts">`...` / arazzo.ts</div> | <div title="Base coverage is: 100%">75.32% (-24.68% 🔻)</div> | <div title="Base coverage is: 100%">0% (-100% 🔻)</div> | <div title="Base coverage is: 100%">0% (-100% 🔻)</div> | <div title="Base coverage is: 100%">75.32% (-24.68% 🔻)</div> |

</details>

## Test suite run success
759 tests passing in 107 suites.

<p align="right">Report generated by <a href="https://github.com/ArtiomTr/jest-coverage-report-action">🧪jest coverage report action</a> from 5b757494d05bca5da18a5e4bbf8d4069eba99b69</p>

DmitryAnansky: @RomanHotsiy / @tatomyr 
There is an open question if we need to keep `export const arazzoSchema` in cli or move it back to Spot?

Keeping it in cli will give us single place to manage schemas and not switching between projects.
Also there is some ongoing activities on Arazzo side - they are going to have official schema and we might use it as source of truth in future.
DmitryAnansky: > @RomanHotsiy / @tatomyr There is an open question if we need to keep `export const arazzoSchema` in cli or move it back to Spot?
> 
> Keeping it in cli will give us single place to manage schemas and not switching between projects. Also there is some ongoing activities on Arazzo side - they are going to have official schema and we might use it as the source of truth in future.

Discussed offline - I will move it back to Spot codebase.

Patch:
diff --git a/docs/guides/lint-arazzo.md b/docs/guides/lint-arazzo.md
index ef3f12d1..559e0af4 100644
--- a/docs/guides/lint-arazzo.md
+++ b/docs/guides/lint-arazzo.md
@@ -1,3 +1,9 @@
+---
+seo:
+  title: Lint Arazzo with Redocly CLI
+  description: Unlock powerful linting capabilities for Arazzo documents. Use the Redocly CLI to enforce basic validation, configure rules, or even build custom plugins for Arazzo.
+---
+
 # Lint Arazzo with Redocly CLI
 
 [Arazzo](https://spec.openapis.org/arazzo/latest.html#arazzo-specification) is an open standard from the OpenAPI Initiative for describing a sequence API calls, defining success criteria, and adding response content to subsequent API calls.
@@ -108,6 +114,13 @@ With this action in place, the intentional errors I added to the Arazzo descript
 
 ![Screenshot of annotation flagging "workfloo" as an unexpected value and suggesting "workflow"](images/museum-arazzo-lint.png)
 
+## Arazzo rules
+
+To expand the linting checks for an Arazzo description, start by enabling
+some of the built-in rules. The currently-supported rules are:
+
+- `parameters-no-body-inside-in`: the `in` section inside `parameters` must not contain a `body`.
+
 ## Participate in Redocly CLI
 
 Redocly CLI is an open source project, so we invite you to check out the [code on GitHub](https://github.com/Redocly/redocly-cli/), and open issues to report problems or request features.
diff --git a/jest.config.js b/jest.config.js
index bd440843..1f73e377 100644
--- a/jest.config.js
+++ b/jest.config.js
@@ -13,7 +13,7 @@ module.exports = {
   coverageThreshold: {
     'packages/core/': {
       statements: 80,
-      branches: 72,
+      branches: 71,
       functions: 74,
       lines: 80,
     },
diff --git a/packages/core/src/config/all.ts b/packages/core/src/config/all.ts
index 31d4e0e2..4515f8a2 100644
--- a/packages/core/src/config/all.ts
+++ b/packages/core/src/config/all.ts
@@ -123,7 +123,7 @@ const all: PluginStyleguideConfig<'built-in'> = {
     'channels-kebab-case': 'error',
     'no-channel-trailing-slash': 'error',
   },
-  arazzoRules: { spec: 'error' },
+  arazzoRules: { spec: 'error', 'parameters-no-body-inside-in': 'off' },
 };
 
 export default all;
diff --git a/packages/core/src/config/minimal.ts b/packages/core/src/config/minimal.ts
index 16c2e269..20ba1922 100644
--- a/packages/core/src/config/minimal.ts
+++ b/packages/core/src/config/minimal.ts
@@ -107,6 +107,7 @@ const minimal: PluginStyleguideConfig<'built-in'> = {
   },
   arazzoRules: {
     spec: 'error',
+    'parameters-no-body-inside-in': 'off',
   },
 };
 
diff --git a/packages/core/src/config/recommended-strict.ts b/packages/core/src/config/recommended-strict.ts
index b5482f54..0428bafe 100644
--- a/packages/core/src/config/recommended-strict.ts
+++ b/packages/core/src/config/recommended-strict.ts
@@ -107,6 +107,7 @@ const recommendedStrict: PluginStyleguideConfig<'built-in'> = {
   },
   arazzoRules: {
     spec: 'error',
+    'parameters-no-body-inside-in': 'off',
   },
 };
 
diff --git a/packages/core/src/config/recommended.ts b/packages/core/src/config/recommended.ts
index df79a866..bf43ac36 100644
--- a/packages/core/src/config/recommended.ts
+++ b/packages/core/src/config/recommended.ts
@@ -107,6 +107,7 @@ const recommended: PluginStyleguideConfig<'built-in'> = {
   },
   arazzoRules: {
     spec: 'error',
+    'parameters-no-body-inside-in': 'off',
   },
 };
 
diff --git a/packages/core/src/rules/arazzo/index.ts b/packages/core/src/rules/arazzo/index.ts
index 8e1a4b48..a06234ea 100644
--- a/packages/core/src/rules/arazzo/index.ts
+++ b/packages/core/src/rules/arazzo/index.ts
@@ -1,5 +1,6 @@
 import { Spec } from '../common/spec';
 import { Assertions } from '../common/assertions';
+import { ParametersNoBodyInsideIn } from '../spot/parameters-no-body-inside-in';
 
 import type { ArazzoRule } from '../../visitors';
 import type { ArazzoRuleSet } from '../../oas-types';
@@ -7,6 +8,7 @@ import type { ArazzoRuleSet } from '../../oas-types';
 export const rules: ArazzoRuleSet<'built-in'> = {
   spec: Spec as ArazzoRule,
   assertions: Assertions as ArazzoRule,
+  'parameters-no-body-inside-in': ParametersNoBodyInsideIn as ArazzoRule,
 };
 
 export const preprocessors = {};
diff --git a/packages/core/src/rules/spot/parameters-no-body-inside-in.ts b/packages/core/src/rules/spot/parameters-no-body-inside-in.ts
new file mode 100644
index 00000000..89e7b72c
--- /dev/null
+++ b/packages/core/src/rules/spot/parameters-no-body-inside-in.ts
@@ -0,0 +1,17 @@
+import type { ArazzoRule } from '../../visitors';
+import type { UserContext } from '../../walk';
+
+export const ParametersNoBodyInsideIn: ArazzoRule = () => {
+  return {
+    Parameter: {
+      enter(parameter, { report, location }: UserContext) {
+        if (parameter.in === 'body') {
+          report({
+            message: 'The `body` value of the `in` property is not supported by Spot.',
+            location: location.child(['in']),
+          });
+        }
+      },
+    },
+  };
+};
diff --git a/packages/core/src/types/arazzo.ts b/packages/core/src/types/arazzo.ts
index aec445fe..9beb1517 100755
--- a/packages/core/src/types/arazzo.ts
+++ b/packages/core/src/types/arazzo.ts
@@ -1,220 +1,254 @@
-import { getNodeTypesFromJSONSchema } from './json-schema-adapter';
+import { mapOf, type NodeType, listOf } from '.';
+import { DependentRequired, Schema, SchemaProperties } from './oas3_1';
+import { Discriminator, DiscriminatorMapping, ExternalDocs, Xml } from './oas3';
 
-import type { NodeType } from '.';
-
-export const ARAZZO_ROOT_TYPE = 'Root';
-
-export const operationMethod = {
-  type: 'string',
-  enum: ['get', 'post', 'put', 'delete', 'patch'],
-} as const;
-export const expectSchema = {
-  type: 'object',
+const Root: NodeType = {
   properties: {
-    statusCode: { type: 'number' },
-    mimeType: { type: 'string' },
-    body: {},
-    schema: {
-      type: 'object',
-      additionalProperties: true,
-    },
+    arazzo: { type: 'string', enum: ['1.0.0'] },
+    info: 'Info',
+    sourceDescriptions: 'SourceDescriptions',
+    'x-parameters': 'Parameters',
+    workflows: 'Workflows',
+    components: 'Components',
+  },
+  required: ['arazzo', 'info', 'sourceDescriptions', 'workflows'],
+  extensionsPrefix: 'x-',
+};
+const NamedParameters: NodeType = {
+  properties: {},
+  additionalProperties: 'Parameter',
+};
+const NamedSuccessActions: NodeType = {
+  properties: {},
+  additionalProperties: 'SuccessActionObject',
+};
+const NamedFailureActions: NodeType = {
+  properties: {},
+  additionalProperties: 'FailureActionObject',
+};
+const Components: NodeType = {
+  properties: {
+    inputs: 'NamedInputs',
+    parameters: 'NamedParameters',
+    successActions: 'NamedSuccessActions',
+    failureActions: 'NamedFailureActions',
+  },
+  extensionsPrefix: 'x-',
+};
+const NamedInputs: NodeType = mapOf('Schema');
+const Info: NodeType = {
+  properties: {
+    title: { type: 'string' },
+    description: { type: 'string' },
+    summary: { type: 'string' },
+    version: { type: 'string' },
   },
-  additionalProperties: false,
-  oneOf: [
-    { required: ['statusCode'] },
-    { required: ['mimeType'] },
-    { required: ['body'] },
-    { required: ['schema'] },
-  ],
-} as const;
-const openAPISourceDescriptionSchema = {
-  type: 'object',
+  required: ['title', 'version'],
+  extensionsPrefix: 'x-',
+};
+const SourceDescriptions: NodeType = {
+  properties: {},
+  items: (value: any) => {
+    if (value?.type === 'openapi') {
+      return 'OpenAPISourceDescription';
+    } else if (value?.type === 'arazzo') {
+      return 'ArazzoSourceDescription';
+    } else {
+      return 'NoneSourceDescription';
+    }
+  },
+};
+const OpenAPISourceDescription: NodeType = {
   properties: {
     name: { type: 'string' },
     type: { type: 'string', enum: ['openapi'] },
     url: { type: 'string' },
     'x-serverUrl': { type: 'string' },
   },
-  additionalProperties: false,
   required: ['name', 'type', 'url'],
-} as const;
-const noneSourceDescriptionSchema = {
-  type: 'object',
+  extensionsPrefix: 'x-',
+};
+const NoneSourceDescription: NodeType = {
   properties: {
     name: { type: 'string' },
     type: { type: 'string', enum: ['none'] },
     'x-serverUrl': { type: 'string' },
   },
-  additionalProperties: false,
   required: ['name', 'type', 'x-serverUrl'],
-} as const;
-const arazzoSourceDescriptionSchema = {
-  type: 'object',
+  extensionsPrefix: 'x-',
+};
+const ArazzoSourceDescription: NodeType = {
   properties: {
     name: { type: 'string' },
     type: { type: 'string', enum: ['arazzo'] },
     url: { type: 'string' },
   },
-  additionalProperties: false,
   required: ['name', 'type', 'url'],
-} as const;
-export const sourceDescriptionSchema = {
-  type: 'object',
-  oneOf: [
-    openAPISourceDescriptionSchema,
-    noneSourceDescriptionSchema,
-    arazzoSourceDescriptionSchema,
-  ],
-} as const;
-const sourceDescriptionsSchema = {
-  type: 'array',
-  items: sourceDescriptionSchema,
-} as const;
-const extendedOperation = {
-  type: 'object',
+  extensionsPrefix: 'x-',
+};
+const ReusableObject: NodeType = {
   properties: {
-    path: { type: 'string' },
-    method: operationMethod,
-    sourceDescriptionName: { type: 'string' },
-    serverUrl: { type: 'string' },
-  },
-  additionalProperties: false,
-  required: ['path', 'method'],
-} as const;
-export const parameter = {
-  type: 'object',
-  oneOf: [
-    {
-      type: 'object',
-      properties: {
-        in: { type: 'string', enum: ['header', 'query', 'path', 'cookie', 'body'] },
-        name: { type: 'string' },
-        value: {
-          oneOf: [{ type: 'string' }, { type: 'number' }, { type: 'boolean' }],
-        },
-      },
-      required: ['name', 'value'],
-      additionalProperties: false,
-    },
-    {
-      type: 'object',
-      properties: {
-        reference: { type: 'string' },
-        value: {
-          oneOf: [{ type: 'string' }, { type: 'number' }, { type: 'boolean' }],
-        },
-      },
-      required: ['reference'],
-      additionalProperties: false,
+    reference: { type: 'string' },
+    value: {
+      type: 'string',
     },
-  ],
-} as const;
-const parameters = {
-  type: 'array',
-  items: parameter,
-} as const;
-export const infoObject = {
-  type: 'object',
+  },
+  required: ['reference'],
+  extensionsPrefix: 'x-',
+};
+const Parameter: NodeType = {
   properties: {
-    title: { type: 'string' },
-    description: { type: 'string' },
+    in: { type: 'string', enum: ['header', 'query', 'path', 'cookie', 'body'] },
+    name: { type: 'string' },
+    value: {}, // any
+  },
+  required: ['name', 'value'],
+  extensionsPrefix: 'x-',
+};
+const Parameters: NodeType = {
+  properties: {},
+  items: (value: any) => {
+    if (value?.in) {
+      return 'Parameter';
+    } else {
+      return 'ReusableObject';
+    }
+  },
+};
+const Workflow: NodeType = {
+  properties: {
+    workflowId: { type: 'string' },
     summary: { type: 'string' },
-    version: { type: 'string' },
+    description: { type: 'string' },
+    parameters: 'Parameters',
+    dependsOn: { type: 'array', items: { type: 'string' } },
+    inputs: 'NamedInputs',
+    outputs: 'Outputs',
+    steps: 'Steps',
+    successActions: 'OnSuccessActionList',
+    failureActions: 'OnFailureActionList',
   },
-  additionalProperties: false,
-  required: ['title', 'version'],
-} as const;
-export const replacement = {
-  type: 'object',
+  required: ['workflowId', 'steps'],
+  extensionsPrefix: 'x-',
+};
+const Workflows: NodeType = listOf('Workflow');
+const Steps: NodeType = listOf('Step');
+const Step: NodeType = {
   properties: {
-    target: { type: 'string' },
-    value: {
-      oneOf: [
-        { type: 'string' },
-        { type: 'object' },
-        { type: 'array' },
-        { type: 'number' },
-        { type: 'boolean' },
-      ],
-    },
+    stepId: { type: 'string' },
+    description: { type: 'string' },
+    operationId: { type: 'string' },
+    operationPath: { type: 'string' },
+    workflowId: { type: 'string' },
+    parameters: 'Parameters',
+    successCriteria: listOf('CriterionObject'),
+    onSuccess: 'OnSuccessActionList',
+    onFailure: 'OnFailureActionList',
+    outputs: 'Outputs',
+    'x-inherit': { enum: ['auto', 'none'] },
+    'x-expect': 'ExpectSchema',
+    'x-assert': { type: 'string' },
+    'x-operation': 'ExtendedOperation',
+    requestBody: 'RequestBody',
+  },
+  required: ['stepId'],
+  requiredOneOf: ['x-operation', 'operationId', 'operationPath', 'workflowId'],
+  extensionsPrefix: 'x-',
+};
+const Outputs: NodeType = {
+  properties: {},
+  additionalProperties: {
+    type: 'string',
   },
-} as const;
-export const requestBody = {
-  type: 'object',
+};
+const RequestBody: NodeType = {
   properties: {
     contentType: { type: 'string' },
-    payload: {
-      oneOf: [
-        { type: 'string' },
-        { type: 'object', additionalProperties: true },
-        { type: 'array' },
-        { type: 'number' },
-        { type: 'boolean' },
-      ],
-    },
-    encoding: { type: 'string' },
-    replacements: {
-      type: 'array',
-      items: replacement,
-    },
+    payload: {},
+    replacements: listOf('Replacement'),
   },
-  additionalProperties: false,
   required: ['payload'],
-} as const;
-export const criteriaObject = {
-  type: 'object',
+  extensionsPrefix: 'x-',
+};
+const Replacement: NodeType = {
+  properties: {
+    target: { type: 'string' },
+    value: {},
+  },
+  required: ['target', 'value'],
+  extensionsPrefix: 'x-',
+};
+const ExtendedOperation: NodeType = {
+  properties: {
+    path: { type: 'string' },
+    method: {
+      enum: ['get', 'post', 'put', 'delete', 'patch'],
+    },
+    sourceDescriptionName: { type: 'string' },
+    serverUrl: { type: 'string' },
+  },
+  required: ['path', 'method'],
+};
+const ExpectSchema: NodeType = {
+  properties: {
+    statusCode: { type: 'number' },
+    mimeType: { type: 'string' },
+    body: {},
+    schema: 'Schema',
+  },
+  requiredOneOf: ['statusCode', 'mimeType', 'body', 'schema'],
+};
+const CriterionObject: NodeType = {
   properties: {
     condition: { type: 'string' },
     context: { type: 'string' },
-    type: {
-      oneOf: [
-        { type: 'string', enum: ['regex', 'jsonpath', 'simple', 'xpath'] },
-        {
-          type: 'object',
-          properties: {
-            type: { type: 'string', enum: ['jsonpath'] },
-            version: { type: 'string', enum: ['draft-goessner-dispatch-jsonpath-00'] },
-          },
-        },
-        {
-          type: 'object',
-          properties: {
-            type: { type: 'string', enum: ['xpath'] },
-            version: { type: 'string', enum: ['xpath-30', 'xpath-20', 'xpath-10'] },
-          },
-        },
-      ],
+    type: (value: any) => {
+      if (!value) {
+        return undefined;
+      } else if (typeof value === 'string') {
+        return { enum: ['regex', 'jsonpath', 'simple', 'xpath'] };
+      } else if (value.type === 'jsonpath') {
+        return 'JSONPathCriterion';
+      } else {
+        return 'XPathCriterion';
+      }
     },
   },
   required: ['condition'],
-  additionalProperties: false,
-} as const;
-const criteriaObjects = {
-  type: 'array',
-  items: criteriaObject,
-} as const;
-export const inherit = {
-  type: 'string',
-  enum: ['auto', 'none'],
-} as const;
-const onSuccessObject = {
-  type: 'object',
+};
+const JSONPathCriterion: NodeType = {
+  properties: {
+    type: { type: 'string', enum: ['jsonpath'] },
+    version: { type: 'string', enum: ['draft-goessner-dispatch-jsonpath-00'] },
+  },
+};
+const XPathCriterion: NodeType = {
+  properties: {
+    type: { type: 'string', enum: ['xpath'] },
+    version: { type: 'string', enum: ['xpath-30', 'xpath-20', 'xpath-10'] },
+  },
+};
+const SuccessActionObject: NodeType = {
   properties: {
     name: { type: 'string' },
     type: { type: 'string', enum: ['goto', 'end'] },
     stepId: { type: 'string' },
     workflowId: { type: 'string' },
-    criteria: criteriaObjects,
+    criteria: 'CriterionObject',
   },
-  additionalProperties: false,
   required: ['type', 'name'],
-} as const;
-const onSuccessList = {
-  type: 'array',
-  items: onSuccessObject,
-} as const;
-const onFailureObject = {
-  type: 'object',
+};
+const OnSuccessActionList: NodeType = {
+  properties: {},
+  items: (value: any) => {
+    if (value?.type && value?.name) {
+      return 'SuccessActionObject';
+    } else {
+      return 'ReusableObject';
+    }
+  },
+};
+const FailureActionObject: NodeType = {
   properties: {
     name: { type: 'string' },
     type: { type: 'string', enum: ['goto', 'retry', 'end'] },
@@ -222,170 +256,59 @@ const onFailureObject = {
     stepId: { type: 'string' },
     retryAfter: { type: 'number' },
     retryLimit: { type: 'number' },
-    criteria: criteriaObjects,
+    criteria: 'CriterionObject',
   },
-  additionalProperties: false,
   required: ['type', 'name'],
-} as const;
-const onFailureList = {
-  type: 'array',
-  items: onFailureObject,
-} as const;
-export const step = {
-  type: 'object',
-  properties: {
-    stepId: { type: 'string' },
-    description: { type: 'string' },
-    operationId: { type: 'string' },
-    operationPath: { type: 'string' },
-    workflowId: { type: 'string' },
-    parameters: parameters,
-    successCriteria: criteriaObjects,
-    onSuccess: onSuccessList,
-    onFailure: onFailureList,
-    outputs: {
-      type: 'object',
-      additionalProperties: {
-        oneOf: [
-          {
-            type: 'string',
-          },
-          {
-            type: 'object',
-          },
-          {
-            type: 'array',
-          },
-          {
-            type: 'boolean',
-          },
-          {
-            type: 'number',
-          },
-        ],
-      },
-    },
-    'x-inherit': inherit,
-    'x-expect': expectSchema,
-    'x-assert': { type: 'string' },
-    'x-operation': extendedOperation,
-    requestBody: requestBody,
+};
+const OnFailureActionList: NodeType = {
+  properties: {},
+  items: (value: any) => {
+    if (value?.type && value?.name) {
+      return 'FailureActionObject';
+    } else {
+      return 'ReusableObject';
+    }
   },
-  required: ['stepId'],
-  oneOf: [
-    { required: ['x-operation'] },
-    { required: ['operationId'] },
-    { required: ['operationPath'] },
-    { required: ['workflowId'] },
-  ],
-} as const;
-const steps = {
-  type: 'array',
-  items: step,
-} as const;
-const JSONSchema = {
-  type: 'object',
-  properties: {
-    type: {
-      type: 'string',
-      enum: ['object', 'array', 'string', 'number', 'integer', 'boolean', 'null'],
-    },
-    properties: {
-      type: 'object',
-      additionalProperties: true,
-    },
-    required: {
-      type: 'array',
-      items: { type: 'string' },
-    },
-    items: {
-      type: 'object',
-      additionalProperties: true,
-    },
-  },
-  required: ['type'],
-  additionalProperties: true,
-} as const;
-export const workflow = {
-  type: 'object',
-  properties: {
-    workflowId: { type: 'string' },
-    summary: { type: 'string' },
-    description: { type: 'string' },
-    parameters: parameters,
-    dependsOn: { type: 'array', items: { type: 'string' } },
-    inputs: JSONSchema,
-    outputs: {
-      type: 'object',
-      additionalProperties: {
-        type: 'string',
-      },
-    },
-    steps: steps,
-    successActions: {
-      type: 'array',
-      items: onSuccessObject,
-    },
-    failureActions: {
-      type: 'array',
-      items: onFailureObject,
-    },
-  },
-  additionalProperties: false,
-  required: ['workflowId', 'steps'],
-} as const;
-const workflows = {
-  type: 'array',
-  items: workflow,
-} as const;
-export const arazzoSchema = {
-  type: 'object',
-  properties: {
-    arazzo: { type: 'string', enum: ['1.0.0'] },
-    info: infoObject,
-    sourceDescriptions: sourceDescriptionsSchema,
-    'x-parameters': parameters,
-    workflows: workflows,
-    components: {
-      type: 'object',
-      properties: {
-        inputs: {
-          type: 'object',
-          additionalProperties: {
-            type: 'object',
-            additionalProperties: true,
-            properties: {
-              type: {
-                type: 'string',
-              },
-              properties: {
-                type: 'object',
-                additionalProperties: true,
-              },
-            },
-            required: ['type'],
-          },
-        },
-        parameters: {
-          type: 'object',
-          additionalProperties: parameter,
-        },
-        successActions: {
-          type: 'object',
-          additionalProperties: onSuccessObject,
-        },
-        failureActions: {
-          type: 'object',
-          additionalProperties: onFailureObject,
-        },
-      },
-    },
-  },
-  additionalProperties: false,
-  required: ['arazzo', 'info', 'sourceDescriptions', 'workflows'],
-} as const;
+};
 
-export const ArazzoTypes: Record<string, NodeType> = getNodeTypesFromJSONSchema(
-  ARAZZO_ROOT_TYPE,
-  arazzoSchema
-);
+export const ArazzoTypes: Record<string, NodeType> = {
+  Root,
+  Info,
+  SourceDescriptions,
+  OpenAPISourceDescription,
+  NoneSourceDescription,
+  ArazzoSourceDescription,
+  Parameters,
+  Parameter,
+  ReusableObject,
+  Workflows,
+  Workflow,
+  Steps,
+  Step,
+  RequestBody,
+  Replacement,
+  ExtendedOperation,
+  ExpectSchema,
+  Outputs,
+  CriterionObject,
+  XPathCriterion,
+  JSONPathCriterion,
+  SuccessActionObject,
+  OnSuccessActionList,
+  FailureActionObject,
+  OnFailureActionList,
+  Schema,
+  NamedSchemas: mapOf('Schema'),
+  ExternalDocs,
+  DiscriminatorMapping,
+  Discriminator,
+  DependentRequired,
+  SchemaProperties,
+  PatternProperties: SchemaProperties,
+  Components,
+  NamedInputs,
+  NamedParameters,
+  NamedSuccessActions,
+  NamedFailureActions,
+  Xml,
+};
diff --git a/packages/core/src/types/oas3.ts b/packages/core/src/types/oas3.ts
index 647e3acf..5dcf5b26 100755
--- a/packages/core/src/types/oas3.ts
+++ b/packages/core/src/types/oas3.ts
@@ -44,7 +44,7 @@ const TagGroup: NodeType = {
   extensionsPrefix: 'x-',
 };
 
-const ExternalDocs: NodeType = {
+export const ExternalDocs: NodeType = {
   properties: {
     description: { type: 'string' },
     url: { type: 'string' },
@@ -369,7 +369,7 @@ const Schema: NodeType = {
   extensionsPrefix: 'x-',
 };
 
-const Xml: NodeType = {
+export const Xml: NodeType = {
   properties: {
     name: { type: 'string' },
     namespace: { type: 'string' },
@@ -385,7 +385,7 @@ const SchemaProperties: NodeType = {
   additionalProperties: 'Schema',
 };
 
-const DiscriminatorMapping: NodeType = {
+export const DiscriminatorMapping: NodeType = {
   properties: {},
   additionalProperties: (value: any) => {
     if (isMappingRef(value)) {
@@ -396,7 +396,7 @@ const DiscriminatorMapping: NodeType = {
   },
 };
 
-const Discriminator: NodeType = {
+export const Discriminator: NodeType = {
   properties: {
     propertyName: { type: 'string' },
     mapping: 'DiscriminatorMapping',
diff --git a/packages/core/src/types/oas3_1.ts b/packages/core/src/types/oas3_1.ts
index 80d87a56..c9c5de77 100755
--- a/packages/core/src/types/oas3_1.ts
+++ b/packages/core/src/types/oas3_1.ts
@@ -87,7 +87,7 @@ const Operation: NodeType = {
   extensionsPrefix: 'x-',
 };
 
-const Schema: NodeType = {
+export const Schema: NodeType = {
   properties: {
     $id: { type: 'string' },
     $anchor: { type: 'string' },
@@ -186,7 +186,7 @@ const Schema: NodeType = {
   extensionsPrefix: 'x-',
 };
 
-const SchemaProperties: NodeType = {
+export const SchemaProperties: NodeType = {
   properties: {},
   additionalProperties: (value: any) => {
     if (typeof value === 'boolean') {
@@ -267,7 +267,7 @@ const SecurityScheme: NodeType = {
   extensionsPrefix: 'x-',
 };
 
-const DependentRequired: NodeType = {
+export const DependentRequired: NodeType = {
   properties: {},
   additionalProperties: { type: 'array', items: { type: 'string' } },
 };
diff --git a/packages/core/src/types/redocly-yaml.ts b/packages/core/src/types/redocly-yaml.ts
index c436f10f..d2ee63bf 100644
--- a/packages/core/src/types/redocly-yaml.ts
+++ b/packages/core/src/types/redocly-yaml.ts
@@ -106,7 +106,7 @@ export type BuiltInAsync2RuleId = typeof builtInAsync2Rules[number];
 
 export type BuiltInAsync3RuleId = typeof builtInAsync3Rules[number];
 
-const builtInArazzoRules = ['spec'] as const;
+const builtInArazzoRules = ['spec', 'parameters-no-body-inside-in'] as const;
 
 export type BuiltInArazzoRuleId = typeof builtInArazzoRules[number];
 
diff --git a/packages/core/src/typings/arazzo.ts b/packages/core/src/typings/arazzo.ts
index 5c61171f..6629965e 100644
--- a/packages/core/src/typings/arazzo.ts
+++ b/packages/core/src/typings/arazzo.ts
@@ -1,44 +1,172 @@
-import type { FromSchema } from 'json-schema-to-ts';
-import type {
-  arazzoSchema,
-  parameter,
-  operationMethod,
-  expectSchema,
-  sourceDescriptionSchema,
-  infoObject,
-  requestBody,
-  replacement,
-  inherit,
-  criteriaObject,
-  step,
-  workflow,
-} from '../types/arazzo';
-
-export type ArazzoDefinition = FromSchema<typeof arazzoSchema>;
-export type OperationMethod = FromSchema<typeof operationMethod>;
-export type ResponseContext = {
-  statusCode: number;
-  body: any;
-  headers: Headers;
-  mimeType: string;
-} & Record<string, any>;
-export type Expect = FromSchema<typeof expectSchema>;
-export type SourceDescription = FromSchema<typeof sourceDescriptionSchema>;
-export type Parameter = FromSchema<typeof parameter>;
-export type InfoObject = FromSchema<typeof infoObject>;
-export type RequestBody = FromSchema<typeof requestBody>;
-export type Replacement = FromSchema<typeof replacement>;
-export type Inherit = FromSchema<typeof inherit>;
-export type CriteriaObject = FromSchema<typeof criteriaObject>;
-export type VerboseLog = {
-  method: OperationMethod;
+export interface InfoObject {
+  title: string;
+  description?: string;
+  summary?: string;
+  version: string;
+}
+
+export interface OpenAPISourceDescription {
+  name: string;
+  type: 'openapi';
+  url: string;
+  'x-serverUrl'?: string;
+}
+
+export interface NoneSourceDescription {
+  name: string;
+  type: 'none';
+  'x-serverUrl': string;
+}
+
+export interface ArazzoSourceDescription {
+  name: string;
+  type: 'arazzo';
+  url: string;
+}
+
+export type SourceDescription =
+  | OpenAPISourceDescription
+  | NoneSourceDescription
+  | ArazzoSourceDescription;
+
+export interface Parameter {
+  in?: 'header' | 'query' | 'path' | 'cookie' | 'body';
+  name: string;
+  value: string | number | boolean;
+  reference?: string;
+}
+
+export interface ExtendedOperation {
   path: string;
-  host: string;
-  body?: any;
-  headerParams?: Record<string, string>;
+  method: 'get' | 'post' | 'put' | 'delete' | 'patch';
+  sourceDescriptionName?: string;
+  serverUrl?: string;
+}
+
+export interface ExpectSchema {
   statusCode?: number;
-};
-export type Step = FromSchema<typeof step>;
-export type Workflow = FromSchema<typeof workflow> & {
+  mimeType?: string;
+  body?: any;
+  schema?: {
+    [key: string]: any;
+  };
+}
+
+export interface Replacement {
+  target: string;
+  value: string | object | any[];
+}
+
+export interface RequestBody {
+  contentType?: string;
+  payload: string | object | any[];
+  encoding?: string;
+  replacements?: Replacement[];
+}
+
+export interface CriteriaObject {
+  condition: string;
+  context?: string;
+  type?:
+    | 'regex'
+    | 'jsonpath'
+    | 'simple'
+    | 'xpath'
+    | {
+        type: 'jsonpath';
+        version: 'draft-goessner-dispatch-jsonpath-00';
+      }
+    | {
+        type: 'xpath';
+        version: 'xpath-30' | 'xpath-20' | 'xpath-10';
+      };
+}
+
+export interface OnSuccessObject {
+  name: string;
+  type: 'goto' | 'end';
+  stepId?: string;
+  workflowId?: string;
+  criteria?: CriteriaObject[];
+}
+
+export interface OnFailureObject {
+  name: string;
+  type: 'goto' | 'retry' | 'end';
+  workflowId?: string;
+  stepId?: string;
+  retryAfter?: number;
+  retryLimit?: number;
+  criteria?: CriteriaObject[];
+}
+
+export interface Step {
+  stepId: string;
+  description?: string;
+  operationId?: string;
+  operationPath?: string;
+  workflowId?: string;
+  parameters?: Parameter[];
+  successCriteria?: CriteriaObject[];
+  onSuccess?: OnSuccessObject[];
+  onFailure?: OnFailureObject[];
+  outputs?: {
+    [key: string]: string | object | any[] | boolean | number;
+  };
+  'x-inherit'?: 'auto' | 'none';
+  'x-expect'?: ExpectSchema;
+  'x-assert'?: string;
+  'x-operation'?: ExtendedOperation;
+  requestBody?: RequestBody;
+}
+
+export interface Workflow {
+  workflowId: string;
+  summary?: string;
+  description?: string;
+  parameters?: Parameter[];
+  dependsOn?: string[];
+  inputs?: {
+    type: 'object' | 'array' | 'string' | 'number' | 'integer' | 'boolean' | 'null';
+    properties?: {
+      [key: string]: any;
+    };
+    required?: string[];
+    items?: {
+      [key: string]: any;
+    };
+  };
+  outputs?: {
+    [key: string]: string;
+  };
   steps: Step[];
-};
+  successActions?: OnSuccessObject[];
+  failureActions?: OnFailureObject[];
+}
+
+export interface ArazzoDefinition {
+  arazzo: '1.0.0';
+  info: InfoObject;
+  sourceDescriptions: SourceDescription[];
+  'x-parameters'?: Parameter[];
+  workflows: Workflow[];
+  components?: {
+    inputs?: {
+      [key: string]: {
+        type: string;
+        properties?: {
+          [key: string]: any;
+        };
+      };
+    };
+    parameters?: {
+      [key: string]: Parameter;
+    };
+    successActions?: {
+      [key: string]: OnSuccessObject;
+    };
+    failureActions?: {
+      [key: string]: OnFailureObject;
+    };
+  };
+}
diff --git a/packages/core/src/visitors.ts b/packages/core/src/visitors.ts
index 67775e9d..ac7aa00c 100644
--- a/packages/core/src/visitors.ts
+++ b/packages/core/src/visitors.ts
@@ -51,7 +51,24 @@ import type {
 } from './typings/swagger';
 import type { Async2Definition } from './typings/asyncapi';
 import type { Async3Definition } from './typings/asyncapi3';
-import type { ArazzoDefinition } from './typings/arazzo';
+import type {
+  ArazzoDefinition,
+  ArazzoSourceDescription,
+  CriteriaObject,
+  ExpectSchema,
+  ExtendedOperation,
+  InfoObject,
+  NoneSourceDescription,
+  OnFailureObject,
+  OnSuccessObject,
+  OpenAPISourceDescription,
+  Parameter,
+  Replacement,
+  RequestBody,
+  SourceDescription,
+  Step,
+  Workflow,
+} from './typings/arazzo';
 
 export type SkipFunctionContext = Pick<
   UserContext,
@@ -220,6 +237,23 @@ type Async3FlatVisitor = {
 
 type ArazzoFlatVisitor = {
   Root?: VisitFunctionOrObject<ArazzoDefinition>;
+  ParameterObject?: VisitFunctionOrObject<Parameter>;
+  InfoObject?: VisitFunctionOrObject<InfoObject>;
+  OpenAPISourceDescription?: VisitFunctionOrObject<OpenAPISourceDescription>;
+  NoneSourceDescription?: VisitFunctionOrObject<NoneSourceDescription>;
+  ArazzoSourceDescription?: VisitFunctionOrObject<ArazzoSourceDescription>;
+  SourceDescription?: VisitFunctionOrObject<SourceDescription>;
+  ExtendedOperation?: VisitFunctionOrObject<ExtendedOperation>;
+  ExpectSchema?: VisitFunctionOrObject<ExpectSchema>;
+  Replacement?: VisitFunctionOrObject<Replacement>;
+  RequestBody?: VisitFunctionOrObject<RequestBody>;
+  CriteriaObject?: VisitFunctionOrObject<CriteriaObject>;
+  OnSuccessObject?: VisitFunctionOrObject<OnSuccessObject>;
+  OnFailureObject?: VisitFunctionOrObject<OnFailureObject>;
+  Step?: VisitFunctionOrObject<Step>;
+  Steps?: VisitFunctionOrObject<Step[]>;
+  Workflow?: VisitFunctionOrObject<Workflow>;
+  Workflows?: VisitFunctionOrObject<Workflow[]>;
 };
 
 const legacyTypesMap = {
diff --git a/resources/arazzo.yaml b/resources/arazzo.yaml
new file mode 100644
index 00000000..66ac0259
--- /dev/null
+++ b/resources/arazzo.yaml
@@ -0,0 +1,119 @@
+arazzo: 1.0.0
+info:
+  title: Redocly Museum API Test Workflow
+  description: >-
+    Use the Museum API with Arazzo as an example of describing multi-step workflows.
+    Built with love by Redocly.
+  version: 1.0.0
+
+sourceDescriptions:
+  - name: museum-api
+    type: openapi
+    url: ../openapi.yaml
+  - name: tickets-from-museum-api
+    type: arazzo
+    url: museum-tickets.arazzo.yaml
+
+workflows:
+  - workflowId: get-museum-hours
+    description: >-
+      This workflow demonstrates how to get the museum opening hours and buy tickets.
+    parameters:
+      - in: header
+        name: Authorization
+        value: Basic Og==
+    steps:
+      - stepId: get-museum-hours
+        description: >-
+          Get museum hours by resolving request details with getMuseumHours operationId from openapi.yaml description.
+        operationId: museum-api.getMuseumHours
+        successCriteria:
+          - condition: $statusCode == 200
+        outputs:
+          schedule: $response.body
+      - stepId: buy-ticket
+        description: >-
+          Buy a ticket for the museum by calling an external workflow from another Arazzo file.
+        workflowId: $sourceDescriptions.tickets-from-museum-api.workflows.get-museum-tickets
+        outputs:
+          ticketId: $outputs.ticketId
+  - workflowId: events-crud
+    description: >-
+      This workflow demonstrates how to list, create, update, and delete special events at the museum.
+    parameters:
+      - in: header
+        name: Authorization
+        value: Basic Og==
+    steps:
+      - stepId: list-events
+        description: >-
+          Request the list of events.
+        operationPath: $sourceDescriptions.museum-api#/paths/~1special-events/get
+        outputs:
+          events: $response.body
+      - stepId: create-event
+        description: >-
+          Create a new special event.
+        operationPath: $sourceDescriptions.museum-api#/paths/~1special-events/post
+        requestBody:
+          payload:
+            name: 'Mermaid Treasure Identification and Analysis'
+            location: 'Under the seaaa 🦀 🎶 🌊.'
+            eventDescription: 'Join us as we review and classify a rare collection of 20 thingamabobs, gadgets, gizmos, whoosits, and whatsits, kindly donated by Ariel.'
+            dates:
+              - '2023-09-05'
+              - '2023-09-08'
+            price: 0
+        successCriteria:
+          - condition: $statusCode == 201
+          - context: $response.body
+            condition: $.name == 'Mermaid Treasure Identification and Analysis'
+            type: jsonpath
+        outputs:
+          createdEventId: $response.body.eventId
+          name: $response.body.name
+      - stepId: get-event-by-id
+        description: >-
+          Get the details of the event that was created in the previous step.
+        operationPath: $sourceDescriptions.museum-api#/paths/~1special-events~1{eventId}/get
+        parameters:
+          - name: eventId
+            in: body
+            value: $steps.create-event.outputs.createdEventId
+        successCriteria:
+          - context: $statusCode
+            condition: '^200$'
+            type: regex
+      - stepId: update-event
+        description: >-
+          Update the created event with new details.
+        operationPath: $sourceDescriptions.museum-api#/paths/~1special-events~1{eventId}/patch
+        parameters:
+          - name: eventId
+            in: path
+            value: $steps.create-event.outputs.createdEventId
+        requestBody:
+          payload:
+            name: 'Orca Identification and Analysis'
+            location: 'Under the seaaa 🦀 🎶 🌊.'
+            dates:
+              - '2023-09-05'
+              - '2023-09-08'
+            price: 0
+        successCriteria:
+          - condition: $statusCode == 200
+          - context: $response.body
+            condition: $.name == 'Orca Identification and Analysis'
+            type: jsonpath
+        outputs:
+          updatedEventId: $response.body.eventId
+      - stepId: delete-event
+        description: >-
+          Delete the event that was updated in the previous step.
+        operationPath: $sourceDescriptions.museum-api#/paths/~1special-events~1{eventId}/delete
+        parameters:
+          - name: eventId
+            in: path
+            value: $steps.update-event.outputs.updatedEventId
+        successCriteria:
+          - condition: $statusCode == 204
diff --git a/resources/museum-tickets.arazzo.yaml b/resources/museum-tickets.arazzo.yaml
new file mode 100644
index 00000000..1f1b101f
--- /dev/null
+++ b/resources/museum-tickets.arazzo.yaml
@@ -0,0 +1,37 @@
+arazzo: 1.0.0
+info:
+  title: Redocly Museum Tickets Workflow
+  description: >-
+    Use the Museum API as an example in a simple Arazzo workflow.
+    Built with love by Redocly.
+  version: 1.0.0
+
+sourceDescriptions:
+  - name: museum-api
+    type: openapi
+    url: ../openapi.yaml
+
+workflows:
+  - workflowId: get-museum-tickets
+    description: >-
+      This workflow demonstrates how to buy tickets for the museum.
+    parameters:
+      - in: header
+        name: Authorization
+        value: Basic Og==
+    steps:
+      - stepId: buy-tickets
+        description: >-
+          Buy museum tickets resolving request details with buyMuseumTickets operationId from openapi.yaml description.
+        operationId: buyMuseumTickets
+        requestBody:
+          payload:
+            ticketType: general
+            ticketDate: 2023-09-07
+            email: todd@example.com
+        successCriteria:
+          - condition: $statusCode == 201
+        outputs:
+          ticketId: $response.body.ticketId
+    outputs:
+      ticketId: $steps.buy-tickets.outputs.ticketId
diff --git a/resources/museum.yaml b/resources/museum.yaml
index f9f78350..f1eba785 100644
--- a/resources/museum.yaml
+++ b/resources/museum.yaml
@@ -1,21 +1,22 @@
 openapi: 3.1.0
 info:
   title: Redocly Museum API
-  description: An imaginary, but delightful Museum API for interacting with museum services and information. Built with love by Redocly.
-  version: 1.0.0
+  description: Imaginary, but delightful Museum API for interacting with museum services and information. Built with love by Redocly.
+  version: 1.1.1
+  termsOfService: 'https://redocly.com/subscription-agreement/'
   contact:
     email: team@redocly.com
     url: 'https://redocly.com/docs/cli/'
   license:
     name: MIT
-    url: 'https://opensource.org/license/mit/ '
+    url: 'https://opensource.org/license/mit/'
 servers:
-  - url: 'https://api.fake-museum-example.com/v1'
+  - url: 'https://redocly.com/_mock/docs/openapi/museum-api'
 paths:
   /museum-hours:
     get:
       summary: Get museum hours
-      description: Get upcoming museum operating hours
+      description: Get upcoming museum operating hours.
       operationId: getMuseumHours
       tags:
         - Operations
@@ -25,7 +26,7 @@ paths:
         - $ref: '#/components/parameters/PaginationLimit'
       responses:
         '200':
-          description: Success
+          description: Success.
           content:
             application/json:
               schema:
@@ -34,9 +35,9 @@ paths:
                 default_example:
                   $ref: '#/components/examples/GetMuseumHoursResponseExample'
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
   /special-events:
     post:
       summary: Create special events
@@ -54,8 +55,8 @@ paths:
               default_example:
                 $ref: '#/components/examples/CreateSpecialEventRequestExample'
       responses:
-        '200':
-          description: Success
+        '201':
+          description: Created.
           content:
             application/json:
               schema:
@@ -64,9 +65,9 @@ paths:
                 default_example:
                   $ref: '#/components/examples/CreateSpecialEventResponseExample'
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
     get:
       summary: List special events
       description: Return a list of upcoming special events at the museum.
@@ -80,7 +81,7 @@ paths:
         - $ref: '#/components/parameters/PaginationLimit'
       responses:
         '200':
-          description: Success
+          description: Success.
           content:
             application/json:
               schema:
@@ -89,9 +90,9 @@ paths:
                 default_example:
                   $ref: '#/components/examples/ListSpecialEventsResponseExample'
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
   /special-events/{eventId}:
     get:
       summary: Get special event
@@ -103,7 +104,7 @@ paths:
         - $ref: '#/components/parameters/EventId'
       responses:
         '200':
-          description: Success
+          description: Success.
           content:
             application/json:
               schema:
@@ -112,12 +113,12 @@ paths:
                 default_example:
                   $ref: '#/components/examples/GetSpecialEventResponseExample'
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
     patch:
       summary: Update special event
-      description: Update the details of a special event
+      description: Update the details of a special event.
       operationId: updateSpecialEvent
       tags:
         - Events
@@ -134,7 +135,7 @@ paths:
                 $ref: '#/components/examples/UpdateSpecialEventRequestExample'
       responses:
         '200':
-          description: Success
+          description: Success.
           content:
             application/json:
               schema:
@@ -143,9 +144,9 @@ paths:
                 default_example:
                   $ref: '#/components/examples/UpdateSpecialEventResponseExample'
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
     delete:
       summary: Delete special event
       description: Delete a special event from the collection. Allows museum to cancel planned events.
@@ -156,13 +157,13 @@ paths:
         - $ref: '#/components/parameters/EventId'
       responses:
         '204':
-          description: Success - no content
+          description: Success - no content.
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '401':
-          description: Unauthorized
+          $ref: '#/components/responses/Unauthorized'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
   /tickets:
     post:
       summary: Buy museum tickets
@@ -182,8 +183,8 @@ paths:
               event_entry:
                 $ref: '#/components/examples/BuyEventTicketsRequestExample'
       responses:
-        '200':
-          description: Success
+        '201':
+          description: Created.
           content:
             application/json:
               schema:
@@ -194,9 +195,9 @@ paths:
                 event_entry:
                   $ref: '#/components/examples/BuyEventTicketsResponseExample'
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
   /tickets/{ticketId}/qr:
     get:
       summary: Get ticket QR code
@@ -208,15 +209,15 @@ paths:
         - $ref: '#/components/parameters/TicketId'
       responses:
         '200':
-          description: Scannable event ticket in image format
+          description: Scannable event ticket in image format.
           content:
             image/png:
               schema:
                 $ref: '#/components/schemas/GetTicketCodeResponse'
         '400':
-          description: Bad request
+          $ref: '#/components/responses/BadRequest'
         '404':
-          description: Not found
+          $ref: '#/components/responses/NotFound'
 components:
   schemas:
     TicketType:
@@ -229,7 +230,7 @@ components:
     Date:
       type: string
       format: date
-      example: 2023-10-29
+      example: '2023-10-29'
     Email:
       description: Email address for ticket purchaser.
       type: string
@@ -238,7 +239,7 @@ components:
     Phone:
       description: Phone number for the ticket purchaser (optional).
       type: string
-      example: +1(234)-567-8910
+      example: '+1(234)-567-8910'
     BuyMuseumTicketsRequest:
       description: Request payload used for purchasing museum tickets.
       type: object
@@ -271,7 +272,7 @@ components:
     TicketConfirmation:
       description: Unique confirmation code used to verify ticket purchase.
       type: string
-      example: ticket-event-a98c8f-7eb12
+      example: 'ticket-event-a98c8f-7eb12'
     BuyMuseumTicketsResponse:
       description: Details for a museum ticket after a successful purchase.
       type: object
@@ -296,7 +297,7 @@ components:
         - ticketDate
         - confirmationCode
     GetTicketCodeResponse:
-      description: An image of a ticket with a QR code used for museum or event entry.
+      description: Image of a ticket with a QR code used for museum or event entry.
       type: string
       format: binary
     GetMuseumHoursResponse:
@@ -311,7 +312,7 @@ components:
         date:
           description: Date the operating hours apply to.
           $ref: '#/components/schemas/Date'
-          example: 02-02-2022
+          example: '2024-12-31'
         timeOpen:
           type: string
           pattern: '^([01]\d|2[0-3]):?([0-5]\d)$'
@@ -333,28 +334,29 @@ components:
       example: 3be6453c-03eb-4357-ae5a-984a0e574a54
     EventName:
       type: string
-      description: Name of the special event
+      description: Name of the special event.
       example: Pirate Coding Workshop
     EventLocation:
       type: string
-      description: Location where the special event is held
+      description: Location where the special event is held.
       example: Computer Room
     EventDescription:
       type: string
-      description: Description of the special event
+      description: Description of the special event.
       example: Captain Blackbeard shares his love of the C...language. And possibly Arrrrr (R lang).
     EventDates:
       type: array
       items:
         $ref: '#/components/schemas/Date'
-      description: List of planned dates for the special event
+      description: List of planned dates for the special event.
     EventPrice:
-      description: Price of a ticket for the special event
+      description: Price of a ticket for the special event.
       type: number
       format: float
       example: 25
     CreateSpecialEventRequest:
       description: Request payload for creating new special events at the museum.
+      type: object
       properties:
         name:
           $ref: '#/components/schemas/EventName'
@@ -374,6 +376,7 @@ components:
         - price
     UpdateSpecialEventRequest:
       description: Request payload for updating an existing special event. Only included fields are updated in the event.
+      type: object
       properties:
         name:
           $ref: '#/components/schemas/EventName'
@@ -386,12 +389,13 @@ components:
         price:
           $ref: '#/components/schemas/EventPrice'
     ListSpecialEventsResponse:
-      description: A list of upcoming special events
+      description: List of upcoming special events.
       type: array
       items:
         $ref: '#/components/schemas/SpecialEventResponse'
     SpecialEventResponse:
       description: Information about a special event.
+      type: object
       properties:
         eventId:
           $ref: '#/components/schemas/EventId'
@@ -412,6 +416,16 @@ components:
         - eventDescription
         - dates
         - price
+    Error:
+      type: object
+      properties:
+        type:
+          type: string
+          example: object
+        title:
+          type: string
+          example: Validation failed
+
   securitySchemes:
     MuseumPlaceholderAuth:
       type: http
@@ -421,14 +435,14 @@ components:
       summary: General entry ticket
       value:
         ticketType: general
-        ticketDate: 2023-09-07
+        ticketDate: '2023-09-07'
         email: todd@example.com
     BuyEventTicketsRequestExample:
       summary: Special event ticket
       value:
         ticketType: general
         eventId: dad4bce8-f5cb-4078-a211-995864315e39
-        ticketDate: 2023-09-05
+        ticketDate: '2023-09-05'
         email: todd@example.com
     BuyGeneralTicketsResponseExample:
       summary: General entry ticket
@@ -436,7 +450,7 @@ components:
         message: Museum general entry ticket purchased
         ticketId: 382c0820-0530-4f4b-99af-13811ad0f17a
         ticketType: general
-        ticketDate: 2023-09-07
+        ticketDate: '2023-09-07'
         confirmationCode: ticket-general-e5e5c6-dce78
     BuyEventTicketsResponseExample:
       summary: Special event ticket
@@ -445,7 +459,7 @@ components:
         ticketId: b811f723-17b2-44f7-8952-24b03e43d8a9
         eventName: Mermaid Treasure Identification and Analysis
         ticketType: event
-        ticketDate: 2023-09-05
+        ticketDate: '2023-09-05'
         confirmationCode: ticket-event-9c55eg-8v82a
     CreateSpecialEventRequestExample:
       summary: Create special event
@@ -454,8 +468,8 @@ components:
         location: Under the seaaa 🦀 🎶 🌊.
         eventDescription: Join us as we review and classify a rare collection of 20 thingamabobs, gadgets, gizmos, whoosits, and whatsits, kindly donated by Ariel.
         dates:
-          - 2023-09-05
-          - 2023-09-08
+          - '2023-09-05'
+          - '2023-09-08'
         price: 0
     CreateSpecialEventResponseExample:
       summary: Special event created
@@ -465,8 +479,8 @@ components:
         location: Under the seaaa 🦀 🎶 🌊.
         eventDescription: Join us as we review and classify a rare collection of 20 thingamabobs, gadgets, gizmos, whoosits, and whatsits, kindly donated by Ariel.
         dates:
-          - 2023-09-05
-          - 2023-09-08
+          - '2023-09-05'
+          - '2023-09-08'
         price: 30
     GetSpecialEventResponseExample:
       summary: Get special event
@@ -476,9 +490,9 @@ components:
         location: Temporal Tearoom
         eventDescription: Sip tea with important historical figures.
         dates:
-          - 2023-11-18
-          - 2023-11-25
-          - 2023-12-02
+          - '2023-11-18'
+          - '2023-11-25'
+          - '2023-12-02'
         price: 60
     ListSpecialEventsResponseExample:
       summary: List of special events
@@ -488,85 +502,85 @@ components:
           location: Seattle... probably
           eventDescription: They're big, they're hairy, but they're also graceful. Come learn how the biggest feet can have the lightest touch.
           dates:
-            - 2023-12-15
-            - 2023-12-22
+            - '2023-12-15'
+            - '2023-12-22'
           price: 40
         - eventId: 2f14374a-9c65-4ee5-94b7-fba66d893483
           name: Solar Telescope Demonstration
           location: Far from the sun.
           eventDescription: Look at the sun without going blind!
           dates:
-            - 2023-09-07
-            - 2023-09-14
+            - '2023-09-07'
+            - '2023-09-14'
           price: 50
         - eventId: 6aaa61ba-b2aa-4868-b803-603dbbf7bfdb
           name: Cook like a Caveman
           location: Fire Pit on East side
           eventDescription: Learn to cook on an open flame.
           dates:
-            - 2023-11-10
-            - 2023-11-17
-            - 2023-11-24
+            - '2023-11-10'
+            - '2023-11-17'
+            - '2023-11-24'
           price: 5
         - eventId: 602b75e1-5696-4ab8-8c7a-f9e13580f910
           name: Underwater Basket Weaving
           location: Rec Center Pool next door.
           eventDescription: Learn to weave baskets underwater.
           dates:
-            - 2023-09-12
-            - 2023-09-15
+            - '2023-09-12'
+            - '2023-09-15'
           price: 15
         - eventId: dad4bce8-f5cb-4078-a211-995864315e39
           name: Mermaid Treasure Identification and Analysis
           location: Room Sea-12
           eventDescription: Join us as we review and classify a rare collection of 20 thingamabobs, gadgets, gizmos, whoosits, and whatsits — kindly donated by Ariel.
           dates:
-            - 2023-09-05
-            - 2023-09-08
+            - '2023-09-05'
+            - '2023-09-08'
           price: 30
         - eventId: 6744a0da-4121-49cd-8479-f8cc20526495
           name: Time Traveler Tea Party
           location: Temporal Tearoom
           eventDescription: Sip tea with important historical figures.
           dates:
-            - 2023-11-18
-            - 2023-11-25
-            - 2023-12-02
+            - '2023-11-18'
+            - '2023-11-25'
+            - '2023-12-02'
           price: 60
         - eventId: 3be6453c-03eb-4357-ae5a-984a0e574a54
           name: Pirate Coding Workshop
           location: Computer Room
           eventDescription: Captain Blackbeard shares his love of the C...language. And possibly Arrrrr (R lang).
           dates:
-            - 2023-10-29
-            - 2023-10-30
-            - 2023-10-31
+            - '2023-10-29'
+            - '2023-10-30'
+            - '2023-10-31'
           price: 45
         - eventId: 9d90d29a-2af5-4206-97d9-9ea9ceadcb78
           name: Llama Street Art Through the Ages
           location: Auditorium
           eventDescription: Llama street art?! Alpaca my bags -- let's go!
           dates:
-            - 2023-10-29
-            - 2023-10-30
-            - 2023-10-31
+            - '2023-10-29'
+            - '2023-10-30'
+            - '2023-10-31'
           price: 45
         - eventId: a3c7b2c4-b5fb-4ef7-9322-00a919864957
           name: The Great Parrot Debate
           location: Outdoor Amphitheatre
           eventDescription: See leading parrot minds discuss important geopolitical issues.
           dates:
-            - 2023-11-03
-            - 2023-11-10
+            - '2023-11-03'
+            - '2023-11-10'
           price: 35
         - eventId: b92d46b7-4c5d-422b-87a5-287767e26f29
           name: Eat a Bunch of Corn
           location: Cafeteria
           eventDescription: We accidentally bought too much corn. Please come eat it.
           dates:
-            - 2023-11-10
-            - 2023-11-17
-            - 2023-11-24
+            - '2023-11-10'
+            - '2023-11-17'
+            - '2023-11-24'
           price: 5
     UpdateSpecialEventRequestExample:
       summary: Update special event request
@@ -581,8 +595,8 @@ components:
         location: On the beach.
         eventDescription: Join us as we review and classify a rare collection of 20 thingamabobs, gadgets, gizmos, whoosits, and whatsits, kindly donated by Ariel.
         dates:
-          - 2023-09-05
-          - 2023-09-08
+          - '2023-09-05'
+          - '2023-09-08'
         price: 15
     GetMuseumHoursResponseExample:
       summary: Get hours response
@@ -621,7 +635,7 @@ components:
     PaginationPage:
       name: page
       in: query
-      description: The page number to retrieve.
+      description: Page number to retrieve.
       schema:
         type: integer
         default: 1
@@ -629,7 +643,7 @@ components:
     PaginationLimit:
       name: limit
       in: query
-      description: The number of days per page.
+      description: Number of days per page.
       schema:
         type: integer
         default: 10
@@ -638,7 +652,7 @@ components:
     EventId:
       name: eventId
       in: path
-      description: An identifier for a special event.
+      description: Identifier for a special event.
       required: true
       schema:
         type: string
@@ -647,33 +661,52 @@ components:
     StartDate:
       name: startDate
       in: query
-      description: The starting date to retrieve future operating hours from. Defaults to today's date.
+      description: Starting date to retrieve future operating hours from. Defaults to today's date.
       schema:
         type: string
         format: date
-        example: 2023-02-23
+        example: '2023-02-23'
     EndDate:
       name: endDate
       in: query
-      description: The end of a date range to retrieve special events for. Defaults to 7 days after `startDate`.
+      description: End of a date range to retrieve special events for. Defaults to 7 days after `startDate`.
       schema:
         type: string
         format: date
-        example: 2023-04-18
+        example: '2023-04-18'
     TicketId:
       name: ticketId
       in: path
-      description: An identifier for a ticket to a museum event. Used to generate ticket image.
+      description: Identifier for a ticket to a museum event. Used to generate ticket image.
       required: true
       schema:
         type: string
         format: uuid
         example: a54a57ca-36f8-421b-a6b4-2e8f26858a4c
+  responses:
+    BadRequest:
+      description: Bad request.
+      content:
+        application/problem+json:
+          schema:
+            $ref: '#/components/schemas/Error'
+    NotFound:
+      description: Not found.
+      content:
+        application/problem+json:
+          schema:
+            $ref: '#/components/schemas/Error'
+    Unauthorized:
+      description: Unauthorized.
+      content:
+        application/problem+json:
+          schema:
+            $ref: '#/components/schemas/Error'
 tags:
   - name: Operations
     description: Operational information about the museum.
   - name: Events
-    description: Special events hosted by the Museum
+    description: Special events hosted by the museum.
   - name: Tickets
     description: Museum tickets for general entrance or special events.
 security:


Test patch:
diff --git a/__tests__/check-config/wrong-config-type-extensions-in-assertions/snapshot.js b/__tests__/check-config/wrong-config-type-extensions-in-assertions/snapshot.js
index 1d06f0cc..4a116dc5 100644
--- a/__tests__/check-config/wrong-config-type-extensions-in-assertions/snapshot.js
+++ b/__tests__/check-config/wrong-config-type-extensions-in-assertions/snapshot.js
@@ -4,7 +4,7 @@ exports[`E2E check-config wrong config type extension in assertions 1`] = `
 
 [1] redocly.yaml:10:13 at #/rules/rule~1metadata-lifecycle/subject/type
 
-\`type\` can be one of the following only: "any", "Root", "Tag", "TagList", "TagGroups", "TagGroup", "ExternalDocs", "Example", "ExamplesMap", "EnumDescriptions", "SecurityRequirement", "SecurityRequirementList", "Info", "Contact", "License", "Logo", "Paths", "PathItem", "Parameter", "ParameterItems", "ParameterList", "Operation", "Examples", "Header", "Responses", "Response", "Schema", "Xml", "SchemaProperties", "NamedSchemas", "NamedResponses", "NamedParameters", "NamedSecuritySchemes", "SecurityScheme", "XCodeSample", "XCodeSampleList", "XServerList", "XServer", "Server", "ServerList", "ServerVariable", "ServerVariablesMap", "Callback", "CallbacksMap", "RequestBody", "MediaTypesMap", "MediaType", "Encoding", "EncodingMap", "HeadersMap", "Link", "DiscriminatorMapping", "Discriminator", "Components", "LinksMap", "NamedExamples", "NamedRequestBodies", "NamedHeaders", "NamedLinks", "NamedCallbacks", "ImplicitFlow", "PasswordFlow", "ClientCredentials", "AuthorizationCode", "OAuth2Flows", "XUsePkce", "WebhooksMap", "XMetaData", "PatternProperties", "NamedPathItems", "DependentRequired", "HttpServerBinding", "HttpChannelBinding", "HttpMessageBinding", "HttpOperationBinding", "WsServerBinding", "WsChannelBinding", "WsMessageBinding", "WsOperationBinding", "KafkaServerBinding", "KafkaTopicConfiguration", "KafkaChannelBinding", "KafkaMessageBinding", "KafkaOperationBinding", "AnypointmqServerBinding", "AnypointmqChannelBinding", "AnypointmqMessageBinding", "AnypointmqOperationBinding", "AmqpServerBinding", "AmqpChannelBinding", "AmqpMessageBinding", "AmqpOperationBinding", "Amqp1ServerBinding", "Amqp1ChannelBinding", "Amqp1MessageBinding", "Amqp1OperationBinding", "MqttServerBindingLastWill", "MqttServerBinding", "MqttChannelBinding", "MqttMessageBinding", "MqttOperationBinding", "Mqtt5ServerBinding", "Mqtt5ChannelBinding", "Mqtt5MessageBinding", "Mqtt5OperationBinding", "NatsServerBinding", "NatsChannelBinding", "NatsMessageBinding", "NatsOperationBinding", "JmsServerBinding", "JmsChannelBinding", "JmsMessageBinding", "JmsOperationBinding", "SolaceServerBinding", "SolaceChannelBinding", "SolaceMessageBinding", "SolaceDestination", "SolaceOperationBinding", "StompServerBinding", "StompChannelBinding", "StompMessageBinding", "StompOperationBinding", "RedisServerBinding", "RedisChannelBinding", "RedisMessageBinding", "RedisOperationBinding", "MercureServerBinding", "MercureChannelBinding", "MercureMessageBinding", "MercureOperationBinding", "ServerBindings", "ChannelBindings", "MessageBindings", "OperationBindings", "ServerMap", "ChannelMap", "Channel", "ParametersMap", "MessageExample", "NamedMessages", "NamedMessageTraits", "NamedOperationTraits", "NamedCorrelationIds", "SecuritySchemeFlows", "Message", "OperationTrait", "OperationTraitList", "MessageTrait", "MessageTraitList", "MessageExampleList", "CorrelationId", "Dependencies", "OperationReply", "OperationReplyAddress", "NamedTags", "NamedExternalDocs", "NamedChannels", "NamedOperations", "NamedOperationReplies", "NamedOperationRelyAddresses", "SecuritySchemeList", "MessageList", "Root.info", "Root.sourceDescriptions_items_0", "Root.sourceDescriptions_items_1", "Root.sourceDescriptions_items_2", "Root.sourceDescriptions", "Root.x-parameters_items_0", "Root.x-parameters_items_1", "Root.x-parameters", "Root.workflows_items.parameters_items_0", "Root.workflows_items.parameters_items_1", "Root.workflows_items.parameters", "Root.workflows_items.inputs", "Root.workflows_items.outputs", "Root.workflows_items.steps_items.parameters_items_0", "Root.workflows_items.steps_items.parameters_items_1", "Root.workflows_items.steps_items.parameters", "Root.workflows_items.steps_items.successCriteria_items.type_1", "Root.workflows_items.steps_items.successCriteria_items.type_2", "Root.workflows_items.steps_items.successCriteria_items", "Root.workflows_items.steps_items.successCriteria", "Root.workflows_items.steps_items.onSuccess_items.criteria_items.type_1", "Root.workflows_items.steps_items.onSuccess_items.criteria_items.type_2", "Root.workflows_items.steps_items.onSuccess_items.criteria_items", "Root.workflows_items.steps_items.onSuccess_items.criteria", "Root.workflows_items.steps_items.onSuccess_items", "Root.workflows_items.steps_items.onSuccess", "Root.workflows_items.steps_items.onFailure_items.criteria_items.type_1", "Root.workflows_items.steps_items.onFailure_items.criteria_items.type_2", "Root.workflows_items.steps_items.onFailure_items.criteria_items", "Root.workflows_items.steps_items.onFailure_items.criteria", "Root.workflows_items.steps_items.onFailure_items", "Root.workflows_items.steps_items.onFailure", "Root.workflows_items.steps_items.outputs", "Root.workflows_items.steps_items.x-expect", "Root.workflows_items.steps_items.x-operation", "Root.workflows_items.steps_items.requestBody.replacements_items", "Root.workflows_items.steps_items.requestBody.replacements", "Root.workflows_items.steps_items.requestBody", "Root.workflows_items.steps_items", "Root.workflows_items.steps", "Root.workflows_items.successActions_items.criteria_items.type_1", "Root.workflows_items.successActions_items.criteria_items.type_2", "Root.workflows_items.successActions_items.criteria_items", "Root.workflows_items.successActions_items.criteria", "Root.workflows_items.successActions_items", "Root.workflows_items.successActions", "Root.workflows_items.failureActions_items.criteria_items.type_1", "Root.workflows_items.failureActions_items.criteria_items.type_2", "Root.workflows_items.failureActions_items.criteria_items", "Root.workflows_items.failureActions_items.criteria", "Root.workflows_items.failureActions_items", "Root.workflows_items.failureActions", "Root.workflows_items", "Root.workflows", "Root.components.inputs_additionalProperties", "Root.components.inputs", "Root.components.parameters_additionalProperties_0", "Root.components.parameters_additionalProperties_1", "Root.components.parameters", "Root.components.successActions_additionalProperties.criteria_items.type_1", "Root.components.successActions_additionalProperties.criteria_items.type_2", "Root.components.successActions_additionalProperties.criteria_items", "Root.components.successActions_additionalProperties.criteria", "Root.components.successActions_additionalProperties", "Root.components.successActions", "Root.components.failureActions_additionalProperties.criteria_items.type_1", "Root.components.failureActions_additionalProperties.criteria_items.type_2", "Root.components.failureActions_additionalProperties.criteria_items", "Root.components.failureActions_additionalProperties.criteria", "Root.components.failureActions_additionalProperties", "Root.components.failureActions", "Root.components", "SpecExtension".
+\`type\` can be one of the following only: "any", "Root", "Tag", "TagList", "TagGroups", "TagGroup", "ExternalDocs", "Example", "ExamplesMap", "EnumDescriptions", "SecurityRequirement", "SecurityRequirementList", "Info", "Contact", "License", "Logo", "Paths", "PathItem", "Parameter", "ParameterItems", "ParameterList", "Operation", "Examples", "Header", "Responses", "Response", "Schema", "Xml", "SchemaProperties", "NamedSchemas", "NamedResponses", "NamedParameters", "NamedSecuritySchemes", "SecurityScheme", "XCodeSample", "XCodeSampleList", "XServerList", "XServer", "Server", "ServerList", "ServerVariable", "ServerVariablesMap", "Callback", "CallbacksMap", "RequestBody", "MediaTypesMap", "MediaType", "Encoding", "EncodingMap", "HeadersMap", "Link", "DiscriminatorMapping", "Discriminator", "Components", "LinksMap", "NamedExamples", "NamedRequestBodies", "NamedHeaders", "NamedLinks", "NamedCallbacks", "ImplicitFlow", "PasswordFlow", "ClientCredentials", "AuthorizationCode", "OAuth2Flows", "XUsePkce", "WebhooksMap", "XMetaData", "PatternProperties", "NamedPathItems", "DependentRequired", "HttpServerBinding", "HttpChannelBinding", "HttpMessageBinding", "HttpOperationBinding", "WsServerBinding", "WsChannelBinding", "WsMessageBinding", "WsOperationBinding", "KafkaServerBinding", "KafkaTopicConfiguration", "KafkaChannelBinding", "KafkaMessageBinding", "KafkaOperationBinding", "AnypointmqServerBinding", "AnypointmqChannelBinding", "AnypointmqMessageBinding", "AnypointmqOperationBinding", "AmqpServerBinding", "AmqpChannelBinding", "AmqpMessageBinding", "AmqpOperationBinding", "Amqp1ServerBinding", "Amqp1ChannelBinding", "Amqp1MessageBinding", "Amqp1OperationBinding", "MqttServerBindingLastWill", "MqttServerBinding", "MqttChannelBinding", "MqttMessageBinding", "MqttOperationBinding", "Mqtt5ServerBinding", "Mqtt5ChannelBinding", "Mqtt5MessageBinding", "Mqtt5OperationBinding", "NatsServerBinding", "NatsChannelBinding", "NatsMessageBinding", "NatsOperationBinding", "JmsServerBinding", "JmsChannelBinding", "JmsMessageBinding", "JmsOperationBinding", "SolaceServerBinding", "SolaceChannelBinding", "SolaceMessageBinding", "SolaceDestination", "SolaceOperationBinding", "StompServerBinding", "StompChannelBinding", "StompMessageBinding", "StompOperationBinding", "RedisServerBinding", "RedisChannelBinding", "RedisMessageBinding", "RedisOperationBinding", "MercureServerBinding", "MercureChannelBinding", "MercureMessageBinding", "MercureOperationBinding", "ServerBindings", "ChannelBindings", "MessageBindings", "OperationBindings", "ServerMap", "ChannelMap", "Channel", "ParametersMap", "MessageExample", "NamedMessages", "NamedMessageTraits", "NamedOperationTraits", "NamedCorrelationIds", "SecuritySchemeFlows", "Message", "OperationTrait", "OperationTraitList", "MessageTrait", "MessageTraitList", "MessageExampleList", "CorrelationId", "Dependencies", "OperationReply", "OperationReplyAddress", "NamedTags", "NamedExternalDocs", "NamedChannels", "NamedOperations", "NamedOperationReplies", "NamedOperationRelyAddresses", "SecuritySchemeList", "MessageList", "SourceDescriptions", "OpenAPISourceDescription", "NoneSourceDescription", "ArazzoSourceDescription", "Parameters", "ReusableObject", "Workflows", "Workflow", "Steps", "Step", "Replacement", "ExtendedOperation", "ExpectSchema", "Outputs", "CriterionObject", "XPathCriterion", "JSONPathCriterion", "SuccessActionObject", "OnSuccessActionList", "FailureActionObject", "OnFailureActionList", "NamedInputs", "NamedSuccessActions", "NamedFailureActions", "SpecExtension".
 
  8 | rule/metadata-lifecycle:
  9 |   subject:
diff --git a/__tests__/lint-config/invalid-config-assertation-config-type/snapshot.js b/__tests__/lint-config/invalid-config-assertation-config-type/snapshot.js
index bec6ab82..d07c1737 100644
--- a/__tests__/lint-config/invalid-config-assertation-config-type/snapshot.js
+++ b/__tests__/lint-config/invalid-config-assertation-config-type/snapshot.js
@@ -6,7 +6,7 @@ exports[`E2E lint-config test with option: { dirName: 'invalid-config-assertatio
 The 'assert/' syntax in assert/path-item-mutually-required is deprecated. Update your configuration to use 'rule/' instead. Examples and more information: https://redocly.com/docs/cli/rules/configurable-rules/
 [1] .redocly.yaml:9:17 at #/rules/assert~1path-item-mutually-required/where/0/subject/type
 
-\`type\` can be one of the following only: "any", "Root", "Tag", "TagList", "TagGroups", "TagGroup", "ExternalDocs", "Example", "ExamplesMap", "EnumDescriptions", "SecurityRequirement", "SecurityRequirementList", "Info", "Contact", "License", "Logo", "Paths", "PathItem", "Parameter", "ParameterItems", "ParameterList", "Operation", "Examples", "Header", "Responses", "Response", "Schema", "Xml", "SchemaProperties", "NamedSchemas", "NamedResponses", "NamedParameters", "NamedSecuritySchemes", "SecurityScheme", "XCodeSample", "XCodeSampleList", "XServerList", "XServer", "Server", "ServerList", "ServerVariable", "ServerVariablesMap", "Callback", "CallbacksMap", "RequestBody", "MediaTypesMap", "MediaType", "Encoding", "EncodingMap", "HeadersMap", "Link", "DiscriminatorMapping", "Discriminator", "Components", "LinksMap", "NamedExamples", "NamedRequestBodies", "NamedHeaders", "NamedLinks", "NamedCallbacks", "ImplicitFlow", "PasswordFlow", "ClientCredentials", "AuthorizationCode", "OAuth2Flows", "XUsePkce", "WebhooksMap", "PatternProperties", "NamedPathItems", "DependentRequired", "HttpServerBinding", "HttpChannelBinding", "HttpMessageBinding", "HttpOperationBinding", "WsServerBinding", "WsChannelBinding", "WsMessageBinding", "WsOperationBinding", "KafkaServerBinding", "KafkaTopicConfiguration", "KafkaChannelBinding", "KafkaMessageBinding", "KafkaOperationBinding", "AnypointmqServerBinding", "AnypointmqChannelBinding", "AnypointmqMessageBinding", "AnypointmqOperationBinding", "AmqpServerBinding", "AmqpChannelBinding", "AmqpMessageBinding", "AmqpOperationBinding", "Amqp1ServerBinding", "Amqp1ChannelBinding", "Amqp1MessageBinding", "Amqp1OperationBinding", "MqttServerBindingLastWill", "MqttServerBinding", "MqttChannelBinding", "MqttMessageBinding", "MqttOperationBinding", "Mqtt5ServerBinding", "Mqtt5ChannelBinding", "Mqtt5MessageBinding", "Mqtt5OperationBinding", "NatsServerBinding", "NatsChannelBinding", "NatsMessageBinding", "NatsOperationBinding", "JmsServerBinding", "JmsChannelBinding", "JmsMessageBinding", "JmsOperationBinding", "SolaceServerBinding", "SolaceChannelBinding", "SolaceMessageBinding", "SolaceDestination", "SolaceOperationBinding", "StompServerBinding", "StompChannelBinding", "StompMessageBinding", "StompOperationBinding", "RedisServerBinding", "RedisChannelBinding", "RedisMessageBinding", "RedisOperationBinding", "MercureServerBinding", "MercureChannelBinding", "MercureMessageBinding", "MercureOperationBinding", "ServerBindings", "ChannelBindings", "MessageBindings", "OperationBindings", "ServerMap", "ChannelMap", "Channel", "ParametersMap", "MessageExample", "NamedMessages", "NamedMessageTraits", "NamedOperationTraits", "NamedCorrelationIds", "SecuritySchemeFlows", "Message", "OperationTrait", "OperationTraitList", "MessageTrait", "MessageTraitList", "MessageExampleList", "CorrelationId", "Dependencies", "OperationReply", "OperationReplyAddress", "NamedTags", "NamedExternalDocs", "NamedChannels", "NamedOperations", "NamedOperationReplies", "NamedOperationRelyAddresses", "SecuritySchemeList", "MessageList", "Root.info", "Root.sourceDescriptions_items_0", "Root.sourceDescriptions_items_1", "Root.sourceDescriptions_items_2", "Root.sourceDescriptions", "Root.x-parameters_items_0", "Root.x-parameters_items_1", "Root.x-parameters", "Root.workflows_items.parameters_items_0", "Root.workflows_items.parameters_items_1", "Root.workflows_items.parameters", "Root.workflows_items.inputs", "Root.workflows_items.outputs", "Root.workflows_items.steps_items.parameters_items_0", "Root.workflows_items.steps_items.parameters_items_1", "Root.workflows_items.steps_items.parameters", "Root.workflows_items.steps_items.successCriteria_items.type_1", "Root.workflows_items.steps_items.successCriteria_items.type_2", "Root.workflows_items.steps_items.successCriteria_items", "Root.workflows_items.steps_items.successCriteria", "Root.workflows_items.steps_items.onSuccess_items.criteria_items.type_1", "Root.workflows_items.steps_items.onSuccess_items.criteria_items.type_2", "Root.workflows_items.steps_items.onSuccess_items.criteria_items", "Root.workflows_items.steps_items.onSuccess_items.criteria", "Root.workflows_items.steps_items.onSuccess_items", "Root.workflows_items.steps_items.onSuccess", "Root.workflows_items.steps_items.onFailure_items.criteria_items.type_1", "Root.workflows_items.steps_items.onFailure_items.criteria_items.type_2", "Root.workflows_items.steps_items.onFailure_items.criteria_items", "Root.workflows_items.steps_items.onFailure_items.criteria", "Root.workflows_items.steps_items.onFailure_items", "Root.workflows_items.steps_items.onFailure", "Root.workflows_items.steps_items.outputs", "Root.workflows_items.steps_items.x-expect", "Root.workflows_items.steps_items.x-operation", "Root.workflows_items.steps_items.requestBody.replacements_items", "Root.workflows_items.steps_items.requestBody.replacements", "Root.workflows_items.steps_items.requestBody", "Root.workflows_items.steps_items", "Root.workflows_items.steps", "Root.workflows_items.successActions_items.criteria_items.type_1", "Root.workflows_items.successActions_items.criteria_items.type_2", "Root.workflows_items.successActions_items.criteria_items", "Root.workflows_items.successActions_items.criteria", "Root.workflows_items.successActions_items", "Root.workflows_items.successActions", "Root.workflows_items.failureActions_items.criteria_items.type_1", "Root.workflows_items.failureActions_items.criteria_items.type_2", "Root.workflows_items.failureActions_items.criteria_items", "Root.workflows_items.failureActions_items.criteria", "Root.workflows_items.failureActions_items", "Root.workflows_items.failureActions", "Root.workflows_items", "Root.workflows", "Root.components.inputs_additionalProperties", "Root.components.inputs", "Root.components.parameters_additionalProperties_0", "Root.components.parameters_additionalProperties_1", "Root.components.parameters", "Root.components.successActions_additionalProperties.criteria_items.type_1", "Root.components.successActions_additionalProperties.criteria_items.type_2", "Root.components.successActions_additionalProperties.criteria_items", "Root.components.successActions_additionalProperties.criteria", "Root.components.successActions_additionalProperties", "Root.components.successActions", "Root.components.failureActions_additionalProperties.criteria_items.type_1", "Root.components.failureActions_additionalProperties.criteria_items.type_2", "Root.components.failureActions_additionalProperties.criteria_items", "Root.components.failureActions_additionalProperties.criteria", "Root.components.failureActions_additionalProperties", "Root.components.failureActions", "Root.components", "SpecExtension".
+\`type\` can be one of the following only: "any", "Root", "Tag", "TagList", "TagGroups", "TagGroup", "ExternalDocs", "Example", "ExamplesMap", "EnumDescriptions", "SecurityRequirement", "SecurityRequirementList", "Info", "Contact", "License", "Logo", "Paths", "PathItem", "Parameter", "ParameterItems", "ParameterList", "Operation", "Examples", "Header", "Responses", "Response", "Schema", "Xml", "SchemaProperties", "NamedSchemas", "NamedResponses", "NamedParameters", "NamedSecuritySchemes", "SecurityScheme", "XCodeSample", "XCodeSampleList", "XServerList", "XServer", "Server", "ServerList", "ServerVariable", "ServerVariablesMap", "Callback", "CallbacksMap", "RequestBody", "MediaTypesMap", "MediaType", "Encoding", "EncodingMap", "HeadersMap", "Link", "DiscriminatorMapping", "Discriminator", "Components", "LinksMap", "NamedExamples", "NamedRequestBodies", "NamedHeaders", "NamedLinks", "NamedCallbacks", "ImplicitFlow", "PasswordFlow", "ClientCredentials", "AuthorizationCode", "OAuth2Flows", "XUsePkce", "WebhooksMap", "PatternProperties", "NamedPathItems", "DependentRequired", "HttpServerBinding", "HttpChannelBinding", "HttpMessageBinding", "HttpOperationBinding", "WsServerBinding", "WsChannelBinding", "WsMessageBinding", "WsOperationBinding", "KafkaServerBinding", "KafkaTopicConfiguration", "KafkaChannelBinding", "KafkaMessageBinding", "KafkaOperationBinding", "AnypointmqServerBinding", "AnypointmqChannelBinding", "AnypointmqMessageBinding", "AnypointmqOperationBinding", "AmqpServerBinding", "AmqpChannelBinding", "AmqpMessageBinding", "AmqpOperationBinding", "Amqp1ServerBinding", "Amqp1ChannelBinding", "Amqp1MessageBinding", "Amqp1OperationBinding", "MqttServerBindingLastWill", "MqttServerBinding", "MqttChannelBinding", "MqttMessageBinding", "MqttOperationBinding", "Mqtt5ServerBinding", "Mqtt5ChannelBinding", "Mqtt5MessageBinding", "Mqtt5OperationBinding", "NatsServerBinding", "NatsChannelBinding", "NatsMessageBinding", "NatsOperationBinding", "JmsServerBinding", "JmsChannelBinding", "JmsMessageBinding", "JmsOperationBinding", "SolaceServerBinding", "SolaceChannelBinding", "SolaceMessageBinding", "SolaceDestination", "SolaceOperationBinding", "StompServerBinding", "StompChannelBinding", "StompMessageBinding", "StompOperationBinding", "RedisServerBinding", "RedisChannelBinding", "RedisMessageBinding", "RedisOperationBinding", "MercureServerBinding", "MercureChannelBinding", "MercureMessageBinding", "MercureOperationBinding", "ServerBindings", "ChannelBindings", "MessageBindings", "OperationBindings", "ServerMap", "ChannelMap", "Channel", "ParametersMap", "MessageExample", "NamedMessages", "NamedMessageTraits", "NamedOperationTraits", "NamedCorrelationIds", "SecuritySchemeFlows", "Message", "OperationTrait", "OperationTraitList", "MessageTrait", "MessageTraitList", "MessageExampleList", "CorrelationId", "Dependencies", "OperationReply", "OperationReplyAddress", "NamedTags", "NamedExternalDocs", "NamedChannels", "NamedOperations", "NamedOperationReplies", "NamedOperationRelyAddresses", "SecuritySchemeList", "MessageList", "SourceDescriptions", "OpenAPISourceDescription", "NoneSourceDescription", "ArazzoSourceDescription", "Parameters", "ReusableObject", "Workflows", "Workflow", "Steps", "Step", "Replacement", "ExtendedOperation", "ExpectSchema", "Outputs", "CriterionObject", "XPathCriterion", "JSONPathCriterion", "SuccessActionObject", "OnSuccessActionList", "FailureActionObject", "OnFailureActionList", "NamedInputs", "NamedSuccessActions", "NamedFailureActions", "SpecExtension".
 
  7 | where:
  8 |   - subject:
diff --git a/__tests__/lint/arazzo-type-extensions-with-plugin/plugins/type-extention.js b/__tests__/lint/arazzo-type-extensions-with-plugin/plugins/type-extention.js
index b5972d57..1d5049c1 100644
--- a/__tests__/lint/arazzo-type-extensions-with-plugin/plugins/type-extention.js
+++ b/__tests__/lint/arazzo-type-extensions-with-plugin/plugins/type-extention.js
@@ -13,10 +13,10 @@ module.exports = {
       newTypes = {
         ...types,
         XMetaData: XMetaData,
-        'Root.info': {
-          ...types['Root.info'],
+        Info: {
+          ...types['Info'],
           properties: {
-            ...types['Root.info'].properties,
+            ...types['Info'].properties,
             metadata: 'XMetaData',
           },
         },
diff --git a/__tests__/stats/stats-json/snapshot.js b/__tests__/stats/stats-json/snapshot.js
index 660905d7..2c1f9390 100644
--- a/__tests__/stats/stats-json/snapshot.js
+++ b/__tests__/stats/stats-json/snapshot.js
@@ -4,7 +4,7 @@ exports[`E2E stats stats should produce correct JSON output 1`] = `
 {
   "refs": {
     "metric": "🚗 References",
-    "total": 39
+    "total": 43
   },
   "externalDocs": {
     "metric": "📦 External Documents",
@@ -12,7 +12,7 @@ exports[`E2E stats stats should produce correct JSON output 1`] = `
   },
   "schemas": {
     "metric": "📈 Schemas",
-    "total": 22
+    "total": 23
   },
   "parameters": {
     "metric": "👉 Parameters",
diff --git a/__tests__/stats/stats-markdown/snapshot.js b/__tests__/stats/stats-markdown/snapshot.js
index c98c9e4a..5fb0e4b7 100644
--- a/__tests__/stats/stats-markdown/snapshot.js
+++ b/__tests__/stats/stats-markdown/snapshot.js
@@ -3,9 +3,9 @@
 exports[`E2E stats stats should produce correct Markdown format 1`] = `
 | Feature  | Count  |
 | --- | --- |
-| 🚗 References | 39 |
+| 🚗 References | 43 |
 | 📦 External Documents | 0 |
-| 📈 Schemas | 22 |
+| 📈 Schemas | 23 |
 | 👉 Parameters | 6 |
 | 🔗 Links | 0 |
 | 🔀 Path Items | 5 |
diff --git a/__tests__/stats/stats-stylish/snapshot.js b/__tests__/stats/stats-stylish/snapshot.js
index 4c617c36..ff9e0bca 100644
--- a/__tests__/stats/stats-stylish/snapshot.js
+++ b/__tests__/stats/stats-stylish/snapshot.js
@@ -4,9 +4,9 @@ exports[`E2E stats stats should produce correct output (stylish format) 1`] = `
 
 Document: museum.yaml stats:
 
-🚗 References: 39 
+🚗 References: 43 
 📦 External Documents: 0 
-📈 Schemas: 22 
+📈 Schemas: 23 
 👉 Parameters: 6 
 🔗 Links: 0 
 🔀 Path Items: 5 
diff --git a/packages/core/__tests__/utils.ts b/packages/core/__tests__/utils.ts
index 9f51bfb3..69b3ef4b 100644
--- a/packages/core/__tests__/utils.ts
+++ b/packages/core/__tests__/utils.ts
@@ -69,17 +69,24 @@ export function makeConfigForRuleset(
   });
 }
 
-export async function makeConfig(
-  rules: Record<string, RuleConfig>,
-  decorators?: Record<string, DecoratorConfig>,
-  configPath?: string
-) {
+export async function makeConfig({
+  rules,
+  decorators,
+  configPath,
+  arazzoRules,
+}: {
+  rules: Record<string, RuleConfig>;
+  decorators?: Record<string, DecoratorConfig>;
+  configPath?: string;
+  arazzoRules?: Record<string, RuleConfig>;
+}) {
   return new StyleguideConfig(
     await resolveStyleguideConfig({
       styleguideConfig: {
         plugins: [],
         extends: [],
         rules,
+        arazzoRules,
         decorators,
       },
     }),
diff --git a/packages/core/src/__tests__/bundle.test.ts b/packages/core/src/__tests__/bundle.test.ts
index aed9007f..a56c8f02 100644
--- a/packages/core/src/__tests__/bundle.test.ts
+++ b/packages/core/src/__tests__/bundle.test.ts
@@ -164,7 +164,7 @@ describe('bundle', () => {
       ''
     );
 
-    const config = await makeConfig({}, { 'registry-dependencies': 'on' });
+    const config = await makeConfig({ rules: {}, decorators: { 'registry-dependencies': 'on' } });
 
     const {
       bundle: result,
@@ -205,7 +205,7 @@ describe('bundle', () => {
       ''
     );
 
-    const config = await makeConfig({});
+    const config = await makeConfig({ rules: {} });
 
     const {
       bundle: { parsed },
@@ -305,7 +305,7 @@ describe('bundle async', () => {
       ''
     );
 
-    const config = await makeConfig({});
+    const config = await makeConfig({ rules: {} });
 
     const {
       bundle: { parsed },
@@ -375,7 +375,7 @@ describe('bundle async', () => {
       ''
     );
 
-    const config = await makeConfig({});
+    const config = await makeConfig({ rules: {} });
 
     const {
       bundle: { parsed },
diff --git a/packages/core/src/__tests__/lint.test.ts b/packages/core/src/__tests__/lint.test.ts
index 4e1ca1bc..9784c16d 100644
--- a/packages/core/src/__tests__/lint.test.ts
+++ b/packages/core/src/__tests__/lint.test.ts
@@ -1413,7 +1413,7 @@ describe('lint', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -1492,7 +1492,7 @@ describe('lint', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -1528,7 +1528,11 @@ describe('lint', () => {
     const result = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-operationId': 'error' }, undefined, configFilePath),
+      config: await makeConfig({
+        rules: { 'operation-operationId': 'error' },
+        decorators: undefined,
+        configPath: configFilePath,
+      }),
     });
     expect(result).toHaveLength(1);
     expect(result).toMatchObject([
@@ -1590,7 +1594,11 @@ describe('lint', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }, undefined, configFilePath),
+      config: await makeConfig({
+        rules: { spec: 'error' },
+        decorators: undefined,
+        configPath: configFilePath,
+      }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -1662,7 +1670,11 @@ describe('lint', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }, undefined, configFilePath),
+      config: await makeConfig({
+        rules: { spec: 'error' },
+        decorators: undefined,
+        configPath: configFilePath,
+      }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/config/__tests__/__snapshots__/config-resolvers.test.ts.snap b/packages/core/src/config/__tests__/__snapshots__/config-resolvers.test.ts.snap
index 535a9795..b3e46893 100644
--- a/packages/core/src/config/__tests__/__snapshots__/config-resolvers.test.ts.snap
+++ b/packages/core/src/config/__tests__/__snapshots__/config-resolvers.test.ts.snap
@@ -5,6 +5,7 @@ exports[`resolveConfig should ignore minimal from the root and read local file 1
   "arazzoDecorators": {},
   "arazzoPreprocessors": {},
   "arazzoRules": {
+    "parameters-no-body-inside-in": "off",
     "spec": "error",
   },
   "async2Decorators": {},
@@ -133,6 +134,7 @@ exports[`resolveStyleguideConfig should resolve extends with local file config w
   "arazzoDecorators": {},
   "arazzoPreprocessors": {},
   "arazzoRules": {
+    "parameters-no-body-inside-in": "off",
     "spec": "error",
   },
   "async2Decorators": {},
diff --git a/packages/core/src/decorators/__tests__/filter-in.test.ts b/packages/core/src/decorators/__tests__/filter-in.test.ts
index c1191664..cd0bc8fa 100644
--- a/packages/core/src/decorators/__tests__/filter-in.test.ts
+++ b/packages/core/src/decorators/__tests__/filter-in.test.ts
@@ -56,7 +56,10 @@ describe('oas3 filter-in', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'filter-in': { value: 'public', property: 'x-access' } }),
+      config: await makeConfig({
+        rules: {},
+        decorators: { 'filter-in': { value: 'public', property: 'x-access' } },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -76,16 +79,16 @@ describe('oas3 filter-in', () => {
     const { bundle: res } = await bundleDocument({
       document: inputDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-in': {
             property: 'x-audience',
             value: ['Public', 'Protected'],
             matchStrategy: 'all',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -130,16 +133,16 @@ describe('oas3 filter-in', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-in': {
             property: 'x-audience',
             value: ['Public', 'Global'],
             matchStrategy: 'any',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -171,16 +174,16 @@ describe('oas3 filter-in', () => {
     const { bundle: res } = await bundleDocument({
       document: inputDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-in': {
             property: 'x-audience',
             value: 'non-existing-audience',
             matchStrategy: 'any',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -220,16 +223,16 @@ describe('oas3 filter-in', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-in': {
             property: 'x-audience',
             value: ['Public', 'Global'],
             matchStrategy: 'any',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -279,16 +282,16 @@ describe('oas2 filter-in', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-in': {
             property: 'x-access',
             value: ['public', 'global'],
             matchStrategy: 'any',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       swagger: '2.0'
diff --git a/packages/core/src/decorators/__tests__/filter-out.test.ts b/packages/core/src/decorators/__tests__/filter-out.test.ts
index 58e52944..fca6b2fa 100644
--- a/packages/core/src/decorators/__tests__/filter-out.test.ts
+++ b/packages/core/src/decorators/__tests__/filter-out.test.ts
@@ -52,7 +52,10 @@ describe('oas3 filter-out', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'filter-out': { property: 'x-access', value: 'private' } }),
+      config: await makeConfig({
+        rules: {},
+        decorators: { 'filter-out': { property: 'x-access', value: 'private' } },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
           openapi: 3.0.0
@@ -68,16 +71,16 @@ describe('oas3 filter-out', () => {
     const { bundle: res } = await bundleDocument({
       document: inputDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-out': {
             property: 'x-audience',
             value: ['Private', 'Protected'],
             matchStrategy: 'all',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -99,16 +102,16 @@ describe('oas3 filter-out', () => {
     const { bundle: res } = await bundleDocument({
       document: inputDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-out': {
             property: 'x-audience',
             value: ['Private', 'Protected'],
             matchStrategy: 'any',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
         openapi: 3.0.0
@@ -138,16 +141,16 @@ describe('oas3 filter-out', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-out': {
             property: 'x-access',
             value: 'private',
             matchStrategy: 'any',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -192,7 +195,10 @@ describe('oas3 filter-out', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'filter-out': { property: 'x-prop', value: false } }),
+      config: await makeConfig({
+        rules: {},
+        decorators: { 'filter-out': { property: 'x-prop', value: false } },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -244,7 +250,10 @@ describe('oas3 filter-out', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'filter-out': { property: 'x-prop', value: null } }),
+      config: await makeConfig({
+        rules: {},
+        decorators: { 'filter-out': { property: 'x-prop', value: null } },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.0
@@ -305,16 +314,16 @@ describe('oas2 filter-out', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'filter-out': {
             property: 'x-access',
             value: ['private', 'protected'],
             matchStrategy: 'any',
           },
-        }
-      ),
+        },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       swagger: '2.0'
diff --git a/packages/core/src/decorators/__tests__/media-type-examples-override.test.ts b/packages/core/src/decorators/__tests__/media-type-examples-override.test.ts
index 91588ded..a29b9a63 100644
--- a/packages/core/src/decorators/__tests__/media-type-examples-override.test.ts
+++ b/packages/core/src/decorators/__tests__/media-type-examples-override.test.ts
@@ -28,9 +28,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -43,8 +43,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -88,9 +88,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -101,8 +101,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -153,9 +153,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -176,8 +176,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -245,9 +245,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -264,8 +264,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -345,9 +345,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -364,8 +364,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -417,9 +417,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -436,8 +436,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -489,9 +489,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -504,8 +504,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -550,9 +550,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -565,8 +565,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -618,9 +618,9 @@ describe('oas3 media-type-examples-override', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig(
-        {},
-        {
+      config: await makeConfig({
+        rules: {},
+        decorators: {
           'media-type-examples-override': {
             operationIds: {
               getUserById: {
@@ -633,8 +633,8 @@ describe('oas3 media-type-examples-override', () => {
               },
             },
           },
-        }
-      ),
+        },
+      }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
diff --git a/packages/core/src/decorators/__tests__/remove-x-internal.test.ts b/packages/core/src/decorators/__tests__/remove-x-internal.test.ts
index 4c9f31c7..7035cd74 100644
--- a/packages/core/src/decorators/__tests__/remove-x-internal.test.ts
+++ b/packages/core/src/decorators/__tests__/remove-x-internal.test.ts
@@ -25,7 +25,10 @@ describe('oas3 remove-x-internal', () => {
     const { bundle: res } = await bundleDocument({
       document: testDocument,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'remove-x-internal': { internalFlagProperty: 'removeit' } }),
+      config: await makeConfig({
+        rules: {},
+        decorators: { 'remove-x-internal': { internalFlagProperty: 'removeit' } },
+      }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
           openapi: 3.0.0
@@ -92,7 +95,7 @@ describe('oas3 remove-x-internal', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'remove-x-internal': 'on' }),
+      config: await makeConfig({ rules: {}, decorators: { 'remove-x-internal': 'on' } }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.1.0
@@ -165,7 +168,7 @@ describe('oas3 remove-x-internal', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'remove-x-internal': 'on' }),
+      config: await makeConfig({ rules: {}, decorators: { 'remove-x-internal': 'on' } }),
     });
 
     expect(res.parsed).toMatchInlineSnapshot(`
@@ -239,7 +242,7 @@ describe('oas3 remove-x-internal', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'remove-x-internal': 'on' }),
+      config: await makeConfig({ rules: {}, decorators: { 'remove-x-internal': 'on' } }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
       openapi: 3.0.1
@@ -302,7 +305,7 @@ describe('oas2 remove-x-internal', () => {
     const { bundle: res } = await bundleDocument({
       document: testDoc,
       externalRefResolver: new BaseResolver(),
-      config: await makeConfig({}, { 'remove-x-internal': 'on' }),
+      config: await makeConfig({ rules: {}, decorators: { 'remove-x-internal': 'on' } }),
     });
     expect(res.parsed).toMatchInlineSnapshot(`
           swagger: '2.0'
diff --git a/packages/core/src/decorators/oas2/__tests__/remove-unused-components.test.ts b/packages/core/src/decorators/oas2/__tests__/remove-unused-components.test.ts
index e5af0836..03b63e10 100644
--- a/packages/core/src/decorators/oas2/__tests__/remove-unused-components.test.ts
+++ b/packages/core/src/decorators/oas2/__tests__/remove-unused-components.test.ts
@@ -38,7 +38,7 @@ describe('oas2 remove-unused-components', () => {
     const results = await bundleDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({}),
+      config: await makeConfig({ rules: {} }),
       removeUnusedComponents: true,
     });
 
@@ -111,7 +111,7 @@ describe('oas2 remove-unused-components', () => {
     const results = await bundleDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({}),
+      config: await makeConfig({ rules: {} }),
       removeUnusedComponents: true,
     });
 
@@ -192,7 +192,7 @@ describe('oas2 remove-unused-components', () => {
     const results = await bundleDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({}),
+      config: await makeConfig({ rules: {} }),
       removeUnusedComponents: true,
     });
 
diff --git a/packages/core/src/decorators/oas3/__tests__/remove-unused-components.test.ts b/packages/core/src/decorators/oas3/__tests__/remove-unused-components.test.ts
index a6159c0a..7d0d223e 100644
--- a/packages/core/src/decorators/oas3/__tests__/remove-unused-components.test.ts
+++ b/packages/core/src/decorators/oas3/__tests__/remove-unused-components.test.ts
@@ -42,7 +42,7 @@ describe('oas3 remove-unused-components', () => {
     const results = await bundleDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({}),
+      config: await makeConfig({ rules: {} }),
       removeUnusedComponents: true,
     });
 
@@ -121,7 +121,7 @@ describe('oas3 remove-unused-components', () => {
     const results = await bundleDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({}),
+      config: await makeConfig({ rules: {} }),
       removeUnusedComponents: true,
     });
 
@@ -204,7 +204,7 @@ describe('oas3 remove-unused-components', () => {
     const results = await bundleDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({}),
+      config: await makeConfig({ rules: {} }),
       removeUnusedComponents: true,
     });
 
@@ -270,7 +270,7 @@ describe('oas3 remove-unused-components', () => {
     const results = await bundleDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({}),
+      config: await makeConfig({ rules: {} }),
       removeUnusedComponents: true,
     });
 
diff --git a/packages/core/src/rules/__tests__/no-unresolved-refs.test.ts b/packages/core/src/rules/__tests__/no-unresolved-refs.test.ts
index 650d0ccc..8299d1d7 100644
--- a/packages/core/src/rules/__tests__/no-unresolved-refs.test.ts
+++ b/packages/core/src/rules/__tests__/no-unresolved-refs.test.ts
@@ -22,7 +22,9 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-unresolved-refs': 'error',
+        rules: {
+          'no-unresolved-refs': 'error',
+        },
       }),
     });
 
@@ -62,7 +64,9 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-unresolved-refs': 'error',
+        rules: {
+          'no-unresolved-refs': 'error',
+        },
       }),
     });
 
@@ -119,7 +123,9 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-unresolved-refs': 'error',
+        rules: {
+          'no-unresolved-refs': 'error',
+        },
       }),
     });
 
@@ -143,7 +149,9 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-unresolved-refs': 'error',
+        rules: {
+          'no-unresolved-refs': 'error',
+        },
       }),
     });
 
@@ -190,7 +198,9 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-unresolved-refs': 'error',
+        rules: {
+          'no-unresolved-refs': 'error',
+        },
       }),
     });
 
@@ -219,7 +229,9 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-unresolved-refs': 'error',
+        rules: {
+          'no-unresolved-refs': 'error',
+        },
       }),
     });
 
@@ -248,7 +260,9 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-unresolved-refs': 'error',
+        rules: {
+          'no-unresolved-refs': 'error',
+        },
       }),
     });
 
diff --git a/packages/core/src/rules/arazzo/__tests__/parameters-no-body-inside-in.test.ts b/packages/core/src/rules/arazzo/__tests__/parameters-no-body-inside-in.test.ts
new file mode 100644
index 00000000..8551082b
--- /dev/null
+++ b/packages/core/src/rules/arazzo/__tests__/parameters-no-body-inside-in.test.ts
@@ -0,0 +1,76 @@
+import { outdent } from 'outdent';
+import { lintDocument } from '../../../lint';
+import { parseYamlToDocument, replaceSourceWithRef, makeConfig } from '../../../../__tests__/utils';
+import { BaseResolver } from '../../../resolve';
+import { StyleguideConfig } from '../../../config';
+import { ArazzoRule } from '../../../visitors';
+
+describe('Arazzo parameters-no-body-inside-in', () => {
+  const document = parseYamlToDocument(
+    outdent`
+      arazzo: '1.0.0'
+      info:
+        title: Cool API
+        version: 1.0.0
+        description: A cool API
+      sourceDescriptions:
+        - name: museum-api
+          type: openapi
+          url: openapi.yaml
+      workflows:
+        - workflowId: get-museum-hours
+          description: This workflow demonstrates how to get the museum opening hours and buy tickets.
+          parameters:
+            - in: body
+              name: Authorization
+              value: Basic Og==
+          steps:
+            - stepId: get-museum-hours
+              description: >-
+                Get museum hours by resolving request details with getMuseumHours operationId from openapi.yaml description.
+              operationId: museum-api.getMuseumHours
+              successCriteria:
+                - condition: $statusCode == 200
+    `,
+    'arazzo.yaml'
+  );
+
+  it('should not report on `body` inside parameter `in` field', async () => {
+    const results = await lintDocument({
+      externalRefResolver: new BaseResolver(),
+      document,
+      config: await makeConfig({ rules: {} }),
+    });
+
+    expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
+  });
+
+  it('should report on `body` inside parameter `in` field', async () => {
+    const results = await lintDocument({
+      externalRefResolver: new BaseResolver(),
+      document,
+      config: await makeConfig({
+        rules: {},
+        arazzoRules: { 'parameters-no-body-inside-in': 'error' },
+      }),
+    });
+
+    expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
+      [
+        {
+          "location": [
+            {
+              "pointer": "#/workflows/0/parameters/0/in",
+              "reportOnKey": false,
+              "source": "arazzo.yaml",
+            },
+          ],
+          "message": "The \`body\` value of the \`in\` property is not supported by Spot.",
+          "ruleId": "parameters-no-body-inside-in",
+          "severity": "error",
+          "suggest": [],
+        },
+      ]
+    `);
+  });
+});
diff --git a/packages/core/src/rules/async2/__tests__/channels-kebab-case.test.ts b/packages/core/src/rules/async2/__tests__/channels-kebab-case.test.ts
index 843495db..befb02bb 100644
--- a/packages/core/src/rules/async2/__tests__/channels-kebab-case.test.ts
+++ b/packages/core/src/rules/async2/__tests__/channels-kebab-case.test.ts
@@ -23,7 +23,7 @@ describe('Async2 channels-kebab-case', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'channels-kebab-case': 'error' }),
+      config: await makeConfig({ rules: { 'channels-kebab-case': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -64,7 +64,7 @@ describe('Async2 channels-kebab-case', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'channels-kebab-case': 'error' }),
+      config: await makeConfig({ rules: { 'channels-kebab-case': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -106,8 +106,10 @@ describe('Async2 channels-kebab-case', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'paths-kebab-case': 'error',
-        'no-path-trailing-slash': 'off',
+        rules: {
+          'paths-kebab-case': 'error',
+          'no-path-trailing-slash': 'off',
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -133,7 +135,9 @@ describe('Async2 channels-kebab-case', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'paths-kebab-case': 'error',
+        rules: {
+          'paths-kebab-case': 'error',
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/async2/__tests__/no-channel-trailing-slash.test.ts b/packages/core/src/rules/async2/__tests__/no-channel-trailing-slash.test.ts
index c9ae151f..3d0719ea 100644
--- a/packages/core/src/rules/async2/__tests__/no-channel-trailing-slash.test.ts
+++ b/packages/core/src/rules/async2/__tests__/no-channel-trailing-slash.test.ts
@@ -23,7 +23,7 @@ describe('no-channel-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-channel-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-channel-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -64,7 +64,7 @@ describe('no-channel-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-channel-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-channel-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -89,7 +89,7 @@ describe('no-channel-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-channel-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-channel-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/async3/__tests__/channels-kebab-case.test.ts b/packages/core/src/rules/async3/__tests__/channels-kebab-case.test.ts
index 3123b817..5d6c4a95 100644
--- a/packages/core/src/rules/async3/__tests__/channels-kebab-case.test.ts
+++ b/packages/core/src/rules/async3/__tests__/channels-kebab-case.test.ts
@@ -23,7 +23,7 @@ describe('Async2 channels-kebab-case', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'channels-kebab-case': 'error' }),
+      config: await makeConfig({ rules: { 'channels-kebab-case': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -64,7 +64,7 @@ describe('Async2 channels-kebab-case', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'channels-kebab-case': 'error' }),
+      config: await makeConfig({ rules: { 'channels-kebab-case': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -106,8 +106,10 @@ describe('Async2 channels-kebab-case', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'paths-kebab-case': 'error',
-        'no-path-trailing-slash': 'off',
+        rules: {
+          'paths-kebab-case': 'error',
+          'no-path-trailing-slash': 'off',
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -133,7 +135,9 @@ describe('Async2 channels-kebab-case', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'paths-kebab-case': 'error',
+        rules: {
+          'paths-kebab-case': 'error',
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/async3/__tests__/no-channel-trailing-slash.test.ts b/packages/core/src/rules/async3/__tests__/no-channel-trailing-slash.test.ts
index cb84e9b7..30cdf182 100644
--- a/packages/core/src/rules/async3/__tests__/no-channel-trailing-slash.test.ts
+++ b/packages/core/src/rules/async3/__tests__/no-channel-trailing-slash.test.ts
@@ -23,7 +23,7 @@ describe('no-channel-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-channel-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-channel-trailing-slash': 'error' } }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
       [
@@ -63,7 +63,7 @@ describe('no-channel-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-channel-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-channel-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -88,7 +88,7 @@ describe('no-channel-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-channel-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-channel-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/info-license.test.ts b/packages/core/src/rules/common/__tests__/info-license.test.ts
index 577ddcb8..b3e6e1a4 100644
--- a/packages/core/src/rules/common/__tests__/info-license.test.ts
+++ b/packages/core/src/rules/common/__tests__/info-license.test.ts
@@ -17,7 +17,7 @@ describe('Oas3 info-license', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'info-license': 'error' }),
+      config: await makeConfig({ rules: { 'info-license': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -54,7 +54,7 @@ describe('Oas3 info-license', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'info-license': 'error' }),
+      config: await makeConfig({ rules: { 'info-license': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/license-url.test.ts b/packages/core/src/rules/common/__tests__/license-url.test.ts
index 86041ab1..60f602f4 100644
--- a/packages/core/src/rules/common/__tests__/license-url.test.ts
+++ b/packages/core/src/rules/common/__tests__/license-url.test.ts
@@ -18,7 +18,7 @@ describe('Oas3 license-url', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'info-license-url': 'error' }),
+      config: await makeConfig({ rules: { 'info-license-url': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -55,7 +55,7 @@ describe('Oas3 license-url', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'info-license-url': 'error' }),
+      config: await makeConfig({ rules: { 'info-license': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/no-ambiguous-paths.test.ts b/packages/core/src/rules/common/__tests__/no-ambiguous-paths.test.ts
index e89312b2..a0171508 100644
--- a/packages/core/src/rules/common/__tests__/no-ambiguous-paths.test.ts
+++ b/packages/core/src/rules/common/__tests__/no-ambiguous-paths.test.ts
@@ -46,7 +46,7 @@ describe('no-ambiguous-paths', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-ambiguous-paths': 'error' }),
+      config: await makeConfig({ rules: { 'no-ambiguous-paths': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/no-enum-type-mismatch.test.ts b/packages/core/src/rules/common/__tests__/no-enum-type-mismatch.test.ts
index c6c08ed7..f7cacf3e 100644
--- a/packages/core/src/rules/common/__tests__/no-enum-type-mismatch.test.ts
+++ b/packages/core/src/rules/common/__tests__/no-enum-type-mismatch.test.ts
@@ -29,7 +29,7 @@ describe('Oas3 typed enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-enum-type-mismatch': 'error' }),
+      config: await makeConfig({ rules: { 'no-enum-type-mismatch': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -62,7 +62,7 @@ describe('Oas3 typed enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-enum-type-mismatch': 'error' }),
+      config: await makeConfig({ rules: { 'no-enum-type-mismatch': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -92,7 +92,7 @@ describe('Oas3 typed enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-enum-type-mismatch': 'error' }),
+      config: await makeConfig({ rules: { 'no-enum-type-mismatch': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -140,7 +140,7 @@ describe('Oas3 typed enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-enum-type-mismatch': 'error' }),
+      config: await makeConfig({ rules: { 'no-enum-type-mismatch': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -185,7 +185,7 @@ describe('Oas3 typed enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error', 'no-enum-type-mismatch': 'error' }),
+      config: await makeConfig({ rules: { spec: 'error', 'no-enum-type-mismatch': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/no-identical-paths.test.ts b/packages/core/src/rules/common/__tests__/no-identical-paths.test.ts
index ac17fada..a2310a41 100644
--- a/packages/core/src/rules/common/__tests__/no-identical-paths.test.ts
+++ b/packages/core/src/rules/common/__tests__/no-identical-paths.test.ts
@@ -34,7 +34,7 @@ describe('no-identical-paths', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-identical-paths': 'error' }),
+      config: await makeConfig({ rules: { 'no-identical-paths': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/no-invalid-parameter-examples.test.ts b/packages/core/src/rules/common/__tests__/no-invalid-parameter-examples.test.ts
index df1b05eb..9df4aad2 100644
--- a/packages/core/src/rules/common/__tests__/no-invalid-parameter-examples.test.ts
+++ b/packages/core/src/rules/common/__tests__/no-invalid-parameter-examples.test.ts
@@ -25,7 +25,7 @@ describe('no-invalid-parameter-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-parameter-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-parameter-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/no-invalid-schema-examples.test.ts b/packages/core/src/rules/common/__tests__/no-invalid-schema-examples.test.ts
index 96830c97..e6f4353c 100644
--- a/packages/core/src/rules/common/__tests__/no-invalid-schema-examples.test.ts
+++ b/packages/core/src/rules/common/__tests__/no-invalid-schema-examples.test.ts
@@ -23,7 +23,7 @@ describe('no-invalid-schema-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-schema-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-schema-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/no-path-trailing-slash.test.ts b/packages/core/src/rules/common/__tests__/no-path-trailing-slash.test.ts
index 869ab1c8..9e4bec42 100644
--- a/packages/core/src/rules/common/__tests__/no-path-trailing-slash.test.ts
+++ b/packages/core/src/rules/common/__tests__/no-path-trailing-slash.test.ts
@@ -19,7 +19,7 @@ describe('no-path-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-path-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-path-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -60,7 +60,7 @@ describe('no-path-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-path-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-path-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -97,7 +97,7 @@ describe('no-path-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-path-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-path-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -118,7 +118,7 @@ describe('no-path-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-path-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-path-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/no-required-schema-properties-undefined.test.ts b/packages/core/src/rules/common/__tests__/no-required-schema-properties-undefined.test.ts
index eedc4dc6..4d49c927 100644
--- a/packages/core/src/rules/common/__tests__/no-required-schema-properties-undefined.test.ts
+++ b/packages/core/src/rules/common/__tests__/no-required-schema-properties-undefined.test.ts
@@ -30,7 +30,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -79,7 +79,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -134,7 +134,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -190,7 +190,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -223,7 +223,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -286,7 +286,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -329,7 +329,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -378,7 +378,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -447,7 +447,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -486,7 +486,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -542,7 +542,7 @@ describe('no-required-schema-properties-undefined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-required-schema-properties-undefined': 'error' }),
+      config: await makeConfig({ rules: { 'no-required-schema-properties-undefined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/operation-2xx-response.test.ts b/packages/core/src/rules/common/__tests__/operation-2xx-response.test.ts
index bd037935..e05b5804 100644
--- a/packages/core/src/rules/common/__tests__/operation-2xx-response.test.ts
+++ b/packages/core/src/rules/common/__tests__/operation-2xx-response.test.ts
@@ -21,7 +21,7 @@ describe('Oas3 operation-2xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-2xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-2xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -60,7 +60,7 @@ describe('Oas3 operation-2xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-2xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-2xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -83,7 +83,7 @@ describe('Oas3 operation-2xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-2xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-2xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -104,7 +104,7 @@ describe('Oas3 operation-2xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-2xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-2xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -144,7 +144,9 @@ describe('Oas3 operation-2xx-response', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'operation-2xx-response': { severity: 'error', validateWebhooks: true },
+        rules: {
+          'operation-2xx-response': { severity: 'error', validateWebhooks: true },
+        },
       }),
     });
 
@@ -184,7 +186,7 @@ describe('Oas3 operation-2xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-2xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-2xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/operation-4xx-response.test.ts b/packages/core/src/rules/common/__tests__/operation-4xx-response.test.ts
index 6dad72f5..aaf9bb23 100644
--- a/packages/core/src/rules/common/__tests__/operation-4xx-response.test.ts
+++ b/packages/core/src/rules/common/__tests__/operation-4xx-response.test.ts
@@ -21,7 +21,7 @@ describe('Oas3 operation-4xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -60,7 +60,7 @@ describe('Oas3 operation-4xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -83,7 +83,7 @@ describe('Oas3 operation-4xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -106,7 +106,7 @@ describe('Oas3 operation-4xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -143,7 +143,7 @@ describe('Oas3 operation-4xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-2xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-2xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -183,7 +183,9 @@ describe('Oas3 operation-4xx-response', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'operation-4xx-response': { severity: 'error', validateWebhooks: true },
+        rules: {
+          'operation-4xx-response': { severity: 'error', validateWebhooks: true },
+        },
       }),
     });
 
@@ -223,7 +225,7 @@ describe('Oas3 operation-4xx-response', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-response': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-response': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/operation-operationId-unique.test.ts b/packages/core/src/rules/common/__tests__/operation-operationId-unique.test.ts
index 954f1b9d..398f7db9 100644
--- a/packages/core/src/rules/common/__tests__/operation-operationId-unique.test.ts
+++ b/packages/core/src/rules/common/__tests__/operation-operationId-unique.test.ts
@@ -26,7 +26,7 @@ describe('Oas3 operation-operationId-unique', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-operationId-unique': 'error' }),
+      config: await makeConfig({ rules: { 'operation-operationId-unique': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -68,7 +68,7 @@ describe('Oas3 operation-operationId-unique', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'peration-operationId-unique': 'error' }),
+      config: await makeConfig({ rules: { 'peration-operationId-unique': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/operation-operationId-url-safe.test.ts b/packages/core/src/rules/common/__tests__/operation-operationId-url-safe.test.ts
index 74a8c2ff..ede27d19 100644
--- a/packages/core/src/rules/common/__tests__/operation-operationId-url-safe.test.ts
+++ b/packages/core/src/rules/common/__tests__/operation-operationId-url-safe.test.ts
@@ -21,7 +21,7 @@ describe('Oas3 operation-operationId-url-safe', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-operationId-url-safe': 'error' }),
+      config: await makeConfig({ rules: { 'operation-operationId-url-safe': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/operation-parameters-unique.test.ts b/packages/core/src/rules/common/__tests__/operation-parameters-unique.test.ts
index 286a6489..77b95ff5 100644
--- a/packages/core/src/rules/common/__tests__/operation-parameters-unique.test.ts
+++ b/packages/core/src/rules/common/__tests__/operation-parameters-unique.test.ts
@@ -22,7 +22,7 @@ describe('Oas3 operation-parameters-unique', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-parameters-unique': 'error' }),
+      config: await makeConfig({ rules: { 'operation-parameters-unique': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -65,7 +65,7 @@ describe('Oas3 operation-parameters-unique', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-parameters-unique': 'error' }),
+      config: await makeConfig({ rules: { 'operation-parameters-unique': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -95,7 +95,7 @@ describe('Oas3 operation-parameters-unique', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-parameters-unique': 'error' }),
+      config: await makeConfig({ rules: { 'operation-parameters-unique': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -143,7 +143,7 @@ describe('Oas3 operation-parameters-unique', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-parameters-unique': 'error' }),
+      config: await makeConfig({ rules: { 'operation-parameters-unique': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/operation-singular-tag.test.ts b/packages/core/src/rules/common/__tests__/operation-singular-tag.test.ts
index 5a071d75..adeaf99f 100644
--- a/packages/core/src/rules/common/__tests__/operation-singular-tag.test.ts
+++ b/packages/core/src/rules/common/__tests__/operation-singular-tag.test.ts
@@ -24,7 +24,7 @@ describe('Oas3 operation-singular-tag', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-singular-tag': 'error' }),
+      config: await makeConfig({ rules: { 'operation-singular-tag': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -64,7 +64,7 @@ describe('Oas3 operation-singular-tag', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-singular-tag': 'error' }),
+      config: await makeConfig({ rules: { 'operation-singular-tag': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/path-http-verbs-order.test.ts b/packages/core/src/rules/common/__tests__/path-http-verbs-order.test.ts
index 9cc3a49f..ff97482e 100644
--- a/packages/core/src/rules/common/__tests__/path-http-verbs-order.test.ts
+++ b/packages/core/src/rules/common/__tests__/path-http-verbs-order.test.ts
@@ -23,7 +23,7 @@ describe('Common path-http-verbs-order', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-http-verbs-order': 'error' }),
+      config: await makeConfig({ rules: { 'path-http-verbs-order': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -87,7 +87,7 @@ describe('Common path-http-verbs-order', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-http-verbs-order': 'error' }),
+      config: await makeConfig({ rules: { 'path-http-verbs-order': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/path-not-include-query.test.ts b/packages/core/src/rules/common/__tests__/path-not-include-query.test.ts
index 90b50c54..aff97901 100644
--- a/packages/core/src/rules/common/__tests__/path-not-include-query.test.ts
+++ b/packages/core/src/rules/common/__tests__/path-not-include-query.test.ts
@@ -19,7 +19,7 @@ describe('Oas3 path-not-include-query', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-not-include-query': 'error' }),
+      config: await makeConfig({ rules: { 'path-not-include-query': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -56,7 +56,7 @@ describe('Oas3 path-not-include-query', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-not-include-query': 'error' }),
+      config: await makeConfig({ rules: { 'path-not-include-query': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/path-params-defined.test.ts b/packages/core/src/rules/common/__tests__/path-params-defined.test.ts
index 1a2bd2ae..0193df2b 100644
--- a/packages/core/src/rules/common/__tests__/path-params-defined.test.ts
+++ b/packages/core/src/rules/common/__tests__/path-params-defined.test.ts
@@ -24,7 +24,7 @@ describe('Oas3 path-params-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-params-defined': 'error' }),
+      config: await makeConfig({ rules: { 'path-params-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -52,7 +52,7 @@ describe('Oas3 path-params-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-params-defined': 'error' }),
+      config: await makeConfig({ rules: { 'path-params-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -96,7 +96,7 @@ describe('Oas3 path-params-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-params-defined': 'error' }),
+      config: await makeConfig({ rules: { 'path-params-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -150,7 +150,7 @@ describe('Oas3 path-params-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-params-defined': 'error' }),
+      config: await makeConfig({ rules: { 'path-params-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -194,7 +194,7 @@ describe('Oas3 path-params-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'path-params-defined': 'error' }),
+      config: await makeConfig({ rules: { 'path-params-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/paths-kebab-case.test.ts b/packages/core/src/rules/common/__tests__/paths-kebab-case.test.ts
index 87312986..a93c5a38 100644
--- a/packages/core/src/rules/common/__tests__/paths-kebab-case.test.ts
+++ b/packages/core/src/rules/common/__tests__/paths-kebab-case.test.ts
@@ -22,7 +22,7 @@ describe('Oas3 paths-kebab-case', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'paths-kebab-case': 'error' }),
+      config: await makeConfig({ rules: { 'paths-kebab-case': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -61,7 +61,7 @@ describe('Oas3 paths-kebab-case', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'paths-kebab-case': 'error' }),
+      config: await makeConfig({ rules: { 'paths-kebab-case': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -99,8 +99,10 @@ describe('Oas3 paths-kebab-case', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'paths-kebab-case': 'error',
-        'no-path-trailing-slash': 'off',
+        rules: {
+          'paths-kebab-case': 'error',
+          'no-path-trailing-slash': 'off',
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/scalar-property-missing-example.test.ts b/packages/core/src/rules/common/__tests__/scalar-property-missing-example.test.ts
index e7facbe3..22ed256d 100644
--- a/packages/core/src/rules/common/__tests__/scalar-property-missing-example.test.ts
+++ b/packages/core/src/rules/common/__tests__/scalar-property-missing-example.test.ts
@@ -24,7 +24,7 @@ describe('Oas3 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -68,7 +68,7 @@ describe('Oas3.1 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -111,7 +111,7 @@ describe('Oas3.1 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -140,7 +140,7 @@ describe('Oas3.1 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -174,7 +174,7 @@ describe('Oas3.1 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -199,7 +199,7 @@ describe('Oas3.1 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -230,7 +230,7 @@ describe('Oas3.1 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -256,7 +256,7 @@ describe('Oas3.1 scalar-property-missing-example', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'scalar-property-missing-example': 'error' }),
+      config: await makeConfig({ rules: { 'scalar-property-missing-example': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/security-defined.test.ts b/packages/core/src/rules/common/__tests__/security-defined.test.ts
index 53decfd3..34d10112 100644
--- a/packages/core/src/rules/common/__tests__/security-defined.test.ts
+++ b/packages/core/src/rules/common/__tests__/security-defined.test.ts
@@ -19,7 +19,7 @@ describe('Oas3 security-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'security-defined': 'error' }),
+      config: await makeConfig({ rules: { 'security-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -53,7 +53,7 @@ describe('Oas3 security-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'security-defined': 'error' }),
+      config: await makeConfig({ rules: { 'security-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -73,7 +73,7 @@ describe('Oas3 security-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'security-defined': 'error' }),
+      config: await makeConfig({ rules: { 'security-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -112,7 +112,7 @@ describe('Oas3 security-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'security-defined': 'error' }),
+      config: await makeConfig({ rules: { 'security-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -167,7 +167,7 @@ describe('Oas3 security-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'security-defined': 'error' }),
+      config: await makeConfig({ rules: { 'security-defined': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -190,7 +190,9 @@ describe('Oas3 security-defined', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'security-defined': { exceptions: [{ path: '/excluded' }] },
+        rules: {
+          'security-defined': { exceptions: [{ path: '/excluded' }] },
+        },
       }),
     });
 
@@ -217,7 +219,9 @@ describe('Oas3 security-defined', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'security-defined': { exceptions: [{ path: '/partially-excluded', methods: ['GET'] }] },
+        rules: {
+          'security-defined': { exceptions: [{ path: '/partially-excluded', methods: ['GET'] }] },
+        },
       }),
     });
 
@@ -254,7 +258,9 @@ describe('Oas3 security-defined', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'security-defined': { exceptions: [{ path: '/excluded' }] } }),
+      config: await makeConfig({
+        rules: { 'security-defined': { exceptions: [{ path: '/excluded' }] } },
+      }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/spec-strict-refs.test.ts b/packages/core/src/rules/common/__tests__/spec-strict-refs.test.ts
index 3ddce6e5..e144a33a 100644
--- a/packages/core/src/rules/common/__tests__/spec-strict-refs.test.ts
+++ b/packages/core/src/rules/common/__tests__/spec-strict-refs.test.ts
@@ -33,7 +33,7 @@ describe('Oas3 spec-strict-refs', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'spec-strict-refs': 'error' }),
+      config: await makeConfig({ rules: { 'spec-strict-refs': 'error' } }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
       [
diff --git a/packages/core/src/rules/common/__tests__/spec.test.ts b/packages/core/src/rules/common/__tests__/spec.test.ts
index ee35721d..f1daa99c 100644
--- a/packages/core/src/rules/common/__tests__/spec.test.ts
+++ b/packages/core/src/rules/common/__tests__/spec.test.ts
@@ -25,7 +25,7 @@ describe('Oas3 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -85,7 +85,7 @@ describe('Oas3 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -157,7 +157,7 @@ describe('Oas3 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -231,7 +231,7 @@ describe('Oas3 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -322,7 +322,7 @@ describe('Oas3 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -384,7 +384,7 @@ describe('Oas3.1 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -432,7 +432,7 @@ describe('Oas3.1 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -486,7 +486,7 @@ describe('Oas3.1 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -557,7 +557,7 @@ describe('Oas3.1 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -632,7 +632,7 @@ describe('Oas3.1 spec', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ spec: 'error' }),
+      config: await makeConfig({ rules: { spec: 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/common/__tests__/tag-description.test.ts b/packages/core/src/rules/common/__tests__/tag-description.test.ts
index 15355a0a..8dcf4954 100644
--- a/packages/core/src/rules/common/__tests__/tag-description.test.ts
+++ b/packages/core/src/rules/common/__tests__/tag-description.test.ts
@@ -19,7 +19,7 @@ describe('Oas3 tag-description', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'tag-description': 'error' }),
+      config: await makeConfig({ rules: { 'tag-description': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -57,7 +57,7 @@ describe('Oas3 tag-description', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'tag-description': 'error' }),
+      config: await makeConfig({ rules: { 'tag-description': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/common/__tests__/tags-alphabetical.test.ts b/packages/core/src/rules/common/__tests__/tags-alphabetical.test.ts
index fef94dc7..3019c93d 100644
--- a/packages/core/src/rules/common/__tests__/tags-alphabetical.test.ts
+++ b/packages/core/src/rules/common/__tests__/tags-alphabetical.test.ts
@@ -19,7 +19,7 @@ describe('Oas3 tags-alphabetical', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'tags-alphabetical': 'error' }),
+      config: await makeConfig({ rules: { 'tags-alphabetical': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -56,7 +56,7 @@ describe('Oas3 tags-alphabetical', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'tags-alphabetical': 'error' }),
+      config: await makeConfig({ rules: { 'tags-alphabetical': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -77,7 +77,7 @@ describe('Oas3 tags-alphabetical', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'tags-alphabetical': 'error' }),
+      config: await makeConfig({ rules: { 'tags-alphabetical': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -114,7 +114,9 @@ describe('Oas3 tags-alphabetical', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'tags-alphabetical': { severity: 'error', ignoreCase: true } }),
+      config: await makeConfig({
+        rules: { 'tags-alphabetical': { severity: 'error', ignoreCase: true } },
+      }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/oas2/__tests__/boolean-parameter-prefixes.test.ts b/packages/core/src/rules/oas2/__tests__/boolean-parameter-prefixes.test.ts
index 32007dd3..d1a47e31 100644
--- a/packages/core/src/rules/oas2/__tests__/boolean-parameter-prefixes.test.ts
+++ b/packages/core/src/rules/oas2/__tests__/boolean-parameter-prefixes.test.ts
@@ -21,7 +21,7 @@ describe('oas2 boolean-parameter-prefixes', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'boolean-parameter-prefixes': 'error' }),
+      config: await makeConfig({ rules: { 'boolean-parameter-prefixes': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -73,7 +73,7 @@ describe('oas2 boolean-parameter-prefixes', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'boolean-parameter-prefixes': 'error' }),
+      config: await makeConfig({ rules: { 'boolean-parameter-prefixes': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -98,9 +98,11 @@ describe('oas2 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'boolean-parameter-prefixes': {
-          severity: 'error',
-          prefixes: ['should'],
+        rules: {
+          'boolean-parameter-prefixes': {
+            severity: 'error',
+            prefixes: ['should'],
+          },
         },
       }),
     });
diff --git a/packages/core/src/rules/oas2/__tests__/response-contains-header.test.ts b/packages/core/src/rules/oas2/__tests__/response-contains-header.test.ts
index bbb95089..4d63afb5 100644
--- a/packages/core/src/rules/oas2/__tests__/response-contains-header.test.ts
+++ b/packages/core/src/rules/oas2/__tests__/response-contains-header.test.ts
@@ -29,9 +29,11 @@ describe('Oas2 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: { '2xx': ['Content-Length'], '4xx': ['Content-Length'] },
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: { '2xx': ['Content-Length'], '4xx': ['Content-Length'] },
+          },
         },
       }),
     });
@@ -136,9 +138,11 @@ describe('Oas2 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: { '2xx': ['Content-Length'], '400': ['Content-Length'] },
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: { '2xx': ['Content-Length'], '400': ['Content-Length'] },
+          },
         },
       }),
     });
@@ -164,8 +168,10 @@ describe('Oas2 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+          },
         },
       }),
     });
diff --git a/packages/core/src/rules/oas2/__tests__/response-contains-property.test.ts b/packages/core/src/rules/oas2/__tests__/response-contains-property.test.ts
index 0459f181..821bd9c7 100644
--- a/packages/core/src/rules/oas2/__tests__/response-contains-property.test.ts
+++ b/packages/core/src/rules/oas2/__tests__/response-contains-property.test.ts
@@ -35,9 +35,11 @@ describe('Oas2 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { '2xx': ['id'], '4xx': ['id'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { '2xx': ['id'], '4xx': ['id'] },
+          },
         },
       }),
     });
@@ -117,9 +119,11 @@ describe('Oas2 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { '200': ['id'], '4xx': ['id'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { '200': ['id'], '4xx': ['id'] },
+          },
         },
       }),
     });
@@ -145,8 +149,10 @@ describe('Oas2 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+          },
         },
       }),
     });
diff --git a/packages/core/src/rules/oas2/__tests__/spec/referenceableScalars.test.ts b/packages/core/src/rules/oas2/__tests__/spec/referenceableScalars.test.ts
index a485cee9..84e17fe4 100644
--- a/packages/core/src/rules/oas2/__tests__/spec/referenceableScalars.test.ts
+++ b/packages/core/src/rules/oas2/__tests__/spec/referenceableScalars.test.ts
@@ -26,7 +26,9 @@ describe('Referenceable scalars', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        spec: 'error',
+        rules: {
+          spec: 'error',
+        },
       }),
     });
 
diff --git a/packages/core/src/rules/oas3/__tests__/array-parameter-serialization.test.ts b/packages/core/src/rules/oas3/__tests__/array-parameter-serialization.test.ts
index bda47b8d..cb122596 100644
--- a/packages/core/src/rules/oas3/__tests__/array-parameter-serialization.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/array-parameter-serialization.test.ts
@@ -30,7 +30,9 @@ describe('oas3 array-parameter-serialization', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        rules: {
+          'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -73,7 +75,9 @@ describe('oas3 array-parameter-serialization', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        rules: {
+          'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -126,7 +130,9 @@ describe('oas3 array-parameter-serialization', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        rules: {
+          'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -170,7 +176,9 @@ describe('oas3 array-parameter-serialization', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        rules: {
+          'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -194,7 +202,9 @@ describe('oas3 array-parameter-serialization', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        rules: {
+          'array-parameter-serialization': { severity: 'error', in: ['query'] },
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -226,7 +236,9 @@ describe('oas3 array-parameter-serialization', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'array-parameter-serialization': { severity: 'error' },
+        rules: {
+          'array-parameter-serialization': { severity: 'error' },
+        },
       }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/oas3/__tests__/boolean-parameter-prefixes.test.ts b/packages/core/src/rules/oas3/__tests__/boolean-parameter-prefixes.test.ts
index a9059146..52bd61df 100644
--- a/packages/core/src/rules/oas3/__tests__/boolean-parameter-prefixes.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/boolean-parameter-prefixes.test.ts
@@ -22,7 +22,7 @@ describe('oas3 boolean-parameter-prefixes', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'boolean-parameter-prefixes': 'error' }),
+      config: await makeConfig({ rules: { 'boolean-parameter-prefixes': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -74,7 +74,7 @@ describe('oas3 boolean-parameter-prefixes', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'boolean-parameter-prefixes': 'error' }),
+      config: await makeConfig({ rules: { 'boolean-parameter-prefixes': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -99,9 +99,11 @@ describe('oas3 boolean-parameter-prefixes', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'boolean-parameter-prefixes': {
-          severity: 'error',
-          prefixes: ['should'],
+        rules: {
+          'boolean-parameter-prefixes': {
+            severity: 'error',
+            prefixes: ['should'],
+          },
         },
       }),
     });
diff --git a/packages/core/src/rules/oas3/__tests__/no-empty-enum-servers.com.test.ts b/packages/core/src/rules/oas3/__tests__/no-empty-enum-servers.com.test.ts
index ac9c1222..d7bf7dd5 100644
--- a/packages/core/src/rules/oas3/__tests__/no-empty-enum-servers.com.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/no-empty-enum-servers.com.test.ts
@@ -24,7 +24,7 @@ describe('Oas3 as3-no-server-variables-empty-enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-variables-empty-enum': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-variables-empty-enum': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -78,7 +78,7 @@ describe('Oas3 as3-no-server-variables-empty-enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-variables-empty-enum': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-variables-empty-enum': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -117,7 +117,7 @@ describe('Oas3 as3-no-server-variables-empty-enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-variables-empty-enum': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-variables-empty-enum': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -141,7 +141,7 @@ describe('Oas3 as3-no-server-variables-empty-enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-variables-empty-enum': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-variables-empty-enum': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -168,7 +168,7 @@ describe('Oas3 as3-no-server-variables-empty-enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-variables-empty-enum': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-variables-empty-enum': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -197,7 +197,7 @@ describe('Oas3 as3-no-server-variables-empty-enum', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-variables-empty-enum': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-variables-empty-enum': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/oas3/__tests__/no-example-value-and-externalValue.test.ts b/packages/core/src/rules/oas3/__tests__/no-example-value-and-externalValue.test.ts
index 14d38501..209972ad 100644
--- a/packages/core/src/rules/oas3/__tests__/no-example-value-and-externalValue.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/no-example-value-and-externalValue.test.ts
@@ -20,7 +20,7 @@ describe('Oas3 oas3-no-example-value-and-externalValue', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-example-value-and-externalValue': 'error' }),
+      config: await makeConfig({ rules: { 'no-example-value-and-externalValue': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -57,7 +57,7 @@ describe('Oas3 oas3-no-example-value-and-externalValue', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-example-value-and-externalValue': 'error' }),
+      config: await makeConfig({ rules: { 'no-example-value-and-externalValue': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/oas3/__tests__/no-invalid-media-type-examples.test.ts b/packages/core/src/rules/oas3/__tests__/no-invalid-media-type-examples.test.ts
index 146e79a7..fd09a7fe 100644
--- a/packages/core/src/rules/oas3/__tests__/no-invalid-media-type-examples.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/no-invalid-media-type-examples.test.ts
@@ -33,7 +33,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -107,9 +107,11 @@ describe('no-invalid-media-type-examples', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-invalid-media-type-examples': {
-          severity: 'error',
-          allowAdditionalProperties: false,
+        rules: {
+          'no-invalid-media-type-examples': {
+            severity: 'error',
+            allowAdditionalProperties: false,
+          },
         },
       }),
     });
@@ -159,9 +161,11 @@ describe('no-invalid-media-type-examples', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-invalid-media-type-examples': {
-          severity: 'error',
-          allowAdditionalProperties: false,
+        rules: {
+          'no-invalid-media-type-examples': {
+            severity: 'error',
+            allowAdditionalProperties: false,
+          },
         },
       }),
     });
@@ -219,9 +223,11 @@ describe('no-invalid-media-type-examples', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-invalid-media-type-examples': {
-          severity: 'error',
-          allowAdditionalProperties: false,
+        rules: {
+          'no-invalid-media-type-examples': {
+            severity: 'error',
+            allowAdditionalProperties: false,
+          },
         },
       }),
     });
@@ -268,9 +274,11 @@ describe('no-invalid-media-type-examples', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-invalid-media-type-examples': {
-          severity: 'error',
-          allowAdditionalProperties: false,
+        rules: {
+          'no-invalid-media-type-examples': {
+            severity: 'error',
+            allowAdditionalProperties: false,
+          },
         },
       }),
     });
@@ -318,9 +326,11 @@ describe('no-invalid-media-type-examples', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'no-invalid-media-type-examples': {
-          severity: 'error',
-          allowAdditionalProperties: false,
+        rules: {
+          'no-invalid-media-type-examples': {
+            severity: 'error',
+            allowAdditionalProperties: false,
+          },
         },
       }),
     });
@@ -370,7 +380,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -402,7 +412,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -437,7 +447,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -465,7 +475,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -517,7 +527,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -551,7 +561,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -588,7 +598,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -625,7 +635,7 @@ describe('no-invalid-media-type-examples', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-invalid-media-type-examples': 'error' }),
+      config: await makeConfig({ rules: { 'no-invalid-media-type-examples': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/oas3/__tests__/no-server-example.com.test.ts b/packages/core/src/rules/oas3/__tests__/no-server-example.com.test.ts
index 7a103837..c58df4e2 100644
--- a/packages/core/src/rules/oas3/__tests__/no-server-example.com.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/no-server-example.com.test.ts
@@ -17,7 +17,7 @@ describe('Oas3 oas3-no-server-example.com', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-example.com': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-example.com': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -52,7 +52,7 @@ describe('Oas3 oas3-no-server-example.com', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-example.com': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-example.com': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -71,7 +71,7 @@ describe('Oas3 oas3-no-server-example.com', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-example.com': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-example.com': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/oas3/__tests__/no-server-trailing-slash.test.ts b/packages/core/src/rules/oas3/__tests__/no-server-trailing-slash.test.ts
index 2a2ca150..c228b5b6 100644
--- a/packages/core/src/rules/oas3/__tests__/no-server-trailing-slash.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/no-server-trailing-slash.test.ts
@@ -17,7 +17,7 @@ describe('Oas3 oas3-no-server-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
@@ -52,7 +52,7 @@ describe('Oas3 oas3-no-server-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
@@ -71,7 +71,7 @@ describe('Oas3 oas3-no-server-trailing-slash', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-server-trailing-slash': 'error' }),
+      config: await makeConfig({ rules: { 'no-server-trailing-slash': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`[]`);
diff --git a/packages/core/src/rules/oas3/__tests__/no-unused-components.test.ts b/packages/core/src/rules/oas3/__tests__/no-unused-components.test.ts
index 0d9367a3..5608717f 100644
--- a/packages/core/src/rules/oas3/__tests__/no-unused-components.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/no-unused-components.test.ts
@@ -42,7 +42,7 @@ describe('Oas3 no-unused-components', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'no-unused-components': 'error' }),
+      config: await makeConfig({ rules: { 'no-unused-components': 'error' } }),
     });
 
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
diff --git a/packages/core/src/rules/oas3/__tests__/operation-4xx-problem-details-rfc7807.test.ts b/packages/core/src/rules/oas3/__tests__/operation-4xx-problem-details-rfc7807.test.ts
index 5fa9a586..18f56436 100644
--- a/packages/core/src/rules/oas3/__tests__/operation-4xx-problem-details-rfc7807.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/operation-4xx-problem-details-rfc7807.test.ts
@@ -32,7 +32,7 @@ describe('Oas3 operation-4xx-problem-details-rfc7807', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-problem-details-rfc7807': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-problem-details-rfc7807': 'error' } }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
       [
@@ -79,7 +79,7 @@ describe('Oas3 operation-4xx-problem-details-rfc7807', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-problem-details-rfc7807': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-problem-details-rfc7807': 'error' } }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
       [
@@ -122,7 +122,7 @@ describe('Oas3 operation-4xx-problem-details-rfc7807', () => {
     const results = await lintDocument({
       externalRefResolver: new BaseResolver(),
       document,
-      config: await makeConfig({ 'operation-4xx-problem-details-rfc7807': 'error' }),
+      config: await makeConfig({ rules: { 'operation-4xx-problem-details-rfc7807': 'error' } }),
     });
     expect(replaceSourceWithRef(results)).toMatchInlineSnapshot(`
       [
diff --git a/packages/core/src/rules/oas3/__tests__/response-contains-header.test.ts b/packages/core/src/rules/oas3/__tests__/response-contains-header.test.ts
index 047c7d4b..e7eb6096 100644
--- a/packages/core/src/rules/oas3/__tests__/response-contains-header.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/response-contains-header.test.ts
@@ -27,9 +27,11 @@ describe('Oas3 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: { '200': ['Content-Length'] },
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: { '200': ['Content-Length'] },
+          },
         },
       }),
     });
@@ -107,11 +109,13 @@ describe('Oas3 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: {
-            '2XX': ['x-request-id'],
-            '400': ['Content-Length'],
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: {
+              '2XX': ['x-request-id'],
+              '400': ['Content-Length'],
+            },
           },
         },
       }),
@@ -259,11 +263,13 @@ describe('Oas3 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: {
-            '2xx': ['x-request-id'],
-            '400': ['Content-Length'],
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: {
+              '2xx': ['x-request-id'],
+              '400': ['Content-Length'],
+            },
           },
         },
       }),
@@ -294,9 +300,11 @@ describe('Oas3 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: { '2XX': ['x-test-header'] },
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: { '2XX': ['x-test-header'] },
+          },
         },
       }),
     });
@@ -326,9 +334,11 @@ describe('Oas3 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: { '2XX': ['X-Test-Header'] },
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: { '2XX': ['X-Test-Header'] },
+          },
         },
       }),
     });
@@ -352,9 +362,11 @@ describe('Oas3 response-contains-header', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-header': {
-          severity: 'error',
-          names: { '2XX': ['X-Test-Header'] },
+        rules: {
+          'response-contains-header': {
+            severity: 'error',
+            names: { '2XX': ['X-Test-Header'] },
+          },
         },
       }),
     });
diff --git a/packages/core/src/rules/oas3/__tests__/response-contains-property.test.ts b/packages/core/src/rules/oas3/__tests__/response-contains-property.test.ts
index 89cf8f95..109e5a2c 100644
--- a/packages/core/src/rules/oas3/__tests__/response-contains-property.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/response-contains-property.test.ts
@@ -27,9 +27,11 @@ describe('Oas3 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { 201: ['id'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { 201: ['id'] },
+          },
         },
       }),
     });
@@ -103,9 +105,11 @@ describe('Oas3 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { '2xx': ['id'], '400': ['error'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { '2xx': ['id'], '400': ['error'] },
+          },
         },
       }),
     });
@@ -231,9 +235,11 @@ describe('Oas3 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { '2xx': ['id'], '400': ['error'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { '2xx': ['id'], '400': ['error'] },
+          },
         },
       }),
     });
@@ -259,9 +265,11 @@ describe('Oas3 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { 201: ['id'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { 201: ['id'] },
+          },
         },
       }),
     });
@@ -300,8 +308,10 @@ describe('Oas3 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+          },
         },
       }),
     });
@@ -331,9 +341,11 @@ describe('Oas3 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { '2xx': ['id'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { '2xx': ['id'] },
+          },
         },
       }),
     });
@@ -360,9 +372,11 @@ describe('Oas3 response-contains-property', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'response-contains-property': {
-          severity: 'error',
-          names: { '2xx': ['id'] },
+        rules: {
+          'response-contains-property': {
+            severity: 'error',
+            names: { '2xx': ['id'] },
+          },
         },
       }),
     });
diff --git a/packages/core/src/rules/oas3/__tests__/spec-components-invalid-map-name.test.ts b/packages/core/src/rules/oas3/__tests__/spec-components-invalid-map-name.test.ts
index 92f9629f..cad9e2ee 100644
--- a/packages/core/src/rules/oas3/__tests__/spec-components-invalid-map-name.test.ts
+++ b/packages/core/src/rules/oas3/__tests__/spec-components-invalid-map-name.test.ts
@@ -31,7 +31,9 @@ describe('Oas3 spec-components-invalid-map-name', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'spec-components-invalid-map-name': 'error',
+        rules: {
+          'spec-components-invalid-map-name': 'error',
+        },
       }),
     });
 
@@ -208,7 +210,9 @@ describe('Oas3 spec-components-invalid-map-name', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'spec-components-invalid-map-name': 'error',
+        rules: {
+          'spec-components-invalid-map-name': 'error',
+        },
       }),
     });
 
@@ -235,7 +239,9 @@ describe('Oas3 spec-components-invalid-map-name', () => {
       externalRefResolver: new BaseResolver(),
       document,
       config: await makeConfig({
-        'spec-components-invalid-map-name': 'error',
+        rules: {
+          'spec-components-invalid-map-name': 'error',
+        },
       }),
     });
 
diff --git a/packages/core/src/rules/oas3/__tests__/utils/lint-document-for-test.ts b/packages/core/src/rules/oas3/__tests__/utils/lint-document-for-test.ts
index b13266be..f424d85a 100644
--- a/packages/core/src/rules/oas3/__tests__/utils/lint-document-for-test.ts
+++ b/packages/core/src/rules/oas3/__tests__/utils/lint-document-for-test.ts
@@ -18,6 +18,6 @@ export async function lintDocumentForTest(
   return await lintDocument({
     externalRefResolver: baseResolver,
     document,
-    config: await makeConfig(rules),
+    config: await makeConfig({ rules }),
   });
 }