Fixed method sortByRequired

This commit is contained in:
yan.nan 2019-11-15 08:55:11 +08:00
parent dc5430e53d
commit db96ed0f71
4 changed files with 397 additions and 23 deletions

View File

@ -154,12 +154,11 @@ export class OperationModel implements IMenuItem {
).map(paramOrRef => new FieldModel(this.parser, paramOrRef, this.pointer, this.options)); ).map(paramOrRef => new FieldModel(this.parser, paramOrRef, this.pointer, this.options));
if (this.options.sortPropsAlphabetically) { if (this.options.sortPropsAlphabetically) {
sortByField(_parameters, 'name'); return sortByField(_parameters, 'name');
} }
if (this.options.requiredPropsFirst) { if (this.options.requiredPropsFirst) {
sortByRequired(_parameters); return sortByRequired(_parameters);
} }
return _parameters;
} }
@memoize @memoize

View File

@ -251,7 +251,7 @@ function buildFields(
const props = schema.properties || {}; const props = schema.properties || {};
const additionalProps = schema.additionalProperties; const additionalProps = schema.additionalProperties;
const defaults = schema.default || {}; const defaults = schema.default || {};
const fields = Object.keys(props || []).map(fieldName => { let fields = Object.keys(props || []).map(fieldName => {
let field = props[fieldName]; let field = props[fieldName];
if (!field) { if (!field) {
@ -280,11 +280,11 @@ function buildFields(
}); });
if (options.sortPropsAlphabetically) { if (options.sortPropsAlphabetically) {
sortByField(fields, 'name'); fields = sortByField(fields, 'name');
} }
if (options.requiredPropsFirst) { if (options.requiredPropsFirst) {
// if not sort alphabetically sort in the order from required keyword // if not sort alphabetically sort in the order from required keyword
sortByRequired(fields, !options.sortPropsAlphabetically ? schema.required : undefined); fields = sortByRequired(fields, !options.sortPropsAlphabetically ? schema.required : undefined);
} }
if (typeof additionalProps === 'object' || additionalProps === true) { if (typeof additionalProps === 'object' || additionalProps === true) {

View File

@ -9,6 +9,7 @@ import {
normalizeServers, normalizeServers,
pluralizeType, pluralizeType,
serializeParameterValue, serializeParameterValue,
sortByRequired,
} from '../'; } from '../';
import { FieldModel, OpenAPIParser, RedocNormalizedOptions } from '../../services'; import { FieldModel, OpenAPIParser, RedocNormalizedOptions } from '../../services';
@ -387,7 +388,9 @@ describe('Utils', () => {
expect(pluralizeType('objects (Pet)')).toEqual('objects (Pet)'); expect(pluralizeType('objects (Pet)')).toEqual('objects (Pet)');
expect(pluralizeType('strings <email>')).toEqual('strings <email>'); expect(pluralizeType('strings <email>')).toEqual('strings <email>');
expect(pluralizeType('objects or strings')).toEqual('objects or strings'); expect(pluralizeType('objects or strings')).toEqual('objects or strings');
expect(pluralizeType('objects (Pet) or numbers <int64>')).toEqual('objects (Pet) or numbers <int64>'); expect(pluralizeType('objects (Pet) or numbers <int64>')).toEqual(
'objects (Pet) or numbers <int64>',
);
}); });
}); });
@ -621,4 +624,370 @@ describe('Utils', () => {
}); });
}); });
}); });
describe('OpenAPI sortByRequired', () => {
it('should equal to the old data when all items have no required props', () => {
let fields = [
{
name: 'loginName',
required: false,
},
{
name: 'displayName',
required: false,
},
{
name: 'email',
required: false,
},
{
name: 'space',
required: false,
},
{
name: 'type',
required: false,
},
{
name: 'depIds',
required: false,
},
{
name: 'depNames',
required: false,
},
{
name: 'password',
required: false,
},
{
name: 'pwdControl',
required: false,
},
{
name: 'csfLevel',
required: false,
},
{
name: 'priority',
required: false,
},
{
name: 'siteId',
required: false,
},
];
expect(sortByRequired(fields as FieldModel[])).toEqual(fields);
});
it('other item should be the same order when some of items are required', () => {
let fields = [
{
name: 'loginName',
required: true,
},
{
name: 'displayName',
required: false,
},
{
name: 'email',
required: true,
},
{
name: 'space',
required: false,
},
{
name: 'type',
required: false,
},
{
name: 'depIds',
required: false,
},
{
name: 'depNames',
required: false,
},
{
name: 'password',
required: false,
},
{
name: 'pwdControl',
required: false,
},
{
name: 'csfLevel',
required: false,
},
{
name: 'priority',
required: false,
},
{
name: 'siteId',
required: false,
},
];
let sortedFields = [
{
name: 'loginName',
required: true,
},
{
name: 'email',
required: true,
},
{
name: 'displayName',
required: false,
},
{
name: 'space',
required: false,
},
{
name: 'type',
required: false,
},
{
name: 'depIds',
required: false,
},
{
name: 'depNames',
required: false,
},
{
name: 'password',
required: false,
},
{
name: 'pwdControl',
required: false,
},
{
name: 'csfLevel',
required: false,
},
{
name: 'priority',
required: false,
},
{
name: 'siteId',
required: false,
},
];
expect(sortByRequired(fields as FieldModel[])).toEqual(sortedFields);
});
it('should the order of required items is as same as the order parameter ', () => {
let fields = [
{
name: 'loginName',
required: true,
},
{
name: 'displayName',
required: true,
},
{
name: 'email',
required: true,
},
{
name: 'space',
required: false,
},
{
name: 'type',
required: false,
},
{
name: 'depIds',
required: false,
},
{
name: 'depNames',
required: false,
},
{
name: 'password',
required: false,
},
{
name: 'pwdControl',
required: false,
},
{
name: 'csfLevel',
required: false,
},
{
name: 'priority',
required: false,
},
{
name: 'siteId',
required: false,
},
];
expect(
sortByRequired(fields as FieldModel[], ['siteId', 'displayName', 'loginName', 'email']),
).toEqual([
{
name: 'displayName',
required: true,
},
{
name: 'loginName',
required: true,
},
{
name: 'email',
required: true,
},
{
name: 'space',
required: false,
},
{
name: 'type',
required: false,
},
{
name: 'depIds',
required: false,
},
{
name: 'depNames',
required: false,
},
{
name: 'password',
required: false,
},
{
name: 'pwdControl',
required: false,
},
{
name: 'csfLevel',
required: false,
},
{
name: 'priority',
required: false,
},
{
name: 'siteId',
required: false,
},
]);
expect(sortByRequired(fields as FieldModel[], ['email', 'displayName'])).toEqual([
{
name: 'email',
required: true,
},
{
name: 'displayName',
required: true,
},
{
name: 'loginName',
required: true,
},
{
name: 'space',
required: false,
},
{
name: 'type',
required: false,
},
{
name: 'depIds',
required: false,
},
{
name: 'depNames',
required: false,
},
{
name: 'password',
required: false,
},
{
name: 'pwdControl',
required: false,
},
{
name: 'csfLevel',
required: false,
},
{
name: 'priority',
required: false,
},
{
name: 'siteId',
required: false,
},
]);
expect(sortByRequired(fields as FieldModel[], ['displayName'])).toEqual([
{
name: 'displayName',
required: true,
},
{
name: 'loginName',
required: true,
},
{
name: 'email',
required: true,
},
{
name: 'space',
required: false,
},
{
name: 'type',
required: false,
},
{
name: 'depIds',
required: false,
},
{
name: 'depNames',
required: false,
},
{
name: 'password',
required: false,
},
{
name: 'pwdControl',
required: false,
},
{
name: 'csfLevel',
required: false,
},
{
name: 'priority',
required: false,
},
{
name: 'siteId',
required: false,
},
]);
});
});
}); });

View File

@ -1,6 +1,7 @@
import { dirname } from 'path'; import { dirname } from 'path';
const URLtemplate = require('url-template'); const URLtemplate = require('url-template');
import { FieldModel } from '../services/models';
import { OpenAPIParser } from '../services/OpenAPIParser'; import { OpenAPIParser } from '../services/OpenAPIParser';
import { import {
OpenAPIEncoding, OpenAPIEncoding,
@ -428,25 +429,30 @@ export function humanizeConstraints(schema: OpenAPISchema): string[] {
return res; return res;
} }
export function sortByRequired( export function sortByRequired(fields: FieldModel[], order: string[] = []) {
fields: Array<{ required: boolean; name: string }>, const mapped = fields.map((field, index) => {
order: string[] = [], return {
) { index,
fields.sort((a, b) => { weights: field.required
if (!a.required && b.required) { ? order.indexOf(field.name) === -1
return 1; ? order.length - fields.length
} else if (a.required && !b.required) { : order.indexOf(field.name) - fields.length
return -1; : index,
} else if (a.required && b.required) { };
return order.indexOf(a.name) - order.indexOf(b.name);
} else {
return 0;
}
}); });
mapped.sort((a, b) => {
return a.weights - b.weights || a.index - b.index;
});
return mapped.map(el => fields[el.index]);
} }
export function sortByField<T extends string>(fields: Array<{ [P in T]: string }>, param: T) { export function sortByField(
fields.sort((a, b) => { fields: FieldModel[],
param: keyof Pick<FieldModel, 'name' | 'description' | 'kind'>,
) {
return [...fields].sort((a, b) => {
return a[param].localeCompare(b[param]); return a[param].localeCompare(b[param]);
}); });
} }