Skip to content

Commit 4d088de

Browse files
committed
Commit to undo the changes I've made since forked the original project. The reason is that I've made a mistake and created a unique PR to solve several issues, which is a bad practice.
1 parent a3937b2 commit 4d088de

File tree

5 files changed

+55
-371
lines changed

5 files changed

+55
-371
lines changed

src/main/java/org/codehaus/plexus/interpolation/multi/MultiDelimiterStringSearchInterpolator.java

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -201,16 +201,13 @@ private String interpolate( String input, RecursionInterceptor recursionIntercep
201201

202202
if ( startIdx >= 0 && escapeString != null && escapeString.length() > 0 )
203203
{
204-
int startEscapeIdx = (startIdx == 0) ? 0 : startIdx - escapeString.length();
204+
int startEscapeIdx = startIdx == 0 ? 0 : startIdx - escapeString.length();
205205
if ( startEscapeIdx >= 0 )
206206
{
207207
String escape = input.substring( startEscapeIdx, startIdx );
208208
if ( escape != null && escapeString.equals( escape ) )
209209
{
210210
result.append( wholeExpr );
211-
if (startEscapeIdx > 0) {
212-
--startEscapeIdx;
213-
}
214211
result.replace( startEscapeIdx, startEscapeIdx + escapeString.length(), "" );
215212
continue;
216213
}
Lines changed: 38 additions & 266 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,5 @@
11
package org.codehaus.plexus.interpolation.reflection;
22

3-
import java.lang.ref.WeakReference;
4-
import java.lang.reflect.Array;
5-
import java.lang.reflect.InvocationTargetException;
6-
import java.lang.reflect.Method;
7-
import java.util.List;
8-
import java.util.Map;
9-
import java.util.WeakHashMap;
10-
113
/*
124
* Copyright 2001-2006 Codehaus Foundation.
135
*
@@ -26,6 +18,13 @@
2618

2719
import org.codehaus.plexus.interpolation.util.StringUtils;
2820

21+
import java.lang.ref.SoftReference;
22+
import java.lang.ref.WeakReference;
23+
import java.lang.reflect.Method;
24+
import java.util.Map;
25+
import java.util.StringTokenizer;
26+
import java.util.WeakHashMap;
27+
2928
/**
3029
* <b>NOTE:</b> This class was copied from plexus-utils, to allow this library
3130
* to stand completely self-contained.
@@ -44,317 +43,90 @@ public class ReflectionValueExtractor
4443
private static final Object[] OBJECT_ARGS = new Object[0];
4544

4645
/**
47-
* Use a WeakHashMap here, so the keys (Class objects) can be garbage collected. This approach prevents permgen
48-
* space overflows due to retention of discarded classloaders.
46+
* Use a WeakHashMap here, so the keys (Class objects) can be garbage collected.
47+
* This approach prevents permgen space overflows due to retention of discarded
48+
* classloaders.
4949
*/
50-
private static final Map<Class<?>, WeakReference<ClassMap>> classMaps =
51-
new WeakHashMap<Class<?>, WeakReference<ClassMap>>();
52-
53-
static final int EOF = -1;
54-
55-
static final char PROPERTY_START = '.';
56-
57-
static final char INDEXED_START = '[';
58-
59-
static final char INDEXED_END = ']';
60-
61-
static final char MAPPED_START = '(';
62-
63-
static final char MAPPED_END = ')';
64-
65-
static class Tokenizer
66-
{
67-
final String expression;
68-
69-
int idx;
70-
71-
public Tokenizer( String expression )
72-
{
73-
this.expression = expression;
74-
}
75-
76-
public int peekChar()
77-
{
78-
return idx < expression.length() ? expression.charAt( idx ) : EOF;
79-
}
80-
81-
public int skipChar()
82-
{
83-
return idx < expression.length() ? expression.charAt( idx++ ) : EOF;
84-
}
85-
86-
public String nextToken( char delimiter )
87-
{
88-
int start = idx;
89-
90-
while ( idx < expression.length() && delimiter != expression.charAt( idx ) )
91-
{
92-
idx++;
93-
}
94-
95-
// delimiter MUST be present
96-
if ( idx <= start || idx >= expression.length() )
97-
{
98-
return null;
99-
}
100-
101-
return expression.substring( start, idx++ );
102-
}
103-
104-
public String nextPropertyName()
105-
{
106-
final int start = idx;
107-
108-
while ( idx < expression.length() && Character.isJavaIdentifierPart( expression.charAt( idx ) ) )
109-
{
110-
idx++;
111-
}
112-
113-
// property name does not require delimiter
114-
if ( idx <= start || idx > expression.length() )
115-
{
116-
return null;
117-
}
118-
119-
return expression.substring( start, idx );
120-
}
121-
122-
public int getPosition()
123-
{
124-
return idx < expression.length() ? idx : EOF;
125-
}
126-
127-
// to make tokenizer look pretty in debugger
128-
@Override
129-
public String toString()
130-
{
131-
return idx < expression.length() ? expression.substring( idx ) : "<EOF>";
132-
}
133-
}
50+
private static final Map<Class<?>, WeakReference<ClassMap>> classMaps = new WeakHashMap<Class<?>, WeakReference<ClassMap>>();
13451

13552
private ReflectionValueExtractor()
13653
{
13754
}
13855

139-
/**
140-
* <p>
141-
* The implementation supports indexed, nested and mapped properties.
142-
* </p>
143-
* <ul>
144-
* <li>nested properties should be defined by a dot, i.e. "user.address.street"</li>
145-
* <li>indexed properties (java.util.List or array instance) should be contains <code>(\\w+)\\[(\\d+)\\]</code>
146-
* pattern, i.e. "user.addresses[1].street"</li>
147-
* <li>mapped properties should be contains <code>(\\w+)\\((.+)\\)</code> pattern, i.e.
148-
* "user.addresses(myAddress).street"</li>
149-
* <ul>
150-
*
151-
* @param expression not null expression
152-
* @param root not null object
153-
* @return the object defined by the expression
154-
* @throws Exception if any
155-
*/
15656
public static Object evaluate( String expression, Object root )
15757
throws Exception
15858
{
15959
return evaluate( expression, root, true );
16060
}
16161

162-
/**
163-
* <p>
164-
* The implementation supports indexed, nested and mapped properties.
165-
* </p>
166-
* <ul>
167-
* <li>nested properties should be defined by a dot, i.e. "user.address.street"</li>
168-
* <li>indexed properties (java.util.List or array instance) should be contains <code>(\\w+)\\[(\\d+)\\]</code>
169-
* pattern, i.e. "user.addresses[1].street"</li>
170-
* <li>mapped properties should be contains <code>(\\w+)\\((.+)\\)</code> pattern, i.e.
171-
* "user.addresses(myAddress).street"</li>
172-
* <ul>
173-
*
174-
* @param expression not null expression
175-
* @param root not null object
176-
* @return the object defined by the expression
177-
* @throws Exception if any
178-
*/
17962
// TODO: don't throw Exception
180-
public static Object evaluate( String expression, final Object root, final boolean trimRootToken )
63+
public static Object evaluate( String expression, Object root, boolean trimRootToken )
18164
throws Exception
18265
{
66+
// if the root token refers to the supplied root object parameter, remove it.
67+
if ( trimRootToken )
68+
{
69+
expression = expression.substring( expression.indexOf( '.' ) + 1 );
70+
}
71+
18372
Object value = root;
18473

18574
// ----------------------------------------------------------------------
18675
// Walk the dots and retrieve the ultimate value desired from the
18776
// MavenProject instance.
18877
// ----------------------------------------------------------------------
18978

190-
if ( expression == null || "".equals(expression.trim()) || !Character.isJavaIdentifierStart( expression.charAt( 0 ) ) )
191-
{
192-
return null;
193-
}
79+
StringTokenizer parser = new StringTokenizer( expression, "." );
19480

195-
boolean hasDots = expression.indexOf( PROPERTY_START ) >= 0;
196-
197-
final Tokenizer tokenizer;
198-
if ( trimRootToken && hasDots )
81+
while ( parser.hasMoreTokens() )
19982
{
200-
tokenizer = new Tokenizer( expression );
201-
tokenizer.nextPropertyName();
202-
if ( tokenizer.getPosition() == EOF )
203-
{
204-
return null;
205-
}
206-
}
207-
else
208-
{
209-
tokenizer = new Tokenizer( "." + expression );
210-
}
83+
String token = parser.nextToken();
21184

212-
int propertyPosition = tokenizer.getPosition();
213-
while ( value != null && tokenizer.peekChar() != EOF )
214-
{
215-
switch ( tokenizer.skipChar() )
85+
if ( value == null )
21686
{
217-
case INDEXED_START:
218-
value =
219-
getIndexedValue( expression, propertyPosition, tokenizer.getPosition(), value,
220-
tokenizer.nextToken( INDEXED_END ) );
221-
break;
222-
case MAPPED_START:
223-
value =
224-
getMappedValue( expression, propertyPosition, tokenizer.getPosition(), value,
225-
tokenizer.nextToken( MAPPED_END ) );
226-
break;
227-
case PROPERTY_START:
228-
propertyPosition = tokenizer.getPosition();
229-
value = getPropertyValue( value, tokenizer.nextPropertyName() );
230-
break;
231-
default:
232-
// could not parse expression
233-
return null;
87+
return null;
23488
}
235-
}
236-
237-
return value;
238-
}
23989

240-
private static Object getMappedValue( final String expression, final int from, final int to, final Object value,
241-
final String key )
242-
throws Exception
243-
{
244-
if ( value == null || key == null )
245-
{
246-
return null;
247-
}
248-
249-
if ( value instanceof Map )
250-
{
251-
Object[] localParams = new Object[] { key };
25290
ClassMap classMap = getClassMap( value.getClass() );
253-
Method method = classMap.findMethod( "get", localParams );
254-
return method.invoke( value, localParams );
255-
}
25691

257-
final String message =
258-
String.format( "The token '%s' at position '%d' refers to a java.util.Map, but the value seems is an instance of '%s'",
259-
expression.subSequence( from, to ), from, value.getClass() );
92+
String methodBase = StringUtils.capitalizeFirstLetter( token );
26093

261-
throw new Exception( message );
262-
}
94+
String methodName = "get" + methodBase;
26395

264-
private static Object getIndexedValue( final String expression, final int from, final int to, final Object value,
265-
final String indexStr )
266-
throws Exception
267-
{
268-
try
269-
{
270-
int index = Integer.parseInt( indexStr );
96+
Method method = classMap.findMethod( methodName, CLASS_ARGS );
27197

272-
if ( value.getClass().isArray() )
98+
if ( method == null )
27399
{
274-
return Array.get( value, index );
275-
}
100+
// perhaps this is a boolean property??
101+
methodName = "is" + methodBase;
276102

277-
if ( value instanceof List )
278-
{
279-
ClassMap classMap = getClassMap( value.getClass() );
280-
// use get method on List interface
281-
Object[] localParams = new Object[] { index };
282-
Method method = classMap.findMethod( "get", localParams );
283-
return method.invoke( value, localParams );
103+
method = classMap.findMethod( methodName, CLASS_ARGS );
284104
}
285-
}
286-
catch ( NumberFormatException e )
287-
{
288-
return null;
289-
}
290-
catch ( InvocationTargetException e )
291-
{
292-
// catch array index issues gracefully, otherwise release
293-
if ( e.getCause() instanceof IndexOutOfBoundsException )
105+
106+
if ( method == null )
294107
{
295108
return null;
296109
}
297110

298-
throw e;
299-
}
300-
301-
final String message =
302-
String.format( "The token '%s' at position '%d' refers to a java.util.List or an array, but the value seems is an instance of '%s'",
303-
expression.subSequence( from, to ), from, value.getClass() );
304-
305-
throw new Exception( message );
306-
}
307-
308-
private static Object getPropertyValue( Object value, String property )
309-
throws Exception
310-
{
311-
if ( value == null || property == null )
312-
{
313-
return null;
111+
value = method.invoke( value, OBJECT_ARGS );
314112
}
315113

316-
ClassMap classMap = getClassMap( value.getClass() );
317-
String methodBase = StringUtils.capitalizeFirstLetter( property );
318-
String methodName = "get" + methodBase;
319-
Method method = classMap.findMethod( methodName, CLASS_ARGS );
320-
321-
if ( method == null )
322-
{
323-
// perhaps this is a boolean property??
324-
methodName = "is" + methodBase;
325-
326-
method = classMap.findMethod( methodName, CLASS_ARGS );
327-
}
328-
329-
if ( method == null )
330-
{
331-
return null;
332-
}
333-
334-
try
335-
{
336-
return method.invoke( value, OBJECT_ARGS );
337-
}
338-
catch ( InvocationTargetException e )
339-
{
340-
throw e;
341-
}
114+
return value;
342115
}
343116

344117
private static ClassMap getClassMap( Class<?> clazz )
345118
{
346-
347-
WeakReference<ClassMap> softRef = classMaps.get( clazz );
119+
WeakReference<ClassMap> ref = classMaps.get( clazz);
348120

349121
ClassMap classMap;
350122

351-
if ( softRef == null || ( classMap = softRef.get() ) == null )
123+
if ( ref == null || (classMap = ref.get()) == null )
352124
{
353125
classMap = new ClassMap( clazz );
354126

355-
classMaps.put( clazz, new WeakReference<ClassMap>( classMap ) );
127+
classMaps.put( clazz, new WeakReference<ClassMap>(classMap) );
356128
}
357129

358130
return classMap;
359131
}
360-
}
132+
}

0 commit comments

Comments
 (0)