mirror of
https://github.com/KRTirtho/spotube.git
synced 2025-09-13 07:55:18 +00:00
refactor: Dart based Github Workflow CLI (#1490)
* feat: add build dart script for windows * feat: add android build support * feat: add linux build support * feat: add macos build support * feat: add ios build support * feat: add deps install command and workflow file * cd: what? * cd: what? * cd: what? * cd: update workflow inputs * cd: replace release binary * cd: run flutter pub get * cd: use dpkg zstd instead of xz, windows disable innoInstall, fix channel enum.name and reset pubspec after changing build no for nightly * cd: fix tar copy path * cd: fix copy linux command * cd: fix windows inno depend and fix android aab path * cd: idk * cd: linux why??? * cd: windows choco copy failed * cd: use dart tar archive for creating tar file * cd: fix linux file copy error * cd: use tar command directly * feat: add linux_arm platform * cd: add linux_arm platform * cd: don't know what? * feat: notification about nightly channel update * chore: fix some errors parsing nightly version info
This commit is contained in:
parent
4ca893950b
commit
a77b6776e8
@ -9,3 +9,6 @@ ENABLE_UPDATE_CHECK=
|
|||||||
|
|
||||||
LASTFM_API_KEY=
|
LASTFM_API_KEY=
|
||||||
LASTFM_API_SECRET=
|
LASTFM_API_SECRET=
|
||||||
|
|
||||||
|
# Release channel. Can be: nightly, stable
|
||||||
|
RELEASE_CHANNEL=
|
||||||
|
8
.github/Dockerfile
vendored
8
.github/Dockerfile
vendored
@ -10,14 +10,10 @@ COPY . .
|
|||||||
|
|
||||||
RUN chown -R $(whoami) /app
|
RUN chown -R $(whoami) /app
|
||||||
|
|
||||||
RUN flutter pub get &&\
|
RUN flutter pub get
|
||||||
flutter config --enable-linux-desktop &&\
|
|
||||||
flutter pub get &&\
|
|
||||||
dart run build_runner build --delete-conflicting-outputs
|
|
||||||
|
|
||||||
RUN alias dpkg-deb="dpkg-deb --Zxz" &&\
|
RUN alias dpkg-deb="dpkg-deb --Zxz" &&\
|
||||||
flutter_distributor package --platform=linux --targets=deb
|
flutter_distributor package --platform=linux --targets=deb --skip-clean
|
||||||
|
|
||||||
|
|
||||||
RUN make tar VERSION=${BUILD_VERSION} ARCH=arm64 PKG_ARCH=aarch64
|
RUN make tar VERSION=${BUILD_VERSION} ARCH=arm64 PKG_ARCH=aarch64
|
||||||
|
|
||||||
|
519
.github/workflows/spotube-release-binary.yml
vendored
519
.github/workflows/spotube-release-binary.yml
vendored
@ -2,296 +2,65 @@ name: Spotube Release Binary
|
|||||||
on:
|
on:
|
||||||
workflow_dispatch:
|
workflow_dispatch:
|
||||||
inputs:
|
inputs:
|
||||||
version:
|
|
||||||
description: Version to release (x.x.x)
|
|
||||||
default: 3.6.0
|
|
||||||
required: true
|
|
||||||
channel:
|
channel:
|
||||||
type: choice
|
type: choice
|
||||||
description: Release Channel
|
|
||||||
required: true
|
|
||||||
options:
|
options:
|
||||||
- stable
|
- stable
|
||||||
- nightly
|
- nightly
|
||||||
default: nightly
|
default: nightly
|
||||||
|
description: The release channel
|
||||||
debug:
|
debug:
|
||||||
description: Debug on failed when channel is nightly
|
|
||||||
required: true
|
|
||||||
type: boolean
|
type: boolean
|
||||||
default: false
|
default: false
|
||||||
|
description: Debug with SSH toggle
|
||||||
|
required: false
|
||||||
dry_run:
|
dry_run:
|
||||||
description: Dry run
|
|
||||||
required: true
|
|
||||||
type: boolean
|
type: boolean
|
||||||
default: true
|
default: false
|
||||||
|
description: Dry run without uploading to release
|
||||||
|
|
||||||
env:
|
env:
|
||||||
FLUTTER_VERSION: '3.19.5'
|
FLUTTER_VERSION: 3.19.5
|
||||||
|
|
||||||
|
permissions:
|
||||||
|
contents: write
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
windows:
|
build_platform:
|
||||||
runs-on: windows-latest
|
strategy:
|
||||||
steps:
|
matrix:
|
||||||
- uses: actions/checkout@v4
|
include:
|
||||||
- uses: subosito/flutter-action@v2.12.0
|
- os: ubuntu-latest
|
||||||
with:
|
platform: linux
|
||||||
cache: true
|
files: |
|
||||||
flutter-version: ${{ env.FLUTTER_VERSION }}
|
dist/Spotube-linux-x86_64.deb
|
||||||
|
dist/Spotube-linux-x86_64.rpm
|
||||||
- name: Replace pubspec version and BUILD_VERSION Env (nightly)
|
dist/spotube-linux-*-x86_64.tar.xz
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
- os: ubuntu-latest
|
||||||
run: |
|
platform: linux_arm
|
||||||
choco install sed make yq -y
|
files: |
|
||||||
yq -i '.version |= sub("\+\d+", "-${{ inputs.channel }}+")' pubspec.yaml
|
dist/Spotube-linux-aarch64.deb
|
||||||
yq -i '.version += strenv(GITHUB_RUN_NUMBER)' pubspec.yaml
|
dist/spotube-linux-*-aarch64.tar.xz
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}+${{ inputs.channel }}.${{ github.run_number }}" >> $GITHUB_ENV
|
- os: ubuntu-latest
|
||||||
shell: bash
|
platform: android
|
||||||
|
files: |
|
||||||
- name: BUILD_VERSION Env (stable)
|
build/Spotube-android-all-arch.apk
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
build/Spotube-playstore-all-arch.aab
|
||||||
run: |
|
- os: windows-latest
|
||||||
"BUILD_VERSION=${{ inputs.version }}" >> $env:GITHUB_ENV
|
platform: windows
|
||||||
|
files: |
|
||||||
- name: Replace version in files
|
dist/Spotube-windows-x86_64.nupkg
|
||||||
run: |
|
dist/Spotube-windows-x86_64-setup.exe
|
||||||
choco install sed make -y
|
- os: macos-latest
|
||||||
sed -i "s/%{{SPOTUBE_VERSION}}%/${{ env.BUILD_VERSION }}/" windows/runner/Runner.rc
|
platform: ios
|
||||||
sed -i "s/%{{SPOTUBE_VERSION}}%/${{ env.BUILD_VERSION }}/" choco-struct/tools/VERIFICATION.txt
|
files: |
|
||||||
sed -i "s/%{{SPOTUBE_VERSION}}%/${{ env.BUILD_VERSION }}/" choco-struct/spotube.nuspec
|
Spotube-iOS.ipa
|
||||||
|
- os: macos-14
|
||||||
- name: Create Stable .env
|
platform: macos
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
files: |
|
||||||
run: echo '${{ secrets.DOTENV_RELEASE }}' > .env
|
build/Spotube-macos-universal.dmg
|
||||||
|
build/Spotube-macos-universal.pkg
|
||||||
- name: Create Nightly .env
|
runs-on: ${{matrix.os}}
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_NIGHTLY }}' > .env
|
|
||||||
|
|
||||||
- name: Generating Secrets
|
|
||||||
run: |
|
|
||||||
flutter config --enable-windows-desktop
|
|
||||||
flutter pub get
|
|
||||||
dart run build_runner build --delete-conflicting-outputs
|
|
||||||
|
|
||||||
- name: Build Windows Executable
|
|
||||||
run: |
|
|
||||||
dart pub global activate flutter_distributor
|
|
||||||
make innoinstall
|
|
||||||
flutter_distributor package --platform=windows --targets=exe --skip-clean
|
|
||||||
mv dist/**/spotube-*-windows-setup.exe dist/Spotube-windows-x86_64-setup.exe
|
|
||||||
|
|
||||||
- name: Create Chocolatey Package and set hash
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: |
|
|
||||||
Set-Variable -Name HASH -Value (Get-FileHash dist\Spotube-windows-x86_64-setup.exe).Hash
|
|
||||||
sed -i "s/%{{WIN_SHA256}}%/$HASH/" choco-struct/tools/VERIFICATION.txt
|
|
||||||
make choco
|
|
||||||
mv dist/spotube.*.nupkg dist/Spotube-windows-x86_64.nupkg
|
|
||||||
|
|
||||||
|
|
||||||
- name: Upload Artifact
|
|
||||||
uses: actions/upload-artifact@v3
|
|
||||||
with:
|
|
||||||
if-no-files-found: error
|
|
||||||
name: Spotube-Release-Binaries
|
|
||||||
path: |
|
|
||||||
dist/Spotube-windows-x86_64.nupkg
|
|
||||||
dist/Spotube-windows-x86_64-setup.exe
|
|
||||||
|
|
||||||
- name: Debug With SSH When fails
|
|
||||||
if: ${{ failure() && inputs.debug && inputs.channel == 'nightly' }}
|
|
||||||
uses: mxschmitt/action-tmate@v3
|
|
||||||
with:
|
|
||||||
limit-access-to-actor: true
|
|
||||||
|
|
||||||
linux:
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v4
|
|
||||||
- uses: subosito/flutter-action@v2.12.0
|
|
||||||
with:
|
|
||||||
cache: true
|
|
||||||
flutter-version: ${{ env.FLUTTER_VERSION }}
|
|
||||||
|
|
||||||
- name: Get current date
|
|
||||||
id: date
|
|
||||||
run: echo "::set-output name=date::$(date +'%Y-%m-%d')"
|
|
||||||
|
|
||||||
- name: Install Dependencies
|
|
||||||
run: |
|
|
||||||
sudo apt-get update -y
|
|
||||||
sudo apt-get install -y tar clang cmake ninja-build pkg-config libgtk-3-dev make python3-pip python3-setuptools desktop-file-utils libgdk-pixbuf2.0-dev fakeroot strace fuse libunwind-dev locate patchelf gir1.2-appindicator3-0.1 libappindicator3-1 libappindicator3-dev libsecret-1-0 libjsoncpp25 libsecret-1-dev libjsoncpp-dev libnotify-bin libnotify-dev mpv libmpv-dev
|
|
||||||
|
|
||||||
- name: Install AppImage Tool
|
|
||||||
run: |
|
|
||||||
wget -O appimagetool "https://github.com/AppImage/AppImageKit/releases/download/continuous/appimagetool-x86_64.AppImage"
|
|
||||||
chmod +x appimagetool
|
|
||||||
mv appimagetool /usr/local/bin/
|
|
||||||
|
|
||||||
- name: Replace pubspec version and BUILD_VERSION Env (nightly)
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: |
|
|
||||||
curl -sS https://webi.sh/yq | sh
|
|
||||||
yq -i '.version |= sub("\+\d+", "+${{ inputs.channel }}.")' pubspec.yaml
|
|
||||||
yq -i '.version += strenv(GITHUB_RUN_NUMBER)' pubspec.yaml
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}+${{ inputs.channel }}.${{ github.run_number }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: BUILD_VERSION Env (stable)
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: |
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: Create Stable .env
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_RELEASE }}' > .env
|
|
||||||
|
|
||||||
- name: Create Nightly .env
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_NIGHTLY }}' > .env
|
|
||||||
|
|
||||||
- name: Replace Version in files
|
|
||||||
run: |
|
|
||||||
sed -i 's|%{{APPDATA_RELEASE}}%|<release version="${{ env.BUILD_VERSION }}" date="${{ steps.date.outputs.date }}" />|' linux/com.github.KRTirtho.Spotube.appdata.xml
|
|
||||||
|
|
||||||
- name: Generate Secrets
|
|
||||||
run: |
|
|
||||||
flutter config --enable-linux-desktop
|
|
||||||
flutter pub get
|
|
||||||
dart run build_runner build --delete-conflicting-outputs
|
|
||||||
|
|
||||||
- name: Build Linux Packages
|
|
||||||
run: |
|
|
||||||
dart pub global activate flutter_distributor
|
|
||||||
alias dpkg-deb="dpkg-deb --Zxz"
|
|
||||||
flutter_distributor package --platform=linux --targets=deb
|
|
||||||
flutter_distributor package --platform=linux --targets=rpm
|
|
||||||
|
|
||||||
- name: Create tar.xz (stable)
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: make tar VERSION=${{ env.BUILD_VERSION }} ARCH=x64 PKG_ARCH=x86_64
|
|
||||||
|
|
||||||
- name: Create tar.xz (nightly)
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: make tar VERSION=nightly ARCH=x64 PKG_ARCH=x86_64
|
|
||||||
|
|
||||||
- name: Move Files to dist
|
|
||||||
run: |
|
|
||||||
mv build/spotube-linux-*-x86_64.tar.xz dist/
|
|
||||||
mv dist/**/spotube-*-linux.deb dist/Spotube-linux-x86_64.deb
|
|
||||||
mv dist/**/spotube-*-linux.rpm dist/Spotube-linux-x86_64.rpm
|
|
||||||
|
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
with:
|
|
||||||
if-no-files-found: error
|
|
||||||
name: Spotube-Release-Binaries
|
|
||||||
path: |
|
|
||||||
dist/Spotube-linux-x86_64.deb
|
|
||||||
dist/Spotube-linux-x86_64.rpm
|
|
||||||
dist/spotube-linux-${{ env.BUILD_VERSION }}-x86_64.tar.xz
|
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
with:
|
|
||||||
if-no-files-found: error
|
|
||||||
name: Spotube-Release-Binaries
|
|
||||||
path: |
|
|
||||||
dist/Spotube-linux-x86_64.deb
|
|
||||||
dist/Spotube-linux-x86_64.rpm
|
|
||||||
dist/spotube-linux-nightly-x86_64.tar.xz
|
|
||||||
|
|
||||||
- name: Debug With SSH When fails
|
|
||||||
if: ${{ failure() && inputs.debug && inputs.channel == 'nightly' }}
|
|
||||||
uses: mxschmitt/action-tmate@v3
|
|
||||||
with:
|
|
||||||
limit-access-to-actor: true
|
|
||||||
|
|
||||||
linux_arm:
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v4
|
|
||||||
- name: Set up QEMU
|
|
||||||
uses: docker/setup-qemu-action@v3
|
|
||||||
- name: Set up Docker Buildx
|
|
||||||
uses: docker/setup-buildx-action@v3
|
|
||||||
|
|
||||||
- name: Get current date
|
|
||||||
id: date
|
|
||||||
run: echo "::set-output name=date::$(date +'%Y-%m-%d')"
|
|
||||||
|
|
||||||
- name: Install Dependencies
|
|
||||||
run: |
|
|
||||||
sudo apt-get update -y
|
|
||||||
sudo apt-get install -y pkg-config make python3-pip python3-setuptools
|
|
||||||
|
|
||||||
- name: Replace pubspec version and BUILD_VERSION Env (nightly)
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: |
|
|
||||||
curl -sS https://webi.sh/yq | sh
|
|
||||||
yq -i '.version |= sub("\+\d+", "+${{ inputs.channel }}.")' pubspec.yaml
|
|
||||||
yq -i '.version += strenv(GITHUB_RUN_NUMBER)' pubspec.yaml
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}+${{ inputs.channel }}.${{ github.run_number }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: BUILD_VERSION Env (stable)
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: |
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: Create Stable .env
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_RELEASE }}' > .env
|
|
||||||
|
|
||||||
- name: Create Nightly .env
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_NIGHTLY }}' > .env
|
|
||||||
|
|
||||||
- name: Replace Version in files
|
|
||||||
run: |
|
|
||||||
sed -i 's|%{{APPDATA_RELEASE}}%|<release version="${{ env.BUILD_VERSION }}" date="${{ steps.date.outputs.date }}" />|' linux/com.github.KRTirtho.Spotube.appdata.xml
|
|
||||||
|
|
||||||
- name: Build Binaries (stable)
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: |
|
|
||||||
docker buildx build --platform=linux/arm64 -f .github/Dockerfile . --build-arg FLUTTER_VERSION=${{env.FLUTTER_VERSION}} --build-arg BUILD_VERSION=${{env.BUILD_VERSION}} -t krtirtho/spotube_linux_arm:latest --load
|
|
||||||
|
|
||||||
- name: Build Binaries (nightly)
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: |
|
|
||||||
docker buildx build --platform=linux/arm64 -f .github/Dockerfile . --build-arg FLUTTER_VERSION=${{env.FLUTTER_VERSION}} --build-arg BUILD_VERSION=nightly -t krtirtho/spotube_linux_arm:latest --load
|
|
||||||
|
|
||||||
- name: Copy the built packages
|
|
||||||
run: |
|
|
||||||
docker images ls
|
|
||||||
docker create --name spotube_linux_arm krtirtho/spotube_linux_arm:latest
|
|
||||||
docker cp spotube_linux_arm:/app/dist/ dist/
|
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
with:
|
|
||||||
if-no-files-found: error
|
|
||||||
name: Spotube-Release-Binaries
|
|
||||||
path: |
|
|
||||||
dist/Spotube-linux-aarch64.deb
|
|
||||||
dist/spotube-linux-${{ env.BUILD_VERSION }}-aarch64.tar.xz
|
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
with:
|
|
||||||
if-no-files-found: error
|
|
||||||
name: Spotube-Release-Binaries
|
|
||||||
path: |
|
|
||||||
dist/Spotube-linux-aarch64.deb
|
|
||||||
dist/spotube-linux-nightly-aarch64.tar.xz
|
|
||||||
|
|
||||||
- name: Debug With SSH When fails
|
|
||||||
if: ${{ failure() && inputs.debug && inputs.channel == 'nightly' }}
|
|
||||||
uses: mxschmitt/action-tmate@v3
|
|
||||||
with:
|
|
||||||
limit-access-to-actor: true
|
|
||||||
|
|
||||||
android:
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
- uses: subosito/flutter-action@v2.12.0
|
- uses: subosito/flutter-action@v2.12.0
|
||||||
@ -299,191 +68,42 @@ jobs:
|
|||||||
cache: true
|
cache: true
|
||||||
flutter-version: ${{ env.FLUTTER_VERSION }}
|
flutter-version: ${{ env.FLUTTER_VERSION }}
|
||||||
- name: Setup Java
|
- name: Setup Java
|
||||||
|
if: ${{matrix.platform == 'android'}}
|
||||||
uses: actions/setup-java@v4
|
uses: actions/setup-java@v4
|
||||||
with:
|
with:
|
||||||
distribution: 'zulu'
|
distribution: 'zulu'
|
||||||
java-version: '17'
|
java-version: '17'
|
||||||
cache: 'gradle'
|
cache: 'gradle'
|
||||||
check-latest: true
|
check-latest: true
|
||||||
|
- name: Set up QEMU
|
||||||
|
if: ${{matrix.platform == 'linux_arm'}}
|
||||||
|
uses: docker/setup-qemu-action@v3
|
||||||
|
- name: Set up Docker Buildx
|
||||||
|
if: ${{matrix.platform == 'linux_arm'}}
|
||||||
|
uses: docker/setup-buildx-action@v3
|
||||||
|
|
||||||
- name: Install Dependencies
|
- name: Install ${{matrix.platform}} dependencies
|
||||||
run: |
|
|
||||||
sudo apt-get update -y
|
|
||||||
sudo apt-get install -y clang cmake ninja-build pkg-config libgtk-3-dev make python3-pip python3-setuptools patchelf desktop-file-utils libgdk-pixbuf2.0-dev fakeroot strace fuse xmlstarlet
|
|
||||||
|
|
||||||
- name: Replace pubspec version and BUILD_VERSION Env (nightly)
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: |
|
|
||||||
curl -sS https://webi.sh/yq | sh
|
|
||||||
yq -i '.version |= sub("\+\d+", "+${{ inputs.channel }}.")' pubspec.yaml
|
|
||||||
yq -i '.version += strenv(GITHUB_RUN_NUMBER)' pubspec.yaml
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}+${{ inputs.channel }}.${{ github.run_number }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: BUILD_VERSION Env (stable)
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: |
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: Create Stable .env
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_RELEASE }}' > .env
|
|
||||||
|
|
||||||
- name: Create Nightly .env
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_NIGHTLY }}' > .env
|
|
||||||
|
|
||||||
- name: Generate Secrets
|
|
||||||
run: |
|
run: |
|
||||||
flutter pub get
|
flutter pub get
|
||||||
dart run build_runner build --delete-conflicting-outputs
|
dart cli/cli.dart install-dependencies --platform=${{matrix.platform}}
|
||||||
|
|
||||||
- name: Sign Apk
|
- name: Sign Apk
|
||||||
|
if: ${{matrix.platform == 'android'}}
|
||||||
run: |
|
run: |
|
||||||
echo '${{ secrets.KEYSTORE }}' | base64 --decode > android/app/upload-keystore.jks
|
echo '${{ secrets.KEYSTORE }}' | base64 --decode > android/app/upload-keystore.jks
|
||||||
echo '${{ secrets.KEY_PROPERTIES }}' > android/key.properties
|
echo '${{ secrets.KEY_PROPERTIES }}' > android/key.properties
|
||||||
|
|
||||||
- name: Build Apk
|
- name: Build ${{matrix.platform}} binaries
|
||||||
run: |
|
run: dart cli/cli.dart build ${{matrix.platform}}
|
||||||
flutter build apk --flavor ${{ inputs.channel }}
|
env:
|
||||||
mv build/app/outputs/flutter-apk/app-${{ inputs.channel }}-release.apk build/Spotube-android-all-arch.apk
|
CHANNEL: ${{inputs.channel}}
|
||||||
|
DOTENV: ${{secrets.DOTENV_RELEASE}}
|
||||||
- name: Build Playstore AppBundle
|
|
||||||
run: |
|
|
||||||
echo 'ENABLE_UPDATE_CHECK=0' >> .env
|
|
||||||
dart run build_runner build --delete-conflicting-outputs
|
|
||||||
export MANIFEST=android/app/src/main/AndroidManifest.xml
|
|
||||||
xmlstarlet ed -d '//meta-data[@android:name="com.google.android.gms.car.application"]' $MANIFEST > $MANIFEST.tmp
|
|
||||||
mv $MANIFEST.tmp $MANIFEST
|
|
||||||
flutter build appbundle --flavor ${{ inputs.channel }}
|
|
||||||
mv build/app/outputs/bundle/${{ inputs.channel }}Release/app-${{ inputs.channel }}-release.aab build/Spotube-playstore-all-arch.aab
|
|
||||||
|
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
- uses: actions/upload-artifact@v3
|
||||||
with:
|
with:
|
||||||
if-no-files-found: error
|
if-no-files-found: error
|
||||||
name: Spotube-Release-Binaries
|
name: Spotube-Release-Binaries
|
||||||
path: |
|
path: ${{matrix.files}}
|
||||||
build/Spotube-android-all-arch.apk
|
|
||||||
build/Spotube-playstore-all-arch.aab
|
|
||||||
|
|
||||||
- name: Debug With SSH When fails
|
|
||||||
if: ${{ failure() && inputs.debug && inputs.channel == 'nightly' }}
|
|
||||||
uses: mxschmitt/action-tmate@v3
|
|
||||||
with:
|
|
||||||
limit-access-to-actor: true
|
|
||||||
|
|
||||||
macos:
|
|
||||||
runs-on: macos-14
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v4
|
|
||||||
- uses: subosito/flutter-action@v2.12.0
|
|
||||||
with:
|
|
||||||
cache: true
|
|
||||||
flutter-version: ${{ env.FLUTTER_VERSION }}
|
|
||||||
|
|
||||||
- name: Replace pubspec version and BUILD_VERSION Env (nightly)
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: |
|
|
||||||
brew install yq
|
|
||||||
yq -i '.version |= sub("\+\d+", "+${{ inputs.channel }}.")' pubspec.yaml
|
|
||||||
yq -i '.version += strenv(GITHUB_RUN_NUMBER)' pubspec.yaml
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}+${{ inputs.channel }}.${{ github.run_number }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: BUILD_VERSION Env (stable)
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: |
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: Create Stable .env
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_RELEASE }}' > .env
|
|
||||||
|
|
||||||
- name: Create Nightly .env
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_NIGHTLY }}' > .env
|
|
||||||
|
|
||||||
- name: Generate Secrets
|
|
||||||
run: |
|
|
||||||
dart pub global activate flutter_distributor
|
|
||||||
flutter pub get
|
|
||||||
dart run build_runner build --delete-conflicting-outputs
|
|
||||||
|
|
||||||
- name: Build Macos App
|
|
||||||
run: |
|
|
||||||
flutter config --enable-macos-desktop
|
|
||||||
flutter build macos
|
|
||||||
du -sh build/macos/Build/Products/Release/spotube.app
|
|
||||||
|
|
||||||
- name: Package Macos App
|
|
||||||
run: |
|
|
||||||
brew install python-setuptools
|
|
||||||
npm install -g appdmg
|
|
||||||
mkdir -p build/${{ env.BUILD_VERSION }}
|
|
||||||
appdmg appdmg.json build/Spotube-macos-universal.dmg
|
|
||||||
flutter_distributor package --platform=macos --targets pkg --skip-clean
|
|
||||||
mv dist/**/spotube-*-macos.pkg build/Spotube-macos-universal.pkg
|
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
|
||||||
with:
|
|
||||||
if-no-files-found: error
|
|
||||||
name: Spotube-Release-Binaries
|
|
||||||
path: |
|
|
||||||
build/Spotube-macos-universal.dmg
|
|
||||||
build/Spotube-macos-universal.pkg
|
|
||||||
|
|
||||||
- name: Debug With SSH When fails
|
|
||||||
if: ${{ failure() && inputs.debug && inputs.channel == 'nightly' }}
|
|
||||||
uses: mxschmitt/action-tmate@v3
|
|
||||||
with:
|
|
||||||
limit-access-to-actor: true
|
|
||||||
|
|
||||||
iOS:
|
|
||||||
runs-on: macos-14
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v4
|
|
||||||
- uses: subosito/flutter-action@v2.10.0
|
|
||||||
with:
|
|
||||||
cache: true
|
|
||||||
flutter-version: ${{ env.FLUTTER_VERSION }}
|
|
||||||
|
|
||||||
- name: Replace pubspec version and BUILD_VERSION Env (nightly)
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: |
|
|
||||||
brew install yq
|
|
||||||
yq -i '.version |= sub("\+\d+", "+${{ inputs.channel }}.")' pubspec.yaml
|
|
||||||
yq -i '.version += strenv(GITHUB_RUN_NUMBER)' pubspec.yaml
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}+${{ inputs.channel }}.${{ github.run_number }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: BUILD_VERSION Env (stable)
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: |
|
|
||||||
echo "BUILD_VERSION=${{ inputs.version }}" >> $GITHUB_ENV
|
|
||||||
|
|
||||||
- name: Create Stable .env
|
|
||||||
if: ${{ inputs.channel == 'stable' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_RELEASE }}' > .env
|
|
||||||
|
|
||||||
- name: Create Nightly .env
|
|
||||||
if: ${{ inputs.channel == 'nightly' }}
|
|
||||||
run: echo '${{ secrets.DOTENV_NIGHTLY }}' > .env
|
|
||||||
|
|
||||||
- name: Generate Secrets
|
|
||||||
run: |
|
|
||||||
flutter pub get
|
|
||||||
dart run build_runner build --delete-conflicting-outputs
|
|
||||||
|
|
||||||
- name: Build iOS iPA
|
|
||||||
run: |
|
|
||||||
flutter build ios --release --no-codesign --flavor ${{ inputs.channel }}
|
|
||||||
ln -sf ./build/ios/iphoneos Payload
|
|
||||||
zip -r9 Spotube-iOS.ipa Payload/${{ inputs.channel }}.app
|
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
|
||||||
with:
|
|
||||||
if-no-files-found: error
|
|
||||||
name: Spotube-Release-Binaries
|
|
||||||
path: |
|
|
||||||
Spotube-iOS.ipa
|
|
||||||
|
|
||||||
- name: Debug With SSH When fails
|
- name: Debug With SSH When fails
|
||||||
if: ${{ failure() && inputs.debug && inputs.channel == 'nightly' }}
|
if: ${{ failure() && inputs.debug && inputs.channel == 'nightly' }}
|
||||||
@ -493,14 +113,8 @@ jobs:
|
|||||||
|
|
||||||
upload:
|
upload:
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
|
|
||||||
needs:
|
needs:
|
||||||
- windows
|
- build_platform
|
||||||
- linux
|
|
||||||
- linux_arm
|
|
||||||
- android
|
|
||||||
- macos
|
|
||||||
- iOS
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/download-artifact@v3
|
- uses: actions/download-artifact@v3
|
||||||
with:
|
with:
|
||||||
@ -517,6 +131,10 @@ jobs:
|
|||||||
sha256sum Spotube-Release-Binaries/* >> RELEASE.sha256sum
|
sha256sum Spotube-Release-Binaries/* >> RELEASE.sha256sum
|
||||||
sed -i 's|Spotube-Release-Binaries/||' RELEASE.sha256sum RELEASE.md5sum
|
sed -i 's|Spotube-Release-Binaries/||' RELEASE.sha256sum RELEASE.md5sum
|
||||||
|
|
||||||
|
- name: Extract pubspec version
|
||||||
|
run: |
|
||||||
|
echo "PUBSPEC_VERSION=$(grep -oP 'version:\s*\K[^+]+(?=\+)' pubspec.yaml)" >> $GITHUB_ENV
|
||||||
|
|
||||||
- uses: actions/upload-artifact@v3
|
- uses: actions/upload-artifact@v3
|
||||||
with:
|
with:
|
||||||
if-no-files-found: error
|
if-no-files-found: error
|
||||||
@ -530,7 +148,7 @@ jobs:
|
|||||||
uses: ncipollo/release-action@v1
|
uses: ncipollo/release-action@v1
|
||||||
with:
|
with:
|
||||||
token: ${{ secrets.GITHUB_TOKEN }}
|
token: ${{ secrets.GITHUB_TOKEN }}
|
||||||
tag: v${{ inputs.version }} # mind the "v" prefix
|
tag: v${{ env.PUBSPEC_VERSION }} # mind the "v" prefix
|
||||||
omitBodyDuringUpdate: true
|
omitBodyDuringUpdate: true
|
||||||
omitNameDuringUpdate: true
|
omitNameDuringUpdate: true
|
||||||
omitPrereleaseDuringUpdate: true
|
omitPrereleaseDuringUpdate: true
|
||||||
@ -548,3 +166,8 @@ jobs:
|
|||||||
omitPrereleaseDuringUpdate: true
|
omitPrereleaseDuringUpdate: true
|
||||||
allowUpdates: true
|
allowUpdates: true
|
||||||
artifacts: Spotube-Release-Binaries/*,RELEASE.sha256sum,RELEASE.md5sum
|
artifacts: Spotube-Release-Binaries/*,RELEASE.sha256sum,RELEASE.md5sum
|
||||||
|
body: |
|
||||||
|
Build Number: ${{github.run_number}}
|
||||||
|
|
||||||
|
Nightly release includes newest features but may contain bugs
|
||||||
|
It is preferred to use the stable version unless you know what you're doing
|
||||||
|
16
.metadata
16
.metadata
@ -1,11 +1,11 @@
|
|||||||
# This file tracks properties of this Flutter project.
|
# This file tracks properties of this Flutter project.
|
||||||
# Used by Flutter tool to assess capabilities and perform upgrades etc.
|
# Used by Flutter tool to assess capabilities and perform upgrades etc.
|
||||||
#
|
#
|
||||||
# This file should be version controlled.
|
# This file should be version controlled and should not be manually edited.
|
||||||
|
|
||||||
version:
|
version:
|
||||||
revision: eb6d86ee27deecba4a83536aa20f366a6044895c
|
revision: "300451adae589accbece3490f4396f10bdf15e6e"
|
||||||
channel: stable
|
channel: "stable"
|
||||||
|
|
||||||
project_type: app
|
project_type: app
|
||||||
|
|
||||||
@ -13,11 +13,11 @@ project_type: app
|
|||||||
migration:
|
migration:
|
||||||
platforms:
|
platforms:
|
||||||
- platform: root
|
- platform: root
|
||||||
create_revision: eb6d86ee27deecba4a83536aa20f366a6044895c
|
create_revision: 300451adae589accbece3490f4396f10bdf15e6e
|
||||||
base_revision: eb6d86ee27deecba4a83536aa20f366a6044895c
|
base_revision: 300451adae589accbece3490f4396f10bdf15e6e
|
||||||
- platform: macos
|
- platform: windows
|
||||||
create_revision: eb6d86ee27deecba4a83536aa20f366a6044895c
|
create_revision: 300451adae589accbece3490f4396f10bdf15e6e
|
||||||
base_revision: eb6d86ee27deecba4a83536aa20f366a6044895c
|
base_revision: 300451adae589accbece3490f4396f10bdf15e6e
|
||||||
|
|
||||||
# User provided section
|
# User provided section
|
||||||
|
|
||||||
|
4
cli/README.md
Normal file
4
cli/README.md
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
## Spotube Configuration CLI
|
||||||
|
|
||||||
|
This is used for building the project for multiple platforms and having utilities specific for the project.
|
||||||
|
Written in Dart
|
16
cli/cli.dart
Normal file
16
cli/cli.dart
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
|
||||||
|
import 'commands/build.dart';
|
||||||
|
import 'commands/install-dependencies.dart';
|
||||||
|
|
||||||
|
void main(List<String> args) {
|
||||||
|
final commandRunner = CommandRunner(
|
||||||
|
"cli",
|
||||||
|
"Configuration CLI for Spotube",
|
||||||
|
);
|
||||||
|
|
||||||
|
commandRunner.addCommand(InstallDependenciesCommand());
|
||||||
|
commandRunner.addCommand(BuildCommand());
|
||||||
|
|
||||||
|
commandRunner.run(args);
|
||||||
|
}
|
25
cli/commands/build.dart
Normal file
25
cli/commands/build.dart
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
|
||||||
|
import 'build/android.dart';
|
||||||
|
import 'build/ios.dart';
|
||||||
|
import 'build/linux.dart';
|
||||||
|
import 'build/linux_arm.dart';
|
||||||
|
import 'build/macos.dart';
|
||||||
|
import 'build/windows.dart';
|
||||||
|
|
||||||
|
class BuildCommand extends Command {
|
||||||
|
@override
|
||||||
|
String get description => "Build for different platforms";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "build";
|
||||||
|
|
||||||
|
BuildCommand() {
|
||||||
|
addSubcommand(AndroidBuildCommand());
|
||||||
|
addSubcommand(IosBuildCommand());
|
||||||
|
addSubcommand(LinuxBuildCommand());
|
||||||
|
addSubcommand(LinuxArmBuildCommand());
|
||||||
|
addSubcommand(MacosBuildCommand());
|
||||||
|
addSubcommand(WindowsBuildCommand());
|
||||||
|
}
|
||||||
|
}
|
90
cli/commands/build/android.dart
Normal file
90
cli/commands/build/android.dart
Normal file
@ -0,0 +1,90 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
import 'dart:io';
|
||||||
|
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:collection/collection.dart';
|
||||||
|
import 'package:path/path.dart';
|
||||||
|
import 'package:xml/xml.dart';
|
||||||
|
|
||||||
|
import '../../core/env.dart';
|
||||||
|
import 'common.dart';
|
||||||
|
|
||||||
|
class AndroidBuildCommand extends Command with BuildCommandCommonSteps {
|
||||||
|
@override
|
||||||
|
String get description => "Build for android";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "android";
|
||||||
|
|
||||||
|
@override
|
||||||
|
FutureOr? run() async {
|
||||||
|
await bootstrap();
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"flutter build apk --flavor ${CliEnv.channel.name}",
|
||||||
|
);
|
||||||
|
|
||||||
|
await dotEnvFile.writeAsString(
|
||||||
|
"\nENABLE_UPDATE_CHECK=0",
|
||||||
|
mode: FileMode.append,
|
||||||
|
);
|
||||||
|
|
||||||
|
final androidManifestFile = File(
|
||||||
|
join(cwd.path, "android", "app", "src", "main", "AndroidManifest.xml"));
|
||||||
|
|
||||||
|
final androidManifestXml =
|
||||||
|
XmlDocument.parse(await androidManifestFile.readAsString());
|
||||||
|
|
||||||
|
final deletingElement =
|
||||||
|
androidManifestXml.findAllElements("meta-data").firstWhereOrNull(
|
||||||
|
(el) =>
|
||||||
|
el.getAttribute("android:name") ==
|
||||||
|
"com.google.android.gms.car.application",
|
||||||
|
);
|
||||||
|
|
||||||
|
deletingElement?.parent?.children.remove(deletingElement);
|
||||||
|
|
||||||
|
await androidManifestFile.writeAsString(
|
||||||
|
androidManifestXml.toXmlString(pretty: true),
|
||||||
|
);
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
dart run build_runner build --delete-conflicting-outputs
|
||||||
|
flutter build appbundle --flavor ${CliEnv.channel.name}
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
|
||||||
|
final ogApkFile = File(
|
||||||
|
join(
|
||||||
|
"build",
|
||||||
|
"app",
|
||||||
|
"outputs",
|
||||||
|
"flutter-apk",
|
||||||
|
"app-${CliEnv.channel.name}-release.apk",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await ogApkFile.copy(
|
||||||
|
join(cwd.path, "build", "Spotube-android-all-arch.apk"),
|
||||||
|
);
|
||||||
|
|
||||||
|
final ogAppbundleFile = File(
|
||||||
|
join(
|
||||||
|
cwd.path,
|
||||||
|
"build",
|
||||||
|
"app",
|
||||||
|
"outputs",
|
||||||
|
"bundle",
|
||||||
|
"${CliEnv.channel.name}Release",
|
||||||
|
"app-${CliEnv.channel.name}-release.aab",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await ogAppbundleFile.copy(
|
||||||
|
join(cwd.path, "build", "Spotube-playstore-all-arch.aab"),
|
||||||
|
);
|
||||||
|
|
||||||
|
stdout.writeln("✅ Built Android Apk and Appbundle");
|
||||||
|
}
|
||||||
|
}
|
66
cli/commands/build/common.dart
Normal file
66
cli/commands/build/common.dart
Normal file
@ -0,0 +1,66 @@
|
|||||||
|
import 'dart:io';
|
||||||
|
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:path/path.dart';
|
||||||
|
import 'package:process_run/shell_run.dart';
|
||||||
|
import 'package:pubspec_parse/pubspec_parse.dart';
|
||||||
|
|
||||||
|
import '../../core/env.dart';
|
||||||
|
|
||||||
|
mixin BuildCommandCommonSteps on Command {
|
||||||
|
final shell = Shell();
|
||||||
|
Directory get cwd => Directory.current;
|
||||||
|
|
||||||
|
Pubspec? _pubspec;
|
||||||
|
|
||||||
|
Pubspec get pubspec {
|
||||||
|
if (_pubspec != null) {
|
||||||
|
return _pubspec!;
|
||||||
|
}
|
||||||
|
|
||||||
|
final pubspecFile = File(join(cwd.path, "pubspec.yaml"));
|
||||||
|
_pubspec = Pubspec.parse(pubspecFile.readAsStringSync());
|
||||||
|
|
||||||
|
return _pubspec!;
|
||||||
|
}
|
||||||
|
|
||||||
|
String get versionWithoutBuildNumber {
|
||||||
|
return "${pubspec.version!.major}.${pubspec.version!.minor}.${pubspec.version!.patch}";
|
||||||
|
}
|
||||||
|
|
||||||
|
RegExp get versionVarRegExp =>
|
||||||
|
RegExp(r"\%\{\{SPOTUBE_VERSION\}\}\%", multiLine: true);
|
||||||
|
|
||||||
|
File get dotEnvFile => File(join(cwd.path, ".env"));
|
||||||
|
|
||||||
|
Future<void> bootstrap() async {
|
||||||
|
await dotEnvFile.create(recursive: true);
|
||||||
|
|
||||||
|
await dotEnvFile.writeAsString(
|
||||||
|
"${CliEnv.dotenv}\n"
|
||||||
|
"RELEASE_CHANNEL=${CliEnv.channel.name}\n",
|
||||||
|
);
|
||||||
|
|
||||||
|
if (CliEnv.channel == BuildChannel.nightly) {
|
||||||
|
final pubspecFile = File(join(cwd.path, "pubspec.yaml"));
|
||||||
|
|
||||||
|
pubspecFile.writeAsStringSync(
|
||||||
|
pubspecFile.readAsStringSync().replaceAll(
|
||||||
|
"version: ${pubspec.version!.canonicalizedVersion}",
|
||||||
|
"version: $versionWithoutBuildNumber+${CliEnv.ghRunNumber}",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
_pubspec = null;
|
||||||
|
pubspec;
|
||||||
|
}
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
flutter pub get
|
||||||
|
dart run build_runner build --delete-conflicting-outputs
|
||||||
|
dart pub global activate flutter_distributor
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
29
cli/commands/build/ios.dart
Normal file
29
cli/commands/build/ios.dart
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:path/path.dart';
|
||||||
|
|
||||||
|
import '../../core/env.dart';
|
||||||
|
import 'common.dart';
|
||||||
|
|
||||||
|
class IosBuildCommand extends Command with BuildCommandCommonSteps {
|
||||||
|
@override
|
||||||
|
String get description => "iOS build command";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "ios";
|
||||||
|
|
||||||
|
@override
|
||||||
|
FutureOr? run() async {
|
||||||
|
await bootstrap();
|
||||||
|
|
||||||
|
final buildDirPath = join(cwd.path, "build", "ios", "iphoneos");
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
flutter build ios --release --no-codesign --flavor ${CliEnv.channel.name}
|
||||||
|
ln -sf $buildDirPath Payload
|
||||||
|
zip -r9 Spotube-iOS.ipa ${join("Payload", "${CliEnv.channel.name}.app")}
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
106
cli/commands/build/linux.dart
Normal file
106
cli/commands/build/linux.dart
Normal file
@ -0,0 +1,106 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
import 'dart:io';
|
||||||
|
|
||||||
|
import 'package:io/io.dart';
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:intl/intl.dart';
|
||||||
|
import 'package:path/path.dart';
|
||||||
|
|
||||||
|
import '../../core/env.dart';
|
||||||
|
import 'common.dart';
|
||||||
|
|
||||||
|
class LinuxBuildCommand extends Command with BuildCommandCommonSteps {
|
||||||
|
@override
|
||||||
|
String get description => "Linux build command";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "linux";
|
||||||
|
|
||||||
|
@override
|
||||||
|
FutureOr? run() async {
|
||||||
|
stdout.writeln("Replacing versions");
|
||||||
|
|
||||||
|
final appDataFile = File(
|
||||||
|
join(cwd.path, "linux", "com.github.KRTirtho.Spotube.appdata.xml"),
|
||||||
|
);
|
||||||
|
|
||||||
|
appDataFile.writeAsStringSync(
|
||||||
|
appDataFile.readAsStringSync().replaceAll(
|
||||||
|
versionVarRegExp,
|
||||||
|
'<release'
|
||||||
|
' version="$versionWithoutBuildNumber"'
|
||||||
|
' date="${DateFormat("yyyy-MM-dd").format(DateTime.now())}"'
|
||||||
|
'/>',
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await bootstrap();
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
flutter_distributor package --platform=linux --targets=deb
|
||||||
|
flutter_distributor package --platform=linux --targets=rpm
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
|
||||||
|
final tempDir = join(Directory.systemTemp.path, "spotube-tar");
|
||||||
|
|
||||||
|
final bundleDirPath =
|
||||||
|
join(cwd.path, "build", "linux", "x64", "release", "bundle");
|
||||||
|
|
||||||
|
final tarFile = File(join(
|
||||||
|
cwd.path,
|
||||||
|
"dist",
|
||||||
|
"spotube-linux-"
|
||||||
|
"${CliEnv.channel == BuildChannel.nightly ? "nightly" : versionWithoutBuildNumber}"
|
||||||
|
"-x86_64.tar.xz",
|
||||||
|
));
|
||||||
|
|
||||||
|
await copyPath(bundleDirPath, tempDir);
|
||||||
|
await File(join(cwd.path, "linux", "spotube.desktop")).copy(
|
||||||
|
join(tempDir, "spotube.desktop"),
|
||||||
|
);
|
||||||
|
await File(
|
||||||
|
join(cwd.path, "linux", "com.github.KRTirtho.Spotube.appdata.xml"),
|
||||||
|
).copy(
|
||||||
|
join(tempDir, "com.github.KRTirtho.Spotube.appdata.xml"),
|
||||||
|
);
|
||||||
|
await File(join(cwd.path, "assets", "spotube-logo.png")).copy(
|
||||||
|
join(tempDir, "spotube-logo.png"),
|
||||||
|
);
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"tar -cJf ${tarFile.path} -C $tempDir .",
|
||||||
|
);
|
||||||
|
|
||||||
|
final ogDeb = File(
|
||||||
|
join(
|
||||||
|
cwd.path,
|
||||||
|
"dist",
|
||||||
|
pubspec.version.toString(),
|
||||||
|
"spotube-${pubspec.version}-linux.deb",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
final ogRpm = File(
|
||||||
|
join(
|
||||||
|
cwd.path,
|
||||||
|
"dist",
|
||||||
|
pubspec.version.toString(),
|
||||||
|
"spotube-${pubspec.version}-linux.rpm",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await ogDeb.copy(
|
||||||
|
join(cwd.path, "dist", "Spotube-linux-x86_64.deb"),
|
||||||
|
);
|
||||||
|
await ogRpm.copy(
|
||||||
|
join(cwd.path, "dist", "Spotube-linux-x86_64.rpm"),
|
||||||
|
);
|
||||||
|
|
||||||
|
await ogDeb.delete();
|
||||||
|
await ogRpm.delete();
|
||||||
|
|
||||||
|
stdout.writeln("✅ Linux building done");
|
||||||
|
}
|
||||||
|
}
|
37
cli/commands/build/linux_arm.dart
Normal file
37
cli/commands/build/linux_arm.dart
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:path/path.dart';
|
||||||
|
|
||||||
|
import '../../core/env.dart';
|
||||||
|
import 'common.dart';
|
||||||
|
|
||||||
|
class LinuxArmBuildCommand extends Command with BuildCommandCommonSteps {
|
||||||
|
@override
|
||||||
|
String get description => "Build Linux Arm";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "linux_arm";
|
||||||
|
|
||||||
|
@override
|
||||||
|
FutureOr? run() async {
|
||||||
|
await bootstrap();
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"docker buildx build --platform=linux/arm64 "
|
||||||
|
"-f ${join(cwd.path, ".github", "Dockerfile")} ${cwd.path} "
|
||||||
|
"--build-arg FLUTTER_VERSION=${CliEnv.flutterVersion} "
|
||||||
|
"--build-arg BUILD_VERSION=${CliEnv.channel == BuildChannel.nightly ? "nightly" : versionWithoutBuildNumber} "
|
||||||
|
"-t krtirtho/spotube_linux_arm:latest "
|
||||||
|
"--load",
|
||||||
|
);
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
docker images ls
|
||||||
|
docker create --name spotube_linux_arm krtirtho/spotube_linux_arm:latest
|
||||||
|
docker cp spotube_linux_arm:/app/dist/ dist/
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
42
cli/commands/build/macos.dart
Normal file
42
cli/commands/build/macos.dart
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
import 'dart:io';
|
||||||
|
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:path/path.dart';
|
||||||
|
|
||||||
|
import 'common.dart';
|
||||||
|
|
||||||
|
class MacosBuildCommand extends Command with BuildCommandCommonSteps {
|
||||||
|
@override
|
||||||
|
String get description => "Macos Build command";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "macos";
|
||||||
|
|
||||||
|
@override
|
||||||
|
FutureOr? run() async {
|
||||||
|
await bootstrap();
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
flutter build macos
|
||||||
|
appdmg appdmg.json ${join(cwd.path, "build", "Spotube-macos-universal.dmg")}
|
||||||
|
flutter_distributor package --platform=macos --targets pkg --skip-clean
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
|
||||||
|
final ogPkg = File(
|
||||||
|
join(
|
||||||
|
cwd.path,
|
||||||
|
"dist",
|
||||||
|
pubspec.version.toString(),
|
||||||
|
"spotube-${pubspec.version}-macos.pkg",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await ogPkg.copy(
|
||||||
|
join(cwd.path, "build", "Spotube-macos-universal.pkg"),
|
||||||
|
);
|
||||||
|
await ogPkg.delete();
|
||||||
|
}
|
||||||
|
}
|
100
cli/commands/build/windows.dart
Normal file
100
cli/commands/build/windows.dart
Normal file
@ -0,0 +1,100 @@
|
|||||||
|
import 'dart:io';
|
||||||
|
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:path/path.dart';
|
||||||
|
import 'package:crypto/crypto.dart';
|
||||||
|
import 'common.dart';
|
||||||
|
|
||||||
|
class WindowsBuildCommand extends Command with BuildCommandCommonSteps {
|
||||||
|
@override
|
||||||
|
String get description => "Build Windows exe";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "windows";
|
||||||
|
|
||||||
|
Future<void> innoDependInstall() async {
|
||||||
|
final innoDependencyPath = join(cwd.path, "build", "inno-depend");
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"git clone https://github.com/DomGries/InnoDependencyInstaller.git $innoDependencyPath",
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void run() async {
|
||||||
|
stdout.writeln("Replace versions");
|
||||||
|
|
||||||
|
final chocoFiles = [
|
||||||
|
join(cwd.path, "choco-struct", "tools", "VERIFICATION.txt"),
|
||||||
|
join(cwd.path, "choco-struct", "spotube.nuspec"),
|
||||||
|
];
|
||||||
|
|
||||||
|
for (final filePath in chocoFiles) {
|
||||||
|
final file = File(filePath);
|
||||||
|
final content = file.readAsStringSync();
|
||||||
|
final newContent =
|
||||||
|
content.replaceAll(versionVarRegExp, versionWithoutBuildNumber);
|
||||||
|
|
||||||
|
file.writeAsStringSync(newContent);
|
||||||
|
}
|
||||||
|
|
||||||
|
await bootstrap();
|
||||||
|
await innoDependInstall();
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"flutter_distributor package --platform=windows --targets=exe --skip-clean",
|
||||||
|
);
|
||||||
|
|
||||||
|
final ogExe = File(
|
||||||
|
join(
|
||||||
|
cwd.path,
|
||||||
|
"dist",
|
||||||
|
pubspec.version.toString(),
|
||||||
|
"spotube-${pubspec.version}-windows-setup.exe",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
final exePath = join(cwd.path, "dist", "Spotube-windows-x86_64-setup.exe");
|
||||||
|
|
||||||
|
await ogExe.copy(exePath);
|
||||||
|
await ogExe.delete();
|
||||||
|
|
||||||
|
stdout.writeln("✅ Windows exe built at $exePath");
|
||||||
|
|
||||||
|
final exeFile = File(exePath);
|
||||||
|
|
||||||
|
final hash = sha256.convert(await exeFile.readAsBytes()).toString();
|
||||||
|
|
||||||
|
final chocoVerificationFile = File(chocoFiles.first);
|
||||||
|
|
||||||
|
chocoVerificationFile.writeAsStringSync(
|
||||||
|
chocoVerificationFile.readAsStringSync().replaceAll(
|
||||||
|
RegExp(r"\%\{\{WIN_SHA256\}\}\%"),
|
||||||
|
hash,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await exeFile.copy(
|
||||||
|
join(cwd.path, "choco-struct", "tools", basename(exeFile.path)),
|
||||||
|
);
|
||||||
|
|
||||||
|
await shell.run(
|
||||||
|
"choco pack ${chocoFiles[1]} --outputdirectory ${join(cwd.path, "dist")}",
|
||||||
|
);
|
||||||
|
|
||||||
|
final chocoNupkg = File(
|
||||||
|
join(cwd.path, "dist", "spotube.$versionWithoutBuildNumber.nupkg"),
|
||||||
|
);
|
||||||
|
|
||||||
|
final distNupkgPath = join(
|
||||||
|
cwd.path,
|
||||||
|
"dist",
|
||||||
|
"Spotube-windows-x86_64.nupkg",
|
||||||
|
);
|
||||||
|
|
||||||
|
await chocoNupkg.copy(distNupkgPath);
|
||||||
|
await chocoNupkg.delete();
|
||||||
|
|
||||||
|
stdout.writeln("✅ Windows nupkg built at $distNupkgPath");
|
||||||
|
}
|
||||||
|
}
|
74
cli/commands/install-dependencies.dart
Normal file
74
cli/commands/install-dependencies.dart
Normal file
@ -0,0 +1,74 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
|
||||||
|
import 'package:args/command_runner.dart';
|
||||||
|
import 'package:process_run/shell_run.dart';
|
||||||
|
|
||||||
|
class InstallDependenciesCommand extends Command {
|
||||||
|
@override
|
||||||
|
String get description => "Install platform dependencies";
|
||||||
|
|
||||||
|
@override
|
||||||
|
String get name => "install-dependencies";
|
||||||
|
|
||||||
|
InstallDependenciesCommand() {
|
||||||
|
argParser.addOption(
|
||||||
|
"platform",
|
||||||
|
abbr: "p",
|
||||||
|
allowed: [
|
||||||
|
"windows",
|
||||||
|
"linux",
|
||||||
|
"linux_arm",
|
||||||
|
"macos",
|
||||||
|
"ios",
|
||||||
|
"android",
|
||||||
|
],
|
||||||
|
mandatory: true,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
FutureOr? run() async {
|
||||||
|
final shell = Shell();
|
||||||
|
|
||||||
|
switch (argResults!.option("platform")) {
|
||||||
|
case "windows":
|
||||||
|
break;
|
||||||
|
case "linux":
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
sudo apt-get update -y
|
||||||
|
sudo apt-get install -y tar clang cmake ninja-build pkg-config libgtk-3-dev make python3-pip python3-setuptools desktop-file-utils libgdk-pixbuf2.0-dev fakeroot strace fuse libunwind-dev locate patchelf gir1.2-appindicator3-0.1 libappindicator3-1 libappindicator3-dev libsecret-1-0 libjsoncpp25 libsecret-1-dev libjsoncpp-dev libnotify-bin libnotify-dev mpv libmpv-dev
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
case "linux_arm":
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
sudo apt-get update -y
|
||||||
|
sudo apt-get install -y pkg-config make python3-pip python3-setuptools
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
case "macos":
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
brew install python-setuptools
|
||||||
|
npm install -g appdmg
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
case "ios":
|
||||||
|
break;
|
||||||
|
case "android":
|
||||||
|
await shell.run(
|
||||||
|
"""
|
||||||
|
sudo apt-get update -y
|
||||||
|
sudo apt-get install -y clang cmake ninja-build pkg-config libgtk-3-dev make python3-pip python3-setuptools patchelf desktop-file-utils libgdk-pixbuf2.0-dev fakeroot strace fuse
|
||||||
|
""",
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
24
cli/core/env.dart
Normal file
24
cli/core/env.dart
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
import 'dart:io';
|
||||||
|
|
||||||
|
enum BuildChannel {
|
||||||
|
stable,
|
||||||
|
nightly;
|
||||||
|
|
||||||
|
factory BuildChannel.fromEnvironment(String name) {
|
||||||
|
final channel = Platform.environment[name]!;
|
||||||
|
if (channel == "stable") {
|
||||||
|
return BuildChannel.stable;
|
||||||
|
} else if (channel == "nightly") {
|
||||||
|
return BuildChannel.nightly;
|
||||||
|
} else {
|
||||||
|
throw Exception("Invalid channel: $channel");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class CliEnv {
|
||||||
|
static final channel = BuildChannel.fromEnvironment("CHANNEL");
|
||||||
|
static final dotenv = Platform.environment["DOTENV"]!;
|
||||||
|
static final ghRunNumber = Platform.environment["GITHUB_RUN_NUMBER"];
|
||||||
|
static final flutterVersion = Platform.environment["FLUTTER_VERSION"]!;
|
||||||
|
}
|
@ -3,6 +3,11 @@ import 'package:spotube/utils/platform.dart';
|
|||||||
|
|
||||||
part 'env.g.dart';
|
part 'env.g.dart';
|
||||||
|
|
||||||
|
enum ReleaseChannel {
|
||||||
|
nightly,
|
||||||
|
stable,
|
||||||
|
}
|
||||||
|
|
||||||
@Envied(obfuscate: true, requireEnvFile: true, path: ".env")
|
@Envied(obfuscate: true, requireEnvFile: true, path: ".env")
|
||||||
abstract class Env {
|
abstract class Env {
|
||||||
@EnviedField(varName: 'SPOTIFY_SECRETS')
|
@EnviedField(varName: 'SPOTIFY_SECRETS')
|
||||||
@ -25,6 +30,13 @@ abstract class Env {
|
|||||||
@EnviedField(varName: 'ENABLE_UPDATE_CHECK', defaultValue: "1")
|
@EnviedField(varName: 'ENABLE_UPDATE_CHECK', defaultValue: "1")
|
||||||
static final String _enableUpdateChecker = _Env._enableUpdateChecker;
|
static final String _enableUpdateChecker = _Env._enableUpdateChecker;
|
||||||
|
|
||||||
|
@EnviedField(varName: "RELEASE_CHANNEL", defaultValue: "nightly")
|
||||||
|
static final String _releaseChannel = _Env._releaseChannel;
|
||||||
|
|
||||||
|
static ReleaseChannel get releaseChannel => _releaseChannel == "stable"
|
||||||
|
? ReleaseChannel.stable
|
||||||
|
: ReleaseChannel.nightly;
|
||||||
|
|
||||||
static bool get enableUpdateChecker =>
|
static bool get enableUpdateChecker =>
|
||||||
kIsFlatpak || _enableUpdateChecker == "1";
|
kIsFlatpak || _enableUpdateChecker == "1";
|
||||||
|
|
||||||
|
@ -5,18 +5,23 @@ import 'package:version/version.dart';
|
|||||||
|
|
||||||
class RootAppUpdateDialog extends StatelessWidget {
|
class RootAppUpdateDialog extends StatelessWidget {
|
||||||
final Version? version;
|
final Version? version;
|
||||||
const RootAppUpdateDialog({super.key, this.version});
|
final int? nightlyBuildNum;
|
||||||
|
|
||||||
|
const RootAppUpdateDialog({super.key, this.version}) : nightlyBuildNum = null;
|
||||||
|
const RootAppUpdateDialog.nightly({super.key, required this.nightlyBuildNum})
|
||||||
|
: version = null;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
const url = "https://spotube.krtirtho.dev/downloads";
|
const url = "https://spotube.krtirtho.dev/downloads";
|
||||||
|
const nightlyUrl = "https://spotube.krtirtho.dev/downloads/nightly";
|
||||||
return AlertDialog(
|
return AlertDialog(
|
||||||
title: const Text("Spotube has an update"),
|
title: const Text("Spotube has an update"),
|
||||||
actions: [
|
actions: [
|
||||||
FilledButton(
|
FilledButton(
|
||||||
child: const Text("Download Now"),
|
child: const Text("Download Now"),
|
||||||
onPressed: () => launchUrlString(
|
onPressed: () => launchUrlString(
|
||||||
url,
|
nightlyBuildNum != null ? nightlyUrl : url,
|
||||||
mode: LaunchMode.externalApplication,
|
mode: LaunchMode.externalApplication,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@ -24,21 +29,26 @@ class RootAppUpdateDialog extends StatelessWidget {
|
|||||||
content: Column(
|
content: Column(
|
||||||
mainAxisSize: MainAxisSize.min,
|
mainAxisSize: MainAxisSize.min,
|
||||||
children: [
|
children: [
|
||||||
Text("Spotube v$version has been released"),
|
Text(
|
||||||
Row(
|
nightlyBuildNum != null
|
||||||
mainAxisAlignment: MainAxisAlignment.center,
|
? "Spotube Nightly $nightlyBuildNum has been released"
|
||||||
children: [
|
: "Spotube v$version has been released",
|
||||||
const Text("Read the latest "),
|
|
||||||
AnchorButton(
|
|
||||||
"release notes",
|
|
||||||
style: const TextStyle(color: Colors.blue),
|
|
||||||
onTap: () => launchUrlString(
|
|
||||||
url,
|
|
||||||
mode: LaunchMode.externalApplication,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
],
|
|
||||||
),
|
),
|
||||||
|
if (nightlyBuildNum == null)
|
||||||
|
Row(
|
||||||
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
|
children: [
|
||||||
|
const Text("Read the latest "),
|
||||||
|
AnchorButton(
|
||||||
|
"release notes",
|
||||||
|
style: const TextStyle(color: Colors.blue),
|
||||||
|
onTap: () => launchUrlString(
|
||||||
|
url,
|
||||||
|
mode: LaunchMode.externalApplication,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter/services.dart';
|
import 'package:flutter/services.dart';
|
||||||
import 'package:spotube/collections/assets.gen.dart';
|
import 'package:spotube/collections/assets.gen.dart';
|
||||||
|
import 'package:spotube/collections/env.dart';
|
||||||
import 'package:spotube/components/shared/image/universal_image.dart';
|
import 'package:spotube/components/shared/image/universal_image.dart';
|
||||||
import 'package:spotube/components/shared/links/hyper_link.dart';
|
import 'package:spotube/components/shared/links/hyper_link.dart';
|
||||||
import 'package:spotube/components/shared/page_window_title_bar.dart';
|
import 'package:spotube/components/shared/page_window_title_bar.dart';
|
||||||
@ -72,6 +73,13 @@ class AboutSpotube extends HookConsumerWidget {
|
|||||||
Text("v${packageInfo.version}")
|
Text("v${packageInfo.version}")
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
|
TableRow(
|
||||||
|
children: [
|
||||||
|
Text(context.l10n.channel),
|
||||||
|
colon,
|
||||||
|
Text(Env.releaseChannel.name)
|
||||||
|
],
|
||||||
|
),
|
||||||
TableRow(
|
TableRow(
|
||||||
children: [
|
children: [
|
||||||
Text(context.l10n.build_number),
|
Text(context.l10n.build_number),
|
||||||
|
@ -335,35 +335,59 @@ abstract class ServiceUtils {
|
|||||||
) async {
|
) async {
|
||||||
if (!Env.enableUpdateChecker) return;
|
if (!Env.enableUpdateChecker) return;
|
||||||
if (!ref.read(userPreferencesProvider.select((s) => s.checkUpdate))) return;
|
if (!ref.read(userPreferencesProvider.select((s) => s.checkUpdate))) return;
|
||||||
|
|
||||||
final packageInfo = await PackageInfo.fromPlatform();
|
final packageInfo = await PackageInfo.fromPlatform();
|
||||||
|
|
||||||
final value = await http.get(
|
if (Env.releaseChannel == ReleaseChannel.nightly) {
|
||||||
Uri.parse(
|
final value = await http.get(
|
||||||
"https://api.github.com/repos/KRTirtho/spotube/releases/latest",
|
Uri.parse(
|
||||||
),
|
"https://api.github.com/repos/KRTirtho/spotube/actions/workflows/spotube-release-binary.yml/runs?status=success&per_page=1",
|
||||||
);
|
),
|
||||||
final tagName =
|
);
|
||||||
(jsonDecode(value.body)["tag_name"] as String).replaceAll("v", "");
|
|
||||||
final currentVersion = packageInfo.version == "Unknown"
|
|
||||||
? null
|
|
||||||
: Version.parse(packageInfo.version);
|
|
||||||
final latestVersion = tagName == "nightly" ? null : Version.parse(tagName);
|
|
||||||
|
|
||||||
if (currentVersion == null ||
|
final buildNum =
|
||||||
latestVersion == null ||
|
jsonDecode(value.body)["workflow_runs"][0]["run_number"] as int;
|
||||||
(latestVersion.isPreRelease && !currentVersion.isPreRelease) ||
|
|
||||||
(!latestVersion.isPreRelease && currentVersion.isPreRelease)) return;
|
|
||||||
|
|
||||||
if (latestVersion <= currentVersion || !context.mounted) return;
|
if (buildNum <= int.parse(packageInfo.buildNumber) || !context.mounted) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
showDialog(
|
await showDialog(
|
||||||
context: context,
|
context: context,
|
||||||
barrierDismissible: true,
|
barrierDismissible: true,
|
||||||
barrierColor: Colors.black26,
|
barrierColor: Colors.black26,
|
||||||
builder: (context) {
|
builder: (context) {
|
||||||
return RootAppUpdateDialog(version: latestVersion);
|
return RootAppUpdateDialog.nightly(nightlyBuildNum: buildNum);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
} else {
|
||||||
|
final value = await http.get(
|
||||||
|
Uri.parse(
|
||||||
|
"https://api.github.com/repos/KRTirtho/spotube/releases/latest",
|
||||||
|
),
|
||||||
|
);
|
||||||
|
final tagName =
|
||||||
|
(jsonDecode(value.body)["tag_name"] as String).replaceAll("v", "");
|
||||||
|
final currentVersion = packageInfo.version == "Unknown"
|
||||||
|
? null
|
||||||
|
: Version.parse(packageInfo.version);
|
||||||
|
final latestVersion =
|
||||||
|
tagName == "nightly" ? null : Version.parse(tagName);
|
||||||
|
|
||||||
|
if (currentVersion == null ||
|
||||||
|
latestVersion == null ||
|
||||||
|
(latestVersion.isPreRelease && !currentVersion.isPreRelease) ||
|
||||||
|
(!latestVersion.isPreRelease && currentVersion.isPreRelease)) return;
|
||||||
|
|
||||||
|
if (latestVersion <= currentVersion || !context.mounted) return;
|
||||||
|
|
||||||
|
showDialog(
|
||||||
|
context: context,
|
||||||
|
barrierDismissible: true,
|
||||||
|
barrierColor: Colors.black26,
|
||||||
|
builder: (context) {
|
||||||
|
return RootAppUpdateDialog(version: latestVersion);
|
||||||
|
},
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
24
pubspec.lock
24
pubspec.lock
@ -45,10 +45,10 @@ packages:
|
|||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: archive
|
name: archive
|
||||||
sha256: "22600aa1e926be775fa5fe7e6894e7fb3df9efda8891c73f70fb3262399a432d"
|
sha256: ecf4273855368121b1caed0d10d4513c7241dfc813f7d3c8933b36622ae9b265
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "3.4.10"
|
version: "3.5.1"
|
||||||
args:
|
args:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -1271,7 +1271,7 @@ packages:
|
|||||||
source: hosted
|
source: hosted
|
||||||
version: "3.1.14"
|
version: "3.1.14"
|
||||||
io:
|
io:
|
||||||
dependency: transitive
|
dependency: "direct dev"
|
||||||
description:
|
description:
|
||||||
name: io
|
name: io
|
||||||
sha256: "2ec25704aba361659e10e3e5f5d672068d332fc8ac516421d483a11e5cbd061e"
|
sha256: "2ec25704aba361659e10e3e5f5d672068d332fc8ac516421d483a11e5cbd061e"
|
||||||
@ -1702,14 +1702,6 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.8"
|
version: "2.1.8"
|
||||||
pointycastle:
|
|
||||||
dependency: transitive
|
|
||||||
description:
|
|
||||||
name: pointycastle
|
|
||||||
sha256: "70fe966348fe08c34bf929582f1d8247d9d9408130723206472b4687227e4333"
|
|
||||||
url: "https://pub.dev"
|
|
||||||
source: hosted
|
|
||||||
version: "3.8.0"
|
|
||||||
pool:
|
pool:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -1734,6 +1726,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "5.0.2"
|
version: "5.0.2"
|
||||||
|
process_run:
|
||||||
|
dependency: "direct dev"
|
||||||
|
description:
|
||||||
|
name: process_run
|
||||||
|
sha256: "8d9c6198b98fbbfb511edd42e7364e24d85c163e47398919871b952dc86a423e"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "0.14.2"
|
||||||
provider:
|
provider:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -2462,7 +2462,7 @@ packages:
|
|||||||
source: hosted
|
source: hosted
|
||||||
version: "1.0.4"
|
version: "1.0.4"
|
||||||
xml:
|
xml:
|
||||||
dependency: transitive
|
dependency: "direct dev"
|
||||||
description:
|
description:
|
||||||
name: xml
|
name: xml
|
||||||
sha256: b015a8ad1c488f66851d762d3090a21c600e479dc75e68328c52774040cf9226
|
sha256: b015a8ad1c488f66851d762d3090a21c600e479dc75e68328c52774040cf9226
|
||||||
|
@ -144,6 +144,9 @@ dev_dependencies:
|
|||||||
freezed: ^2.5.2
|
freezed: ^2.5.2
|
||||||
custom_lint: ^0.6.4
|
custom_lint: ^0.6.4
|
||||||
riverpod_lint: ^2.3.10
|
riverpod_lint: ^2.3.10
|
||||||
|
process_run: ^0.14.2
|
||||||
|
xml: ^6.5.0
|
||||||
|
io: ^1.0.4
|
||||||
|
|
||||||
dependency_overrides:
|
dependency_overrides:
|
||||||
uuid: ^4.4.0
|
uuid: ^4.4.0
|
||||||
|
@ -1,13 +1,16 @@
|
|||||||
|
# Project-level configuration.
|
||||||
cmake_minimum_required(VERSION 3.14)
|
cmake_minimum_required(VERSION 3.14)
|
||||||
project(spotube LANGUAGES CXX)
|
project(spotube LANGUAGES CXX)
|
||||||
|
|
||||||
|
# The name of the executable created for the application. Change this to change
|
||||||
|
# the on-disk name of your application.
|
||||||
set(BINARY_NAME "spotube")
|
set(BINARY_NAME "spotube")
|
||||||
|
|
||||||
cmake_policy(SET CMP0063 NEW)
|
# Explicitly opt in to modern CMake behaviors to avoid warnings with recent
|
||||||
|
# versions of CMake.
|
||||||
|
cmake_policy(VERSION 3.14...3.25)
|
||||||
|
|
||||||
set(CMAKE_INSTALL_RPATH "$ORIGIN/lib")
|
# Define build configuration option.
|
||||||
|
|
||||||
# Configure build options.
|
|
||||||
get_property(IS_MULTICONFIG GLOBAL PROPERTY GENERATOR_IS_MULTI_CONFIG)
|
get_property(IS_MULTICONFIG GLOBAL PROPERTY GENERATOR_IS_MULTI_CONFIG)
|
||||||
if(IS_MULTICONFIG)
|
if(IS_MULTICONFIG)
|
||||||
set(CMAKE_CONFIGURATION_TYPES "Debug;Profile;Release"
|
set(CMAKE_CONFIGURATION_TYPES "Debug;Profile;Release"
|
||||||
@ -20,7 +23,7 @@ else()
|
|||||||
"Debug" "Profile" "Release")
|
"Debug" "Profile" "Release")
|
||||||
endif()
|
endif()
|
||||||
endif()
|
endif()
|
||||||
|
# Define settings for the Profile build mode.
|
||||||
set(CMAKE_EXE_LINKER_FLAGS_PROFILE "${CMAKE_EXE_LINKER_FLAGS_RELEASE}")
|
set(CMAKE_EXE_LINKER_FLAGS_PROFILE "${CMAKE_EXE_LINKER_FLAGS_RELEASE}")
|
||||||
set(CMAKE_SHARED_LINKER_FLAGS_PROFILE "${CMAKE_SHARED_LINKER_FLAGS_RELEASE}")
|
set(CMAKE_SHARED_LINKER_FLAGS_PROFILE "${CMAKE_SHARED_LINKER_FLAGS_RELEASE}")
|
||||||
set(CMAKE_C_FLAGS_PROFILE "${CMAKE_C_FLAGS_RELEASE}")
|
set(CMAKE_C_FLAGS_PROFILE "${CMAKE_C_FLAGS_RELEASE}")
|
||||||
@ -30,6 +33,10 @@ set(CMAKE_CXX_FLAGS_PROFILE "${CMAKE_CXX_FLAGS_RELEASE}")
|
|||||||
add_definitions(-DUNICODE -D_UNICODE)
|
add_definitions(-DUNICODE -D_UNICODE)
|
||||||
|
|
||||||
# Compilation settings that should be applied to most targets.
|
# Compilation settings that should be applied to most targets.
|
||||||
|
#
|
||||||
|
# Be cautious about adding new options here, as plugins use this function by
|
||||||
|
# default. In most cases, you should add new options to specific targets instead
|
||||||
|
# of modifying this function.
|
||||||
function(APPLY_STANDARD_SETTINGS TARGET)
|
function(APPLY_STANDARD_SETTINGS TARGET)
|
||||||
target_compile_features(${TARGET} PUBLIC cxx_std_17)
|
target_compile_features(${TARGET} PUBLIC cxx_std_17)
|
||||||
target_compile_options(${TARGET} PRIVATE /W4 /WX /wd"4100")
|
target_compile_options(${TARGET} PRIVATE /W4 /WX /wd"4100")
|
||||||
@ -38,14 +45,14 @@ function(APPLY_STANDARD_SETTINGS TARGET)
|
|||||||
target_compile_definitions(${TARGET} PRIVATE "$<$<CONFIG:Debug>:_DEBUG>")
|
target_compile_definitions(${TARGET} PRIVATE "$<$<CONFIG:Debug>:_DEBUG>")
|
||||||
endfunction()
|
endfunction()
|
||||||
|
|
||||||
set(FLUTTER_MANAGED_DIR "${CMAKE_CURRENT_SOURCE_DIR}/flutter")
|
|
||||||
|
|
||||||
# Flutter library and tool build rules.
|
# Flutter library and tool build rules.
|
||||||
|
set(FLUTTER_MANAGED_DIR "${CMAKE_CURRENT_SOURCE_DIR}/flutter")
|
||||||
add_subdirectory(${FLUTTER_MANAGED_DIR})
|
add_subdirectory(${FLUTTER_MANAGED_DIR})
|
||||||
|
|
||||||
# Application build
|
# Application build; see runner/CMakeLists.txt.
|
||||||
add_subdirectory("runner")
|
add_subdirectory("runner")
|
||||||
|
|
||||||
|
|
||||||
# Generated plugin build rules, which manage building the plugins and adding
|
# Generated plugin build rules, which manage building the plugins and adding
|
||||||
# them to the application.
|
# them to the application.
|
||||||
include(flutter/generated_plugins.cmake)
|
include(flutter/generated_plugins.cmake)
|
||||||
@ -80,6 +87,12 @@ if(PLUGIN_BUNDLED_LIBRARIES)
|
|||||||
COMPONENT Runtime)
|
COMPONENT Runtime)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
|
# Copy the native assets provided by the build.dart from all packages.
|
||||||
|
set(NATIVE_ASSETS_DIR "${PROJECT_BUILD_DIR}native_assets/windows/")
|
||||||
|
install(DIRECTORY "${NATIVE_ASSETS_DIR}"
|
||||||
|
DESTINATION "${INSTALL_BUNDLE_LIB_DIR}"
|
||||||
|
COMPONENT Runtime)
|
||||||
|
|
||||||
# Fully re-copy the assets directory on each build to avoid having stale files
|
# Fully re-copy the assets directory on each build to avoid having stale files
|
||||||
# from a previous install.
|
# from a previous install.
|
||||||
set(FLUTTER_ASSET_DIR_NAME "flutter_assets")
|
set(FLUTTER_ASSET_DIR_NAME "flutter_assets")
|
||||||
|
@ -60,16 +60,16 @@ IDI_APP_ICON ICON "resources\\app_icon.ico"
|
|||||||
// Version
|
// Version
|
||||||
//
|
//
|
||||||
|
|
||||||
#ifdef FLUTTER_BUILD_NUMBER
|
#if defined(FLUTTER_VERSION_MAJOR) && defined(FLUTTER_VERSION_MINOR) && defined(FLUTTER_VERSION_PATCH) && defined(FLUTTER_VERSION_BUILD)
|
||||||
#define VERSION_AS_NUMBER FLUTTER_BUILD_NUMBER
|
#define VERSION_AS_NUMBER FLUTTER_VERSION_MAJOR,FLUTTER_VERSION_MINOR,FLUTTER_VERSION_PATCH,FLUTTER_VERSION_BUILD
|
||||||
#else
|
#else
|
||||||
#define VERSION_AS_NUMBER 1,0,0
|
#define VERSION_AS_NUMBER 1,0,0,0
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef FLUTTER_BUILD_NAME
|
#if defined(FLUTTER_VERSION)
|
||||||
#define VERSION_AS_STRING #FLUTTER_BUILD_NAME
|
#define VERSION_AS_STRING FLUTTER_VERSION
|
||||||
#else
|
#else
|
||||||
#define VERSION_AS_STRING "%{{SPOTUBE_VERSION}}%"
|
#define VERSION_AS_STRING "3.6.0"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
VS_VERSION_INFO VERSIONINFO
|
VS_VERSION_INFO VERSIONINFO
|
||||||
@ -93,7 +93,7 @@ BEGIN
|
|||||||
VALUE "FileDescription", "Spotube" "\0"
|
VALUE "FileDescription", "Spotube" "\0"
|
||||||
VALUE "FileVersion", VERSION_AS_STRING "\0"
|
VALUE "FileVersion", VERSION_AS_STRING "\0"
|
||||||
VALUE "InternalName", "spotube" "\0"
|
VALUE "InternalName", "spotube" "\0"
|
||||||
VALUE "LegalCopyright", "Copyright (C) 2022 oss.krtirtho. All rights reserved." "\0"
|
VALUE "LegalCopyright", "Copyright (C) 2024 oss.krtirtho. All rights reserved." "\0"
|
||||||
VALUE "OriginalFilename", "spotube.exe" "\0"
|
VALUE "OriginalFilename", "spotube.exe" "\0"
|
||||||
VALUE "ProductName", "spotube" "\0"
|
VALUE "ProductName", "spotube" "\0"
|
||||||
VALUE "ProductVersion", VERSION_AS_STRING "\0"
|
VALUE "ProductVersion", VERSION_AS_STRING "\0"
|
||||||
|
Loading…
Reference in New Issue
Block a user