Merge pull request #11341 from vector-im/jryans/feature-flag-process

Document feature flag process
This commit is contained in:
J. Ryan Stinnett 2019-11-08 17:58:33 +02:00 committed by GitHub
commit 2db876d12c
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 116 additions and 3 deletions

View file

@ -22,9 +22,10 @@ For a good example, see https://riot.im/develop/config.json.
`default_hs_url` is specified. When multiple sources are specified, it is unclear
which should take priority and therefore the application cannot continue.
* As of Riot 1.4.0, identity servers are optional. See [Identity servers](#identity-servers) below.
1. `features`: Lookup of optional features that may be `enable`d, `disable`d, or exposed to the user
in the `labs` section of settings. The available optional experimental features vary from
release to release. The available features are described in [labs.md](labs.md).
1. `features`: Lookup of optional features that may be `enable`d, `disable`d, or
exposed to the user in the `labs` section of settings. The available
optional experimental features vary from release to release and are [documented](labs.md). The feature flag process is
[documented](feature-flags.md) as well.
1. `showLabsSettings`: Shows the "labs" tab of user settings even when no `features` are enabled
or present. Useful for getting at settings which may be otherwise hidden.
1. `brand`: String to pass to your homeserver when configuring email notifications, to let the

112
docs/feature-flags.md Normal file
View file

@ -0,0 +1,112 @@
# Feature flags
When developing new features for Riot, we use feature flags to give us more
flexibility and control over when and where those features are enabled.
For example, flags make the following things possible:
* Extended testing of a feature via labs on develop
* Enabling features when ready instead of the first moment the code is released
* Testing a feature with a specific set of users (by enabling only on a specific
Riot instance)
The size of the feature controlled by a feature flag may vary widely: it could
be a large project like reactions or a smaller change to an existing algorithm.
A large project might use several feature flags if it's useful to control the
deployment of different portions independently.
Everyone involved in a feature (engineering, design, product, reviewers) should
think about its deployment plan up front as best as possible so we can have the
right feature flags in place from the start.
## Interaction with spec process
Historically, we have often used feature flags to guard client features that
depend on unstable spec features. Unfortunately, there was never clear agreement
about how long such a flag should live for, when it should be removed, etc.
Under the [new spec
process](https://github.com/matrix-org/matrix-doc/pull/2324), server-side
unstable features can be used by clients and enabled by default as long as
clients commit to doing the associated clean up work once a feature stabilises.
## Starting work on a feature
When starting work on a feature, we should create a matching feature flag:
1. Add a new
[setting](https://github.com/matrix-org/matrix-react-sdk/blob/develop/src/settings/Settings.js)
of the form:
```js
"feature_cats": {
isFeature: true,
displayName: _td("Adds cats everywhere"),
supportedLevels: LEVELS_FEATURE,
default: false,
},
```
2. Check whether the feature is enabled as appropriate:
```js
SettingsStore.isFeatureEnabled("feature_cats")
```
3. Add the feature to the [set of labs on develop](https://github.com/vector-im/riot-web/blob/develop/riot.im/develop/config.json):
```json
"features": {
"feature_cats": "labs"
},
```
4. Document the feature in the [labs documentation](https://github.com/vector-im/riot-web/blob/develop/docs/labs.md)
With these steps completed, the feature is disabled by default, but can be
enabled on develop by interested users for testing.
Different features may have different deployment plans for when to enable where.
The following lists a few common options.
## Enabling by default on develop
Set the feature to `enable` in the [develop config](https://github.com/vector-im/riot-web/blob/develop/riot.im/develop/config.json):
```json
"features": {
"feature_cats": "enable"
},
```
## Enabling by default on staging and app
Set the feature to `enable` in the [app
config](https://github.com/vector-im/riot-web/blob/develop/riot.im/app/config.json).
## Feature deployed successfully
Once we're confident that a feature is working well, we should remove the flag:
1. Remove the [setting](https://github.com/matrix-org/matrix-react-sdk/blob/develop/src/settings/Settings.js)
2. Remove all `isFeatureEnabled` lines that test for the feature's setting
3. Remove the feature from the [labs documentation](https://github.com/vector-im/riot-web/blob/develop/docs/labs.md)
4. Remove feature state from
[develop](https://github.com/vector-im/riot-web/blob/develop/riot.im/develop/config.json)
and [app](https://github.com/vector-im/riot-web/blob/develop/riot.im/app/config.json)
configs
5. Celebrate! 🥳
## Convert to a regular setting (optional)
Sometimes we decide a feature should always be user-controllable as a setting
even after it has been fully deployed. In that case, we would craft a new,
regular setting:
1. Remove the feature flag from
[settings](https://github.com/matrix-org/matrix-react-sdk/blob/develop/src/settings/Settings.js)
and add a regular setting with the appropriate levels for your feature
2. Replace the `isFeatureEnabled` lines with `getValue` or similar calls
according to the [settings
docs](https://github.com/matrix-org/matrix-react-sdk/blob/develop/docs/settings.md)
(checking carefully, as we may want a different mix of code paths when the
feature is always present but gated by a setting)
3. Remove the feature from the [labs documentation](https://github.com/vector-im/riot-web/blob/develop/docs/labs.md)
4. Remove feature state from
[develop](https://github.com/vector-im/riot-web/blob/develop/riot.im/develop/config.json)
and [app](https://github.com/vector-im/riot-web/blob/develop/riot.im/app/config.json)
configs