How to run npm postinstall script only on MacOS

1.1k views Asked by At

How can a postinstall script be restricted to run only on macOS?

I have a shell script inside my React native library and it needs to be started when the npm install has completed.

This works great with postinstall but the problem is that Windows can't execute the shell script.

"scripts": {
  "postinstall": "./iospatch.sh"
},

I need a way to limit that, to only run on macOS.

I tried with this library but it didn't work for my case https://www.npmjs.com/package/cross-os

1

There are 1 answers

2
RobC On

For cross-platform consider redefining your npm script as follows. This ensures that the shell script (.sh) is run only, via the postinstall npm script, when installing your package on macOS.

"scripts": {
  "postinstall": "node -e \"process.platform === 'darwin' && require('child_process').spawn('sh', ['./iospatch.sh'], { stdio: 'inherit'})\""
}

Explanation:

The node -e \"...\" part utilizes the Node.js command line option -e to evaluate the inline JavaScript as follows:

  • process.platform === 'darwin' utilizes the process.platform property to identify the operating system platform. If it equals darwin then it's macOS.

  • The last part on the right-hand side of the && operator;

    require('child_process').spawn('sh', ['./iospatch.sh'], { stdio: 'inherit'})
    

    is executed only if the expression on the left-hand side of the && operator is true, i.e. it only runs if the platform is macOS.

    That part of the code essentially utilizes the child_process.spawn() method to invoke your .sh file. The stdio option is set to inherit to configure the pipes for stdin, stdout, stderr in the child process.

    Also note the command passed to child_process.spawn() is sh and the argument is the file path to the shell script, i.e. ['./iospatch.sh']. We do this to avoid having to set file permissions on macOS so that it can execute iospatch.sh.