From 98d023c7b65065cfaa32d7297eceeb4869ab0fa8 Mon Sep 17 00:00:00 2001 From: Luna Wei Date: Tue, 6 Feb 2024 15:09:21 -0800 Subject: [PATCH] Fix`set-version` to also update `packages/react-native` source (#42897) Summary: Changelog: [Internal] - Update nightly flow to use set-version This change fixes `set-version` to update the `packages/react-native` native source and build files (as `set-rn-version` does) -- this was an oversight but not an issue as `set-version` isn't actually used anywhere right now. Differential Revision: D53463414 --- scripts/releases/README.md | 16 +- .../releases/__tests__/set-rn-version-test.js | 23 +- scripts/releases/set-rn-version.js | 34 +- .../ReactAndroid/gradle.properties | 1 + .../__snapshots__/set-version-test.js.snap | 555 +++++++++++++++++- .../set-version/__tests__/set-version-test.js | 25 +- scripts/releases/set-version/index.js | 45 +- scripts/releases/utils/version-utils.js | 32 +- 8 files changed, 675 insertions(+), 56 deletions(-) create mode 100644 scripts/releases/set-version/__tests__/__fixtures__/packages/react-native/ReactAndroid/gradle.properties diff --git a/scripts/releases/README.md b/scripts/releases/README.md index 9d426897a66745..b0f3417fed72f6 100644 --- a/scripts/releases/README.md +++ b/scripts/releases/README.md @@ -6,14 +6,22 @@ Scripts related to creating a React Native release. These are the lower level en For information on command arguments, run `node --help`. -### `remove-new-arch-flags.js` +### `remove-new-arch-flags` Updates native build files to disable the New Architecture. -### `set-rn-version.js` +### `set-version` + +Sets a singular version for the entire monorepo (including `react-native` package). In detail: +* Update all public npm packages under `/packages` to specified version +* Update all npm dependencies of a `/packages` package to specified version +* Update npm dependencies of the template app (`packages/react-native/template`) to specified version +* Update `packages/react-native` native source and build files to specified version + +### `set-rn-version` Updates relevant files in the `react-native` package and template to materialize the given release version. -### `update-template-package.js` +### `update-template-package` -Updates local dependencies in the template `package.json`. +Updates `/packages` dependencies in the template app`package.json` diff --git a/scripts/releases/__tests__/set-rn-version-test.js b/scripts/releases/__tests__/set-rn-version-test.js index aa3f29f1682edf..92a6a9682b03f3 100644 --- a/scripts/releases/__tests__/set-rn-version-test.js +++ b/scripts/releases/__tests__/set-rn-version-test.js @@ -24,14 +24,23 @@ jest.mock('fs', () => ({ jest.mock('./../update-template-package', () => updateTemplatePackageMock); const {setReactNativeVersion} = require('../set-rn-version'); +const path = require('path'); + +const REPO_ROOT = path.resolve(__filename, '../../../..'); describe('setReactNativeVersion', () => { beforeAll(() => { - readFileMock.mockImplementation(path => { - if (path === 'packages/react-native/ReactAndroid/gradle.properties') { + readFileMock.mockImplementation(filePath => { + if ( + filePath === + path.join( + REPO_ROOT, + 'packages/react-native/ReactAndroid/gradle.properties', + ) + ) { return 'VERSION_NAME=1000.0.0\n'; } - if (path === 'packages/react-native/package.json') { + if (filePath === 'packages/react-native/package.json') { return JSON.stringify({ name: 'react-native', version: '1000.0.0', @@ -60,7 +69,9 @@ describe('setReactNativeVersion', () => { }); for (const [filePath, contents] of writeFileMock.mock.calls) { - expect(formatGeneratedFile(contents)).toMatchSnapshot(filePath); + expect(formatGeneratedFile(contents)).toMatchSnapshot( + path.relative(REPO_ROOT, filePath), + ); } }); @@ -73,7 +84,9 @@ describe('setReactNativeVersion', () => { }); for (const [filePath, contents] of writeFileMock.mock.calls) { - expect(formatGeneratedFile(contents)).toMatchSnapshot(filePath); + expect(formatGeneratedFile(contents)).toMatchSnapshot( + path.relative(REPO_ROOT, filePath), + ); } }); }); diff --git a/scripts/releases/set-rn-version.js b/scripts/releases/set-rn-version.js index 0d89895ee4f2ee..2c8cc4b624cba1 100755 --- a/scripts/releases/set-rn-version.js +++ b/scripts/releases/set-rn-version.js @@ -19,8 +19,13 @@ const updateTemplatePackage = require('./update-template-package'); const {parseVersion, validateBuildType} = require('./utils/version-utils'); const {parseArgs} = require('@pkgjs/parseargs'); const {promises: fs} = require('fs'); +const path = require('path'); -const GRADLE_FILE_PATH = 'packages/react-native/ReactAndroid/gradle.properties'; +const REPO_ROOT = path.join(path.dirname(__filename), '..', '..'); +const GRADLE_FILE_PATH = path.join( + REPO_ROOT, + 'packages/react-native/ReactAndroid/gradle.properties', +); const REACT_NATIVE_PACKAGE_JSON = 'packages/react-native/package.json'; const config = { @@ -101,36 +106,47 @@ async function setReactNativePackageVersion( packageJson.version = version; await fs.writeFile( - 'packages/react-native/package.json', + path.join(REPO_ROOT, 'packages/react-native/package.json'), JSON.stringify(packageJson, null, 2), 'utf-8', ); } -function updateSourceFiles(versionInfo /*: Version */) { +function updateSourceFiles( + versionInfo /*: Version */, +) /*: Promise>*/ { const templateData = {version: versionInfo}; return Promise.all([ fs.writeFile( - 'packages/react-native/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/ReactNativeVersion.java', + path.join( + REPO_ROOT, + 'packages/react-native/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/ReactNativeVersion.java', + ), require('./templates/ReactNativeVersion.java-template')(templateData), ), fs.writeFile( - 'packages/react-native/React/Base/RCTVersion.m', + path.join(REPO_ROOT, 'packages/react-native/React/Base/RCTVersion.m'), require('./templates/RCTVersion.m-template')(templateData), ), fs.writeFile( - 'packages/react-native/ReactCommon/cxxreact/ReactNativeVersion.h', + path.join( + REPO_ROOT, + 'packages/react-native/ReactCommon/cxxreact/ReactNativeVersion.h', + ), require('./templates/ReactNativeVersion.h-template')(templateData), ), fs.writeFile( - 'packages/react-native/Libraries/Core/ReactNativeVersion.js', + path.join( + REPO_ROOT, + 'packages/react-native/Libraries/Core/ReactNativeVersion.js', + ), require('./templates/ReactNativeVersion.js-template')(templateData), ), ]); } -async function updateGradleFile(version /*: string */) { +async function updateGradleFile(version /*: string */) /*: Promise */ { const contents = await fs.readFile(GRADLE_FILE_PATH, 'utf-8'); return fs.writeFile( @@ -141,6 +157,8 @@ async function updateGradleFile(version /*: string */) { module.exports = { setReactNativeVersion, + updateGradleFile, + updateSourceFiles, }; if (require.main === module) { diff --git a/scripts/releases/set-version/__tests__/__fixtures__/packages/react-native/ReactAndroid/gradle.properties b/scripts/releases/set-version/__tests__/__fixtures__/packages/react-native/ReactAndroid/gradle.properties new file mode 100644 index 00000000000000..0b2a27b00a7747 --- /dev/null +++ b/scripts/releases/set-version/__tests__/__fixtures__/packages/react-native/ReactAndroid/gradle.properties @@ -0,0 +1 @@ +VERSION_NAME=1000.0.0 diff --git a/scripts/releases/set-version/__tests__/__snapshots__/set-version-test.js.snap b/scripts/releases/set-version/__tests__/__snapshots__/set-version-test.js.snap index bbf805d8fc4bde..168a014540291c 100644 --- a/scripts/releases/set-version/__tests__/__snapshots__/set-version-test.js.snap +++ b/scripts/releases/set-version/__tests__/__snapshots__/set-version-test.js.snap @@ -1,28 +1,28 @@ // Jest Snapshot v1, https://goo.gl/fbAQLP -exports[`setVersion updates all public packages to version: monorepo-pkg-a 1`] = ` +exports[`setVersion updates monorepo for nightly: packages/monorepo-pkg-a/package.json 1`] = ` "{ \\"name\\": \\"@monorepo/pkg-a\\", - \\"version\\": \\"0.80.0\\", + \\"version\\": \\"0.81.0-nightly-29282302-abcd1234\\", \\"description\\": \\"@monorepo/pkg-a\\", \\"dependencies\\": { - \\"@monorepo/pkg-b\\": \\"0.80.0\\", + \\"@monorepo/pkg-b\\": \\"0.81.0-nightly-29282302-abcd1234\\", \\"@monorepo/other\\": \\"0.0.1\\" }, \\"devDependencies\\": { - \\"@monorepo/pkg-c\\": \\"0.80.0\\" + \\"@monorepo/pkg-c\\": \\"0.81.0-nightly-29282302-abcd1234\\" } } " `; -exports[`setVersion updates all public packages to version: monorepo-pkg-b 1`] = ` +exports[`setVersion updates monorepo for nightly: packages/monorepo-pkg-b/package.json 1`] = ` "{ \\"name\\": \\"@monorepo/pkg-b\\", - \\"version\\": \\"0.80.0\\", + \\"version\\": \\"0.81.0-nightly-29282302-abcd1234\\", \\"description\\": \\"@monorepo/pkg-b\\", \\"dependencies\\": { - \\"@monorepo/pkg-c\\": \\"0.80.0\\", + \\"@monorepo/pkg-c\\": \\"0.81.0-nightly-29282302-abcd1234\\", \\"metro-config\\": \\"^0.80.3\\", \\"metro-runtime\\": \\"^0.80.3\\" } @@ -30,10 +30,10 @@ exports[`setVersion updates all public packages to version: monorepo-pkg-b 1`] = " `; -exports[`setVersion updates all public packages to version: monorepo-pkg-c 1`] = ` +exports[`setVersion updates monorepo for nightly: packages/monorepo-pkg-c/package.json 1`] = ` "{ \\"name\\": \\"@monorepo/pkg-c\\", - \\"version\\": \\"0.80.0\\", + \\"version\\": \\"0.81.0-nightly-29282302-abcd1234\\", \\"description\\": \\"@monorepo/pkg-c\\", \\"dependencies\\": { \\"metro-config\\": \\"^0.80.3\\", @@ -43,15 +43,534 @@ exports[`setVersion updates all public packages to version: monorepo-pkg-c 1`] = " `; -exports[`setVersion updates all public packages to version: react-native 1`] = ` +exports[`setVersion updates monorepo for nightly: packages/react-native/Libraries/Core/ReactNativeVersion.js 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @flow strict + * @generated by scripts/releases/set-rn-version.js + */ + +const version: $ReadOnly<{ + major: number, + minor: number, + patch: number, + prerelease: string | null, +}> = { + major: 0, + minor: 81, + patch: 0, + prerelease: 'nightly-29282302-abcd1234', +}; + +module.exports = {version}; +" +`; + +exports[`setVersion updates monorepo for nightly: packages/react-native/React/Base/RCTVersion.m 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +#import \\"RCTVersion.h\\" + +NSString* const RCTVersionMajor = @\\"major\\"; +NSString* const RCTVersionMinor = @\\"minor\\"; +NSString* const RCTVersionPatch = @\\"patch\\"; +NSString* const RCTVersionPrerelease = @\\"prerelease\\"; + + +NSDictionary* RCTGetReactNativeVersion(void) +{ + static NSDictionary* __rnVersion; + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^(void){ + __rnVersion = @{ + RCTVersionMajor: @(0), + RCTVersionMinor: @(81), + RCTVersionPatch: @(0), + RCTVersionPrerelease: @\\"nightly-29282302-abcd1234\\", + }; + }); + return __rnVersion; +} +" +`; + +exports[`setVersion updates monorepo for nightly: packages/react-native/ReactAndroid/gradle.properties 1`] = ` +"VERSION_NAME=0.81.0-nightly-29282302-abcd1234 +" +`; + +exports[`setVersion updates monorepo for nightly: packages/react-native/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/ReactNativeVersion.java 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +package com.facebook.react.modules.systeminfo; + +import com.facebook.react.common.MapBuilder; + +import java.util.Map; + +public class ReactNativeVersion { + public static final Map VERSION = MapBuilder.of( + \\"major\\", 0, + \\"minor\\", 81, + \\"patch\\", 0, + \\"prerelease\\", \\"nightly-29282302-abcd1234\\"); +} +" +`; + +exports[`setVersion updates monorepo for nightly: packages/react-native/ReactCommon/cxxreact/ReactNativeVersion.h 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +#pragma once + +#include +#include + +namespace facebook::react { + +constexpr struct { + int32_t Major = 0; + int32_t Minor = 81; + int32_t Patch = 0; + std::string_view Prerelease = \\"nightly-29282302-abcd1234\\"; +} ReactNativeVersion; + +} // namespace facebook::react +" +`; + +exports[`setVersion updates monorepo for nightly: packages/react-native/package.json 1`] = ` +"{ + \\"name\\": \\"react-native\\", + \\"version\\": \\"0.81.0-nightly-29282302-abcd1234\\", + \\"description\\": \\"fake react native package\\", + \\"dependencies\\": { + \\"@monorepo/pkg-a\\": \\"0.81.0-nightly-29282302-abcd1234\\", + \\"@monorepo/pkg-b\\": \\"0.81.0-nightly-29282302-abcd1234\\", + \\"@monorepo/pkg-c\\": \\"0.81.0-nightly-29282302-abcd1234\\", + \\"metro-config\\": \\"^0.80.3\\", + \\"metro-runtime\\": \\"^0.80.3\\" + } +} +" +`; + +exports[`setVersion updates monorepo for nightly: packages/react-native/template/package.json 1`] = ` +"{ + \\"name\\": \\"react-native-test-template\\", + \\"version\\": \\"0.0.1\\", + \\"private\\": true, + \\"dependencies\\": { + \\"react\\": \\"18.2.0\\", + \\"react-native\\": \\"0.81.0-nightly-29282302-abcd1234\\" + }, + \\"devDependencies\\": { + \\"@monorepo/pkg-a\\": \\"0.81.0-nightly-29282302-abcd1234\\", + \\"@monorepo/pkg-c\\": \\"0.81.0-nightly-29282302-abcd1234\\", + \\"@types/react\\": \\"^18.2.6\\", + \\"@types/react-test-renderer\\": \\"^18.0.0\\" + } +} +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/monorepo-pkg-a/package.json 1`] = ` +"{ + \\"name\\": \\"@monorepo/pkg-a\\", + \\"version\\": \\"0.80.0-rc.3\\", + \\"description\\": \\"@monorepo/pkg-a\\", + \\"dependencies\\": { + \\"@monorepo/pkg-b\\": \\"0.80.0-rc.3\\", + \\"@monorepo/other\\": \\"0.0.1\\" + }, + \\"devDependencies\\": { + \\"@monorepo/pkg-c\\": \\"0.80.0-rc.3\\" + } +} +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/monorepo-pkg-b/package.json 1`] = ` +"{ + \\"name\\": \\"@monorepo/pkg-b\\", + \\"version\\": \\"0.80.0-rc.3\\", + \\"description\\": \\"@monorepo/pkg-b\\", + \\"dependencies\\": { + \\"@monorepo/pkg-c\\": \\"0.80.0-rc.3\\", + \\"metro-config\\": \\"^0.80.3\\", + \\"metro-runtime\\": \\"^0.80.3\\" + } +} +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/monorepo-pkg-c/package.json 1`] = ` +"{ + \\"name\\": \\"@monorepo/pkg-c\\", + \\"version\\": \\"0.80.0-rc.3\\", + \\"description\\": \\"@monorepo/pkg-c\\", + \\"dependencies\\": { + \\"metro-config\\": \\"^0.80.3\\", + \\"metro-runtime\\": \\"^0.80.3\\" + } +} +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/react-native/Libraries/Core/ReactNativeVersion.js 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @flow strict + * @generated by scripts/releases/set-rn-version.js + */ + +const version: $ReadOnly<{ + major: number, + minor: number, + patch: number, + prerelease: string | null, +}> = { + major: 0, + minor: 80, + patch: 0, + prerelease: 'rc.3', +}; + +module.exports = {version}; +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/react-native/React/Base/RCTVersion.m 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +#import \\"RCTVersion.h\\" + +NSString* const RCTVersionMajor = @\\"major\\"; +NSString* const RCTVersionMinor = @\\"minor\\"; +NSString* const RCTVersionPatch = @\\"patch\\"; +NSString* const RCTVersionPrerelease = @\\"prerelease\\"; + + +NSDictionary* RCTGetReactNativeVersion(void) +{ + static NSDictionary* __rnVersion; + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^(void){ + __rnVersion = @{ + RCTVersionMajor: @(0), + RCTVersionMinor: @(80), + RCTVersionPatch: @(0), + RCTVersionPrerelease: @\\"rc.3\\", + }; + }); + return __rnVersion; +} +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/react-native/ReactAndroid/gradle.properties 1`] = ` +"VERSION_NAME=0.80.0-rc.3 +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/react-native/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/ReactNativeVersion.java 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +package com.facebook.react.modules.systeminfo; + +import com.facebook.react.common.MapBuilder; + +import java.util.Map; + +public class ReactNativeVersion { + public static final Map VERSION = MapBuilder.of( + \\"major\\", 0, + \\"minor\\", 80, + \\"patch\\", 0, + \\"prerelease\\", \\"rc.3\\"); +} +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/react-native/ReactCommon/cxxreact/ReactNativeVersion.h 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +#pragma once + +#include +#include + +namespace facebook::react { + +constexpr struct { + int32_t Major = 0; + int32_t Minor = 80; + int32_t Patch = 0; + std::string_view Prerelease = \\"rc.3\\"; +} ReactNativeVersion; + +} // namespace facebook::react +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/react-native/package.json 1`] = ` +"{ + \\"name\\": \\"react-native\\", + \\"version\\": \\"0.80.0-rc.3\\", + \\"description\\": \\"fake react native package\\", + \\"dependencies\\": { + \\"@monorepo/pkg-a\\": \\"0.80.0-rc.3\\", + \\"@monorepo/pkg-b\\": \\"0.80.0-rc.3\\", + \\"@monorepo/pkg-c\\": \\"0.80.0-rc.3\\", + \\"metro-config\\": \\"^0.80.3\\", + \\"metro-runtime\\": \\"^0.80.3\\" + } +} +" +`; + +exports[`setVersion updates monorepo for release-candidate: packages/react-native/template/package.json 1`] = ` +"{ + \\"name\\": \\"react-native-test-template\\", + \\"version\\": \\"0.0.1\\", + \\"private\\": true, + \\"dependencies\\": { + \\"react\\": \\"18.2.0\\", + \\"react-native\\": \\"0.80.0-rc.3\\" + }, + \\"devDependencies\\": { + \\"@monorepo/pkg-a\\": \\"0.80.0-rc.3\\", + \\"@monorepo/pkg-c\\": \\"0.80.0-rc.3\\", + \\"@types/react\\": \\"^18.2.6\\", + \\"@types/react-test-renderer\\": \\"^18.0.0\\" + } +} +" +`; + +exports[`setVersion updates monorepo for stable version: packages/monorepo-pkg-a/package.json 1`] = ` +"{ + \\"name\\": \\"@monorepo/pkg-a\\", + \\"version\\": \\"0.80.1\\", + \\"description\\": \\"@monorepo/pkg-a\\", + \\"dependencies\\": { + \\"@monorepo/pkg-b\\": \\"0.80.1\\", + \\"@monorepo/other\\": \\"0.0.1\\" + }, + \\"devDependencies\\": { + \\"@monorepo/pkg-c\\": \\"0.80.1\\" + } +} +" +`; + +exports[`setVersion updates monorepo for stable version: packages/monorepo-pkg-b/package.json 1`] = ` +"{ + \\"name\\": \\"@monorepo/pkg-b\\", + \\"version\\": \\"0.80.1\\", + \\"description\\": \\"@monorepo/pkg-b\\", + \\"dependencies\\": { + \\"@monorepo/pkg-c\\": \\"0.80.1\\", + \\"metro-config\\": \\"^0.80.3\\", + \\"metro-runtime\\": \\"^0.80.3\\" + } +} +" +`; + +exports[`setVersion updates monorepo for stable version: packages/monorepo-pkg-c/package.json 1`] = ` +"{ + \\"name\\": \\"@monorepo/pkg-c\\", + \\"version\\": \\"0.80.1\\", + \\"description\\": \\"@monorepo/pkg-c\\", + \\"dependencies\\": { + \\"metro-config\\": \\"^0.80.3\\", + \\"metro-runtime\\": \\"^0.80.3\\" + } +} +" +`; + +exports[`setVersion updates monorepo for stable version: packages/react-native/Libraries/Core/ReactNativeVersion.js 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @flow strict + * @generated by scripts/releases/set-rn-version.js + */ + +const version: $ReadOnly<{ + major: number, + minor: number, + patch: number, + prerelease: string | null, +}> = { + major: 0, + minor: 80, + patch: 1, + prerelease: null, +}; + +module.exports = {version}; +" +`; + +exports[`setVersion updates monorepo for stable version: packages/react-native/React/Base/RCTVersion.m 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +#import \\"RCTVersion.h\\" + +NSString* const RCTVersionMajor = @\\"major\\"; +NSString* const RCTVersionMinor = @\\"minor\\"; +NSString* const RCTVersionPatch = @\\"patch\\"; +NSString* const RCTVersionPrerelease = @\\"prerelease\\"; + + +NSDictionary* RCTGetReactNativeVersion(void) +{ + static NSDictionary* __rnVersion; + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^(void){ + __rnVersion = @{ + RCTVersionMajor: @(0), + RCTVersionMinor: @(80), + RCTVersionPatch: @(1), + RCTVersionPrerelease: [NSNull null], + }; + }); + return __rnVersion; +} +" +`; + +exports[`setVersion updates monorepo for stable version: packages/react-native/ReactAndroid/gradle.properties 1`] = ` +"VERSION_NAME=0.80.1 +" +`; + +exports[`setVersion updates monorepo for stable version: packages/react-native/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/ReactNativeVersion.java 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +package com.facebook.react.modules.systeminfo; + +import com.facebook.react.common.MapBuilder; + +import java.util.Map; + +public class ReactNativeVersion { + public static final Map VERSION = MapBuilder.of( + \\"major\\", 0, + \\"minor\\", 80, + \\"patch\\", 1, + \\"prerelease\\", null); +} +" +`; + +exports[`setVersion updates monorepo for stable version: packages/react-native/ReactCommon/cxxreact/ReactNativeVersion.h 1`] = ` +"/** + * Copyright (c) Meta Platforms, Inc. and affiliates. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + * + * @generated by scripts/releases/set-rn-version.js + */ + +#pragma once + +#include +#include + +namespace facebook::react { + +constexpr struct { + int32_t Major = 0; + int32_t Minor = 80; + int32_t Patch = 1; + std::string_view Prerelease = \\"\\"; +} ReactNativeVersion; + +} // namespace facebook::react +" +`; + +exports[`setVersion updates monorepo for stable version: packages/react-native/package.json 1`] = ` "{ \\"name\\": \\"react-native\\", - \\"version\\": \\"0.80.0\\", + \\"version\\": \\"0.80.1\\", \\"description\\": \\"fake react native package\\", \\"dependencies\\": { - \\"@monorepo/pkg-a\\": \\"0.80.0\\", - \\"@monorepo/pkg-b\\": \\"0.80.0\\", - \\"@monorepo/pkg-c\\": \\"0.80.0\\", + \\"@monorepo/pkg-a\\": \\"0.80.1\\", + \\"@monorepo/pkg-b\\": \\"0.80.1\\", + \\"@monorepo/pkg-c\\": \\"0.80.1\\", \\"metro-config\\": \\"^0.80.3\\", \\"metro-runtime\\": \\"^0.80.3\\" } @@ -59,18 +578,18 @@ exports[`setVersion updates all public packages to version: react-native 1`] = ` " `; -exports[`setVersion updates all public packages to version: template 1`] = ` +exports[`setVersion updates monorepo for stable version: packages/react-native/template/package.json 1`] = ` "{ \\"name\\": \\"react-native-test-template\\", \\"version\\": \\"0.0.1\\", \\"private\\": true, \\"dependencies\\": { \\"react\\": \\"18.2.0\\", - \\"react-native\\": \\"0.80.0\\" + \\"react-native\\": \\"0.80.1\\" }, \\"devDependencies\\": { - \\"@monorepo/pkg-a\\": \\"0.80.0\\", - \\"@monorepo/pkg-c\\": \\"0.80.0\\", + \\"@monorepo/pkg-a\\": \\"0.80.1\\", + \\"@monorepo/pkg-c\\": \\"0.80.1\\", \\"@types/react\\": \\"^18.2.6\\", \\"@types/react-test-renderer\\": \\"^18.0.0\\" } diff --git a/scripts/releases/set-version/__tests__/set-version-test.js b/scripts/releases/set-version/__tests__/set-version-test.js index c30ffcd1c9dfeb..8d26a91f970e55 100644 --- a/scripts/releases/set-version/__tests__/set-version-test.js +++ b/scripts/releases/set-version/__tests__/set-version-test.js @@ -28,17 +28,30 @@ describe('setVersion', () => { return { ...originalFs, - writeFileSync: (packagePath, content) => { - expect(content).toMatchSnapshot( - path.basename(path.join(packagePath, '..')), - ); + promises: { + ...originalFs.promises, + writeFile: (filePath, content) => { + expect(content).toMatchSnapshot( + path.relative(path.join(__dirname, '__fixtures__'), filePath), + ); + }, }, }; }); }); - test('updates all public packages to version', () => { - setVersion('0.80.0'); + + test('updates monorepo for release-candidate', async () => { + await setVersion('0.80.0-rc.3'); + }); + + test('updates monorepo for stable version', async () => { + await setVersion('0.80.1'); }); + + test('updates monorepo for nightly', async () => { + await setVersion('0.81.0-nightly-29282302-abcd1234'); + }); + afterAll(() => { jest.unmock('path'); jest.unmock('fs'); diff --git a/scripts/releases/set-version/index.js b/scripts/releases/set-version/index.js index a0cdeee814effb..021f6e94f73695 100644 --- a/scripts/releases/set-version/index.js +++ b/scripts/releases/set-version/index.js @@ -12,7 +12,9 @@ 'use strict'; const forEachPackage = require('../../monorepo/for-each-package'); -const {readFileSync, writeFileSync} = require('fs'); +const {updateGradleFile, updateSourceFiles} = require('../set-rn-version'); +const {getBuildType, parseVersion} = require('../utils/version-utils'); +const {promises: fs, readFileSync} = require('fs'); const path = require('path'); const yargs = require('yargs'); @@ -30,8 +32,9 @@ function getPublicPackages() { return packages; } -function setVersion(version /*: string */) { +function updatePackages(version /*: string */) { const publicPackages = getPublicPackages(); + const writes = []; forEachPackage( (packageAbsolutePath, _, packageJson) => { @@ -57,10 +60,12 @@ function setVersion(version /*: string */) { } } - writeFileSync( - path.join(packageAbsolutePath, 'package.json'), - JSON.stringify(packageJson, null, 2) + '\n', - 'utf-8', + writes.push( + fs.writeFile( + path.join(packageAbsolutePath, 'package.json'), + JSON.stringify(packageJson, null, 2) + '\n', + 'utf-8', + ), ); // Update template package.json @@ -92,18 +97,29 @@ function setVersion(version /*: string */) { } } } - writeFileSync( - templatePackageJsonPath, - JSON.stringify(templatePackageJson, null, 2) + '\n', - 'utf-8', + writes.push( + fs.writeFile( + templatePackageJsonPath, + JSON.stringify(templatePackageJson, null, 2) + '\n', + 'utf-8', + ), ); } }, {includeReactNative: true}, ); + + return Promise.all(writes); } -module.exports = setVersion; +async function setVersion(version /*: string */) { + const buildType = getBuildType(version); + const parsedVersion = parseVersion(version, buildType); + + await updateSourceFiles(parsedVersion); + await updateGradleFile(parsedVersion.version); + await updatePackages(parsedVersion.version); +} if (require.main === module) { const {toVersion} = yargs(process.argv.slice(2)) @@ -118,5 +134,10 @@ if (require.main === module) { }), ) .parseSync(); - setVersion(toVersion); + setVersion(toVersion).then( + () => process.exit(0), + () => process.exit(1), + ); } + +module.exports = setVersion; diff --git a/scripts/releases/utils/version-utils.js b/scripts/releases/utils/version-utils.js index 5eb34d2d5eac90..6d1e8c0fe54025 100644 --- a/scripts/releases/utils/version-utils.js +++ b/scripts/releases/utils/version-utils.js @@ -43,10 +43,16 @@ function parseVersion( throw new Error(`Unsupported build type: ${buildType}`); } + const parsedVersion = _parse(versionStr); + validateVersion(parsedVersion, buildType); + return parsedVersion; +} + +function _parse(versionStr /*: string */) /*: Version */ { const match = extractMatchIfValid(versionStr); const [, version, major, minor, patch, prerelease] = match; - const versionObject = { + const parsedVersion = { version, major, minor, @@ -54,9 +60,28 @@ function parseVersion( prerelease, }; - validateVersion(versionObject, buildType); + return parsedVersion; +} + +function getBuildType(version /*: string */) /*: BuildType */ { + const parsedVersion = _parse(version); + if (isNightly(parsedVersion)) { + return 'nightly'; + } + + if (isStableRelease(parsedVersion) || isStablePrerelease(parsedVersion)) { + return 'release'; + } + + if (isMain(parsedVersion)) { + return 'dry-run'; + } + + if (isValidPrealpha(parsedVersion)) { + return 'prealpha'; + } - return versionObject; + throw new Error(`Version ${version} is not a valid`); } function validateBuildType( @@ -186,4 +211,5 @@ module.exports = { isMain, isStableRelease, isStablePrerelease, + getBuildType, };