- Android Studio Hedgehog (2023.1.1) or later
- JDK 11+
- Android SDK 34
- GitHub Personal Access Token
- Visit: https://github.com/settings/tokens
- Click "Generate new token" → "Generate new token (classic)"
- Name: "GSY GitHub App"
- Select scopes:
- ✅ repo (Full control of private repositories)
- ✅ user (Read all user profile data)
- Generate and copy the token
# Clone repository
git clone https://github.com/CarGuo/GSYGithubAppCompose.git
cd GSYGithubAppCompose
# Build
./gradlew build
# Install on device/emulator
./gradlew installDebug
# Or open in Android Studio and click Run ▶- App launches to Welcome screen (2-second splash)
- Navigate to Login screen
- Paste your GitHub Personal Access Token
- Click "Login"
- Explore the app!
app/src/main/java/com/shuyu/gsygithubappcompose/
├── MainActivity.kt # Navigation setup
├── MainViewModel.kt # App-level state
└── GSYApplication.kt # Hilt application
core/
├── network/
│ ├── api/GitHubApiService.kt # API interface
│ ├── model/Models.kt # Data models
│ └── di/NetworkModule.kt # DI setup
├── database/
│ ├── AppDatabase.kt # Room database
│ ├── dao/Daos.kt # Database access
│ ├── entity/Entities.kt # DB entities
│ └── di/DatabaseModule.kt # DI setup
├── common/
│ ├── datastore/UserPreferencesDataStore.kt # Preferences
│ └── di/CommonModule.kt # DI setup
└── ui/
├── theme/ # Material 3 theme
└── components/AvatarImage.kt # Reusable components
data/src/main/java/com/shuyu/gsygithubappcompose/data/repository/
├── UserRepository.kt # User data
├── EventRepository.kt # Activity events
└── RepositoryRepository.kt # GitHub repos
feature/
├── welcome/WelcomeScreen.kt # Splash
├── login/
│ ├── LoginScreen.kt # UI
│ └── LoginViewModel.kt # State
├── home/HomeScreen.kt # Bottom nav
├── dynamic/
│ ├── DynamicScreen.kt # UI
│ └── DynamicViewModel.kt # State
├── trending/
│ ├── TrendingScreen.kt # UI
│ └── TrendingViewModel.kt # State
└── profile/
├── ProfileScreen.kt # UI
└── ProfileViewModel.kt # State
welcome→ Splash screenlogin→ Token inputhome→ Main app (3 tabs)
- 动态 (Dynamic): User activity feed
- 趋势 (Trending): Popular repositories
- 我的 (Profile): User profile
Each feature follows MVVM:
Screen (Composable)
↓ observes
UiState (StateFlow)
↓ updated by
ViewModel
↓ calls
Repository
↓ fetches from
API/DatabaseEverything is provided by Hilt:
@HiltAndroidApp
class GSYApplication : Application()
@AndroidEntryPoint
class MainActivity : ComponentActivity()
@HiltViewModel
class MyViewModel @Inject constructor(
private val repository: MyRepository
) : ViewModel()
@Singleton
class MyRepository @Inject constructor(
private val apiService: GitHubApiService
)- Create module:
feature/myfeature - Add to
settings.gradle.kts - Create
build.gradle.kts - Implement
MyFeatureScreen.kt - Implement
MyFeatureViewModel.kt - Add route to
MainActivity
- Add method to
GitHubApiService.kt - Update models in
Models.ktif needed - Add repository method
- Call from ViewModel
- Create entity in
core/database/entity/ - Create DAO in
core/database/dao/ - Add to
AppDatabase.kt - Update repository
# Clean and rebuild
./gradlew clean build- Check token has correct permissions
- Check internet connection
- Check GitHub API status
- Check internet connection
- Verify URLs are valid
GitHub API has rate limits:
- Authenticated: 5,000 requests/hour
- Unauthenticated: 60 requests/hour
Use authentication token to get higher limit.
- Hot Reload: Use Compose Preview for quick UI iteration
- Logging: Check Logcat for OkHttp network logs
- Debug DB: Use Database Inspector in Android Studio
- State: Use
rememberSaveablefor screen rotations - Navigation: Use
popUpToto manage back stack
# Unit tests
./gradlew test
# Instrumented tests
./gradlew connectedAndroidTest- Offline-first: Database caches data
- Lazy Loading: LazyColumn for lists
- Image Caching: Coil handles caching
- Coroutines: Non-blocking async operations
See LICENSE file for details.