Skip to content

Commit 3b6b3fb

Browse files
authored
CLOUDP-271997: IPA 108 - delete method schema (#483)
1 parent 054e36c commit 3b6b3fb

File tree

7 files changed

+193
-0
lines changed

7 files changed

+193
-0
lines changed

tools/spectral/CONTRIBUTING.md

Whitespace-only changes.
Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
import testRule from './__helpers__/testRule';
2+
import { DiagnosticSeverity } from '@stoplight/types';
3+
4+
testRule('xgen-IPA-108-delete-response-should-be-empty', [
5+
{
6+
name: 'valid DELETE with void 204',
7+
document: {
8+
paths: {
9+
'/resource/{id}': {
10+
delete: {
11+
responses: {
12+
204: {},
13+
},
14+
},
15+
},
16+
},
17+
},
18+
errors: [],
19+
},
20+
{
21+
name: 'valid DELETE with void 204 versioned',
22+
document: {
23+
paths: {
24+
'/resource/{id}': {
25+
delete: {
26+
responses: {
27+
204: {
28+
description: 'No Content',
29+
content: {
30+
'application/vnd.atlas.2023-01-01+json': {
31+
'x-xgen-version': '2023-01-01',
32+
},
33+
'application/vnd.atlas.2023-03-01+json': {
34+
'x-xgen-version': '2023-01-01',
35+
},
36+
},
37+
},
38+
},
39+
},
40+
},
41+
},
42+
},
43+
errors: [],
44+
},
45+
{
46+
name: 'invalid DELETE with non-void 204',
47+
document: {
48+
paths: {
49+
'/resource/{id}': {
50+
delete: {
51+
responses: {
52+
204: {
53+
content: {
54+
'application/vnd.atlas.2023-01-01+json': {
55+
schema: { type: 'object' },
56+
},
57+
},
58+
},
59+
},
60+
},
61+
},
62+
},
63+
},
64+
errors: [
65+
{
66+
code: 'xgen-IPA-108-delete-response-should-be-empty',
67+
message:
68+
'Error found for application/vnd.atlas.2023-01-01+json: DELETE method should return an empty response. The response should not have a schema property. http://go/ipa/108',
69+
path: ['paths', '/resource/{id}', 'delete', 'responses', '204'],
70+
severity: DiagnosticSeverity.Warning,
71+
},
72+
],
73+
},
74+
{
75+
name: 'valid with exception',
76+
document: {
77+
paths: {
78+
'/resource/{id}': {
79+
delete: {
80+
responses: {
81+
204: {
82+
'application/vnd.atlas.2023-01-01+json': {
83+
'x-xgen-IPA-exception': {
84+
'xgen-IPA-108-delete-response-should-be-empty': 'Legacy API',
85+
},
86+
content: {
87+
schema: { type: 'object' },
88+
},
89+
},
90+
},
91+
},
92+
},
93+
},
94+
},
95+
},
96+
errors: [],
97+
},
98+
]);

tools/spectral/ipa/ipa-spectral.yaml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ extends:
66
- ./rulesets/IPA-113.yaml
77
- ./rulesets/IPA-123.yaml
88
- ./rulesets/IPA-106.yaml
9+
- ./rulesets/IPA-108.yaml
910

1011
overrides:
1112
- files:
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
# IPA-108: Delete
2+
# http://go/ipa/108
3+
4+
rules:
5+
xgen-IPA-108-delete-response-should-be-empty:
6+
description: Delete method response should not have schema reference to object. http://go/ipa/108
7+
message: '{{error}} http://go/ipa/108'
8+
severity: warn
9+
given: $.paths[*].delete.responses[204]
10+
then:
11+
function: deleteMethodResponseShouldNotHaveSchema
12+
13+
functions:
14+
- deleteMethodResponseShouldNotHaveSchema

tools/spectral/ipa/rulesets/README.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,14 @@ For rule definitions, see [IPA-106.yaml](https://github.com/mongodb/openapi/blob
4646
| xgen-IPA-106-create-method-request-body-is-request-suffixed-object | The Create method request should be a Request suffixed object. http://go/ipa/106 | warn |
4747
| xgen-IPA-106-create-method-should-not-have-query-parameters | Create operations should not use query parameters. http://go/ipa/xxx | warn |
4848

49+
### IPA-108
50+
51+
For rule definitions, see [IPA-108.yaml](https://github.com/mongodb/openapi/blob/main/tools/spectral/ipa/rulesets/IPA-108.yaml).
52+
53+
| Rule Name | Description | Severity |
54+
| -------------------------------------------- | ------------------------------------------------------------------------------------ | -------- |
55+
| xgen-IPA-108-delete-response-should-be-empty | Delete method response should not have schema reference to object. http://go/ipa/108 | warn |
56+
4957
### IPA-109
5058

5159
For rule definitions, see [IPA-109.yaml](https://github.com/mongodb/openapi/blob/main/tools/spectral/ipa/rulesets/IPA-109.yaml).
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
import { hasException } from './utils/exceptions.js';
2+
import {
3+
collectAdoption,
4+
collectAndReturnViolation,
5+
collectException,
6+
handleInternalError,
7+
} from './utils/collectionUtils.js';
8+
9+
const RULE_NAME = 'xgen-IPA-108-delete-response-should-be-empty';
10+
const ERROR_MESSAGE = 'DELETE method should return an empty response. The response should not have a schema property.';
11+
12+
/**
13+
* Delete method should return an empty response
14+
* @param {object} input - The delete operation object
15+
* @param {object} _ - Unused
16+
* @param {object} context - The context object containing the path
17+
*/
18+
export default (input, _, { path }) => {
19+
// 1. Handle exception on OpenAPI schema
20+
if (hasException(input, RULE_NAME)) {
21+
collectException(input, RULE_NAME, path);
22+
return;
23+
}
24+
25+
// 2. Validation
26+
const errors = checkViolations(input, path);
27+
if (errors.length > 0) {
28+
return collectAndReturnViolation(path, RULE_NAME, errors);
29+
}
30+
31+
collectAdoption(path, RULE_NAME);
32+
};
33+
34+
/**
35+
* Check if the operation has validation issues
36+
* @param {object} input - The object to vefify
37+
* @param {object} jsonPathArray - The jsonPathArray covering location in the OpenAPI schema
38+
* @return {Array<string>} - errors array ()
39+
*/
40+
function checkViolations(input, jsonPathArray) {
41+
const errors = [];
42+
try {
43+
const successResponse = input;
44+
if (successResponse.content) {
45+
for (const contentType of Object.keys(successResponse.content)) {
46+
if (successResponse.content[contentType] && successResponse.content[contentType].schema) {
47+
errors.push({
48+
path: jsonPathArray,
49+
message: `Error found for ${contentType}: ${ERROR_MESSAGE}`,
50+
});
51+
}
52+
}
53+
}
54+
} catch (e) {
55+
handleInternalError(RULE_NAME, jsonPathArray, e);
56+
}
57+
return errors;
58+
}

tools/spectral/ipa/rulesets/functions/utils/collectionUtils.js

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,3 +46,17 @@ export function collectException(object, ruleName, jsonPath) {
4646
collector.add(EntryType.EXCEPTION, jsonPath, ruleName, exceptionReason);
4747
}
4848
}
49+
50+
/**
51+
* Creates internal rule error entry for the collector in order to not fail validation process.
52+
* @param {Array<string>} jsonPathArray - The JSON path for the object where the rule exception occurred.
53+
* @param {string} ruleName - The name of the rule that was adopted.
54+
*/
55+
export function handleInternalError(ruleName, jsonPathArray, error) {
56+
return [
57+
{
58+
path: jsonPathArray,
59+
message: `${ruleName} Internal Rule Error: ${error} Please report issue in https://github.com/mongodb/openapi/issues`,
60+
},
61+
];
62+
}

0 commit comments

Comments
 (0)