Skip to content

akt/SGFishing

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

4 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Singapore Fishing Guide

A mobile app that helps locals and tourists find legal fishing spots in Singapore, understand regulations, identify fish species, and get practical fishing tips — enhanced with real-time weather, tide, marine conditions, and fish activity data from multiple live APIs.

Tech Stack

Layer Technology
Backend Spring Boot 3.x + Java 17
Frontend React Native (Expo SDK 51)
Database H2 (embedded, file-based)
HTTP Client Spring WebClient (async API calls)
Caching Caffeine (TTL-based) + ConcurrentHashMap
Build Gradle (backend), Expo CLI (frontend)

Features

  • 10 fishing spots across Singapore with GPS coordinates, difficulty ratings, and facilities info
  • 8 fish species with identification details, best bait, and seasonal advice
  • 8 regulations from PUB and NParks with severity indicators
  • 8 fishing tips organized by category and difficulty
  • Real-time conditions for each spot:
    • Weather (temperature, wind, humidity, UV, rainfall) via NEA/Open-Meteo
    • Tides (status, next high/low, solunar rating) via TideCheck
    • Marine conditions (wave height, sea temperature, currents) via Open-Meteo Marine
    • Air quality (PSI, PM2.5) via NEA
    • Barometric pressure with fish activity prediction
    • Moon phase and sunrise/sunset
  • Composite Fishing Score (0-100) calculated from 7 environmental factors
  • Fallback API chains — if one data source fails, the next takes over
  • Offline-capable — seed data always available, conditions show "Unavailable" when APIs fail
  • Pull-to-refresh on all screens
  • Sort spots by fishing conditions or name
  • Filter spots by type (shore, offshore, reservoir)

Prerequisites

  • Java 17+ (for the Spring Boot backend)
  • Node.js 18+ (for the React Native mobile app)
  • Expo CLI (npm install -g expo-cli)
  • Expo Go app on your phone (Android/iOS) for testing

Getting Started

Backend

cd backend
./gradlew bootRun

The backend starts on http://localhost:8080. The H2 database is auto-created and seeded with fishing spots, species, regulations, and tips on first run.

Verify it's working:

curl http://localhost:8080/api/spots
curl http://localhost:8080/api/conditions/1

Mobile App

cd mobile
npm install --legacy-peer-deps
npx expo start

Scan the QR code with Expo Go (Android/iOS), or press a for Android emulator / i for iOS simulator.

Note: The mobile app connects to http://10.0.2.2:8080 on Android emulator and http://localhost:8080 on iOS simulator. If using a physical device, update the base URL in mobile/services/api.js to your machine's local IP.

API Key Setup

The app works out of the box with no API keys — free, keyless APIs (data.gov.sg NEA, Open-Meteo) provide weather, marine, air quality, and pressure data.

For enhanced data (tides, solunar ratings), set environment variables before starting the backend:

# Recommended for tide data (free: 50 req/day)
export TIDECHECK_API_KEY=your_key    # Register at tidecheck.com/dashboard/login

# Optional fallbacks (enhance data but not required)
export STORMGLASS_API_KEY=your_key   # Free: 10 req/day at stormglass.io/register
export WORLDTIDES_API_KEY=your_key   # Free tier at worldtides.info

APIs That Need No Key

API Data Provided
data.gov.sg (NEA) Weather forecasts, temperature, wind, humidity, UV, rainfall, PSI, PM2.5
Open-Meteo Weather fallback, barometric pressure
Open-Meteo Marine Wave height, sea temperature, ocean currents
Open-Meteo Air Quality PM2.5, PM10 fallback

APIs That Need a Free Key

API Data Provided Free Tier
TideCheck Tide times, solunar rating, moon phase, sunrise/sunset 50 req/day
StormGlass Marine data fallback, tide fallback 10 req/day
WorldTides Tide extremes fallback Limited free

API Endpoints

Method Endpoint Description
GET /api/spots List all fishing spots
GET /api/spots/{id} Spot details
GET /api/spots?type=shore Filter by type (shore/offshore/reservoir)
GET /api/spots?zone=East Filter by zone (East/West/North/South/Central/Northeast)
GET /api/species List all fish species
GET /api/species/{id} Species details
GET /api/regulations List all regulations
GET /api/regulations/{id} Regulation details
GET /api/tips List all fishing tips
GET /api/tips/{id} Tip details
GET /api/conditions/{spotId} Full live conditions for a spot
GET /api/conditions/all Summary conditions (score + label) for all spots
GET /api/conditions/weather Current Singapore-wide weather
GET /api/conditions/tides Current Singapore tide status

Fishing Score Algorithm

Each spot gets a composite score from 0-100 based on real-time environmental conditions:

Component Points Best Condition
Solunar Rating 0-25 5 stars (peak fish activity)
Tide Phase 0-15 Moving tide (rising/falling)
Barometric Pressure 0-15 Falling (fish most active)
Weather 0-15 Clear or overcast skies
Wind Speed 0-10 Under 15 km/h
Wave Height 0-10 Under 1m (calm seas)
Air Quality (PSI) 0-10 Under 50 (good)

Score Labels: 85-100 Excellent | 65-84 Good | 40-64 Fair | 0-39 Poor

Project Structure

SGFishing/
├── backend/
│   ├── src/main/java/com/sgfishing/
│   │   ├── SgFishingApplication.java          # Spring Boot entry point
│   │   ├── controller/
│   │   │   ├── SpotController.java            # /api/spots endpoints
│   │   │   ├── SpeciesController.java         # /api/species endpoints
│   │   │   ├── RegulationController.java      # /api/regulations endpoints
│   │   │   ├── TipController.java             # /api/tips endpoints
│   │   │   └── ConditionsController.java      # /api/conditions endpoints
│   │   ├── model/
│   │   │   ├── FishingSpot.java               # Spot entity (JPA)
│   │   │   ├── FishSpecies.java               # Species entity (JPA)
│   │   │   ├── Regulation.java                # Regulation entity (JPA)
│   │   │   ├── FishingTip.java                # Tip entity (JPA)
│   │   │   └── FishingConditions.java         # Composite conditions DTO
│   │   ├── repository/                        # Spring Data JPA repositories
│   │   ├── service/
│   │   │   ├── FishingScoreService.java       # Score calculation + orchestration
│   │   │   ├── WeatherService.java            # NEA + Open-Meteo weather
│   │   │   ├── TideService.java               # TideCheck + WorldTides + StormGlass
│   │   │   ├── MarineService.java             # Open-Meteo Marine + StormGlass
│   │   │   ├── AirQualityService.java         # NEA PSI/PM2.5 + Open-Meteo
│   │   │   └── PressureService.java           # Barometric pressure + fish impact
│   │   ├── config/
│   │   │   ├── DataSeeder.java                # Seeds 10 spots, 8 species, 8 regs, 8 tips
│   │   │   ├── CacheConfig.java               # Caffeine cache with TTLs
│   │   │   └── ApiKeyConfig.java              # Environment variable API keys
│   │   └── scheduler/
│   │       └── DataRefreshScheduler.java      # Periodic condition refresh
│   ├── src/main/resources/
│   │   └── application.properties
│   └── build.gradle
├── mobile/
│   ├── App.js                                 # Tab + stack navigation
│   ├── screens/
│   │   ├── SpotsScreen.js                     # Spot list with scores, filters, sorting
│   │   ├── SpotDetailScreen.js                # Spot info + live conditions panel
│   │   ├── SpeciesScreen.js                   # Species list
│   │   ├── SpeciesDetailScreen.js             # Species details
│   │   ├── RegulationsScreen.js               # Regulations with severity badges
│   │   └── TipsScreen.js                      # Expandable tips by category
│   ├── components/
│   │   ├── ConditionsPanel.js                 # Weather/tide/marine/pressure display
│   │   ├── FishingScoreBadge.js               # Animated color-coded score circle
│   │   ├── TideChart.js                       # Tide visualization bars
│   │   ├── SpotCard.js                        # Spot summary with score badge
│   │   ├── SpeciesCard.js                     # Species summary card
│   │   └── RegulationCard.js                  # Regulation with severity styling
│   ├── services/
│   │   └── api.js                             # Axios API client
│   ├── constants/
│   │   └── theme.js                           # Colors, spacing, shadows
│   ├── app.json
│   └── package.json
├── PROJECT_PLAN.md
└── README.md

Offline Behavior

The app is designed to work gracefully when APIs are unreachable:

  • Seed data (spots, species, regulations, tips) is stored in the embedded H2 database and always available
  • Live conditions show "Conditions unavailable" with a retry button when APIs fail
  • Fallback chains ensure maximum data availability — if NEA is down, Open-Meteo fills in; if TideCheck is down, WorldTides or StormGlass take over
  • Cached data is served when APIs are temporarily unreachable

Data Refresh Schedule

Data Type Refresh Interval Cache TTL
Weather 5 minutes 5 minutes
Tides & Solunar 3 hours 1 hour
Marine Conditions 30 minutes 30 minutes
Air Quality 30 minutes 30 minutes
Barometric Pressure 15 minutes 15 minutes

About

Singapore Fishing Guide — real-time conditions, tide data, fishing scores

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors