diff --git a/.github/workflows/ci_android.yml b/.github/workflows/ci_android.yml index b502c1cc..4aa908eb 100644 --- a/.github/workflows/ci_android.yml +++ b/.github/workflows/ci_android.yml @@ -41,7 +41,7 @@ jobs: - name: Build APK run: | - bash ./run_build.sh android dummy + dart build_release.dart android dummy - if: github.event_name == 'workflow_dispatch' && github.event.inputs.tag_name != 'nightly' name: Release diff --git a/.github/workflows/ci_windows.yml b/.github/workflows/ci_windows.yml index 9e3dde5b..b7cc515d 100644 --- a/.github/workflows/ci_windows.yml +++ b/.github/workflows/ci_windows.yml @@ -14,7 +14,12 @@ jobs: steps: - name: Checkout uses: actions/checkout@v2 - + - name: Workaround - Export pub environment variable on Windows + run: | + if [ "$RUNNER_OS" == "Windows" ]; then + echo "PUB_CACHE=$LOCALAPPDATA\\Pub\\Cache" >> $GITHUB_ENV + fi + shell: bash - name: Install Flutter uses: subosito/flutter-action@v2 with: @@ -28,11 +33,7 @@ jobs: - name: Build Executable run: | - .\run_build.bat windows dummy - - - name: Package Executable - run: 7z a -r -sse ..\..\..\..\build\app\app-release.zip * - working-directory: build\windows\runner\Release + dart build_release.dart windows dummy - if: github.event_name == 'workflow_dispatch' && github.event.inputs.tag_name != 'nightly' name: Release diff --git a/build_release.dart b/build_release.dart new file mode 100644 index 00000000..74ed251a --- /dev/null +++ b/build_release.dart @@ -0,0 +1,153 @@ +// ignore_for_file: avoid_print + +/* + * Copyright (C) 2024 DanXi-Dev + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +import 'dart:io'; + +import 'package:archive/archive_io.dart'; +import 'package:git/git.dart'; +import 'package:path/path.dart' as p; + +void main(List arguments) async { + if (arguments.isEmpty || + !['android', 'windows', 'aab'].contains(arguments[0])) { + print('A valid target is required: android, windows, aab'); + exit(1); + } + + print('Warning: Before building task, ensure that you have uncommented'); + print( + 'the line "signingConfig signingConfigs.release" in android/app/build.gradle,'); + print('and choose your signing key in android/key.properties.'); + + String? versionCode; + if (arguments.length > 1) { + versionCode = arguments[1]; + print('Version code: $versionCode'); + } else { + print('Please enter the version code:'); + versionCode = stdin.readLineSync(); + } + + String gitHash; + if (await GitDir.isGitDir(p.current)) { + final gitDir = await GitDir.fromExisting(p.current); + final head = await gitDir.currentBranch(); + gitHash = head.sha.substring(0, 7); + } else { + print( + 'This script must be run in a directory containing a git repository.'); + exit(1); + } + + print('Start building...'); + + print('Run build_runner...'); + await runDartProcess( + ['run', 'build_runner', 'build', '--delete-conflicting-outputs']); + + switch (arguments[0]) { + case 'android': + await buildAndroid(versionCode, gitHash); + break; + case 'windows': + await buildWindows(versionCode, gitHash); + break; + case 'aab': + await buildAppBundle(versionCode, gitHash); + break; + } +} + +Future runFlutterProcess(List args) async { + final buildProcess = await Process.start('flutter', args, runInShell: true); + stdout.addStream(buildProcess.stdout); + stderr.addStream(buildProcess.stderr); + return await buildProcess.exitCode; +} + +Future runDartProcess(List args) async { + final buildProcess = await Process.start('dart', args, runInShell: true); + stdout.addStream(buildProcess.stdout); + stderr.addStream(buildProcess.stderr); + return await buildProcess.exitCode; +} + +Future buildAndroid(String? versionCode, String gitHash) async { + print('Build for Android...'); + await runFlutterProcess([ + 'build', + 'apk', + '--release', + '--dart-define=GIT_HASH=$gitHash', + ]); + + print('Clean old files...'); + File oldFile = File('build/app/DanXi-$versionCode-release.android.apk'); + if (oldFile.existsSync()) { + oldFile.deleteSync(); + } + print('Copy file...'); + File newFile = File('build/app/DanXi-$versionCode-release.android.apk'); + File sourceFile = File('build/app/outputs/flutter-apk/app-release.apk'); + sourceFile.copySync(newFile.path); + print('Build success.'); +} + +Future buildWindows(String? versionCode, String gitHash) async { + print('Build for Windows...'); + await runFlutterProcess([ + 'build', + 'windows', + '--release', + '--dart-define=GIT_HASH=$gitHash', + ]); + + print('Clean old files...'); + File oldFile = File('build/app/DanXi-$versionCode-release.windows-x64.zip'); + if (oldFile.existsSync()) { + oldFile.deleteSync(); + } + print('Compress file...'); + var encoder = ZipFileEncoder(); + File newFile = File('build/app/DanXi-$versionCode-release.windows-x64.zip'); + Directory sourceDir = Directory('build/windows/runner/Release'); + encoder.zipDirectory(sourceDir, filename: newFile.path); + print('Build success.'); +} + +Future buildAppBundle(String? versionCode, String gitHash) async { + print('Build for App Bundle (Google Play Distribution)...'); + await runFlutterProcess([ + 'build', + 'appbundle', + '--release', + '--dart-define=GIT_HASH=$gitHash', + ]); + + print('Clean old files...'); + File oldFile = File('build/app/DanXi-$versionCode-release.android.aab'); + if (oldFile.existsSync()) { + oldFile.deleteSync(); + } + print('Copy file...'); + File newFile = File('build/app/DanXi-$versionCode-release.android.aab'); + File sourceFile = File('build/app/outputs/bundle/release/app-release.aab'); + sourceFile.copySync(newFile.path); + print('Build success.'); +} diff --git a/pubspec.lock b/pubspec.lock index 17557416..0e7fac1b 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -18,7 +18,7 @@ packages: source: hosted version: "6.4.1" archive: - dependency: transitive + dependency: "direct dev" description: name: archive sha256: "22600aa1e926be775fa5fe7e6894e7fb3df9efda8891c73f70fb3262399a432d" @@ -824,6 +824,14 @@ packages: url: "https://pub.dev" source: hosted version: "2.3.0" + git: + dependency: "direct dev" + description: + name: git + sha256: "1982737427ef1ef2bb69027ea0234469774495e86afe202de81ee46d37364e55" + url: "https://pub.dev" + source: hosted + version: "2.2.1" glob: dependency: transitive description: @@ -1196,7 +1204,7 @@ packages: source: hosted version: "2.1.0" path: - dependency: transitive + dependency: "direct dev" description: name: path sha256: "087ce49c3f0dc39180befefc60fdb4acd8f8620e5682fe2476afd0b3688bb4af" diff --git a/pubspec.yaml b/pubspec.yaml index 12306d3f..cbe3e245 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -119,6 +119,10 @@ dev_dependencies: sdk: flutter flutter_lints: ^3.0.0 intl_utils: ^2.8.5 + # below used in build.dart + archive: ^3.4.10 + git: ^2.2.1 + path: ^1.9.0 flutter_intl: enabled: true diff --git a/run_build.bat b/run_build.bat deleted file mode 100644 index d3491046..00000000 --- a/run_build.bat +++ /dev/null @@ -1,69 +0,0 @@ -@echo off -setlocal enabledelayedexpansion - -echo. -echo Warning: Before building task, ensure that you have uncommented -echo the line "signingConfig signingConfigs.release" in android/app/build.gradle, -echo and choose your signing key in android/key.properties. -echo. -if "%~2"=="" ( - set /p version_code=Input your version name to continue: -) else ( - set version_code=%~2 -) -echo Start building... - -for /f %%i in ('git rev-parse --short HEAD') do set GIT_HASH=%%i - -:exec_build_runner -echo Executing build runner... -echo. -start /WAIT cmd /C dart run build_runner build --delete-conflicting-outputs - -if "%~1"=="android" ( - goto build_android -) else if "%~1"=="windows" ( - goto build_windows -) else if "%~1"=="aab" ( - goto build_app_bundle -) else ( - printf "A valid target is required: android, windows, aab\n" - exit /b 1 -) - -:build_android -echo Build for Android... -echo. -echo Clean old files... -del /Q build\app\DanXi-%version_code%-release.android.apk -start /WAIT cmd /C flutter build apk --release --dart-define=GIT_HASH=!GIT_HASH! -echo Copy file... -copy build\app\outputs\flutter-apk\app-release.apk build\app\DanXi-%version_code%-release.android.apk -echo. -goto end_success - -:build_windows -echo Build for Windows... -echo. -start /WAIT cmd /C flutter build windows --release --dart-define=GIT_HASH=!GIT_HASH! -echo Clean old files... -del /Q build\app\DanXi-%version_code%-release.windows-x64.zip -cd build\windows\runner\Release\ -echo Copy file... -7z a -r -sse ..\..\..\..\build\app\DanXi-%version_code%-release.windows-x64.zip * -cd ..\..\..\..\ -echo. -goto end_success - -:build_app_bundle -echo Build for App Bundle (Google Play Distribution)... -echo. -echo Clean old files... -del /Q build\app\DanXi-%version_code%-release.android.aab -start /WAIT cmd /C flutter build appbundle --release --dart-define=GIT_HASH=!GIT_HASH! -echo Copy file... -copy build\app\outputs\bundle\release\app-release.aab build\app\DanXi-%version_code%-release.android.aab -goto end_success - -:end_success -echo Build success. diff --git a/run_build.ps1 b/run_build.ps1 deleted file mode 100644 index e7ad8ef7..00000000 --- a/run_build.ps1 +++ /dev/null @@ -1,61 +0,0 @@ -param( - [string]$target, - [string]$version_code -) - -if (-not $version_code) { - $version_code = Read-Host -Prompt "Input your version name to continue" -} - -Write-Output "Start building..." - -$GIT_HASH = git rev-parse --short HEAD - -Write-Output "Executing build runner..." -Start-Process -Wait -NoNewWindow -FilePath "cmd.exe" -ArgumentList "/C dart run build_runner build --delete-conflicting-outputs" - -switch ($target) { - "android" { - & { - Write-Output "Build for Android..." - Write-Output "" - Write-Output "Clean old files..." - Remove-Item -Force -Path "build\app\DanXi-$version_code-release.android.apk" - Start-Process -Wait -NoNewWindow -FilePath "cmd.exe" -ArgumentList "/C flutter build apk --release --dart-define=GIT_HASH=$GIT_HASH" - Write-Output "Copy file..." - Copy-Item -Path "build\app\outputs\flutter-apk\app-release.apk" -Destination "build\app\DanXi-$version_code-release.android.apk" - Write-Output "" - } - } - "windows" { - & { - Write-Output "Build for Windows..." - Write-Output "" - Start-Process -Wait -NoNewWindow -FilePath "cmd.exe" -ArgumentList "/C flutter build windows --release --dart-define=GIT_HASH=$GIT_HASH" - Write-Output "Clean old files..." - Remove-Item -Force -Path "build\app\DanXi-$version_code-release.windows-x64.zip" - Set-Location -Path "build\windows\runner\Release\" - Write-Output "Copy file..." - 7z a -r -sse "..\..\..\..\build\app\DanXi-$version_code-release.windows-x64.zip" * - Set-Location -Path "..\..\..\..\" - Write-Output "" - } - } - "aab" { - & { - Write-Output "Build for App Bundle (Google Play Distribution)..." - Write-Output "" - Write-Output "Clean old files..." - Remove-Item -Force -Path "build\app\DanXi-$version_code-release.android.aab" - Start-Process -Wait -NoNewWindow -FilePath "cmd.exe" -ArgumentList "/C flutter build appbundle --release --dart-define=GIT_HASH=$GIT_HASH" - Write-Output "Copy file..." - Copy-Item -Path "build\app\outputs\bundle\release\app-release.aab" -Destination "build\app\DanXi-$version_code-release.android.aab" - } - } - default { - Write-Error "A valid target is required: android, windows, aab" - exit 1 - } -} - -Write-Output "Build success." diff --git a/run_build.sh b/run_build.sh deleted file mode 100644 index f8f65f33..00000000 --- a/run_build.sh +++ /dev/null @@ -1,84 +0,0 @@ -#!/bin/bash - -# -# Copyright (C) 2024 DanXi-Dev -# -# This program is free software: you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation, either version 3 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License -# along with this program. If not, see . -# - -# if the 2nd argument is provided, it will be used as the version code -echo "Warning: Before building task, ensure that you have uncommented" -echo "the line \"signingConfig signingConfigs.release\" in android/app/build.gradle," -echo "and choose your signing key in android/key.properties." -echo -if [ -z "$2" ]; then - read -p "Input your version name to continue: " version_code -else - version_code=$2 -fi -echo "Start building..." - -# get current hash -git_hash=$(git rev-parse --short HEAD) - -ENV_FLAG="--dart-define=GIT_HASH=$git_hash" - -exec_build_runner() { - echo "Executing build runner..." - dart run build_runner build --delete-conflicting-outputs -} - -build_android() { - echo "Build for Android..." - echo "Clean old files..." - rm -f build/app/DanXi-$version_code-release.android.apk - flutter build apk --release $ENV_FLAG - echo "Copy file..." - cp build/app/outputs/flutter-apk/app-release.apk build/app/DanXi-$version_code-release.android.apk - echo -} - -build_windows() { - echo "Build for Windows..." - flutter build windows --release $ENV_FLAG - echo "Clean old files..." - rm -f build/app/DanXi-$version_code-release.windows-x64.zip - pushd build/windows/runner/Release/ - echo "Copy file..." - 7z a -r -sse ../../../../build/app/DanXi-$version_code-release.windows-x64.zip * - popd - echo -} - -build_bundle() { - echo "Build for Android App Bundle..." - echo "Clean old files..." - rm -f build/app/DanXi-$version_code-release.android.aab - flutter build appbundle --release $ENV_FLAG - echo "Copy file..." - cp build/app/outputs/bundle/release/app-release.aab build/app/DanXi-$version_code-release.android.aab - echo -} - -exec_build_runner - -if [ "$1" == "android" ]; then - build_android -elif [ "$1" == "windows" ]; then - build_windows -elif [ "$1" == "aab" ]; then - build_bundle -else - printf "A valid target is required: android, windows, aab\n" -fi \ No newline at end of file