From b395df6268a6114cf0fe66eec1553a0e32e390f3 Mon Sep 17 00:00:00 2001
From: sathwikcs <85106054+sathwikcs@users.noreply.github.com>
Date: Mon, 3 Mar 2025 14:37:41 +0530
Subject: [PATCH] new version 3.1.1
---
.idea/other.xml | 77 ++++++++++++++++
app/build.gradle.kts | 4 +-
.../screens/home/viewModel/homeVM.kt | 90 +++++++++++++------
.../attendanceapp/ExampleUnitTest.kt | 43 +++++++--
4 files changed, 177 insertions(+), 37 deletions(-)
diff --git a/.idea/other.xml b/.idea/other.xml
index 25d338a..e965764 100644
--- a/.idea/other.xml
+++ b/.idea/other.xml
@@ -47,6 +47,28 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -245,6 +267,17 @@
+
+
+
+
+
+
+
+
+
+
+
@@ -256,6 +289,17 @@
+
+
+
+
+
+
+
+
+
+
+
@@ -311,6 +355,17 @@
+
+
+
+
+
+
+
+
+
+
+
@@ -367,6 +422,17 @@
+
+
+
+
+
+
+
+
+
+
+
@@ -389,6 +455,17 @@
+
+
+
+
+
+
+
+
+
+
+
diff --git a/app/build.gradle.kts b/app/build.gradle.kts
index 83ce672..79df26c 100644
--- a/app/build.gradle.kts
+++ b/app/build.gradle.kts
@@ -14,9 +14,9 @@ android {
applicationId = "in.sminnovations.attendanceapp.user"
minSdk = 26
targetSdk = 34
- versionCode = 4
+ versionCode = 11
- versionName = "3.1.1"
+ versionName = "3.1.4"
testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner"
vectorDrawables {
diff --git a/app/src/main/java/in/sminnovations/attendanceapp/screens/home/viewModel/homeVM.kt b/app/src/main/java/in/sminnovations/attendanceapp/screens/home/viewModel/homeVM.kt
index e7fede0..3638325 100644
--- a/app/src/main/java/in/sminnovations/attendanceapp/screens/home/viewModel/homeVM.kt
+++ b/app/src/main/java/in/sminnovations/attendanceapp/screens/home/viewModel/homeVM.kt
@@ -9,11 +9,11 @@ import com.google.firebase.Timestamp
import com.google.firebase.firestore.DocumentSnapshot
import com.google.firebase.firestore.FirebaseFirestore
import dagger.hilt.android.lifecycle.HiltViewModel
+import `in`.sminnovations.attendanceapp.screens.home.data.AttendanceUiState
import `in`.sminnovations.attendanceapp.utils.AppUpdater
import `in`.sminnovations.attendanceapp.utils.NetworkMonitor
-import `in`.sminnovations.attendanceapp.utils.UpdateInfo
-import `in`.sminnovations.attendanceapp.screens.home.data.AttendanceUiState
import `in`.sminnovations.attendanceapp.utils.UpdateChecker
+import `in`.sminnovations.attendanceapp.utils.UpdateInfo
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asStateFlow
@@ -31,6 +31,8 @@ import java.util.Locale
import javax.inject.Inject
import kotlin.math.abs
+
+const val timeFormat = "dd MMMM yyyy hh:mm:ss a"
@HiltViewModel
class HomeViewModel @Inject constructor(
applicationContext: Context,
@@ -78,12 +80,15 @@ class HomeViewModel @Inject constructor(
is AppUpdater.UpdaterState.Downloading -> {
_downloadProgress.value = state.progress
}
+
is AppUpdater.UpdaterState.Success -> {
_downloadProgress.value = 1f
}
+
is AppUpdater.UpdaterState.Error -> {
_downloadProgress.value = 0f
}
+
AppUpdater.UpdaterState.Idle -> {
// No op
}
@@ -154,7 +159,8 @@ class HomeViewModel @Inject constructor(
processQRCode(value)
}
}
- private fun processQRCode(userId: String) {
+
+ private fun processQRCode(userId: String) {
if (userId.isBlank()) return
viewModelScope.launch {
@@ -247,7 +253,7 @@ class HomeViewModel @Inject constructor(
private fun formatTimestamp(timestamp: Timestamp): String {
return SimpleDateFormat(
- "dd MMMM yyyy hh:mm:ss a", Locale.getDefault()
+ timeFormat, Locale.getDefault()
).format(timestamp.toDate())
}
@@ -259,30 +265,59 @@ class HomeViewModel @Inject constructor(
// }
-
-
private suspend fun handleExistingAttendance(document: DocumentSnapshot) {
val data = document.data ?: return
val checkIns = data.filterKeys { it.startsWith("checkIn") }.size
val checkOuts = data.filterKeys { it.startsWith("checkOut") }.size
-
- if (checkIns > checkOuts) {
- processCheckOut(document, checkIns)
- } else {
- processCheckIn(document, checkIns + 1)
- }
+ val checkIn = document.getString("checkIn$checkIns")!!
+ if (isTimeDifferenceGreaterThanSec(givenTimeStr = checkIn, currentTimeStr = formatTimestamp(Timestamp.now()), secVal = 5L)) {
+ if (!isTimeDifferenceGreaterThanMinutes(
+ givenTimeStr = checkIn,
+ currentTimeStr = formatTimestamp(Timestamp.now()),
+ minutesVal = 5L
+ )
+ ) {
+ handleError("Wait 5 minutes before logging off")
+ } else {
+ if (checkIns > checkOuts) {
+ processCheckOut(document, checkIns)
+ } else {
+ processCheckIn(document, checkIns + 1)
+ }
+ }
+ }
}
-// private fun isTimeDifferenceGreaterThanMinutes(givenTimeStr: String, currentTimeStr: String = formatTimestamp(Timestamp.now()), minutes: Long): Boolean {
-// val formatter = DateTimeFormatter.ofPattern("dd MMMM yyyy hh:mm:ss a")
-//
-// val givenTime = LocalDateTime.parse(givenTimeStr, formatter)
-// val currentTime = LocalDateTime.parse(currentTimeStr, formatter)
-//
-// val timeDifference = abs(ChronoUnit.MINUTES.between(givenTime, currentTime))
-//
-// return timeDifference > minutes
-// }
+
+ private fun isTimeDifferenceGreaterThanMinutes(
+ givenTimeStr: String,
+ currentTimeStr: String = formatTimestamp(Timestamp.now()),
+ minutesVal: Long
+ ): Boolean {
+ val formatter = DateTimeFormatter.ofPattern(timeFormat)
+
+ val givenTime = LocalDateTime.parse(givenTimeStr, formatter)
+ val currentTime = LocalDateTime.parse(currentTimeStr, formatter)
+
+ val timeDifference = abs(ChronoUnit.MINUTES.between(givenTime, currentTime))
+
+ return timeDifference > minutesVal
+ }
+
+
+ private fun isTimeDifferenceGreaterThanSec(
+ givenTimeStr: String,
+ currentTimeStr: String = formatTimestamp(Timestamp.now()),
+ secVal: Long
+ ): Boolean {
+ val formatter = DateTimeFormatter.ofPattern(timeFormat)
+ val givenTime = LocalDateTime.parse(givenTimeStr, formatter)
+ val currentTime = LocalDateTime.parse(currentTimeStr, formatter)
+
+ val timeDifference = abs(ChronoUnit.SECONDS.between(givenTime, currentTime))
+
+ return timeDifference > secVal
+ }
private suspend fun handleNewAttendance(userId: String, currentDate: String) {
try {
@@ -307,7 +342,8 @@ class HomeViewModel @Inject constructor(
private suspend fun processCheckIn(document: DocumentSnapshot, checkInCount: Int) {
try {
- document.reference.update("checkIn$checkInCount", formatTimestamp(Timestamp.now())).await()
+ document.reference.update("checkIn$checkInCount", formatTimestamp(Timestamp.now()))
+ .await()
_uiState.update {
it.copy(
isCheckedIn = true, qrCodeValue = null
@@ -338,8 +374,8 @@ class HomeViewModel @Inject constructor(
}
}
- private fun calculateTotalWork(document: DocumentSnapshot): Pair {
- val formatter = DateTimeFormatter.ofPattern("dd MMMM yyyy hh:mm:ss a", Locale.getDefault())
+ private fun calculateTotalWork(document: DocumentSnapshot): Pair {
+ val formatter = DateTimeFormatter.ofPattern(timeFormat, Locale.getDefault())
var totalMinutes = 0L
for (i in 1..20) {
val checkIn = document.getString("checkIn$i") ?: break
@@ -351,8 +387,8 @@ class HomeViewModel @Inject constructor(
val hours = totalMinutes / 60
val minutes = totalMinutes % 60
- val isDayCompleted = totalMinutes >=420L
- return Pair(String.format("%02d:%02d:00", hours, minutes),isDayCompleted)
+ val isDayCompleted = totalMinutes >= 420L
+ return Pair(String.format("%02d:%02d:00", hours, minutes), isDayCompleted)
}
diff --git a/app/src/test/java/in/sminnovations/attendanceapp/ExampleUnitTest.kt b/app/src/test/java/in/sminnovations/attendanceapp/ExampleUnitTest.kt
index 8cd1458..bd22223 100644
--- a/app/src/test/java/in/sminnovations/attendanceapp/ExampleUnitTest.kt
+++ b/app/src/test/java/in/sminnovations/attendanceapp/ExampleUnitTest.kt
@@ -1,10 +1,13 @@
package `in`.sminnovations.attendanceapp
+import com.google.firebase.Timestamp
import org.junit.Assert.assertEquals
import org.junit.Test
+import java.text.SimpleDateFormat
import java.time.LocalDateTime
import java.time.format.DateTimeFormatter
import java.time.temporal.ChronoUnit
+import java.util.Locale
import kotlin.math.abs
/**
@@ -19,14 +22,15 @@ class ExampleUnitTest {
assertEquals(4, 2 + 2)
}
-// @Test
-// fun timeTest(){
-// val currentTime = "30 January 2025 11:01:55 am"
-// val givenTime = "30 January 2025 10:30:55 am"
-// val minutes = 20L
-// val result = isTimeDifferenceGreaterThanMinutes(givenTime, currentTime, minutes)
-// assertEquals(true,result)
-// }
+ @Test
+ fun timeTest(){
+ val currentTime = "30 January 2025 10:30:55 am"
+ val givenTime = "30 January 2025 10:31:01 am"
+ val minutes = 7L
+ val result = isTimeDifferenceGreaterThanSec(givenTime, currentTime, minutes)
+ println(result)
+ assertEquals(false,result)
+ }
//
// private fun isTimeDifferenceGreaterThanMinutes(givenTimeStr: String, currentTimeStr: String, minutes: Long): Boolean {
// val formatter = DateTimeFormatter.ofPattern("dd MMMM yyyy hh:mm:ss a")
@@ -35,4 +39,27 @@ class ExampleUnitTest {
// val timeDifference = abs(ChronoUnit.MINUTES.between(givenTime, currentTime))
// return timeDifference > minutes
// }
+
+ private fun isTimeDifferenceGreaterThanSec(
+ givenTimeStr: String,
+ currentTimeStr: String = formatTimestamp(Timestamp.now()),
+ sec: Long = 5
+ ): Boolean {
+ val formatter = DateTimeFormatter.ofPattern("dd MMMM yyyy hh:mm:ss a")
+ val givenTime = LocalDateTime.parse(givenTimeStr, formatter)
+ val currentTime = LocalDateTime.parse(currentTimeStr, formatter)
+
+ val timeDifference = abs(ChronoUnit.SECONDS.between(givenTime, currentTime))
+
+ return timeDifference > sec
+ }
+
+ private fun formatTimestamp(timestamp: Timestamp): String {
+ return SimpleDateFormat(
+ "dd MMMM yyyy hh:mm:ss a", Locale.getDefault()
+ ).format(timestamp.toDate())
+ }
+
+
+
}
\ No newline at end of file