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

Fix dylib linking for Mac app bundles #12711

Open
wants to merge 3 commits into
base: dev
Choose a base branch
from

Conversation

shi-yan
Copy link
Contributor

@shi-yan shi-yan commented Feb 16, 2025

Problem

Currently, Tauri allows packaging additional .dylib libraries and frameworks, but it does not fix their linking in the final bundled app.

For example, in my case, I use the rust-opencv library, which links to OpenCV libraries installed via Homebrew:

/opt/homebrew/opt/opencv/lib/libopencv_imgcodecs.411.dylib (compatibility version 411.0.0, current version 4.11.0)
/opt/homebrew/opt/opencv/lib/libopencv_imgproc.411.dylib (compatibility version 411.0.0, current version 4.11.0)
/opt/homebrew/opt/opencv/lib/libopencv_core.411.dylib (compatibility version 411.0.0, current version 4.11.0)

While Tauri can bundle these .dylib files, it does not adjust the binary to correctly reference them. If I deploy my app to another computer without these libraries, the app crashes. Worse, if the new system has a different version of the library installed, the app will also crash due to version mismatches.

Solution

To fix this, I added an additional bundling step that:

  1. Updates the binary to reference the bundled .dylib files using @rpath.
  2. Updates the .dylib files themselves to use @rpath instead of absolute paths.
  3. Ensures the app binary has the correct rpath to locate the bundled libraries in Contents/Frameworks.

This mirrors what the following Bash script does manually:

# Define paths
APP_BUNDLE="/xxx/src-tauri/target/release/bundle/macos/xxx.app"
BINARY="$APP_BUNDLE/Contents/MacOS/xxx"
FRAMEWORKS="$APP_BUNDLE/Contents/Frameworks"

# List of dylibs to update
DYLIBS=(
    "libopencv_core.411.dylib"
    "libopencv_imgcodecs.411.dylib"
    "libopencv_imgproc.411.dylib"
)

# Update binary to reference bundled dylibs
for dylib in "${DYLIBS[@]}"; do
    install_name_tool -change "/opt/homebrew/opt/opencv/lib/$dylib" "@rpath/$dylib" "$BINARY"
done

# Set install_name for each dylib
for dylib in "${DYLIBS[@]}"; do
    install_name_tool -id "@rpath/$dylib" "$FRAMEWORKS/$dylib"
done

# Ensure binary can find dylibs in Contents/Frameworks
install_name_tool -add_rpath "@executable_path/../Frameworks" "$BINARY"

# Verify changes
echo "Updated binary dependencies:"
otool -L "$BINARY"

codesign --force --deep --sign - "$APP_BUNDLE"

Since this script needs to run before generating the .dmg file, I added an extra step in Tauri’s bundling process to automate it.

Issue

To control whether this step runs, I introduced a new configuration option:

"fixDylibLinking": true

By default, this option is false to avoid breaking existing setups.

However, when testing locally with cargo tauri build, I encountered the following error:

  unknown field `fixDylibLinking`, expected one of `frameworks`, `files`, `minimum-system-version`, `minimumSystemVersion`, `exception-domain`, `exceptionDomain`, `signing-identity`, `signingIdentity`, `hardened-runtime`, `hardenedRuntime`, `provider-short-name`, `providerShortName`, `entitlements`, `dmg`
  found an unknown configuration field. This usually means that you are using a CLI version that is newer than `tauri-build` and is incompatible. Please try updating the Rust crates by running `cargo update` in the Tauri app folder.

Do you know a way to workaround this error?

@shi-yan shi-yan requested a review from a team as a code owner February 16, 2025 03:29
Copy link
Contributor

Package Changes Through b4cdbc7

There are 8 changes which include tauri-cli with minor, tauri-runtime with minor, tauri-runtime-wry with minor, tauri-utils with minor, tauri with minor, @tauri-apps/api with minor, @tauri-apps/cli with minor, tauri-bundler with patch

Planned Package Versions

The following package releases are the planned based on the context of changes in this pull request.

package current next
@tauri-apps/api 2.2.0 2.3.0
tauri-utils 2.1.1 2.2.0
tauri-bundler 2.2.3 2.2.4
tauri-runtime 2.3.0 2.4.0
tauri-runtime-wry 2.3.0 2.4.0
tauri-codegen 2.0.4 2.0.5
tauri-macros 2.0.4 2.0.5
tauri-plugin 2.0.4 2.0.5
tauri-build 2.0.5 2.0.6
tauri 2.2.5 2.3.0
@tauri-apps/cli 2.2.7 2.3.0
tauri-cli 2.2.7 2.3.0

Add another change file through the GitHub UI by following this link.


Read about change files or the docs at github.com/jbolda/covector

@FabianLars
Copy link
Member

Do you know a way to workaround this error?

Make sure to point tauri and tauri-build in cargo.toml to your fork and install tauri-cli from it as well to properly test config changes.

@shi-yan
Copy link
Contributor Author

shi-yan commented Feb 16, 2025

I have tested it. as it turned out, I need to swap a whole tree of tauri dependencies, including all plugins used. But the PR seems to work.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants