This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
OneBusAway for Android is a real-time transit information app providing bus arrival predictions, trip planning, and transit-related features. It's part of the non-profit Open Transit Software Foundation.
# Build and install debug version (default OBA brand for Google Play)
./gradlew installObaGoogleDebug
# Run instrumented tests
./gradlew connectedObaGoogleDebugAndroidTest
# Build release APK (requires signing configuration)
./gradlew assembleObaGoogleRelease
# Full CI check (tests + lint)
./gradlew test check connectedObaGoogleDebugAndroidTest
# Start app manually after install
adb shell am start -n com.joulespersecond.seattlebusbot/org.onebusaway.android.ui.HomeActivityThe project uses two flavor dimensions:
- Platform:
google(Google Play release) - Brand:
oba(original OneBusAway),agencyX,agencyY(sample rebrands)
Default variant: obaGoogleDebug
Main module: onebusaway-android/src/main/java/org/onebusaway/android/
Key packages:
app/- Application class and lifecycle managementui/- Activities and Fragments (HomeActivity is the main entry point)io/- REST API integration using Jackson for JSON bindingelements/- Response data modelsrequest/- API request classes (e.g., ObaArrivalInfoRequest)
provider/- Content provider (ObaProvider, ObaContract)map/- Google Maps integration (Google flavor only)region/- Multi-region support for different OBA server instancesdirections/- OpenTripPlanner integration for trip planningtripservice/- WorkManager-based arrival remindersutil/- Utility classes (LocationUtils, PreferenceUtils, RegionUtils)
- Requests extend base classes and return typed responses
- Jackson handles JSON serialization/deserialization
- ObaApi provides static singleton access to API constants
- Multi-region architecture auto-discovers OBA servers based on device location
- Content Provider with ObaContract for data access
- Room database for structured storage (schemas in
schemas/directory) - SharedPreferences for user settings via PreferenceUtils
Add to onebusaway-android/gradle.properties:
Pelias_oba=YOUR_API_KEY
Add to onebusaway-android/gradle.properties:
ONESIGNAL_APP_ID=YOUR_APP_ID
Create secure.properties with keystore info and reference it in onebusaway-android/gradle.properties:
secure.properties=/path/to/secure.properties
Use AOSP code style. Import AndroidStyle.xml (in repo root) into Android Studio:
- Place in Android Studio
/codestylesdirectory - Select "AndroidStyle" under File > Settings > Code Style
Tests are in onebusaway-android/src/androidTest/java/. Key test classes:
- API request/response tests (ArrivalInfoRequestTest, StopRequestTest)
- Region functionality tests (RegionsTest)
- Utility tests (LocationUtilsTest, RegionUtilTest)
CI runs on API level 33 emulator via GitHub Actions.
- Min SDK: 21 (Android 5.0)
- Target SDK: 36 (Android 15)
- Application ID:
com.joulespersecond.seattlebusbot(historical, must keep for Google Play) - Namespace:
org.onebusaway.android - Java compatibility: 1.8
- Kotlin version: 1.9.21
The app supports multiple OBA server deployments. Region configuration:
USE_FIXED_REGIONbuild config controls single vs. multi-region mode- ObaRegionsTask handles async region discovery
- Regions API auto-selects server based on device location
The app supports white-labeling via Gradle product flavors. See REBRANDING.md for full documentation.
Strings containing the app name use %1$s placeholders that are replaced at runtime:
<!-- In strings.xml -->
<string name="tutorial_welcome_title">Welcome to %1$s!</string>// In code - pass app_name as format argument
getString(R.string.tutorial_welcome_title, getString(R.string.app_name))When adding new user-facing strings that mention the app name:
- Use
%1$splaceholder instead of hardcoding "OneBusAway" - Update code to pass
getString(R.string.app_name)as the format argument - Update all translation files (
values-*/strings.xml) with the same placeholder pattern
Important: Strings referenced directly in XML layouts (via @string/...) cannot use placeholders - the placeholder would display as literal %1$s text. For these strings, set the text programmatically in Java/Kotlin code after inflating the view.
This allows white-label brands to only override app_name instead of duplicating entire string files.
- PRs should be single squashed commits
- ICLA signature required via CLA Assistant
- Run tests before submitting:
./gradlew connectedObaGoogleDebugAndroidTest