Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
爱吃血肠
spring-framework
提交
9a8bb5f7
S
spring-framework
项目概览
爱吃血肠
/
spring-framework
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
S
spring-framework
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
9a8bb5f7
编写于
4月 09, 2009
作者:
A
Andy Clement
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
More tests and some fixes. Also created tests based on the documentation examples.
上级
9ce71f67
变更
31
显示空白变更内容
内联
并排
Showing
31 changed file
with
736 addition
and
163 deletion
+736
-163
org.springframework.expression/src/main/java/org/springframework/expression/EvaluationContext.java
...ava/org/springframework/expression/EvaluationContext.java
+7
-0
org.springframework.expression/src/main/java/org/springframework/expression/spel/ExpressionState.java
.../org/springframework/expression/spel/ExpressionState.java
+1
-7
org.springframework.expression/src/main/java/org/springframework/expression/spel/SpelMessages.java
...ava/org/springframework/expression/spel/SpelMessages.java
+4
-4
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/ConstructorReference.java
...ngframework/expression/spel/ast/ConstructorReference.java
+3
-2
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/FunctionReference.java
...pringframework/expression/spel/ast/FunctionReference.java
+4
-1
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/Indexer.java
...java/org/springframework/expression/spel/ast/Indexer.java
+10
-3
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/MethodReference.java
.../springframework/expression/spel/ast/MethodReference.java
+4
-32
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/PropertyOrFieldReference.java
...amework/expression/spel/ast/PropertyOrFieldReference.java
+0
-1
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/Selection.java
...va/org/springframework/expression/spel/ast/Selection.java
+11
-6
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/TypeCode.java
...ava/org/springframework/expression/spel/ast/TypeCode.java
+14
-73
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/TypeReference.java
...rg/springframework/expression/spel/ast/TypeReference.java
+1
-1
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/VariableReference.java
...pringframework/expression/spel/ast/VariableReference.java
+2
-5
org.springframework.expression/src/main/java/org/springframework/expression/spel/support/ReflectiveConstructorResolver.java
...xpression/spel/support/ReflectiveConstructorResolver.java
+4
-8
org.springframework.expression/src/main/java/org/springframework/expression/spel/support/ReflectivePropertyResolver.java
...k/expression/spel/support/ReflectivePropertyResolver.java
+1
-1
org.springframework.expression/src/main/java/org/springframework/expression/spel/support/StandardEvaluationContext.java
...rk/expression/spel/support/StandardEvaluationContext.java
+2
-2
org.springframework.expression/src/test/java/org/springframework/expression/spel/ConstructorInvocationTests.java
...framework/expression/spel/ConstructorInvocationTests.java
+25
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/EvaluationTests.java
.../org/springframework/expression/spel/EvaluationTests.java
+29
-9
org.springframework.expression/src/test/java/org/springframework/expression/spel/ExpressionTestCase.java
...g/springframework/expression/spel/ExpressionTestCase.java
+1
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/HelperTests.java
...java/org/springframework/expression/spel/HelperTests.java
+5
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/MethodInvocationTests.java
...pringframework/expression/spel/MethodInvocationTests.java
+4
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/OperatorOverloaderTests.java
...ingframework/expression/spel/OperatorOverloaderTests.java
+65
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/OperatorTests.java
...va/org/springframework/expression/spel/OperatorTests.java
+3
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/PerformanceTests.java
...org/springframework/expression/spel/PerformanceTests.java
+15
-4
org.springframework.expression/src/test/java/org/springframework/expression/spel/PropertyAccessTests.java
.../springframework/expression/spel/PropertyAccessTests.java
+5
-1
org.springframework.expression/src/test/java/org/springframework/expression/spel/ScenariosForSpringSecurity.java
...framework/expression/spel/ScenariosForSpringSecurity.java
+1
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/SetValueTests.java
...va/org/springframework/expression/spel/SetValueTests.java
+5
-1
org.springframework.expression/src/test/java/org/springframework/expression/spel/SpelDocumentationTests.java
...ringframework/expression/spel/SpelDocumentationTests.java
+480
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/TestScenarioCreator.java
.../springframework/expression/spel/TestScenarioCreator.java
+1
-0
org.springframework.expression/src/test/java/org/springframework/expression/spel/testresources/Fruit.java
.../springframework/expression/spel/testresources/Fruit.java
+14
-1
org.springframework.expression/src/test/java/org/springframework/expression/spel/testresources/Inventor.java
...ringframework/expression/spel/testresources/Inventor.java
+13
-1
org.springframework.expression/src/test/java/org/springframework/expression/spel/testresources/PlaceOfBirth.java
...framework/expression/spel/testresources/PlaceOfBirth.java
+2
-0
未找到文件。
org.springframework.expression/src/main/java/org/springframework/expression/EvaluationContext.java
浏览文件 @
9a8bb5f7
...
...
@@ -37,6 +37,13 @@ public interface EvaluationContext {
*/
TypedValue
getRootObject
();
/**
* @param rootObject the root object against which unqualified properties/methods/etc should be resolved
*/
void
setRootObject
(
Object
object
);
/**
* Set a named variable within this execution context to a specified value.
* @param name variable to set
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ExpressionState.java
浏览文件 @
9a8bb5f7
...
...
@@ -48,17 +48,11 @@ public class ExpressionState {
private
final
Stack
<
TypedValue
>
contextObjects
=
new
Stack
<
TypedValue
>();
public
ExpressionState
()
{
this
(
null
);
}
public
ExpressionState
(
EvaluationContext
context
)
{
this
.
relatedContext
=
context
;
createVariableScope
();
}
private
void
createVariableScope
()
{
this
.
variableScopes
.
add
(
new
VariableScope
());
// create an empty top level VariableScope
}
...
...
@@ -95,7 +89,7 @@ public class ExpressionState {
public
TypedValue
lookupVariable
(
String
name
)
{
Object
value
=
this
.
relatedContext
.
lookupVariable
(
name
);
return
new
TypedValue
(
value
,
TypeDescriptor
.
valueOf
((
value
==
null
?
null
:
value
.
getClass
())
));
return
new
TypedValue
(
value
,
TypeDescriptor
.
forObject
(
value
));
}
public
TypeComparator
getTypeComparator
()
{
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/SpelMessages.java
浏览文件 @
9a8bb5f7
...
...
@@ -113,10 +113,10 @@ public enum SpelMessages {
"The value ''{0}'' cannot be parsed as a long"
),
PARSE_PROBLEM
(
Kind
.
ERROR
,
1066
,
"Error occurred during expression parse: {0}"
),
INVALID_FIRST_OPERAND_FOR_MATCHES_OPERATOR
(
Kind
.
ERROR
,
1067
,
"First operand to matches operator must be a string. ''{0}'' is not"
),
INVALID_SECOND_OPERAND_FOR_MATCHES_OPERATOR
(
Kind
.
ERROR
,
1068
,
"Second operand to matches operator must be a string. ''{0}'' is not"
),
FUNCTION_MUST_BE_STATIC
(
Kind
.
ERROR
,
1069
,
"Only static methods can be called via function references. The method ''{0}'' referred to by name ''{1}'' is not static.
"
);
Kind
.
ERROR
,
1068
,
"Second operand to matches operator must be a string. ''{0}'' is not"
),
//
FUNCTION_MUST_BE_STATIC
(
Kind
.
ERROR
,
1069
,
"Only static methods can be called via function references. The method ''{0}'' referred to by name ''{1}'' is not static."
),
//
CANNOT_INDEX_INTO_NULL_VALUE
(
Kind
.
ERROR
,
1070
,
"Cannot index into a null value
"
);
private
Kind
kind
;
private
int
code
;
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/ConstructorReference.java
浏览文件 @
9a8bb5f7
...
...
@@ -74,8 +74,9 @@ public class ConstructorReference extends SpelNodeImpl {
Class
<?>[]
argumentTypes
=
new
Class
[
getChildCount
()
-
1
];
for
(
int
i
=
0
;
i
<
arguments
.
length
;
i
++)
{
TypedValue
childValue
=
getChild
(
i
+
1
).
getValueInternal
(
state
);
arguments
[
i
]
=
childValue
.
getValue
();
argumentTypes
[
i
]
=
childValue
.
getValue
().
getClass
();
Object
value
=
childValue
.
getValue
();
arguments
[
i
]
=
value
;
argumentTypes
[
i
]
=
value
==
null
?
Object
.
class
:
value
.
getClass
();
}
ConstructorExecutor
executorToUse
=
this
.
cachedExecutor
;
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/FunctionReference.java
浏览文件 @
9a8bb5f7
...
...
@@ -30,6 +30,7 @@ import org.springframework.expression.spel.ExpressionState;
import
org.springframework.expression.spel.SpelException
;
import
org.springframework.expression.spel.SpelMessages
;
import
org.springframework.expression.spel.support.ReflectionHelper
;
import
org.springframework.util.ReflectionUtils
;
/**
* A function reference is of the form "#someFunction(a,b,c)". Functions may be defined in the context prior to the
...
...
@@ -101,7 +102,9 @@ public class FunctionReference extends SpelNodeImpl {
}
try
{
return
new
TypedValue
(
m
.
invoke
(
m
.
getClass
(),
functionArgs
),
new
TypeDescriptor
(
new
MethodParameter
(
m
,-
1
)));
ReflectionUtils
.
makeAccessible
(
m
);
Object
result
=
m
.
invoke
(
m
.
getClass
(),
functionArgs
);
return
new
TypedValue
(
result
,
new
TypeDescriptor
(
new
MethodParameter
(
m
,-
1
)));
}
catch
(
IllegalArgumentException
e
)
{
throw
new
SpelException
(
getCharPositionInLine
(),
e
,
SpelMessages
.
EXCEPTION_DURING_FUNCTION_CALL
,
name
,
e
.
getMessage
());
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/Indexer.java
浏览文件 @
9a8bb5f7
...
...
@@ -60,9 +60,13 @@ public class Indexer extends SpelNodeImpl {
int
idx
=
state
.
convertValue
(
index
,
INTEGER_TYPE_DESCRIPTOR
);
if
(
targetObjectTypeDescriptor
.
isArray
())
{
if
(
targetObject
==
null
)
{
throw
new
SpelException
(
SpelMessages
.
CANNOT_INDEX_INTO_NULL_VALUE
);
}
if
(
targetObject
.
getClass
().
isArray
())
{
return
new
TypedValue
(
accessArrayElement
(
targetObject
,
idx
),
TypeDescriptor
.
valueOf
(
targetObjectTypeDescriptor
.
getElementType
()));
}
else
if
(
targetObject
TypeDescriptor
.
isCollection
()
)
{
}
else
if
(
targetObject
instanceof
Collection
)
{
Collection
<?>
c
=
(
Collection
<?>)
targetObject
;
if
(
idx
>=
c
.
size
())
{
throw
new
SpelException
(
SpelMessages
.
COLLECTION_INDEX_OUT_OF_BOUNDS
,
c
.
size
(),
idx
);
...
...
@@ -81,7 +85,7 @@ public class Indexer extends SpelNodeImpl {
}
return
new
TypedValue
(
String
.
valueOf
(
ctxString
.
charAt
(
idx
)),
STRING_TYPE_DESCRIPTOR
);
}
throw
new
SpelException
(
SpelMessages
.
INDEXING_NOT_SUPPORTED_FOR_TYPE
,
targetObjectTypeDescriptor
);
throw
new
SpelException
(
SpelMessages
.
INDEXING_NOT_SUPPORTED_FOR_TYPE
,
targetObjectTypeDescriptor
.
asString
()
);
}
...
...
@@ -98,6 +102,9 @@ public class Indexer extends SpelNodeImpl {
TypeDescriptor
targetObjectTypeDescriptor
=
contextObject
.
getTypeDescriptor
();
TypedValue
index
=
getChild
(
0
).
getValueInternal
(
state
);
if
(
targetObject
==
null
)
{
throw
new
SpelException
(
SpelMessages
.
CANNOT_INDEX_INTO_NULL_VALUE
);
}
// Indexing into a Map
if
(
targetObjectTypeDescriptor
.
isMap
())
{
Map
map
=
(
Map
)
targetObject
;
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/MethodReference.java
浏览文件 @
9a8bb5f7
...
...
@@ -54,9 +54,9 @@ public class MethodReference extends SpelNodeImpl {
for
(
int
i
=
0
;
i
<
arguments
.
length
;
i
++)
{
arguments
[
i
]
=
getChild
(
i
).
getValueInternal
(
state
).
getValue
();
}
if
(
currentContext
==
null
)
{
if
(
currentContext
.
getValue
()
==
null
)
{
throw
new
SpelException
(
getCharPositionInLine
(),
SpelMessages
.
ATTEMPTED_METHOD_CALL_ON_NULL_CONTEXT_OBJECT
,
formatMethodForMessage
(
name
,
getTypes
(
arguments
)));
FormatHelper
.
formatMethodForMessage
(
name
,
getTypes
(
arguments
)));
}
MethodExecutor
executorToUse
=
this
.
cachedExecutor
;
...
...
@@ -85,12 +85,9 @@ public class MethodReference extends SpelNodeImpl {
}
private
Class
<?>[]
getTypes
(
Object
...
arguments
)
{
if
(
arguments
==
null
)
{
return
null
;
}
Class
<?>[]
argumentTypes
=
new
Class
[
arguments
.
length
];
for
(
int
i
=
0
;
i
<
arguments
.
length
;
i
++)
{
argumentTypes
[
i
]
=
arguments
[
i
].
getClass
(
);
argumentTypes
[
i
]
=
(
arguments
[
i
]==
null
?
Object
.
class
:
arguments
[
i
].
getClass
()
);
}
return
argumentTypes
;
}
...
...
@@ -108,38 +105,13 @@ public class MethodReference extends SpelNodeImpl {
return
sb
.
toString
();
}
/**
* Produce a nice string for a given method name with specified arguments.
* @param name the name of the method
* @param argumentTypes the types of the arguments to the method
* @return nicely formatted string, eg. foo(String,int)
*/
private
String
formatMethodForMessage
(
String
name
,
Class
<?>...
argumentTypes
)
{
StringBuilder
sb
=
new
StringBuilder
();
sb
.
append
(
name
);
sb
.
append
(
"("
);
if
(
argumentTypes
!=
null
)
{
for
(
int
i
=
0
;
i
<
argumentTypes
.
length
;
i
++)
{
if
(
i
>
0
)
sb
.
append
(
","
);
sb
.
append
(
argumentTypes
[
i
].
getClass
());
}
}
sb
.
append
(
")"
);
return
sb
.
toString
();
}
protected
MethodExecutor
findAccessorForMethod
(
String
name
,
Class
<?>[]
argumentTypes
,
ExpressionState
state
)
throws
SpelException
{
TypedValue
context
=
state
.
getActiveContextObject
();
Object
contextObject
=
context
.
getValue
();
EvaluationContext
eContext
=
state
.
getEvaluationContext
();
if
(
contextObject
==
null
)
{
throw
new
SpelException
(
SpelMessages
.
ATTEMPTED_METHOD_CALL_ON_NULL_CONTEXT_OBJECT
,
FormatHelper
.
formatMethodForMessage
(
name
,
argumentTypes
));
}
List
<
MethodResolver
>
mResolvers
=
eContext
.
getMethodResolvers
();
if
(
mResolvers
!=
null
)
{
for
(
MethodResolver
methodResolver
:
mResolvers
)
{
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/PropertyOrFieldReference.java
浏览文件 @
9a8bb5f7
...
...
@@ -145,7 +145,6 @@ public class PropertyOrFieldReference extends SpelNodeImpl {
}
}
}
catch
(
AccessException
ae
)
{
ae
.
printStackTrace
();
throw
new
SpelException
(
getCharPositionInLine
(),
ae
,
SpelMessages
.
EXCEPTION_DURING_PROPERTY_WRITE
,
name
,
ae
.
getMessage
());
}
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/Selection.java
浏览文件 @
9a8bb5f7
...
...
@@ -62,8 +62,10 @@ public class Selection extends SpelNodeImpl {
Map
<?,
?>
mapdata
=
(
Map
<?,
?>)
operand
;
// TODO don't lose generic info for the new map
Map
<
Object
,
Object
>
result
=
new
HashMap
<
Object
,
Object
>();
Object
lastKey
=
null
;
for
(
Object
k
:
mapdata
.
keySet
())
{
try
{
lastKey
=
k
;
KeyValuePair
kvp
=
new
KeyValuePair
(
k
,
mapdata
.
get
(
k
));
TypedValue
kvpair
=
new
TypedValue
(
kvp
,
TypeDescriptor
.
valueOf
(
KeyValuePair
.
class
));
state
.
pushActiveContextObject
(
kvpair
);
...
...
@@ -83,12 +85,15 @@ public class Selection extends SpelNodeImpl {
}
finally
{
state
.
popActiveContextObject
();
}
}
if
((
variant
==
FIRST
||
variant
==
LAST
)
&&
result
.
size
()
==
0
)
{
return
null
;
return
new
TypedValue
(
null
,
TypeDescriptor
.
NULL_TYPE_DESCRIPTOR
)
;
}
if
(
variant
==
LAST
)
{
return
new
TypedValue
(
result
.
get
(
result
.
size
()
-
1
),
TypeDescriptor
.
valueOf
(
op
.
getTypeDescriptor
().
getElementType
()));
}
Object
lastValue
=
result
.
get
(
lastKey
);
Map
resultMap
=
new
HashMap
();
resultMap
.
put
(
lastKey
,
result
.
get
(
lastKey
));
return
new
TypedValue
(
resultMap
,
TypeDescriptor
.
valueOf
(
Map
.
class
));
}
return
new
TypedValue
(
result
,
op
.
getTypeDescriptor
());
}
else
if
(
operand
instanceof
Collection
)
{
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/TypeCode.java
浏览文件 @
9a8bb5f7
...
...
@@ -16,16 +16,14 @@
package
org.springframework.expression.spel.ast
;
enum
TypeCode
{
public
enum
TypeCode
{
OBJECT
(
0
,
Object
.
class
),
BOOLEAN
(
1
,
Boolean
.
TYPE
),
BYTE
(
1
,
Byte
.
TYPE
),
CHAR
(
1
,
Character
.
TYPE
),
SHORT
(
2
,
Short
.
TYPE
),
INT
(
3
,
Integer
.
TYPE
),
LONG
(
4
,
Long
.
TYPE
),
FLOAT
(
5
,
Float
.
TYPE
),
DOUBLE
(
6
,
Double
.
TYPE
);
OBJECT
(
Object
.
class
),
BOOLEAN
(
Boolean
.
TYPE
),
BYTE
(
Byte
.
TYPE
),
CHAR
(
Character
.
TYPE
),
//
SHORT
(
Short
.
TYPE
),
INT
(
Integer
.
TYPE
),
LONG
(
Long
.
TYPE
),
FLOAT
(
Float
.
TYPE
),
DOUBLE
(
Double
.
TYPE
);
private
int
code
;
private
Class
<?>
type
;
TypeCode
(
int
code
,
Class
<?>
type
)
{
this
.
code
=
code
;
TypeCode
(
Class
<?>
type
)
{
this
.
type
=
type
;
}
...
...
@@ -33,72 +31,15 @@ enum TypeCode {
return
type
;
}
public
static
TypeCode
forClass
(
Class
<?>
c
)
{
TypeCode
[]
allValues
=
TypeCode
.
values
();
for
(
int
i
=
0
;
i
<
allValues
.
length
;
i
++)
{
TypeCode
typeCode
=
allValues
[
i
];
if
(
c
==
typeCode
.
getType
())
{
return
typeCode
;
}
}
return
OBJECT
;
}
/**
* For a primitive name this will determine the typecode value - supports
* int,byte,char,short,long,double,float,boolean
*/
public
static
TypeCode
forName
(
String
name
)
{
if
(
name
.
equals
(
"int"
))
return
TypeCode
.
INT
;
else
if
(
name
.
equals
(
"boolean"
))
return
TypeCode
.
BOOLEAN
;
else
if
(
name
.
equals
(
"char"
))
return
TypeCode
.
CHAR
;
else
if
(
name
.
equals
(
"long"
))
return
TypeCode
.
LONG
;
else
if
(
name
.
equals
(
"float"
))
return
TypeCode
.
FLOAT
;
else
if
(
name
.
equals
(
"double"
))
return
TypeCode
.
DOUBLE
;
else
if
(
name
.
equals
(
"short"
))
return
TypeCode
.
SHORT
;
else
if
(
name
.
equals
(
"byte"
))
return
TypeCode
.
BYTE
;
return
TypeCode
.
OBJECT
;
}
public
int
getCode
()
{
return
code
;
}
// public static TypeCode forClass(Class<?> c) {
// TypeCode[] allValues = TypeCode.values();
// for (int i = 0; i < allValues.length; i++) {
// TypeCode typeCode = allValues[i];
// if (c == typeCode.getType()) {
// return typeCode;
// }
// }
// return OBJECT;
// }
public
Object
coerce
(
TypeCode
fromTypeCode
,
Object
fromObject
)
{
if
(
this
==
TypeCode
.
INT
)
{
switch
(
fromTypeCode
)
{
case
BOOLEAN:
return
((
Boolean
)
fromObject
).
booleanValue
()
?
1
:
0
;
}
}
//
// return Integer.valueOf
// } else if (this==TypeCode.BOOLEAN) {
// return new Boolean(left).intValue();
return
null
;
}
public
static
TypeCode
forValue
(
Number
op1
)
{
return
forClass
(
op1
.
getClass
());
}
public
boolean
isDouble
()
{
return
this
==
DOUBLE
;
}
public
boolean
isFloat
()
{
return
this
==
FLOAT
;
}
public
boolean
isLong
()
{
return
this
==
LONG
;
}
}
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/TypeReference.java
浏览文件 @
9a8bb5f7
...
...
@@ -37,7 +37,7 @@ public class TypeReference extends SpelNodeImpl {
// TODO possible optimization here if we cache the discovered type reference, but can we do that?
String
typename
=
(
String
)
getChild
(
0
).
getValueInternal
(
state
).
getValue
();
if
(
typename
.
indexOf
(
"."
)
==
-
1
&&
Character
.
isLowerCase
(
typename
.
charAt
(
0
)))
{
TypeCode
tc
=
TypeCode
.
forName
(
typename
);
TypeCode
tc
=
TypeCode
.
valueOf
(
typename
.
toUpperCase
()
);
if
(
tc
!=
TypeCode
.
OBJECT
)
{
// it is a primitive type
return
new
TypedValue
(
tc
.
getType
(),
CLASS_TYPE_DESCRIPTOR
);
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/ast/VariableReference.java
浏览文件 @
9a8bb5f7
...
...
@@ -20,7 +20,6 @@ import org.antlr.runtime.Token;
import
org.springframework.expression.TypedValue
;
import
org.springframework.expression.spel.ExpressionState
;
import
org.springframework.expression.spel.SpelException
;
import
org.springframework.expression.spel.SpelMessages
;
/**
* Represents a variable reference, eg. #someVar. Note this is different to a *local* variable like $someVar
...
...
@@ -52,9 +51,7 @@ public class VariableReference extends SpelNodeImpl {
return
state
.
getRootContextObject
();
}
TypedValue
result
=
state
.
lookupVariable
(
this
.
name
);
if
(
result
==
null
)
{
throw
new
SpelException
(
getCharPositionInLine
(),
SpelMessages
.
VARIABLE_NOT_FOUND
,
this
.
name
);
}
// a null value will mean either the value was null or the variable was not found
return
result
;
}
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/support/ReflectiveConstructorResolver.java
浏览文件 @
9a8bb5f7
...
...
@@ -70,11 +70,9 @@ public class ReflectiveConstructorResolver implements ConstructorResolver {
if
(
matchInfo
!=
null
)
{
if
(
matchInfo
.
kind
==
ReflectionHelper
.
ArgsMatchKind
.
EXACT
)
{
return
new
ReflectiveConstructorExecutor
(
ctor
,
null
);
}
else
if
(
matchInfo
.
kind
==
ReflectionHelper
.
ArgsMatchKind
.
CLOSE
)
{
}
else
if
(
matchInfo
.
kind
==
ReflectionHelper
.
ArgsMatchKind
.
CLOSE
)
{
closeMatch
=
ctor
;
}
else
if
(
matchInfo
.
kind
==
ReflectionHelper
.
ArgsMatchKind
.
REQUIRES_CONVERSION
)
{
}
else
if
(
matchInfo
.
kind
==
ReflectionHelper
.
ArgsMatchKind
.
REQUIRES_CONVERSION
)
{
argsToConvert
=
matchInfo
.
argsRequiringConversion
;
matchRequiringConversion
=
ctor
;
}
...
...
@@ -82,11 +80,9 @@ public class ReflectiveConstructorResolver implements ConstructorResolver {
}
if
(
closeMatch
!=
null
)
{
return
new
ReflectiveConstructorExecutor
(
closeMatch
,
null
);
}
else
if
(
matchRequiringConversion
!=
null
)
{
}
else
if
(
matchRequiringConversion
!=
null
)
{
return
new
ReflectiveConstructorExecutor
(
matchRequiringConversion
,
argsToConvert
);
}
else
{
}
else
{
return
null
;
}
}
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/support/ReflectivePropertyResolver.java
浏览文件 @
9a8bb5f7
...
...
@@ -72,7 +72,7 @@ public class ReflectivePropertyResolver implements PropertyAccessor {
Method
method
=
findGetterForProperty
(
name
,
type
,
target
instanceof
Class
);
if
(
method
!=
null
)
{
this
.
readerCache
.
put
(
cacheKey
,
method
);
this
.
typeDescriptorCache
.
put
(
cacheKey
,
new
TypeDescriptor
(
new
MethodParameter
(
method
,
0
)));
this
.
typeDescriptorCache
.
put
(
cacheKey
,
new
TypeDescriptor
(
new
MethodParameter
(
method
,
-
1
)));
return
true
;
}
else
{
...
...
org.springframework.expression/src/main/java/org/springframework/expression/spel/support/StandardEvaluationContext.java
浏览文件 @
9a8bb5f7
...
...
@@ -85,8 +85,8 @@ public class StandardEvaluationContext implements EvaluationContext {
this
.
variables
.
put
(
name
,
value
);
}
public
void
registerFunction
(
String
name
,
Method
m
)
{
this
.
variables
.
put
(
name
,
m
);
public
void
registerFunction
(
String
name
,
Method
m
ethod
)
{
this
.
variables
.
put
(
name
,
m
ethod
);
}
public
Object
lookupVariable
(
String
name
)
{
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/ConstructorInvocationTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -76,6 +76,31 @@ public class ConstructorInvocationTests extends ExpressionTestCase {
// evaluate("new String(new char[]{'h','e','l','l','o'})", "hello", String.class);
}
public
void
testNonExistentType
()
{
evaluateAndCheckError
(
"new FooBar()"
,
SpelMessages
.
PROBLEM_LOCATING_CONSTRUCTOR
);
}
public
void
testVarargsInvocation01
()
{
// Calling 'Fruit(String... strings)'
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit('a','b','c').stringscount()"
,
3
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit('a').stringscount()"
,
1
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit().stringscount()"
,
0
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(1,2,3).stringscount()"
,
3
,
Integer
.
class
);
// all need converting to strings
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(1).stringscount()"
,
1
,
Integer
.
class
);
// needs string conversion
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(1,'a',3.0d).stringscount()"
,
3
,
Integer
.
class
);
// first and last need conversion
}
public
void
testVarargsInvocation02
()
{
// Calling 'Fruit(int i, String... strings)' - returns int+length_of_strings
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(5,'a','b','c').stringscount()"
,
8
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(2,'a').stringscount()"
,
3
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(4).stringscount()"
,
4
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(8,2,3).stringscount()"
,
10
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(9).stringscount()"
,
9
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(2,'a',3.0d).stringscount()"
,
4
,
Integer
.
class
);
evaluate
(
"new org.springframework.expression.spel.testresources.Fruit(8,stringArrayOfThreeItems).stringscount()"
,
11
,
Integer
.
class
);
}
/*
* These tests are attempting to call constructors where we need to widen or convert the argument in order to
* satisfy a suitable constructor.
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/EvaluationTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -61,21 +61,25 @@ public class EvaluationTests extends ExpressionTestCase {
// evaluate("name in {null, \"Anonymous\"}", "false", Boolean.class);
// }
//
// public void testRelOperatorsBetween01() {
// evaluate("1 between {1, 5}", "true", Boolean.class);
// }
public
void
testRelOperatorsBetween01
()
{
evaluate
(
"1 between listOneFive"
,
"true"
,
Boolean
.
class
);
// evaluate("1 between {1, 5}", "true", Boolean.class); // no inline list building at the moment
}
//
// public void testRelOperatorsBetween02() {
// evaluate("'efg' between {'abc', 'xyz'}", "true", Boolean.class);
// }
//
//
public void testRelOperatorsBetweenErrors01() {
//
evaluateAndCheckError("1 between T(String)", SpelMessages.BETWEEN_RIGHT_OPERAND_MUST_BE_TWO_ELEMENT_LIST, 12);
//
}
public
void
testRelOperatorsBetweenErrors01
()
{
evaluateAndCheckError
(
"1 between T(String)"
,
SpelMessages
.
BETWEEN_RIGHT_OPERAND_MUST_BE_TWO_ELEMENT_LIST
,
12
);
}
//
// public void testRelOperatorsBetweenErrors02() {
// evaluateAndCheckError("'abc' between {5,7}", SpelMessages.NOT_COMPARABLE, 6);
// }
public
void
testRelOperatorsBetweenErrors03
()
{
evaluateAndCheckError
(
"1 between listOfNumbersUpToTen"
,
SpelMessages
.
BETWEEN_RIGHT_OPERAND_MUST_BE_TWO_ELEMENT_LIST
,
10
);
}
public
void
testRelOperatorsIs01
()
{
evaluate
(
"'xyz' instanceof T(int)"
,
"false"
,
Boolean
.
class
);
...
...
@@ -347,14 +351,26 @@ public class EvaluationTests extends ExpressionTestCase {
evaluate
(
"mapOfNumbersUpToTen.?{key>5}.size()"
,
"5"
,
Integer
.
class
);
}
public
void
testSelection04
()
{
evaluateAndCheckError
(
"mapOfNumbersUpToTen.?{'hello'}.size()"
,
SpelMessages
.
RESULT_OF_SELECTION_CRITERIA_IS_NOT_BOOLEAN
);
}
public
void
testSelectionFirst01
()
{
evaluate
(
"listOfNumbersUpToTen.^{#isEven(#this) == 'y'}"
,
"2"
,
Integer
.
class
);
}
public
void
testSelectionFirst02
()
{
evaluate
(
"mapOfNumbersUpToTen.^{key>5}.size()"
,
"1"
,
Integer
.
class
);
}
public
void
testSelectionLast01
()
{
evaluate
(
"listOfNumbersUpToTen.${#isEven(#this) == 'y'}"
,
"10"
,
Integer
.
class
);
}
public
void
testSelectionLast02
()
{
evaluate
(
"mapOfNumbersUpToTen.${key>5}.size()"
,
"1"
,
Integer
.
class
);
}
public
void
testSelectionAST
()
throws
Exception
{
SpelExpression
expr
=
(
SpelExpression
)
parser
.
parseExpression
(
"'abc'.^{true}"
);
assertEquals
(
"'abc'.^{true}"
,
expr
.
toStringAST
());
...
...
@@ -412,6 +428,10 @@ public class EvaluationTests extends ExpressionTestCase {
evaluate
(
"'christian'[8]"
,
"n"
,
String
.
class
);
}
public
void
testIndexerError
()
{
evaluateAndCheckError
(
"new org.springframework.expression.spel.testresources.Inventor().inventions[1]"
,
SpelMessages
.
CANNOT_INDEX_INTO_NULL_VALUE
);
}
// Bean references
// public void testReferences01() {
// evaluate("@(apple).name", "Apple", String.class, true);
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/ExpressionTestCase.java
浏览文件 @
9a8bb5f7
...
...
@@ -27,6 +27,7 @@ import org.springframework.expression.ParseException;
import
org.springframework.expression.spel.antlr.SpelAntlrExpressionParser
;
import
org.springframework.expression.spel.support.StandardEvaluationContext
;
///CLOVER:OFF
/**
* Common superclass for expression tests.
*
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/HelperTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -37,4 +37,9 @@ public class HelperTests extends ExpressionTestCase {
assertEquals
(
"goo(java.lang.String,int[])"
,
FormatHelper
.
formatMethodForMessage
(
"goo"
,
String
.
class
,
new
int
[
1
].
getClass
()));
assertEquals
(
"boo()"
,
FormatHelper
.
formatMethodForMessage
(
"boo"
));
}
// public void testReflectionHelper01() {
// ReflectionHelper.convertArguments(parameterTypes, isVarargs, converter, arguments)
//// ReflectionHelper.setupArgumentsForVarargsInvocation(;, args)
// }
}
org.springframework.expression/src/test/java/org/springframework/expression/spel/MethodInvocationTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -86,4 +86,8 @@ public class MethodInvocationTests extends ExpressionTestCase {
// evaluate("aVarargsMethod2(8,new String[]{'a','b','c'})", 11, Integer.class);
}
public
void
testInvocationOnNullContextObject
()
{
evaluateAndCheckError
(
"null.toString()"
,
SpelMessages
.
ATTEMPTED_METHOD_CALL_ON_NULL_CONTEXT_OBJECT
);
}
}
org.springframework.expression/src/test/java/org/springframework/expression/spel/OperatorOverloaderTests.java
0 → 100644
浏览文件 @
9a8bb5f7
/*
* Copyright 2002-2009 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package
org.springframework.expression.spel
;
import
org.springframework.expression.EvaluationException
;
import
org.springframework.expression.Operation
;
import
org.springframework.expression.OperatorOverloader
;
import
org.springframework.expression.spel.support.StandardEvaluationContext
;
/**
* Test providing operator support
*
* @author Andy Clement
*/
public
class
OperatorOverloaderTests
extends
ExpressionTestCase
{
static
class
StringAndBooleanAddition
implements
OperatorOverloader
{
public
Object
operate
(
Operation
operation
,
Object
leftOperand
,
Object
rightOperand
)
throws
EvaluationException
{
if
(
operation
==
Operation
.
ADD
)
{
return
((
String
)
leftOperand
)+((
Boolean
)
rightOperand
).
toString
();
}
else
{
return
leftOperand
;
}
}
public
boolean
overridesOperation
(
Operation
operation
,
Object
leftOperand
,
Object
rightOperand
)
throws
EvaluationException
{
if
(
leftOperand
instanceof
String
&&
rightOperand
instanceof
Boolean
)
{
return
true
;
}
return
false
;
}
}
public
void
testSimpleOperations
()
throws
Exception
{
// no built in support for this:
evaluateAndCheckError
(
"'abc'+true"
,
SpelMessages
.
OPERATOR_NOT_SUPPORTED_BETWEEN_TYPES
);
StandardEvaluationContext
eContext
=
TestScenarioCreator
.
getTestEvaluationContext
();
eContext
.
setOperatorOverloader
(
new
StringAndBooleanAddition
());
SpelExpression
expr
=
(
SpelExpression
)
parser
.
parseExpression
(
"'abc'+true"
);
assertEquals
(
"abctrue"
,
expr
.
getValue
(
eContext
));
expr
=
(
SpelExpression
)
parser
.
parseExpression
(
"'abc'-true"
);
assertEquals
(
"abc"
,
expr
.
getValue
(
eContext
));
}
}
org.springframework.expression/src/test/java/org/springframework/expression/spel/OperatorTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -233,6 +233,9 @@ public class OperatorTests extends ExpressionTestCase {
node
=
getOperatorNode
((
SpelExpression
)
parser
.
parseExpression
(
"3>=4"
));
assertEquals
(
">="
,
node
.
getOperatorName
());
node
=
getOperatorNode
((
SpelExpression
)
parser
.
parseExpression
(
"3 between 4"
));
assertEquals
(
"between"
,
node
.
getOperatorName
());
}
public
void
testOperatorOverloading
()
{
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/PerformanceTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -35,6 +35,8 @@ public class PerformanceTests extends TestCase {
private
static
SpelAntlrExpressionParser
parser
=
new
SpelAntlrExpressionParser
();
private
static
EvaluationContext
eContext
=
TestScenarioCreator
.
getTestEvaluationContext
();
private
static
final
boolean
DEBUG
=
false
;
public
void
testPerformanceOfPropertyAccess
()
throws
Exception
{
long
starttime
=
0
;
long
endtime
=
0
;
...
...
@@ -58,7 +60,9 @@ public class PerformanceTests extends TestCase {
}
endtime
=
System
.
currentTimeMillis
();
long
freshParseTime
=
endtime
-
starttime
;
System
.
out
.
println
(
freshParseTime
);
if
(
DEBUG
)
{
System
.
out
.
println
(
"PropertyAccess: Time for parsing and evaluation x 10000: "
+
freshParseTime
+
"ms"
);
}
Expression
expr
=
parser
.
parseExpression
(
"placeOfBirth.city"
);
if
(
expr
==
null
)
{
...
...
@@ -70,7 +74,9 @@ public class PerformanceTests extends TestCase {
}
endtime
=
System
.
currentTimeMillis
();
long
reuseTime
=
endtime
-
starttime
;
System
.
out
.
println
(
reuseTime
);
if
(
DEBUG
)
{
System
.
out
.
println
(
"PropertyAccess: Time for just evaluation x 10000: "
+
reuseTime
+
"ms"
);
}
if
(
reuseTime
>
freshParseTime
)
{
System
.
out
.
println
(
"Fresh parse every time, ITERATIONS iterations = "
+
freshParseTime
+
"ms"
);
System
.
out
.
println
(
"Reuse SpelExpression, ITERATIONS iterations = "
+
reuseTime
+
"ms"
);
...
...
@@ -101,7 +107,9 @@ public class PerformanceTests extends TestCase {
}
endtime
=
System
.
currentTimeMillis
();
long
freshParseTime
=
endtime
-
starttime
;
System
.
out
.
println
(
freshParseTime
);
if
(
DEBUG
)
{
System
.
out
.
println
(
"MethodExpression: Time for parsing and evaluation x 10000: "
+
freshParseTime
+
"ms"
);
}
Expression
expr
=
parser
.
parseExpression
(
"getPlaceOfBirth().getCity()"
);
if
(
expr
==
null
)
{
...
...
@@ -113,7 +121,10 @@ public class PerformanceTests extends TestCase {
}
endtime
=
System
.
currentTimeMillis
();
long
reuseTime
=
endtime
-
starttime
;
System
.
out
.
println
(
reuseTime
);
if
(
DEBUG
)
{
System
.
out
.
println
(
"MethodExpression: Time for just evaluation x 10000: "
+
reuseTime
+
"ms"
);
}
if
(
reuseTime
>
freshParseTime
)
{
System
.
out
.
println
(
"Fresh parse every time, ITERATIONS iterations = "
+
freshParseTime
+
"ms"
);
System
.
out
.
println
(
"Reuse SpelExpression, ITERATIONS iterations = "
+
reuseTime
+
"ms"
);
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/PropertyAccessTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -41,6 +41,10 @@ public class PropertyAccessTests extends ExpressionTestCase {
evaluate
(
"placeOfBirth.city"
,
"SmilJan"
,
String
.
class
);
}
public
void
testSimpleAccess03
()
{
evaluate
(
"stringArrayOfThreeItems.length"
,
"3"
,
Integer
.
class
);
}
public
void
testNonExistentPropertiesAndMethods
()
{
// madeup does not exist as a property
evaluateAndCheckError
(
"madeup"
,
SpelMessages
.
PROPERTY_OR_FIELD_NOT_FOUND
,
0
);
...
...
@@ -79,7 +83,7 @@ public class PropertyAccessTests extends ExpressionTestCase {
}
catch
(
EvaluationException
e
)
{
// success - message will be: EL1063E:(pos 20): A problem occurred whilst attempting to set the property
// 'flibbles': 'Cannot set flibbles to an object of type 'class java.lang.String''
System
.
out
.
println
(
e
.
getMessage
());
//
System.out.println(e.getMessage());
}
}
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/ScenariosForSpringSecurity.java
浏览文件 @
9a8bb5f7
...
...
@@ -33,6 +33,7 @@ import org.springframework.expression.spel.antlr.SpelAntlrExpressionParser;
import
org.springframework.expression.spel.support.ReflectionHelper
;
import
org.springframework.expression.spel.support.StandardEvaluationContext
;
///CLOVER:OFF
/**
* Spring Security scenarios from https://wiki.springsource.com/display/SECURITY/Spring+Security+Expression-based+Authorization
*
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/SetValueTests.java
浏览文件 @
9a8bb5f7
...
...
@@ -48,6 +48,10 @@ public class SetValueTests extends ExpressionTestCase {
setValue
(
"inventions[0]"
,
"Just the telephone"
);
}
public
void
testSetElementOfNull
()
{
setValueExpectError
(
"new org.springframework.expression.spel.testresources.Inventor().inventions[1]"
,
SpelMessages
.
CANNOT_INDEX_INTO_NULL_VALUE
);
}
public
void
testSetArrayElementValueAllPrimitiveTypes
()
{
setValue
(
"arrayContainer.ints[1]"
,
3
);
setValue
(
"arrayContainer.floats[1]"
,
3.0f
);
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/SpelDocumentationTests.java
0 → 100644
浏览文件 @
9a8bb5f7
/*
* Copyright 2002-2009 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package
org.springframework.expression.spel
;
import
java.util.ArrayList
;
import
java.util.Arrays
;
import
java.util.Date
;
import
java.util.GregorianCalendar
;
import
java.util.HashMap
;
import
java.util.List
;
import
java.util.Map
;
import
org.springframework.expression.EvaluationContext
;
import
org.springframework.expression.Expression
;
import
org.springframework.expression.ExpressionParser
;
import
org.springframework.expression.ParserContext
;
import
org.springframework.expression.spel.antlr.SpelAntlrExpressionParser
;
import
org.springframework.expression.spel.support.StandardEvaluationContext
;
import
org.springframework.expression.spel.testresources.Inventor
;
import
org.springframework.expression.spel.testresources.PlaceOfBirth
;
/**
* Test the examples specified in the documentation.
*
* NOTE: any outgoing changes from this file upon synchronizing with the repo may indicate that
* you need to update the documentation too !
*
* @author Andy Clement
*/
public
class
SpelDocumentationTests
extends
ExpressionTestCase
{
static
Inventor
tesla
;
static
Inventor
pupin
;
static
{
GregorianCalendar
c
=
new
GregorianCalendar
();
c
.
set
(
1856
,
7
,
9
);
tesla
=
new
Inventor
(
"Nikola Tesla"
,
c
.
getTime
(),
"Serbian"
);
tesla
.
setPlaceOfBirth
(
new
PlaceOfBirth
(
"SmilJan"
));
tesla
.
setInventions
(
new
String
[]
{
"Telephone repeater"
,
"Rotating magnetic field principle"
,
"Polyphase alternating-current system"
,
"Induction motor"
,
"Alternating-current power transmission"
,
"Tesla coil transformer"
,
"Wireless communication"
,
"Radio"
,
"Fluorescent lights"
});
pupin
=
new
Inventor
(
"Pupin"
,
c
.
getTime
(),
"Idvor"
);
pupin
.
setPlaceOfBirth
(
new
PlaceOfBirth
(
"Idvor"
));
}
static
class
IEEE
{
private
String
name
;
public
Inventor
[]
Members
=
new
Inventor
[
1
];
public
List
Members2
=
new
ArrayList
();
public
Map
<
String
,
Object
>
officers
=
new
HashMap
<
String
,
Object
>();
IEEE
()
{
officers
.
put
(
"president"
,
pupin
);
List
linv
=
new
ArrayList
();
linv
.
add
(
tesla
);
officers
.
put
(
"advisors"
,
linv
);
Members2
.
add
(
tesla
);
Members2
.
add
(
pupin
);
}
public
boolean
isMember
(
String
name
)
{
return
true
;
}
public
String
getName
()
{
return
name
;
}
public
void
setName
(
String
n
)
{
this
.
name
=
n
;
}
}
public
void
testMethodInvocation
()
{
evaluate
(
"'Hello World'.concat('!')"
,
"Hello World!"
,
String
.
class
);
}
public
void
testBeanPropertyAccess
()
{
evaluate
(
"new String('Hello World'.bytes)"
,
"Hello World"
,
String
.
class
);
}
public
void
testArrayLengthAccess
()
{
evaluate
(
"'Hello World'.bytes.length"
,
11
,
Integer
.
class
);
}
public
void
testRootObject
()
throws
Exception
{
GregorianCalendar
c
=
new
GregorianCalendar
();
c
.
set
(
1856
,
7
,
9
);
// The constructor arguments are name, birthday, and nationaltiy.
Inventor
tesla
=
new
Inventor
(
"Nikola Tesla"
,
c
.
getTime
(),
"Serbian"
);
ExpressionParser
parser
=
new
SpelAntlrExpressionParser
();
Expression
exp
=
parser
.
parseExpression
(
"name"
);
EvaluationContext
context
=
new
StandardEvaluationContext
();
context
.
setRootObject
(
tesla
);
String
name
=
(
String
)
exp
.
getValue
(
context
);
assertEquals
(
"Nikola Tesla"
,
name
);
}
public
void
testEqualityCheck
()
throws
Exception
{
ExpressionParser
parser
=
new
SpelAntlrExpressionParser
();
EvaluationContext
context
=
new
StandardEvaluationContext
();
context
.
setRootObject
(
tesla
);
Expression
exp
=
parser
.
parseExpression
(
"name == 'Nikola Tesla'"
);
boolean
isEqual
=
exp
.
getValue
(
context
,
Boolean
.
class
);
// evaluates to true
assertTrue
(
isEqual
);
}
// Section 7.4.1
public
void
testXMLBasedConfig
()
{
evaluate
(
"(T(java.lang.Math).random() * 100.0 )>0"
,
true
,
Boolean
.
class
);
}
// Section 7.5
public
void
testLiterals
()
throws
Exception
{
ExpressionParser
parser
=
new
SpelAntlrExpressionParser
();
String
helloWorld
=
(
String
)
parser
.
parseExpression
(
"'Hello World'"
).
getValue
();
// evals to "Hello World"
assertEquals
(
"Hello World"
,
helloWorld
);
double
avogadrosNumber
=
(
Double
)
parser
.
parseExpression
(
"6.0221415E+23"
).
getValue
();
assertEquals
(
6.0221415
E
+
23
,
avogadrosNumber
);
int
maxValue
=
(
Integer
)
parser
.
parseExpression
(
"0x7FFFFFFF"
).
getValue
();
// evals to 2147483647
assertEquals
(
Integer
.
MAX_VALUE
,
maxValue
);
boolean
trueValue
=
(
Boolean
)
parser
.
parseExpression
(
"true"
).
getValue
();
assertTrue
(
trueValue
);
Object
nullValue
=
parser
.
parseExpression
(
"null"
).
getValue
();
assertNull
(
nullValue
);
}
public
void
testPropertyAccess
()
throws
Exception
{
EvaluationContext
context
=
TestScenarioCreator
.
getTestEvaluationContext
();
int
year
=
(
Integer
)
parser
.
parseExpression
(
"Birthdate.Year + 1900"
).
getValue
(
context
);
// 1856
assertEquals
(
1856
,
year
);
String
city
=
(
String
)
parser
.
parseExpression
(
"placeOfBirth.City"
).
getValue
(
context
);
assertEquals
(
"SmilJan"
,
city
);
}
public
void
testPropertyNavigation
()
throws
Exception
{
ExpressionParser
parser
=
new
SpelAntlrExpressionParser
();
// Inventions Array
StandardEvaluationContext
teslaContext
=
TestScenarioCreator
.
getTestEvaluationContext
();
// teslaContext.setRootObject(tesla);
// evaluates to "Induction motor"
String
invention
=
parser
.
parseExpression
(
"inventions[3]"
).
getValue
(
teslaContext
,
String
.
class
);
assertEquals
(
"Induction motor"
,
invention
);
// Members List
StandardEvaluationContext
societyContext
=
new
StandardEvaluationContext
();
IEEE
ieee
=
new
IEEE
();
ieee
.
Members
[
0
]=
tesla
;
societyContext
.
setRootObject
(
ieee
);
// evaluates to "Nikola Tesla"
String
name
=
parser
.
parseExpression
(
"Members[0].Name"
).
getValue
(
societyContext
,
String
.
class
);
assertEquals
(
"Nikola Tesla"
,
name
);
// List and Array navigation
// evaluates to "Wireless communication"
invention
=
parser
.
parseExpression
(
"Members[0].Inventions[6]"
).
getValue
(
societyContext
,
String
.
class
);
assertEquals
(
"Wireless communication"
,
invention
);
}
public
void
testDictionaryAccess
()
throws
Exception
{
StandardEvaluationContext
societyContext
=
new
StandardEvaluationContext
();
societyContext
.
setRootObject
(
new
IEEE
());
// Officer's Dictionary
// Inventor pupin = parser.parseExpression("officers['president']").getValue(societyContext, Inventor.class);
//
// // evaluates to "Idvor"
// String city = parser.parseExpression("officers['president'].PlaceOfBirth.city").getValue(societyContext, String.class);
// setting values
Inventor
i
=
parser
.
parseExpression
(
"officers['advisors'][0]"
).
getValue
(
societyContext
,
Inventor
.
class
);
assertEquals
(
"Nikola Tesla"
,
i
.
getName
());
parser
.
parseExpression
(
"officers['advisors'][0].PlaceOfBirth.Country"
).
setValue
(
societyContext
,
"Croatia"
);
}
// 7.5.3
public
void
testMethodInvocation2
()
throws
Exception
{
// string literal, evaluates to "bc"
String
c
=
parser
.
parseExpression
(
"'abc'.substring(1, 3)"
).
getValue
(
String
.
class
);
assertEquals
(
"bc"
,
c
);
StandardEvaluationContext
societyContext
=
new
StandardEvaluationContext
();
societyContext
.
setRootObject
(
new
IEEE
());
// evaluates to true
boolean
isMember
=
parser
.
parseExpression
(
"isMember('Mihajlo Pupin')"
).
getValue
(
societyContext
,
Boolean
.
class
);
assertTrue
(
isMember
);
}
// 7.5.4.1
public
void
testRelationalOperators
()
throws
Exception
{
boolean
result
=
parser
.
parseExpression
(
"2 == 2"
).
getValue
(
Boolean
.
class
);
assertTrue
(
result
);
// evaluates to false
result
=
parser
.
parseExpression
(
"2 < -5.0"
).
getValue
(
Boolean
.
class
);
assertFalse
(
result
);
// evaluates to true
result
=
parser
.
parseExpression
(
"'black' < 'block'"
).
getValue
(
Boolean
.
class
);
assertTrue
(
result
);
}
public
void
testOtherOperators
()
throws
Exception
{
// evaluates to false
boolean
falseValue
=
parser
.
parseExpression
(
"'xyz' instanceof T(int)"
).
getValue
(
Boolean
.
class
);
assertFalse
(
falseValue
);
// evaluates to true
boolean
trueValue
=
parser
.
parseExpression
(
"'5.00' matches '^-?\\d+(\\.\\d{2})?$'"
).
getValue
(
Boolean
.
class
);
assertTrue
(
trueValue
);
//evaluates to false
falseValue
=
parser
.
parseExpression
(
"'5.0067' matches '^-?\\d+(\\.\\d{2})?$'"
).
getValue
(
Boolean
.
class
);
assertFalse
(
falseValue
);
}
// 7.5.4.2
public
void
testLogicalOperators
()
throws
Exception
{
StandardEvaluationContext
societyContext
=
new
StandardEvaluationContext
();
societyContext
.
setRootObject
(
new
IEEE
());
// -- AND --
// evaluates to false
boolean
falseValue
=
parser
.
parseExpression
(
"true and false"
).
getValue
(
Boolean
.
class
);
assertFalse
(
falseValue
);
// evaluates to true
String
expression
=
"isMember('Nikola Tesla') and isMember('Mihajlo Pupin')"
;
boolean
trueValue
=
parser
.
parseExpression
(
expression
).
getValue
(
societyContext
,
Boolean
.
class
);
// -- OR --
// evaluates to true
trueValue
=
parser
.
parseExpression
(
"true or false"
).
getValue
(
Boolean
.
class
);
assertTrue
(
trueValue
);
// evaluates to true
expression
=
"isMember('Nikola Tesla') or isMember('Albert Einstien')"
;
trueValue
=
parser
.
parseExpression
(
expression
).
getValue
(
societyContext
,
Boolean
.
class
);
assertTrue
(
trueValue
);
// -- NOT --
// evaluates to false
falseValue
=
parser
.
parseExpression
(
"!true"
).
getValue
(
Boolean
.
class
);
assertFalse
(
falseValue
);
// -- AND and NOT --
expression
=
"isMember('Nikola Tesla') and !isMember('Mihajlo Pupin')"
;
falseValue
=
parser
.
parseExpression
(
expression
).
getValue
(
societyContext
,
Boolean
.
class
);
assertFalse
(
falseValue
);
}
// 7.5.4.3
public
void
testNumericalOperators
()
throws
Exception
{
// Addition
int
two
=
parser
.
parseExpression
(
"1 + 1"
).
getValue
(
Integer
.
class
);
// 2
assertEquals
(
2
,
two
);
String
testString
=
parser
.
parseExpression
(
"'test' + ' ' + 'string'"
).
getValue
(
String
.
class
);
// 'test string'
assertEquals
(
"test string"
,
testString
);
// Subtraction
int
four
=
parser
.
parseExpression
(
"1 - -3"
).
getValue
(
Integer
.
class
);
// 4
assertEquals
(
4
,
four
);
double
d
=
parser
.
parseExpression
(
"1000.00 - 1e4"
).
getValue
(
Double
.
class
);
// -9000
assertEquals
(-
9000.0d
,
d
);
// Multiplication
int
six
=
parser
.
parseExpression
(
"-2 * -3"
).
getValue
(
Integer
.
class
);
// 6
assertEquals
(
6
,
six
);
double
twentyFour
=
parser
.
parseExpression
(
"2.0 * 3e0 * 4"
).
getValue
(
Double
.
class
);
// 24.0
assertEquals
(
24.0d
,
twentyFour
);
// Division
int
minusTwo
=
parser
.
parseExpression
(
"6 / -3"
).
getValue
(
Integer
.
class
);
// -2
assertEquals
(-
2
,
minusTwo
);
double
one
=
parser
.
parseExpression
(
"8.0 / 4e0 / 2"
).
getValue
(
Double
.
class
);
// 1.0
assertEquals
(
1.0d
,
one
);
// Modulus
int
three
=
parser
.
parseExpression
(
"7 % 4"
).
getValue
(
Integer
.
class
);
// 3
assertEquals
(
3
,
three
);
int
oneInt
=
parser
.
parseExpression
(
"8 / 5 % 2"
).
getValue
(
Integer
.
class
);
// 1
assertEquals
(
1
,
oneInt
);
// Operator precedence
int
minusTwentyOne
=
parser
.
parseExpression
(
"1+2-3*8"
).
getValue
(
Integer
.
class
);
// -21
assertEquals
(-
21
,
minusTwentyOne
);
}
// 7.5.5
public
void
testAssignment
()
throws
Exception
{
Inventor
inventor
=
new
Inventor
();
StandardEvaluationContext
inventorContext
=
new
StandardEvaluationContext
();
inventorContext
.
setRootObject
(
inventor
);
parser
.
parseExpression
(
"foo"
).
setValue
(
inventorContext
,
"Alexander Seovic2"
);
assertEquals
(
"Alexander Seovic2"
,
parser
.
parseExpression
(
"foo"
).
getValue
(
inventorContext
,
String
.
class
));
// alternatively
String
aleks
=
parser
.
parseExpression
(
"foo = 'Alexandar Seovic'"
).
getValue
(
inventorContext
,
String
.
class
);
assertEquals
(
"Alexandar Seovic"
,
parser
.
parseExpression
(
"foo"
).
getValue
(
inventorContext
,
String
.
class
));
assertEquals
(
"Alexandar Seovic"
,
aleks
);
}
// 7.5.6
public
void
testTypes
()
throws
Exception
{
Class
dateClass
=
parser
.
parseExpression
(
"T(java.util.Date)"
).
getValue
(
Class
.
class
);
assertEquals
(
Date
.
class
,
dateClass
);
boolean
trueValue
=
parser
.
parseExpression
(
"T(java.math.RoundingMode).CEILING < T(java.math.RoundingMode).FLOOR"
).
getValue
(
Boolean
.
class
);
assertTrue
(
trueValue
);
}
// 7.5.7
public
void
testConstructors
()
throws
Exception
{
StandardEvaluationContext
societyContext
=
new
StandardEvaluationContext
();
societyContext
.
setRootObject
(
new
IEEE
());
Inventor
einstein
=
parser
.
parseExpression
(
"new org.springframework.expression.spel.testresources.Inventor('Albert Einstein',new java.util.Date(), 'German')"
).
getValue
(
Inventor
.
class
);
assertEquals
(
"Albert Einstein"
,
einstein
.
getName
());
//create new inventor instance within add method of List
parser
.
parseExpression
(
"Members2.add(new org.springframework.expression.spel.testresources.Inventor('Albert Einstein', 'German'))"
).
getValue
(
societyContext
);
}
// 7.5.8
public
void
testVariables
()
throws
Exception
{
Inventor
tesla
=
new
Inventor
(
"Nikola Tesla"
,
"Serbian"
);
StandardEvaluationContext
context
=
new
StandardEvaluationContext
();
context
.
setVariable
(
"newName"
,
"Mike Tesla"
);
context
.
setRootObject
(
tesla
);
parser
.
parseExpression
(
"foo = #newName"
).
getValue
(
context
);
assertEquals
(
"Mike Tesla"
,
tesla
.
getFoo
());
}
public
void
testSpecialVariables
()
throws
Exception
{
// create an array of integers
List
<
Integer
>
primes
=
new
ArrayList
<
Integer
>();
primes
.
addAll
(
Arrays
.
asList
(
2
,
3
,
5
,
7
,
11
,
13
,
17
));
// create parser and set variable 'primes' as the array of integers
ExpressionParser
parser
=
new
SpelAntlrExpressionParser
();
StandardEvaluationContext
context
=
new
StandardEvaluationContext
();
context
.
setVariable
(
"primes"
,
primes
);
// all prime numbers > 10 from the list (using selection ?{...})
List
<
Integer
>
primesGreaterThanTen
=
(
List
<
Integer
>)
parser
.
parseExpression
(
"#primes.?{#this>10}"
).
getValue
(
context
);
assertEquals
(
"[11, 13, 17]"
,
primesGreaterThanTen
.
toString
());
}
// 7.5.9
public
void
testFunctions
()
throws
Exception
{
ExpressionParser
parser
=
new
SpelAntlrExpressionParser
();
StandardEvaluationContext
context
=
new
StandardEvaluationContext
();
context
.
registerFunction
(
"reverseString"
,
StringUtils
.
class
.
getDeclaredMethod
(
"reverseString"
,
new
Class
[]
{
String
.
class
}));
String
helloWorldReversed
=
parser
.
parseExpression
(
"#reverseString('hello world')"
).
getValue
(
context
,
String
.
class
);
assertEquals
(
"dlrow olleh"
,
helloWorldReversed
);
}
// 7.5.10
public
void
testTernary
()
throws
Exception
{
String
falseString
=
parser
.
parseExpression
(
"false ? 'trueExp' : 'falseExp'"
).
getValue
(
String
.
class
);
assertEquals
(
"falseExp"
,
falseString
);
StandardEvaluationContext
societyContext
=
new
StandardEvaluationContext
();
societyContext
.
setRootObject
(
new
IEEE
());
parser
.
parseExpression
(
"Name"
).
setValue
(
societyContext
,
"IEEE"
);
societyContext
.
setVariable
(
"queryName"
,
"Nikola Tesla"
);
String
expression
=
"isMember(#queryName)? #queryName + ' is a member of the ' "
+
"+ Name + ' Society' : #queryName + ' is not a member of the ' + Name + ' Society'"
;
String
queryResultString
=
parser
.
parseExpression
(
expression
).
getValue
(
societyContext
,
String
.
class
);
assertEquals
(
"Nikola Tesla is a member of the IEEE Society"
,
queryResultString
);
// queryResultString = "Nikola Tesla is a member of the IEEE Society"
}
// 7.5.11
public
void
testSelection
()
throws
Exception
{
StandardEvaluationContext
societyContext
=
new
StandardEvaluationContext
();
societyContext
.
setRootObject
(
new
IEEE
());
List
<
Inventor
>
list
=
(
List
<
Inventor
>)
parser
.
parseExpression
(
"Members2.?{nationality == 'Serbian'}"
).
getValue
(
societyContext
);
assertEquals
(
1
,
list
.
size
());
assertEquals
(
"Nikola Tesla"
,
list
.
get
(
0
).
getName
());
}
// 7.5.12
public
void
testTemplating
()
throws
Exception
{
String
randomPhrase
=
parser
.
parseExpression
(
"random number is ${T(java.lang.Math).random()}"
,
new
TemplatedParserContext
()).
getValue
(
String
.
class
);
assertTrue
(
randomPhrase
.
startsWith
(
"random number"
));
}
static
class
TemplatedParserContext
implements
ParserContext
{
public
String
getExpressionPrefix
()
{
return
"${"
;
}
public
String
getExpressionSuffix
()
{
return
"}"
;
}
public
boolean
isTemplate
()
{
return
true
;
}
}
static
class
StringUtils
{
public
static
String
reverseString
(
String
input
)
{
StringBuilder
backwards
=
new
StringBuilder
();
for
(
int
i
=
0
;
i
<
input
.
length
();
i
++)
{
backwards
.
append
(
input
.
charAt
(
input
.
length
()
-
1
-
i
));
}
return
backwards
.
toString
();
}
}
}
org.springframework.expression/src/test/java/org/springframework/expression/spel/TestScenarioCreator.java
浏览文件 @
9a8bb5f7
...
...
@@ -22,6 +22,7 @@ import org.springframework.expression.spel.support.StandardEvaluationContext;
import
org.springframework.expression.spel.testresources.Inventor
;
import
org.springframework.expression.spel.testresources.PlaceOfBirth
;
///CLOVER:OFF
/**
* Builds an evaluation context for test expressions. Features of the test evaluation context are:
* <ul>
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/testresources/Fruit.java
浏览文件 @
9a8bb5f7
...
...
@@ -10,6 +10,7 @@ public class Fruit {
public
String
name
;
// accessible as property field
public
Color
color
;
// accessible as property through getter/setter
public
String
colorName
;
// accessible as property through getter/setter
public
int
stringscount
=
-
1
;
public
Fruit
(
String
name
,
Color
color
,
String
colorName
)
{
this
.
name
=
name
;
...
...
@@ -21,6 +22,18 @@ public class Fruit {
return
color
;
}
public
Fruit
(
String
...
strings
)
{
stringscount
=
strings
.
length
;
}
public
Fruit
(
int
i
,
String
...
strings
)
{
stringscount
=
i
+
strings
.
length
;
}
public
int
stringscount
()
{
return
stringscount
;
}
public
String
toString
()
{
return
"A"
+
(
colorName
.
startsWith
(
"o"
)
?
"n "
:
" "
)
+
colorName
+
" "
+
name
;
}
...
...
org.springframework.expression/src/test/java/org/springframework/expression/spel/testresources/Inventor.java
浏览文件 @
9a8bb5f7
...
...
@@ -12,7 +12,7 @@ public class Inventor {
private
String
name
;
public
String
publicName
;
private
PlaceOfBirth
placeOfBirth
;
Date
birthdate
;
private
Date
birthdate
;
private
int
sinNumber
;
private
String
nationality
;
private
String
[]
inventions
;
...
...
@@ -29,6 +29,9 @@ public class Inventor {
public
Map
<
String
,
Boolean
>
mapOfStringToBoolean
=
new
HashMap
<
String
,
Boolean
>();
public
Map
<
Integer
,
String
>
mapOfNumbersUpToTen
=
new
HashMap
<
Integer
,
String
>();
public
List
<
Integer
>
listOfNumbersUpToTen
=
new
ArrayList
<
Integer
>();
public
List
<
Integer
>
listOneFive
=
new
ArrayList
<
Integer
>();
public
String
[]
stringArrayOfThreeItems
=
new
String
[]{
"1"
,
"2"
,
"3"
};
private
String
foo
;
public
Inventor
(
String
name
,
Date
birthdate
,
String
nationality
)
{
this
.
name
=
name
;
...
...
@@ -43,6 +46,8 @@ public class Inventor {
testMap
.
put
(
"friday"
,
"freitag"
);
testMap
.
put
(
"saturday"
,
"samstag"
);
testMap
.
put
(
"sunday"
,
"sonntag"
);
listOneFive
.
add
(
1
);
listOneFive
.
add
(
5
);
booleanList
.
add
(
false
);
booleanList
.
add
(
false
);
listOfNumbersUpToTen
.
add
(
1
);
...
...
@@ -148,4 +153,11 @@ public class Inventor {
public
void
setSomeProperty
(
boolean
b
)
{
this
.
accessedThroughGetSet
=
b
;
}
public
Date
getBirthdate
()
{
return
birthdate
;}
public
String
getFoo
()
{
return
foo
;
}
public
void
setFoo
(
String
s
)
{
foo
=
s
;
}
public
String
getNationality
()
{
return
nationality
;
}
}
org.springframework.expression/src/test/java/org/springframework/expression/spel/testresources/PlaceOfBirth.java
浏览文件 @
9a8bb5f7
...
...
@@ -4,6 +4,8 @@ package org.springframework.expression.spel.testresources;
public
class
PlaceOfBirth
{
private
String
city
;
public
String
Country
;
@Override
public
String
toString
()
{
return
"PlaceOfBirth("
+
city
+
")"
;}
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录