mirror of
https://github.com/iSoron/uhabits.git
synced 2025-12-06 09:08:52 -06:00
Merge pull request #1108 from sgallese/feature/midnight-timer-remove-jvm
Place MidnightTimer under test
This commit is contained in:
@@ -36,10 +36,15 @@ abstract class DateUtils {
|
|||||||
private var startDayHourOffset: Int = 0
|
private var startDayHourOffset: Int = 0
|
||||||
private var startDayMinuteOffset: Int = 0
|
private var startDayMinuteOffset: Int = 0
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Number of milliseconds in one second.
|
||||||
|
*/
|
||||||
|
const val SECOND_LENGTH: Long = 1000
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Number of milliseconds in one minute.
|
* Number of milliseconds in one minute.
|
||||||
*/
|
*/
|
||||||
const val MINUTE_LENGTH: Long = 60 * 1000
|
const val MINUTE_LENGTH: Long = 60 * SECOND_LENGTH
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Number of milliseconds in one hour.
|
* Number of milliseconds in one hour.
|
||||||
|
|||||||
@@ -33,31 +33,39 @@ open class MidnightTimer @Inject constructor() {
|
|||||||
private val listeners: MutableList<MidnightListener> = LinkedList()
|
private val listeners: MutableList<MidnightListener> = LinkedList()
|
||||||
private lateinit var executor: ScheduledExecutorService
|
private lateinit var executor: ScheduledExecutorService
|
||||||
|
|
||||||
@Synchronized fun addListener(listener: MidnightListener) {
|
@Synchronized
|
||||||
|
fun addListener(listener: MidnightListener) {
|
||||||
this.listeners.add(listener)
|
this.listeners.add(listener)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Synchronized fun onPause(): MutableList<Runnable>? = executor.shutdownNow()
|
@Synchronized
|
||||||
|
fun onPause(): MutableList<Runnable>? = executor.shutdownNow()
|
||||||
|
|
||||||
@Synchronized fun onResume() {
|
@Synchronized
|
||||||
executor = Executors.newSingleThreadScheduledExecutor()
|
fun onResume(
|
||||||
|
delayOffsetInMillis: Long = DateUtils.SECOND_LENGTH,
|
||||||
|
testExecutor: ScheduledExecutorService? = null
|
||||||
|
) {
|
||||||
|
executor = testExecutor ?: Executors.newSingleThreadScheduledExecutor()
|
||||||
executor.scheduleAtFixedRate(
|
executor.scheduleAtFixedRate(
|
||||||
{ notifyListeners() },
|
{ notifyListeners() },
|
||||||
DateUtils.millisecondsUntilTomorrowWithOffset() + 1000,
|
DateUtils.millisecondsUntilTomorrowWithOffset() + delayOffsetInMillis,
|
||||||
DateUtils.DAY_LENGTH,
|
DateUtils.DAY_LENGTH,
|
||||||
TimeUnit.MILLISECONDS
|
TimeUnit.MILLISECONDS
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Synchronized fun removeListener(listener: MidnightListener) = this.listeners.remove(listener)
|
@Synchronized
|
||||||
|
fun removeListener(listener: MidnightListener) = this.listeners.remove(listener)
|
||||||
|
|
||||||
@Synchronized private fun notifyListeners() {
|
@Synchronized
|
||||||
|
private fun notifyListeners() {
|
||||||
for (l in listeners) {
|
for (l in listeners) {
|
||||||
l.atMidnight()
|
l.atMidnight()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
interface MidnightListener {
|
fun interface MidnightListener {
|
||||||
fun atMidnight()
|
fun atMidnight()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -95,15 +95,13 @@ open class BaseUnitTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun unixTime(year: Int, month: Int, day: Int): Long {
|
fun unixTime(year: Int, month: Int, day: Int): Long {
|
||||||
val cal = getStartOfTodayCalendar()
|
return unixTime(year, month, day, 0, 0)
|
||||||
cal.set(year, month, day, 0, 0, 0)
|
|
||||||
return cal.timeInMillis
|
|
||||||
}
|
}
|
||||||
|
|
||||||
open fun unixTime(year: Int, month: Int, day: Int, hour: Int, minute: Int): Long {
|
open fun unixTime(year: Int, month: Int, day: Int, hour: Int, minute: Int, milliseconds: Long = 0): Long {
|
||||||
val cal = getStartOfTodayCalendar()
|
val cal = getStartOfTodayCalendar()
|
||||||
cal.set(year, month, day, hour, minute)
|
cal.set(year, month, day, hour, minute)
|
||||||
return cal.timeInMillis
|
return cal.timeInMillis + milliseconds
|
||||||
}
|
}
|
||||||
|
|
||||||
fun timestamp(year: Int, month: Int, day: Int): Timestamp {
|
fun timestamp(year: Int, month: Int, day: Int): Timestamp {
|
||||||
|
|||||||
@@ -138,7 +138,7 @@ class ReminderSchedulerTest : BaseUnitTest() {
|
|||||||
reminderScheduler.schedule(habit)
|
reminderScheduler.schedule(habit)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun unixTime(year: Int, month: Int, day: Int, hour: Int, minute: Int): Long {
|
override fun unixTime(year: Int, month: Int, day: Int, hour: Int, minute: Int, milliseconds: Long): Long {
|
||||||
val cal: Calendar = getStartOfTodayCalendar()
|
val cal: Calendar = getStartOfTodayCalendar()
|
||||||
cal[year, month, day, hour] = minute
|
cal[year, month, day, hour] = minute
|
||||||
return cal.timeInMillis
|
return cal.timeInMillis
|
||||||
|
|||||||
@@ -0,0 +1,48 @@
|
|||||||
|
package org.isoron.uhabits.core.utils
|
||||||
|
|
||||||
|
import kotlinx.coroutines.asCoroutineDispatcher
|
||||||
|
import kotlinx.coroutines.runBlocking
|
||||||
|
import kotlinx.coroutines.withContext
|
||||||
|
import org.isoron.uhabits.core.BaseUnitTest
|
||||||
|
import org.junit.Test
|
||||||
|
import java.util.Calendar
|
||||||
|
import java.util.TimeZone
|
||||||
|
import java.util.concurrent.Executors
|
||||||
|
import kotlin.coroutines.resume
|
||||||
|
import kotlin.coroutines.suspendCoroutine
|
||||||
|
import kotlin.test.assertEquals
|
||||||
|
|
||||||
|
class MidnightTimerTest : BaseUnitTest() {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun testMidnightTimer_notifyListener_atMidnight() = runBlocking {
|
||||||
|
// Given
|
||||||
|
val executor = Executors.newSingleThreadScheduledExecutor()
|
||||||
|
val dispatcher = executor.asCoroutineDispatcher()
|
||||||
|
|
||||||
|
withContext(dispatcher) {
|
||||||
|
DateUtils.setFixedTimeZone(TimeZone.getTimeZone("GMT"))
|
||||||
|
DateUtils.setFixedLocalTime(
|
||||||
|
unixTime(
|
||||||
|
2017,
|
||||||
|
Calendar.JANUARY,
|
||||||
|
1,
|
||||||
|
23,
|
||||||
|
59,
|
||||||
|
DateUtils.MINUTE_LENGTH - 1
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
val suspendedListener = suspendCoroutine<Boolean> { continuation ->
|
||||||
|
MidnightTimer().apply {
|
||||||
|
addListener { continuation.resume(true) }
|
||||||
|
// When
|
||||||
|
onResume(1, executor)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Then
|
||||||
|
assertEquals(true, suspendedListener)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user