升级至Micronaut 4后consumes和produces功能失效求助
解决Micronaut 4自定义媒体类型编解码异常问题
Micronaut 4 调整了HTTP编解码器的注册逻辑,默认不会将自定义媒体类型(如application/some.v1+json)关联到内置JSON编解码器,导致接口调用时抛出io.micronaut.http.codec.CodecException: Cannot encode value [[]]. No possible encoders found for media type: application/vnd.v1+json异常。
以下两种方案可解决问题,其中方案二能实现通用处理所有自定义+json类媒体类型:
方案一:配置绑定自定义媒体类型到JSON编解码器
无需编写代码,直接在配置文件中指定所有带+json后缀的自定义媒体类型使用JSON编解码器:
application.yml配置示例:
micronaut: codec: json: additional-types: - application/*+json
该配置会匹配所有application/xxx+json格式的自定义媒体类型,自动关联到内置JSON编解码器。
方案二:编写通用自定义编解码器
若需更灵活的控制逻辑,可实现一个通用编解码器,委托内置JSON编解码器处理所有自定义+json媒体类型:
1. 实现编解码器类
创建Kotlin类,继承AbstractMediaTypeCodec并委托给默认JSON编解码器:
import io.micronaut.context.annotation.Requires import io.micronaut.http.MediaType import io.micronaut.http.codec.* import jakarta.inject.Singleton import java.io.InputStream import java.io.OutputStream @Singleton @Requires(classes = [MediaTypeCodec::class]) class GenericJsonCustomMediaTypeCodec( private val jsonCodec: MediaTypeCodec ) : AbstractMediaTypeCodec() { // 匹配所有带+json后缀的自定义媒体类型 override fun getSupportedMediaTypes(): MutableList<MediaType> { return MediaType.of("application/*+json").expand() } override fun getMediaType(): MediaType { return MediaType.APPLICATION_JSON_TYPE } override fun encode(`object`: Any, outputStream: OutputStream, context: CodecContext) { jsonCodec.encode(`object`, outputStream, context) } override fun <T : Any> decode(type: Class<T>, inputStream: InputStream, context: CodecContext): T { return jsonCodec.decode(type, inputStream, context) } override fun <T : Any> decode(type: Argument<T>, inputStream: InputStream, context: CodecContext): T { return jsonCodec.decode(type, inputStream, context) } }
2. 自动注册
通过@Singleton注解,Micronaut会自动识别并注册该编解码器,无需额外配置。它会接管所有application/xxx+json格式的媒体类型,复用内置JSON编解码器的序列化/反序列化逻辑。
验证
修改完成后重启服务,调用指定自定义媒体类型的接口,即可正常完成编解码操作,不再抛出异常。
内容的提问来源于stack exchange,提问作者João Cota
相关产品推荐
相关产品推荐

