Annotations
Moxie uses annotations in order to understand how to process your delegate code.
Learning to use them effectively can help make writing your delegates easier.
You should pay especially close attention to how you use the @DelegateFor
and
@DefaultDelegate
annotations.
Assuming that all of the @DelegateFor
annotations in the following list are for a single
block:
- If you do not annotate any delegates with
@DelegateFor
, then Moxie will auto-implement a delegate for the block at runtime.This case does not require you to use any annotations, but in the following cases, you can annotate delegates with
@AutoDelegateImplementation
to have Moxie auto-implement parts of the delegates that are missing. - If you annotate exactly one delegate with
@DelegateFor
, then Moxie will use that delegate for the block. - If you annotate more than one delegate with
@DelegateFor
, then Moxie will throw an error at runtime unless you also do one of the following:- Annotate exactly one of the delegates with
@DefaultDelegate
, in which case Moxie will use that delegate for the block. - Apply
MoxieJavaDelegate
stereotypes to every instance specification of the block, in which case Moxie will use the delegates specified in each stereotype for their respective instance specifications of the block.The
MoxieJavaDelegate
stereotype overrides all of the other cases in this list, but it only applies to its instance specification, not any other instance specifications of the same block.
- Annotate exactly one of the delegates with
- If you annotate a delegate interface or abstract class with
@DelegateFor
, then Moxie will only use that delegate if you also annotate it with@AutoDelegateImplementation
. - If you annotate a delegate with
@DelegateFor
and other delegates inherit from that first delegate, then Moxie will treat both the first delegate and the inheriting delegates as if they were all annotated with@DelegateFor
, resolving them according to the previous bullets.
If you use an inheritance hierarchy for your delegates, then you should be careful to specify the base delegate that represents the block in any contexts that need to be able to accept any of the inheriting delegates. For example, if you have an interface that represents the block and you have concrete classes that implement that interface, then in a method that needs to accept an instance of the block you should use the interface as the parameter type.
Annotation | Description |
---|---|
@DelegateFor("Structure::Qualified::Name")
|
Maps a SysML block to its corresponding Java delegate. AGI recommends that you define one unique interface with a
You can use the If more than one delegate references the same qualified name in its
|
@DefaultDelegate
|
If two or more classes derive from a base class or interface annotated with
In the following snippet, both
|
@AutoDelegateImplementation
|
This annotation is optional. By annotating a class or interface with In the following snippet, the
|
@EnumerationLiteralName
|
This annotation is optional. This annotation enables you to map enumeration literals in your model to Java enum constants. In particular, if there is a difference in spelling or formatting between a model enumeration literal and its Java counterpart, this annotation will address that for you. If no such annotation is specified, Moxie attempts to map to a literal with the same spelling and formatting on both sides. In the following snippet, the enumeration literals for the model do not match their Java enum constant counterparts.
|
Constructors
Annotation | Description |
---|---|
@InjectByName("injectedDependencyName")
|
Annotates an injection constructor parameter and retrieves the dependency by name. The dependencies for existing tools are listed
with their corresponding
|
@InjectBySlot("propertyName")
|
Annotates an injection constructor parameter and provides the value found in the slot for the corresponding property of the Instance Specification.
If this annotation is specified but a slot value is not provided in the instance specification, a
If a slot value is provided in the instance specification, then the system will
perform a wire-up to set
the value whether or not this parameter is present in the constructor. This simply provides a useful way to gain
access to the value at construction time.
The type of the parameter must match its Java equivalent as specified by the |
@OptionalInjectBySlot("propertyName")
|
This annotation behaves similarly to @InjectBySlot except that missing slot values result in null values being
injected to the constructor rather than an exception being thrown.
|
@InjectStereotype CustomStereotypeImplementation
|
The |
Stereotypes
MoxieJavaDelegate
The Moxie-Base::Configuration::MoxieJavaDelegate
stereotype allows you to map
Instance Specifications explicitly to their
corresponding delegate implementations. This is required when multiple implementations exist for the same block and either (a) none of the
implementations have been annotated with @DefaultDelegate
or (b) you wish to override the type designated as the
@DefaultDelegate
with a different type.
Figure 1
shows this stereotype applied to an instance named passenger. ChildPassenger
is specified as the type to be
used for the
Passenger
block. This informs the
Moxie Engine
that ChildPassenger
will now be used at simulation runtime instead of AdultPassenger
,
even though
AdultPassenger
is annotated with @DefaultDelegate
. This is especially useful for
testing different implementations, as
it allows you to switch between them without having to recompile your Java first.
Figure 1: Configuration stereotypes for a delegate that uses STK
MoxieStkExistingObject
If you are using STK as your analysis tool, you can take advantage of the
Moxie-STK::Configuration::MoxieStkExistingObject
stereotype to map
STK Scenario
objects to their corresponding Instance Specifications. Figure 1
demonstrates this.
In Figure 1, the stkObjectPath
stereotype tag informs
Moxie
which STK object an
Instance Specification corresponds to. This is useful in cases where there is a pre-built STK scenario that forms the basis
of the
simulation. This can include pre-configured background objects that may or may not have specific behaviors defined in SysML but are included as
dependencies for objects that are involved in executing the behaviors.