/** * Copyright (C) 2013 - present by OpenGamma Inc. and the OpenGamma group of companies * * Please see distribution for license. */ package com.opengamma.engine.view.client; import static com.opengamma.engine.view.permission.PortfolioPermission.ALLOW; import static com.opengamma.engine.view.permission.PortfolioPermission.DENY; import static com.opengamma.engine.view.permission.PortfolioPermission.PARTIAL; import java.util.List; import java.util.Map; import com.google.common.collect.ImmutableMap; import com.opengamma.core.position.Portfolio; import com.opengamma.core.position.PortfolioNode; import com.opengamma.engine.view.permission.PortfolioPermission; import com.opengamma.util.ArgumentChecker; /** * Responsible for scanning a portfolio and, based on whether * a node's children are accessible, determines the permissions * for each individual node. */ public class PortfolioPermissionChecker { /** * The permissions determined for each node in the portfolio. Note * that not all nodes may have an entry. Any not can be assumed * to be denied access. */ private final Map<PortfolioNode, PortfolioPermission> _permissions; /** * Constructor for the permission checker taking the portfolio to * check and the checker for each individual node. * * @param portfolio the portfolio to check, not null * @param nodeChecker the checker for each node in the portfolio, not null */ public PortfolioPermissionChecker(Portfolio portfolio, NodeChecker nodeChecker) { ArgumentChecker.notNull(portfolio, "portfolio"); ArgumentChecker.notNull(nodeChecker, "nodeChecker"); _permissions = checkNodes(portfolio.getRootNode(), nodeChecker); } /** * Recursively check each node in the portfolio. * * @param node the node to check * @param nodeChecker the checker for the node * @return map of nodes with permissions */ private Map<PortfolioNode, PortfolioPermission> checkNodes(PortfolioNode node, NodeChecker nodeChecker) { // TODO This should probably use PortfolioNodeTraverser for doing the depth-first traversal of the portfolio if (nodeChecker.check(node) == DENY) { return ImmutableMap.of(node, DENY); } else { List<PortfolioNode> children = node.getChildNodes(); ImmutableMap.Builder<PortfolioNode, PortfolioPermission> builder = ImmutableMap.builder(); // Result for node of interest is dependent on whether the children are accessible // so keep track of whether we are denied access to any boolean allAllowed = true; for (PortfolioNode child : children) { Map<PortfolioNode, PortfolioPermission> result = checkNodes(child, nodeChecker); builder.putAll(result); allAllowed = allAllowed && result.get(child) == ALLOW; } builder.put(node, allAllowed ? ALLOW : PARTIAL); return builder.build(); } } /** * Returns the permissions for the specified node. * * @param node the node to check * @return the permissions for the node */ public PortfolioPermission permissionCheck(PortfolioNode node) { return _permissions.containsKey(node) ? _permissions.get(node) : DENY; } }