nope/modules/mod-GRPC-Interface/helpers/schema-functions.ts
2020-09-10 18:21:19 +02:00

129 lines
3.2 KiB
TypeScript

/**
* @author Martin Karkowski
* @email m.karkowski@zema.de
* @create date 2019-01-10 10:19:24
* @modify date 2020-09-09 15:55:27
* @desc [description]
*/
import { listFiles } from "../../../lib/helpers/fileMethods";
import { rgetattr, rsetattr } from "../../../lib/helpers/objectMethods";
import { replaceAll } from "../../../lib/helpers/stringMethods";
import { IJsonSchema } from "../../../types/IJSONSchema";
const compile = require('protobuf-jsonschema');
function _recursive(segment, source, searchparam = '$ref') {
for (const key in segment) {
if (key == searchparam) {
segment[key] = replaceAll(segment[key], '.', '/');
/** USAGE IN HERE USEFULL ??!? */
const data = rgetattr(source, segment[key], null, '/');
/** Prevent addin Additional Properties */
data.additionalProperties = false;
/** Delete the Key */
delete segment[key];
/** Store the Data */
Object.assign(segment, data);
} else if (typeof segment[key] !== 'string') {
segment[key] = _recursive(segment[key], source, searchparam);
}
}
return segment;
}
/**
* Generate Schemas for a Folder containing Proto-Repositories.
*
* @export
* @param {string} [dir='./proto-repository/protos'] The Path in which files should be found.
* @return {*}
*/
export async function genSchemaForFolder(dir: string = './proto-repository/protos') {
/** Find the Files */
const files = await listFiles(dir, 'proto');
/** Element containing the JSON - Schema */
let result: {
definitions: {
/** Package */
[index: string]: {
/** Type */
[index: string]: IJsonSchema
}
}
} = {
definitions: {}
}
/** Merge all Resources of the different Files */
for (const file of files) {
result = genSchema(file, result)
}
return result;
}
export function genSchema(pathToFile: string, result: {
definitions: {
/** Package */
[index: string]: {
/** Type */
[index: string]: IJsonSchema
}
}
} = { definitions: {} }) {
/** Try to Compile the Proto-File */
try {
const defs = compile(pathToFile);
for (const def in defs.definitions) {
/** Make Fields Required */
defs.definitions[def].required = Object.getOwnPropertyNames(defs.definitions[def].properties);
/** Add it to the Definition-File */
rsetattr(result, 'definitions.' + def, defs.definitions[def], '.');
}
} catch (e) {
console.log(pathToFile, '-> circular');
}
return result;
}
export function flattenSchema(data: {
definitions: {
/** Package */
[index: string]: {
/** Type */
[index: string]: IJsonSchema
}
}
}) {
const _ret = {};
/** Sets the Value */
rsetattr(_ret, '#', data);
const res = _recursive(data, _ret);
for (const def in res.definitions) {
/** Get the Current Definition */
const obj = res.definitions[def];
obj.additionalProperties = false;
}
return res;
}