2727import org .apache .commons .logging .Log ;
2828import org .apache .commons .logging .LogFactory ;
2929import org .springframework .context .ApplicationContextAware ;
30- import org .springframework .core .convert .ConverterNotFoundException ;
3130import org .springframework .core .convert .converter .Converter ;
32- import org .springframework .core .convert .converter .ConverterRegistry ;
3331import org .springframework .data .convert .CustomConversions ;
3432import org .springframework .data .jdbc .core .mapping .AggregateReference ;
3533import org .springframework .data .jdbc .core .mapping .JdbcValue ;
@@ -80,7 +78,7 @@ public class MappingJdbcConverter extends MappingRelationalConverter implements
8078 * {@link #MappingJdbcConverter(RelationalMappingContext, RelationResolver, CustomConversions, JdbcTypeFactory)}
8179 * (MappingContext, RelationResolver, JdbcTypeFactory)} to convert arrays and large objects into JDBC-specific types.
8280 *
83- * @param context must not be {@literal null}.
81+ * @param context must not be {@literal null}.
8482 * @param relationResolver used to fetch additional relations from the database. Must not be {@literal null}.
8583 */
8684 public MappingJdbcConverter (RelationalMappingContext context , RelationResolver relationResolver ) {
@@ -91,19 +89,17 @@ public MappingJdbcConverter(RelationalMappingContext context, RelationResolver r
9189
9290 this .typeFactory = JdbcTypeFactory .unsupported ();
9391 this .relationResolver = relationResolver ;
94-
95- registerAggregateReferenceConverters ();
9692 }
9793
9894 /**
9995 * Creates a new {@link MappingJdbcConverter} given {@link MappingContext}.
10096 *
101- * @param context must not be {@literal null}.
97+ * @param context must not be {@literal null}.
10298 * @param relationResolver used to fetch additional relations from the database. Must not be {@literal null}.
103- * @param typeFactory must not be {@literal null}
99+ * @param typeFactory must not be {@literal null}
104100 */
105101 public MappingJdbcConverter (RelationalMappingContext context , RelationResolver relationResolver ,
106- CustomConversions conversions , JdbcTypeFactory typeFactory ) {
102+ CustomConversions conversions , JdbcTypeFactory typeFactory ) {
107103
108104 super (context , conversions );
109105
@@ -112,14 +108,6 @@ public MappingJdbcConverter(RelationalMappingContext context, RelationResolver r
112108
113109 this .typeFactory = typeFactory ;
114110 this .relationResolver = relationResolver ;
115-
116- registerAggregateReferenceConverters ();
117- }
118-
119- private void registerAggregateReferenceConverters () {
120-
121- ConverterRegistry registry = (ConverterRegistry ) getConversionService ();
122- AggregateReferenceConverters .getConvertersToRegister (getConversionService ()).forEach (registry ::addConverter );
123111 }
124112
125113 @ Nullable
@@ -185,33 +173,48 @@ private Class<?> doGetColumnType(RelationalPersistentProperty property) {
185173 }
186174
187175 @ Override
188- @ Nullable
189- public Object readValue (@ Nullable Object value , TypeInformation <?> type ) {
190-
191- if (value == null ) {
192- return value ;
193- }
176+ protected Object readTechnologyType (Object value ) {
194177
195178 if (value instanceof Array array ) {
196179 try {
197- return super . readValue ( array .getArray (), type );
198- } catch (SQLException | ConverterNotFoundException e ) {
180+ return array .getArray ();
181+ } catch (SQLException e ) {
199182 LOG .info ("Failed to extract a value of type %s from an Array; Attempting to use standard conversions" , e );
183+
200184 }
201185 }
202186
203- return super .readValue (value , type );
187+ return value ;
188+ }
189+
190+ @ Override
191+ protected TypeInformation <?> determineModuleReadTarget (TypeInformation <?> ultimateTargetType ) {
192+
193+ if (AggregateReference .class .isAssignableFrom (ultimateTargetType .getType ())) {
194+ // the id type of a AggregateReference
195+ return ultimateTargetType .getTypeArguments ().get (1 );
196+ }
197+ return ultimateTargetType ;
204198 }
205199
206200 @ Override
201+ protected Object readModuleType (Object value , TypeInformation <?> targetType ) {
202+
203+ if (AggregateReference .class .isAssignableFrom (targetType .getType ())) {
204+ return AggregateReference .to (value );
205+ }
206+ return value ;
207+ }
208+
207209 @ Nullable
208- public Object writeValue (@ Nullable Object value , TypeInformation <?> type ) {
210+ @ Override
211+ protected Object getPotentiallyConvertedSimpleWrite (Object value , TypeInformation <?> type ) {
209212
210- if (value == null ) {
211- return null ;
213+ if (value instanceof AggregateReference <?, ?> aggregateReference ) {
214+ return writeValue ( aggregateReference . getId (), type ) ;
212215 }
213216
214- return super .writeValue (value , type );
217+ return super .getPotentiallyConvertedSimpleWrite (value , type );
215218 }
216219
217220 private boolean canWriteAsJdbcValue (@ Nullable Object value ) {
@@ -285,7 +288,7 @@ public <R> R readAndResolve(TypeInformation<R> type, RowDocument source, Identif
285288
286289 @ Override
287290 protected RelationalPropertyValueProvider newValueProvider (RowDocumentAccessor documentAccessor ,
288- ValueExpressionEvaluator evaluator , ConversionContext context ) {
291+ ValueExpressionEvaluator evaluator , ConversionContext context ) {
289292
290293 if (context instanceof ResolvingConversionContext rcc ) {
291294
@@ -314,7 +317,7 @@ class ResolvingRelationalPropertyValueProvider implements RelationalPropertyValu
314317 private final Identifier identifier ;
315318
316319 private ResolvingRelationalPropertyValueProvider (AggregatePathValueProvider delegate , RowDocumentAccessor accessor ,
317- ResolvingConversionContext context , Identifier identifier ) {
320+ ResolvingConversionContext context , Identifier identifier ) {
318321
319322 AggregatePath path = context .aggregatePath ();
320323
@@ -323,15 +326,15 @@ private ResolvingRelationalPropertyValueProvider(AggregatePathValueProvider dele
323326 this .context = context ;
324327 this .identifier = path .isEntity ()
325328 ? potentiallyAppendIdentifier (identifier , path .getRequiredLeafEntity (),
326- property -> delegate .getValue (path .append (property )))
329+ property -> delegate .getValue (path .append (property )))
327330 : identifier ;
328331 }
329332
330333 /**
331334 * Conditionally append the identifier if the entity has an identifier property.
332335 */
333336 static Identifier potentiallyAppendIdentifier (Identifier base , RelationalPersistentEntity <?> entity ,
334- Function <RelationalPersistentProperty , Object > getter ) {
337+ Function <RelationalPersistentProperty , Object > getter ) {
335338
336339 if (entity .hasIdProperty ()) {
337340
@@ -460,7 +463,7 @@ public RelationalPropertyValueProvider withContext(ConversionContext context) {
460463
461464 return context == this .context ? this
462465 : new ResolvingRelationalPropertyValueProvider (delegate .withContext (context ), accessor ,
463- (ResolvingConversionContext ) context , identifier );
466+ (ResolvingConversionContext ) context , identifier );
464467 }
465468 }
466469
@@ -472,7 +475,7 @@ public RelationalPropertyValueProvider withContext(ConversionContext context) {
472475 * @param identifier
473476 */
474477 private record ResolvingConversionContext (ConversionContext delegate , AggregatePath aggregatePath ,
475- Identifier identifier ) implements ConversionContext {
478+ Identifier identifier ) implements ConversionContext {
476479
477480 @ Override
478481 public <S > S convert (Object source , TypeInformation <? extends S > typeHint ) {
0 commit comments