You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: proposals/0012-introduce-reactNativeMetadata.md
+51-7
Original file line number
Diff line number
Diff line change
@@ -27,6 +27,8 @@ This new section will allow developers to follow a declarative approach to expre
27
27
28
28
The need to specify **capabilities and metadata** for a react-native library is inherent to the React Native ecosystem. This need is so evident that various frameworks provided their own ways to specify those values. Look at `react-native.config.js` for the CLI or `app.json` for Expo.
29
29
30
+
Notice that we do not expect that frameworks stop using those files to configure **framework-specific** settings. What we would like to enforce with this proposal is to have single source of truth for what concern the React Native core settings.
31
+
30
32
Another issue is that, as of today, there is no simple programmatic way to know if a NPM package is a React Native library.
31
33
We have some heuristics, though:
32
34
* Presence of a `react-native:*` dependency in the `peerDependencies` section of the `package.json` ([example](https://github.com/RonRadtke/react-native-blob-util/blob/80628d418a5c81439dc2c1a1f05fae6406f0ba7f/package.json#L46C10-L49))
@@ -43,7 +45,7 @@ While we can continue to build tooling that tries to infer metadata and capabili
43
45
We suggest to provide a declarative way to describe such capabilities.
44
46
This approach would yield several benefits:
45
47
***predictability**: developers can easily understand what a library is capable of doing and if such capability matches their app.
46
-
***tooling**: tooling can easily consume this information and provide a better experience to developers.
48
+
***tooling**: tooling can easily consume this information and provide a better experience to developers. For example, we could tailor `microsoft/rnx-kit`'s align-deps tool to consume this information to help users double-check whether all their dependencies are supporting the New Architecture. See [`align-deps` support](#align-deps) below
47
49
***single source of thruth**: a single manifest will act as a source of truth for all those capabilities and flag definition, that can easily be consumed by different platforms to provide a unified way to enable/disable capabilities.
48
50
***verifiability**: the manifest can be easily verified and linted by tooling to ensure that apps and libraries are not using an incompatible set of dependencies. Similarly, the JSON schema we publish can be used to validate the `reactNativeManifest` section.
49
51
@@ -147,6 +149,22 @@ The precedence rules are that platform-specific settings override general settin
147
149
148
150
would means that, in general, the app/library support the New Architecture, but not for Android.
149
151
152
+
##### Planning forward: what happen when the New Architecture will be the default?
153
+
154
+
The manifest is versioned, and we will use the versioning system to track breaking changes and different semantics.
155
+
156
+
For version `1.0.0` the semantic would be:
157
+
*`newArchitecture` default value set to `false`
158
+
159
+
In a future version, let's say `K.0.0`, the semantic would be:
160
+
*`newArchitecture` default value set to `true`
161
+
*`newArchitecture` field deprecated
162
+
163
+
In a more future version, let's say `N.0.0`, the semantic would be:
164
+
*`newArchitecture` field removed, together with the Old Architecture code.
165
+
166
+
Notice that this system can also help us to track unmaintained/old packages: they would either not have the manifest at all or have old version of the manifest with its version's semantic.
167
+
150
168
#### `codegenConfig` support
151
169
152
170
Similarly to the New Architecture support metadata, the `codegenConfig` is a key metadata of the New Architecture build pipeline.
@@ -170,7 +188,7 @@ We propose to move this key under the `reactNativeManifest.capabilites` section
170
188
}
171
189
```
172
190
173
-
### Hermes Support
191
+
####Hermes Support
174
192
175
193
Similarly to the New Architecture support, the current way to enable/disable the Hermes engine is toggled by using a Gradle Property `hermesEnabled` on Android and changing the `:hermes_enabled` property in the Podfile.
176
194
@@ -236,7 +254,7 @@ The precedence rules are that platform-specific settings override general settin
236
254
237
255
would means that the app will run with Hermes for all the platforms it supports but not for Android.
238
256
239
-
### React Native Release feature flagging
257
+
####React Native Release feature flagging
240
258
241
259
We currently have a number of different files where capabilities of React Native can be toggled to enable/disable features in the runtime.
242
260
For example we have:
@@ -252,6 +270,32 @@ We propose to define `reactNativeManifest` as the **preferred entry point** for
252
270
253
271
It's outside the scope of this RFC to declare all the new sections we intend to add, and we defer to the [Future proof and extensibility](#future-proof-and-extensibility) section for the process on how to include a new key to the `reactNativeManifest` section.
254
272
273
+
#### Out-of-Tree Platforms
274
+
275
+
Although this proposal does not cover directly out-of-tree platforms, we strongly suggests maintainers of out-of-tree platforms to follow the same path.
276
+
277
+
Tools written on top of the React Native Manifest would be able to work with iOS, Android and all the out of tree platforms that they support. They should follow the same precedence rules: if there is no platform specified, then the main flag would take precedence. If there is a platform specified, then that platform setup would have precedence.
278
+
279
+
So, for example, given the manifest:
280
+
281
+
```json
282
+
{
283
+
"reactNativeManifest": {
284
+
"windows": {
285
+
"capabilities": {
286
+
"hermes": {
287
+
"enabled": false
288
+
}
289
+
}
290
+
},
291
+
}
292
+
}
293
+
```
294
+
295
+
It means that for all the platforms but Windows, React Native will use Hermes as JS engine (`hermes.enabled` default value is `true`). For Windows specifically, it would be disabled.
296
+
297
+
As an extra note, please be careful to **follow the same semantics** as the React Native Core: in this way we can avoid confusion for our users.
298
+
255
299
## Excluded use cases
256
300
257
301
This section lists the use cases where we believe the `reactNativeManifest` section should **not** be used.
@@ -279,7 +323,7 @@ Build tools such as Gradle/CocoaPods or others should account for the `reactNati
279
323
1. If the two values are **incompatible**, notify the user and use the value specified in the `reactNativeManifest.capabilities.foo` section will prevail and the value specified in the build tool specific configuration will be ignored.
280
324
1. If the capability `foo` is **not** specificed in the `reactNativeManifest.capabilities` section, honor the value specified in the build tool specific configuration or the default value if not specified.
281
325
282
-
### `align-deps` support
326
+
### <aname="align-deps"></a>`align-deps` support
283
327
284
328
This RFC originated from a [conversation between Meta and Microsoft](https://github.com/microsoft/rnx-kit/issues/1863) to use `align-deps` as key feature in the New Architecture rollout support, in helping developers understand if a library they're using is compatible with the New Architecture or not. Very quickly it became clear that there is currently no straightforward way to know if a library indeed has that support.
285
329
@@ -294,9 +338,9 @@ It's outside the scope of this RFC to delve into details of which tool will impl
294
338
295
339
### React Native Directory
296
340
297
-
The React Native direcotry can easily consume the `reactNativeManifest` by:
341
+
The React Native directory can easily consume the `reactNativeManifest` by:
298
342
1. Query the NPM registry with [their API](https://github.com/npm/registry/blob/master/docs/REGISTRY-API.md) to obtain the repository information.
299
-
2. Query the repository information to obtain the `packge.json` and read the `reactNativeManifest` section.
343
+
2. Query the repository information to obtain the `packge.json` and read the `reactNativeManifest` section. By putting these configurations in the package.json, React Native Directory can fetch only this file, rather than downloading the whole package and crawling its files.
300
344
301
345
## Future proof and extensibility
302
346
@@ -384,7 +428,7 @@ Ideally, we'll start by adding the `reactNativeManifest` section to the app temp
384
428
385
429
We foresee a phase in which only a part of the user base has this section configured, and tool and developers need to account for the absence of this section.
386
430
387
-
Once the v1.0.0 version of the shape is finalised, we can start integrating it across the board in various tools mentioned in [Proposed Tooling](#proposed-tooling) section. This first wave of support would have to be aligned around a given React Native release, say in 0.73 (which branch has not been cut).
431
+
Once the v1.0.0 version of the shape is finalised, we can start integrating it across the board in various tools mentioned in [Proposed Tooling](#proposed-tooling) section. This first wave of support would have to be aligned around a given React Native release, say in 0.74 (which branch has not been cut).
388
432
389
433
After adding this first wave of support, and related documentation, we could more broadly communicate to the community and the maintainers how adding this section would benefit them too.
0 commit comments