diff --git a/extensions-core/kafka-indexing-service/src/test/java/org/apache/druid/indexing/kafka/simulate/EmbeddedDimensionValueSetShardSpecTest.java b/extensions-core/kafka-indexing-service/src/test/java/org/apache/druid/indexing/kafka/simulate/EmbeddedDimensionValueSetShardSpecTest.java
index 74ad0c6ecdb9..d332e4f99873 100644
--- a/extensions-core/kafka-indexing-service/src/test/java/org/apache/druid/indexing/kafka/simulate/EmbeddedDimensionValueSetShardSpecTest.java
+++ b/extensions-core/kafka-indexing-service/src/test/java/org/apache/druid/indexing/kafka/simulate/EmbeddedDimensionValueSetShardSpecTest.java
@@ -244,8 +244,8 @@ public void test_multiDimensionAndMultiValuePartitionDimensionValues()
Assertions.assertEquals("5", cluster.runSql(
"SELECT COUNT(*) FROM %s WHERE %s = 'tenant_b'", dataSource, COL_TENANT));
- // Numeric dimension equality filter still returns correct counts. Note this does NOT prune (numeric filters
- // opt out of segment pruning); pruning behavior is asserted in test_numericDimension_isNotPruned.
+ // Numeric equality filter correctness. Its LongDimensionSchema makes it eligible for type-gated pruning, which is
+ // asserted in test_numericLongDimension_isPruned.
Assertions.assertEquals("5", cluster.runSql(
"SELECT COUNT(*) FROM %s WHERE %s = 1", dataSource, colRegionCode));
Assertions.assertEquals("5", cluster.runSql(
@@ -277,26 +277,24 @@ public void test_multiDimensionAndMultiValuePartitionDimensionValues()
}
/**
- * Numeric (Long) tracked dimensions are recorded in the shard spec but are NOT used for pruning: numeric query
- * filters opt out of segment pruning (their getDimensionRangeSet returns null, since pruning compares values
- * lexicographically), so a numeric equality filter scans every segment even though each segment declares exactly
- * one numeric value. Queries stay correct; there is simply no pruning benefit.
- *
- *
This is intentional for now. We could either consider extending pruning to numeric types with type-aware
- * (non-lexicographic) comparison, or (b) reject numeric dimensions outright when they're declared.
+ * A numeric (LONG) tracked dimension with an explicit {@link LongDimensionSchema} IS pruned: the broker's
+ * equality/IN/IS NULL channel is type-gated on {@code dimensionColumnTypes}, which the task stamps only for such a
+ * schema (a LONG stringifies identically on ingest and query, so set membership is exact). This is exact
+ * set-membership, not a range comparison, so it works even though the dimension is numeric.
*/
@Test
- public void test_numericDimension_isNotPruned()
+ public void test_numericLongDimension_isPruned()
{
- final String colCode = "code"; // numeric (Long), tracked
+ final String colCode = "code"; // numeric (Long), tracked, explicit LongDimensionSchema
final String topic = dataSource + "_topic";
kafkaServer.createTopicWithPartitions(topic, 1);
- // One distinct numeric code per DAY segment: Day1=1, Day2=2, Day3=3. If numeric pruning worked, "code = 1" would
- // scan only Day1; because it does NOT, all three segments are scanned.
+ // One code per day: Day1=1, Day2=2, Day3=3; stamped LONG, so "code = 1" prunes to Day1 only. Day1's raw tokens are
+ // deliberately non-canonical ("00001", "+1") to exercise the capture-time coercion to the canonical "1" (the
+ // broker's query value); without it Day1 would stamp ["00001","+1"], miss the query set {"1"}, and be wrongly pruned.
final List> records = new ArrayList<>();
- records.add(record(topic, "%s,1,val_0", DateTimes.of("2025-01-01T01:00:00")));
- records.add(record(topic, "%s,1,val_1", DateTimes.of("2025-01-01T02:00:00")));
+ records.add(record(topic, "%s,00001,val_0", DateTimes.of("2025-01-01T01:00:00")));
+ records.add(record(topic, "%s,+1,val_1", DateTimes.of("2025-01-01T02:00:00")));
records.add(record(topic, "%s,2,val_2", DateTimes.of("2025-01-02T01:00:00")));
records.add(record(topic, "%s,2,val_3", DateTimes.of("2025-01-02T02:00:00")));
records.add(record(topic, "%s,3,val_4", DateTimes.of("2025-01-03T01:00:00")));
@@ -341,20 +339,43 @@ public void test_numericDimension_isNotPruned()
awaitRowsProcessed(6);
suspendAndAwaitHandoff(spec, 1);
- // The numeric value IS recorded in the shard spec (stringified), even though it is never used for pruning.
verifyAllSegmentsHaveDimensionValueSetShardSpec(dataSource);
+ // The published shard spec stamps colCode's type as LONG, gating the broker's numeric pruning channel.
+ final List