ThingWorx Edge Java SDK Edge Extensions > Defining Services for an ETS > Alternatives to Annotations: A Simple Example
Alternatives to Annotations: A Simple Example
Annotations are not appropriate for all situations. You may want to add shapes at runtime instead of define them at compile time. To permit this, the functions used by the ThingworxEdgeThingShapeDefinitionare exposed on the ETT. The following snippet demonstrates how to create an Edge Thing Shape dynamically at runtime, using thedefineThingShapemethod.
String thingName = "MyDynamicRuntimeThing"
boolean NO_NAMESPACE = false;
String name = "MyDynamicRuntimeShape";

EdgeThingTemplate thing = new EdgeThingTemplate(thingName, thingName);

thing.defineThingShape(PropertyTestShapeWithNamespace.class, name, NO_NAMESPACE);
The code above constructs a generic EdgeThingTemplate. However, you could also use a class that extends ETS. Composition of ETT at runtime is useful in testing scenarios, allowing test cases to construct an ETT from multiple edge thing shapes, in different combinations, without requiring a concrete ETT class for each test. Note that you can pass an array of EdgeShapeDefinitions to an ETT at runtime. In addition, you could use compile-time and runtime shape definitions in conjunction with each other.
Another scenario is the dynamic declaration of shape properties at runtime. This scenario would allow a shape to change in response to a function at runtime, or to expose properties that it discovers during configuration. The following example shows how to add a properties at runtime without the use of annotations.
package com.thingworx.edge.ets;

import com.thingworx.communications.client.things.EdgeThingShape;
import com.thingworx.communications.client.things.EdgeThingTemplate;
import com.thingworx.types.BaseTypes;

public class PropertyShape extends EdgeThingShape {

public PropertyShape(EdgeThingTemplate thingInstance, String identifier,boolean usesNamespace) {
super(thingInstance, identifier,usesNamespace);
String NO_NAMESPACE = null;
defineProperty("a","a Number", BaseTypes.NUMBER);
defineProperty("b","a String", BaseTypes.STRING);
defineProperty("c","a Boolean", BaseTypes.BOOLEAN);
FieldDefinitionCollection parameterTypesA = new FieldDefinitionCollection();
FieldDefinition resultTypeA = new FieldDefinition("result","result",BaseTypes.NOTHING);
AspectCollection aspectsA = new AspectCollection();
defineService("serviceA","A Service", parameterTypesA, resultTypeA, aspectsA);

FieldDefinitionCollection parameterTypesB = new FieldDefinitionCollection();
parameterTypesB.addFieldDefinition(new FieldDefinition("aNumber","A Number", BaseTypes.NUMBER));
parameterTypesB.addFieldDefinition(new FieldDefinition("aString","A String", BaseTypes.STRING));
parameterTypesB.addFieldDefinition(new FieldDefinition("aBoolean","A Boolean", BaseTypes.BOOLEAN));
FieldDefinition resultTypeB = new FieldDefinition("result","result",BaseTypes.NOTHING);
AspectCollection aspectsB = new AspectCollection();
defineService("serviceB","B Service", parameterTypesB, resultTypeB, aspectsB);
FieldDefinitionCollection parameterTypesC = new FieldDefinitionCollection();
FieldDefinition resultTypeC = new FieldDefinition("result","result",BaseTypes.STRING);
parameterTypesC.addFieldDefinition(new FieldDefinition("aNumber","A Number", BaseTypes.NUMBER));
parameterTypesC.addFieldDefinition(new FieldDefinition("aString","A String", BaseTypes.STRING));
parameterTypesC.addFieldDefinition(new FieldDefinition("aBoolean","A Boolean", BaseTypes.BOOLEAN));
AspectCollection aspectsC = new AspectCollection();
defineService("serviceC","C Service", parameterTypesC, resultTypeC, aspectsC);
}
}
In this example, the properties are declared during construction, which is identical to declaring properties using annotations. Your application can use a combination of dynamic property and service declaration and annotation-based property declaration. You can declare properties at any point in the life cycle of a shape.
Was this helpful?