/** * Copyright (C) 2012 - present by OpenGamma Inc. and the OpenGamma group of companies * * Please see distribution for license. */ package com.opengamma.engine.target; import java.io.ObjectStreamException; import org.apache.commons.lang.ObjectUtils; import org.apache.commons.lang.text.StrBuilder; import com.opengamma.engine.ComputationTargetSpecification; import com.opengamma.engine.MemoryUtils; import com.opengamma.id.ExternalId; import com.opengamma.id.ExternalIdBundle; import com.opengamma.util.ArgumentChecker; import com.opengamma.util.PublicAPI; /** * An immutable reference to a particular computation target that will be resolved later on in the view compilation process to a {@link ComputationTargetSpecification} that satisfies the requirement. */ @PublicAPI public final class ComputationTargetRequirement extends ComputationTargetReference { private static final long serialVersionUID = 1L; /** * The identifiers of the target, never null */ private final ExternalIdBundle _identifiers; /** * Creates a reference to a required computation target. * * @param targetType the type of the target, not null * @param id the target identifier, may be null for {@link ComputationTargetType#NULL} target type only */ public ComputationTargetRequirement(final ComputationTargetType targetType, final ExternalId id) { super(targetType); if (targetType != ComputationTargetType.NULL) { ArgumentChecker.notNull(id, "id"); _identifiers = id.toBundle(); } else { ArgumentChecker.isTrue(id == null, "id"); _identifiers = ExternalIdBundle.EMPTY; } } /** * Creates a reference to a required computation target. * * @param targetType the type of the target, not null * @param bundle the identifier bundle, may be null or empty for {@link ComputationTargetType#NULL} target type only */ public ComputationTargetRequirement(final ComputationTargetType targetType, final ExternalIdBundle bundle) { super(targetType); if (targetType != ComputationTargetType.NULL) { ArgumentChecker.notNull(bundle, "bundle"); ArgumentChecker.isFalse(bundle.isEmpty(), "bundle"); _identifiers = bundle; } else { ArgumentChecker.isTrue((bundle == null) || bundle.isEmpty(), "bundle"); _identifiers = ExternalIdBundle.EMPTY; } } /* package */ComputationTargetRequirement(final ComputationTargetType targetType, final ExternalIdBundle bundle, final ComputationTargetReference parent) { super(targetType, parent); ArgumentChecker.notNull(bundle, "bundle"); ArgumentChecker.isFalse(bundle.isEmpty(), "bundle"); _identifiers = bundle; } private ComputationTargetRequirement(final ComputationTargetReference parent, final ComputationTargetType type, final ExternalIdBundle identifiers) { super(parent, type); _identifiers = identifiers; } /** * Creates a requirement that describes an arbitrary target. The identifier is not resolved to a target but will be presented as an arbitrary parameter to a function. * * @param identifier the identifier to hold, not null * @return the target requirement, not null */ public static ComputationTargetRequirement of(final ExternalId identifier) { return new ComputationTargetRequirement(ComputationTargetType.PRIMITIVE, identifier); } /** * Creates a requirement that describes an arbitrary target. The identifiers are not resolved to a target but the preferred one from the bundle will be presented as an arbitrary parameter to a * function. * * @param bundle the identifiers to hold, not null * @return the target specification, not null */ public static ComputationTargetRequirement of(final ExternalIdBundle bundle) { return new ComputationTargetRequirement(ComputationTargetType.PRIMITIVE, bundle); } /** * Gets the external identifier bundle, if one exists. * * @return the external identifier bundle, may be null */ public ExternalIdBundle getIdentifiers() { return _identifiers; } @Override public ComputationTargetRequirement getRequirement() { return this; } @Override public boolean equals(final Object obj) { if (this == obj) { return true; } if (obj instanceof ComputationTargetRequirement) { ComputationTargetRequirement other = (ComputationTargetRequirement) obj; return super.equals(obj) && ObjectUtils.equals(_identifiers, other._identifiers); } return false; } @Override public int hashCode() { final int prime = 31; int result = super.hashCode(); if (_identifiers != null) { result = prime * result + _identifiers.hashCode(); } return result; } @Override protected String getIdStringImpl() { return getIdentifiers().toString(); } @Override public String toString() { return new StrBuilder() .append("CTReq[") .append(getType()) .append(", ") .append(getIdString()) .append(']') .toString(); } private Object readResolve() throws ObjectStreamException { return MemoryUtils.instance(this); } @Override protected ComputationTargetRequirement create(final ComputationTargetReference parent, final ComputationTargetType type) { return new ComputationTargetRequirement(parent, type, getIdentifiers()); } @Override public <T> T accept(final ComputationTargetReferenceVisitor<T> visitor) { return visitor.visitComputationTargetRequirement(this); } }