Spring - 仅当值不为null时才设置属性

Ron*_*onK 23 java spring javabeans

使用Spring时,只有在传递的值不为null时才可以设置属性吗?

例:

<bean name="myBean" class="some.Type">
   <property name="abc" value="${some.param}"/>
</bean>
Run Code Online (Sandbox Code Playgroud)

我正在寻找的行为是:

some.Type myBean = new some.Type();
if (${some.param} != null) myBean.setAbc(${some.param});
Run Code Online (Sandbox Code Playgroud)

我需要这个的原因是因为abc有一个默认值,我不想用a覆盖null.我正在创建的Bean不在我的源代码控制之下 - 所以我无法改变它的行为.(另外,abc为此目的可能是原始的,所以无论如何我都不能用null设置它.

编辑:
根据答案,我认为我的问题需要澄清.

我有bean我需要实例化并传递给我使用的第三方.这个bean拥有各类(的许多特性(目前12) ,,int 等), 每个属性都有一个默认值-我不知道它是什么,宁愿不需要知道,除非它成为一个问题.我正在寻找的是一个来自Spring的能力的通用解决方案 - 目前我唯一的解决方案是基于反射.booleanString

组态

<bean id="myBean" class="some.TypeWrapper">
   <property name="properties">
     <map>
         <entry key="abc" value="${some.value}"/>
         <entry key="xyz" value="${some.other.value}"/>
         ...
      </map>
   </property>
</bean>
Run Code Online (Sandbox Code Playgroud)

public class TypeWrapper
{
    private Type innerBean;

    public TypeWrapper()
    {
        this.innerBean = new Type();
    }

    public void setProperties(Map<String,String> properties)
    {
        if (properties != null)
        {
            for (Entry<String, Object> entry : properties.entrySet())
            {
                String propertyName = entry.getKey();
                Object propertyValue = entry.getValue();

                setValue(propertyName, propertyValue);
            }
        }
    }

    private void setValue(String propertyName, Object propertyValue)
    {
        if (propertyValue != null)
        {
           Method method = getSetter(propertyName);
           Object value = convertToValue(propertyValue, method.getParameterTypes()[0]);
           method.invoke(innerBean, value);
        }
    }

    private Method getSetter(String propertyName)
    {
      // Assume a valid bean, add a "set" at the beginning and toUpper the 1st character.
      // Scan the list of methods for a method with the same name, assume it is a "valid setter" (i.e. single argument)
      ... 
    }

    private Object convertToValue(String valueAsString, Class type)
    {
        // Check the type for all supported types and convert accordingly
        if (type.equals(Integer.TYPE))
        {
          ...
        }
        else if (type.equals(Integer.TYPE))
        {
          ...
        }
        ...
    }
}
Run Code Online (Sandbox Code Playgroud)

真正的"困难"在于实现convertToValue所有可能的价值类型.我一生中不止这样做过 - 所以对于我需要的所有可能类型(主要是原语和一些枚举)实现它并不是一个主要问题 - 但我希望存在更智能的解决方案.

Sam*_*Sam 33

您可以将SpEL占位符机制的占位符和默认值一起使用,如下所示:

<bean name="myBean" class="some.Type">
    <property name="abc" value="${some.param:#{null}}"/>
</bean>
Run Code Online (Sandbox Code Playgroud)


Sam*_*Sam 5

要解决您的问题,您必须使用SEL(Spring Expression Language).通过此功能(在SPring 3.0中添加),您可以像其他动态语言一样编写您的条件.对于您的上下文,答案是:

<bean name="myBean" class="some.Type">
   <property name="abc" value="#(if(${some.param} != null) ${some.param})"/>
</bean>
Run Code Online (Sandbox Code Playgroud)

有关更多信息,请参阅(本教程说明在上下文文件中使用SEL的内容):http: //static.springsource.org/spring/docs/3.0.5.RELEASE/reference/expressions.html

  • 如果param为null,它还不会传递空字符串吗?OP不想传递任何东西:他想避免调用setter. (6认同)

Jig*_*shi 1

您可以创建一个实用程序类,它将充当 的工厂类some.Type,并将逻辑包装在那里

例如 :

public class TypeFactory {
    public static Type craeteType(SomeType param){
        Type t = new Type();
        if(param!=null)
            t.setParam(param);
    }
}
Run Code Online (Sandbox Code Playgroud)

并在 XML 上使用此工厂方法配置 bean 创建

<bean id="myBean" class="some.Type"
      factory-method="craeteType">
    <constructor-arg ref="param"/>  
</bean>
Run Code Online (Sandbox Code Playgroud)