@@ -82,8 +82,7 @@ public final class Metamorph implements StreamPipe<StreamReceiver>, NamedValuePi
82
82
private static final InterceptorFactory NULL_INTERCEPTOR_FACTORY = new NullInterceptorFactory ();
83
83
private static final Map <String , String > NO_VARS = Collections .emptyMap ();
84
84
85
- private final Registry <NamedValueReceiver > dataRegistry =
86
- new WildcardRegistry <>();
85
+ private final Registry <NamedValueReceiver > dataRegistry = new WildcardRegistry <>();
87
86
private final List <NamedValueReceiver > elseSources = new ArrayList <>();
88
87
89
88
private final Map <String , Map <String , String >> maps = new HashMap <>();
@@ -100,7 +99,8 @@ public final class Metamorph implements StreamPipe<StreamReceiver>, NamedValuePi
100
99
private int recordCount ;
101
100
private final List <FlushListener > recordEndListener = new ArrayList <>();
102
101
private boolean elseNested ;
103
- final private Pattern literalPatternOfEntityMarker = Pattern .compile (flattener .getEntityMarker (), Pattern .LITERAL );
102
+ private boolean elseNestedEntityStarted ;
103
+ private String currentLiteralName ;
104
104
private static final Logger LOG = LoggerFactory .getLogger (Metamorph .class );
105
105
106
106
protected Metamorph () {
@@ -122,7 +122,6 @@ public Metamorph(final String morphDef, final InterceptorFactory interceptorFact
122
122
123
123
public Metamorph (final String morphDef , final Map <String , String > vars ,
124
124
final InterceptorFactory interceptorFactory ) {
125
-
126
125
this (getInputSource (morphDef ), vars , interceptorFactory );
127
126
}
128
127
@@ -140,7 +139,6 @@ public Metamorph(final Reader morphDef, final InterceptorFactory interceptorFact
140
139
141
140
public Metamorph (final Reader morphDef , final Map <String , String > vars ,
142
141
final InterceptorFactory interceptorFactory ) {
143
-
144
142
this (new InputSource (morphDef ), vars , interceptorFactory );
145
143
}
146
144
@@ -158,7 +156,6 @@ public Metamorph(final InputStream morphDef, final InterceptorFactory intercepto
158
156
159
157
public Metamorph (final InputStream morphDef , final Map <String , String > vars ,
160
158
final InterceptorFactory interceptorFactory ) {
161
-
162
159
this (new InputSource (morphDef ), vars , interceptorFactory );
163
160
}
164
161
@@ -205,7 +202,7 @@ private void init() {
205
202
flattener .setReceiver (new DefaultStreamReceiver () {
206
203
@ Override
207
204
public void literal (final String name , final String value ) {
208
- dispatch (name , value , getElseSources ());
205
+ dispatch (name , value , getElseSources (), false );
209
206
}
210
207
});
211
208
}
@@ -224,14 +221,16 @@ public void setErrorHandler(final MorphErrorHandler errorHandler) {
224
221
225
222
protected void registerNamedValueReceiver (final String source , final NamedValueReceiver data ) {
226
223
if (ELSE_NESTED_KEYWORD .equals (source )) {
227
- this . elseNested = true ;
224
+ elseNested = true ;
228
225
}
226
+
229
227
if (ELSE_KEYWORD .equals (source ) || ELSE_FLATTENED_KEYWORD .equals (source ) || elseNested ) {
230
- if (elseSources .isEmpty ())
228
+ if (elseSources .isEmpty ()) {
231
229
elseSources .add (data );
232
- else
233
- LOG .warn (
234
- "Only one of '_else', '_elseFlattened' and '_elseNested' is allowed. Ignoring the superflous ones." );
230
+ }
231
+ else {
232
+ LOG .warn ("Only one of '_else', '_elseFlattened' and '_elseNested' is allowed. Ignoring the superflous ones." );
233
+ }
235
234
} else {
236
235
dataRegistry .register (source , data );
237
236
}
@@ -253,12 +252,11 @@ public void startRecord(final String identifier) {
253
252
final String identifierFinal = identifier ;
254
253
255
254
outputStreamReceiver .startRecord (identifierFinal );
256
- dispatch (StandardEventNames .ID , identifierFinal , null );
255
+ dispatch (StandardEventNames .ID , identifierFinal , null , false );
257
256
}
258
257
259
258
@ Override
260
259
public void endRecord () {
261
-
262
260
for (final FlushListener listener : recordEndListener ){
263
261
listener .flush (recordCount , currentEntityCount );
264
262
}
@@ -287,17 +285,16 @@ public void startEntity(final String name) {
287
285
288
286
@ Override
289
287
public void endEntity () {
290
- dispatch (flattener .getCurrentPath (), "" , null );
288
+ dispatch (flattener .getCurrentPath (), "" , getElseSources (), true );
291
289
currentEntityCount = entityCountStack .pop ().intValue ();
292
290
flattener .endEntity ();
293
-
294
291
}
295
292
296
293
297
294
@ Override
298
295
public void literal (final String name , final String value ) {
296
+ currentLiteralName = name ;
299
297
flattener .literal (name , value );
300
-
301
298
}
302
299
303
300
@ Override
@@ -318,38 +315,51 @@ public void closeStream() {
318
315
outputStreamReceiver .closeStream ();
319
316
}
320
317
321
- protected void dispatch (final String path , final String value , final List <NamedValueReceiver > fallbackReceiver ) {
322
- List <NamedValueReceiver > matchingData = dataRegistry .get (path );
323
- boolean fallback = false ;
324
- if (matchingData == null || matchingData .isEmpty ()) {
325
- fallback = true ;
326
- matchingData = fallbackReceiver ;
318
+ private void dispatch (final String path , final String value , final List <NamedValueReceiver > fallbackReceiver , final boolean endEntity ) {
319
+ final List <NamedValueReceiver > matchingData = getData (path );
320
+
321
+ if (matchingData != null ) {
322
+ send (path , value , matchingData );
327
323
}
328
- if (null != matchingData ) {
329
- send (path , value , matchingData , fallback );
324
+ else if (fallbackReceiver != null ) {
325
+ if (endEntity ) {
326
+ if (elseNestedEntityStarted ) {
327
+ outputStreamReceiver .endEntity ();
328
+ elseNestedEntityStarted = false ;
329
+ }
330
+ }
331
+ else {
332
+ final String entityName = elseNested ? flattener .getCurrentEntityName () : null ;
333
+
334
+ if (entityName != null ) {
335
+ if (getData (entityName ) == null ) {
336
+ if (!elseNestedEntityStarted ) {
337
+ outputStreamReceiver .startEntity (entityName );
338
+ elseNestedEntityStarted = true ;
339
+ }
340
+
341
+ send (currentLiteralName , value , fallbackReceiver );
342
+ }
343
+ }
344
+ else {
345
+ send (path , value , fallbackReceiver );
346
+ }
347
+ }
330
348
}
331
349
}
332
350
333
- private void send (final String path , final String value , final List <NamedValueReceiver > dataList ,
334
- final boolean fallback ) {
351
+ private List <NamedValueReceiver > getData (final String path ) {
352
+ final List <NamedValueReceiver > matchingData = dataRegistry .get (path );
353
+ return matchingData != null && !matchingData .isEmpty () ? matchingData : null ;
354
+ }
355
+
356
+ private void send (final String path , final String value , final List <NamedValueReceiver > dataList ) {
335
357
for (final NamedValueReceiver data : dataList ) {
336
- String key = path ;
337
- if (fallback && elseNested ) {
338
- if (flattener .getCurrentEntityName () != null ) {
339
- outputStreamReceiver .startEntity (flattener .getCurrentEntityName ());
340
- key = literalPatternOfEntityMarker .split (path )[1 ];
341
- }
342
- }
343
358
try {
344
- data .receive (key , value , null , recordCount , currentEntityCount );
359
+ data .receive (path , value , null , recordCount , currentEntityCount );
345
360
} catch (final RuntimeException e ) {
346
361
errorHandler .error (e );
347
362
}
348
- if (fallback && elseNested ) {
349
- if (flattener .getCurrentEntityName () != null ) {
350
- outputStreamReceiver .endEntity ();
351
- }
352
- }
353
363
}
354
364
}
355
365
@@ -379,7 +389,7 @@ public void receive(final String name, final String value, final NamedValueSourc
379
389
}
380
390
381
391
if (name .length () != 0 && name .charAt (0 ) == FEEDBACK_CHAR ) {
382
- dispatch (name , value , null );
392
+ dispatch (name , value , null , false );
383
393
return ;
384
394
}
385
395
0 commit comments