graphql.py 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177
  1. """
  2. pygments.lexers.graphql
  3. ~~~~~~~~~~~~~~~~~~~~~~~
  4. Lexer for GraphQL, an open-source data query and manipulation
  5. language for APIs.
  6. More information:
  7. https://graphql.org/
  8. :copyright: Copyright 2006-2023 by the Pygments team, see AUTHORS.
  9. :license: BSD, see LICENSE for details.
  10. """
  11. from pygments.lexer import RegexLexer, words, include, bygroups, default
  12. from pygments.token import (Comment, Keyword, Name, Number, Punctuation, String,
  13. Whitespace)
  14. __all__ = ["GraphQLLexer"]
  15. OPERATION_TYPES = ("query", "mutation", "subscription")
  16. BUILTIN_TYPES = ("Int", "Float", "String", "Boolean", "ID")
  17. BOOLEAN_VALUES = ("true", "false", "null")
  18. KEYWORDS = (
  19. "type",
  20. "schema",
  21. "extend",
  22. "enum",
  23. "scalar",
  24. "implements",
  25. "interface",
  26. "union",
  27. "input",
  28. "directive",
  29. "QUERY",
  30. "MUTATION",
  31. "SUBSCRIPTION",
  32. "FIELD",
  33. "FRAGMENT_DEFINITION",
  34. "FRAGMENT_SPREAD",
  35. "INLINE_FRAGMENT",
  36. "SCHEMA",
  37. "SCALAR",
  38. "OBJECT",
  39. "FIELD_DEFINITION",
  40. "ARGUMENT_DEFINITION",
  41. "INTERFACE",
  42. "UNION",
  43. "ENUM",
  44. "ENUM_VALUE",
  45. "INPUT_OBJECT",
  46. "INPUT_FIELD_DEFINITION",
  47. )
  48. class GraphQLLexer(RegexLexer):
  49. """
  50. Lexer for GraphQL syntax
  51. .. versionadded:: 2.16
  52. """
  53. name = "GraphQL"
  54. aliases = ["graphql"]
  55. filenames = ["*.graphql"]
  56. url = "https://graphql.org"
  57. tokens = {
  58. "ignored_tokens": [
  59. (r"\s+", Whitespace), # Whitespaces
  60. (r"#.*$", Comment),
  61. (",", Punctuation), # Insignificant commas
  62. ],
  63. "value": [
  64. include("ignored_tokens"),
  65. (r"-?\d+(?![.eE])", Number.Integer, "#pop"),
  66. (
  67. r"-?\d+(\.\d+)?([eE][+-]?\d+)?",
  68. Number.Float,
  69. "#pop",
  70. ),
  71. (r'"', String, ("#pop", "string")),
  72. (words(BOOLEAN_VALUES, suffix=r"\b"), Name.Builtin, "#pop"),
  73. (r"\$[a-zA-Z_]\w*", Name.Variable, "#pop"),
  74. (r"[a-zA-Z_]\w*", Name.Constant, "#pop"),
  75. (r"\[", Punctuation, ("#pop", "list_value")),
  76. (r"\{", Punctuation, ("#pop", "object_value")),
  77. ],
  78. "list_value": [
  79. include("ignored_tokens"),
  80. ("]", Punctuation, "#pop"),
  81. default("value"),
  82. ],
  83. "object_value": [
  84. include("ignored_tokens"),
  85. (r"[a-zA-Z_]\w*", Name),
  86. (r":", Punctuation, "value"),
  87. (r"\}", Punctuation, "#pop"),
  88. ],
  89. "string": [
  90. (r'\\(["\\/bfnrt]|u[a-fA-F0-9]{4})', String.Escape),
  91. (r'[^\\"\n]+', String), # all other characters
  92. (r'"', String, "#pop"),
  93. ],
  94. "root": [
  95. include("ignored_tokens"),
  96. (words(OPERATION_TYPES, suffix=r"\b"), Keyword, "operation"),
  97. (words(KEYWORDS, suffix=r"\b"), Keyword),
  98. (r"\{", Punctuation, "selection_set"),
  99. (r"fragment\b", Keyword, "fragment_definition"),
  100. ],
  101. "operation": [
  102. include("ignored_tokens"),
  103. (r"[a-zA-Z_]\w*", Name.Function),
  104. (r"\(", Punctuation, "variable_definition"),
  105. (r"\{", Punctuation, ("#pop", "selection_set")),
  106. ],
  107. "variable_definition": [
  108. include("ignored_tokens"),
  109. (r"\$[a-zA-Z_]\w*", Name.Variable),
  110. (r"[\]!]", Punctuation),
  111. (r":", Punctuation, "type"),
  112. (r"=", Punctuation, "value"),
  113. (r"\)", Punctuation, "#pop"),
  114. ],
  115. "type": [
  116. include("ignored_tokens"),
  117. (r"\[", Punctuation),
  118. (words(BUILTIN_TYPES, suffix=r"\b"), Name.Builtin, "#pop"),
  119. (r"[a-zA-Z_]\w*", Name.Class, "#pop"),
  120. ],
  121. "selection_set": [
  122. include("ignored_tokens"),
  123. (r"([a-zA-Z_]\w*)(\s*)(:)", bygroups(Name.Label, Whitespace, Punctuation)),
  124. (r"[a-zA-Z_]\w*", Name), # Field
  125. (
  126. r"(\.\.\.)(\s+)(on)\b",
  127. bygroups(Punctuation, Whitespace, Keyword),
  128. "inline_fragment",
  129. ),
  130. (r"\.\.\.", Punctuation, "fragment_spread"),
  131. (r"\(", Punctuation, "arguments"),
  132. (r"@[a-zA-Z_]\w*", Name.Decorator, "directive"),
  133. (r"\{", Punctuation, "selection_set"),
  134. (r"\}", Punctuation, "#pop"),
  135. ],
  136. "directive": [
  137. include("ignored_tokens"),
  138. (r"\(", Punctuation, ("#pop", "arguments")),
  139. ],
  140. "arguments": [
  141. include("ignored_tokens"),
  142. (r"[a-zA-Z_]\w*", Name),
  143. (r":", Punctuation, "value"),
  144. (r"\)", Punctuation, "#pop"),
  145. ],
  146. # Fragments
  147. "fragment_definition": [
  148. include("ignored_tokens"),
  149. (r"[\]!]", Punctuation), # For NamedType
  150. (r"on\b", Keyword, "type"),
  151. (r"[a-zA-Z_]\w*", Name.Function),
  152. (r"@[a-zA-Z_]\w*", Name.Decorator, "directive"),
  153. (r"\{", Punctuation, ("#pop", "selection_set")),
  154. ],
  155. "fragment_spread": [
  156. include("ignored_tokens"),
  157. (r"@[a-zA-Z_]\w*", Name.Decorator, "directive"),
  158. (r"[a-zA-Z_]\w*", Name, "#pop"), # Fragment name
  159. ],
  160. "inline_fragment": [
  161. include("ignored_tokens"),
  162. (r"[a-zA-Z_]\w*", Name.Class), # Type condition
  163. (r"@[a-zA-Z_]\w*", Name.Decorator, "directive"),
  164. (r"\{", Punctuation, ("#pop", "selection_set")),
  165. ],
  166. }