Skip to content

Commit 7ecba14

Browse files
authored
Merge pull request #51 from advanced-rest-client/fix/W-11843862/enum-example
[W-11843862] Enum example
2 parents c23c10a + c653c12 commit 7ecba14

File tree

10 files changed

+167
-3
lines changed

10 files changed

+167
-3
lines changed

demo/W-11843862/W-11843862.yaml

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
openapi: 3.0.0
2+
info:
3+
title: eMPF API Specification - Contribution Module
4+
description: eMPF API Specification - Contribution Module
5+
version: 0.1.0
6+
paths:
7+
/cas/ad/contribution/external/v1/bill/list:
8+
get:
9+
tags:
10+
- ER-Portal-API
11+
summary: CON-PERIOD-BILLABLE CON - Retrieve period bill
12+
description: |
13+
**API ID:** CON-PERIOD-BILLABLE \
14+
**CM:** CM-Web-Employer-Contribution A1, A2, A3, A4, B1, B2, B3, B4 \
15+
**FS:** FS-UF-CON-REE-009,FS-UF-CON-CEE-001 \
16+
CON - Retrieve period bill
17+
parameters:
18+
- $ref: '#/components/parameters/x-empf-apiclient-id'
19+
responses:
20+
'200':
21+
description: successfully
22+
content:
23+
application/json:
24+
schema:
25+
$ref: '#/components/schemas/periodBillableResponse'
26+
security:
27+
- bearerAuth: []
28+
29+
components:
30+
parameters:
31+
x-empf-apiclient-id:
32+
in: header
33+
name: x-empf-apiclient-id
34+
description: value should be an integer starting from 1 representing the identity of the API client, 1 for ER Portal, 2 for ER Mobile App, 3 for EE Portal, 4 for EE Mobile App, 5 for admin, 6 for trustee, 7 for mpfa, 8 for kiosk
35+
schema:
36+
type: integer
37+
enum:
38+
- 1
39+
- 2
40+
- 3
41+
- 4
42+
- 5
43+
- 6
44+
- 7
45+
required: true
46+
47+
schemas:
48+
GlobalSuccessResponse:
49+
type: object
50+
properties:
51+
success:
52+
type: boolean
53+
description: The flag indicates there is no bussiness error occurred in the request
54+
code:
55+
type: integer
56+
example: '200'
57+
periodBillableResponse:
58+
allOf:
59+
- $ref: '#/components/schemas/GlobalSuccessResponse'
60+
securitySchemes:
61+
bearerAuth:
62+
type: http
63+
scheme: bearer
64+
bearerFormat: JWT

demo/index.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,8 @@ class ComponentDemo extends ApiDemoPage {
123123
['APIC-391', 'APIC-391'],
124124
['APIC-655', 'APIC-655'],
125125
['xml-api', 'xml-api'],
126+
['W-11843862', 'W-11843862'],
127+
['v4_0_0_api_specs', 'v4_0_0_api_specs']
126128
].map(
127129
([file, label]) => html`
128130
<anypoint-item data-src="${file}-compact.json"

demo/model.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,5 +27,6 @@ files.set('allof-types/allof-types.yaml', { type: 'OAS 3.0', mime: 'application/
2727
files.set('APIC-679/APIC-679.yaml', { type: 'OAS 3.0', mime: 'application/yaml' });
2828
files.set('xml-api/xml-api.yaml', { type: 'OAS 3.0', mime: 'application/yaml' });
2929
files.set('v4_0_0_api_spec/v4_0_0_api_specs.yaml', { type: 'OAS 3.0', mime: 'application/yaml' });
30+
files.set('W-11843862/W-11843862.yaml', { type: 'OAS 3.0', mime: 'application/yaml' });
3031

3132
generator.generate(files);

package-lock.json

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
{
22
"name": "@api-components/api-example-generator",
33
"description": "Examples generator from AMF model",
4-
"version": "4.4.19",
4+
"version": "4.4.20",
55
"license": "Apache-2.0",
66
"main": "index.js",
77
"module": "index.js",

src/ExampleGenerator.d.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -333,6 +333,14 @@ declare class ExampleGenerator extends AmfHelperMixin(Object) {
333333
*/
334334
_computeDefaultRangeValue(range: object): string | number | boolean | null;
335335

336+
/**
337+
* Computes default enum value for given range.
338+
*
339+
* @param {Object} range AMF's range definition for a shape.
340+
* @return {string|number|boolean|null} Value cast to the corresponding type
341+
*/
342+
_computeDefaultEnumRangeValue(range: object): string | number | boolean | null;
343+
336344
/**
337345
* Casts the value to given data type represented in AMF notation.
338346
*

src/ExampleGenerator.js

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1326,6 +1326,31 @@ export class ExampleGenerator extends AmfHelperMixin(Object) {
13261326
return this._typeToValue(value, dt['@id']);
13271327
}
13281328

1329+
/**
1330+
* Computes default enum value for given range.
1331+
*
1332+
* @param {Object} range AMF's range definition for a shape.
1333+
* @return {string|number|boolean|null} Value cast to the corresponding type
1334+
*/
1335+
_computeDefaultEnumRangeValue(range) {
1336+
let enumOptions = range[this._getAmfKey(this.ns.w3.shacl.in)]
1337+
if (Array.isArray(enumOptions)) {
1338+
[enumOptions] = enumOptions;
1339+
}
1340+
const rdfKey = this._getAmfKey(this.ns.w3.rdfSchema.key);
1341+
const firstOptionKey = Object.keys(enumOptions).find((key) => key.indexOf(rdfKey) !== -1);
1342+
let firstOption = enumOptions[firstOptionKey];
1343+
if (Array.isArray(firstOption)) {
1344+
[firstOption] = firstOption;
1345+
}
1346+
const vKey = this._getAmfKey(this.ns.raml.vocabularies.data.value);
1347+
const value = this._getValue(firstOption, vKey);
1348+
if (value) {
1349+
return value;
1350+
}
1351+
return null;
1352+
}
1353+
13291354
/**
13301355
* Computes default value for given range.
13311356
*
@@ -1338,6 +1363,14 @@ export class ExampleGenerator extends AmfHelperMixin(Object) {
13381363
* @return {string|number|boolean|null} Value casted to the corresponding type
13391364
*/
13401365
_computeDefaultRangeValue(range) {
1366+
const isEnum = this._hasProperty(range, this.ns.w3.shacl.in)
1367+
if (isEnum) {
1368+
const value = this._computeDefaultEnumRangeValue(range);
1369+
if (value) {
1370+
return value;
1371+
}
1372+
}
1373+
13411374
const type = this._computeScalarType(range);
13421375
switch (type) {
13431376
case 'Number':

test/ExampleGenerator.test.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2321,7 +2321,7 @@ describe('ExampleGenerator', () => {
23212321
schema = element._resolve(schema);
23222322
const result = element._computeJsonPropertyValue(schema);
23232323
assert.typeOf(result, 'object');
2324-
assert.deepEqual(result, { messages: [{ "referrers": "", "sequenceId": 1, "text": "", "type": "", "tz": "", "variables": "" }]})
2324+
assert.deepEqual(result, { messages: [{ "referrers": "", "sequenceId": 1, "text": "", "type": "init", "tz": "", "variables": "" }]})
23252325
});
23262326
});
23272327
});

test/W-11843862.test.js

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
import { fixture, assert, html } from '@open-wc/testing';
2+
import { AmfLoader } from './amf-loader.js';
3+
import '../api-example-generator.js';
4+
5+
describe('W-11843862', () => {
6+
async function basicFixture(amf) {
7+
return fixture(html`<api-example-generator
8+
.amf="${amf}"
9+
></api-example-generator>`);
10+
}
11+
12+
const apiFile = 'W-11843862';
13+
14+
[
15+
['json+ld data model', false],
16+
['Compact data model', true],
17+
].forEach(([label, compact]) => {
18+
describe(/** @type {string} */ (label), () => {
19+
let element;
20+
let amf;
21+
22+
before(async () => {
23+
amf = await AmfLoader.load(/** @type {boolean} */ (compact), apiFile);
24+
});
25+
26+
beforeEach(async () => {
27+
element = await basicFixture(amf);
28+
});
29+
30+
it('Returns first enum option as example', () => {
31+
const headers = AmfLoader.lookupExpectsHeaderSchema(amf, '/cas/ad/contribution/external/v1/bill/list', 'get');
32+
const examples = element.computeExamples(headers[0], 'application/json', {});
33+
assert.lengthOf(examples, 1);
34+
assert.equal(examples[0].value, '1')
35+
});
36+
});
37+
});
38+
});

test/amf-loader.js

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,24 @@ AmfLoader.lookupPayload = function(model, endpoint, operation) {
6666
return helper._ensureArray(helper._computePayload(expects));
6767
};
6868

69+
/**
70+
* Looks for headers in an operation
71+
* @param {any} model
72+
* @param {string} endpoint Endpoint's path
73+
* @param {string} operation Operation name (lowercase)
74+
* @return {Array<Object>}
75+
*/
76+
AmfLoader.lookupExpectsHeaderSchema = function(model, endpoint, operation) {
77+
const op = AmfLoader.lookupOperation(model, endpoint, operation);
78+
const expects = helper._computeExpects(op);
79+
if (!expects) {
80+
throw new Error(`The ${operation.toUpperCase()} ${endpoint} operation has no request definition.`);
81+
}
82+
const headers = helper._computeHeaders(expects);
83+
const sKey = helper._getAmfKey(helper.ns.aml.vocabularies.shapes.schema);
84+
return headers[0][sKey];
85+
};
86+
6987
/**
7088
* Looks for a payload in the responses list of an operation
7189
* @param {any} model

0 commit comments

Comments
 (0)