Using MTP on macOS with Node.js: Part 7

Feature image

Yesterday I described the issue and options surrounding distributing libmtp as part of my node-mtp module. Basically, I don't need to distribute it on Linux as it's already available on most distro's, but it's not available by default on macOS without requiring the user to run brew install libmtp.

I think I have finally found a solution. Looking at the sodium-native post-install script I noticed that they're using the install_name_tool to tell the binaries where to look for their dynamically linked library. The full path is hard-coded into the binary, and you can view the shared libraries used using otool -L <filename>.

The easiest place to edit the linked library paths would be after the Node module is built, but before the prebuilds are generated, so I added the following to the before_deploy step in Travis:

if [ $TRAVIS_OS_NAME = osx ]; then
  cp "$TRAVIS_BUILD_DIR/lib/libmtp.dylib" "$TRAVIS_BUILD_DIR/prebuilds/darwin-x64/";
  install_name_tool -change "/usr/local/opt/libmtp/lib/libmtp.9.dylib" "@loader_path/libmtp.dylib" "$TRAVIS_BUILD_DIR/prebuilds/darwin-x64/node-napi.node";
  otool -L "$TRAVIS_BUILD_DIR/prebuilds/darwin-x64/node-napi.node";
fi

So, if we're building on macOS, we copy the shared library libmtp.dylib into the prebuilds folder and then change the shared library path in our node-napi.node[1] module to point to that file. I also run otool just so that we can check that the path was changed correctly.


  1. our module that is generated by prebuildify --napi ↩︎