Migrate start of today with offsets

pull/1120/head
sgallese 4 years ago
parent 2301158925
commit f12ecb16fc

@ -141,10 +141,6 @@ data class LocalDate(val daysSince2000: Int) {
}
companion object {
var fixedLocalTime: Long? = null
var fixedTimeZone: TimeZone? = null
var fixedLocale: Locale? = null
/**
* Number of milliseconds in one second.
*/
@ -165,6 +161,17 @@ data class LocalDate(val daysSince2000: Int) {
*/
const val DAY_LENGTH: Long = 24 * HOUR_LENGTH
var fixedLocalTime: Long? = null
var fixedTimeZone: TimeZone? = null
var fixedLocale: Locale? = null
var startDayHourOffset: Int = 0
var startDayMinuteOffset: Int = 0
fun setStartDayOffset(hourOffset: Int, minuteOffset: Int) {
startDayHourOffset = hourOffset
startDayMinuteOffset = minuteOffset
}
fun getLocalTime(testTimeInMillis: Long? = null): Long {
if (fixedLocalTime != null) return fixedLocalTime as Long
@ -205,6 +212,13 @@ data class LocalDate(val daysSince2000: Int) {
fun getStartOfDay(timestamp: Long): Long = (timestamp / DAY_LENGTH) * DAY_LENGTH
fun getStartOfToday(): Long = getStartOfDay(getLocalTime())
fun getStartOfDayWithOffset(timestamp: Long): Long {
val offset = startDayHourOffset * HOUR_LENGTH + startDayMinuteOffset * MINUTE_LENGTH
return getStartOfDay(timestamp - offset)
}
fun getStartOfTodayWithOffset(): Long = getStartOfDayWithOffset(getLocalTime())
}
}

@ -23,7 +23,9 @@ import kotlinx.datetime.LocalDateTime
import kotlinx.datetime.TimeZone
import kotlinx.datetime.toInstant
import org.isoron.platform.time.LocalDate.Companion.getStartOfDay
import org.isoron.platform.time.LocalDate.Companion.getStartOfDayWithOffset
import org.isoron.platform.time.LocalDate.Companion.getStartOfToday
import org.isoron.platform.time.LocalDate.Companion.getStartOfTodayWithOffset
import org.isoron.platform.time.LocalDate.Companion.getWeekdaySequence
import kotlin.test.Test
import kotlin.test.assertContentEquals
@ -42,9 +44,7 @@ class DatesTest {
fun testGetLocalTime() {
LocalDate.fixedLocalTime = null
LocalDate.fixedTimeZone = TimeZone.of("Australia/Sydney")
val utcTestTimeInMillis = LocalDateTime(
2015, 1, 11, 0, 0, 0, 0
).toInstant(TimeZone.UTC).toEpochMilliseconds()
val utcTestTimeInMillis = unixTime(2015, 1, 11)
val localTimeInMillis = LocalDate.getLocalTime(utcTestTimeInMillis)
val expectedUnixTimeOffsetForSydney = 11 * 60 * 60 * 1000
val expectedUnixTimeForSydney = utcTestTimeInMillis + expectedUnixTimeOffsetForSydney
@ -59,25 +59,74 @@ class DatesTest {
@Test
fun testGetStartOfDay() {
val expectedStartOfDayUtc = LocalDateTime(
2017, 1, 1, 0, 0, 0, 0
).toInstant(TimeZone.UTC).toEpochMilliseconds()
val laterInTheDayUtc = LocalDateTime(
2017, 1, 1, 20, 0, 0, 0
).toInstant(TimeZone.UTC).toEpochMilliseconds()
val expectedStartOfDayUtc = unixTime(2017, 1, 1)
val laterInTheDayUtc = unixTime(2017, 1, 1, 20, 0)
val startOfDay = getStartOfDay(laterInTheDayUtc)
assertEquals(expectedStartOfDayUtc, startOfDay)
}
@Test
fun testGetStartOfToday() {
val expectedStartOfDayUtc = LocalDateTime(
2017, 1, 1, 0, 0, 0, 0
).toInstant(TimeZone.UTC).toEpochMilliseconds()
val laterInTheDayUtc = LocalDateTime(
2017, 1, 1, 20, 0, 0, 0
).toInstant(TimeZone.UTC).toEpochMilliseconds()
val expectedStartOfDayUtc = unixTime(2017, 1, 1)
val laterInTheDayUtc = unixTime(2017, 1, 1, 20, 0)
LocalDate.fixedLocalTime = laterInTheDayUtc
val startOfToday = getStartOfToday()
assertEquals(expectedStartOfDayUtc, startOfToday)
}
@Test
@Throws(Exception::class)
fun testGetStartOfDayWithOffset() {
val timestamp = unixTime(2020, 9, 3)
assertEquals(
timestamp,
getStartOfDayWithOffset(timestamp + LocalDate.HOUR_LENGTH),
)
LocalDate.setStartDayOffset(3, 30)
assertEquals(
(timestamp - LocalDate.DAY_LENGTH),
getStartOfDayWithOffset(timestamp + 3 * LocalDate.HOUR_LENGTH + 29 * LocalDate.MINUTE_LENGTH),
)
}
@Test
fun testGetStartOfTodayWithOffset_priorToOffset() {
val hourOffset = 3
LocalDate.setStartDayOffset(hourOffset, 0)
LocalDate.fixedTimeZone = kotlinx.datetime.TimeZone.UTC
val startOfYesterday = unixTime(2017, 1, 1, 0, 0)
val priorToOffset = unixTime(2017, 1, 2, hourOffset - 1, 0)
LocalDate.fixedLocalTime = priorToOffset
val startOfTodayWithOffset = getStartOfTodayWithOffset()
assertEquals(startOfYesterday, startOfTodayWithOffset)
}
@Test
fun testGetStartOfTodayWithOffset_afterOffset() {
val hourOffset = 3
LocalDate.setStartDayOffset(hourOffset, 0)
LocalDate.fixedTimeZone = kotlinx.datetime.TimeZone.UTC
val startOfToday = unixTime(2017, 1, 1, 0, 0)
val afterOffset = unixTime(2017, 1, 1, hourOffset + 1, 0)
LocalDate.fixedLocalTime = afterOffset
val startOfTodayWithOffset = getStartOfTodayWithOffset()
assertEquals(startOfToday, startOfTodayWithOffset)
}
private fun unixTime(year: Int, month: Int, day: Int): Long {
return unixTime(year, month, day, 0, 0)
}
private fun unixTime(
year: Int,
month: Int,
day: Int,
hour: Int,
minute: Int,
milliseconds: Long = 0
): Long {
return LocalDateTime(
year, month, day, hour, minute, (milliseconds / 1000).toInt(), 0
).toInstant(TimeZone.UTC).toEpochMilliseconds()
}
}

@ -19,6 +19,7 @@
package org.isoron.uhabits.core.reminders
import org.isoron.platform.time.LocalDate.Companion.getLocalTime
import org.isoron.platform.time.LocalDate.Companion.getStartOfDayWithOffset
import org.isoron.uhabits.core.AppScope
import org.isoron.uhabits.core.commands.ChangeHabitColorCommand
import org.isoron.uhabits.core.commands.Command
@ -29,7 +30,6 @@ import org.isoron.uhabits.core.models.HabitList
import org.isoron.uhabits.core.models.HabitMatcher
import org.isoron.uhabits.core.preferences.WidgetPreferences
import org.isoron.uhabits.core.utils.DateUtils.Companion.applyTimezone
import org.isoron.uhabits.core.utils.DateUtils.Companion.getStartOfDayWithOffset
import org.isoron.uhabits.core.utils.DateUtils.Companion.removeTimezone
import java.util.Locale
import java.util.Objects

@ -22,12 +22,12 @@ import kotlinx.datetime.Instant
import kotlinx.datetime.offsetAt
import org.isoron.platform.time.LocalDate
import org.isoron.platform.time.LocalDate.Companion.DAY_LENGTH
import org.isoron.platform.time.LocalDate.Companion.HOUR_LENGTH
import org.isoron.platform.time.LocalDate.Companion.MINUTE_LENGTH
import org.isoron.platform.time.LocalDate.Companion.getLocalTime
import org.isoron.platform.time.LocalDate.Companion.getStartOfDay
import org.isoron.platform.time.LocalDate.Companion.getStartOfToday
import org.isoron.platform.time.LocalDate.Companion.getStartOfTodayWithOffset
import org.isoron.platform.time.LocalDate.Companion.getTimeZone
import org.isoron.platform.time.LocalDate.Companion.startDayHourOffset
import org.isoron.platform.time.LocalDate.Companion.startDayMinuteOffset
import org.isoron.uhabits.core.models.Timestamp
import java.util.Calendar
import java.util.Calendar.DAY_OF_MONTH
@ -36,12 +36,9 @@ import java.util.Calendar.SHORT
import java.util.GregorianCalendar
import java.util.Locale
import java.util.TimeZone
import kotlin.collections.ArrayList
abstract class DateUtils {
companion object {
private var startDayHourOffset: Int = 0
private var startDayMinuteOffset: Int = 0
@JvmStatic
fun applyTimezone(localTimestamp: Long): Long {
@ -147,21 +144,12 @@ abstract class DateUtils {
@JvmStatic
fun getTodayWithOffset(): Timestamp = Timestamp(getStartOfTodayWithOffset())
@JvmStatic
fun getStartOfDayWithOffset(timestamp: Long): Long {
val offset = startDayHourOffset * HOUR_LENGTH + startDayMinuteOffset * MINUTE_LENGTH
return getStartOfDay(timestamp - offset)
}
@JvmStatic
fun getStartOfTomorrowWithOffset(): Long = getUpcomingTimeInMillis(
startDayHourOffset,
startDayMinuteOffset
)
@JvmStatic
fun getStartOfTodayWithOffset(): Long = getStartOfDayWithOffset(getLocalTime())
@JvmStatic
fun millisecondsUntilTomorrowWithOffset(): Long =
getStartOfTomorrowWithOffset() - getLocalTime()
@ -179,12 +167,6 @@ abstract class DateUtils {
return timestamp + (tz.offsetAt(Instant.fromEpochMilliseconds(timestamp)).totalSeconds * 1000)
}
@JvmStatic
fun setStartDayOffset(hourOffset: Int, minuteOffset: Int) {
startDayHourOffset = hourOffset
startDayMinuteOffset = minuteOffset
}
private fun getLocale(): Locale {
return Locale.forLanguageTag(LocalDate.getLocale().toLanguageTag().toString())
}

@ -22,6 +22,7 @@ import com.nhaarman.mockitokotlin2.spy
import com.nhaarman.mockitokotlin2.validateMockitoUsage
import org.apache.commons.io.IOUtils
import org.isoron.platform.time.LocalDate
import org.isoron.platform.time.LocalDate.Companion.setStartDayOffset
import org.isoron.uhabits.core.commands.CommandRunner
import org.isoron.uhabits.core.database.Database
import org.isoron.uhabits.core.database.DatabaseOpener
@ -34,7 +35,6 @@ import org.isoron.uhabits.core.models.memory.MemoryModelFactory
import org.isoron.uhabits.core.tasks.SingleThreadTaskRunner
import org.isoron.uhabits.core.test.HabitFixtures
import org.isoron.uhabits.core.utils.DateUtils.Companion.getStartOfTodayCalendar
import org.isoron.uhabits.core.utils.DateUtils.Companion.setStartDayOffset
import org.junit.After
import org.junit.Before
import org.junit.Test

@ -26,15 +26,14 @@ import org.isoron.platform.time.LocalDate
import org.isoron.platform.time.LocalDate.Companion.DAY_LENGTH
import org.isoron.platform.time.LocalDate.Companion.HOUR_LENGTH
import org.isoron.platform.time.LocalDate.Companion.MINUTE_LENGTH
import org.isoron.platform.time.LocalDate.Companion.setStartDayOffset
import org.isoron.uhabits.core.BaseUnitTest
import org.isoron.uhabits.core.models.Timestamp
import org.isoron.uhabits.core.utils.DateUtils.Companion.applyTimezone
import org.isoron.uhabits.core.utils.DateUtils.Companion.formatHeaderDate
import org.isoron.uhabits.core.utils.DateUtils.Companion.getStartOfDayWithOffset
import org.isoron.uhabits.core.utils.DateUtils.Companion.getTodayWithOffset
import org.isoron.uhabits.core.utils.DateUtils.Companion.millisecondsUntilTomorrowWithOffset
import org.isoron.uhabits.core.utils.DateUtils.Companion.removeTimezone
import org.isoron.uhabits.core.utils.DateUtils.Companion.setStartDayOffset
import org.isoron.uhabits.core.utils.DateUtils.Companion.truncate
import org.junit.Before
import org.junit.Test
@ -144,30 +143,6 @@ class DateUtilsTest : BaseUnitTest() {
assertThat(startOfTomorrowWithOffset, equalTo(startOfTomorrow))
}
@Test
fun testGetStartOfTodayWithOffset_priorToOffset() {
val hourOffset = 3
setStartDayOffset(hourOffset, 0)
LocalDate.fixedTimeZone = kotlinx.datetime.TimeZone.UTC
val startOfYesterday = unixTime(2017, Calendar.JANUARY, 1, 0, 0)
val priorToOffset = unixTime(2017, Calendar.JANUARY, 2, hourOffset - 1, 0)
LocalDate.fixedLocalTime = priorToOffset
val startOfTodayWithOffset = DateUtils.getStartOfTodayWithOffset()
assertThat(startOfYesterday, equalTo(startOfTodayWithOffset))
}
@Test
fun testGetStartOfTodayWithOffset_afterOffset() {
val hourOffset = 3
setStartDayOffset(hourOffset, 0)
LocalDate.fixedTimeZone = kotlinx.datetime.TimeZone.UTC
val startOfToday = unixTime(2017, Calendar.JANUARY, 1, 0, 0)
val afterOffset = unixTime(2017, Calendar.JANUARY, 1, hourOffset + 1, 0)
LocalDate.fixedLocalTime = afterOffset
val startOfTodayWithOffset = DateUtils.getStartOfTodayWithOffset()
assertThat(startOfToday, equalTo(startOfTodayWithOffset))
}
@Test
fun testTruncate_dayOfWeek() {
val field = DateUtils.TruncateField.WEEK_NUMBER
@ -343,21 +318,6 @@ class DateUtilsTest : BaseUnitTest() {
)
}
@Test
@Throws(Exception::class)
fun testGetStartOfDayWithOffset() {
val timestamp = unixTime(2020, Calendar.SEPTEMBER, 3)
assertThat(
getStartOfDayWithOffset(timestamp + HOUR_LENGTH),
equalTo(timestamp)
)
setStartDayOffset(3, 30)
assertThat(
getStartOfDayWithOffset(timestamp + 3 * HOUR_LENGTH + 29 * MINUTE_LENGTH),
equalTo(timestamp - DAY_LENGTH)
)
}
@Test
fun test_applyTimezone() {
LocalDate.fixedTimeZone = kotlinx.datetime.TimeZone.of("Australia/Sydney")

Loading…
Cancel
Save