1
1
package com .fasterxml .jackson .dataformat .csv ;
2
2
3
3
import java .util .Collection ;
4
+ import java .util .Objects ;
4
5
5
6
import com .fasterxml .jackson .core .type .TypeReference ;
6
7
import com .fasterxml .jackson .databind .*;
@@ -86,17 +87,62 @@ public Builder configure(CsvGenerator.Feature f, boolean state)
86
87
}
87
88
}
88
89
90
+
91
+ /**
92
+ * Simple class in order to create a map key based on {@link JavaType} and a given view.
93
+ * Used for caching associated schemas in {@code _untypedSchemas} and {@code _typedSchemas}.
94
+ */
95
+ public static final class ViewKey
96
+ implements java .io .Serializable
97
+ {
98
+ private static final long serialVersionUID = 1L ;
99
+
100
+ private final JavaType _pojoType ;
101
+ private final Class <?> _view ;
102
+ private final int _hashCode ;
103
+
104
+
105
+ public ViewKey (final JavaType pojoType , final Class <?> view )
106
+ {
107
+ _pojoType = pojoType ;
108
+ _view = view ;
109
+ _hashCode = Objects .hash (pojoType , view );
110
+ }
111
+
112
+
113
+ @ Override
114
+ public int hashCode () { return _hashCode ; }
115
+
116
+ @ Override
117
+ public boolean equals (final Object o )
118
+ {
119
+ if (o == this ) { return true ; }
120
+ if (o == null || o .getClass () != getClass ()) { return false ; }
121
+ final ViewKey other = (ViewKey ) o ;
122
+ if (_hashCode != other ._hashCode || _view != other ._view ) { return false ; }
123
+ return Objects .equals (_pojoType , other ._pojoType );
124
+ }
125
+
126
+ @ Override
127
+ public String toString ()
128
+ {
129
+ String viewName = _view != null ? _view .getName () : null ;
130
+ return "[ViewKey: pojoType=" + _pojoType + ", view=" + viewName + "]" ;
131
+ }
132
+ }
133
+
134
+
89
135
/**
90
136
* Simple caching for schema instances, given that they are relatively expensive
91
137
* to construct; this one is for "loose" (non-typed) schemas
92
138
*/
93
- protected final LRUMap <JavaType ,CsvSchema > _untypedSchemas ;
139
+ protected final LRUMap <ViewKey ,CsvSchema > _untypedSchemas ;
94
140
95
141
/**
96
142
* Simple caching for schema instances, given that they are relatively expensive
97
143
* to construct; this one is for typed schemas
98
144
*/
99
- protected final LRUMap <JavaType ,CsvSchema > _typedSchemas ;
145
+ protected final LRUMap <ViewKey ,CsvSchema > _typedSchemas ;
100
146
101
147
/*
102
148
/**********************************************************************
@@ -114,8 +160,8 @@ public CsvMapper(CsvFactory f)
114
160
super (f );
115
161
// As per #11: default to alphabetic ordering
116
162
enable (MapperFeature .SORT_PROPERTIES_ALPHABETICALLY );
117
- _untypedSchemas = new LRUMap <JavaType ,CsvSchema >(8 ,32 );
118
- _typedSchemas = new LRUMap <JavaType ,CsvSchema >(8 ,32 );
163
+ _untypedSchemas = new LRUMap <ViewKey ,CsvSchema >(8 ,32 );
164
+ _typedSchemas = new LRUMap <ViewKey ,CsvSchema >(8 ,32 );
119
165
}
120
166
121
167
/**
@@ -128,8 +174,8 @@ public CsvMapper(CsvFactory f)
128
174
protected CsvMapper (CsvMapper src )
129
175
{
130
176
super (src );
131
- _untypedSchemas = new LRUMap <JavaType ,CsvSchema >(8 ,32 );
132
- _typedSchemas = new LRUMap <JavaType ,CsvSchema >(8 ,32 );
177
+ _untypedSchemas = new LRUMap <ViewKey ,CsvSchema >(8 ,32 );
178
+ _typedSchemas = new LRUMap <ViewKey ,CsvSchema >(8 ,32 );
133
179
}
134
180
135
181
/**
@@ -422,34 +468,28 @@ public final CsvSchema typedSchemaForWithView(TypeReference<?> pojoTypeRef, Clas
422
468
/**********************************************************************
423
469
*/
424
470
425
- protected CsvSchema _schemaFor (JavaType pojoType , LRUMap <JavaType ,CsvSchema > schemas ,
471
+ protected CsvSchema _schemaFor (JavaType pojoType , LRUMap <ViewKey ,CsvSchema > schemas ,
426
472
boolean typed , Class <?> view )
427
473
{
428
- // 15-Dec-2021, tatu: [dataformats-text#288] Only cache if we don't have
429
- // a view, to avoid conflicts. For now. May be improved by changing cache
430
- // key if that is considered a performance problem.
431
- if (view == null ) {
432
- synchronized (schemas ) {
433
- CsvSchema s = schemas .get (pojoType );
434
- if (s != null ) {
435
- return s ;
436
- }
474
+ final ViewKey viewKey = new ViewKey (pojoType , view );
475
+ synchronized (schemas ) {
476
+ CsvSchema s = schemas .get (viewKey );
477
+ if (s != null ) {
478
+ return s ;
437
479
}
438
480
}
439
481
final AnnotationIntrospector intr = _deserializationConfig .getAnnotationIntrospector ();
440
482
CsvSchema .Builder builder = CsvSchema .builder ();
441
483
_addSchemaProperties (builder , intr , typed , pojoType , null , view );
442
484
CsvSchema result = builder .build ();
443
- if (view == null ) { // only cache without view (see above)
444
- synchronized (schemas ) {
445
- schemas .put (pojoType , result );
446
- }
485
+ synchronized (schemas ) {
486
+ schemas .put (viewKey , result );
447
487
}
448
488
return result ;
449
489
}
450
490
451
491
@ Deprecated // since 2.11 (remove from 3.0 at latest)
452
- protected CsvSchema _schemaFor (JavaType pojoType , LRUMap <JavaType ,CsvSchema > schemas , boolean typed ) {
492
+ protected CsvSchema _schemaFor (JavaType pojoType , LRUMap <ViewKey ,CsvSchema > schemas , boolean typed ) {
453
493
return _schemaFor (pojoType , schemas , typed , null );
454
494
}
455
495
0 commit comments