@Override public Object[] extract(T item) { ExpressionParser parser = new SpelExpressionParser(); EvaluationContext elContext = new CoreMappingEvaluationContext(item); elContext.getPropertyAccessors().add(new ExtendedAttributePropertyAccessor()); try (InputStream iStream = resource.getInputStream()) { List<String> expressions = IOUtils.readLines(iStream); List<Object> fields = Lists.newArrayListWithCapacity(expressions.size()); for (String expression : expressions) { String value = parser.parseExpression(expression).getValue(elContext, String.class); if (value != null && value.contains("\"") && !"\"\"".equals(value)) { value = value.replaceAll("\"", "\"\""); } if (value != null && value.contains(",")) { StringBuilder sb = new StringBuilder(value.length() + 2); sb.append("\""); sb.append(value); sb.append("\""); value = sb.toString(); } fields.add(value); } return fields.toArray(new Object[fields.size()]); } catch (IOException e) { throw new RuntimeException(e); } }
@Test public void test() { ExpressionParser parser = new SpelExpressionParser(); Expression expression = parser.parseExpression("('Hello' + ' World').concat(#end)"); EvaluationContext context = new StandardEvaluationContext(); context.setVariable("end", "!"); System.out.println(expression.getValue(context)); Assert.assertEquals("Hello World!", expression.getValue(context)); }
public MethodExecutor resolve( EvaluationContext context, Object targetObject, String name, Class<?>[] arguments) throws AccessException { if (name.equals("hasRole")) { return new HasRoleExecutor(context.getTypeConverter()); } return null; }
@Override public Object lookupVariable(String name) { Object result = delegate.lookupVariable(name); if (result == null) { String pattern = (String) request.getAttribute(PATTERN_ATTR_PREFIX + conditionId); if (pattern != null) { Map<String, String> pathVariables = getPathMatcher().extractUriTemplateVariables(pattern, request.getServletPath()); result = pathVariables.get(name); } } return result; }
public static void main(String[] args) { // 创建一个ExpressionParser对象,用于解析表达式 ExpressionParser parser = new SpelExpressionParser(); List<String> list = new ArrayList<String>(); list.add("疯狂Java讲义"); list.add("疯狂Ajax讲义"); list.add("疯狂XML讲义"); list.add("经典Java EE企业应用实战"); EvaluationContext ctx = new StandardEvaluationContext(); ctx.setVariable("mylist", list); // 得到的新集合的元素是原集合的每个元素length()方法返回值 Expression expr = parser.parseExpression("#mylist.![length()]"); System.out.println(expr.getValue(ctx)); List<Person> list2 = new ArrayList<Person>(); list2.add(new Person(1, "孙悟空", 162)); list2.add(new Person(1, "猪八戒", 182)); list2.add(new Person(1, "牛魔王", 195)); ctx.setVariable("mylist2", list2); // 得到的新集合的元素是原集合的每个元素name属性值 expr = parser.parseExpression("#mylist2.![name]"); System.out.println(expr.getValue(ctx)); }
/** * Determines if there is a type converter available in the specified context and attempts to use * it to convert the supplied value to the specified type. Throws an exception if conversion is * not possible. * * @param context the evaluation context that may define a type converter * @param typedValue the value to convert and a type descriptor describing it * @param targetType the type to attempt conversion to * @return the converted value * @throws EvaluationException if there is a problem during conversion or conversion of the value * to the specified type is not supported */ @SuppressWarnings("unchecked") public static <T> T convertTypedValue( EvaluationContext context, TypedValue typedValue, Class<T> targetType) { Object value = typedValue.getValue(); if ((targetType == null) || (value != null && ClassUtils.isAssignableValue(targetType, value))) { return (T) value; } if (context != null) { return (T) context .getTypeConverter() .convertValue( value, typedValue.getTypeDescriptor(), TypeDescriptor.valueOf(targetType)); } throw new EvaluationException( "Cannot convert value '" + value + "' to type '" + targetType.getName() + "'"); }
@Override public TypeConverter getTypeConverter() { return delegate.getTypeConverter(); }
@Override public void write(EvaluationContext context, Object target, String name, Object newValue) throws AccessException { if (target == null) { throw new AccessException("Cannot write property on null target"); } Class<?> type = (target instanceof Class ? (Class<?>) target : target.getClass()); Object possiblyConvertedNewValue = newValue; TypeDescriptor typeDescriptor = getTypeDescriptor(context, target, name); if (typeDescriptor != null) { try { possiblyConvertedNewValue = context .getTypeConverter() .convertValue(newValue, TypeDescriptor.forObject(newValue), typeDescriptor); } catch (EvaluationException evaluationException) { throw new AccessException("Type conversion failure", evaluationException); } } PropertyCacheKey cacheKey = new PropertyCacheKey(type, name, target instanceof Class); Member cachedMember = this.writerCache.get(cacheKey); if (cachedMember == null || cachedMember instanceof Method) { Method method = (Method) cachedMember; if (method == null) { method = findSetterForProperty(name, type, target); if (method != null) { cachedMember = method; this.writerCache.put(cacheKey, cachedMember); } } if (method != null) { try { ReflectionUtils.makeAccessible(method); method.invoke(target, possiblyConvertedNewValue); return; } catch (Exception ex) { throw new AccessException( "Unable to access property '" + name + "' through setter method", ex); } } } if (cachedMember == null || cachedMember instanceof Field) { Field field = (Field) cachedMember; if (field == null) { field = findField(name, type, target); if (field != null) { cachedMember = field; this.writerCache.put(cacheKey, cachedMember); } } if (field != null) { try { ReflectionUtils.makeAccessible(field); field.set(target, possiblyConvertedNewValue); return; } catch (Exception ex) { throw new AccessException("Unable to access field '" + name + "'", ex); } } } throw new AccessException("Neither setter method nor field found for property '" + name + "'"); }
@Override public TypedValue getRootObject() { return delegate.getRootObject(); }
@Override public BeanResolver getBeanResolver() { return delegate.getBeanResolver(); }
@Override public void setVariable(String name, Object value) { delegate.setVariable(name, value); }
public ExpressionState(EvaluationContext context, SpelParserConfiguration configuration) { this(context, context.getRootObject(), configuration); }
@Override public OperatorOverloader getOperatorOverloader() { return delegate.getOperatorOverloader(); }
/** * Locate a constructor on the type. There are three kinds of match that might occur: * * <ol> * <li>An exact match where the types of the arguments match the types of the constructor * <li>An in-exact match where the types we are looking for are subtypes of those defined on the * constructor * <li>A match where we are able to convert the arguments into those expected by the * constructor, according to the registered type converter. * </ol> */ @Override public ConstructorExecutor resolve( EvaluationContext context, String typename, List<TypeDescriptor> argumentTypes) throws AccessException { try { TypeConverter typeConverter = context.getTypeConverter(); Class<?> type = context.getTypeLocator().findType(typename); Constructor<?>[] ctors = type.getConstructors(); Arrays.sort( ctors, new Comparator<Constructor<?>>() { @Override public int compare(Constructor<?> c1, Constructor<?> c2) { int c1pl = c1.getParameterTypes().length; int c2pl = c2.getParameterTypes().length; return (new Integer(c1pl)).compareTo(c2pl); } }); Constructor<?> closeMatch = null; for (Constructor<?> ctor : ctors) { Class<?>[] paramTypes = ctor.getParameterTypes(); List<TypeDescriptor> paramDescriptors = new ArrayList<TypeDescriptor>(paramTypes.length); for (int i = 0; i < paramTypes.length; i++) { paramDescriptors.add(new TypeDescriptor(new MethodParameter(ctor, i))); } ReflectionHelper.ArgumentsMatchInfo matchInfo = null; if (ctor.isVarArgs() && argumentTypes.size() >= paramTypes.length - 1) { // *sigh* complicated // Basically.. we have to have all parameters match up until the varargs one, then the // rest of what is // being provided should be // the same type whilst the final argument to the method must be an array of that (oh, how // easy...not) - // or the final parameter // we are supplied does match exactly (it is an array already). matchInfo = ReflectionHelper.compareArgumentsVarargs( paramDescriptors, argumentTypes, typeConverter); } else if (paramTypes.length == argumentTypes.size()) { // worth a closer look matchInfo = ReflectionHelper.compareArguments(paramDescriptors, argumentTypes, typeConverter); } if (matchInfo != null) { if (matchInfo.isExactMatch()) { return new ReflectiveConstructorExecutor(ctor); } else if (matchInfo.isCloseMatch() || matchInfo.isMatchRequiringConversion()) { closeMatch = ctor; } } } return (closeMatch != null ? new ReflectiveConstructorExecutor(closeMatch) : null); } catch (EvaluationException ex) { throw new AccessException("Failed to resolve constructor", ex); } }
@Override public TypeLocator getTypeLocator() { return delegate.getTypeLocator(); }
@Override public List<PropertyAccessor> getPropertyAccessors() { return delegate.getPropertyAccessors(); }
@Override public List<MethodResolver> getMethodResolvers() { return delegate.getMethodResolvers(); }
@Override public List<ConstructorResolver> getConstructorResolvers() { return delegate.getConstructorResolvers(); }
@Override public TypeComparator getTypeComparator() { return delegate.getTypeComparator(); }
public ExpressionState(EvaluationContext context) { this(context, context.getRootObject(), new SpelParserConfiguration(false, false)); }