7

GraphQL 语法的 EBNF 定义

 3 years ago
source link: https://zhuanlan.zhihu.com/p/339401770
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

最近一直在忙着魔改 GraphQL 实现. 现有的 GraphQL 实现理论上无论是性能还是新特性跟进提升空间还有很多, 但是大部分实现都困于 GraphQL 本身的语法定义过于复杂或社区人手不足, 导致实现版本还停留在 GraphQL 的很早期的版本.

所以我开展了一个跟进 GraphQL 最新语法规范的项目, 目前还处于一个很初级的阶段. 而这个项目的第一步, 是需要重新梳理 GraphQL 的语法规则.

GraphQL 官方提供了一个详细的规范文档, 这个文档对于用来写 Lexer 和 Parser 足够了, 但为了方便理解, 我顺便根据这个文档整理了 GraphQL 语法的 EBNF 定义.

Preview:

/* SourceCharacter Expression */
SourceCharacter ::=  #x0009 | #x000A | #x000D | [#x0020-#xFFFF] /* /[\u0009\u000A\u000D\u0020-\uFFFF]/ */
/* Ignored Tokens Expression */
Ignored        ::= UnicodeBOM | WhiteSpace | LineTerminator | Comment | Comma
UnicodeBOM     ::= #xFEFF  /* Byte Order Mark (U+FEFF) */
WhiteSpace     ::= #x0009 | #x0020 /* ASCII: \t | Space, Horizontal Tab (U+0009), Space (U+0020) */
LineTerminator ::= #x000A | #x000D | #x000D#x000A   /* ASCII: \n | \r\n | \r, New Line (U+000A) | Carriage Return (U+000D) [Lookahead != New Line (U+000A)] | Carriage Return (U+000D)New Line (U+000A) */
Comment        ::= "#" CommentChar* LineTerminator
CommentChar    ::= SourceCharacter - LineTerminator
Comma          ::= ","
...

语法图:

NJZZRfR.jpg!mobile

Github:

graphql-grammar-ebnf-definition github.com

该项目旨在整理一份清晰的, 基于W3C EBNF 规则的 EBNF 定义, 以及根据这个定义生成 GraphQL 语法图 (铁路图).

目前已经实现了 GraphQL 的最新标准 (June 2018), 未来会继续跟进最新的 Working Draft.

需要注意的是, 现有不同语言的 GraphQL 实现的语法规则可能都不尽相同, 有的实现了较新版本的规则, 有的版本则很旧. 如果需要使用 GraphQL 的新特性需要测试后再投入生产.

为什么不用 ISO-14977 定义的 EBNF 书写?

因为 ISO-14977 定义的 EBNF 有一些问题, 详情可以参考 dont-use-iso-14977-ebnf , W3C 定义的 EBNF 则不存在这些问题.


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK