|
1 |
| -# Stages for changes to the GraphQL Specification |
| 1 | +# GraphQL Specification Contribution Guide |
2 | 2 |
|
3 |
| -> **Document status:** [Draft](https://github.com/facebook/graphql/pull/342) |
| 3 | +GraphQL is still an evolving language. This repository contains the |
| 4 | +specification text as well as Pull Requests with suggested improvements and |
| 5 | +contibutions. |
4 | 6 |
|
5 |
| -This document describes the stages required for merging changes to the |
6 |
| -GraphQL Specification. These stages are intended to: |
| 7 | +Contributions which do not change the interpretation of the spec but instead |
| 8 | +improve legibility, fix editorial errors, clear up ambiguity and improve |
| 9 | +examples are encouraged and are often merged by a spec editor with |
| 10 | +little process. |
7 | 11 |
|
8 |
| -+ Be as flexible as possible. |
9 |
| -+ Define a clear process for getting changes into the specification. |
10 |
| -+ Provide visibility for participants in the GraphQL ecosystem into the |
11 |
| -status and progress of proposals. |
12 |
| -+ Encourage community discussion around the proposed changes. |
| 12 | +However, contributions which do meaningfully change the interpretation of the |
| 13 | +spec must follow an RFC (Request For Comments) process led by a *champion* |
| 14 | +through a series of *stages* intended to improve *visibility*, allow for |
| 15 | +*discussion* to reach the best solution, and arrive at *consensus*. This process |
| 16 | +becomes ever more important as GraphQL's community broadens. |
13 | 17 |
|
14 |
| -Any changes to the specification that affect the behavior of **GraphQL server |
15 |
| -or client implementations** should go through the stages below no matter how |
16 |
| -small they are. All other changes should be labeled as “editorial” and may |
17 |
| -be merged right away. Also, please read the [Code of Conduct](CODE_OF_CONDUCT.md) |
18 |
| -to know what is expected when making contributions to this project. |
| 18 | +When proposing or weighing-in on any issue or pull request, consider the |
| 19 | +[Code of Conduct](CODE_OF_CONDUCT.md) to better understand expected and |
| 20 | +unacceptable behavior. |
19 | 21 |
|
20 |
| -## Stage -2: proposed change (optional) |
21 | 22 |
|
22 |
| -**Prerequisite**: Described problem/change should be specific to the content of |
23 |
| -GraphQL Specification and not be an implementation detail. |
| 23 | +## Contributing to GraphQL Libraries |
24 | 24 |
|
25 |
| -**Purpose**: Filter out questions and issues for other repos, and engage community |
26 |
| -discussion. |
| 25 | +A common point of confusion for those who wish to contribute to GraphQL is where |
| 26 | +to start. In fact, you may have found yourself here after attempting to make an |
| 27 | +improvement to a GraphQL library. Should a new addition be made to the GraphQL |
| 28 | +spec first or a GraphQL library first? Admittedly, this can become a bit of a |
| 29 | +[chicken-or-egg](https://en.wikipedia.org/wiki/Chicken_or_the_egg) dilemma. |
27 | 30 |
|
28 |
| -## Stage -1: PR requested (optional) |
| 31 | +GraphQL libraries seek to be "spec compliant", which means they discourage |
| 32 | +changes that cause them to behave differently from the spec as written. However, |
| 33 | +they also encourage pull requests for changes that accompany an RFC *proposal* |
| 34 | +or RFC *draft*. In fact, a spec contribution RFC won't be *accepted* until it |
| 35 | +has experience being implemented in a GraphQL library. |
29 | 36 |
|
30 |
| -**Prerequisite**: Issue should contain description of problem or use case and |
31 |
| -proposed solution. |
| 37 | +To allow a library to remain spec compliant while also implementing *proposals* |
| 38 | +and *drafts*, it may request that these features are built so they are disabled |
| 39 | +by default with opt-in option flags or it may simply wait to merge a well-tested |
| 40 | +pull request until the spec proposal is *accepted*. |
32 | 41 |
|
33 |
| -**Purpose**: Find member of community to be champion for this change. |
34 | 42 |
|
35 |
| -## Stage 0: Proposal |
| 43 | +## Guiding Principles |
36 | 44 |
|
37 |
| -**Prerequisite**: |
38 |
| -+ Initial version of spec changes. |
39 |
| -+ Filled checklist ([TBD](https://youtu.be/mePT9MNTM98?t=20m32s)) in PR description. |
| 45 | +GraphQL's evolution is guided by a few principles. Suggested contributions |
| 46 | +should use these principles to guide the details of an RFC and decisions to |
| 47 | +move forward. See editor Lee Byron talk about |
| 48 | +[guiding principles at GraphQL Europe 2017](https://youtu.be/mePT9MNTM98?t=17m9s). |
40 | 49 |
|
41 |
| -**Steps**: Start review process. |
| 50 | +* **Backwards compatibility** |
42 | 51 |
|
43 |
| -**Post-Acceptance Changes Expected**: Major. |
| 52 | + Once a query is written, it should always mean the same thing and return the |
| 53 | + same shaped result. Future changes should not change the meaning of existing |
| 54 | + schema or queries or in any other way cause an existing compliant GraphQL |
| 55 | + service to become non-compliant for prior versions of the spec. |
44 | 56 |
|
45 |
| -## Stage 1: Draft |
| 57 | +* **Performance is a feature** |
46 | 58 |
|
47 |
| -**Prerequisite**: |
48 |
| -+ Finalized wording inside specification document. |
49 |
| -+ Proposed spec changes don’t have any blind spots (undescribed edge-cases, |
50 |
| -missed changes to related part of spec, etc). |
| 59 | + GraphQL typically avoids syntax or behaviors which could place burden on |
| 60 | + runtime efficiency or make demands of a GraphQL service it cannot |
| 61 | + efficiently fulfill. |
51 | 62 |
|
52 |
| -**Steps**: Start working on [graphql-js](https://github.com/graphql/graphql-js) |
53 |
| -PR |
| 63 | +* **Favor no change** |
54 | 64 |
|
55 |
| -**Post-Acceptance Changes Expected**: Incremental. |
| 65 | + As GraphQL is implemented in over a dozen languages under the collaboration |
| 66 | + of hundreds of individuals, incorporating any change has a high cost. |
| 67 | + Accordingly, proposed changes must meet a very high bar of added value. |
| 68 | + The burden of proof of value is on the contributor to illustrate this value. |
56 | 69 |
|
57 |
| -## Stage 2: Candidate |
| 70 | +* **Enable new capabilities motivated by real use cases** |
58 | 71 |
|
59 |
| -**Prerequisite**: |
60 |
| -+ Prepared PR for graphql-js. |
61 |
| -+ Notify all members of [GraphQL WG](https://github.com/graphql/graphql-wg). |
62 |
| -+ Community consent on the proposed change. If it’s hard to achieve, add it to |
63 |
| -agenda of the next WG meeting. |
64 |
| -+ No changes to the graphql and graphql-js PRs for at least last 7 days. |
| 72 | + Every change should intend on unlocking a real and reasonable use case. Real |
| 73 | + examples are always more interesting than theoretical ones, and common |
| 74 | + scenarios are more interesting than rare ones. RFCs should do more than offer |
| 75 | + a different way to reach an already achievable outcome. |
65 | 76 |
|
66 |
| -**Steps**: Merge graphql-js PR and release NPM package |
| 77 | +* **Simplicity and consistency over expressiveness and terseness** |
67 | 78 |
|
68 |
| -**Post-Acceptance Changes Expected**: Only those deemed critical based on |
69 |
| -implementation experience. |
| 79 | + There are plenty of behaviors and patterns found in other languages |
| 80 | + intentionally absent from GraphQL. "Possible but awkward" is often favored |
| 81 | + over more complex alternatives. Simplicity (e.g. fewer concepts) is |
| 82 | + more important than expressing more sophisticated ideas or writing less. |
70 | 83 |
|
71 |
| -## Stage 3: Merged |
| 84 | +* **Preserve option value** |
72 | 85 |
|
73 |
| -**Prerequisite**: |
74 |
| -+ At least one month since release of the graphql-js with proposed change. |
75 |
| -+ Community consent on proposed change. If it’s hard to achieve add to agenda of |
76 |
| -the next WG meeting.. |
| 86 | + It's hard to know what the future brings, so whenever possible decisions |
| 87 | + should be made which allow for more options in the future. Sometimes this is |
| 88 | + unintuitive: spec rules often begin more strict than necessary with a future |
| 89 | + option to loosen when motivated by a real use case. |
77 | 90 |
|
78 |
| -**Steps**: Merge PR into “master” branch. |
| 91 | +* **Understandability is just as important as correctness** |
79 | 92 |
|
80 |
| -**Post-Acceptance Changes Expected**: None. |
| 93 | + The GraphQL spec, despite describing technical behavior, is intended to be |
| 94 | + read by people. Use natural tone and include motivation and examples. |
| 95 | + |
| 96 | + |
| 97 | +## RFC Contribution Champions |
| 98 | + |
| 99 | +Contributing to GraphQL requires a lot of dedicated work. To set clear |
| 100 | +expectations and provide accountability, each proposed RFC (request for |
| 101 | +comments) must have a *champion* who is responsible for addressing feedback and |
| 102 | +completing next steps. An RFC may have multiple *champions*. The spec editors |
| 103 | +are not responsible for completing RFCs which lack a *champion* (though an |
| 104 | +editor may be a *champion* for an RFC). |
| 105 | + |
| 106 | +An RFC which does not have a *champion* may not progress through stages, and can |
| 107 | +become stale. Stale proposals may be picked up by a new *champion* or may |
| 108 | +be *rejected*. |
| 109 | + |
| 110 | + |
| 111 | +## RFC Contribution Stages |
| 112 | + |
| 113 | +RFCs are guided by a *champion* through a series of stages: *strawman*, |
| 114 | +*proposal*, *draft*, and *accepted* (or *rejected*), each of which has suggested |
| 115 | +entrance criteria and next steps detailed below. RFCs typically advance one |
| 116 | +stage at a time, however may advance multiple stages at a time. Stage |
| 117 | +advancements typically occur during |
| 118 | +[Working Group](https://github.com/graphql/graphql-wg) meetings, however may |
| 119 | +occur online. |
| 120 | + |
| 121 | +All RFCs start as either a *strawman* or *proposal*. |
| 122 | + |
| 123 | +## Stage 0: *Strawman* |
| 124 | + |
| 125 | +A RFC at the *strawman* stage captures a described problem or |
| 126 | +partially-considered solutions. A *strawman* does not need to meet any entrance |
| 127 | +criteria. A *strawman's* goal is prove or disprove a problem and guide |
| 128 | +discussion towards rejection or a preferred solution. A *strawman* may be an |
| 129 | +issue or a pull request (though an illustrative pull request is preferrable). |
| 130 | + |
| 131 | +*There is no entrance criteria for a Strawman* |
| 132 | + |
| 133 | +As implied by the name [strawman](https://en.wikipedia.org/wiki/Straw_man_proposal), |
| 134 | +the goal at this stage is to knock it down (*reject*) by considering other |
| 135 | +possible related solutions, showing that the motivating problem can be solved |
| 136 | +with no change to the specification, or that it is not aligned with the |
| 137 | +*guiding principles*. |
| 138 | + |
| 139 | +Once determined that the *strawman* is compelling, it should seek the entrance |
| 140 | +criteria for *proposal*. |
| 141 | + |
| 142 | + |
| 143 | +## Stage 1: *Proposal* |
| 144 | + |
| 145 | +An RFC at the *proposal* stage is a solution to a problem with enough fidelity |
| 146 | +to be discussed in detail. It must be backed by a willing *champion*. |
| 147 | +A *proposal*'s goal is to make a compelling case for acceptance by describing |
| 148 | +both the problem and the solution via examples and spec edits. A *proposal* |
| 149 | +should be a pull request. |
| 150 | + |
| 151 | +*Entrance criteria:* |
| 152 | + |
| 153 | +* Identified *champion* |
| 154 | +* Clear explanation of problem and solution |
| 155 | +* Illustrative examples |
| 156 | +* Incomplete spec edits |
| 157 | +* Identification of potential concerns, challenges, and drawbacks |
| 158 | + |
| 159 | +A *proposal* is subject to the same discussion as a *strawman*: ensuring that it |
| 160 | +is well aligned with the *guiding principles*, is a problem worth solving, and |
| 161 | +is the preferred solution to that problem. A *champion* is not expected to have |
| 162 | +confidence in every detail at this stage and should instead focus on identifying |
| 163 | +and resolving issues and edge-cases. To better understand the ramifications of a |
| 164 | +*proposal*, a *champion* is encouraged to implement it in a GraphQL library. |
| 165 | + |
| 166 | +Most *proposals* are expected to evolve or change and may be rejected. Therefore, |
| 167 | +it is unwise to rely on a *proposal* in a production GraphQL service. GraphQL |
| 168 | +libraries *may* implement *proposals*, though are encouraged to not enable the |
| 169 | +*proposal* feature without explicit opt-in. |
| 170 | + |
| 171 | + |
| 172 | +## Stage 2: *Draft* |
| 173 | + |
| 174 | +An RFC at the *draft* stage is a fully formed solution. There is working group |
| 175 | +consensus that the problem identified is worth solving, and this particular |
| 176 | +solution is preferred. A *draft's* goal is to precisely and completely describe |
| 177 | +the solution and resolve any concerns through library implementations. A *draft* |
| 178 | +must be a pull request. |
| 179 | + |
| 180 | +*Entrance criteria* |
| 181 | + |
| 182 | +* Consensus the solution is preferred (typically via Working Group) |
| 183 | +* Resolution of identified concerns and challenges |
| 184 | +* Precisely described with spec edits |
| 185 | +* Compliant implementation in GraphQL.js (via unmerged pull request) |
| 186 | + |
| 187 | +A *proposal* becomes a *draft* when the set of problems or drawbacks have been |
| 188 | +fully considered and accepted or resolved, and the solution is deemed |
| 189 | +desireable. A *draft*'s goal is to complete final spec edits that are ready to |
| 190 | +be merged and implement the *draft* in GraphQL libraries along with tests to |
| 191 | +gain confidence that the spec text is sufficient. |
| 192 | + |
| 193 | +*Drafts* may continue to evolve and change, occasionally dramatically, and are |
| 194 | +not guaranteed to be accepted. Therefore, it is unwise to rely on a *draft* in a |
| 195 | +production GraphQL Service. GraphQL libraries *should* implement *drafts* to |
| 196 | +provide valuable feedback, though are encouraged not to enable the *draft* |
| 197 | +feature without explicit opt-in when possible. |
| 198 | + |
| 199 | + |
| 200 | +## Stage 3: *Accepted* |
| 201 | + |
| 202 | +An RFC at the *accepted* stage is a completed solution. According to a spec |
| 203 | +editor it is ready to be merged as-is into the spec. The RFC is ready to be |
| 204 | +deployed in GraphQL libraries. An *accepted* RFC must be implemented |
| 205 | +in GraphQL.js. |
| 206 | + |
| 207 | +*Entrace criteria* |
| 208 | + |
| 209 | +* Consensus the solution is complete (via editor or working group) |
| 210 | +* Complete spec edits, including examples and prose |
| 211 | +* Compliant implementation in GraphQL.js (fully tested and merged) |
| 212 | + |
| 213 | +A *draft* is *accepted* when it has learned via implementation and tests that it |
| 214 | +appropriately handles all edge cases, that the spec edits do not only precisely |
| 215 | +describe the new syntax and semantics but include motivating prose, examples, |
| 216 | +and include edits to any other affected areas of the spec. Once *accepted*, a |
| 217 | +*champion* should encourage adoption of the RFC by opening issues or pull |
| 218 | +requests on other popular GraphQL libaries. |
| 219 | + |
| 220 | +An *accepted* RFC is merged into the GraphQL spec's master branch by an editor |
| 221 | +and will be included in the next released revision. |
| 222 | + |
| 223 | + |
| 224 | +## Stage X: *Rejected* |
| 225 | + |
| 226 | +An RFC may be *rejected* at any point and for any reason. Most often because a |
| 227 | +*strawman* was proven to be unnecessary, was not aligned with the *guiding |
| 228 | +principles*, or failed to meet the entrance criteria to become a *proposal*. |
| 229 | +A *proposal* may become *rejected* for similar reasons as well as if it fails to |
| 230 | +reach consensus or loses the confidence of its *champion*. Likewise a *draft* |
| 231 | +may encounter unforseen issues during implementions which cause it to lose |
| 232 | +consensus or the confidence of its *champion*. |
| 233 | + |
| 234 | +RFCs which have lost a *champion* will not be *rejected* immediately, but may |
| 235 | +become *rejected* if they fail to attract a new *champion*. |
| 236 | + |
| 237 | +Once *rejected*, an RFC will typically not be reconsidered. Reconsideration is |
| 238 | +possible if a *champion* believes the original reason for rejection no longer |
| 239 | +applies due to new circumstances or new evidence. |
0 commit comments