From 0fd933dfff7c96c822d3da04166b1acc74cbb688 Mon Sep 17 00:00:00 2001 From: imDMK Date: Mon, 2 Mar 2026 12:27:19 +0100 Subject: [PATCH 1/2] refactor: replace synchronized access with AtomicReference Removes explicit synchronization and introduces lock-free thread-safe registration using AtomicReference#compareAndSet. --- .../imdmk/playtime/PlayTimeApiProvider.java | 20 +++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java b/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java index 66478e8..662c686 100644 --- a/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java +++ b/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java @@ -2,9 +2,11 @@ import org.jetbrains.annotations.NotNull; +import java.util.concurrent.atomic.AtomicReference; + public final class PlayTimeApiProvider { - private static volatile PlayTimeApi API; // visibility across threads + private static final AtomicReference API = new AtomicReference<>(); private PlayTimeApiProvider() { throw new UnsupportedOperationException("This class cannot be instantiated."); @@ -12,7 +14,7 @@ private PlayTimeApiProvider() { @NotNull public static PlayTimeApi get() { - final PlayTimeApi api = API; + final PlayTimeApi api = API.get(); if (api == null) { throw new IllegalStateException("PlayTimeAPI is not registered."); } @@ -20,20 +22,18 @@ public static PlayTimeApi get() { } public static boolean isRegistered() { - return API != null; + return API.get() != null; } - static synchronized void register(@NotNull PlayTimeApi api) { - if (API != null) { + static void register(@NotNull PlayTimeApi api) { + if (!API.compareAndSet(null, api)) { throw new IllegalStateException("PlayTimeAPI is already registered."); } - API = api; } - static synchronized void unregister() { - if (API == null) { + static void unregister() { + if (!API.compareAndSet(API.get(), null)) { throw new IllegalStateException("PlayTimeAPI is not registered."); } - API = null; } -} +} \ No newline at end of file From 49484841ae93f9b78228b14ae455617c9f4d1256 Mon Sep 17 00:00:00 2001 From: imDMK Date: Mon, 2 Mar 2026 12:33:39 +0100 Subject: [PATCH 2/2] Follow Gemini review suggestions. --- .../java/com/github/imdmk/playtime/PlayTimeApiProvider.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java b/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java index 662c686..4cf18ac 100644 --- a/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java +++ b/playtime-api/src/main/java/com/github/imdmk/playtime/PlayTimeApiProvider.java @@ -32,7 +32,7 @@ static void register(@NotNull PlayTimeApi api) { } static void unregister() { - if (!API.compareAndSet(API.get(), null)) { + if (API.getAndSet(null) == null) { throw new IllegalStateException("PlayTimeAPI is not registered."); } }