-
Notifications
You must be signed in to change notification settings - Fork 2k
[RFC]SDL validation #1438
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[RFC]SDL validation #1438
Changes from all commits
ce1d49d
ca82c30
6aff49c
1e24f87
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -11,6 +11,7 @@ import keyMap from '../jsutils/keyMap'; | |
import keyValMap from '../jsutils/keyValMap'; | ||
import type { ObjMap } from '../jsutils/ObjMap'; | ||
import { valueFromAST } from './valueFromAST'; | ||
import { assertValidSDL } from '../validation/validate'; | ||
import blockStringValue from '../language/blockStringValue'; | ||
import { TokenKind } from '../language/lexer'; | ||
import { parse } from '../language/parser'; | ||
|
@@ -86,6 +87,13 @@ export type BuildSchemaOptions = { | |
* Default: false | ||
*/ | ||
commentDescriptions?: boolean, | ||
|
||
/** | ||
* Set to true to assume the SDL is valid. | ||
* | ||
* Default: false | ||
*/ | ||
assumeValidSDL?: boolean, | ||
}; | ||
|
||
/** | ||
|
@@ -112,6 +120,10 @@ export function buildASTSchema( | |
throw new Error('Must provide a document ast.'); | ||
} | ||
|
||
if (!options || !(options.assumeValid || options.assumeValidSDL)) { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @mjmahone We need separate const errors = validateSDL(ast, null, customSetOfRules);
if (errors.length !== 0) {
// ...
}
const schema = buildASTSchema(ast, { assumeValidSDL: true }); There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ok this makes sense. A little bit annoying to add in that second key, but not the end of the world. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Wait: are you thinking There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @mjmahone My proposal: |
||
assertValidSDL(ast); | ||
} | ||
|
||
let schemaDef: ?SchemaDefinitionNode; | ||
|
||
const typeDefs: Array<TypeDefinitionNode> = []; | ||
|
@@ -121,9 +133,6 @@ export function buildASTSchema( | |
const d = ast.definitions[i]; | ||
switch (d.kind) { | ||
case Kind.SCHEMA_DEFINITION: | ||
if (schemaDef) { | ||
throw new Error('Must provide only one schema definition.'); | ||
} | ||
schemaDef = d; | ||
break; | ||
case Kind.SCALAR_TYPE_DEFINITION: | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -19,6 +19,7 @@ import type { | |
FragmentSpreadNode, | ||
FragmentDefinitionNode, | ||
} from '../language/ast'; | ||
import type { ASTVisitor } from '../language/visitor'; | ||
import type { GraphQLSchema } from '../type/schema'; | ||
import type { | ||
GraphQLInputType, | ||
|
@@ -64,6 +65,21 @@ export class ASTValidationContext { | |
} | ||
} | ||
|
||
export class SDLValidationContext extends ASTValidationContext { | ||
_schema: ?GraphQLSchema; | ||
|
||
constructor(ast: DocumentNode, schema?: ?GraphQLSchema): void { | ||
super(ast); | ||
this._schema = schema; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I don't think we should even allow access to a Ideally, the current I like the idea that there's a split between "validation that needs a schema" and "validation that does not", and "validation that does not need a schema" is a superset of "SDL validation". There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @mjmahone Problem is that conversion from SDL to Also after And there are others many potential scenarious where we loose something by such converion especially if schema that we trying to extend was build from And it's not a technical problem, since
"validation that does not need a schema" => ASTValidationContext If rule should check conflicts/dependencies beetween definitions it should handle case when you extending existing schema and use There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We should fix it so it's lossless, but that would be a different PR, and we could probably target 14.1 for that.
I think there's a way around this, where we'd do
Makes sense, so let's push this forward as-is. But I'd like to switch our mental model to being AST-validation first, and then only using the schema when it's truly necessary. You've mostly accomplished this, but I envision a bunch of people creating validation rules that silently fail if no schema is present (because they assume they always have a schema present). That would be an unfortunate future. |
||
} | ||
|
||
getSchema(): ?GraphQLSchema { | ||
return this._schema; | ||
} | ||
} | ||
|
||
export type SDLValidationRule = SDLValidationContext => ASTVisitor; | ||
|
||
export class ValidationContext extends ASTValidationContext { | ||
_schema: GraphQLSchema; | ||
_typeInfo: TypeInfo; | ||
|
@@ -234,3 +250,5 @@ export class ValidationContext extends ASTValidationContext { | |
return this._typeInfo.getArgument(); | ||
} | ||
} | ||
|
||
export type ValidationRule = ValidationContext => ASTVisitor; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this should just piggyback on the
GraphQLSchemaValidationOptions
'sassumeValid
key.If I set
assumeValid
and then get an error thrown when building the AST schema, that would be surprising. Especially asbuildASTSchema
's sole job is to build a schema.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@mjmahone Good catch 🔎 🐞
Fixed.