diff --git a/dice/pom.xml b/dice/pom.xml
index 09616eca..02e4d08d 100644
--- a/dice/pom.xml
+++ b/dice/pom.xml
@@ -53,7 +53,7 @@
- com.fasterxml.jackson.module
+ tools.jackson.module
jackson-module-kotlin
diff --git a/dice/src/main/kotlin/com/embabel/dice/agent/DiscoveryTools.kt b/dice/src/main/kotlin/com/embabel/dice/agent/DiscoveryTools.kt
index ae898528..d60efc7e 100644
--- a/dice/src/main/kotlin/com/embabel/dice/agent/DiscoveryTools.kt
+++ b/dice/src/main/kotlin/com/embabel/dice/agent/DiscoveryTools.kt
@@ -18,6 +18,7 @@ package com.embabel.dice.agent
import com.embabel.agent.api.annotation.LlmTool
import com.embabel.agent.api.tool.Tool
import com.embabel.agent.core.ContextId
+import com.embabel.dice.agent.DiscoveryTools.Companion.asTools
import com.embabel.dice.projection.lineage.ProjectionRecordStore
import com.embabel.dice.projection.memory.CollectorRunner
import com.embabel.dice.query.discovery.CollectorDryRunDto
@@ -25,8 +26,8 @@ import com.embabel.dice.query.discovery.DiscoveryQuery
import com.embabel.dice.query.discovery.ProjectionHealthDto
import com.embabel.dice.query.discovery.RetrievalMode
import com.embabel.dice.query.discovery.RetrievalRouter
-import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
import org.slf4j.LoggerFactory
+import tools.jackson.module.kotlin.jacksonObjectMapper
/**
* LLM-invocable tools exposing the discovery surface — proposition query, graph path, why-explain,
diff --git a/dice/src/main/kotlin/com/embabel/dice/agent/Memory.kt b/dice/src/main/kotlin/com/embabel/dice/agent/Memory.kt
index 8220e706..7c15e3d7 100644
--- a/dice/src/main/kotlin/com/embabel/dice/agent/Memory.kt
+++ b/dice/src/main/kotlin/com/embabel/dice/agent/Memory.kt
@@ -27,8 +27,8 @@ import com.embabel.dice.proposition.Proposition
import com.embabel.dice.proposition.PropositionQuery
import com.embabel.dice.proposition.PropositionRepository
import com.embabel.dice.proposition.PropositionStatus
-import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
import org.slf4j.LoggerFactory
+import tools.jackson.module.kotlin.jacksonObjectMapper
import java.util.function.UnaryOperator
/**
diff --git a/dice/src/main/kotlin/com/embabel/dice/proposition/store/JsonFilePropositionRepository.kt b/dice/src/main/kotlin/com/embabel/dice/proposition/store/JsonFilePropositionRepository.kt
index 6665dbe6..79f7e654 100644
--- a/dice/src/main/kotlin/com/embabel/dice/proposition/store/JsonFilePropositionRepository.kt
+++ b/dice/src/main/kotlin/com/embabel/dice/proposition/store/JsonFilePropositionRepository.kt
@@ -24,9 +24,9 @@ import com.embabel.dice.proposition.PropositionQuery
import com.embabel.dice.proposition.PropositionRepository
import com.embabel.dice.proposition.PropositionStatus
import com.embabel.dice.proposition.PropositionStoreType
-import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
-import com.fasterxml.jackson.module.kotlin.readValue
import org.slf4j.LoggerFactory
+import tools.jackson.module.kotlin.jacksonObjectMapper
+import tools.jackson.module.kotlin.readValue
import java.nio.file.Files
import java.nio.file.Path
import java.nio.file.StandardCopyOption
@@ -55,7 +55,7 @@ class JsonFilePropositionRepository @JvmOverloads constructor(
private val logger = LoggerFactory.getLogger(JsonFilePropositionRepository::class.java)
- private val mapper = jacksonObjectMapper().findAndRegisterModules()
+ private val mapper = jacksonObjectMapper()
private val propositions = ConcurrentHashMap()
private val embeddings = ConcurrentHashMap()
diff --git a/dice/src/main/kotlin/com/embabel/dice/web/rest/PropositionPipelineController.kt b/dice/src/main/kotlin/com/embabel/dice/web/rest/PropositionPipelineController.kt
index a129e153..8394ed76 100644
--- a/dice/src/main/kotlin/com/embabel/dice/web/rest/PropositionPipelineController.kt
+++ b/dice/src/main/kotlin/com/embabel/dice/web/rest/PropositionPipelineController.kt
@@ -33,15 +33,15 @@ import com.embabel.dice.pipeline.ChunkPropositionResult
import com.embabel.dice.pipeline.PropositionPipeline
import com.embabel.dice.proposition.PropositionRepository
import com.embabel.dice.proposition.revision.RevisionResult
-import com.fasterxml.jackson.databind.ObjectMapper
-import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
-import com.fasterxml.jackson.module.kotlin.readValue
import org.slf4j.LoggerFactory
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean
import org.springframework.http.MediaType
import org.springframework.http.ResponseEntity
import org.springframework.web.bind.annotation.*
import org.springframework.web.multipart.MultipartFile
+import tools.jackson.databind.ObjectMapper
+import tools.jackson.module.kotlin.jacksonObjectMapper
+import tools.jackson.module.kotlin.readValue
/**
* REST controller that runs the proposition extraction pipeline over text or uploaded files.
diff --git a/dice/src/test/kotlin/com/embabel/dice/common/GateDiceEventSerializationTest.kt b/dice/src/test/kotlin/com/embabel/dice/common/GateDiceEventSerializationTest.kt
index c8591200..a426c688 100644
--- a/dice/src/test/kotlin/com/embabel/dice/common/GateDiceEventSerializationTest.kt
+++ b/dice/src/test/kotlin/com/embabel/dice/common/GateDiceEventSerializationTest.kt
@@ -19,14 +19,13 @@ import com.embabel.agent.core.ContextId
import com.embabel.dice.proposition.EntityMention
import com.embabel.dice.proposition.MentionRole
import com.embabel.dice.proposition.Proposition
-import com.fasterxml.jackson.databind.DeserializationFeature
-import com.fasterxml.jackson.databind.ObjectMapper
-import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule
-import com.fasterxml.jackson.module.kotlin.registerKotlinModule
import org.junit.jupiter.api.Assertions.assertEquals
import org.junit.jupiter.api.Assertions.assertInstanceOf
import org.junit.jupiter.api.Assertions.assertTrue
import org.junit.jupiter.api.Test
+import tools.jackson.databind.DeserializationFeature
+import tools.jackson.databind.ObjectMapper
+import tools.jackson.module.kotlin.jacksonMapperBuilder
/**
* The gate-decision events are declared on a `@JsonTypeInfo(use = CLASS)` interface, which is the
@@ -40,10 +39,9 @@ class GateDiceEventSerializationTest {
// (the @JsonTypeInfo discriminator on the DiceEvent interface) without coupling to the
// nested Proposition type's own serialization shape, which carries a derived getter
// (contextIdValue) that has no matching constructor parameter.
- private val mapper: ObjectMapper = ObjectMapper()
- .registerKotlinModule()
- .registerModule(JavaTimeModule())
- .configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false)
+ private val mapper: ObjectMapper = jacksonMapperBuilder()
+ .disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES)
+ .build()
private fun proposition(): Proposition = Proposition(
contextId = ContextId("ctx"),
diff --git a/dice/src/test/kotlin/com/embabel/dice/proposition/PropositionJacksonRoundTripTest.kt b/dice/src/test/kotlin/com/embabel/dice/proposition/PropositionJacksonRoundTripTest.kt
index 08b56abf..d624cbd8 100644
--- a/dice/src/test/kotlin/com/embabel/dice/proposition/PropositionJacksonRoundTripTest.kt
+++ b/dice/src/test/kotlin/com/embabel/dice/proposition/PropositionJacksonRoundTripTest.kt
@@ -16,12 +16,9 @@
package com.embabel.dice.proposition
import com.embabel.agent.core.ContextId
-import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
import org.junit.jupiter.api.Assertions.assertEquals
import org.junit.jupiter.api.Test
-
-// A real consumer registers modules (incl. JSR-310 for the Instant fields) on its mapper;
-// findAndRegisterModules() picks up jackson-datatype-jsr310 from the classpath.
+import tools.jackson.module.kotlin.jacksonObjectMapper
/**
* Verifies that a [Proposition] round-trips cleanly through JSON. The class exposes computed
@@ -32,7 +29,7 @@ import org.junit.jupiter.api.Test
*/
class PropositionJacksonRoundTripTest {
- private val mapper = jacksonObjectMapper().findAndRegisterModules()
+ private val mapper = jacksonObjectMapper()
@Test
fun `a Proposition round-trips through JSON preserving its core fields`() {
diff --git a/dice/src/test/kotlin/com/embabel/dice/provenance/SourceLocatorTest.kt b/dice/src/test/kotlin/com/embabel/dice/provenance/SourceLocatorTest.kt
index 46253a08..8fdd8d38 100644
--- a/dice/src/test/kotlin/com/embabel/dice/provenance/SourceLocatorTest.kt
+++ b/dice/src/test/kotlin/com/embabel/dice/provenance/SourceLocatorTest.kt
@@ -15,13 +15,13 @@
*/
package com.embabel.dice.provenance
-import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
-import com.fasterxml.jackson.module.kotlin.readValue
import org.junit.jupiter.api.Assertions.assertEquals
import org.junit.jupiter.api.Assertions.assertNotEquals
import org.junit.jupiter.api.Assertions.assertThrows
import org.junit.jupiter.api.Assertions.assertTrue
import org.junit.jupiter.api.Test
+import tools.jackson.module.kotlin.jacksonObjectMapper
+import tools.jackson.module.kotlin.readValue
class SourceLocatorTest {
diff --git a/dice/src/test/kotlin/com/embabel/dice/support/EntitiesTest.kt b/dice/src/test/kotlin/com/embabel/dice/support/EntitiesTest.kt
index 5ef927af..f1e88553 100644
--- a/dice/src/test/kotlin/com/embabel/dice/support/EntitiesTest.kt
+++ b/dice/src/test/kotlin/com/embabel/dice/support/EntitiesTest.kt
@@ -16,7 +16,7 @@
package com.embabel.dice.support
import com.embabel.dice.text2graph.support.Entities
-import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
+import tools.jackson.module.kotlin.jacksonObjectMapper
import org.junit.jupiter.api.Test
class EntitiesTest {
diff --git a/dice/src/test/kotlin/com/embabel/dice/web/rest/DiscoveryControllerTest.kt b/dice/src/test/kotlin/com/embabel/dice/web/rest/DiscoveryControllerTest.kt
index b44ab35a..fad5deac 100644
--- a/dice/src/test/kotlin/com/embabel/dice/web/rest/DiscoveryControllerTest.kt
+++ b/dice/src/test/kotlin/com/embabel/dice/web/rest/DiscoveryControllerTest.kt
@@ -26,28 +26,27 @@ import com.embabel.dice.proposition.MentionRole
import com.embabel.dice.proposition.Proposition
import com.embabel.dice.proposition.PropositionRepository
import com.embabel.dice.proposition.store.InMemoryPropositionRepository
-import com.fasterxml.jackson.databind.ObjectMapper
-import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule
-import com.fasterxml.jackson.module.kotlin.KotlinModule
import org.junit.jupiter.api.Assertions.assertDoesNotThrow
import org.junit.jupiter.api.Assertions.assertFalse
import org.junit.jupiter.api.Assertions.assertTrue
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.Test
import org.springframework.context.annotation.AnnotationConfigApplicationContext
-import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter
+import org.springframework.http.MediaType
+import org.springframework.http.converter.json.JacksonJsonHttpMessageConverter
import org.springframework.test.web.servlet.MockMvc
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post
import org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath
import org.springframework.test.web.servlet.result.MockMvcResultMatchers.status
import org.springframework.test.web.servlet.setup.MockMvcBuilders
+import tools.jackson.databind.json.JsonMapper
+import tools.jackson.module.kotlin.kotlinModule
import java.time.Instant
import kotlin.reflect.KClass
import kotlin.reflect.KType
import kotlin.reflect.full.functions
import kotlin.reflect.jvm.javaMethod
-import org.springframework.http.MediaType
/**
* Opt-in and leak-free contract for the discovery REST surface, plus the cross-tier signature gate
@@ -82,16 +81,17 @@ class DiscoveryControllerTest {
@BeforeEach
fun setUp() {
repository = TestPropositionRepository()
- val objectMapper = ObjectMapper()
- .registerModule(KotlinModule.Builder().build())
- .registerModule(JavaTimeModule())
+ val objectMapper = JsonMapper.builder()
+ .addModule(kotlinModule())
+ .findAndAddModules()
+ .build()
val controller = DiscoveryController(
store = repository,
projectionRecordStore = emptyRecordStore,
collectorRunner = noopCollectorRunner,
)
mockMvc = MockMvcBuilders.standaloneSetup(controller)
- .setMessageConverters(MappingJackson2HttpMessageConverter(objectMapper))
+ .setMessageConverters(JacksonJsonHttpMessageConverter(objectMapper))
.build()
}
@@ -192,16 +192,17 @@ class DiscoveryControllerTest {
override fun delete(id: String): Boolean = false
override fun count(): Int = 0
}
- val objectMapper = ObjectMapper()
- .registerModule(KotlinModule.Builder().build())
- .registerModule(JavaTimeModule())
+ val objectMapper = JsonMapper.builder()
+ .addModule(kotlinModule())
+ .findAndAddModules()
+ .build()
val controller = DiscoveryController(
store = failingStore,
projectionRecordStore = emptyRecordStore,
collectorRunner = noopCollectorRunner,
)
val mvc = MockMvcBuilders.standaloneSetup(controller)
- .setMessageConverters(MappingJackson2HttpMessageConverter(objectMapper))
+ .setMessageConverters(JacksonJsonHttpMessageConverter(objectMapper))
.build()
mvc.perform(
diff --git a/dice/src/test/kotlin/com/embabel/dice/web/rest/MemoryControllerTest.kt b/dice/src/test/kotlin/com/embabel/dice/web/rest/MemoryControllerTest.kt
index f6f646b0..83957bc3 100644
--- a/dice/src/test/kotlin/com/embabel/dice/web/rest/MemoryControllerTest.kt
+++ b/dice/src/test/kotlin/com/embabel/dice/web/rest/MemoryControllerTest.kt
@@ -19,23 +19,19 @@ import com.embabel.agent.core.ContextId
import com.embabel.agent.rag.service.RetrievableIdentifier
import com.embabel.common.core.types.SimilarityResult
import com.embabel.common.core.types.TextSimilaritySearchRequest
-import com.embabel.dice.proposition.EntityMention
-import com.embabel.dice.proposition.MentionRole
-import com.embabel.dice.proposition.Proposition
-import com.embabel.dice.proposition.PropositionRepository
-import com.embabel.dice.proposition.PropositionStatus
-import com.fasterxml.jackson.databind.ObjectMapper
-import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule
-import com.fasterxml.jackson.module.kotlin.KotlinModule
+import com.embabel.dice.proposition.*
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.Nested
import org.junit.jupiter.api.Test
import org.springframework.http.MediaType
-import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter
+import org.springframework.http.converter.json.JacksonJsonHttpMessageConverter
import org.springframework.test.web.servlet.MockMvc
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*
-import org.springframework.test.web.servlet.result.MockMvcResultMatchers.*
+import org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath
+import org.springframework.test.web.servlet.result.MockMvcResultMatchers.status
import org.springframework.test.web.servlet.setup.MockMvcBuilders
+import tools.jackson.databind.json.JsonMapper
+import tools.jackson.module.kotlin.kotlinModule
import java.util.concurrent.ConcurrentHashMap
/**
@@ -89,22 +85,23 @@ class MemoryControllerTest {
private lateinit var mockMvc: MockMvc
private lateinit var propositionRepository: TestPropositionRepository
- private lateinit var objectMapper: ObjectMapper
+ private lateinit var objectMapper: JsonMapper
@BeforeEach
fun setUp() {
propositionRepository = TestPropositionRepository()
- objectMapper = ObjectMapper()
- .registerModule(KotlinModule.Builder().build())
- .registerModule(JavaTimeModule())
+ objectMapper = JsonMapper.builder()
+ .addModule(kotlinModule())
+ .findAndAddModules()
+ .build()
val controller = MemoryController(
propositionRepository = propositionRepository,
)
mockMvc = MockMvcBuilders.standaloneSetup(controller)
- .setMessageConverters(MappingJackson2HttpMessageConverter(objectMapper))
+ .setMessageConverters(JacksonJsonHttpMessageConverter(objectMapper))
.build()
}
diff --git a/dice/src/test/kotlin/com/embabel/dice/web/rest/PropositionPipelineControllerTest.kt b/dice/src/test/kotlin/com/embabel/dice/web/rest/PropositionPipelineControllerTest.kt
index 1df89616..1dcfa00e 100644
--- a/dice/src/test/kotlin/com/embabel/dice/web/rest/PropositionPipelineControllerTest.kt
+++ b/dice/src/test/kotlin/com/embabel/dice/web/rest/PropositionPipelineControllerTest.kt
@@ -17,32 +17,29 @@ package com.embabel.dice.web.rest
import com.embabel.agent.core.ContextId
import com.embabel.agent.core.DataDictionary
+import com.embabel.agent.rag.ingestion.ContentChunker
+import com.embabel.agent.rag.ingestion.HierarchicalContentReader
+import com.embabel.agent.rag.model.Chunk
+import com.embabel.agent.rag.model.NavigableDocument
import com.embabel.dice.common.EntityResolver
import com.embabel.dice.common.NewEntity
import com.embabel.dice.common.Resolutions
import com.embabel.dice.common.SuggestedEntity
import com.embabel.dice.common.resolver.AlwaysCreateEntityResolver
import com.embabel.dice.common.support.InMemorySchemaRegistry
-import com.embabel.agent.rag.ingestion.ContentChunker
-import com.embabel.agent.rag.ingestion.HierarchicalContentReader
-import com.embabel.agent.rag.model.Chunk
-import com.embabel.agent.rag.model.NavigableDocument
import com.embabel.dice.pipeline.ChunkPropositionResult
import com.embabel.dice.pipeline.PropositionPipeline
import com.embabel.dice.pipeline.PropositionResults
import com.embabel.dice.proposition.*
import com.embabel.dice.proposition.revision.RevisionResult
import com.fasterxml.jackson.annotation.JsonClassDescription
-import com.fasterxml.jackson.databind.ObjectMapper
-import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule
-import com.fasterxml.jackson.module.kotlin.KotlinModule
import io.mockk.every
import io.mockk.mockk
import io.mockk.verify
import org.junit.jupiter.api.BeforeEach
import org.junit.jupiter.api.Test
import org.springframework.http.MediaType
-import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter
+import org.springframework.http.converter.json.JacksonJsonHttpMessageConverter
import org.springframework.mock.web.MockMultipartFile
import org.springframework.test.web.servlet.MockMvc
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.multipart
@@ -50,6 +47,8 @@ import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post
import org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath
import org.springframework.test.web.servlet.result.MockMvcResultMatchers.status
import org.springframework.test.web.servlet.setup.MockMvcBuilders
+import tools.jackson.databind.json.JsonMapper
+import tools.jackson.module.kotlin.kotlinModule
/**
* Contract tests for the proposition extraction REST controller.
@@ -64,7 +63,7 @@ class PropositionPipelineControllerTest {
private lateinit var propositionPipeline: PropositionPipeline
private lateinit var entityResolver: EntityResolver
private lateinit var schemaRegistry: InMemorySchemaRegistry
- private lateinit var objectMapper: ObjectMapper
+ private lateinit var objectMapper: JsonMapper
@JsonClassDescription("A composer of music")
data class Composer(val id: String, val name: String)
@@ -80,9 +79,10 @@ class PropositionPipelineControllerTest {
val schema = DataDictionary.fromClasses("test", Composer::class.java, Work::class.java)
schemaRegistry = InMemorySchemaRegistry(schema)
- objectMapper = ObjectMapper()
- .registerModule(KotlinModule.Builder().build())
- .registerModule(JavaTimeModule())
+ objectMapper = JsonMapper.builder()
+ .addModule(kotlinModule())
+ .findAndAddModules()
+ .build()
val controller = PropositionPipelineController(
propositionPipeline = propositionPipeline,
@@ -92,7 +92,7 @@ class PropositionPipelineControllerTest {
)
mockMvc = MockMvcBuilders.standaloneSetup(controller)
- .setMessageConverters(MappingJackson2HttpMessageConverter(objectMapper))
+ .setMessageConverters(JacksonJsonHttpMessageConverter(objectMapper))
.build()
}
@@ -306,7 +306,7 @@ class PropositionPipelineControllerTest {
contentChunker = chunker,
)
val mvc = MockMvcBuilders.standaloneSetup(fileController)
- .setMessageConverters(MappingJackson2HttpMessageConverter(objectMapper))
+ .setMessageConverters(JacksonJsonHttpMessageConverter(objectMapper))
.build()
mvc.perform(