Skip to content

Commit

Permalink
Implement common Node Property accessors for client Nodes (#572)
Browse files Browse the repository at this point in the history
  • Loading branch information
kevinherron committed Nov 23, 2019
1 parent c42d0e9 commit 26ae362
Show file tree
Hide file tree
Showing 27 changed files with 1,576 additions and 368 deletions.
Expand Up @@ -527,8 +527,8 @@ private void addSqrtMethod(UaFolderNode folderNode) {
.build();

SqrtMethod sqrtMethod = new SqrtMethod(methodNode);
methodNode.setProperty(UaMethodNode.InputArguments, sqrtMethod.getInputArguments());
methodNode.setProperty(UaMethodNode.OutputArguments, sqrtMethod.getOutputArguments());
methodNode.setInputArguments(sqrtMethod.getInputArguments());
methodNode.setOutputArguments(sqrtMethod.getOutputArguments());
methodNode.setInvocationHandler(sqrtMethod);

getNodeManager().addNode(methodNode);
Expand All @@ -551,8 +551,8 @@ private void addGenerateEventMethod(UaFolderNode folderNode) {
.build();

GenerateEventMethod generateEventMethod = new GenerateEventMethod(methodNode);
methodNode.setProperty(UaMethodNode.InputArguments, generateEventMethod.getInputArguments());
methodNode.setProperty(UaMethodNode.OutputArguments, generateEventMethod.getOutputArguments());
methodNode.setInputArguments(generateEventMethod.getInputArguments());
methodNode.setOutputArguments(generateEventMethod.getOutputArguments());
methodNode.setInvocationHandler(generateEventMethod);

getNodeManager().addNode(methodNode);
Expand Down
Expand Up @@ -12,62 +12,11 @@

import java.util.concurrent.CompletableFuture;

import org.eclipse.milo.opcua.sdk.core.QualifiedProperty;
import org.eclipse.milo.opcua.sdk.core.ValueRanks;
import org.eclipse.milo.opcua.stack.core.Identifiers;
import org.eclipse.milo.opcua.stack.core.StatusCodes;
import org.eclipse.milo.opcua.stack.core.UaException;
import org.eclipse.milo.opcua.stack.core.types.builtin.DataValue;
import org.eclipse.milo.opcua.stack.core.types.builtin.StatusCode;
import org.eclipse.milo.opcua.stack.core.types.structured.Argument;
import org.eclipse.milo.opcua.stack.core.util.Namespaces;

public interface MethodNode extends Node {

/**
* The NodeVersion Property is used to indicate the version of a Node.
* <p>
* The NodeVersion Property is updated each time a Reference is added or deleted to the Node the Property belongs
* to. Attribute value changes do not cause the NodeVersion to change. Clients may read the NodeVersion Property or
* subscribe to it to determine when the structure of a Node has changed.
*
* @see MethodNode#getNodeVersion()
*/
QualifiedProperty<String> NodeVersion = new QualifiedProperty<>(
Namespaces.OPC_UA,
"NodeVersion",
Identifiers.String,
ValueRanks.Scalar,
String.class
);

/**
* The InputArguments Property is used to specify the arguments that shall be used by a client when calling the
* Method.
*
* @see MethodNode#getInputArguments()
*/
QualifiedProperty<Argument[]> InputArguments = new QualifiedProperty<>(
Namespaces.OPC_UA,
"InputArguments",
Identifiers.Argument,
ValueRanks.OneDimension,
Argument[].class
);

/**
* The OutputArguments Property specifies the result returned from the Method call.
*
* @see MethodNode#getOutputArguments()
*/
QualifiedProperty<Argument[]> OutputArguments = new QualifiedProperty<>(
Namespaces.OPC_UA,
"OutputArguments",
Identifiers.Argument,
ValueRanks.OneDimension,
Argument[].class
);

/**
* Get the Executable attribute.
* <p>
Expand Down Expand Up @@ -132,45 +81,4 @@ public interface MethodNode extends Node {
*/
CompletableFuture<StatusCode> writeUserExecutable(DataValue value);

/**
* Get the value of the NodeVersion Property, if it exists.
* <p>
* The NodeVersion Property is used to indicate the version of a Node.
* <p>
* The NodeVersion Property is updated each time a Reference is added or deleted to the Node the Property belongs
* to. Attribute value changes do not cause the NodeVersion to change. Clients may read the NodeVersion Property or
* subscribe to it to determine when the structure of a Node has changed.
* <p>
* This Property is optional. If not present, the future will be completed exceptionally with a {@link UaException}
* indicating {@link StatusCodes#Bad_NotFound}.
*
* @return the value of the NodeVersion Property, if it exists.
*/
CompletableFuture<String> getNodeVersion();

/**
* Get the value of the InputArguments Property, if it exists.
* <p>
* The InputArguments Property is used to specify the arguments that shall be used by a client when calling the
* Method.
* <p>
* This Property is optional. If not present, the future will be completed exceptionally with a {@link UaException}
* indicating {@link StatusCodes#Bad_NotFound}.
*
* @return the value of the InputArguments Property, if it exists.
*/
CompletableFuture<Argument[]> getInputArguments();

/**
* Get the value of the OutputArguments Property, if it exists.
* <p>
* The OutputArguments Property specifies the result returned from the Method call.
* <p>
* This Property is optional. If not present, the future will be completed exceptionally with a {@link UaException}
* indicating {@link StatusCodes#Bad_NotFound}.
*
* @return the value of the OutputArguments Property, if it exists.
*/
CompletableFuture<Argument[]> getOutputArguments();

}
Expand Up @@ -14,12 +14,16 @@

import org.eclipse.milo.opcua.sdk.client.OpcUaClient;
import org.eclipse.milo.opcua.sdk.client.api.nodes.DataTypeNode;
import org.eclipse.milo.opcua.sdk.core.nodes.DataTypeNodeProperties;
import org.eclipse.milo.opcua.stack.core.AttributeId;
import org.eclipse.milo.opcua.stack.core.types.builtin.DataValue;
import org.eclipse.milo.opcua.stack.core.types.builtin.LocalizedText;
import org.eclipse.milo.opcua.stack.core.types.builtin.NodeId;
import org.eclipse.milo.opcua.stack.core.types.builtin.StatusCode;
import org.eclipse.milo.opcua.stack.core.types.builtin.Variant;
import org.eclipse.milo.opcua.stack.core.types.structured.EnumValueType;

import static org.eclipse.milo.opcua.sdk.core.nodes.DataTypeNodeProperties.NodeVersion;
import static org.eclipse.milo.opcua.stack.core.types.builtin.DataValue.valueOnly;

public class UaDataTypeNode extends UaNode implements DataTypeNode {
Expand Down Expand Up @@ -48,4 +52,88 @@ public CompletableFuture<StatusCode> writeIsAbstract(DataValue value) {
return writeAttribute(AttributeId.IsAbstract, value);
}

/**
* Get the value of the {@link DataTypeNodeProperties#NodeVersion} Property, if it exists.
*
* @return the value of the NodeVersion Property, if it exists.
* @see DataTypeNodeProperties
*/
public CompletableFuture<String> getNodeVersion() {
return getProperty(DataTypeNodeProperties.NodeVersion);
}

/**
* Get the value of the {@link DataTypeNodeProperties#EnumStrings} Property, if it exists.
*
* @return the value of the EnumStrings Property, if it exists.
* @see DataTypeNodeProperties
*/
public CompletableFuture<LocalizedText[]> getEnumStrings() {
return getProperty(DataTypeNodeProperties.EnumStrings);
}

/**
* Get the value of the {@link DataTypeNodeProperties#EnumValues} Property, if it exists.
*
* @return the value of the EnumValues Property, if it exists.
* @see DataTypeNodeProperties
*/
public CompletableFuture<EnumValueType[]> getEnumValues() {
return getProperty(DataTypeNodeProperties.EnumValues);
}

/**
* Get the value of the {@link DataTypeNodeProperties#OptionSetValues} Property, if it exists.
*
* @return the value of the OptionSetValues Property, if it exists.
* @see DataTypeNodeProperties
*/
public CompletableFuture<LocalizedText[]> getOptionSetValues() {
return getProperty(DataTypeNodeProperties.OptionSetValues);
}

/**
* Set the value of the {@link DataTypeNodeProperties#NodeVersion} Property, if it exists.
*
* @param nodeVersion the value to set.
* @return a {@link CompletableFuture} that completes with the {@link StatusCode} of the write operation.
* @see DataTypeNodeProperties
*/
public CompletableFuture<StatusCode> setNodeVersion(String nodeVersion) {
return setProperty(NodeVersion, nodeVersion);
}

/**
* Set the value of the EnumStrings Property, if it exists.
*
* @param enumStrings the value to set.
* @return a {@link CompletableFuture} that completes with the {@link StatusCode} of the write operation.
* @see DataTypeNodeProperties
*/
public CompletableFuture<StatusCode> setEnumStrings(LocalizedText[] enumStrings) {
return setProperty(DataTypeNodeProperties.EnumStrings, enumStrings);
}

/**
* Set the value of the {@link DataTypeNodeProperties#EnumValues} Property, if it exists.
*
* @param enumValues the value to set.
* @return a {@link CompletableFuture} that completes with the {@link StatusCode} of the write operation.
* @see DataTypeNodeProperties
*/
public CompletableFuture<StatusCode> setEnumValues(EnumValueType[] enumValues) {
return setProperty(DataTypeNodeProperties.EnumValues, enumValues);
}

/**
* Set the value of the {@link DataTypeNodeProperties#OptionSetValues} Property, if it exists.
*
* @param optionSetValues the value to set.
* @return a {@link CompletableFuture} that completes with the {@link StatusCode} of the write operation.
* @see DataTypeNodeProperties
*/
public CompletableFuture<StatusCode> setOptionSetValues(LocalizedText[] optionSetValues) {
return setProperty(DataTypeNodeProperties.OptionSetValues, optionSetValues);
}

}
Expand Up @@ -14,7 +14,10 @@

import org.eclipse.milo.opcua.sdk.client.OpcUaClient;
import org.eclipse.milo.opcua.sdk.client.api.nodes.MethodNode;
import org.eclipse.milo.opcua.sdk.core.nodes.MethodNodeProperties;
import org.eclipse.milo.opcua.stack.core.AttributeId;
import org.eclipse.milo.opcua.stack.core.StatusCodes;
import org.eclipse.milo.opcua.stack.core.UaException;
import org.eclipse.milo.opcua.stack.core.types.builtin.DataValue;
import org.eclipse.milo.opcua.stack.core.types.builtin.NodeId;
import org.eclipse.milo.opcua.stack.core.types.builtin.StatusCode;
Expand Down Expand Up @@ -69,19 +72,87 @@ public CompletableFuture<StatusCode> writeUserExecutable(DataValue value) {
return writeAttribute(AttributeId.UserExecutable, value);
}

@Override
/**
* Get the value of the {@link MethodNodeProperties#NodeVersion} Property, if it exists.
* <p>
* The NodeVersion Property is used to indicate the version of a Node.
* <p>
* The NodeVersion Property is updated each time a Reference is added or deleted to the Node the Property belongs
* to. Attribute value changes do not cause the NodeVersion to change. Clients may read the NodeVersion Property or
* subscribe to it to determine when the structure of a Node has changed.
* <p>
* This Property is optional. If not present, the future will be completed exceptionally with a {@link UaException}
* indicating {@link StatusCodes#Bad_NotFound}.
*
* @return the value of the NodeVersion Property, if it exists.
* @see MethodNodeProperties
*/
public CompletableFuture<String> getNodeVersion() {
return getProperty(MethodNode.NodeVersion);
return getProperty(MethodNodeProperties.NodeVersion);
}

@Override
/**
* Get the value of the {@link MethodNodeProperties#InputArguments} Property, if it exists.
* <p>
* The InputArguments Property is used to specify the arguments that shall be used by a client when calling the
* Method.
* <p>
* This Property is optional. If not present, the future will be completed exceptionally with a {@link UaException}
* indicating {@link StatusCodes#Bad_NotFound}.
*
* @return the value of the InputArguments Property, if it exists.
* @see MethodNodeProperties
*/
public CompletableFuture<Argument[]> getInputArguments() {
return getProperty(MethodNode.InputArguments);
return getProperty(MethodNodeProperties.InputArguments);
}

@Override
/**
* Get the value of the {@link MethodNodeProperties#OutputArguments} Property, if it exists.
* <p>
* The OutputArguments Property specifies the result returned from the Method call.
* <p>
* This Property is optional. If not present, the future will be completed exceptionally with a {@link UaException}
* indicating {@link StatusCodes#Bad_NotFound}.
*
* @return the value of the OutputArguments Property, if it exists.
* @see MethodNodeProperties
*/
public CompletableFuture<Argument[]> getOutputArguments() {
return getProperty(MethodNode.OutputArguments);
return getProperty(MethodNodeProperties.OutputArguments);
}

/**
* Set the value of the {@link MethodNodeProperties#NodeVersion} Property, if it exists.
*
* @param nodeVersion the value to set.
* @return a {@link CompletableFuture} that completes with the {@link StatusCode} of the write operation.
* @see MethodNodeProperties
*/
public CompletableFuture<StatusCode> setNodeVersion(String nodeVersion) {
return setProperty(MethodNodeProperties.NodeVersion, nodeVersion);
}

/**
* Set the value of the {@link MethodNodeProperties#InputArguments} Property, if it exists.
*
* @param inputArguments the value to set.
* @return a {@link CompletableFuture} that completes with the {@link StatusCode} of the write operation.
* @see MethodNodeProperties
*/
public CompletableFuture<StatusCode> setInputArguments(Argument[] inputArguments) {
return setProperty(MethodNodeProperties.InputArguments, inputArguments);
}

/**
* Set the value of the {@link MethodNodeProperties#OutputArguments} Property, if it exists.
*
* @param outputArguments the value to set.
* @return a {@link CompletableFuture} that completes with the {@link StatusCode} of the write operation.
* @see MethodNodeProperties
*/
public CompletableFuture<StatusCode> setOutputArguments(Argument[] outputArguments) {
return setProperty(MethodNodeProperties.OutputArguments, outputArguments);
}

}
Expand Up @@ -109,7 +109,7 @@ protected CompletableFuture<PropertyTypeNode> getPropertyNode(QualifiedName brow
});
}

protected <T> CompletableFuture<T> getProperty(QualifiedProperty<T> property) {
public <T> CompletableFuture<T> getProperty(QualifiedProperty<T> property) {
return getPropertyNode(property)
.thenCompose(VariableNode::getValue)
.thenApply(value -> cast(value, property.getJavaType()));
Expand Down

0 comments on commit 26ae362

Please sign in to comment.