When using a module marked as non-hygienic, the schema of the input to the Module Reference automatically overrides the schema defined in input streams in the module. Non-hygienic modules were formerly referred to as flexible modules in previous releases.
Modules are marked non-hygienic by selecting the References to this module check box in the EventFlow Editor's Annotations tab:
Interfaces are marked non-hygienic by selecting the Allow implementations check box in the Interface Editor's Interfaces tab:
Non-hygienic modules allow maximum flexibility in re-using the module, such that a module input stream that defines a certain set of fields can be referenced with a stream that defines more or fewer than that number of fields, as long as the criteria for completing the module's processing are met. Any field names referenced by name in the module must be named the same in the calling reference, and the data type of fields actually processed in the module must be compatible enough to allow that processing to occur. In a non-hygienic module, all other fields in the calling reference are accepted and passed through.
For example, an inner module might define three fields as int
, long
, string
and its purpose is to multiply the first two fields and return the result in a new field. When set as non-hygienic, this
module can be called by a Module Reference whose input has five fields, as long as the first two fields have the same field
names and have compatibly coercible data types as the inner module.
See EventFlow Editor Read-Only Canvas for information on the context menu item that can open non-hygienic modules in a way that shows how their input stream schemas will be overridden at runtime.
When using a module marked as hygienic, the schema of the Module Reference must be strictly compatible with the number and data type of the module's input streams, or must be compatibly coercible to the module's data types. Interfaces can be marked hygienic, as well, which requires modules that implement that interface to be hygienic.
Compliance of the Module Reference's schema with the module's schema is enforced by typechecking. This has the advantage of eliminating field name conflicts and other difficult-to-debug typecheck errors, and allows for faster typechecking.
An EventFlow module is marked hygienic in the Annotations tab of the EventFlow Editor by clearing the check box for the References to this module control:
Newly created modules and interfaces are marked hygienic by default.
You can emulate the flexibility of a non-hygienic module by using a capture field with your hygienic module.
Module instances can be connected to extension points using an Extension Point operator as well as to streams. Each extension point is built on an interface (defined in an .sbint file). The interface can require extensions that implement it to match its schema in either a strict or a non-strict way.
Like modules, EventFlow interfaces can also be either non-hygienic (non-strict) or hygienic (strict). A new interface is by default hygienic. To cause it to be non-hygienic (not recommended), select the check box
on its Interface tab.Modules that implement an extension point can also by non-hygienic or hygienic, potentially entailing several types of incompatibilities. The following table characterizes how the strictness of interfaces and implementations interact.
Non-Hygienic Interface | Hygienic Interface | |
---|---|---|
Non-Hygienic Child Module | Unmatched fields are tolerated | Error 2: No module instance can be non-Hygienic |
Hygienic Child Module | Error 1: All module instances must be non-Hygienic | All fields in child modules must match the interface |
When mismatches that cannot be coerced occur, StreamBase raises errors that identify the extension point as their locus. Fixing the problem requires changing either the interface or the implementing modules from non-Hygienic to hygienic or vice versa, or modifying one or more of the schemas involved. When modifying schemas is not feasible, consider using hygienic modules and interfaces that define capture fields.