9.2 KiB
9.2 KiB
📝 CHANGELOG - Aplikasi Absensi Akademik
Version 1.1.0 - Enhancement Release
🎯 Overview
Aplikasi Absensi Akademik telah diperkaya dengan fitur-fitur penting untuk meningkatkan fungsionalitas dan keamanan sistem. Fitur baru mencakup validasi lokasi berbasis radius, penyimpanan riwayat absensi lokal, dan privacy protection untuk koordinat GPS.
✨ Fitur Baru (NEW FEATURES)
1. Location Radius Validation
File: MainActivity.kt
- Fungsi:
isWithinAbsensiRadius() - Deskripsi: Validasi otomatis apakah mahasiswa berada dalam radius yang diizinkan (default 100 meter)
- Default Location: UBH Campus (-6.2030, 107.0045)
- Benefit: Mencegah absensi dari lokasi yang tidak sesuai
fun isWithinAbsensiRadius(
studentLat: Double,
studentLon: Double,
campusLat: Double = -6.2030,
campusLon: Double = 107.0045,
radiusMeters: Float = 100f
): Boolean
2. Distance Calculation
File: MainActivity.kt
- Fungsi:
calculateDistance() - Deskripsi: Menghitung jarak presisi antara dua koordinat dalam meter
- Method: Menggunakan Android Location API
fun calculateDistance(lat1: Double, lon1: Double, lat2: Double, lon2: Double): Float
3. Coordinate Obfuscation (Privacy)
File: MainActivity.kt
- Fungsi:
obfuscateCoordinates() - Deskripsi: Menambahkan offset random pada koordinat untuk melindungi privasi (mencegah kebocoran lokasi rumah)
- Default Offset: 0.002 derajat (~200 meter)
- Benefit: Privacy protection sambil tetap valid untuk validasi radius
fun obfuscateCoordinates(
latitude: Double,
longitude: Double,
offsetDegrees: Double = 0.002
): Pair<Double, Double>
4. Attendance History Storage
File: DatabaseHelper.kt
- Database Version: Upgraded from v1 to v2
- New Table:
attendance - Columns:
id(INTEGER PRIMARY KEY)npm(TEXT - Foreign Key)timestamp(INTEGER)latitude(REAL)longitude(REAL)status(TEXT - "success" or "invalid_location")
5. Attendance Management Functions
File: DatabaseHelper.kt
addAttendanceRecord(): Menyimpan record absensi ke databasegetAttendanceHistory(): Mengambil semua history absensi mahasiswa
fun addAttendanceRecord(
npm: String,
timestamp: Long,
latitude: Double,
longitude: Double,
status: String
): Boolean
fun getAttendanceHistory(npm: String): List<AttendanceRecord>
6. AttendanceRecord Data Class
File: DatabaseHelper.kt
- Model data untuk riwayat absensi
- Fields: timestamp, latitude, longitude, status
data class AttendanceRecord(
val timestamp: Long,
val latitude: Double,
val longitude: Double,
val status: String
)
7. History Screen UI
File: MainActivity.kt
- Composable:
HistoryScreen() - Features:
- List view riwayat absensi
- Status visual (✓ Diterima / ✗ Ditolak)
- Formatted date/time (dd/MM/yyyy HH:mm:ss)
- Coordinate display (4 decimal places)
- Empty state handling
- Back navigation
8. Attendance Card Component
File: MainActivity.kt
- Composable:
AttendanceCard() - Shows: Tanggal, Status, dan Koordinat
- Styling: Color-coded status (green for success, red for rejected)
9. Enhanced Webhook Integration
File: MainActivity.kt
- Updated Function:
kirimKeN8n() - New Features:
- Automatic location validation
- Local database saving before sending
- Enhanced JSON payload with validation info
- Better error messages
- Status feedback based on validation result
JSON Payload:
{
"npm": "string",
"nama": "string",
"latitude": "number",
"longitude": "number",
"timestamp": "number",
"foto_base64": "string",
"validation_status": "success|invalid_location",
"is_within_radius": "boolean"
}
10. Navigation Enhancement
File: MainActivity.kt
- Added Screen: "history" screen
- Navigation Flow: home ↔ history
- Button: "Lihat Riwayat" di halaman absensi
🔧 Perubahan Existing Code
MainActivity.kt Changes
Updated Function Signatures
// Before
fun kirimKeN8n(
context: ComponentActivity,
npm: String,
nama: String,
latitude: Double,
longitude: Double,
foto: Bitmap
)
// After
fun kirimKeN8n(
context: ComponentActivity,
db: DatabaseHelper, // NEW
npm: String,
nama: String,
latitude: Double,
longitude: Double,
foto: Bitmap
)
Updated AbsensiScreen Signature
// Before
fun AbsensiScreen(
activity: ComponentActivity,
npm: String,
nama: String,
onLogout: () -> Unit
)
// After
fun AbsensiScreen(
activity: ComponentActivity,
db: DatabaseHelper, // NEW
npm: String,
nama: String,
onLogout: () -> Unit,
onNavigateToHistory: () -> Unit // NEW
)
Navigation Switch Statement
when (currentScreen) {
"login" -> LoginScreen(...)
"register" -> RegisterScreen(...)
"home" -> AbsensiScreen(...) // Added: db parameter, onNavigateToHistory
"history" -> HistoryScreen(...) // NEW BRANCH
}
UI Changes in AbsensiScreen
- Button "📷 Ambil Foto" (menggunakan emoji bukan icon untuk compatibility)
- New button: "Lihat Riwayat" dengan warna secondary
DatabaseHelper.kt Changes
Database Version Upgrade
// Before
private const val DATABASE_VERSION = 1
// After
private const val DATABASE_VERSION = 2
Updated onCreate()
- Added creation of
attendancetable - Maintained existing
userstable with UNIQUE constraint on NPM
Updated onUpgrade()
- Handles migration from v1 to v2
- Creates
attendancetable if upgrading
New Methods
addAttendanceRecord()- Insert attendance recordgetAttendanceHistory()- Query attendance history
build.gradle.kts Changes
Added Dependencies
// Material Icons Extended (untuk dukungan icon yang lebih lengkap)
implementation("androidx.compose.material:material-icons-extended:1.6.0")
📊 Database Changes
Migration from v1 to v2
v1 Schema (before):
Table: users
├── id (INTEGER PRIMARY KEY AUTOINCREMENT)
├── username (TEXT)
├── npm (TEXT)
└── password (TEXT)
v2 Schema (after):
Table: users
├── id (INTEGER PRIMARY KEY AUTOINCREMENT)
├── username (TEXT)
├── npm (TEXT UNIQUE) // Added UNIQUE constraint
└── password (TEXT)
Table: attendance (NEW)
├── id (INTEGER PRIMARY KEY AUTOINCREMENT)
├── npm (TEXT - FOREIGN KEY)
├── timestamp (INTEGER)
├── latitude (REAL)
├── longitude (REAL)
└── status (TEXT)
🔐 Security Improvements
- UNIQUE Constraint on NPM: Mencegah duplicate user registration
- Foreign Key: Linking attendance records to users
- Privacy Protection: Coordinate obfuscation untuk melindungi privacy
- Validation: Location validation sebelum accepting absensi
- Error Handling: Better error messages dan handling exceptions
🎨 UI/UX Improvements
- History Screen: Dedicated screen untuk melihat riwayat absensi
- Status Indicators: Visual feedback (✓/✗) untuk status absensi
- Date Formatting: Tanggal dalam format Indonesia (dd/MM/yyyy HH:mm:ss)
- Color Coding:
- Green (#4CAF50) untuk status accepted
- Red (#F44336) untuk status rejected
- Empty State: Message untuk ketika tidak ada riwayat
📱 Screen Flow
LOGIN/REGISTER
↓
HOME (ABSENSI)
├─ 📸 Ambil Foto
├─ 📍 Auto Detect Lokasi
├─ ✅ Kirim Absensi
│ ├─ Validasi Radius
│ ├─ Simpan ke DB
│ └─ Kirim ke n8n
└─ 📄 Lihat Riwayat
└─ History Screen
🧪 Testing Checklist
- Login dengan NPM dan password valid
- Register user baru dengan NPM yang unik
- Ambil foto dengan kamera
- Arahkan ke lokasi yang valid dan kirim absensi
- Arahkan ke lokasi yang tidak valid dan cek validasi
- Lihat riwayat absensi
- Verifikasi data di webhook n8n
- Cek database lokal dengan status yang benar
- Coba logout dan login kembali
🚀 Version History
| Version | Date | Changes |
|---|---|---|
| 1.0.0 | Jan 2026 | Initial Starter Release |
| 1.1.0 | Jan 14, 2026 | Added History, Location Validation, Privacy Features |
📋 Known Limitations & Future Work
Current Limitations
- Foto hanya tersimpan di RAM, tidak di storage permanent
- Database hanya lokal, tidak sync ke server
- Tidak ada resume mechanism untuk koneksi yang terputus
- Radius validation menggunakan hardcoded default location
Future Enhancements
- Persistent photo storage di device
- Database sync dengan server
- Offline queue untuk pending uploads
- Admin panel untuk manage allowed locations
- Statistics dashboard
- Real-time location tracking visualization
- Biometric authentication support
- Push notifications untuk absensi status
📞 Support & Contact
Untuk pertanyaan atau issue, silakan contact development team atau refer ke DEVELOPMENT_GUIDE.md untuk informasi lebih detail.
Last Updated: 14 January 2026 Status: ✅ Production Ready v1.1.0