Я делаю это следующим образом. Это заставляет меня чувствовать себя больным!
public class CounselInfoServiceImpl
extends BaseServiceImpl<CounselInfoDao, CounselInfoEntity, Long>
implements CounselInfoService {
@Inject
ClassService classService;
@Inject
@Override
public void setDao(CounselInfoDao dao)
{
super.setDao(dao);
}
@Override
public CounselInfoEntity editTo(CounselInfoEntity model)
{
CounselInfoEntity entity = id(model.getId());
if (!Strings.isNullOrEmpty(model.getName()))
{
entity.setName(model.getName());
}
if (!Strings.isNullOrEmpty(model.getAddress()))
{
entity.setAddress(model.getAddress());
}
if (!Strings.isNullOrEmpty(model.getEducation()))
{
entity.setEducation(model.getEducation());
}
if (!Strings.isNullOrEmpty(model.getPhone()))
{
entity.setPhone(model.getPhone());
}
if (!Strings.isNullOrEmpty(model.getQQ()))
{
entity.setQQ(model.getQQ());
}
if (!Strings.isNullOrEmpty(model.getRemark()))
{
entity.setPhone(model.getPhone());
}
if (!Strings.isNullOrEmpty(model.getSchool()))
{
entity.setSchool(model.getSchool());
}
if (model.getAge() != null)
{
entity.setAge(model.getAge());
}
if (model.getSex() != null)
{
entity.setSex(model.getSex());
}
if (model.getClassIntention() != null)
{
entity.setClassIntention(
classService.id(
model.getClassIntention().getId()));
}
return entity;
}
}
Любые предложения, чтобы избежать этого spaghetti code
?
Кстати, писать этот код - тяжелая работа!
РЕДАКТИРОВАТЬ
Кстати, я не думаю, что em.merge
готов к этому. См. Здесь
The EntityManager.merge() operation is used to merge the changes made to a detached object into the persistence context.
Он упомянул detached object
, но модель обновления просто получила кусочек даты. Итак, если я объединил модель, все значение модели будет применено к объекту (например, пароль, который я не хочу обновлять, и editTo
не должен касаться пароля).
Теперь обновление выглядит так.
public CounselInfoEntity editTo(CounselInfoEntity model)
{
CounselInfoEntity entity = id(model.getId());
List<? extends Attribute<CounselInfoEntity, ?>> editAttrs = Lists.<Attribute<CounselInfoEntity, ?>>newArrayList(CounselInfoEntity_.name,
CounselInfoEntity_.address,
CounselInfoEntity_.education,
CounselInfoEntity_.phone,
CounselInfoEntity_.QQ,
CounselInfoEntity_.remark,
CounselInfoEntity_.school,
CounselInfoEntity_.age,
CounselInfoEntity_.sex);
BeanHelper.merge(entity, model, BeanHelper.skipNullOrEmpty(model, editAttrs));
if (model.getClassIntention() != null)
{
entity.setClassIntention(classService.id(model.getClassIntention().getId()));
}
return entity;
}
Вот BeanHelper
package me.wener.practices.web.common.util;
import com.google.common.collect.Lists;
import java.lang.reflect.Field;
import java.util.List;
import javax.persistence.metamodel.Attribute;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.reflect.FieldUtils;
@Slf4j
public class BeanHelper
{
/**
* 获取 bean 的属性,如果属性不存在或发生异常返回null
*/
public static Object tryGetProperty(Object bean, String attrName)
{
Object property = null;
try
{
Field field = FieldUtils.getField(bean.getClass(), attrName, true);
property = field.get(bean);
} catch (Exception e)
{
if (log.isErrorEnabled())
log.error("Exception when get property " + attrName + " on " + bean, e);
}
return property;
}
public static <T, A extends Attribute<T, ?>> Object tryGetProperty(T bean, A attr)
{
return tryGetProperty(bean, attr.getName());
}
public static <T, A extends Attribute<T, ?>> boolean trySetProperty(T bean, A attr, Object value)
{
return trySetProperty(bean, attr.getName(), value);
}
public static boolean trySetProperty(Object bean, String attrName, Object value)
{
boolean failed = false;
try
{
// 对于 chain 的 setter 方法, 必须要使用 force access.
Field field = FieldUtils.getField(bean.getClass(), attrName, true);
field.set(bean, value);
} catch (Exception e)
{
if (log.isErrorEnabled())
log.error("Exception when set property " + attrName + " on " + bean, e);
failed = true;
}
return !failed;
}
/**
* Test the value of search in attrs is make the isNull and isEmpty
* <p/>
* isEmpty will apply when value is String
*/
@SafeVarargs
public static <E, A extends Attribute<E, ?>> List<A> skip(Object searcher, boolean skipNull, boolean skipEmpty, A... attrs)
{
return skip(searcher, skipNull, skipEmpty, Lists.newArrayList(attrs));
}
public static <E, A extends Attribute<E, ?>> List<A> skip(Object searcher, boolean skipNull, boolean skipEmpty, List<A> attrs)
{
List<A> list = Lists.newArrayList();
boolean valid;
for (A attr : attrs)
{
Object value = tryGetProperty(searcher, attr.getName());
valid = skipNull || value != null;
if (valid && skipEmpty && value instanceof String)
valid = ((String) value).length() != 0;
if (valid)
list.add(attr);
}
return list;
}
@SafeVarargs
public static <E, A extends Attribute<E, ?>> List<A> skipNullOrEmpty(Object searcher, A... attrs)
{
return skip(searcher, true, true, attrs);
}
public static <E, A extends Attribute<E, ?>> List<A> skipNullOrEmpty(Object searcher, List<A> attrs)
{
return skip(searcher, true, true, attrs);
}
@SafeVarargs
public static <T, A extends Attribute<T, ?>> T merge(T target, T src, A... attrs)
{
return merge(target, src, Lists.newArrayList(attrs));
}
public static <T, A extends Attribute<T, ?>> T merge(T target, T src, List<A> attrs)
{
for (A attr : attrs)
{
String attrName = attr.getName();
Object value = tryGetProperty(src, attrName);
trySetProperty(target, attrName, value);
}
return target;
}
}
Это лучше, потому что
Он включает
Я стараюсь изо всех сил, это лучшее, что я могу сделать.