Skip to content

Commit 99189d9

Browse files
committed
Add oneOf directive
This adds the @OneOf directive as a default directive to indicate Objects and Input Objects as OneOf Objects/Input Objects which ensure there is exactly one non-null entry. Future commits will work to implement this directive.
1 parent da57238 commit 99189d9

File tree

7 files changed

+36
-4
lines changed

7 files changed

+36
-4
lines changed

src/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ export {
6464
GraphQLSkipDirective,
6565
GraphQLDeprecatedDirective,
6666
GraphQLSpecifiedByDirective,
67+
GraphQLOneOfDirective,
6768
// "Enum" of Type Kinds
6869
TypeKind,
6970
// Constant Deprecation Reason

src/type/__tests__/introspection-test.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -989,6 +989,12 @@ describe('Introspection', () => {
989989
},
990990
],
991991
},
992+
{
993+
name: 'oneOf',
994+
isRepeatable: false,
995+
locations: ['OBJECT', 'INPUT_OBJECT'],
996+
args: [],
997+
},
992998
],
993999
},
9941000
},

src/type/directives.ts

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -209,6 +209,17 @@ export const GraphQLSpecifiedByDirective: GraphQLDirective =
209209
},
210210
});
211211

212+
/**
213+
* Used to declare an Input Object as a OneOf Input Objects and an Object as a OneOf Object.
214+
*/
215+
export const GraphQLOneOfDirective: GraphQLDirective = new GraphQLDirective({
216+
name: 'oneOf',
217+
description:
218+
'Indicates an Object is a OneOf Object or an Input Object is a OneOf Input Object.',
219+
locations: [DirectiveLocation.OBJECT, DirectiveLocation.INPUT_OBJECT],
220+
args: {},
221+
});
222+
212223
/**
213224
* The full list of specified directives.
214225
*/
@@ -218,6 +229,7 @@ export const specifiedDirectives: ReadonlyArray<GraphQLDirective> =
218229
GraphQLSkipDirective,
219230
GraphQLDeprecatedDirective,
220231
GraphQLSpecifiedByDirective,
232+
GraphQLOneOfDirective,
221233
]);
222234

223235
export function isSpecifiedDirective(directive: GraphQLDirective): boolean {

src/type/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,7 @@ export {
133133
GraphQLSkipDirective,
134134
GraphQLDeprecatedDirective,
135135
GraphQLSpecifiedByDirective,
136+
GraphQLOneOfDirective,
136137
// Constant Deprecation Reason
137138
DEFAULT_DEPRECATION_REASON,
138139
} from './directives';

src/utilities/__tests__/buildASTSchema-test.ts

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ import {
2323
assertDirective,
2424
GraphQLDeprecatedDirective,
2525
GraphQLIncludeDirective,
26+
GraphQLOneOfDirective,
2627
GraphQLSkipDirective,
2728
GraphQLSpecifiedByDirective,
2829
} from '../../type/directives';
@@ -222,7 +223,7 @@ describe('Schema Builder', () => {
222223
it('Maintains @include, @skip & @specifiedBy', () => {
223224
const schema = buildSchema('type Query');
224225

225-
expect(schema.getDirectives()).to.have.lengthOf(4);
226+
expect(schema.getDirectives()).to.have.lengthOf(5);
226227
expect(schema.getDirective('skip')).to.equal(GraphQLSkipDirective);
227228
expect(schema.getDirective('include')).to.equal(GraphQLIncludeDirective);
228229
expect(schema.getDirective('deprecated')).to.equal(
@@ -231,6 +232,7 @@ describe('Schema Builder', () => {
231232
expect(schema.getDirective('specifiedBy')).to.equal(
232233
GraphQLSpecifiedByDirective,
233234
);
235+
expect(schema.getDirective('oneOf')).to.equal(GraphQLOneOfDirective);
234236
});
235237

236238
it('Overriding directives excludes specified', () => {
@@ -239,9 +241,10 @@ describe('Schema Builder', () => {
239241
directive @include on FIELD
240242
directive @deprecated on FIELD_DEFINITION
241243
directive @specifiedBy on FIELD_DEFINITION
244+
directive @oneOf on OBJECT
242245
`);
243246

244-
expect(schema.getDirectives()).to.have.lengthOf(4);
247+
expect(schema.getDirectives()).to.have.lengthOf(5);
245248
expect(schema.getDirective('skip')).to.not.equal(GraphQLSkipDirective);
246249
expect(schema.getDirective('include')).to.not.equal(
247250
GraphQLIncludeDirective,
@@ -252,18 +255,20 @@ describe('Schema Builder', () => {
252255
expect(schema.getDirective('specifiedBy')).to.not.equal(
253256
GraphQLSpecifiedByDirective,
254257
);
258+
expect(schema.getDirective('oneOf')).to.not.equal(GraphQLOneOfDirective);
255259
});
256260

257-
it('Adding directives maintains @include, @skip & @specifiedBy', () => {
261+
it('Adding directives maintains @include, @skip, @deprecated, @specifiedBy, and @oneOf', () => {
258262
const schema = buildSchema(`
259263
directive @foo(arg: Int) on FIELD
260264
`);
261265

262-
expect(schema.getDirectives()).to.have.lengthOf(5);
266+
expect(schema.getDirectives()).to.have.lengthOf(6);
263267
expect(schema.getDirective('skip')).to.not.equal(undefined);
264268
expect(schema.getDirective('include')).to.not.equal(undefined);
265269
expect(schema.getDirective('deprecated')).to.not.equal(undefined);
266270
expect(schema.getDirective('specifiedBy')).to.not.equal(undefined);
271+
expect(schema.getDirective('oneOf')).to.not.equal(undefined);
267272
});
268273

269274
it('Type modifiers', () => {

src/utilities/__tests__/findBreakingChanges-test.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import { describe, it } from 'mocha';
44
import {
55
GraphQLDeprecatedDirective,
66
GraphQLIncludeDirective,
7+
GraphQLOneOfDirective,
78
GraphQLSkipDirective,
89
GraphQLSpecifiedByDirective,
910
} from '../../type/directives';
@@ -802,6 +803,7 @@ describe('findBreakingChanges', () => {
802803
GraphQLSkipDirective,
803804
GraphQLIncludeDirective,
804805
GraphQLSpecifiedByDirective,
806+
GraphQLOneOfDirective,
805807
],
806808
});
807809

src/utilities/__tests__/printSchema-test.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -656,6 +656,11 @@ describe('Type System Printer', () => {
656656
url: String!
657657
) on SCALAR
658658
659+
"""
660+
Indicates an Object is a OneOf Object or an Input Object is a OneOf Input Object.
661+
"""
662+
directive @oneOf on OBJECT | INPUT_OBJECT
663+
659664
"""
660665
A GraphQL Schema defines the capabilities of a GraphQL server. It exposes all available types and directives on the server, as well as the entry points for query, mutation, and subscription operations.
661666
"""

0 commit comments

Comments
 (0)