feat(ci/cd): Add Android builds and quality checks (#694)

This commit is contained in:
Gauvain
2025-06-02 13:14:20 +02:00
committed by GitHub
parent 5899cc8625
commit ce00aeb5f1
19 changed files with 728 additions and 192 deletions

View File

@@ -0,0 +1,142 @@
Streamyfin
Jellyfin
TVOS
Expo
submodule-reload
prebuild
bun
biome
Gradle
APK
AAB
Android
iOS
React
ReactDOM
ReactNative
TypeScript
JavaScript
NodeJS
Yarn
npm
Babel
Husky
Jest
Lodash
Zod
Axios
i18next
Jotai
TailwindCSS
NativeWind
Zeego
Shopify
FlashList
MMKV
Podfile
CocoaPods
async
backend
boolean
callback
config
const
dequeue
endpoint
frontend
getter
initializer
middleware
namespace
nullable
param
params
preload
reducer
refactor
runtime
singleton
slug
submodule
thunk
token
utils
uuid
webpack
API
CLI
CPU
DB
DEV
ENV
ID
JSON
OS
PR
SHA
UI
URL
UTF
UUID
VSCode
XML
GitHub
GitLab
Bitbucket
Apple
Google
PlayStore
AppStore
Xcode
FlatList
ScrollView
TouchableOpacity
ViewPager
SafeArea
Navigator
NavigatorIOS
Drawer
BottomSheet
TabView
Reanimated
GestureHandler
ContextMenu
WebView
ProgressBar
Carousel
Slider
VolumeManager
EdgeToEdge
CircularProgress
VisibilitySensor
BackgroundDownloader
NetInfo
ActionSheet
MaterialTopTabs
BottomTabs
ReactQuery
DeviceInfo
ImageColors
LinearGradient
Localization
Notifications
ScreenOrientation
Sensors
Sharing
SplashScreen
StatusBar
SystemUI
TaskManager
Updates
WebBrowser
TODO
FIXME
README
Changelog
Docs
Docstring
Linter
Formatter
Prettier
ESLint
Stylelint

13
.github/spell-check.json vendored Normal file
View File

@@ -0,0 +1,13 @@
{
"ignore_files": [
"**/node_modules/**",
"**/bun.lockb",
"**/android/**",
"**/ios/**",
"**/*.apk",
"**/*.aab",
"**/*.ipa",
".github/actions/spell-check-this/dictionary.txt",
".github/spell-check.json"
]
}

80
.github/workflows/build-android.yml vendored Normal file
View File

@@ -0,0 +1,80 @@
name: 🤖 Android APK Build
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
on:
workflow_dispatch:
pull_request:
branches: [develop, master]
push:
branches: [develop, master]
jobs:
build:
runs-on: ubuntu-24.04
name: 🏗️ Build Android APK
permissions:
contents: read
steps:
- name: 📥 Checkout code
uses: actions/checkout@v4.2.2
with:
ref: ${{ github.event.pull_request.head.sha || github.sha }}
show-progress: false
submodules: recursive
fetch-depth: 0
- name: 🍞 Setup Bun
uses: oven-sh/setup-bun@v2.0.2
with:
# @todo: update to 1.x once this is fixed: https://github.com/streamyfin/streamyfin/pull/690#discussion_r2089749689
bun-version: '1.2.13'
- name: ☕ Setup JDK
uses: actions/setup-java@v4.7.1
with:
distribution: 'zulu'
java-version: '17'
- name: 💾 Cache Bun dependencies
uses: actions/cache@v4
with:
path: ~/.bun/install/cache
key: ${{ runner.os }}-bun-cache-${{ hashFiles('bun.lock') }}
restore-keys: |
${{ runner.os }}-bun-cache-
- name: 📦 Install dependencies
run: |
bun install --frozen-lockfile
bun run submodule-reload
- name: 💾 Cache Android dependencies
uses: actions/cache@v4
with:
path: |
android/.gradle
key: ${{ runner.os }}-android-deps-${{ hashFiles('android/**/build.gradle') }}
restore-keys: |
${{ runner.os }}-android-deps-
- name: 🛠️ Generate project files
run: bun run prebuild
- name: 🚀 Build APK via Bun
run: bun run build:android:local
- name: 📅 Set date tag
run: echo "DATE_TAG=$(date +%d-%m-%Y_%H-%M-%S)" >> $GITHUB_ENV
- name: 📤 Upload APK artifact
uses: actions/upload-artifact@v4.6.2
with:
name: streamyfin-apk-${{ github.sha }}-${{ env.DATE_TAG }}
path: |
android/app/build/outputs/apk/release/*.apk
android/app/build/outputs/bundle/release/*.aab
retention-days: 7

View File

@@ -1,25 +1,51 @@
name: Automatic Build and Deploy
name: 🤖 iOS IPA Build
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
on:
workflow_dispatch:
push:
branches:
- main
# push:
# branches: [develop]
jobs:
build:
runs-on: macos-15
name: Build IOS
name: 🏗️ Build iOS IPA
permissions:
contents: read
steps:
- uses: actions/checkout@v2
name: Check out repository
- uses: oven-sh/setup-bun@v2
- name: 📥 Check out repository
uses: actions/checkout@v4.2.2
with:
bun-version: latest
- run: |
ref: ${{ github.event.pull_request.head.sha || github.sha }}
show-progress: false
submodules: recursive
fetch-depth: 0
- name: 🍞 Setup Bun
uses: oven-sh/setup-bun@v2.0.2
with:
# @todo: update to 1.x once this is fixed: https://github.com/streamyfin/streamyfin/pull/690#discussion_r2089749689
bun-version: '1.2.13'
- name: 💾 Cache Bun dependencies
uses: actions/cache@v4
with:
path: ~/.bun/install/cache
key: ${{ runner.os }}-bun-cache-${{ hashFiles('bun.lock') }}
restore-keys: |
${{ runner.os }}-bun-cache-
- name: 📦 Install & Prepare
run: |
bun i && bun run submodule-reload
npx expo prebuild
- uses: sparkfabrik/ios-build-action@v2.3.0
- name: 🏗️ Build iOS app
uses: sparkfabrik/ios-build-action@v2.3.2
with:
upload-to-testflight: false
increment-build-number: false
@@ -47,3 +73,13 @@ jobs:
#fastlane-env: stage
ios-app-id: com.stetsed.teststreamyfin
output-path: build-${{ github.sha }}.ipa
- name: 📅 Set date tag
run: echo "DATE_TAG=$(date +%d-%m-%Y_%H-%M-%S)" >> $GITHUB_ENV
- name: 📤 Upload IPA artifact
uses: actions/upload-artifact@v4.6.2
with:
name: streamyfin-ipa-${{ github.sha }}-${{ env.DATE_TAG }}
path: build-*.ipa
retention-days: 7

47
.github/workflows/check-lockfile.yml vendored Normal file
View File

@@ -0,0 +1,47 @@
name: 🔒 Lockfile Consistency Check
on:
pull_request:
branches: [develop, master]
push:
branches: [develop, master]
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
jobs:
check-lockfile:
name: 🔍 Check bun.lock and package.json consistency
runs-on: ubuntu-24.04
permissions:
contents: read
steps:
- name: 📥 Checkout repository
uses: actions/checkout@v4.2.2
with:
ref: ${{ github.event.pull_request.head.sha || github.sha }}
show-progress: false
submodules: recursive
fetch-depth: 0
- name: 🍞 Setup Bun
uses: oven-sh/setup-bun@v2.0.2
# @todo: update to 1.x once this is fixed: https://github.com/streamyfin/streamyfin/pull/690#discussion_r2089749689
with:
bun-version: '1.2.13'
- name: 💾 Cache Bun dependencies
uses: actions/cache@v4.2.3
with:
path: |
~/.bun/install/cache
key: ${{ runner.os }}-bun-${{ hashFiles('bun.lock') }}
- name: 🛡️ Verify lockfile consistency
run: |
set -euxo pipefail
echo "➡️ Checking for discrepancies between bun.lock and package.json..."
bun install --frozen-lockfile --dry-run --ignore-scripts
echo "✅ Lockfile is consistent with package.json!"

66
.github/workflows/check_spelling.yaml vendored Normal file
View File

@@ -0,0 +1,66 @@
name: 📝 Check Spelling
on:
push:
branches:
- develop
- master
pull_request_target:
branches:
- develop
- master
types:
- 'opened'
- 'reopened'
- 'synchronize'
jobs:
spelling:
name: 🔎 Spelling Check
permissions:
contents: read
pull-requests: read
actions: read
outputs:
followup: ${{ steps.spelling.outputs.followup }}
runs-on: ubuntu-24.04
concurrency:
group: spelling-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
steps:
- name: 📥 Checkout repository
uses: actions/checkout@v4.2.2
with:
ref: ${{ github.event.pull_request.head.sha || github.sha }}
show-progress: false
submodules: recursive
fetch-depth: 0
- name: 🪄 Run Spelling Checker
id: spelling
uses: check-spelling/check-spelling@main
with:
checkout: true
check_file_names: 1
spell_check_this: check-spelling/spell-check-this@prerelease
post_comment: 0
warnings: bad-regex,deprecated-feature,noisy-file
extra_dictionaries: |
cspell:software-terms/dict/softwareTerms.txt
local:.github/actions/spell-check-this/dictionary.txt
comment-pr:
name: 💬 Report (PR)
runs-on: ubuntu-24.04
needs: spelling
permissions:
pull-requests: write
if: (success() || failure()) && needs.spelling.outputs.followup
steps:
- name: 💬 Post Spelling Report
uses: check-spelling/check-spelling@main
with:
checkout: true
spell_check_this: check-spelling/spell-check-this@prerelease
task: ${{ needs.spelling.outputs.followup }}

43
.github/workflows/ci-codeql.yml vendored Normal file
View File

@@ -0,0 +1,43 @@
name: 🛡️ CodeQL Analysis
on:
push:
branches: [master, develop]
pull_request:
branches: [master, develop]
schedule:
- cron: '24 2 * * *'
jobs:
analyze:
name: 🔎 Analyze with CodeQL
runs-on: ubuntu-24.04
permissions:
contents: read
security-events: write
strategy:
fail-fast: false
matrix:
language: [ 'javascript-typescript' ]
steps:
- name: 📥 Checkout repository
uses: actions/checkout@v4.2.2
with:
ref: ${{ github.event.pull_request.head.sha || github.sha }}
show-progress: false
fetch-depth: 0
- name: 🏁 Initialize CodeQL
uses: github/codeql-action/init@v3.28.17
with:
languages: ${{ matrix.language }}
queries: +security-extended,security-and-quality
- name: 🛠️ Autobuild
uses: github/codeql-action/autobuild@v3.28.17
- name: 🧪 Perform CodeQL Analysis
uses: github/codeql-action/analyze@v3.28.1

24
.github/workflows/conflict.yml vendored Normal file
View File

@@ -0,0 +1,24 @@
name: 🏷🔀Merge Conflict Labeler
on:
push:
branches: [develop]
pull_request_target:
branches: [develop]
types: [synchronize]
jobs:
label:
name: 🏷️ Labeling Merge Conflicts
runs-on: ubuntu-24.04
if: ${{ github.repository == 'streamyfin/streamyfin' }}
permissions:
contents: read
pull-requests: write
steps:
- name: 🚩 Apply merge conflict label
uses: eps1lon/actions-label-merge-conflict@v3.0.3
with:
dirtyLabel: 'merge conflict'
commentOnDirty: 'This pull request has merge conflicts. Please resolve the conflicts so the PR can be successfully reviewed and merged.'
repoToken: '${{ secrets.GITHUB_TOKEN }}'

View File

@@ -1,41 +0,0 @@
name: "Lint PR"
on:
pull_request_target:
types:
- opened
- edited
- synchronize
- reopened
permissions:
pull-requests: write
jobs:
main:
name: Validate PR title
runs-on: ubuntu-latest
steps:
- uses: amannn/action-semantic-pull-request@v5
id: lint_pr_title
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- uses: marocchino/sticky-pull-request-comment@v2
if: always() && (steps.lint_pr_title.outputs.error_message != null)
with:
header: pr-title-lint-error
message: |
Hey there and thank you for opening this pull request! 👋🏼
We require pull request titles to follow the [Conventional Commits specification](https://www.conventionalcommits.org/en/v1.0.0/) and it looks like your proposed title needs to be adjusted.
Details:
```
${{ steps.lint_pr_title.outputs.error_message }}
```
- if: ${{ steps.lint_pr_title.outputs.error_message == null }}
uses: marocchino/sticky-pull-request-comment@v2
with:
header: pr-title-lint-error
delete: true

View File

@@ -1,28 +0,0 @@
name: Lint
on:
pull_request:
branches: [ develop, master ]
jobs:
lint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Setup Node.js
uses: actions/setup-node@v3
with:
node-version: '20.x'
- name: Setup Bun
uses: oven-sh/setup-bun@v1
with:
bun-version: latest
- name: Install dependencies
run: bun install
- name: Run linting checks
run: bun run check

104
.github/workflows/linting.yml vendored Normal file
View File

@@ -0,0 +1,104 @@
name: 🚦 Security & Quality Gate
on:
pull_request_target:
types: [opened, edited, synchronize, reopened]
branches: [develop, master]
workflow_dispatch:
permissions:
contents: read
jobs:
validate_pr_title:
name: "📝 Validate PR Title"
runs-on: ubuntu-24.04
permissions:
pull-requests: write
contents: read
steps:
- uses: amannn/action-semantic-pull-request@v5.5.3
id: lint_pr_title
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- uses: marocchino/sticky-pull-request-comment@v2.9.2
if: always() && (steps.lint_pr_title.outputs.error_message != null)
with:
header: pr-title-lint-error
message: |
Hey there and thank you for opening this pull request! 👋🏼
We require pull request titles to follow the [Conventional Commits specification](https://www.conventionalcommits.org/en/v1.0.0/).
**Error details:**
```
${{ steps.lint_pr_title.outputs.error_message }}
```
- if: ${{ steps.lint_pr_title.outputs.error_message == null }}
uses: marocchino/sticky-pull-request-comment@v2.9.2
with:
header: pr-title-lint-error
delete: true
dependency-review:
name: 🔍 Vulnerable Dependencies
runs-on: ubuntu-24.04
permissions:
contents: read
steps:
- name: Checkout Repository
uses: actions/checkout@v4.2.2
with:
ref: ${{ github.event.pull_request.head.sha }}
fetch-depth: 0
- name: Dependency Review
uses: actions/dependency-review-action@v4.7.1
with:
fail-on-severity: high
deny-licenses: GPL-3.0, AGPL-3.0
base-ref: ${{ github.event.pull_request.base.sha || 'develop' }}
head-ref: ${{ github.event.pull_request.head.sha || github.ref }}
code_quality:
name: "🔍 Lint & Test (${{ matrix.command }})"
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
command:
- "lint"
- "check"
steps:
- name: "📥 Checkout PR code"
uses: actions/checkout@v4.2.2
with:
ref: ${{ github.event.pull_request.head.sha }}
submodules: recursive
fetch-depth: 0
- name: "🟢 Setup Node.js"
uses: actions/setup-node@v4.4.0
with:
node-version: '20.x'
cache: bun
- name: "🍞 Setup Bun"
uses: oven-sh/setup-bun@v2.0.2
with:
# @todo: update to 1.x once this is fixed: https://github.com/streamyfin/streamyfin/pull/690#discussion_r2089749689
bun-version: '1.2.13'
- name: 💾 Cache Bun dependencies
uses: actions/cache@v4.2.3
with:
path: |
~/.bun/install/cache
key: ${{ runner.os }}-bun-${{ hashFiles('bun.lock') }}
- name: "📦 Install dependencies"
run: bun install --frozen-lockfile
- name: "🚨 Run ${{ matrix.command }}"
run: bun run ${{ matrix.command }}

View File

@@ -1,39 +0,0 @@
name: Handle Stale Issues
on:
schedule:
- cron: "30 1 * * *" # Runs at 1:30 UTC every day
jobs:
stale:
runs-on: ubuntu-latest
permissions:
issues: write
pull-requests: write
steps:
- uses: actions/stale@v9
with:
# Issue specific settings
days-before-issue-stale: 90
days-before-issue-close: 7
stale-issue-label: "stale"
stale-issue-message: |
This issue has been automatically marked as stale because it has had no activity in the last 30 days.
If this issue is still relevant, please leave a comment to keep it open.
Otherwise, it will be closed in 7 days if no further activity occurs.
Thank you for your contributions!
close-issue-message: |
This issue has been automatically closed because it has been inactive for 7 days since being marked as stale.
If you believe this issue is still relevant, please feel free to reopen it and add a comment explaining the current status.
# Pull request settings (disabled)
days-before-pr-stale: -1
days-before-pr-close: -1
# Other settings
repo-token: ${{ secrets.GITHUB_TOKEN }}
operations-per-run: 100
exempt-issue-labels: "Roadmap v1,help needed,enhancement"

View File

@@ -1,18 +0,0 @@
name: Discord Pull Request Notification
on:
pull_request:
types: [opened, reopened]
jobs:
notify:
runs-on: ubuntu-latest
steps:
- uses: joelwmale/webhook-action@master
with:
url: ${{ secrets.DISCORD_WEBHOOK_URL }}
body: |
{
"content": "New Pull Request: ${{ github.event.pull_request.title }}\nBy: ${{ github.event.pull_request.user.login }}\n\n${{ github.event.pull_request.html_url }}",
"avatar_url": "https://avatars.githubusercontent.com/u/193271640"
}

24
.github/workflows/notification.yml vendored Normal file
View File

@@ -0,0 +1,24 @@
name: 🛎️ Discord Pull Request Notification
on:
pull_request:
types: [opened, reopened]
branches: [develop]
jobs:
notify:
runs-on: ubuntu-24.04
steps:
- name: 🛎️ Notify Discord
uses: Ilshidur/action-discord@0.3.2
env:
DISCORD_WEBHOOK: ${{ secrets.DISCORD_WEBHOOK_URL }}
DISCORD_AVATAR: https://avatars.githubusercontent.com/u/193271640
with:
args: |
📢 New Pull Request in **${{ github.repository }}**
**Title:** ${{ github.event.pull_request.title }}
**By:** ${{ github.event.pull_request.user.login }}
**Branch:** ${{ github.event.pull_request.head.ref }}
**Description:** ${{ github.event.pull_request.body }}
🔗 ${{ github.event.pull_request.html_url }}

49
.github/workflows/stale.yml vendored Normal file
View File

@@ -0,0 +1,49 @@
name: 🕒 Handle Stale Issues
on:
schedule:
# Runs daily at 1:30 AM UTC (3:30 AM CEST - France time)
- cron: "30 1 * * *"
jobs:
stale-issues:
name: 🗑️ Cleanup Stale Issues
runs-on: ubuntu-24.04
permissions:
issues: write
pull-requests: write
steps:
- name: 🔄 Mark/Close Stale Issues
uses: actions/stale@v9.1.0
with:
# Global settings
repo-token: ${{ secrets.GITHUB_TOKEN }}
operations-per-run: 500 # Increase if you have >1000 issues
log-level: debug
# Issue configuration
days-before-issue-stale: 90
days-before-issue-close: 7
stale-issue-label: "stale"
exempt-issue-labels: "Roadmap v1,help needed,enhancement"
# Notifications messages
stale-issue-message: |
⏳ This issue has been automatically marked as **stale** because it has had no activity for 90 days.
**Next steps:**
- If this is still relevant, add a comment to keep it open
- Otherwise, it will be closed in 7 days
Thank you for your contributions! 🙌
close-issue-message: |
🚮 This issue has been automatically closed due to inactivity (7 days since being marked stale).
**Need to reopen?**
Click "Reopen" and add a comment explaining why this should stay open.
# Disable PR handling
days-before-pr-stale: -1
days-before-pr-close: -1