Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

point react gradle config to monorepo #44901

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
155 changes: 74 additions & 81 deletions packages/core-cli-utils/src/private/android.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,117 +12,110 @@
import type {Task} from './types';
import type {ExecaPromise} from 'execa';

import {isWindows, task, toPascalCase} from './utils';
import {isWindows, task} from './utils';
import execa from 'execa';

type AndroidBuildMode = 'debug' | 'release';
type AndroidBuildMode = 'Debug' | 'Release';

type AndroidBuild = {
sourceDir: string,
appName: string,
type Path = string;
type Args = $ReadOnlyArray<string>;

type Config = {
cwd: Path,
hermes?: boolean,
mode: AndroidBuildMode,
gradleArgs?: Array<string>,
name: string,
newArchitecture?: boolean,
sdk?: Path,
};

function gradle(cwd: string, ...args: string[]): ExecaPromise {
function gradle(
taskName: string,
args: Args,
options: {cwd: string, env?: {[k: string]: string | void}},
): ExecaPromise {
const gradlew = isWindows ? 'gradlew.bat' : './gradlew';
return execa(gradlew, args, {
cwd,
stdio: 'inherit',
return execa(gradlew, [taskName, ...args], {
cwd: options.cwd,
env: options.env,
});
}

//
// Gradle Task wrappers
//

/**
* Assembles an Android app using Gradle
*/
export const assemble = (
cwd: string,
appName: string,
mode: AndroidBuildMode,
...args: $ReadOnlyArray<string>
): ExecaPromise =>
gradle(cwd, `${appName}:assemble${toPascalCase(mode)}`, ...args);

/**
* Assembles and tests an Android app using Gradle
*/
export const build = (
cwd: string,
appName: string,
mode: AndroidBuildMode,
...args: $ReadOnlyArray<string>
): ExecaPromise =>
gradle(cwd, `${appName}:build${toPascalCase(mode)}`, ...args);

/**
* Installs an Android app using Gradle
*/
export const install = (
cwd: string,
appName: string,
mode: AndroidBuildMode,
...args: $ReadOnlyArray<string>
): ExecaPromise =>
gradle(cwd, `${appName}:install${toPascalCase(mode)}`, ...args);
function androidSdkPath(sdk?: string): string {
return sdk ?? process.env.ANDROID_HOME ?? process.env.ANDROID_SDK ?? '';
}

/**
* Runs a custom Gradle task if your frameworks needs aren't handled by assemble, build or install.
*/
export const customTask = (
cwd: string,
customTaskName: string,
...args: $ReadOnlyArray<string>
): ExecaPromise => gradle(cwd, customTaskName, ...args);
function boolToStr(value: boolean): string {
return value ? 'true' : 'false';
}

const FIRST = 1;

//
// Android Tasks
//
type AndroidTasks = {
assemble: (
options: AndroidBuild,
...args: $ReadOnlyArray<string>
) => {run: Task<ExecaPromise>},
build: (
options: AndroidBuild,
...args: $ReadOnlyArray<string>
) => {run: Task<ExecaPromise>},
install: (
options: AndroidBuild,
...args: $ReadOnlyArray<string>
) => {run: Task<ExecaPromise>},
};

export const tasks: AndroidTasks = {
assemble: (options: AndroidBuild, ...gradleArgs: $ReadOnlyArray<string>) => ({
run: task(FIRST, 'Assemble Android App', () =>
assemble(options.sourceDir, options.appName, options.mode, ...gradleArgs),
),
export const tasks = (
config: Config,
): ({
assemble: (...gradleArgs: Args) => {
run: Task<ExecaPromise>,
},
build: (...gradleArgs: Args) => {
run: Task<ExecaPromise>,
},
install: (...gradleArgs: Args) => {
run: Task<ExecaPromise>,
},
}) => ({
assemble: (...gradleArgs: Args) => ({
run: task(FIRST, 'Assemble Android App', () => {
const args = [];
if (config.hermes != null) {
args.push(`-PhermesEnabled=${boolToStr(config.hermes)}`);
}
if (config.newArchitecture != null) {
args.push(`-PnewArchEnabled=${boolToStr(config.newArchitecture)}`);
}
args.push(...gradleArgs);
return gradle(`${config.name}:assemble${config.mode}`, gradleArgs, {
cwd: config.cwd,
env: {ANDROID_HOME: androidSdkPath(config.sdk)},
});
}),
}),
build: (options: AndroidBuild, ...gradleArgs: $ReadOnlyArray<string>) => ({
run: task(FIRST, 'Assembles and tests Android App', () =>
build(options.sourceDir, options.appName, options.mode, ...gradleArgs),
),
build: (...gradleArgs: Args) => ({
run: task(FIRST, 'Assembles and tests Android App', () => {
const args = [];
if (config.hermes != null) {
args.push(`-PhermesEnabled=${boolToStr(config.hermes)}`);
}
if (config.newArchitecture != null) {
args.push(`-PnewArchEnabled=${boolToStr(config.newArchitecture)}`);
}
args.push(...gradleArgs);
return gradle(`${config.name}:bundle${config.mode}`, args, {
cwd: config.cwd,
env: {ANDROID_HOME: androidSdkPath(config.sdk)},
});
}),
}),
/**
* Useful extra gradle arguments:
*
* -PreactNativeDevServerPort=8081 sets the port for the installed app to point towards a Metro
* server on (for example) 8081.
*/
install: (options: AndroidBuild, ...gradleArgs: $ReadOnlyArray<string>) => ({
install: (...gradleArgs: Args) => ({
run: task(FIRST, 'Installs the assembled Android App', () =>
install(options.sourceDir, options.appName, options.mode, ...gradleArgs),
gradle(`${config.name}:install${config.mode}`, gradleArgs, {
cwd: config.cwd,
env: {ANDROID_HOME: androidSdkPath(config.sdk)},
}),
),
}),

// We are not supporting launching the app and setting up the tunnel for metro <-> app, this is
// a framework concern. For an example of how one could do this, please look at the community
// CLI's code:
// https://github.com/react-native-community/cli/blob/54d48a4e08a1aef334ae6168788e0157a666b4f5/packages/cli-platform-android/src/commands/runAndroid/index.ts#L272C1-L290C2
};
});
24 changes: 16 additions & 8 deletions packages/helloworld/android/app/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -9,21 +9,24 @@ apply plugin: "com.android.application"
apply plugin: "org.jetbrains.kotlin.android"
apply plugin: "com.facebook.react"

// Build a simple config (instead of depending on npx @react-native-communtiy/cli config).
def generatedConfig = file("../../.react-native.config").getText().replaceAll("HELLOWORLD_PATH", project.file("../../").absolutePath)

/**
* This is the configuration block to customize your React Native Android app.
* By default you don't need to apply any configuration, just uncomment the lines you need.
*/
react {
/* Folders */
// The root of your project, i.e. where "package.json" lives. Default is '..'
// root = file("../")
root = file("../")
// The folder where the react-native NPM package is. Default is ../node_modules/react-native
// reactNativeDir = file("../node_modules/react-native")
reactNativeDir = file("../../../react-native")
// The folder where the react-native Codegen package is. Default is ../node_modules/@react-native/codegen
// codegenDir = file("../node_modules/@react-native/codegen")
// The cli.js file which is the React Native CLI entrypoint. Default is ../node_modules/react-native/cli.js
// cliFile = file("../node_modules/react-native/cli.js")

codegenDir = file("../../../react-native-codegen")
// The cli.js file which is the React Native CLI entrypoint. Default is ../node_modules/react-native/cli.js,
// but now points to our simplified bundle wrapper.
cliFile = file("../../scripts/bundle.js")
/* Variants */
// The list of variants to that are debuggable. For those we're going to
// skip the bundling of the JS bundle and the assets. By default is just 'debug'.
Expand All @@ -34,8 +37,9 @@ react {
// A list containing the node command and its flags. Default is just 'node'.
// nodeExecutableAndArgs = ["node"]
//
// The command to run when bundling. By default is 'bundle'
// bundleCommand = "ram-bundle"
// The command to run when bundling. By default is 'bundle', but since we're calling out simplified bundle
// wrapper we need this to be empty.
bundleCommand = ""
//
// The path to the CLI configuration file. Default is empty.
// bundleConfig = file(../rn-cli.config.js)
Expand All @@ -49,6 +53,10 @@ react {
// A list of extra flags to pass to the 'bundle' commands.
// See https://github.com/react-native-community/cli/blob/main/docs/commands.md#bundle
// extraPackagerArgs = []
extraPackagerArgs = [
"--load-config",
generatedConfig
]

/* Hermes Commands */
// The hermes compiler command to run. By default it is 'hermesc'
Expand Down