From 8d8c9feab846e6b545002dc229fee2cfe8b56bf6 Mon Sep 17 00:00:00 2001 From: Tarun Rao Date: Mon, 15 Jun 2026 12:01:40 +0530 Subject: [PATCH 1/5] NO-TICKET: Add upsertObjectWithExplicitPrev to IdentifiedObjectStore --- .../config/objectstore/IdentifiedObjectStore.java | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java index 7166024089..04a48aa4a6 100644 --- a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java +++ b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java @@ -82,6 +82,10 @@ protected Value buildValueForChangeEvent(T data) { return this.buildValueFromData(data); } + protected Optional getDefaultPreviousValue(RequestContext requestContext, T data) { + return Optional.empty(); + } + protected String buildClassNameForChangeEvent(T data) { return data.getClass().getName(); } @@ -279,7 +283,13 @@ private Optional> processUpsertResult( if (response.hasPrevConfig()) { tryReportUpdate(requestContext, result, response.getPrevConfig()); } else { - tryReportCreation(requestContext, result); + Optional defaultPrev = + getDefaultPreviousValue(requestContext, result.getData()); + if (defaultPrev.isPresent()) { + tryReportUpdate(requestContext, result, defaultPrev.get()); + } else { + tryReportCreation(requestContext, result); + } } }); return optionalResult; From 16fefa12419b9294f757e6d08e91665f63148587 Mon Sep 17 00:00:00 2001 From: Tarun Rao Date: Tue, 16 Jun 2026 19:24:29 +0530 Subject: [PATCH 2/5] NO-TICKET: Apply spotless formatting and update gradle locks --- .../hypertrace/config/objectstore/IdentifiedObjectStore.java | 3 +-- settings-gradle.lockfile | 5 +++++ 2 files changed, 6 insertions(+), 2 deletions(-) create mode 100644 settings-gradle.lockfile diff --git a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java index 8fe0cd9df7..a3e2484b0b 100644 --- a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java +++ b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java @@ -283,8 +283,7 @@ private Optional> processUpsertResult( if (response.hasPrevConfig()) { tryReportUpdate(requestContext, result, response.getPrevConfig()); } else { - Optional defaultPrev = - getDefaultPreviousValue(requestContext, result.getData()); + Optional defaultPrev = getDefaultPreviousValue(requestContext, result.getData()); if (defaultPrev.isPresent()) { tryReportUpdate(requestContext, result, defaultPrev.get()); } else { diff --git a/settings-gradle.lockfile b/settings-gradle.lockfile new file mode 100644 index 0000000000..814e316493 --- /dev/null +++ b/settings-gradle.lockfile @@ -0,0 +1,5 @@ +# This is a Gradle generated file for dependency locking. +# Manual edits can break the build and are not advised. +# This file is expected to be part of source control. +org.hypertrace.bom:hypertrace-version-catalog:0.3.49=incomingCatalogForCommonLibs0 +empty=incomingCatalogForLocalLibs0 From acf31d45ba2674e5d2360f43bd22dbd0a75dc014 Mon Sep 17 00:00:00 2001 From: Tarun Rao Date: Tue, 16 Jun 2026 19:30:24 +0530 Subject: [PATCH 3/5] NO-TICKET: Remove settings-gradle.lockfile --- settings-gradle.lockfile | 5 ----- 1 file changed, 5 deletions(-) delete mode 100644 settings-gradle.lockfile diff --git a/settings-gradle.lockfile b/settings-gradle.lockfile deleted file mode 100644 index 814e316493..0000000000 --- a/settings-gradle.lockfile +++ /dev/null @@ -1,5 +0,0 @@ -# This is a Gradle generated file for dependency locking. -# Manual edits can break the build and are not advised. -# This file is expected to be part of source control. -org.hypertrace.bom:hypertrace-version-catalog:0.3.49=incomingCatalogForCommonLibs0 -empty=incomingCatalogForLocalLibs0 From 72a237963752d094de6329e20917bf46bf8bfe61 Mon Sep 17 00:00:00 2001 From: Tarun Rao Date: Mon, 29 Jun 2026 22:52:03 +0530 Subject: [PATCH 4/5] NO-TICKET: Add default_config_json to change events via getDefaultConfigValue hook --- .../objectstore/IdentifiedObjectStore.java | 10 +++- .../event/v1/config_change_event_value.proto | 1 + .../event/api/ConfigChangeEventGenerator.java | 20 ++++++++ .../impl/ConfigChangeEventGeneratorImpl.java | 51 +++++++++++++++++-- 4 files changed, 77 insertions(+), 5 deletions(-) diff --git a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java index a3e2484b0b..c018653cac 100644 --- a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java +++ b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java @@ -90,6 +90,10 @@ protected String buildClassNameForChangeEvent(T data) { return data.getClass().getName(); } + protected Optional getDefaultConfigValue(RequestContext requestContext, T data) { + return Optional.empty(); + } + protected List> orderFetchedObjects( List> objects) { return objects; @@ -342,7 +346,8 @@ private void tryReportCreation(RequestContext requestContext, ContextualConfigOb requestContext, this.buildClassNameForChangeEvent(result.getData()), result.getContext(), - this.buildValueForChangeEvent(result.getData()))); + this.buildValueForChangeEvent(result.getData()), + getDefaultConfigValue(requestContext, result.getData()))); } private void tryReportUpdate( @@ -365,7 +370,8 @@ private void tryReportUpdate( previousValue); return previousValue; }), - this.buildValueForChangeEvent(result.getData()))); + this.buildValueForChangeEvent(result.getData()), + getDefaultConfigValue(requestContext, result.getData()))); } protected Deadline getDeadline() { diff --git a/config-service-change-event-api/src/main/proto/org/hypertrace/config/change/event/v1/config_change_event_value.proto b/config-service-change-event-api/src/main/proto/org/hypertrace/config/change/event/v1/config_change_event_value.proto index 728fef1895..a1596a2ce6 100644 --- a/config-service-change-event-api/src/main/proto/org/hypertrace/config/change/event/v1/config_change_event_value.proto +++ b/config-service-change-event-api/src/main/proto/org/hypertrace/config/change/event/v1/config_change_event_value.proto @@ -16,6 +16,7 @@ message ConfigChangeEventValue { optional string user_name = 5; string user_email = 7; int64 event_time_millis = 6; + string default_config_json = 8; } message ConfigCreateEvent { diff --git a/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/api/ConfigChangeEventGenerator.java b/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/api/ConfigChangeEventGenerator.java index 6181cfa293..cbec5026b9 100644 --- a/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/api/ConfigChangeEventGenerator.java +++ b/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/api/ConfigChangeEventGenerator.java @@ -1,6 +1,7 @@ package org.hypertrace.config.service.change.event.api; import com.google.protobuf.Value; +import java.util.Optional; import org.hypertrace.core.grpcutils.context.RequestContext; /** The interface config change event generator. */ @@ -72,4 +73,23 @@ void sendUpdateNotification( String context, Value prevConfig, Value latestConfig); + + default void sendCreateNotification( + RequestContext requestContext, + String configType, + String context, + Value config, + Optional defaultConfig) { + sendCreateNotification(requestContext, configType, context, config); + } + + default void sendUpdateNotification( + RequestContext requestContext, + String configType, + String context, + Value prevConfig, + Value latestConfig, + Optional defaultConfig) { + sendUpdateNotification(requestContext, configType, context, prevConfig, latestConfig); + } } diff --git a/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java b/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java index 86aabdd750..e4a7fce9be 100644 --- a/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java +++ b/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java @@ -70,7 +70,7 @@ public void sendDeleteNotification( public void sendUpdateNotification( RequestContext requestContext, String configType, Value prevConfig, Value latestConfig) { produceUpdateNotification( - requestContext, configType, Optional.empty(), prevConfig, latestConfig); + requestContext, configType, Optional.empty(), prevConfig, latestConfig, Optional.empty()); } @Override @@ -93,7 +93,29 @@ public void sendUpdateNotification( Value prevConfig, Value latestConfig) { produceUpdateNotification( - requestContext, configType, Optional.of(context), prevConfig, latestConfig); + requestContext, configType, Optional.of(context), prevConfig, latestConfig, Optional.empty()); + } + + @Override + public void sendCreateNotification( + RequestContext requestContext, + String configType, + String context, + Value config, + Optional defaultConfig) { + produceCreateNotification(requestContext, configType, Optional.of(context), config, defaultConfig); + } + + @Override + public void sendUpdateNotification( + RequestContext requestContext, + String configType, + String context, + Value prevConfig, + Value latestConfig, + Optional defaultConfig) { + produceUpdateNotification( + requestContext, configType, Optional.of(context), prevConfig, latestConfig, defaultConfig); } private void produceCreateNotification( @@ -101,6 +123,15 @@ private void produceCreateNotification( String configType, Optional contextOptional, Value config) { + produceCreateNotification(requestContext, configType, contextOptional, config, Optional.empty()); + } + + private void produceCreateNotification( + RequestContext requestContext, + String configType, + Optional contextOptional, + Value config, + Optional defaultConfig) { String tenantId = requestContext.getTenantId().get(); try { Builder builder = ConfigChangeEventValue.newBuilder(); @@ -110,6 +141,7 @@ private void produceCreateNotification( .build()); builder.setEventTimeMillis(clock.millis()); populateUserDetails(requestContext, builder); + setDefaultConfigJson(builder, defaultConfig); configChangeEventProducer.send( KeyUtil.getKey(tenantId, configType, contextOptional), builder.build()); } catch (Exception ex) { @@ -127,7 +159,8 @@ private void produceUpdateNotification( String configType, Optional contextOptional, Value prevConfig, - Value latestConfig) { + Value latestConfig, + Optional defaultConfig) { String tenantId = requestContext.getTenantId().get(); try { Builder builder = ConfigChangeEventValue.newBuilder(); @@ -138,6 +171,7 @@ private void produceUpdateNotification( .build()); builder.setEventTimeMillis(clock.millis()); populateUserDetails(requestContext, builder); + setDefaultConfigJson(builder, defaultConfig); configChangeEventProducer.send( KeyUtil.getKey(tenantId, configType, contextOptional), builder.build()); } catch (Exception ex) { @@ -176,6 +210,17 @@ private void produceDeleteNotification( } } + private void setDefaultConfigJson(Builder builder, Optional defaultConfig) { + defaultConfig.ifPresent( + value -> { + try { + builder.setDefaultConfigJson(ConfigProtoConverter.convertToJsonString(value)); + } catch (Exception ex) { + log.warn("Unable to convert default config to JSON for change event", ex); + } + }); + } + private void populateUserDetails(RequestContext requestContext, Builder builder) { requestContext.getUserId().ifPresent(builder::setUserId); requestContext.getName().ifPresent(builder::setUserName); From 01ce69765f20efc49826c1f3dcdc8ce0b960505a Mon Sep 17 00:00:00 2001 From: Tarun Rao Date: Mon, 29 Jun 2026 23:20:46 +0530 Subject: [PATCH 5/5] NO-TICKET: Remove getDefaultPreviousValue, merge produceCreateNotification into single overload --- .../config/objectstore/IdentifiedObjectStore.java | 11 +---------- .../event/impl/ConfigChangeEventGeneratorImpl.java | 12 ++---------- 2 files changed, 3 insertions(+), 20 deletions(-) diff --git a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java index c018653cac..03256ea947 100644 --- a/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java +++ b/config-object-store/src/main/java/org/hypertrace/config/objectstore/IdentifiedObjectStore.java @@ -82,10 +82,6 @@ protected Value buildValueForChangeEvent(T data) { return this.buildValueFromData(data); } - protected Optional getDefaultPreviousValue(RequestContext requestContext, T data) { - return Optional.empty(); - } - protected String buildClassNameForChangeEvent(T data) { return data.getClass().getName(); } @@ -287,12 +283,7 @@ private Optional> processUpsertResult( if (response.hasPrevConfig()) { tryReportUpdate(requestContext, result, response.getPrevConfig()); } else { - Optional defaultPrev = getDefaultPreviousValue(requestContext, result.getData()); - if (defaultPrev.isPresent()) { - tryReportUpdate(requestContext, result, defaultPrev.get()); - } else { - tryReportCreation(requestContext, result); - } + tryReportCreation(requestContext, result); } }); return optionalResult; diff --git a/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java b/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java index e4a7fce9be..885e867cd8 100644 --- a/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java +++ b/config-service-change-event-generator/src/main/java/org/hypertrace/config/service/change/event/impl/ConfigChangeEventGeneratorImpl.java @@ -57,7 +57,7 @@ public class ConfigChangeEventGeneratorImpl implements ConfigChangeEventGenerato @Override public void sendCreateNotification( RequestContext requestContext, String configType, Value config) { - produceCreateNotification(requestContext, configType, Optional.empty(), config); + produceCreateNotification(requestContext, configType, Optional.empty(), config, Optional.empty()); } @Override @@ -76,7 +76,7 @@ public void sendUpdateNotification( @Override public void sendCreateNotification( RequestContext requestContext, String configType, String context, Value config) { - produceCreateNotification(requestContext, configType, Optional.of(context), config); + produceCreateNotification(requestContext, configType, Optional.of(context), config, Optional.empty()); } @Override @@ -118,14 +118,6 @@ public void sendUpdateNotification( requestContext, configType, Optional.of(context), prevConfig, latestConfig, defaultConfig); } - private void produceCreateNotification( - RequestContext requestContext, - String configType, - Optional contextOptional, - Value config) { - produceCreateNotification(requestContext, configType, contextOptional, config, Optional.empty()); - } - private void produceCreateNotification( RequestContext requestContext, String configType,