Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions reverse_engineering/helpers/getDefinitionReferencePath.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
/**
* @import {DefinitionTypeName} from "../../shared/types/types"
*/

/**
* Returns the path to the definition reference
*
* @param {object} params
* @param {DefinitionTypeName} params.definitionCategoryName - The definition category name
* @param {string} params.definitionName - The definition name
* @returns {string} The path to the definition reference
*/
function getDefinitionReferencePath({ definitionCategoryName, definitionName }) {
return `#model/definitions/${definitionCategoryName}/${definitionName}`;
}

module.exports = {
getDefinitionReferencePath,
};
7 changes: 4 additions & 3 deletions reverse_engineering/mappers/field.js
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
/**
* @import {FieldDefinitionNode, TypeNode, InputValueDefinitionNode, ValueNode} from "graphql"
* @import {DefinitionNameToTypeNameMap, FieldsOrder, FieldTypeProperties, InputTypeFieldProperties, PreProcessedFieldData, REFieldsSchemaProperties, REPropertiesSchema} from "./../../shared/types/types"
* @import {FieldDefinitionNode, TypeNode, InputValueDefinitionNode} from "graphql"
* @import {DefinitionNameToTypeNameMap, FieldsOrder, FieldTypeProperties, PreProcessedFieldData, REFieldsSchemaProperties, REPropertiesSchema} from "./../../shared/types/types"
*/

const { mapDirectivesUsage } = require('./directiveUsage');
const { astNodeKind } = require('../constants/graphqlAST');
const { BUILT_IN_SCALAR_LIST } = require('../constants/types');
const { getDefinitionReferencePath } = require('../helpers/getDefinitionReferencePath');
const { getArguments } = require('./arguments');
const { parseDefaultValue } = require('./defaultValue');
const { sortByName } = require('../helpers/sortByName');
Expand Down Expand Up @@ -118,7 +119,7 @@ function getTypeProperties({ type, definitionCategoryByNameMap }) {
const definitionCategoryName = definitionCategoryByNameMap[typeName];
if (definitionCategoryName) {
return {
'$ref': `#model/definitions/${definitionCategoryName}/${typeName}`,
'$ref': getDefinitionReferencePath({ definitionCategoryName, definitionName: typeName }),
required: false,
};
}
Expand Down
38 changes: 28 additions & 10 deletions reverse_engineering/mappers/typeDefinitions/typeDefinitions.js
Original file line number Diff line number Diff line change
@@ -1,21 +1,23 @@
/**
* @import {DefinitionNode} from "graphql"
* @import {REDirectiveDefinition,
* FieldsOrder,
* RECustomScalarDefinition,
* REDefinition,
* REModelDefinitionsSchema,
* DefinitionREStructure,
* DirectiveStructureType,
* REEnumDefinition,
* EnumStructureType,
* ObjectStructureType,
* ScalarStructureType,
* FieldsOrder,
* RECustomScalarDefinition,
* REDefinition,
* REModelDefinitionsSchema,
* DefinitionREStructure,
* DirectiveStructureType,
* REEnumDefinition,
* EnumStructureType,
* ObjectStructureType,
* ScalarStructureType,
* REObjectTypeDefinition,
* InterfaceStructureType,
* REInterfaceDefinition,
* REInputTypeDefinition,
* InputStructureType,
* REUnionDefinition,
* UnionStructureType,
* DefinitionNameToTypeNameMap} from "../../../shared/types/types"
*/

Expand All @@ -28,6 +30,7 @@ const { getObjectTypeDefinitions } = require('./objectType');
const { getEnumTypeDefinitions } = require('./enum');
const { getInterfaceDefinitions } = require('./interface');
const { getInputObjectTypeDefinitions } = require('./inputType');
const { getUnionTypeDefinitions } = require('./union');

/**
* Gets the type definitions structure
Expand Down Expand Up @@ -72,6 +75,11 @@ function getTypeDefinitions({ typeDefinitions, fieldsOrder, rootTypeNames, defin
fieldsOrder,
});

const unions = getUnionTypeDefinitions({
unions: findNodesByKind({ nodes: typeDefinitions, kind: astNodeKind.UNION_TYPE_DEFINITION }),
definitionCategoryByNameMap,
});

const definitions = getTypeDefinitionsStructure({
fieldsOrder,
directives,
Expand All @@ -80,6 +88,7 @@ function getTypeDefinitions({ typeDefinitions, fieldsOrder, rootTypeNames, defin
objectTypes,
interfaces,
inputTypes,
unions,
});

return definitions;
Expand All @@ -96,6 +105,7 @@ function getTypeDefinitions({ typeDefinitions, fieldsOrder, rootTypeNames, defin
* @param {REObjectTypeDefinition[]} params.objectTypes - The object type definitions
* @param {REInterfaceDefinition[]} params.interfaces - The interface definitions
* @param {REInputTypeDefinition[]} params.inputTypes - The input type definitions
* @param {REUnionDefinition[]} params.unions - The union definitions
* @returns {REModelDefinitionsSchema} The type definitions structure
*/
function getTypeDefinitionsStructure({
Expand All @@ -106,6 +116,7 @@ function getTypeDefinitionsStructure({
objectTypes,
interfaces,
inputTypes,
unions,
}) {
const definitions = {
['Directives']: /** @type {DirectiveStructureType} */ (
Expand Down Expand Up @@ -150,6 +161,13 @@ function getTypeDefinitionsStructure({
properties: inputTypes,
})
),
['Unions']: /** @type {UnionStructureType} */ (
getDefinitionCategoryStructure({
fieldsOrder,
subtype: 'union',
properties: unions,
})
),
};

return {
Expand Down
67 changes: 67 additions & 0 deletions reverse_engineering/mappers/typeDefinitions/union.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
/**
* @import {NamedTypeNode, UnionTypeDefinitionNode} from "graphql"
* @import {DefinitionNameToTypeNameMap, REUnionDefinition, REUnionMemberType} from "../../../shared/types/types"
*/

const { getDefinitionReferencePath } = require('../../helpers/getDefinitionReferencePath');
const { mapDirectivesUsage } = require('../directiveUsage');

/**
* Maps union type definitions
*
* @param {object} params
* @param {UnionTypeDefinitionNode[]} params.unions - The union types
* @param {DefinitionNameToTypeNameMap} params.definitionCategoryByNameMap - The definition category by name map
* @returns {REUnionDefinition[]} The mapped union type definitions
*/
function getUnionTypeDefinitions({ unions = [], definitionCategoryByNameMap }) {
return unions.map(union => mapUnion({ union, definitionCategoryByNameMap }));
}

/**
* Maps a single union type definition
*
* @param {object} params
* @param {UnionTypeDefinitionNode} params.union - The union to map
* @param {DefinitionNameToTypeNameMap} params.definitionCategoryByNameMap - The definition category by name map
* @returns {REUnionDefinition} The mapped union type definition
*/
function mapUnion({ union, definitionCategoryByNameMap }) {
return {
type: 'union',
name: union.name.value,
description: union.description?.value || '',
typeDirectives: mapDirectivesUsage({ directives: [...(union.directives || [])] }),
oneOf: mapUnionTypes({ types: [...(union.types || [])], definitionCategoryByNameMap }),
};
}

/**
* Maps the union types to references
*
* @param {object} params
* @param {NamedTypeNode[]} params.types - The types that the union can be
* @param {DefinitionNameToTypeNameMap} params.definitionCategoryByNameMap - The definition category by name map
* @returns {REUnionMemberType[]} The mapped union types as references
*/
function mapUnionTypes({ types, definitionCategoryByNameMap }) {
return types.map(type => {
const typeName = type.name.value;
const definitionCategoryName = definitionCategoryByNameMap[typeName];

if (definitionCategoryName) {
return {
$ref: getDefinitionReferencePath({ definitionCategoryName, definitionName: typeName }),
};
}

// Fallback to Objects
return {
$ref: getDefinitionReferencePath({ definitionCategoryName: 'Objects', definitionName: typeName }),
};
});
}

module.exports = {
getUnionTypeDefinitions,
};
25 changes: 23 additions & 2 deletions shared/types/re.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -135,14 +135,16 @@ type REObjectDefinitionsSchema = Record<string, REObjectTypeDefinition>;
type REEnumDefinitionsSchema = Record<string, REEnumDefinition>;
type REInterfaceDefinitionsSchema = Record<string, REInterfaceDefinition>;
type REInputDefinitionsSchema = Record<string, REInputTypeDefinition>;
type REUnionDefinitionsSchema = Record<string, REUnionDefinition>;

export type REDefinition =
| RECustomScalarDefinition
| REDirectiveDefinition
| REEnumDefinition
| REObjectTypeDefinition
| REInterfaceDefinition
| REInputTypeDefinition;
| REInputTypeDefinition
| REUnionDefinition;

export type REModelDefinitionsSchema = {
definitions: {
Expand All @@ -151,6 +153,8 @@ export type REModelDefinitionsSchema = {
Objects: ObjectStructureType;
Enums: EnumStructureType;
Interfaces: InterfaceStructureType;
'Input objects': InputStructureType;
Unions: UnionStructureType;
};
};

Expand All @@ -160,7 +164,8 @@ export type DefinitionREStructure =
| EnumStructureType
| ObjectStructureType
| InterfaceStructureType
| InputStructureType;
| InputStructureType
| UnionStructureType;

type StructureType<T> = {
type: 'type';
Expand Down Expand Up @@ -188,6 +193,10 @@ export type InputStructureType = StructureType<REInputDefinitionsSchema> & {
subtype: 'input';
};

export type UnionStructureType = StructureType<REUnionDefinitionsSchema> & {
subtype: 'union';
};

export type RECustomScalarDefinition = CustomScalarDefinition<StructuredDirective> & {
type: 'scalar';
name: string;
Expand Down Expand Up @@ -230,6 +239,18 @@ export type REInputTypeDefinition = REObjectLikeDefinition & {
type: 'input';
};

export type REUnionDefinition = {
type: 'union';
name: string;
description?: string;
typeDirectives?: StructuredDirective[];
oneOf: REUnionMemberType[];
};

export type REUnionMemberType = {
$ref: string;
};

export type PreProcessedFieldData = FieldData<StructuredDirective> &
FieldTypeProperties & {
name: string;
Expand Down
Loading