From 0d67ff020564fe96829843f87ac9b03936f52a0c Mon Sep 17 00:00:00 2001 From: "Shah, Ankur" Date: Sat, 25 Apr 2026 16:40:59 -0500 Subject: [PATCH] Added a code to build proper AppImage for Linux --- .github/workflows/gui-publish.yml | 64 +++++++++++++++++---------- build/package-linux-appimage.sh | 69 ++++++++++++++++++++++++++++++ build/package-macos-app.sh | 63 +++++++++++++++++++++++++++ src/Csv2Ofx.Gui/Csv2Ofx.Gui.csproj | 3 ++ 4 files changed, 177 insertions(+), 22 deletions(-) create mode 100644 build/package-linux-appimage.sh create mode 100644 build/package-macos-app.sh diff --git a/.github/workflows/gui-publish.yml b/.github/workflows/gui-publish.yml index 1d310dd..668e92d 100644 --- a/.github/workflows/gui-publish.yml +++ b/.github/workflows/gui-publish.yml @@ -1,8 +1,6 @@ name: GUI Publish on: -# push: -# tags: [ "v*" ] release: types: [ published ] @@ -32,7 +30,7 @@ jobs: publish-gui: needs: test - runs-on: ubuntu-latest + runs-on: ${{ matrix.os }} permissions: contents: read actions: write @@ -41,13 +39,21 @@ jobs: matrix: include: - rid: linux-x64 - artifact: csv2ofx-gui-linux-x64 + os: ubuntu-latest + package: appimage + artifact: csv2ofx-gui-linux-x64-package - rid: osx-x64 - artifact: csv2ofx-gui-osx-x64 + os: macos-latest + package: macos-app + artifact: csv2ofx-gui-osx-x64-package - rid: osx-arm64 - artifact: csv2ofx-gui-osx-arm64 + os: macos-latest + package: macos-app + artifact: csv2ofx-gui-osx-arm64-package - rid: win-x64 - artifact: csv2ofx-gui-win-x64 + os: ubuntu-latest + package: zip + artifact: csv2ofx-gui-win-x64-package steps: - uses: actions/checkout@v4 - name: Setup .NET @@ -75,21 +81,35 @@ jobs: -p:IncludeNativeLibrariesForSelfExtract=true \ -p:EnableCompressionInSingleFile=true \ -p:Version=${{ env.VERSION }} \ - -o "artifacts/${{ matrix.artifact }}" - - name: Archive artifact + -o "artifacts/publish/${{ matrix.rid }}" + - name: Package Linux AppImage + if: matrix.package == 'appimage' + run: | + chmod +x build/package-linux-appimage.sh + build/package-linux-appimage.sh \ + "artifacts/publish/${{ matrix.rid }}" \ + "artifacts/packages" \ + "${{ env.VERSION }}" + - name: Package macOS app bundle + if: matrix.package == 'macos-app' + run: | + chmod +x build/package-macos-app.sh + build/package-macos-app.sh \ + "artifacts/publish/${{ matrix.rid }}" \ + "artifacts/packages" \ + "${{ matrix.rid }}" \ + "${{ env.VERSION }}" + - name: Package Windows zip + if: matrix.package == 'zip' run: | - cd artifacts - zip -r "${{ matrix.artifact }}-${{ env.VERSION }}.zip" "${{ matrix.artifact }}" - - name: Upload folder artifact + mkdir -p artifacts/packages + cd artifacts/publish/${{ matrix.rid }} + zip -r ../../packages/Csv2Ofx-${{ env.VERSION }}-${{ matrix.rid }}.zip . + - name: Upload packaged artifact uses: actions/upload-artifact@v4 with: name: ${{ matrix.artifact }} - path: artifacts/${{ matrix.artifact }}/ - - name: Upload zip artifact - uses: actions/upload-artifact@v4 - with: - name: ${{ matrix.artifact }}-zip - path: artifacts/${{ matrix.artifact }}-${{ env.VERSION }}.zip + path: artifacts/packages/* release: needs: publish-gui @@ -115,9 +135,9 @@ jobs: with: tag_name: ${{ github.ref_name }} files: | - artifacts/csv2ofx-gui-linux-x64-zip/csv2ofx-gui-linux-x64-${{ env.VERSION }}.zip - artifacts/csv2ofx-gui-osx-x64-zip/csv2ofx-gui-osx-x64-${{ env.VERSION }}.zip - artifacts/csv2ofx-gui-osx-arm64-zip/csv2ofx-gui-osx-arm64-${{ env.VERSION }}.zip - artifacts/csv2ofx-gui-win-x64-zip/csv2ofx-gui-win-x64-${{ env.VERSION }}.zip + artifacts/csv2ofx-gui-linux-x64-package/Csv2Ofx-${{ env.VERSION }}-linux-x64.AppImage + artifacts/csv2ofx-gui-osx-x64-package/Csv2Ofx-${{ env.VERSION }}-osx-x64.app.zip + artifacts/csv2ofx-gui-osx-arm64-package/Csv2Ofx-${{ env.VERSION }}-osx-arm64.app.zip + artifacts/csv2ofx-gui-win-x64-package/Csv2Ofx-${{ env.VERSION }}-win-x64.zip env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} diff --git a/build/package-linux-appimage.sh b/build/package-linux-appimage.sh new file mode 100644 index 0000000..b7adf6e --- /dev/null +++ b/build/package-linux-appimage.sh @@ -0,0 +1,69 @@ +#!/usr/bin/env bash +set -euo pipefail + +if [ "$#" -ne 3 ]; then + echo "Usage: $0 " >&2 + exit 1 +fi + +PUBLISH_DIR="$(cd "$1" && pwd)" +OUTPUT_DIR="$(mkdir -p "$2" && cd "$2" && pwd)" +VERSION="$3" + +APP_NAME="Csv2Ofx" +EXECUTABLE="Csv2Ofx.Gui" +APP_ID="com.csv2ofx.gui" +APPDIR="$OUTPUT_DIR/$APP_NAME.AppDir" +APPIMAGE_TOOL="$OUTPUT_DIR/appimagetool-x86_64.AppImage" +APPIMAGE_PATH="$OUTPUT_DIR/$APP_NAME-$VERSION-linux-x64.AppImage" + +rm -rf "$APPDIR" +mkdir -p \ + "$APPDIR/usr/bin" \ + "$APPDIR/usr/share/applications" \ + "$APPDIR/usr/share/icons/hicolor/scalable/apps" + +cp -a "$PUBLISH_DIR/." "$APPDIR/usr/bin/" +chmod +x "$APPDIR/usr/bin/$EXECUTABLE" + +cat > "$APPDIR/AppRun" < "$APPDIR/$APP_ID.desktop" < "$APPDIR/csv2ofx.svg" <<'EOF' + + + + + + +EOF +cp "$APPDIR/csv2ofx.svg" "$APPDIR/usr/share/icons/hicolor/scalable/apps/csv2ofx.svg" +ln -s "csv2ofx.svg" "$APPDIR/.DirIcon" + +if [ ! -x "$APPIMAGE_TOOL" ]; then + curl -L \ + "https://github.com/AppImage/AppImageKit/releases/download/continuous/appimagetool-x86_64.AppImage" \ + -o "$APPIMAGE_TOOL" + chmod +x "$APPIMAGE_TOOL" +fi + +rm -f "$APPIMAGE_PATH" +ARCH=x86_64 APPIMAGE_EXTRACT_AND_RUN=1 "$APPIMAGE_TOOL" "$APPDIR" "$APPIMAGE_PATH" +chmod +x "$APPIMAGE_PATH" diff --git a/build/package-macos-app.sh b/build/package-macos-app.sh new file mode 100644 index 0000000..8eaa6b5 --- /dev/null +++ b/build/package-macos-app.sh @@ -0,0 +1,63 @@ +#!/usr/bin/env bash +set -euo pipefail + +if [ "$#" -ne 4 ]; then + echo "Usage: $0 " >&2 + exit 1 +fi + +PUBLISH_DIR="$(cd "$1" && pwd)" +OUTPUT_DIR="$(mkdir -p "$2" && cd "$2" && pwd)" +RID="$3" +VERSION="$4" + +APP_NAME="Csv2Ofx" +EXECUTABLE="Csv2Ofx.Gui" +BUNDLE_ID="com.csv2ofx.gui" +APP_BUNDLE="$OUTPUT_DIR/$APP_NAME.app" +ZIP_PATH="$OUTPUT_DIR/$APP_NAME-$VERSION-$RID.app.zip" + +rm -rf "$APP_BUNDLE" "$ZIP_PATH" +mkdir -p "$APP_BUNDLE/Contents/MacOS" "$APP_BUNDLE/Contents/Resources" + +cp -a "$PUBLISH_DIR/." "$APP_BUNDLE/Contents/MacOS/" +chmod +x "$APP_BUNDLE/Contents/MacOS/$EXECUTABLE" + +cat > "$APP_BUNDLE/Contents/Info.plist" < + + + + CFBundleExecutable + $EXECUTABLE + CFBundleIdentifier + $BUNDLE_ID + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + $APP_NAME + CFBundleDisplayName + $APP_NAME + CFBundlePackageType + APPL + CFBundleShortVersionString + $VERSION + CFBundleVersion + $VERSION + LSMinimumSystemVersion + 10.15 + NSHighResolutionCapable + + + +EOF + +if command -v codesign >/dev/null 2>&1; then + codesign --force --deep --sign - "$APP_BUNDLE" +fi + +if command -v ditto >/dev/null 2>&1; then + ditto -c -k --sequesterRsrc --keepParent "$APP_BUNDLE" "$ZIP_PATH" +else + (cd "$OUTPUT_DIR" && zip -r "$(basename "$ZIP_PATH")" "$(basename "$APP_BUNDLE")") +fi diff --git a/src/Csv2Ofx.Gui/Csv2Ofx.Gui.csproj b/src/Csv2Ofx.Gui/Csv2Ofx.Gui.csproj index ec40047..54f0c1b 100644 --- a/src/Csv2Ofx.Gui/Csv2Ofx.Gui.csproj +++ b/src/Csv2Ofx.Gui/Csv2Ofx.Gui.csproj @@ -1,8 +1,11 @@ + Csv2Ofx.Gui WinExe net8.0 + linux-x64;osx-x64;osx-arm64;win-x64 + true enable enable