@lcap/asl
Version:
NetEase Application Specific Language
164 lines • 7.11 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.getSchemaOfExpressionNode = exports.getQuerySchemaMap = exports.composeDefinition = exports.getFullSchema = exports.getChildSchema = exports.getSchemaFromInterface = void 0;
// Node.js 需要使用,临时拷一下
const __1 = require("..");
const dataTypeUtils_1 = require("../data/dataTypeUtils");
function getSchemaFromInterface(inter) {
if (!inter)
return;
function getNormalResponse(responses) {
return Object.entries(responses).sort((a, b) => a[0] - b[0])[0][1];
}
const response = getNormalResponse(JSON.parse(inter.responses));
// numims 服务: {"description":"响应类型200,新建200响应状态码会覆盖响应信息\n","headers":{},"schema":{"$ref":"#/flowfront0928/structures/ApiReturnOfGetUserList1"}}
const schema = response.content['application/json'].schema || response.schema;
return schema;
}
exports.getSchemaFromInterface = getSchemaFromInterface;
/**
* schema { $ref: "#/zxrbk/structures/ApiReturnOfPageOfEmployee" }
* code data.Data.content
*/
function getChildSchema(schema, code, dataTypesMap) {
if (!schema || !code)
return schema;
const arr = code.split('.');
arr.shift();
if (arr.length === 0)
return schema;
const key = arr[0];
if (schema.isArray && key === 'length')
return { $ref: '#/basicTypes/Integer' };
schema = dataTypesMap[schema.$ref];
const propertyList = schema.propertyList;
const item = propertyList.find((item) => item.name === key);
return getChildSchema(item, arr.join('.'), dataTypesMap);
}
exports.getChildSchema = getChildSchema;
function getFullSchema(schema, entities = [], dataTypesMap, usedSchemaRefs = {}) {
if (!schema)
return schema;
const ref = schema.$ref;
if (ref && usedSchemaRefs[ref])
return;
// 理论上可以继续往下选,但这里先断掉!
const nextUsedSchemaRefs = Object.assign({}, usedSchemaRefs);
if (ref && !ref.startsWith('#/basicTypes/'))
nextUsedSchemaRefs[ref] = true;
schema = cloneDeep(schema);
delete schema.root;
schema.level = getLevelFromRef(schema.$ref);
if (schema.isArray) {
schema.type = 'array';
schema.items = schema.items || {};
schema.items.$ref = schema.$ref;
schema.items = getFullSchema(schema.items, entities, dataTypesMap, usedSchemaRefs);
}
else {
if (schema.level === 'entity')
entities.push(dataTypesMap[schema.$ref]);
const definition = cloneDeep(dataTypesMap[schema.$ref]);
if (definition) {
const { name } = schema;
Object.assign(schema, definition, { name });
const { propertyList } = definition;
if (propertyList) {
for (let i = 0; i < propertyList.length; i++) {
propertyList[i] = getFullSchema(propertyList[i], entities, dataTypesMap, nextUsedSchemaRefs);
if (!propertyList[i])
propertyList.splice(i--, 1);
}
}
}
}
return schema;
}
exports.getFullSchema = getFullSchema;
function getLevelFromRef(ref) {
const arr = ref.split('/');
const map = {
structures: 'structure',
entities: 'entity',
_default: 'property',
};
return map[arr[2]] || map._default;
}
function composeDefinition(definition) {
const removeReplacer = (key, value) => {
if (['root'].includes(key))
return undefined;
else
return value;
};
// 兼容报错
definition = JSON.parse(JSON.stringify(definition, removeReplacer) || '{}');
return convert2SchemaType(definition);
}
exports.composeDefinition = composeDefinition;
function getQuerySchemaMap(resolver, dataTypesMap) {
let schema = getSchemaFromInterface(resolver.interface);
schema = getChildSchema(schema, 'data.Data', dataTypesMap);
const fullSchema = getFullSchema(schema, [], dataTypesMap);
return composeDefinition(fullSchema);
}
exports.getQuerySchemaMap = getQuerySchemaMap;
/**
* 不完整。当前,只考虑 s-member-identifier-select
* @param {*} node
* 用于forEach中的each的schema
*/
function getSchemaOfExpressionNode(node) {
if (!node)
return;
if (node.type === 'Identifier') { //变量,直接返回schemaRef
const vertex = __1.vertexsMap.get(node.schemaRef);
return vertex && vertex.schema;
}
if (node.type === 'MemberExpression') { // a.b.c的情况较复杂
if (node.property.schemaRef) { //a.b,b是实体属性或者结构属性,有schemaRef,直接返回
const property = __1.vertexsMap.get(node.property.schemaRef);
// const { $ref, isArray } = property;
return property;
}
else { // property 无引用,可能是泛型
let object = node.object;
let code = node.property.name;
// 比如变量类型是ApiReturnOf<PageOf<Entity1>>
// 先计算出code "ID_91373b15c33d4b3a9337677b5fb42346.Data.content"
while (object.type === 'MemberExpression' && !object.schemaRef) {
code = (object.property.code || object.property.name) + '.' + code;
object = object.object;
}
code = (object.code || object.name) + '.' + code;
const vertex = __1.vertexsMap.get(object.schemaRef);
const schema = vertex && vertex.schema; // 获取object的schema
if (schema) {
// 获取object的schemaChildren,每个schemaChild里都有code和schema
let schemaChild = dataTypeUtils_1.genRefSchemaChildren(schema, object.code || object.name);
while (schemaChild) {
const codeNode = schemaChild.find((child) => code.startsWith(child.code));
if (codeNode) {
// 如果code相等,向前的schema就是property的schema
// content的schema就是{"name":"content","type":"genericType","typeInstantiation":{"typeName":"List","typeParams":[{"typeParamName":"T","typeParamValue":{"$ref":"#/39c303fd-c0b2-46e6-85a0-1fe9bafd2f5f/b92b294d7e804155b30309910953247f","typeKey":"#/39c303fd-c0b2-46e6-85a0-1fe9bafd2f5f/b92b294d7e804155b30309910953247f"},"type":"typeParam"}]},"typeKey":"#/genericTypes/List"}
if (codeNode.code === code) {
return codeNode.schema;
}
else {
schemaChild = codeNode.children;
}
}
else { // 找不到需要退出,避免死循环
break;
}
}
}
}
}
if (node.type === 'BooleanLiteral')
return {
typeKey: '#/basicTypes/Boolean',
};
}
exports.getSchemaOfExpressionNode = getSchemaOfExpressionNode;
//# sourceMappingURL=tools.js.map