package com.alibaba.tamper; import java.util.List; import com.alibaba.tamper.core.BeanMappingException; import com.alibaba.tamper.core.BeanMappingExecutor; import com.alibaba.tamper.core.BeanMappingParam; import com.alibaba.tamper.core.builder.BeanMappingBuilder; import com.alibaba.tamper.core.config.BeanMappingConfigHelper; import com.alibaba.tamper.core.config.BeanMappingEnvironment; import com.alibaba.tamper.core.config.BeanMappingObject; import com.alibaba.tamper.core.helper.ContextObjectHolder; import com.alibaba.tamper.core.process.ValueProcess; import com.alibaba.tamper.process.script.ScriptHelper; /** * Bean Mapping操作的处理单元 * * <pre> * <code> * 使用例子: * BeanMapping beanMapping = BeanMapping.create(srcClass,targetClass); * beanMapping.mapping(src,target);// 将src的属性mapping到target * * 注意:srcClass/targetClass的映射关系必须实现通过{@linkplain BeanMappingConfigHelper}的registerConfig方法注册mapping配置 * </code> * * changelog * v1.0.2 * mapping执行会有context的概念,缓存一下当前的一些执行信息 * </pre> * * @author jianghang 2011-6-8 上午11:10:24 */ public class BeanMapping { private BeanMappingObject config; // 对应的Bean Mapping配置 public BeanMapping(BeanMappingObject config){ this.config = config; } public BeanMapping(BeanMappingBuilder builder){ this.config = builder.get(); } /** * 创建指定name的BeanMapping操作 */ public static BeanMapping create(String mappingName) { BeanMappingObject config = BeanMappingConfigHelper.getInstance().getBeanMappingObject(mappingName); if (config == null) { throw new BeanMappingException("can not found mapping config for name[" + mappingName + "]"); } return new BeanMapping(config); } /** * 创建srcClass和targetClass之间的BeanMapping操作 */ public static BeanMapping create(Class srcClass, Class targetClass) { BeanMappingObject config = BeanMappingConfigHelper.getInstance().getBeanMappingObject(srcClass, targetClass); if (config == null) { throw new BeanMappingException("can not found mapping config for srcClass[" + srcClass.toString() + "] targetClass[" + targetClass + "]"); } return new BeanMapping(config); } /** * 根据定义的bean-mapping配置进行对象属性的mapping拷贝 , 允许自定义{@linkplain ValueProcess} {@linkplain SetValueProcess} * * @param src * @param target * @throws BeanMappingException */ public void mapping(Object src, Object target) throws BeanMappingException { boolean first = ContextObjectHolder.getInstance().enter(); boolean isBeanMappingSupportScript = BeanMappingEnvironment.isBeanMappingSupportScript(); BeanMappingParam param = new BeanMappingParam(); param.setSrcRef(src); param.setTargetRef(target); param.setConfig(this.config); List<ValueProcess> vps = BeanMappingEnvironment.getBeanMappingVps(); param.setProcesses(vps); // 执行mapping处理 try { BeanMappingExecutor.execute(param); } finally { if (first) {// 第一个进入的负责清空数据,可能存在递归调用处理 ContextObjectHolder.getInstance().clear(); if (isBeanMappingSupportScript) { ScriptHelper.getInstance().getScriptExecutor().disposeFunctions();// 清空记录 } } } } }