@graphql-eslint/eslint-plugin 3.19.3-alpha-20230702093957-98f7783 → 3.20.0-alpha-20230703154330-0d51273

Sign up to get free protection for your applications and to get access to all the features.
Files changed (302) hide show
  1. package/{typings → cjs}/cache.d.ts +3 -1
  2. package/cjs/cache.js +57 -26
  3. package/{typings → cjs}/configs/index.d.ts +3 -1
  4. package/cjs/configs/index.js +47 -14
  5. package/{typings → cjs}/configs/operations-all.d.ts +2 -1
  6. package/cjs/configs/operations-all.js +47 -30
  7. package/{typings → cjs}/configs/operations-recommended.d.ts +2 -1
  8. package/cjs/configs/operations-recommended.js +72 -55
  9. package/{typings → cjs}/configs/relay.d.ts +2 -1
  10. package/cjs/configs/relay.js +31 -11
  11. package/{typings → cjs}/configs/schema-all.d.ts +2 -1
  12. package/cjs/configs/schema-all.js +41 -24
  13. package/{typings → cjs}/configs/schema-recommended.d.ts +2 -1
  14. package/cjs/configs/schema-recommended.js +68 -51
  15. package/{typings → cjs}/documents.d.ts +4 -1
  16. package/cjs/documents.js +74 -43
  17. package/cjs/estree-converter/converter.d.ts +8 -0
  18. package/cjs/estree-converter/converter.js +80 -59
  19. package/cjs/estree-converter/index.d.ts +8 -0
  20. package/cjs/estree-converter/index.js +25 -5
  21. package/{typings → cjs}/estree-converter/types.d.ts +7 -5
  22. package/cjs/estree-converter/types.js +16 -0
  23. package/cjs/estree-converter/utils.d.ts +18 -0
  24. package/cjs/estree-converter/utils.js +119 -95
  25. package/{typings → cjs}/flat-configs.d.ts +12 -1
  26. package/cjs/flat-configs.js +56 -32
  27. package/cjs/graphql-config.d.ts +13 -0
  28. package/cjs/graphql-config.js +78 -47
  29. package/cjs/index.d.ts +22 -0
  30. package/cjs/index.js +50 -18
  31. package/cjs/parser.d.ts +12 -0
  32. package/cjs/parser.js +96 -76
  33. package/cjs/processor.d.ts +9 -0
  34. package/cjs/processor.js +119 -88
  35. package/{typings → cjs}/rules/alphabetize.d.ts +12 -4
  36. package/cjs/rules/alphabetize.js +337 -295
  37. package/{typings → cjs}/rules/description-style.d.ts +12 -4
  38. package/cjs/rules/description-style.js +96 -66
  39. package/cjs/rules/graphql-js-validation.d.ts +12 -0
  40. package/cjs/rules/graphql-js-validation.js +595 -433
  41. package/cjs/rules/index.d.ts +125 -0
  42. package/cjs/rules/index.js +97 -76
  43. package/{typings → cjs}/rules/input-name.d.ts +12 -4
  44. package/cjs/rules/input-name.js +153 -123
  45. package/{typings → cjs}/rules/lone-executable-definition.d.ts +12 -4
  46. package/cjs/rules/lone-executable-definition.js +101 -72
  47. package/{typings → cjs}/rules/match-document-filename.d.ts +14 -6
  48. package/cjs/rules/match-document-filename.js +229 -182
  49. package/{typings → cjs}/rules/naming-convention.d.ts +12 -4
  50. package/cjs/rules/naming-convention.js +380 -316
  51. package/cjs/rules/no-anonymous-operations.d.ts +12 -0
  52. package/cjs/rules/no-anonymous-operations.js +88 -57
  53. package/cjs/rules/no-case-insensitive-enum-values-duplicates.d.ts +12 -0
  54. package/cjs/rules/no-case-insensitive-enum-values-duplicates.js +82 -50
  55. package/cjs/rules/no-deprecated.d.ts +12 -0
  56. package/cjs/rules/no-deprecated.js +106 -75
  57. package/cjs/rules/no-duplicate-fields.d.ts +12 -0
  58. package/cjs/rules/no-duplicate-fields.js +116 -82
  59. package/cjs/rules/no-hashtag-description.d.ts +13 -0
  60. package/cjs/rules/no-hashtag-description.js +119 -82
  61. package/cjs/rules/no-one-place-fragments.d.ts +12 -0
  62. package/cjs/rules/no-one-place-fragments.js +88 -58
  63. package/{typings → cjs}/rules/no-root-type.d.ts +12 -4
  64. package/cjs/rules/no-root-type.js +101 -74
  65. package/cjs/rules/no-scalar-result-type-on-mutation.d.ts +12 -0
  66. package/cjs/rules/no-scalar-result-type-on-mutation.js +90 -60
  67. package/cjs/rules/no-typename-prefix.d.ts +12 -0
  68. package/cjs/rules/no-typename-prefix.js +88 -55
  69. package/cjs/rules/no-unreachable-types.d.ts +12 -0
  70. package/cjs/rules/no-unreachable-types.js +169 -134
  71. package/cjs/rules/no-unused-fields.d.ts +12 -0
  72. package/cjs/rules/no-unused-fields.js +117 -92
  73. package/{typings → cjs}/rules/relay-arguments.d.ts +12 -4
  74. package/cjs/rules/relay-arguments.js +136 -110
  75. package/cjs/rules/relay-connection-types.d.ts +13 -0
  76. package/cjs/rules/relay-connection-types.js +123 -94
  77. package/{typings → cjs}/rules/relay-edge-types.d.ts +12 -4
  78. package/cjs/rules/relay-edge-types.js +196 -179
  79. package/cjs/rules/relay-page-info.d.ts +12 -0
  80. package/cjs/rules/relay-page-info.js +108 -89
  81. package/{typings → cjs}/rules/require-deprecation-date.d.ts +12 -4
  82. package/cjs/rules/require-deprecation-date.js +143 -112
  83. package/cjs/rules/require-deprecation-reason.d.ts +12 -0
  84. package/cjs/rules/require-deprecation-reason.js +80 -46
  85. package/{typings → cjs}/rules/require-description.d.ts +13 -5
  86. package/cjs/rules/require-description.js +170 -132
  87. package/cjs/rules/require-field-of-type-query-in-mutation-result.d.ts +12 -0
  88. package/cjs/rules/require-field-of-type-query-in-mutation-result.js +81 -51
  89. package/{typings → cjs}/rules/require-id-when-available.d.ts +12 -4
  90. package/cjs/rules/require-id-when-available.js +196 -173
  91. package/cjs/rules/require-import-fragment.d.ts +12 -0
  92. package/cjs/rules/require-import-fragment.js +138 -88
  93. package/cjs/rules/require-nullable-fields-with-oneof.d.ts +12 -0
  94. package/cjs/rules/require-nullable-fields-with-oneof.js +80 -50
  95. package/cjs/rules/require-nullable-result-in-root.d.ts +12 -0
  96. package/cjs/rules/require-nullable-result-in-root.js +97 -68
  97. package/cjs/rules/require-type-pattern-with-oneof.d.ts +12 -0
  98. package/cjs/rules/require-type-pattern-with-oneof.js +70 -42
  99. package/{typings → cjs}/rules/selection-set-depth.d.ts +12 -4
  100. package/cjs/rules/selection-set-depth.js +147 -107
  101. package/{typings → cjs}/rules/strict-id-in-types.d.ts +12 -4
  102. package/cjs/rules/strict-id-in-types.js +143 -122
  103. package/cjs/rules/unique-fragment-name.d.ts +13 -0
  104. package/cjs/rules/unique-fragment-name.js +88 -62
  105. package/cjs/rules/unique-operation-name.d.ts +12 -0
  106. package/cjs/rules/unique-operation-name.js +65 -35
  107. package/cjs/schema.d.ts +12 -0
  108. package/cjs/schema.js +62 -30
  109. package/cjs/siblings.d.ts +8 -0
  110. package/cjs/siblings.js +124 -106
  111. package/cjs/testkit.d.ts +8 -0
  112. package/cjs/testkit.js +165 -144
  113. package/cjs/types-e3367e3c.d.ts +129 -0
  114. package/cjs/types.d.ts +8 -0
  115. package/cjs/types.js +16 -0
  116. package/cjs/utils.d.ts +44 -0
  117. package/cjs/utils.js +181 -124
  118. package/{typings/cache.d.cts → esm/cache.d.mts} +3 -1
  119. package/esm/cache.js +25 -23
  120. package/{typings/configs/index.d.cts → esm/configs/index.d.mts} +3 -1
  121. package/esm/configs/index.js +14 -11
  122. package/{typings/configs/operations-all.d.cts → esm/configs/operations-all.d.mts} +2 -1
  123. package/esm/configs/operations-all.js +28 -28
  124. package/{typings/configs/operations-recommended.d.cts → esm/configs/operations-recommended.d.mts} +2 -1
  125. package/esm/configs/operations-recommended.js +53 -53
  126. package/{typings/configs/relay.d.cts → esm/configs/relay.d.mts} +2 -1
  127. package/esm/configs/relay.js +12 -9
  128. package/{typings/configs/schema-all.d.cts → esm/configs/schema-all.d.mts} +2 -1
  129. package/esm/configs/schema-all.js +22 -22
  130. package/{typings/configs/schema-recommended.d.cts → esm/configs/schema-recommended.d.mts} +2 -1
  131. package/esm/configs/schema-recommended.js +49 -49
  132. package/{typings/documents.d.cts → esm/documents.d.mts} +4 -1
  133. package/esm/documents.js +41 -39
  134. package/esm/estree-converter/converter.d.mts +8 -0
  135. package/esm/estree-converter/converter.js +63 -57
  136. package/esm/estree-converter/index.d.mts +8 -0
  137. package/esm/estree-converter/index.js +3 -3
  138. package/{typings/estree-converter/types.d.cts → esm/estree-converter/types.d.mts} +7 -5
  139. package/esm/estree-converter/utils.d.mts +18 -0
  140. package/esm/estree-converter/utils.js +102 -93
  141. package/{typings/flat-configs.d.cts → esm/flat-configs.d.mts} +13 -2
  142. package/esm/flat-configs.js +33 -30
  143. package/esm/graphql-config.d.mts +13 -0
  144. package/esm/graphql-config.js +49 -44
  145. package/esm/index.d.mts +22 -0
  146. package/esm/index.js +18 -9
  147. package/esm/package.json +1 -1
  148. package/esm/parser.d.mts +12 -0
  149. package/esm/parser.js +64 -73
  150. package/esm/processor.d.mts +9 -0
  151. package/esm/processor.js +98 -86
  152. package/{typings/rules/alphabetize.d.cts → esm/rules/alphabetize.d.mts} +12 -4
  153. package/esm/rules/alphabetize.js +304 -290
  154. package/{typings/rules/description-style.d.cts → esm/rules/description-style.d.mts} +12 -4
  155. package/esm/rules/description-style.js +73 -64
  156. package/esm/rules/graphql-js-validation.d.mts +12 -0
  157. package/esm/rules/graphql-js-validation.js +580 -429
  158. package/esm/rules/index.d.mts +125 -0
  159. package/esm/rules/index.js +74 -74
  160. package/{typings/rules/input-name.d.cts → esm/rules/input-name.d.mts} +12 -4
  161. package/esm/rules/input-name.js +132 -121
  162. package/{typings/rules/lone-executable-definition.d.cts → esm/rules/lone-executable-definition.d.mts} +12 -4
  163. package/esm/rules/lone-executable-definition.js +78 -70
  164. package/{typings/rules/match-document-filename.d.cts → esm/rules/match-document-filename.d.mts} +14 -6
  165. package/esm/rules/match-document-filename.js +210 -180
  166. package/{typings/rules/naming-convention.d.cts → esm/rules/naming-convention.d.mts} +12 -4
  167. package/esm/rules/naming-convention.js +363 -314
  168. package/esm/rules/no-anonymous-operations.d.mts +12 -0
  169. package/esm/rules/no-anonymous-operations.js +65 -55
  170. package/esm/rules/no-case-insensitive-enum-values-duplicates.d.mts +12 -0
  171. package/esm/rules/no-case-insensitive-enum-values-duplicates.js +59 -48
  172. package/esm/rules/no-deprecated.d.mts +12 -0
  173. package/esm/rules/no-deprecated.js +83 -73
  174. package/esm/rules/no-duplicate-fields.d.mts +12 -0
  175. package/esm/rules/no-duplicate-fields.js +93 -80
  176. package/esm/rules/no-hashtag-description.d.mts +13 -0
  177. package/esm/rules/no-hashtag-description.js +95 -80
  178. package/esm/rules/no-one-place-fragments.d.mts +12 -0
  179. package/esm/rules/no-one-place-fragments.js +65 -56
  180. package/{typings/rules/no-root-type.d.cts → esm/rules/no-root-type.d.mts} +12 -4
  181. package/esm/rules/no-root-type.js +78 -72
  182. package/esm/rules/no-scalar-result-type-on-mutation.d.mts +12 -0
  183. package/esm/rules/no-scalar-result-type-on-mutation.js +67 -58
  184. package/esm/rules/no-typename-prefix.d.mts +12 -0
  185. package/esm/rules/no-typename-prefix.js +65 -53
  186. package/esm/rules/no-unreachable-types.d.mts +12 -0
  187. package/esm/rules/no-unreachable-types.js +141 -131
  188. package/esm/rules/no-unused-fields.d.mts +12 -0
  189. package/esm/rules/no-unused-fields.js +94 -90
  190. package/{typings/rules/relay-arguments.d.cts → esm/rules/relay-arguments.d.mts} +12 -4
  191. package/esm/rules/relay-arguments.js +113 -108
  192. package/esm/rules/relay-connection-types.d.mts +13 -0
  193. package/esm/rules/relay-connection-types.js +98 -91
  194. package/{typings/rules/relay-edge-types.d.cts → esm/rules/relay-edge-types.d.mts} +12 -4
  195. package/esm/rules/relay-edge-types.js +178 -177
  196. package/esm/rules/relay-page-info.d.mts +12 -0
  197. package/esm/rules/relay-page-info.js +84 -86
  198. package/{typings/rules/require-deprecation-date.d.cts → esm/rules/require-deprecation-date.d.mts} +12 -4
  199. package/esm/rules/require-deprecation-date.js +120 -110
  200. package/esm/rules/require-deprecation-reason.d.mts +12 -0
  201. package/esm/rules/require-deprecation-reason.js +57 -44
  202. package/{typings/rules/require-description.d.cts → esm/rules/require-description.d.mts} +13 -5
  203. package/esm/rules/require-description.js +151 -130
  204. package/esm/rules/require-field-of-type-query-in-mutation-result.d.mts +12 -0
  205. package/esm/rules/require-field-of-type-query-in-mutation-result.js +58 -49
  206. package/{typings/rules/require-id-when-available.d.cts → esm/rules/require-id-when-available.d.mts} +12 -4
  207. package/esm/rules/require-id-when-available.js +186 -171
  208. package/esm/rules/require-import-fragment.d.mts +12 -0
  209. package/esm/rules/require-import-fragment.js +105 -85
  210. package/esm/rules/require-nullable-fields-with-oneof.d.mts +12 -0
  211. package/esm/rules/require-nullable-fields-with-oneof.js +57 -48
  212. package/esm/rules/require-nullable-result-in-root.d.mts +12 -0
  213. package/esm/rules/require-nullable-result-in-root.js +74 -66
  214. package/esm/rules/require-type-pattern-with-oneof.d.mts +12 -0
  215. package/esm/rules/require-type-pattern-with-oneof.js +47 -40
  216. package/{typings/rules/selection-set-depth.d.cts → esm/rules/selection-set-depth.d.mts} +12 -4
  217. package/esm/rules/selection-set-depth.js +114 -104
  218. package/{typings/rules/strict-id-in-types.d.cts → esm/rules/strict-id-in-types.d.mts} +12 -4
  219. package/esm/rules/strict-id-in-types.js +125 -119
  220. package/esm/rules/unique-fragment-name.d.mts +13 -0
  221. package/esm/rules/unique-fragment-name.js +65 -60
  222. package/esm/rules/unique-operation-name.d.mts +12 -0
  223. package/esm/rules/unique-operation-name.js +42 -33
  224. package/esm/schema.d.mts +12 -0
  225. package/esm/schema.js +29 -26
  226. package/esm/siblings.d.mts +8 -0
  227. package/esm/siblings.js +105 -104
  228. package/esm/testkit.d.mts +8 -0
  229. package/esm/testkit.js +132 -141
  230. package/esm/types-2e1afd7c.d.ts +129 -0
  231. package/esm/types.d.mts +8 -0
  232. package/esm/utils.d.mts +44 -0
  233. package/esm/utils.js +138 -116
  234. package/package.json +40 -30
  235. package/typings/estree-converter/converter.d.cts +0 -3
  236. package/typings/estree-converter/converter.d.ts +0 -3
  237. package/typings/estree-converter/index.d.cts +0 -3
  238. package/typings/estree-converter/index.d.ts +0 -3
  239. package/typings/estree-converter/utils.d.cts +0 -13
  240. package/typings/estree-converter/utils.d.ts +0 -13
  241. package/typings/graphql-config.d.cts +0 -4
  242. package/typings/graphql-config.d.ts +0 -4
  243. package/typings/index.d.cts +0 -10
  244. package/typings/index.d.ts +0 -10
  245. package/typings/parser.d.cts +0 -2
  246. package/typings/parser.d.ts +0 -2
  247. package/typings/processor.d.cts +0 -6
  248. package/typings/processor.d.ts +0 -6
  249. package/typings/rules/graphql-js-validation.d.cts +0 -2
  250. package/typings/rules/graphql-js-validation.d.ts +0 -2
  251. package/typings/rules/index.d.cts +0 -111
  252. package/typings/rules/index.d.ts +0 -111
  253. package/typings/rules/no-anonymous-operations.d.cts +0 -2
  254. package/typings/rules/no-anonymous-operations.d.ts +0 -2
  255. package/typings/rules/no-case-insensitive-enum-values-duplicates.d.cts +0 -2
  256. package/typings/rules/no-case-insensitive-enum-values-duplicates.d.ts +0 -2
  257. package/typings/rules/no-deprecated.d.cts +0 -2
  258. package/typings/rules/no-deprecated.d.ts +0 -2
  259. package/typings/rules/no-duplicate-fields.d.cts +0 -2
  260. package/typings/rules/no-duplicate-fields.d.ts +0 -2
  261. package/typings/rules/no-hashtag-description.d.cts +0 -3
  262. package/typings/rules/no-hashtag-description.d.ts +0 -3
  263. package/typings/rules/no-one-place-fragments.d.cts +0 -2
  264. package/typings/rules/no-one-place-fragments.d.ts +0 -2
  265. package/typings/rules/no-scalar-result-type-on-mutation.d.cts +0 -2
  266. package/typings/rules/no-scalar-result-type-on-mutation.d.ts +0 -2
  267. package/typings/rules/no-typename-prefix.d.cts +0 -2
  268. package/typings/rules/no-typename-prefix.d.ts +0 -2
  269. package/typings/rules/no-unreachable-types.d.cts +0 -2
  270. package/typings/rules/no-unreachable-types.d.ts +0 -2
  271. package/typings/rules/no-unused-fields.d.cts +0 -2
  272. package/typings/rules/no-unused-fields.d.ts +0 -2
  273. package/typings/rules/relay-connection-types.d.cts +0 -4
  274. package/typings/rules/relay-connection-types.d.ts +0 -4
  275. package/typings/rules/relay-page-info.d.cts +0 -2
  276. package/typings/rules/relay-page-info.d.ts +0 -2
  277. package/typings/rules/require-deprecation-reason.d.cts +0 -2
  278. package/typings/rules/require-deprecation-reason.d.ts +0 -2
  279. package/typings/rules/require-field-of-type-query-in-mutation-result.d.cts +0 -2
  280. package/typings/rules/require-field-of-type-query-in-mutation-result.d.ts +0 -2
  281. package/typings/rules/require-import-fragment.d.cts +0 -2
  282. package/typings/rules/require-import-fragment.d.ts +0 -2
  283. package/typings/rules/require-nullable-fields-with-oneof.d.cts +0 -2
  284. package/typings/rules/require-nullable-fields-with-oneof.d.ts +0 -2
  285. package/typings/rules/require-nullable-result-in-root.d.cts +0 -2
  286. package/typings/rules/require-nullable-result-in-root.d.ts +0 -2
  287. package/typings/rules/require-type-pattern-with-oneof.d.cts +0 -2
  288. package/typings/rules/require-type-pattern-with-oneof.d.ts +0 -2
  289. package/typings/rules/unique-fragment-name.d.cts +0 -5
  290. package/typings/rules/unique-fragment-name.d.ts +0 -5
  291. package/typings/rules/unique-operation-name.d.cts +0 -2
  292. package/typings/rules/unique-operation-name.d.ts +0 -2
  293. package/typings/schema.d.cts +0 -3
  294. package/typings/schema.d.ts +0 -3
  295. package/typings/siblings.d.cts +0 -22
  296. package/typings/siblings.d.ts +0 -22
  297. package/typings/testkit.d.cts +0 -29
  298. package/typings/testkit.d.ts +0 -29
  299. package/typings/types.d.cts +0 -83
  300. package/typings/types.d.ts +0 -83
  301. package/typings/utils.d.cts +0 -40
  302. package/typings/utils.d.ts +0 -40
@@ -1,367 +1,416 @@
1
- import { Kind } from 'graphql';
2
- import { ARRAY_DEFAULT_OPTIONS, convertCase, englishJoinWords, truthy, TYPES_KINDS, } from '../utils.js';
1
+ import { Kind } from "graphql";
2
+ import {
3
+ ARRAY_DEFAULT_OPTIONS,
4
+ convertCase,
5
+ englishJoinWords,
6
+ truthy,
7
+ TYPES_KINDS
8
+ } from "../utils.js";
3
9
  const KindToDisplayName = {
4
- // types
5
- [Kind.OBJECT_TYPE_DEFINITION]: 'Type',
6
- [Kind.INTERFACE_TYPE_DEFINITION]: 'Interface',
7
- [Kind.ENUM_TYPE_DEFINITION]: 'Enumerator',
8
- [Kind.SCALAR_TYPE_DEFINITION]: 'Scalar',
9
- [Kind.INPUT_OBJECT_TYPE_DEFINITION]: 'Input type',
10
- [Kind.UNION_TYPE_DEFINITION]: 'Union',
11
- // fields
12
- [Kind.FIELD_DEFINITION]: 'Field',
13
- [Kind.INPUT_VALUE_DEFINITION]: 'Input property',
14
- [Kind.ARGUMENT]: 'Argument',
15
- [Kind.DIRECTIVE_DEFINITION]: 'Directive',
16
- // rest
17
- [Kind.ENUM_VALUE_DEFINITION]: 'Enumeration value',
18
- [Kind.OPERATION_DEFINITION]: 'Operation',
19
- [Kind.FRAGMENT_DEFINITION]: 'Fragment',
20
- [Kind.VARIABLE_DEFINITION]: 'Variable',
10
+ // types
11
+ [Kind.OBJECT_TYPE_DEFINITION]: "Type",
12
+ [Kind.INTERFACE_TYPE_DEFINITION]: "Interface",
13
+ [Kind.ENUM_TYPE_DEFINITION]: "Enumerator",
14
+ [Kind.SCALAR_TYPE_DEFINITION]: "Scalar",
15
+ [Kind.INPUT_OBJECT_TYPE_DEFINITION]: "Input type",
16
+ [Kind.UNION_TYPE_DEFINITION]: "Union",
17
+ // fields
18
+ [Kind.FIELD_DEFINITION]: "Field",
19
+ [Kind.INPUT_VALUE_DEFINITION]: "Input property",
20
+ [Kind.ARGUMENT]: "Argument",
21
+ [Kind.DIRECTIVE_DEFINITION]: "Directive",
22
+ // rest
23
+ [Kind.ENUM_VALUE_DEFINITION]: "Enumeration value",
24
+ [Kind.OPERATION_DEFINITION]: "Operation",
25
+ [Kind.FRAGMENT_DEFINITION]: "Fragment",
26
+ [Kind.VARIABLE_DEFINITION]: "Variable"
21
27
  };
22
28
  const StyleToRegex = {
23
- camelCase: /^[a-z][\dA-Za-z]*$/,
24
- PascalCase: /^[A-Z][\dA-Za-z]*$/,
25
- snake_case: /^[a-z][\d_a-z]*[\da-z]*$/,
26
- UPPER_CASE: /^[A-Z][\dA-Z_]*[\dA-Z]*$/,
29
+ camelCase: /^[a-z][\dA-Za-z]*$/,
30
+ PascalCase: /^[A-Z][\dA-Za-z]*$/,
31
+ snake_case: /^[a-z][\d_a-z]*[\da-z]*$/,
32
+ UPPER_CASE: /^[A-Z][\dA-Z_]*[\dA-Z]*$/
27
33
  };
28
34
  const ALLOWED_KINDS = Object.keys(KindToDisplayName).sort();
29
35
  const ALLOWED_STYLES = Object.keys(StyleToRegex);
30
36
  const schemaOption = {
31
- oneOf: [{ $ref: '#/definitions/asString' }, { $ref: '#/definitions/asObject' }],
37
+ oneOf: [{ $ref: "#/definitions/asString" }, { $ref: "#/definitions/asObject" }]
32
38
  };
33
39
  const schema = {
34
- definitions: {
35
- asString: {
36
- enum: ALLOWED_STYLES,
37
- description: `One of: ${ALLOWED_STYLES.map(t => `\`${t}\``).join(', ')}`,
38
- },
39
- asObject: {
40
- type: 'object',
41
- additionalProperties: false,
42
- properties: {
43
- style: { enum: ALLOWED_STYLES },
44
- prefix: { type: 'string' },
45
- suffix: { type: 'string' },
46
- forbiddenPrefixes: ARRAY_DEFAULT_OPTIONS,
47
- forbiddenSuffixes: ARRAY_DEFAULT_OPTIONS,
48
- requiredPrefixes: ARRAY_DEFAULT_OPTIONS,
49
- requiredSuffixes: ARRAY_DEFAULT_OPTIONS,
50
- ignorePattern: {
51
- type: 'string',
52
- description: 'Option to skip validation of some words, e.g. acronyms',
53
- },
54
- },
55
- },
40
+ definitions: {
41
+ asString: {
42
+ enum: ALLOWED_STYLES,
43
+ description: `One of: ${ALLOWED_STYLES.map((t) => `\`${t}\``).join(", ")}`
56
44
  },
57
- type: 'array',
58
- maxItems: 1,
59
- items: {
60
- type: 'object',
61
- additionalProperties: false,
62
- properties: {
63
- types: {
64
- ...schemaOption,
65
- description: `Includes:\n${TYPES_KINDS.map(kind => `- \`${kind}\``).join('\n')}`,
66
- },
67
- ...Object.fromEntries(ALLOWED_KINDS.map(kind => [
68
- kind,
69
- {
70
- ...schemaOption,
71
- description: `Read more about this kind on [spec.graphql.org](https://spec.graphql.org/October2021/#${kind}).`,
72
- },
73
- ])),
74
- allowLeadingUnderscore: {
75
- type: 'boolean',
76
- default: false,
77
- },
78
- allowTrailingUnderscore: {
79
- type: 'boolean',
80
- default: false,
81
- },
82
- },
83
- patternProperties: {
84
- [`^(${ALLOWED_KINDS.join('|')})(.+)?$`]: schemaOption,
85
- },
86
- description: [
87
- "> It's possible to use a [`selector`](https://eslint.org/docs/developer-guide/selectors) that starts with allowed `ASTNode` names which are described below.",
88
- '>',
89
- '> Paste or drop code into the editor in [ASTExplorer](https://astexplorer.net) and inspect the generated AST to compose your selector.',
90
- '>',
91
- '> Example: pattern property `FieldDefinition[parent.name.value=Query]` will match only fields for type `Query`.',
92
- ].join('\n'),
45
+ asObject: {
46
+ type: "object",
47
+ additionalProperties: false,
48
+ properties: {
49
+ style: { enum: ALLOWED_STYLES },
50
+ prefix: { type: "string" },
51
+ suffix: { type: "string" },
52
+ forbiddenPrefixes: ARRAY_DEFAULT_OPTIONS,
53
+ forbiddenSuffixes: ARRAY_DEFAULT_OPTIONS,
54
+ requiredPrefixes: ARRAY_DEFAULT_OPTIONS,
55
+ requiredSuffixes: ARRAY_DEFAULT_OPTIONS,
56
+ ignorePattern: {
57
+ type: "string",
58
+ description: "Option to skip validation of some words, e.g. acronyms"
59
+ }
60
+ }
61
+ }
62
+ },
63
+ type: "array",
64
+ maxItems: 1,
65
+ items: {
66
+ type: "object",
67
+ additionalProperties: false,
68
+ properties: {
69
+ types: {
70
+ ...schemaOption,
71
+ description: `Includes:
72
+ ${TYPES_KINDS.map((kind) => `- \`${kind}\``).join("\n")}`
73
+ },
74
+ ...Object.fromEntries(
75
+ ALLOWED_KINDS.map((kind) => [
76
+ kind,
77
+ {
78
+ ...schemaOption,
79
+ description: `Read more about this kind on [spec.graphql.org](https://spec.graphql.org/October2021/#${kind}).`
80
+ }
81
+ ])
82
+ ),
83
+ allowLeadingUnderscore: {
84
+ type: "boolean",
85
+ default: false
86
+ },
87
+ allowTrailingUnderscore: {
88
+ type: "boolean",
89
+ default: false
90
+ }
93
91
  },
92
+ patternProperties: {
93
+ [`^(${ALLOWED_KINDS.join("|")})(.+)?$`]: schemaOption
94
+ },
95
+ description: [
96
+ "> It's possible to use a [`selector`](https://eslint.org/docs/developer-guide/selectors) that starts with allowed `ASTNode` names which are described below.",
97
+ ">",
98
+ "> Paste or drop code into the editor in [ASTExplorer](https://astexplorer.net) and inspect the generated AST to compose your selector.",
99
+ ">",
100
+ "> Example: pattern property `FieldDefinition[parent.name.value=Query]` will match only fields for type `Query`."
101
+ ].join("\n")
102
+ }
94
103
  };
95
- export const rule = {
96
- meta: {
97
- type: 'suggestion',
98
- docs: {
99
- description: 'Require names to follow specified conventions.',
100
- category: ['Schema', 'Operations'],
101
- recommended: true,
102
- url: 'https://the-guild.dev/graphql/eslint/rules/naming-convention',
103
- examples: [
104
- {
105
- title: 'Incorrect',
106
- usage: [{ types: 'PascalCase', FieldDefinition: 'camelCase' }],
107
- code: /* GraphQL */ `
104
+ const rule = {
105
+ meta: {
106
+ type: "suggestion",
107
+ docs: {
108
+ description: "Require names to follow specified conventions.",
109
+ category: ["Schema", "Operations"],
110
+ recommended: true,
111
+ url: "https://the-guild.dev/graphql/eslint/rules/naming-convention",
112
+ examples: [
113
+ {
114
+ title: "Incorrect",
115
+ usage: [{ types: "PascalCase", FieldDefinition: "camelCase" }],
116
+ code: (
117
+ /* GraphQL */
118
+ `
108
119
  type user {
109
120
  first_name: String!
110
121
  }
111
- `,
112
- },
113
- {
114
- title: 'Incorrect',
115
- usage: [{ FragmentDefinition: { style: 'PascalCase', forbiddenSuffixes: ['Fragment'] } }],
116
- code: /* GraphQL */ `
122
+ `
123
+ )
124
+ },
125
+ {
126
+ title: "Incorrect",
127
+ usage: [{ FragmentDefinition: { style: "PascalCase", forbiddenSuffixes: ["Fragment"] } }],
128
+ code: (
129
+ /* GraphQL */
130
+ `
117
131
  fragment UserFragment on User {
118
132
  # ...
119
133
  }
120
- `,
121
- },
122
- {
123
- title: 'Incorrect',
124
- usage: [{ 'FieldDefinition[parent.name.value=Query]': { forbiddenPrefixes: ['get'] } }],
125
- code: /* GraphQL */ `
134
+ `
135
+ )
136
+ },
137
+ {
138
+ title: "Incorrect",
139
+ usage: [{ "FieldDefinition[parent.name.value=Query]": { forbiddenPrefixes: ["get"] } }],
140
+ code: (
141
+ /* GraphQL */
142
+ `
126
143
  type Query {
127
144
  getUsers: [User!]!
128
145
  }
129
- `,
130
- },
131
- {
132
- title: 'Correct',
133
- usage: [{ types: 'PascalCase', FieldDefinition: 'camelCase' }],
134
- code: /* GraphQL */ `
146
+ `
147
+ )
148
+ },
149
+ {
150
+ title: "Correct",
151
+ usage: [{ types: "PascalCase", FieldDefinition: "camelCase" }],
152
+ code: (
153
+ /* GraphQL */
154
+ `
135
155
  type User {
136
156
  firstName: String
137
157
  }
138
- `,
139
- },
140
- {
141
- title: 'Correct',
142
- usage: [{ FragmentDefinition: { style: 'PascalCase', forbiddenSuffixes: ['Fragment'] } }],
143
- code: /* GraphQL */ `
158
+ `
159
+ )
160
+ },
161
+ {
162
+ title: "Correct",
163
+ usage: [{ FragmentDefinition: { style: "PascalCase", forbiddenSuffixes: ["Fragment"] } }],
164
+ code: (
165
+ /* GraphQL */
166
+ `
144
167
  fragment UserFields on User {
145
168
  # ...
146
169
  }
147
- `,
148
- },
149
- {
150
- title: 'Correct',
151
- usage: [{ 'FieldDefinition[parent.name.value=Query]': { forbiddenPrefixes: ['get'] } }],
152
- code: /* GraphQL */ `
170
+ `
171
+ )
172
+ },
173
+ {
174
+ title: "Correct",
175
+ usage: [{ "FieldDefinition[parent.name.value=Query]": { forbiddenPrefixes: ["get"] } }],
176
+ code: (
177
+ /* GraphQL */
178
+ `
153
179
  type Query {
154
180
  users: [User!]!
155
181
  }
156
- `,
157
- },
158
- {
159
- title: 'Correct',
160
- usage: [{ FieldDefinition: { style: 'camelCase', ignorePattern: '^(EAN13|UPC|UK)' } }],
161
- code: /* GraphQL */ `
182
+ `
183
+ )
184
+ },
185
+ {
186
+ title: "Correct",
187
+ usage: [{ FieldDefinition: { style: "camelCase", ignorePattern: "^(EAN13|UPC|UK)" } }],
188
+ code: (
189
+ /* GraphQL */
190
+ `
162
191
  type Product {
163
192
  EAN13: String
164
193
  UPC: String
165
194
  UKFlag: String
166
195
  }
167
- `,
168
- },
169
- {
170
- title: 'Correct',
171
- usage: [
172
- {
173
- 'FieldDefinition[gqlType.name.value=Boolean]': {
174
- style: 'camelCase',
175
- requiredPrefixes: ['is', 'has'],
176
- },
177
- 'FieldDefinition[gqlType.gqlType.name.value=Boolean]': {
178
- style: 'camelCase',
179
- requiredPrefixes: ['is', 'has'],
180
- },
181
- },
182
- ],
183
- code: /* GraphQL */ `
196
+ `
197
+ )
198
+ },
199
+ {
200
+ title: "Correct",
201
+ usage: [
202
+ {
203
+ "FieldDefinition[gqlType.name.value=Boolean]": {
204
+ style: "camelCase",
205
+ requiredPrefixes: ["is", "has"]
206
+ },
207
+ "FieldDefinition[gqlType.gqlType.name.value=Boolean]": {
208
+ style: "camelCase",
209
+ requiredPrefixes: ["is", "has"]
210
+ }
211
+ }
212
+ ],
213
+ code: (
214
+ /* GraphQL */
215
+ `
184
216
  type Product {
185
217
  isBackordered: Boolean
186
218
  isNew: Boolean!
187
219
  hasDiscount: Boolean!
188
220
  }
189
- `,
190
- },
191
- {
192
- title: 'Correct',
193
- usage: [
194
- {
195
- 'FieldDefinition[gqlType.gqlType.name.value=SensitiveSecret]': {
196
- style: 'camelCase',
197
- requiredSuffixes: ['SensitiveSecret'],
198
- },
199
- },
200
- ],
201
- code: /* GraphQL */ `
221
+ `
222
+ )
223
+ },
224
+ {
225
+ title: "Correct",
226
+ usage: [
227
+ {
228
+ "FieldDefinition[gqlType.gqlType.name.value=SensitiveSecret]": {
229
+ style: "camelCase",
230
+ requiredSuffixes: ["SensitiveSecret"]
231
+ }
232
+ }
233
+ ],
234
+ code: (
235
+ /* GraphQL */
236
+ `
202
237
  scalar SensitiveSecret
203
238
 
204
239
  type Account {
205
240
  accountSensitiveSecret: SensitiveSecret!
206
241
  }
207
- `,
208
- },
209
- ],
210
- configOptions: {
211
- schema: [
212
- {
213
- types: 'PascalCase',
214
- FieldDefinition: 'camelCase',
215
- InputValueDefinition: 'camelCase',
216
- Argument: 'camelCase',
217
- DirectiveDefinition: 'camelCase',
218
- EnumValueDefinition: 'UPPER_CASE',
219
- 'FieldDefinition[parent.name.value=Query]': {
220
- forbiddenPrefixes: ['query', 'get'],
221
- forbiddenSuffixes: ['Query'],
222
- },
223
- 'FieldDefinition[parent.name.value=Mutation]': {
224
- forbiddenPrefixes: ['mutation'],
225
- forbiddenSuffixes: ['Mutation'],
226
- },
227
- 'FieldDefinition[parent.name.value=Subscription]': {
228
- forbiddenPrefixes: ['subscription'],
229
- forbiddenSuffixes: ['Subscription'],
230
- },
231
- },
232
- ],
233
- operations: [
234
- {
235
- VariableDefinition: 'camelCase',
236
- OperationDefinition: {
237
- style: 'PascalCase',
238
- forbiddenPrefixes: ['Query', 'Mutation', 'Subscription', 'Get'],
239
- forbiddenSuffixes: ['Query', 'Mutation', 'Subscription'],
240
- },
241
- FragmentDefinition: {
242
- style: 'PascalCase',
243
- forbiddenPrefixes: ['Fragment'],
244
- forbiddenSuffixes: ['Fragment'],
245
- },
246
- },
247
- ],
242
+ `
243
+ )
244
+ }
245
+ ],
246
+ configOptions: {
247
+ schema: [
248
+ {
249
+ types: "PascalCase",
250
+ FieldDefinition: "camelCase",
251
+ InputValueDefinition: "camelCase",
252
+ Argument: "camelCase",
253
+ DirectiveDefinition: "camelCase",
254
+ EnumValueDefinition: "UPPER_CASE",
255
+ "FieldDefinition[parent.name.value=Query]": {
256
+ forbiddenPrefixes: ["query", "get"],
257
+ forbiddenSuffixes: ["Query"]
248
258
  },
249
- },
250
- hasSuggestions: true,
251
- schema,
259
+ "FieldDefinition[parent.name.value=Mutation]": {
260
+ forbiddenPrefixes: ["mutation"],
261
+ forbiddenSuffixes: ["Mutation"]
262
+ },
263
+ "FieldDefinition[parent.name.value=Subscription]": {
264
+ forbiddenPrefixes: ["subscription"],
265
+ forbiddenSuffixes: ["Subscription"]
266
+ }
267
+ }
268
+ ],
269
+ operations: [
270
+ {
271
+ VariableDefinition: "camelCase",
272
+ OperationDefinition: {
273
+ style: "PascalCase",
274
+ forbiddenPrefixes: ["Query", "Mutation", "Subscription", "Get"],
275
+ forbiddenSuffixes: ["Query", "Mutation", "Subscription"]
276
+ },
277
+ FragmentDefinition: {
278
+ style: "PascalCase",
279
+ forbiddenPrefixes: ["Fragment"],
280
+ forbiddenSuffixes: ["Fragment"]
281
+ }
282
+ }
283
+ ]
284
+ }
252
285
  },
253
- create(context) {
254
- const options = context.options[0] || {};
255
- const { allowLeadingUnderscore, allowTrailingUnderscore, types, ...restOptions } = options;
256
- function normalisePropertyOption(kind) {
257
- const style = (restOptions[kind] || types);
258
- return typeof style === 'object' ? style : { style };
286
+ hasSuggestions: true,
287
+ schema
288
+ },
289
+ create(context) {
290
+ const options = context.options[0] || {};
291
+ const { allowLeadingUnderscore, allowTrailingUnderscore, types, ...restOptions } = options;
292
+ function normalisePropertyOption(kind) {
293
+ const style = restOptions[kind] || types;
294
+ return typeof style === "object" ? style : { style };
295
+ }
296
+ function report(node, message, suggestedNames) {
297
+ context.report({
298
+ node,
299
+ message,
300
+ suggest: suggestedNames.map((suggestedName) => ({
301
+ desc: `Rename to \`${suggestedName}\``,
302
+ fix: (fixer) => fixer.replaceText(node, suggestedName)
303
+ }))
304
+ });
305
+ }
306
+ const checkNode = (selector) => (n) => {
307
+ const { name: node } = n.kind === Kind.VARIABLE_DEFINITION ? n.variable : n;
308
+ if (!node) {
309
+ return;
310
+ }
311
+ const {
312
+ prefix,
313
+ suffix,
314
+ forbiddenPrefixes,
315
+ forbiddenSuffixes,
316
+ style,
317
+ ignorePattern,
318
+ requiredPrefixes,
319
+ requiredSuffixes
320
+ } = normalisePropertyOption(selector);
321
+ const nodeType = KindToDisplayName[n.kind] || n.kind;
322
+ const nodeName = node.value;
323
+ const error = getError();
324
+ if (error) {
325
+ const { errorMessage, renameToNames } = error;
326
+ const [leadingUnderscores] = nodeName.match(/^_*/);
327
+ const [trailingUnderscores] = nodeName.match(/_*$/);
328
+ const suggestedNames = renameToNames.map(
329
+ (renameToName) => leadingUnderscores + renameToName + trailingUnderscores
330
+ );
331
+ report(node, `${nodeType} "${nodeName}" should ${errorMessage}`, suggestedNames);
332
+ }
333
+ function getError() {
334
+ const name = nodeName.replace(/(^_+)|(_+$)/g, "");
335
+ if (ignorePattern && new RegExp(ignorePattern, "u").test(name)) {
336
+ return;
259
337
  }
260
- function report(node, message, suggestedNames) {
261
- context.report({
262
- node,
263
- message,
264
- suggest: suggestedNames.map(suggestedName => ({
265
- desc: `Rename to \`${suggestedName}\``,
266
- fix: fixer => fixer.replaceText(node, suggestedName),
267
- })),
268
- });
338
+ if (prefix && !name.startsWith(prefix)) {
339
+ return {
340
+ errorMessage: `have "${prefix}" prefix`,
341
+ renameToNames: [prefix + name]
342
+ };
269
343
  }
270
- const checkNode = (selector) => (n) => {
271
- const { name: node } = n.kind === Kind.VARIABLE_DEFINITION ? n.variable : n;
272
- if (!node) {
273
- return;
274
- }
275
- const { prefix, suffix, forbiddenPrefixes, forbiddenSuffixes, style, ignorePattern, requiredPrefixes, requiredSuffixes, } = normalisePropertyOption(selector);
276
- const nodeType = KindToDisplayName[n.kind] || n.kind;
277
- const nodeName = node.value;
278
- const error = getError();
279
- if (error) {
280
- const { errorMessage, renameToNames } = error;
281
- const [leadingUnderscores] = nodeName.match(/^_*/);
282
- const [trailingUnderscores] = nodeName.match(/_*$/);
283
- const suggestedNames = renameToNames.map(renameToName => leadingUnderscores + renameToName + trailingUnderscores);
284
- report(node, `${nodeType} "${nodeName}" should ${errorMessage}`, suggestedNames);
285
- }
286
- function getError() {
287
- const name = nodeName.replace(/(^_+)|(_+$)/g, '');
288
- if (ignorePattern && new RegExp(ignorePattern, 'u').test(name)) {
289
- return;
290
- }
291
- if (prefix && !name.startsWith(prefix)) {
292
- return {
293
- errorMessage: `have "${prefix}" prefix`,
294
- renameToNames: [prefix + name],
295
- };
296
- }
297
- if (suffix && !name.endsWith(suffix)) {
298
- return {
299
- errorMessage: `have "${suffix}" suffix`,
300
- renameToNames: [name + suffix],
301
- };
302
- }
303
- const forbiddenPrefix = forbiddenPrefixes === null || forbiddenPrefixes === void 0 ? void 0 : forbiddenPrefixes.find(prefix => name.startsWith(prefix));
304
- if (forbiddenPrefix) {
305
- return {
306
- errorMessage: `not have "${forbiddenPrefix}" prefix`,
307
- renameToNames: [name.replace(new RegExp(`^${forbiddenPrefix}`), '')],
308
- };
309
- }
310
- const forbiddenSuffix = forbiddenSuffixes === null || forbiddenSuffixes === void 0 ? void 0 : forbiddenSuffixes.find(suffix => name.endsWith(suffix));
311
- if (forbiddenSuffix) {
312
- return {
313
- errorMessage: `not have "${forbiddenSuffix}" suffix`,
314
- renameToNames: [name.replace(new RegExp(`${forbiddenSuffix}$`), '')],
315
- };
316
- }
317
- if (requiredPrefixes &&
318
- !requiredPrefixes.some(requiredPrefix => name.startsWith(requiredPrefix))) {
319
- return {
320
- errorMessage: `have one of the following prefixes: ${englishJoinWords(requiredPrefixes)}`,
321
- renameToNames: style
322
- ? requiredPrefixes.map(prefix => convertCase(style, `${prefix} ${name}`))
323
- : requiredPrefixes.map(prefix => `${prefix}${name}`),
324
- };
325
- }
326
- if (requiredSuffixes &&
327
- !requiredSuffixes.some(requiredSuffix => name.endsWith(requiredSuffix))) {
328
- return {
329
- errorMessage: `have one of the following suffixes: ${englishJoinWords(requiredSuffixes)}`,
330
- renameToNames: style
331
- ? requiredSuffixes.map(suffix => convertCase(style, `${name} ${suffix}`))
332
- : requiredSuffixes.map(suffix => `${name}${suffix}`),
333
- };
334
- }
335
- // Style is optional
336
- if (!style) {
337
- return;
338
- }
339
- const caseRegex = StyleToRegex[style];
340
- if (!caseRegex.test(name)) {
341
- return {
342
- errorMessage: `be in ${style} format`,
343
- renameToNames: [convertCase(style, name)],
344
- };
345
- }
346
- }
347
- };
348
- const checkUnderscore = (isLeading) => (node) => {
349
- const suggestedName = node.value.replace(isLeading ? /^_+/ : /_+$/, '');
350
- report(node, `${isLeading ? 'Leading' : 'Trailing'} underscores are not allowed`, [
351
- suggestedName,
352
- ]);
353
- };
354
- const listeners = {};
355
- if (!allowLeadingUnderscore) {
356
- listeners['Name[value=/^_/]:matches([parent.kind!=Field], [parent.kind=Field][parent.alias])'] = checkUnderscore(true);
344
+ if (suffix && !name.endsWith(suffix)) {
345
+ return {
346
+ errorMessage: `have "${suffix}" suffix`,
347
+ renameToNames: [name + suffix]
348
+ };
357
349
  }
358
- if (!allowTrailingUnderscore) {
359
- listeners['Name[value=/_$/]:matches([parent.kind!=Field], [parent.kind=Field][parent.alias])'] = checkUnderscore(false);
350
+ const forbiddenPrefix = forbiddenPrefixes?.find((prefix2) => name.startsWith(prefix2));
351
+ if (forbiddenPrefix) {
352
+ return {
353
+ errorMessage: `not have "${forbiddenPrefix}" prefix`,
354
+ renameToNames: [name.replace(new RegExp(`^${forbiddenPrefix}`), "")]
355
+ };
360
356
  }
361
- const selectors = new Set([types && TYPES_KINDS, Object.keys(restOptions)].flat().filter(truthy));
362
- for (const selector of selectors) {
363
- listeners[selector] = checkNode(selector);
357
+ const forbiddenSuffix = forbiddenSuffixes?.find((suffix2) => name.endsWith(suffix2));
358
+ if (forbiddenSuffix) {
359
+ return {
360
+ errorMessage: `not have "${forbiddenSuffix}" suffix`,
361
+ renameToNames: [name.replace(new RegExp(`${forbiddenSuffix}$`), "")]
362
+ };
364
363
  }
365
- return listeners;
366
- },
364
+ if (requiredPrefixes && !requiredPrefixes.some((requiredPrefix) => name.startsWith(requiredPrefix))) {
365
+ return {
366
+ errorMessage: `have one of the following prefixes: ${englishJoinWords(
367
+ requiredPrefixes
368
+ )}`,
369
+ renameToNames: style ? requiredPrefixes.map((prefix2) => convertCase(style, `${prefix2} ${name}`)) : requiredPrefixes.map((prefix2) => `${prefix2}${name}`)
370
+ };
371
+ }
372
+ if (requiredSuffixes && !requiredSuffixes.some((requiredSuffix) => name.endsWith(requiredSuffix))) {
373
+ return {
374
+ errorMessage: `have one of the following suffixes: ${englishJoinWords(
375
+ requiredSuffixes
376
+ )}`,
377
+ renameToNames: style ? requiredSuffixes.map((suffix2) => convertCase(style, `${name} ${suffix2}`)) : requiredSuffixes.map((suffix2) => `${name}${suffix2}`)
378
+ };
379
+ }
380
+ if (!style) {
381
+ return;
382
+ }
383
+ const caseRegex = StyleToRegex[style];
384
+ if (!caseRegex.test(name)) {
385
+ return {
386
+ errorMessage: `be in ${style} format`,
387
+ renameToNames: [convertCase(style, name)]
388
+ };
389
+ }
390
+ }
391
+ };
392
+ const checkUnderscore = (isLeading) => (node) => {
393
+ const suggestedName = node.value.replace(isLeading ? /^_+/ : /_+$/, "");
394
+ report(node, `${isLeading ? "Leading" : "Trailing"} underscores are not allowed`, [
395
+ suggestedName
396
+ ]);
397
+ };
398
+ const listeners = {};
399
+ if (!allowLeadingUnderscore) {
400
+ listeners["Name[value=/^_/]:matches([parent.kind!=Field], [parent.kind=Field][parent.alias])"] = checkUnderscore(true);
401
+ }
402
+ if (!allowTrailingUnderscore) {
403
+ listeners["Name[value=/_$/]:matches([parent.kind!=Field], [parent.kind=Field][parent.alias])"] = checkUnderscore(false);
404
+ }
405
+ const selectors = new Set(
406
+ [types && TYPES_KINDS, Object.keys(restOptions)].flat().filter(truthy)
407
+ );
408
+ for (const selector of selectors) {
409
+ listeners[selector] = checkNode(selector);
410
+ }
411
+ return listeners;
412
+ }
413
+ };
414
+ export {
415
+ rule
367
416
  };