/** * Copyright (C) 2012 - present by OpenGamma Inc. and the OpenGamma group of companies * * Please see distribution for license. */ package com.opengamma.web.analytics.blotter; import java.util.Collection; import java.util.List; import java.util.Map; import org.joda.beans.Bean; import org.joda.beans.JodaBeanUtils; import org.joda.beans.MetaBean; import org.joda.beans.MetaProperty; import com.google.common.collect.Lists; import com.google.common.collect.Maps; import com.opengamma.util.ArgumentChecker; /** * {@link BeanVisitor} that builds an object by pushing data from a bean into a {@link BeanDataSink sink}. * TODO a MUCH better name is required, this and BeanBuildingVisitor are too similar * @param <T> Type of object built by this visitor's sink */ /* package */ class BuildingBeanVisitor<T> implements BeanVisitor<T> { /** The bean that is the source of the data. */ private final Bean _bean; /** The sink that will receive the converted bean data. */ private final BeanDataSink<T> _sink; /* package */ BuildingBeanVisitor(Bean bean, BeanDataSink<T> sink) { ArgumentChecker.notNull(bean, "bean"); ArgumentChecker.notNull(sink, "sink"); _bean = bean; _sink = sink; } @Override public void visitMetaBean(MetaBean metaBean) { if (!_bean.getClass().equals(metaBean.beanType())) { throw new IllegalArgumentException("Bean type " + _bean.getClass().getName() + " is not the same as " + "MetaBean type " + metaBean.beanType().getName()); } _sink.setBeanData(metaBean, _bean); } @Override public void visitBeanProperty(MetaProperty<?> property, BeanTraverser traverser) { _sink.setValue(property.name(), _sink.convert(property.get(_bean), property, property.propertyType(), traverser)); } private Collection<Object> convertCollection(MetaProperty<?> property, BeanTraverser traverser) { Collection<?> values = (Collection<?>) property.get(_bean); List<Object> convertedValues = Lists.newArrayList(); Class<?> collectionType = JodaBeanUtils.collectionType(property, property.declaringType()); for (Object value : values) { convertedValues.add(_sink.convert(value, property, collectionType, traverser)); } return convertedValues; } @Override public void visitCollectionProperty(MetaProperty<?> property, BeanTraverser traverser) { _sink.setCollection(property.name(), convertCollection(property, traverser)); } @Override public void visitSetProperty(MetaProperty<?> property, BeanTraverser traverser) { _sink.setCollection(property.name(), convertCollection(property, traverser)); } @Override public void visitListProperty(MetaProperty<?> property, BeanTraverser traverser) { _sink.setCollection(property.name(), convertCollection(property, traverser)); } @Override public void visitMapProperty(MetaProperty<?> property, BeanTraverser traverser) { Map<Object, Object> convertedMap = Maps.newHashMap(); Map<?, ?> valueMap = (Map<?, ?>) property.get(_bean); Class<?> keyType = JodaBeanUtils.mapKeyType(property, property.declaringType()); Class<?> valueType = JodaBeanUtils.mapValueType(property, property.declaringType()); for (Map.Entry<?, ?> entry : valueMap.entrySet()) { Object key = _sink.convert(entry.getKey(), property, keyType, traverser); Object value = _sink.convert(entry.getValue(), property, valueType, traverser); convertedMap.put(key, value); } _sink.setMap(property.name(), convertedMap); } @Override public void visitProperty(MetaProperty<?> property, BeanTraverser traverser) { _sink.setValue(property.name(), _sink.convert(property.get(_bean), property, property.propertyType(), traverser)); } @Override public T finish() { return _sink.finish(); } }