/******************************************************************************* * Copyright (c) 2013 Association for Decentralized Information Management * in Industry THTH ry. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Semantum Oy - initial API and implementation *******************************************************************************/ package org.simantics.simulator.variable; import java.util.Collections; import java.util.List; import java.util.Set; import org.simantics.databoard.binding.Binding; import org.simantics.databoard.binding.error.BindingException; import org.simantics.databoard.binding.mutable.Variant; import org.simantics.databoard.type.Datatype; import org.simantics.simulator.variable.exceptions.InvalidPathException; import org.simantics.simulator.variable.exceptions.NoSuchNodeException; import org.simantics.simulator.variable.exceptions.NoValueException; import org.simantics.simulator.variable.exceptions.NodeManagerException; import org.simantics.simulator.variable.exceptions.NotInRealmException; /** * A proxy implementation of NodeManager for debugging purposes. *

* It prints time-stamped enter + exit/return strings when methods are entered * and exited. * * TODO: Implement optional extra delays for different methods. * * @author Tuukka Lehtonen */ public class DebugNodeManager implements NodeManager { protected NodeManager delegate; public DebugNodeManager(NodeManager delegate) { this.delegate = delegate; } // --- Do not require a realm access --- protected long println(String msg) { long ts = System.nanoTime(); double time = (double) ts * 1e-6; System.out.format("[%s @%f] %s\n", delegate.getClass().getSimpleName(), time, msg); return ts; } protected long println(long previousTime, String msg) { long ts = System.nanoTime(); long dt = ts - previousTime; double time = (double) ts * 1e-6; double dtime = (double) dt * 1e-6; System.out.format("[%s @%f, took %f ms] %s\n", delegate.getClass().getSimpleName(), time, dtime, msg); return ts; } protected void format(String msg, Object... args) { println(String.format(msg, args)); } /** * The realm of the node manager. Almost all other methods * of this class must be called inside this realm. */ @Override public Realm getRealm() { println("getRealm"); return delegate.getRealm(); } @Override public String getName(Node node) { long ts = println("enter getName(" + node + ")"); String name = delegate.getName(node); println(ts, "return getName(" + node + ") = " + name); return name; } /** * Adds a listener to a certain node. The new listener is called as * soon as possible (for example before simulator takes the next simulation * step). After the first call, it is called always the node value * or structure may have changed. This can be called outside of the realm. */ @Override public void addNodeListener(Node node, Runnable listener) { long ts = println("enter addNodeListener(" + node + ", " + listener + ")"); delegate.addNodeListener(node, listener); println(ts, "exit addNodeListener(" + node + ", " + listener + ")"); } /** * Removes previously added listener. This can be called outside of * the realm. */ @Override public void removeNodeListener(Node node, Runnable listener) { long ts = println("enter removeNodeListener(" + node + ", " + listener + ")"); delegate.removeNodeListener(node, listener); println(ts, "exit removeNodeListener(" + node + ", " + listener + ")"); } // --- Require a realm access --- /** * @return {@code null} if node cannot be found, otherwise a node with the given path * @throws InvalidPathException if the path is not in a valid path format * @throws NotInRealmException if not synchronized to the realm */ @Override public Node getNode(String path) throws NodeManagerException { long ts = println("enter getNode(" + path + ")"); Node node = getNode(path); println(ts, "return getNode(" + path + ") = " + node); return node; } /** * @return {@code null} if node cannot be found, otherwise a child node with the given name * @throws NotInRealmException if not synchronized to the realm */ @Override public Node getChild(Node node, String name) throws NodeManagerException { long ts = println("enter getChild(" + node + ", " + name + ")"); Node child = getChild(node, name); println(ts, "return getChild(" + node + ", " + name + ") = " + child); return child; } @Override public Node getProperty(Node node, String name) throws NodeManagerException { long ts = println("enter getProperty(" + node + ", " + name + ")"); Node property = delegate.getProperty(node, name); println(ts, "return getProperty(" + node + ", " + name + ") = " + property); return property; } @Override public List getChildNames(Node node) throws NodeManagerException { long ts = println("enter getChildNames(" + node + ")"); List childNames = delegate.getChildNames(node); println(ts, "return getChildNames(" + node + ") = " + childNames); return childNames; } @Override public List getPropertyNames(Node node) throws NodeManagerException { long ts = println("enter getPropertyNames(" + node + ")"); List propertyNames = delegate.getPropertyNames(node); println(ts, "return getPropertyNames(" + node + ") = " + propertyNames); return propertyNames; } @Override public List getChildren(Node node) throws NodeManagerException { long ts = println("enter getChildren(" + node + ")"); List children = delegate.getChildren(node); println(ts, "return getChildren(" + node + ") = " + children); return children; } @Override public List getProperties(Node node) throws NodeManagerException { long ts = println("enter getProperties(" + node + ")"); List properties = delegate.getProperties(node); println(ts, "return getProperties(" + node + ") = " + properties); return properties; } /** * @throws NoValueException if the node has no value (and therefore no datatype) * @throws NotInRealmException if not synchronized to the realm */ @Override public Datatype getDatatype(Node node) throws NodeManagerException { long ts = println("enter getValue(" + node + ")"); Datatype datatype = delegate.getDatatype(node); println(ts, "return getValue(" + node + ") = " + datatype); return datatype; } /** * @throws NoValueException if the node has no value * @throws NotInRealmException if not synchronized to the realm */ @Override public Object getValue(Node node, Binding binding) throws NodeManagerException, BindingException { long ts = println("enter getValue(" + node + ", " + binding + ")"); Object value = delegate.getValue(node, binding); println(ts, "return getValue(" + node + ", " + binding + ") = " + value); return value; } /** * A variant of {@link #getValue(Object, Binding)} that uses * a binding chosen by the node manager. */ @Override public Variant getValue(Node node) throws NodeManagerException { long ts = println("enter getValue(" + node + ")"); Variant value = delegate.getValue(node); println(ts, "return getValue(" + node + ") = " + value); return value; } /** * @throws NoSuchNodeException if the property does not exist * @throws NoValueException if the property has no value * @throws NotInRealmException if not synchronized to the realm * @throws BindingException if the value can not be bound to the given binding */ @Override public Object getValue(Node node, String property, Binding binding) throws NodeManagerException, BindingException { long ts = println("enter getValue(" + node + ", " + property + ", " + binding + ")"); Object value = delegate.getValue(node, property, binding); println(ts, "return getValue(" + node + ", " + property + ", " + binding + ") = " + value); return value; } /** * A variant of {@link #getValue(Object, String, Binding)} that uses * a binding chosen by the node manager. */ @Override public Variant getValue(Node node, String property) throws NodeManagerException { long ts = println("enter getValue(" + node + ", " + property + ")"); Variant value = delegate.getValue(node, property); println(ts, "return getValue(" + node + ", " + property + ") = " + value); return value; } /** * @throws BindingException if the value can not be bound to the given binding * @throws NoValueException if the property has no value that could be assigned * @throws NotInRealmException if not synchronized to the realm */ @Override public void setValue(Node node, Object value, Binding binding) throws NodeManagerException, BindingException { long ts = println("enter setValue(" + node + ", " + value + ", " + binding + ")"); delegate.setValue(node, value, binding); println(ts, "exit setValue(" + node + ", " + value + ", " + binding + ")"); } /** * @throws BindingException if the value can not be bound to the given binding * @throws NoSuchNodeException if the property does not exist * @throws NoValueException if the property has no value that could be assigned * @throws NotInRealmException if not synchronized to the realm */ @Override public void setValue(Node node, String property, Object value, Binding binding) throws NodeManagerException, BindingException { long ts = println("enter setValue(" + node + ", " + property + ", " + value + ", " + binding + ")"); delegate.setValue(node, property, value, binding); println(ts, "exit setValue(" + node + ", " + property + ", " + value + ", " + binding + ")"); } /** * Asks the full URI of a property node. The parent of the property is also given as a parameter. * This is an optional method, NodeManager does not have to implement it for all nodes. */ @Override public String getPropertyURI(Node parent, Node property) { long ts = println("enter getPropertyURI(" + parent + ", " + property + ")"); String result = delegate.getPropertyURI(parent, property); println(ts, "return getPropertyURI(" + parent + ", " + property + ") = " + result); return result; } /** * Asks for the classifications of a property node. * This is an optional method, NodeManager does not have to implement it for all nodes. * A default implementation should just return {@link Collections#emptySet()}. * Classifications can be any strings, however a recommended interpretation is to return * the URIs of the primary ontological types that this node corresponds to. * * @param node the node to classify * @return classifications of the node, empty set if the node has no classifications * @throws NodeManagerException */ @Override public Set getClassifications(Node node) throws NodeManagerException { long ts = println("enter getClassifications(" + node + ")"); Set result = delegate.getClassifications(node); println(ts, "return getClassifications(" + node + ") = " + result); return result; } }