A React Native mobile application assignment built with Expo that allows users to browse, search, and favorite GitHub repositories from Algorand-related organizations (Pera Wallet, Algorand Foundation, and Algorand).
- Repository Browsing: View repositories from three Algorand organizations with details including stars, forks, language, and descriptions
- Search & Filter: Real-time search across repository names and descriptions, with filter chips for organization-based filtering
- Pull-to-Refresh: Sync repositories from GitHub by pulling down on the repositories list
- Favorites System: Save favorite repositories that sync across devices (requires authentication)
- Repository Details: View detailed information about each repository with an option to open it on GitHub
- Offline Support: Full offline functionality with cached data persistence using React Query
- Authentication: Secure sign-in/sign-up using Clerk with email verification support
- Dark/Light Mode: Automatic theme switching based on system preferences
- Offline Indicators: Visual banners to inform users about network connectivity status
- Optimized Performance: Uses FlashList for efficient rendering of large lists
- Haptic Feedback: Enhanced user interactions with haptic feedback on tab navigation
The image files referenced below are only for documentation and are not used by the app bundle.
- React Native (0.81.5) with Expo (~54.0.29)
- Expo Router for file-based routing
- TypeScript for type safety
- TanStack Query (React Query) for server state management
- AsyncStorage Persistence for offline data caching
- Offline-First Architecture: Data is cached and available offline
- Supabase: PostgreSQL database for repositories and favorites
- Supabase Edge Functions: Serverless functions for syncing repositories from GitHub
- Clerk: Authentication and user management
- GitHub API: Repository data synchronization (via Edge Function or sync script)
- React Navigation: Tab and stack navigation
- FlashList: High-performance list rendering
- Expo Image: Optimized image loading
- Expo Web Browser: In-app browser for external links
- React Native NetInfo: Network connectivity monitoring
- Expo Haptics: Tactile feedback
- Expo Secure Store: Secure token storage
The app is designed to work seamlessly offline:
- Repository data is cached using React Query with AsyncStorage persistence
- Cache is valid for 5 minutes (staleTime) and kept for 24 hours (gcTime)
- Network requests use
networkMode: "offlineFirst"to prioritize cached data - Client-side filtering ensures search and filters work without network connectivity
- Uses Clerk for authentication with secure token management
- Supabase RLS (Row Level Security) ensures users can only access their own favorites
- Token caching with Expo Secure Store for persistent sessions
- FlashList: Replaces FlatList for better performance with large datasets
- Debounced Search: Search input is debounced (300ms) to reduce API calls
- Memoized Filtering: Client-side filtering uses
useMemoto prevent unnecessary recalculations - Image Optimization: Uses Expo Image for efficient image loading and caching
- Themed Components: Reusable components that adapt to light/dark themes
- Custom Hooks: Encapsulated logic for repositories, favorites, network status, and more
- Type Safety: Full TypeScript coverage with strict typing
- Edge Functions: Serverless functions for GitHub synchronization
- Unit Testing: Jest setup for testing utility functions
pwrna/
βββ app/ # Expo Router file-based routing
β βββ (auth)/ # Authentication screens (sign-in, sign-up)
β βββ (tabs)/ # Main app screens (repositories, favorites)
β βββ repository/[id].tsx # Repository detail screen
βββ components/ # Reusable UI components
β βββ themed/ # Theme-aware components
β βββ repo-card.tsx # Repository card component
β βββ filter-chips.tsx # Organization filter chips
β βββ ...
βββ hooks/ # Custom React hooks
β βββ use-repositories.ts
β βββ use-sync-repositories.ts # Hook for syncing repos via Edge Function
β βββ use-favorites.ts
β βββ use-network-status.ts
β βββ ...
βββ utils/ # Utility functions
β βββ supabase.ts # Supabase client setup
β βββ query-client.ts # React Query configuration
β βββ storage.ts # AsyncStorage adapter for caching
β βββ online-manager.ts # Network status management
β βββ transform-repository.ts # Repository transformation utility
β βββ __tests__/ # Unit tests
β βββ transform-repository.test.ts
βββ types/ # TypeScript type definitions
βββ constants/ # App constants (themes)
βββ supabase/ # Supabase configuration
β βββ functions/ # Edge Functions
β β βββ sync-repos/ # GitHub sync Edge Function
β βββ migrations/ # Database migrations
βββ scripts/ # Build and sync scripts
βββ sync-repos.ts # GitHub to Supabase sync script (local)
- Uses Expo Router's file-based routing system
- Route groups
(auth)and(tabs)organize navigation structure - Dynamic routes like
repository/[id].tsxfor detail views
- Business logic separated into reusable hooks
- Examples:
useRepositories(),useFavorites(),useDebounce() - Promotes code reusability and testability
- Centralized theme configuration in
constants/theme.ts - Theme-aware components using
useThemeColorhook - Automatic dark/light mode detection
- React Query for all server state
- Query key factories for type-safe cache management
- Optimistic updates and cache invalidation strategies
- Uses
react-native-safe-area-contextfor proper screen insets - Handles notches, status bars, and navigation bars correctly
- FlashList for efficient list rendering
- Image optimization with Expo Image
- Memoization for expensive computations
- Node.js (v18 or later)
- npm or yarn
- Expo CLI (
npm install -g expo-cli) - iOS Simulator (for iOS) or Android Studio (for Android)
-
Clone the repository
git clone <repository-url> cd pwrna
-
Install dependencies
npm install
-
Set up environment variables Create a
.envfile in the root directory:EXPO_PUBLIC_CLERK_PUBLISHABLE_KEY=your_clerk_key EXPO_PUBLIC_SUPABASE_URL=your_supabase_url EXPO_PUBLIC_SUPABASE_ANON_KEY=your_supabase_anon_key
-
Start the development server
npx expo start
-
Run on your device
- Press
ifor iOS simulator - Press
afor Android emulator - Scan QR code with Expo Go app (limited functionality)
- Press
There are two ways to sync repository data:
Simply pull down on the repositories list in the app. This triggers the Supabase Edge Function to sync data from GitHub.
To populate the Supabase database with GitHub repository data locally:
npm run sync-reposThis script fetches repositories from GitHub and syncs them to Supabase.
Deploy and use the Edge Function directly:
# Deploy the function
supabase functions deploy sync-repos
# Set required secrets
supabase secrets set SUPABASE_SERVICE_ROLE_KEY=your_service_role_key
supabase secrets set GITHUB_TOKEN=your_github_tokennpm start- Start Expo development servernpm run android- Start on Android emulatornpm run ios- Start on iOS simulatornpm run web- Start web versionnpm run sync-repos- Sync GitHub repositories to Supabase (local script)npm test- Run unit tests with Jestnpm run test:watch- Run tests in watch modenpm run lint- Run ESLint
- All repository data is cached locally using React Query with AsyncStorage
- Network status is monitored and displayed to users
- Favorites are stored in Supabase but cached locally for offline access
- Clerk handles authentication with secure token storage
- Supabase RLS policies ensure data security
- User-specific favorites are isolated per user account
- Repository data is synced from GitHub to Supabase via:
- Supabase Edge Function (recommended, triggered by pull-to-refresh)
- Local sync script (
npm run sync-repos)
- App fetches from Supabase with React Query
- Data is cached locally for offline access
- Client-side filtering and search work on cached data
- Pull-to-refresh triggers sync and refreshes the cache
- Unit Tests: Jest is configured for unit testing
- Run tests:
npm test - Watch mode:
npm run test:watch - Tests are located in
utils/__tests__/ - Example:
transform-repository.test.tstests the repository transformation utility
- Run tests:
This project is an open-source project with MIT License.