in controlplane/src/core/services/SchemaUsageTrafficInspector.ts [196:326]
export function toInspectorChange(change: SchemaDiff, schemaCheckId: string): InspectorSchemaChange | null {
const path = change.path.split('.');
switch (change.changeType) {
// Not inspectable yet
case ChangeType.SchemaMutationTypeChanged:
case ChangeType.SchemaQueryTypeChanged:
case ChangeType.SchemaSubscriptionTypeChanged:
case ChangeType.DirectiveRemoved:
case ChangeType.DirectiveArgumentAdded:
case ChangeType.DirectiveArgumentRemoved:
case ChangeType.DirectiveArgumentDefaultValueChanged:
case ChangeType.DirectiveArgumentTypeChanged:
case ChangeType.DirectiveLocationRemoved: {
// We cannot inspect these changes. We want to return null instead of throwing an error.
// This is so that other changes that we can in fact inspect are not skipped over in the schema check.
return null;
}
// Safe to ignore
case ChangeType.DirectiveAdded:
case ChangeType.FieldArgumentDescriptionChanged:
case ChangeType.FieldArgumentDefaultChanged:
case ChangeType.DirectiveDescriptionChanged:
case ChangeType.DirectiveArgumentDescriptionChanged:
case ChangeType.DirectiveLocationAdded:
case ChangeType.EnumValueDescriptionChanged:
case ChangeType.EnumValueDeprecationReasonChanged:
case ChangeType.EnumValueDeprecationReasonAdded:
case ChangeType.EnumValueDeprecationReasonRemoved:
case ChangeType.FieldDescriptionChanged:
case ChangeType.FieldDescriptionAdded:
case ChangeType.FieldDescriptionRemoved:
case ChangeType.FieldDeprecationAdded:
case ChangeType.FieldDeprecationRemoved:
case ChangeType.FieldDeprecationReasonChanged:
case ChangeType.FieldDeprecationReasonAdded:
case ChangeType.FieldDeprecationReasonRemoved:
case ChangeType.InputFieldDescriptionAdded:
case ChangeType.InputFieldDescriptionRemoved:
case ChangeType.InputFieldDescriptionChanged:
case ChangeType.InputFieldDefaultValueChanged:
case ChangeType.TypeDescriptionChanged:
case ChangeType.TypeDescriptionRemoved:
case ChangeType.TypeDescriptionAdded:
case ChangeType.TypeAdded:
case ChangeType.FieldAdded:
case ChangeType.UnionMemberAdded:
case ChangeType.DirectiveUsageUnionMemberAdded:
case ChangeType.DirectiveUsageUnionMemberRemoved:
case ChangeType.DirectiveUsageEnumAdded:
case ChangeType.DirectiveUsageEnumRemoved:
case ChangeType.DirectiveUsageEnumValueAdded:
case ChangeType.DirectiveUsageEnumValueRemoved:
case ChangeType.DirectiveUsageInputObjectAdded:
case ChangeType.DirectiveUsageInputObjectRemoved:
case ChangeType.DirectiveUsageFieldAdded:
case ChangeType.DirectiveUsageFieldRemoved:
case ChangeType.DirectiveUsageScalarAdded:
case ChangeType.DirectiveUsageScalarRemoved:
case ChangeType.DirectiveUsageObjectAdded:
case ChangeType.DirectiveUsageObjectRemoved:
case ChangeType.DirectiveUsageInterfaceAdded:
case ChangeType.DirectiveUsageInterfaceRemoved:
case ChangeType.DirectiveUsageArgumentDefinitionAdded:
case ChangeType.DirectiveUsageArgumentDefinitionRemoved:
case ChangeType.DirectiveUsageSchemaAdded:
case ChangeType.DirectiveUsageSchemaRemoved:
case ChangeType.DirectiveUsageFieldDefinitionAdded:
case ChangeType.DirectiveUsageFieldDefinitionRemoved:
case ChangeType.DirectiveUsageInputFieldDefinitionAdded:
case ChangeType.DirectiveUsageInputFieldDefinitionRemoved: {
return null;
}
// 1. When a type is removed we know the exact type name e.g. 'Engineer'. We have no field name.
// 2. When an interface type is removed or added we know the interface 'RoleType'. We have no field name.
case ChangeType.TypeRemoved:
case ChangeType.TypeKindChanged:
case ChangeType.ObjectTypeInterfaceAdded:
case ChangeType.ObjectTypeInterfaceRemoved: {
return {
schemaChangeId: schemaCheckId,
typeName: path[0],
};
}
// 1. When a field is removed we know the exact type and field name e.g. 'Engineer.name'
// 2. When a field type has changed in a breaking way, we know the exact type name and field name e.g. 'Engineer.name'
case ChangeType.FieldRemoved:
case ChangeType.FieldTypeChanged: {
return {
schemaChangeId: schemaCheckId,
typeName: path[0],
fieldName: path[1],
};
}
// 1. When an enum value is added or removed, we only know the affected type. This is fine because any change to an enum value is breaking.
// 2. When a union member is removed, we only know the affected parent type. We use namedType to check for the usage of the union member.
case ChangeType.UnionMemberRemoved:
case ChangeType.EnumValueAdded:
case ChangeType.EnumValueRemoved: {
return {
schemaChangeId: schemaCheckId,
namedType: path[0],
};
}
// 1. When the type of input field has changed, we know the exact type name and field name e.g. 'MyInput.name'
case ChangeType.InputFieldTypeChanged:
case ChangeType.InputFieldRemoved:
case ChangeType.InputFieldAdded: {
return {
schemaChangeId: schemaCheckId,
fieldName: path[1],
typeName: path[0],
isInput: true,
};
}
// 1. When an argument has changed, we know the exact path to the argument e.g. 'Query.engineer.id'
// and the type name e.g. 'Query'
case ChangeType.FieldArgumentRemoved:
case ChangeType.FieldArgumentAdded: // Only when a required argument is added
case ChangeType.FieldArgumentTypeChanged: {
return {
schemaChangeId: schemaCheckId,
path: path.slice(1), // The path to the updated argument e.g. 'engineer.name' of the type names
typeName: path[0], // Enclosing type e.g. 'Query' or 'Engineer' when the argument is on a field of type Engineer
isArgument: true,
};
}
}
// no return to enforce that all cases are handled
}