Skip to content

Commit bee7375

Browse files
authored
Merge pull request #1141 from Quick-Box/fix-macos-bundle
fix: macos bundling
2 parents 847f82c + b5bf538 commit bee7375

3 files changed

Lines changed: 84 additions & 29 deletions

File tree

.github/workflows/macos.yml

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -61,10 +61,11 @@ jobs:
6161
-qmldir='${{ github.workspace }}/quickevent/app/quickevent/plugins' \
6262
-always-overwrite
6363
64-
- name: Fix qsqlmon Qt framework paths
64+
- name: Fix bundle linking
6565
run: |
66-
chmod +x '${{ github.workspace }}/tools/macos-fix-qsqlmon.sh'
67-
'${{ github.workspace }}/tools/macos-fix-qsqlmon.sh' '${{ github.workspace }}/install/quickevent.app'
66+
chmod +x '${{ github.workspace }}/tools/macos-bundle-fix.sh'
67+
'${{ github.workspace }}/tools/macos-bundle-fix.sh' \
68+
'${{ github.workspace }}/install/quickevent.app'
6869
6970
- name: Code sign the app
7071
run: |

tools/macos-bundle-fix.sh

Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
#!/bin/bash
2+
# Fix app bundle linking after macdeployqt:
3+
# - Repoints Qt framework paths in all bundle binaries
4+
# - Copies Homebrew libraries into Frameworks/ and fixes their paths (recursively)
5+
# Usage: ./tools/macos-bundle-fix.sh [bundle-path]
6+
7+
set -euo pipefail
8+
9+
BUNDLE="${1:-install/quickevent.app}"
10+
11+
if [[ ! -d "$BUNDLE" ]]; then
12+
echo "ERROR: bundle not found: $BUNDLE"
13+
exit 1
14+
fi
15+
16+
FRAMEWORKS="$BUNDLE/Contents/Frameworks"
17+
mkdir -p "$FRAMEWORKS"
18+
19+
fix_binary() {
20+
local binary="$1"
21+
local binname; binname=$(basename "$binary")
22+
23+
# otool -L is the macOS equivalent of ldd; tail -n +2 skips the header line.
24+
otool -L "$binary" 2>/dev/null | tail -n +2 | awk '{print $1}' | sort -u | while read -r dep; do
25+
26+
# Unlike ldd, otool -L lists the library's own install name (SONAME
27+
# equivalent) as the first entry — skip it to avoid self-bundling.
28+
[[ "$(basename "$dep")" == "$binname" ]] && continue
29+
30+
case "$dep" in
31+
@*|/usr/lib/*|/System/*)
32+
# @executable_path/… etc. are bundle-relative dyld tokens — already correct.
33+
# /usr/lib and /System are macOS system libs present on every machine.
34+
;;
35+
*/Qt*.framework/*/Qt*)
36+
# Qt uses macOS framework bundles: Name.framework/Versions/A/Name.
37+
# Rewrite leftover absolute Qt install paths to bundle-relative ones.
38+
local fw; fw=$(basename "$dep")
39+
install_name_tool -change "$dep" \
40+
"@executable_path/../Frameworks/$fw.framework/Versions/A/$fw" \
41+
"$binary"
42+
;;
43+
/*)
44+
# Third-party absolute path (Homebrew, Postgres.app, …) —
45+
# macdeployqt ignores these, so we copy them into the bundle.
46+
local lib; lib=$(basename "$dep")
47+
local src="$dep"
48+
49+
# Build-time path may not exist here (e.g. Postgres.app on CI);
50+
# fall back to searching Homebrew by filename.
51+
if [[ ! -f "$src" ]]; then
52+
src=$(find /opt/homebrew /usr/local \( -type f -o -type l \) -name "$lib" 2>/dev/null | head -1)
53+
if [[ -z "$src" ]]; then
54+
echo " WARNING: $lib not found, skipping"
55+
continue
56+
fi
57+
fi
58+
59+
if [[ ! -f "$FRAMEWORKS/$lib" ]]; then
60+
echo " Bundling $lib"
61+
cp "$src" "$FRAMEWORKS/$lib"
62+
chmod 755 "$FRAMEWORKS/$lib"
63+
install_name_tool -id "@executable_path/../Frameworks/$lib" \
64+
"$FRAMEWORKS/$lib" # -id sets own install name (SONAME)
65+
fix_binary "$FRAMEWORKS/$lib" # recurse for transitive deps
66+
fi
67+
68+
install_name_tool -change "$dep" \
69+
"@executable_path/../Frameworks/$lib" "$binary"
70+
;;
71+
esac
72+
done
73+
}
74+
75+
echo "Fixing bundle: $BUNDLE"
76+
# macdeployqt only fixes the main executable; process all binaries in MacOS/.
77+
find "$BUNDLE/Contents/MacOS" -maxdepth 1 -type f | while read -r f; do fix_binary "$f"; done
78+
# Process all dylibs: plugins, frameworks, QML modules.
79+
find "$BUNDLE/Contents" -name "*.dylib" | while read -r f; do fix_binary "$f"; done
80+
echo "Done"

tools/macos-fix-qsqlmon.sh

Lines changed: 0 additions & 26 deletions
This file was deleted.

0 commit comments

Comments
 (0)