StreamCaster is a native Android app for live streaming camera and/or microphone to RTMP/RTMPS endpoints.
It is designed for:
- creators and developers who need a lightweight self-hostable live stream app,
- local/LAN testing against NGINX-RTMP or similar ingest servers,
- privacy-focused distribution (including a
fossflavor with no Google Play services dependency).
- Live stream video + audio, video-only, or audio-only.
- Save and reuse endpoint profiles (URL, stream key, optional auth credentials).
- Continue streaming in background via a foreground service.
- Show live stream HUD (state, bitrate/fps/resolution/duration).
- Optional local recording support (platform/version dependent).
- Package:
com.port80.app - Main app id (foss):
com.port80.app.foss - minSdk: 23
- targetSdk / compileSdk: 35
- Language: Kotlin
- UI: Jetpack Compose
- Architecture: MVVM + Hilt + StateFlow
- Streaming engine: RootEncoder (
RtmpCamera2) - Credentials storage: EncryptedSharedPreferences (Keystore-backed)
foss: F-Droid friendly, no GMS dependencies.gms: Play Store flavor.
- Android Studio (latest stable).
- JDK 17 (Android Studio bundled JDK is fine).
- Android SDK components:
- Platform Tools
- Build Tools for API 35
- Android Platform API 35
- Emulator (optional)
- A connected Android device (USB debugging enabled) or an Android Emulator.
- Open this folder in Android Studio.
- Let Gradle sync finish.
- Select build variant
fossDebug(recommended for local testing). - Connect a device or start an emulator.
- Press Run.
Build debug APK:
./gradlew :app:assembleFossDebugInstall on connected device/emulator:
./gradlew :app:installFossDebugLaunch app:
adb shell am start -n com.port80.app.foss/com.port80.app.MainActivityBuild both flavors:
./gradlew assembleFossDebug assembleGmsDebugUnit tests:
./gradlew testFossDebugUnitTestFOSS flavor check for accidental GMS deps (must be empty):
./gradlew :app:dependencies --configuration fossReleaseRuntimeClasspath | grep -i gmsInstrumented tests:
./gradlew connectedFossDebugAndroidTest- Open the app.
- Go to Endpoints and confirm at least one profile exists.
- Ensure one profile is marked default.
- Grant runtime permissions when prompted:
- Camera
- Microphone
- Notifications (API 33+)
- Tap Start.
A fresh install may include this default profile:
- Name:
Local RTMP - URL:
rtmp://192.168.0.12:1935/live - Stream key:
test
If your server runs on your development machine and you stream from Android Emulator, prefer 10.0.2.2 instead of localhost.
Examples:
- Emulator -> host machine:
rtmp://10.0.2.2:1935/live - Physical device -> host machine on LAN:
rtmp://<your-host-lan-ip>:1935/live
Symptom:
:app:installFossDebugfails withNo connected devices.
Fix:
- Start an emulator or connect a physical device.
- Verify with:
adb devices -lYou should see at least one device entry.
Check these in order:
- Permissions granted (camera/mic/notifications).
- Default endpoint profile exists.
- Endpoint reachable from the device/emulator network.
- RTMP server actually listening on expected interface/port.
Current behavior is intentionally split:
Auth Failed: server-side authentication rejection (wrong stream key or credentials).Profile Missing: app could not resolve the selected/default endpoint profile.No streaming endpoint configured: no profile available to start.
If you see profile-related messages:
- Open Endpoints.
- Create/update a profile.
- Mark it as default.
Cause:
- Profile IDs in storage do not match requested profile IDs.
Fix:
- Recreate endpoint profile and set as default.
- If needed for local dev, clear app data and relaunch.
Common cause:
- Using LAN IP that emulator cannot route to in your environment.
Try:
10.0.2.2for host machine access from emulator.- Confirm server binds to
0.0.0.0or host LAN interface, not only127.0.0.1.
Symptoms:
- Stream start immediately stops on Android 13+ / 14+.
Fix:
- Confirm notification permission granted on API 33+.
- Start streaming from in-app foreground action (button), not background trigger.
Possible causes:
- Another app holds camera.
- Emulator camera config issue.
- Permission denied.
Fix:
- Close other camera apps.
- Re-grant camera permission.
- Restart emulator/device.
Clear logs:
adb logcat -cWatch app/crash related output:
adb logcat -v time | grep --line-buffered -E "FATAL EXCEPTION|AndroidRuntime|com.port80.app"If adb behaves unexpectedly in your shell, run absolute path:
/opt/homebrew/bin/adb devices -l- Credentials are encrypted at rest (Keystore-backed EncryptedSharedPreferences).
- Service start intent carries only profile ID, not raw credentials.
- RTMPS is preferred for production.
- Sensitive values in logs are sanitized/redacted.
- Emulator networking can differ from physical devices.
- Thermal/camera behavior in emulator does not fully represent physical hardware behavior.
- Some features are sensitive to Android API level and OEM restrictions.
app/src/main/java/com/port80/app/ui- Compose UI and ViewModelsapp/src/main/java/com/port80/app/service- Foreground service and streaming controlapp/src/main/java/com/port80/app/data- Settings/profile repositories and modelsapp/src/main/java/com/port80/app/di- Hilt modules
See project license files and dependency licenses for details.