@magidoc/plugin-reverse-schema-mapper
Version:
A library that provides the ability to do a reverse lookup on GraphQL types.
77 lines (74 loc) • 2.47 kB
JavaScript
import { isObjectType, isUnionType, isNonNullType, isListType } from 'graphql';
import { ReverseGraphQLSchemaMapping } from './reverseMapping.js';
import { ReferenceKind } from './reverseUsage.js';
function createReverseMapping(schema) {
const mapping = new Map();
iterateTypes(schema, (type) => {
if (isObjectType(type)) {
iterateFields(type, (field) => {
const fieldType = unwrap(field.type);
const target = getOrCreate(mapping, fieldType);
target.references.push({
kind: ReferenceKind.FIELD,
parent: type,
by: field,
});
iterateArguments(field, (argument) => {
const argumentType = unwrap(argument.type);
const target = getOrCreate(mapping, argumentType);
target.references.push({
kind: ReferenceKind.ARGUMENT,
field: field,
type: type,
by: argument,
});
});
});
}
if (isUnionType(type)) {
type.getTypes().forEach((union) => {
const target = getOrCreate(mapping, union);
target.references.push({
kind: ReferenceKind.UNION,
by: type,
});
});
}
});
return new ReverseGraphQLSchemaMapping(mapping);
}
function iterateTypes(schema, callback) {
Object.entries(schema.getTypeMap()).forEach(([, type]) => {
if (!type.name.startsWith('__')) {
callback(type);
}
});
}
function iterateFields(type, callback) {
Object.entries(type.getFields()).forEach(([, field]) => {
callback(field);
});
}
function iterateArguments(field, callback) {
Object.entries(field.args).forEach(([, arg]) => {
callback(arg);
});
}
function getOrCreate(mapping, type) {
let reverseMapping = mapping.get(type.name);
if (!reverseMapping) {
reverseMapping = {
references: [],
};
mapping.set(type.name, reverseMapping);
}
return reverseMapping;
}
function unwrap(type) {
if (isNonNullType(type) || isListType(type)) {
return unwrap(type.ofType);
}
return type;
}
export { createReverseMapping };
//# sourceMappingURL=createReverseMapping.js.map