Skip to content

muhAzri/go-servis

Repository files navigation

GoService

A vehicle service-log and maintenance-reminder app for Indonesia, built with Kotlin Multiplatform: one shared Kotlin core drives a native UI per platform — Jetpack Compose on Android, SwiftUI on iOS.

Track your vehicles, log every service, monitor wearable components, and get reminded before the next service is due — all stored locally on the device.

Scope: Indonesia-only. Locale, currency, and distance unit are fixed to id-ID, IDR (Rp), and kilometres; there are no pickers for these.


Features

  • Vehicles — add motorcycles/cars with nickname, brand, model, year, plate, colour, and odometer. Odometer is protected against accidental rollback (smaller-than-current needs explicit confirmation). The bottom-nav "+" prompts the user to add a vehicle first when the garage is empty.
  • Service records (3-mode) — log a service as one of:
    • Komponen — pick from the selected vehicle's tracked components; the next-service cycle for each picked component is recalculated automatically.
    • Rutin — generic periodic service (no specific component); auto-creates a reminder ~6 months / 4.000 km (motor) or 10.000 km (mobil) ahead.
    • Manual — one-off service with a free-text title (e.g. spion, jok); no auto-reminder. All modes share date / odometer / workshop / cost (IDR) / notes. Logging a higher odometer automatically advances the vehicle's odometer. History is paged from SQLite with search, per-vehicle filter, sorting, and a filtered total-cost summary.
  • Tracked components — track wearable parts from a catalog (or add custom ones). The app derives the next-service schedule (by km and/or date) and shows an urgency badge: Aman / Segera / Terlewat (OK / Soon / Overdue).
  • Reminders (2-mode) — choose Komponen (pick a tracked component; title + target km + target date auto-fill from the component's interval) or Manual (free-text title + your choice of Km / Date / Both trigger). Snooze, complete, or dismiss; completing a reminder or servicing a component automatically closes the open reminder and opens the next cycle.
  • Notifications — two independent local-notification channels:
    • Pengingat servis — fires ahead of each reminder's due point.
    • Update KM — fires per-vehicle when the odometer hasn't been written for 14 days, at 9 AM local; tap deep-links into the Update KM screen for that vehicle. Both can be toggled separately in Settings; Settings also has test-fire buttons that prompt for POST_NOTIFICATIONS (Android 13+) and fall back to system-settings deep-links if denied.
  • Backup & restore — export a single-file CSV (per-section, per-time-range) and share it; import merges by id so re-importing never duplicates data.
  • Onboarding — guided first-run flow (profile → vehicle type → first vehicle → notification permission), resumable and skippable. The previously in-Home permission banner has been removed; permission is strictly an onboarding concern.
  • Profile & settings — editable profile (name, avatar colour, email), toggles for both notification kinds, and the test-fire shortcuts above.
  • Error surfacing — every form's Failed event funnels through a single app-wide Snackbar host with localized (DomainError.message) messages, so no more silent "tombol tidak bereaksi" failures.

A manual-QA test scenario for the whole app lives in docs/qa/.


Tech stack

Area Choice
Language Kotlin 2.3.21 (Multiplatform)
Build Android Gradle Plugin 9.1.1, Gradle 9.3.1
Shared core :shared framework consumed by both apps (domain + data + ViewModels + DI)
Android UI Jetpack Compose Multiplatform 1.11 + Material 3 + Navigation Compose
iOS UI SwiftUI (consumes the shared Shared framework)
Targets Android (minSdk 24, target/compile 36), iOS (arm64 + simulator arm64)
DI Koin
Persistence Room (KMP, via KSP) on bundled SQLite
Async Kotlinx Coroutines / Flow
Date/time Kotlinx Datetime 0.8 + kotlin.time.Instant
Serialization Kotlinx Serialization (JSON)
Notifications WorkManager (Android) + UNUserNotificationCenter (iOS), two independent channels/categories (Pengingat servis, Update KM) behind shared planners + schedulers
Ads Yandex Mobile Ads (banner / interstitial / native / app-open)

Architecture

Clean Architecture, organised by feature module. Everything except the UI — domain, data, presentation (ViewModels), and DI — lives in :shared, so both platforms drive the same logic and state. Each platform then renders its own native UI on top: Compose on Android, SwiftUI on iOS.

shared/src/commonMain/.../feature/<name>/
├── domain/        # models, repository interfaces, use cases (pure Kotlin)
├── data/          # Room DAOs/entities, repository implementations, mappers
├── presentation/  # ViewModels + UI state
└── di/            # Koin module

Features: onboarding, profile, vehicle, service, component, reminder, backup, settings. (A tip feature still exists in the tree but its UI entry points are hidden until post-MVP.) Cross-cutting helpers live under core/ (value types like Money/Distance/HexColor, AppClock, paging, sync metadata, result types, DI, **notification planners + schedulers

  • deep-link sinks**).
GoService/
├── shared/        # KMP module: domain + data + presentation + DI (the app's brain)
├── composeApp/    # Android app — Jetpack Compose UI + Android entry point
└── iosApp/        # iOS app — SwiftUI UI; open in Xcode

Getting started

Requirements

  • JDK 11+
  • Android Studio (latest stable) with the Kotlin Multiplatform plugin
  • For iOS: macOS + Xcode

Set the Android SDK location in local.properties:

sdk.dir=/path/to/Android/sdk

Run the Android app

Use the run configuration in your IDE, or build from the terminal:

# macOS / Linux
./gradlew :composeApp:assembleDebug

# Windows
.\gradlew.bat :composeApp:assembleDebug

Run the iOS app

Open iosApp/iosApp.xcodeproj in Xcode and run. Xcode builds the Shared Kotlin framework as part of its build phase, so no separate Gradle step is required.

Tests

./gradlew :shared:allTests        # KMP common tests
./gradlew :composeApp:testDebugUnitTest

Project conventions

  • Commit messages are written in English.
  • Indonesia-only product scope (see note at the top) — do not add locale, currency, or distance-unit settings.

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors