Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Different package.json dependencies in React Native flavors

Tags:

react-native

I have two flavors of the same Android application built in React Native (Lite and Pro).
I am able to inject specific variables in the app and gradle flavors, so I can have the two apps behaving differently at runtime.

However, the two flavors end up including the same modules from the same package.json even if one of the two flavors doesn't have all the functionalities and therefore doesn't need all the modules and the permissions set by manifest merger.

Is there a way to include/exclude the modules during the build phase without having to duplicate everything?

To give an example: the Lite version doesn't need the camera, but because I'm including react-native-camera into my package.json, the Lite version ends up requiring the camera permission even if it doesn't use it.

like image 204
pasine Avatar asked Apr 11 '26 17:04

pasine


1 Answers

To manage different dependencies and permissions for your lite and pro flavors in an RN application without duplication. You can follow this step:

Use different package.json files. Something like package-lite.json package-pro.json. Then, add a postinstall script in your main package.json to copy the correct package.json based on the environment variable:

{
  "scripts": {
    "postinstall": "node ./scripts/set-package.js",
    "install-lite": "npm install && npm run postinstall",
    "install-pro": "npm install && npm run postinstall"
  }
}

Create a `scripts` folder and add a `set-package.js` file:

const fs = require('fs');
const path = require('path');

const flavor = process.env.FLAVOR;

if (flavor === 'lite') {
  fs.copyFileSync(path.join(__dirname, '../package-lite.json'), path.join(__dirname, '../package.json'));
} else if (flavor === 'pro') {
  fs.copyFileSync(path.join(__dirname, '../package-pro.json'), path.join(__dirname, '../package.json'));
}

Run the appropriate install script based on the flavor:
FLAVOR=lite npm run install-lite
FLAVOR=pro npm run install-pro

Run the appropriate script to install dependencies for the desired flavor:
npm run install-lite
npm run install-pro

Create a script install-with-overrides.js to merge dependencies and install them without modifying the main package.json.

`scripts/install-with-overrides.js`

const { execSync } = require('child_process');
const fs = require('fs');
const path = require('path');

const flavor = process.env.FLAVOR;

if (!flavor) {
  console.error('FLAVOR environment variable is not set');
  process.exit(1);
}

const mainPackageJson = require('../package.json');
const flavorPackageJsonPath = path.join(__dirname, `../package-${flavor}.json`);

if (!fs.existsSync(flavorPackageJsonPath)) {
  console.error(`Flavor-specific package.json not found at ${flavorPackageJsonPath}`);
  process.exit(1);
}

const flavorPackageJson = require(flavorPackageJsonPath);

const mergedDependencies = {
  ...mainPackageJson.dependencies,
  ...flavorPackageJson.dependencies,
};

const mergedPackageJson = {
  ...mainPackageJson,
  dependencies: mergedDependencies,
};

fs.writeFileSync(
  path.join(__dirname, '../temp-package.json'),
  JSON.stringify(mergedPackageJson, null, 2)
);

try {
  execSync('npm install --no-save', { stdio: 'inherit' });
} finally {
  fs.unlinkSync(path.join(__dirname, '../temp-package.json'));
}

Let me know if it helps or we could look at another solution.

like image 170
Lanre Avatar answered Apr 21 '26 02:04

Lanre



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!