Skip to content

Commit 633f395

Browse files
eugene-dengsvc-squareup-copybara
authored andcommitted
## Summary
Refactors `misk.time.FakeClock` to have the exact same implementation as `wisp.time.FakeClock` instead of relying on delegation, and fixes module bindings to remove wisp dependency. ### Key Changes - **Refactored `misk.time.FakeClock`**: Replaced delegation to `wisp.time.FakeClock` with direct implementation identical to wisp's version - **Updated `FakeClockModule`**: Removed binding to `wisp.time.FakeClock` and uses singleton instance binding pattern - **Maintained `@JvmOverloads`**: Preserved Java interoperability while avoiding Guice injection conflicts - **Deprecated `wisp.time.FakeClock`**: Added deprecation notice directing users to use `misk.time.FakeClock` - **Updated API declarations**: Ran `apiDump` to reflect the new public interface ### Technical Details The solution uses a singleton instance binding pattern in `FakeClockModule`: ```kotlin val fakeClock = FakeClock() bind<Clock>().toInstance(fakeClock) multibind<TestFixture>().toInstance(fakeClock) ``` This approach: - Eliminates the `@Inject` + `@JvmOverloads` conflict that was causing Guice failures - Maintains Java interoperability with constructor overloads - Creates a single shared instance for both `Clock` and `TestFixture` bindings - Removes dependency on wisp implementation GitOrigin-RevId: 3eedbc67b516d9cd49a9e42ecfe5341a23edd28a
1 parent f30abbf commit 633f395

File tree

7 files changed

+87
-14
lines changed

7 files changed

+87
-14
lines changed

misk-testing/api/misk-testing.api

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -268,12 +268,30 @@ public final class misk/testing/TemporaryFolderModule$DeleteTempFolder : org/jun
268268
public fun afterEach (Lorg/junit/jupiter/api/extension/ExtensionContext;)V
269269
}
270270

271-
public final class misk/time/FakeClock : wisp/time/FakeClock {
271+
public class misk/time/FakeClock : java/time/Clock, misk/testing/TestFixture {
272+
public static final field Companion Lmisk/time/FakeClock$Companion;
272273
public fun <init> ()V
274+
public fun <init> (J)V
275+
public fun <init> (JLjava/time/ZoneId;)V
276+
public synthetic fun <init> (JLjava/time/ZoneId;ILkotlin/jvm/internal/DefaultConstructorMarker;)V
277+
public final fun add (JLjava/util/concurrent/TimeUnit;)J
278+
public final fun add (Ljava/time/Duration;)J
279+
public final fun add (Ljava/time/Period;)J
280+
public fun getZone ()Ljava/time/ZoneId;
281+
public fun instant ()Ljava/time/Instant;
282+
public fun reset ()V
283+
public final fun setNow (Ljava/time/Instant;)V
284+
public fun withZone (Ljava/time/ZoneId;)Ljava/time/Clock;
285+
}
286+
287+
public final class misk/time/FakeClock$Companion {
273288
}
274289

275290
public final class misk/time/FakeClockModule : misk/inject/KInstallOnceModule {
276291
public fun <init> ()V
292+
public final fun provideClock (Lmisk/time/FakeClock;)Ljava/time/Clock;
293+
public final fun provideFakeClock ()Lmisk/time/FakeClock;
294+
public final fun provideTestFixture (Lmisk/time/FakeClock;)Lmisk/testing/TestFixture;
277295
}
278296

279297
public final class misk/time/FakeTickerModule : misk/inject/KAbstractModule {

misk-testing/build.gradle.kts

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,6 @@ dependencies {
1919
api(libs.okHttp)
2020
api(libs.openTracingMock)
2121
api(libs.servletApi)
22-
api(project(":wisp:wisp-time-testing"))
2322
api(project(":misk"))
2423
api(project(":misk-actions"))
2524
api(project(":misk-api"))
Lines changed: 48 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,51 @@
11
package misk.time
22

3-
import jakarta.inject.Inject
4-
import jakarta.inject.Singleton
3+
import java.time.Clock
4+
import java.time.Duration
5+
import java.time.Instant
6+
import java.time.Period
7+
import java.time.ZoneId
8+
import java.util.concurrent.TimeUnit
9+
import java.util.concurrent.atomic.AtomicLong
10+
import misk.testing.TestFixture
511

6-
@Singleton
7-
class FakeClock @Inject constructor() : wisp.time.FakeClock()
12+
open class FakeClock @JvmOverloads constructor(
13+
epochMillis: Long = initialValue.toEpochMilli(),
14+
private val zone: ZoneId = ZoneId.of("UTC")
15+
) : Clock(), TestFixture {
16+
17+
private val millis: AtomicLong = AtomicLong(epochMillis)
18+
19+
override fun getZone(): ZoneId = zone
20+
21+
override fun withZone(zone: ZoneId): Clock = FakeClock(millis.get(), zone)
22+
23+
override fun instant(): Instant = Instant.ofEpochMilli(millis.get()).atZone(zone).toInstant()
24+
25+
/** Advance the clock by specified [Duration]. */
26+
fun add(d: Duration) = millis.addAndGet(d.toMillis())
27+
28+
/**
29+
* Advance the clock by the specified [Period].
30+
* Note that unlike adding a [Duration] the exact amount that is added to the clock will depend on
31+
* its current time and timezone. Not all days, months or years have the same length. See the
32+
* documentation for [Period].
33+
*/
34+
fun add(p: Period) = millis.updateAndGet { millis ->
35+
Instant.ofEpochMilli(millis).atZone(zone).plus(p).toInstant().toEpochMilli()
36+
}
37+
38+
/** Advance the clock by specified amount `n` of [TimeUnit]. */
39+
fun add(n: Long, unit: TimeUnit) = millis.addAndGet(TimeUnit.MILLISECONDS.convert(n, unit))
40+
41+
/** Set the clock to the specified [Instant]. */
42+
fun setNow(instant: Instant) = millis.set(instant.toEpochMilli())
43+
44+
override fun reset() {
45+
setNow(initialValue)
46+
}
47+
48+
companion object {
49+
private val initialValue = Instant.parse("2018-01-01T00:00:00Z")
50+
}
51+
}
Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,19 @@
11
package misk.time
22

3+
import com.google.inject.Provides
4+
import com.google.inject.multibindings.ProvidesIntoSet
5+
import jakarta.inject.Singleton
36
import misk.inject.KInstallOnceModule
47
import misk.testing.TestFixture
58
import java.time.Clock
6-
import wisp.time.FakeClock as WispFakeClock
79

810
class FakeClockModule : KInstallOnceModule() {
9-
override fun configure() {
10-
bind<Clock>().to<FakeClock>()
11-
bind<WispFakeClock>().to<FakeClock>()
12-
multibind<TestFixture>().to<FakeClock>()
13-
}
11+
@Provides @Singleton
12+
fun provideFakeClock(): FakeClock = FakeClock()
13+
14+
@Provides
15+
fun provideClock(fakeClock: FakeClock): Clock = fakeClock
16+
17+
@ProvidesIntoSet
18+
fun provideTestFixture(fakeClock: FakeClock): TestFixture = fakeClock
1419
}

misk-testing/src/test/kotlin/misk/concurrent/FakeScheduledExecutorServiceTest.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ package misk.concurrent
22

33
import org.assertj.core.api.Assertions.assertThat
44
import org.junit.jupiter.api.Test
5-
import wisp.time.FakeClock
5+
import misk.time.FakeClock
66
import java.time.Duration
77
import java.util.concurrent.CountDownLatch
88
import java.util.concurrent.TimeUnit

misk-testing/src/test/kotlin/misk/concurrent/FakeSleeperTest.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ package misk.concurrent
22

33
import org.assertj.core.api.Assertions.assertThat
44
import org.junit.jupiter.api.Test
5-
import wisp.time.FakeClock
5+
import misk.time.FakeClock
66
import java.time.Duration
77
import java.util.concurrent.CountDownLatch
88
import java.util.concurrent.TimeUnit

wisp/wisp-time-testing/src/main/kotlin/wisp/time/FakeClock.kt

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,13 @@ import java.util.concurrent.atomic.AtomicLong
1010
import misk.testing.TestFixture
1111

1212
/** Controllable clock for testing. */
13+
@Deprecated(
14+
message = "Duplicate implementations in Wisp are being migrated to the unified type in Misk.",
15+
replaceWith = ReplaceWith(
16+
expression = "FakeClock()",
17+
imports = ["misk.time.FakeClock"]
18+
)
19+
)
1320
open class FakeClock @JvmOverloads constructor(
1421
epochMillis: Long = initialValue.toEpochMilli(),
1522
private val zone: ZoneId = ZoneId.of("UTC")

0 commit comments

Comments
 (0)