public class SpelCompiler extends java.lang.Object implements Opcodes
The SpelCompiler is not currently handling all expression types but covers many of the common cases. The framework is extensible to cover more cases in the future. For absolute maximum speed there is *no checking* in the compiled code. The compiled version of the expression uses information learned during interpreted runs of the expression when it generates the byte code. For example if it knows that a particular property dereference always seems to return a Map then it will generate byte code that expects the result of the property dereference to be a Map. This ensures maximal performance but should the dereference result in something other than a map, the compiled expression will fail - like a ClassCastException would occur if passing data of an unexpected type in a regular Java program.
Due to the lack of checking there are likely some expressions that should never be
compiled, for example if an expression is continuously dealing with different types of
data. Due to these cases the compiler is something that must be selectively turned on
for an associated SpelExpressionParser (through the SpelParserConfiguration
object), it is not on by default.
Individual expressions can be compiled by calling SpelCompiler.compile(expression)
.
Modifier and Type | Class and Description |
---|---|
private static class |
SpelCompiler.ChildClassLoader
A ChildClassLoader will load the generated compiled expression classes.
|
private class |
SpelCompiler.ExpressionClassWriter |
Modifier and Type | Field and Description |
---|---|
private SpelCompiler.ChildClassLoader |
ccl |
private static java.util.Map<java.lang.ClassLoader,SpelCompiler> |
compilers |
private static Log |
logger |
private java.util.concurrent.atomic.AtomicInteger |
suffixId |
AALOAD, AASTORE, ACC_ABSTRACT, ACC_ANNOTATION, ACC_BRIDGE, ACC_DEPRECATED, ACC_ENUM, ACC_FINAL, ACC_INTERFACE, ACC_MANDATED, ACC_MODULE, ACC_NATIVE, ACC_OPEN, ACC_PRIVATE, ACC_PROTECTED, ACC_PUBLIC, ACC_STATIC, ACC_STATIC_PHASE, ACC_STRICT, ACC_SUPER, ACC_SYNCHRONIZED, ACC_SYNTHETIC, ACC_TRANSIENT, ACC_TRANSITIVE, ACC_VARARGS, ACC_VOLATILE, ACONST_NULL, ALOAD, ANEWARRAY, ARETURN, ARRAYLENGTH, ASM4, ASM5, ASM6, ASTORE, ATHROW, BALOAD, BASTORE, BIPUSH, CALOAD, CASTORE, CHECKCAST, D2F, D2I, D2L, DADD, DALOAD, DASTORE, DCMPG, DCMPL, DCONST_0, DCONST_1, DDIV, DLOAD, DMUL, DNEG, DOUBLE, DREM, DRETURN, DSTORE, DSUB, DUP, DUP_X1, DUP_X2, DUP2, DUP2_X1, DUP2_X2, F_APPEND, F_CHOP, F_FULL, F_NEW, F_SAME, F_SAME1, F2D, F2I, F2L, FADD, FALOAD, FASTORE, FCMPG, FCMPL, FCONST_0, FCONST_1, FCONST_2, FDIV, FLOAD, FLOAT, FMUL, FNEG, FREM, FRETURN, FSTORE, FSUB, GETFIELD, GETSTATIC, GOTO, H_GETFIELD, H_GETSTATIC, H_INVOKEINTERFACE, H_INVOKESPECIAL, H_INVOKESTATIC, H_INVOKEVIRTUAL, H_NEWINVOKESPECIAL, H_PUTFIELD, H_PUTSTATIC, I2B, I2C, I2D, I2F, I2L, I2S, IADD, IALOAD, IAND, IASTORE, ICONST_0, ICONST_1, ICONST_2, ICONST_3, ICONST_4, ICONST_5, ICONST_M1, IDIV, IF_ACMPEQ, IF_ACMPNE, IF_ICMPEQ, IF_ICMPGE, IF_ICMPGT, IF_ICMPLE, IF_ICMPLT, IF_ICMPNE, IFEQ, IFGE, IFGT, IFLE, IFLT, IFNE, IFNONNULL, IFNULL, IINC, ILOAD, IMUL, INEG, INSTANCEOF, INTEGER, INVOKEDYNAMIC, INVOKEINTERFACE, INVOKESPECIAL, INVOKESTATIC, INVOKEVIRTUAL, IOR, IREM, IRETURN, ISHL, ISHR, ISTORE, ISUB, IUSHR, IXOR, JSR, L2D, L2F, L2I, LADD, LALOAD, LAND, LASTORE, LCMP, LCONST_0, LCONST_1, LDC, LDIV, LLOAD, LMUL, LNEG, LONG, LOOKUPSWITCH, LOR, LREM, LRETURN, LSHL, LSHR, LSTORE, LSUB, LUSHR, LXOR, MONITORENTER, MONITOREXIT, MULTIANEWARRAY, NEW, NEWARRAY, NOP, NULL, POP, POP2, PUTFIELD, PUTSTATIC, RET, RETURN, SALOAD, SASTORE, SIPUSH, SWAP, T_BOOLEAN, T_BYTE, T_CHAR, T_DOUBLE, T_FLOAT, T_INT, T_LONG, T_SHORT, TABLESWITCH, TOP, UNINITIALIZED_THIS, V1_1, V1_2, V1_3, V1_4, V1_5, V1_6, V1_7, V1_8, V1_9
Modifier | Constructor and Description |
---|---|
private |
SpelCompiler(java.lang.ClassLoader classloader) |
Modifier and Type | Method and Description |
---|---|
static boolean |
compile(Expression expression)
Request that an attempt is made to compile the specified expression.
|
CompiledExpression |
compile(SpelNodeImpl expression)
Attempt compilation of the supplied expression.
|
private java.lang.Class<? extends CompiledExpression> |
createExpressionClass(SpelNodeImpl expressionToCompile)
Generate the class that encapsulates the compiled expression and define it.
|
private static void |
dump(java.lang.String expressionText,
java.lang.String name,
byte[] bytecode)
For debugging purposes, dump the specified byte code into a file on the disk.
|
static SpelCompiler |
getCompiler(java.lang.ClassLoader classLoader)
Factory method for compiler instances.
|
private int |
getNextSuffix() |
static void |
revertToInterpreted(Expression expression)
Request to revert to the interpreter for expression evaluation.
|
private static final Log logger
private static final java.util.Map<java.lang.ClassLoader,SpelCompiler> compilers
private final SpelCompiler.ChildClassLoader ccl
private final java.util.concurrent.atomic.AtomicInteger suffixId
public CompiledExpression compile(SpelNodeImpl expression)
expression
- the expression to compilenull
if compilation is not possibleprivate int getNextSuffix()
private java.lang.Class<? extends CompiledExpression> createExpressionClass(SpelNodeImpl expressionToCompile)
expressionToCompile
- the expression to be compilednull
if the decision was to opt out of
compilation during code generationpublic static SpelCompiler getCompiler(java.lang.ClassLoader classLoader)
classLoader
- the ClassLoader to use as the basis for compilationpublic static boolean compile(Expression expression)
public static void revertToInterpreted(Expression expression)
expression
- the expressionprivate static void dump(java.lang.String expressionText, java.lang.String name, byte[] bytecode)
expressionText
- the text of the expression compiledname
- the name of the class being used for the compiled expressionbytecode
- the bytecode for the generated class