Modules

Overview

The first step in understanding the Niagara architecture is to grasp the concept of modules. Modules are the smallest unit of deployment and versioning in the Niagara architecture. A module is:

Versions

Versions are specified as a series of whole numbers separated by a period, for example "1.0.3042". Two versions can be compared resulting in equality, less than, or greater than. This comparision is made by comparing the version numbers from left to right. If two versions are equal, except one contains more numbers then it is considered greater than the shorter version. For example:

  2.0 > 1.0
  2.0 > 1.8
  2.0.45 > 2.0.43
  1.0.24.2 > 1.0.24

Every module has two versions. The first is the "bajaVersion" which maps the module to a Baja specification version. If the module is not published under the Baja process then this value is "0". Secondly every module declares a "vendor" name and "vendorVersion". The vendor name is a case insensitive identifier for the company who developed the module and the vendorVersion identifies the vendor's specific version of that module.

Tridium's vendorVersions are formatted as "major.minor.build[.patch]:

So the vendorVersion "3.0.22" represents a module of build 22 in Niagara release 3.0. The vendorVersion "3.0.45.2" is the second patch of build 45 in release 3.0.

Manifest

All module JAR files must include a manifest file in "meta-inf/module.xml". The best way to examine the contents of this file is to take an example:

<?xml version="1.0" encoding="UTF-8"?>
<module
  name = "control"
  bajaVersion = "1.0"
  vendor = "Tridium"
  vendorVersion = "3.0.20"
  description = "Niagara Control Module"
  preferredSymbol = "c"
>

<dependencies>
  <dependency name="baja" vendor="Tridium" vendorVersion="3.0"/>
  <dependency name="bajaui" vendor="Tridium" vendorVersion="3.0"/>
  <dependency name="bql" vendor="Tridium" vendorVersion="3.0"/>
  <dependency name="gx" vendor="Tridium" vendorVersion="3.0"/>
  <dependency name="workbench" vendor="Tridium" vendorVersion="3.0"/>
</dependencies>

<dirs>
  <dir name="javax/baja/control" install="runtime"/>
  <dir name="javax/baja/control/enum" install="runtime"/>
  <dir name="javax/baja/control/ext" install="runtime"/>
  <dir name="javax/baja/control/trigger" install="runtime"/>
  <dir name="javax/baja/control/util" install="runtime"/>
  <dir name="com/tridium/control/ui" install="ui"/>
  <dir name="com/tridium/control/ui/trigger" install="ui"/>
  <dir name="doc" install="doc"/>
</dirs>

<defs>
  <def name="control.foo" value="something"/>
</defs>

<types>
  <type name="FooBar" class="javax.baja.control.BFooBar"/>
</types>

<lexicons brand="*">
  <lexicon module="bajaui" resource="fr/bajaui_fr.lexicon" language="fr"/>
</lexicons>

</module>

Looking at the root module element the following attributes are required:

All modules must include a dirs element, which contains a dir subelement for each of the module's content directories. Each dir has a name attribute which contains a system-home relative file path for a directory in the module, and an install attribute which has one of the following values:

All modules include zero or one dependencies element. This element contains zero or more dependency elements which enumerate the module's dependencies. Dependencies must be resolved by the framework before the module can be successfully used. Each dependency has one required attribute. The name attribute specifies the globally unique name of the dependent module. A dependency may also specify a bajaVersion and/or a vendor version. If the bajaVersion attribute is declared then it specifies the lowest bajaVersion of the dependent module required. It is assumed that higher versions of a module are backward compatible, thus any version greater than the one specified in a dependency is considered usable. Likewise the vendor and vendorVersion may be specified to declare a dependency on a specific implementation of a module. The vendor attribute may be specified without the vendorVersion attribute, but not vise versa. The required embed attribute specifies whether the dependency should be enforced on embedded Niagara devices.

Modules can declare zero or more def elements which store String name/value pairs. The defs from all modules are collapsed into a global def database by the registry.

Modules which contain concrete Niagara BObjects also include a types element. This element includes zero or more type elements. Each type element defines a mapping between a Baja type name and a Java class name. This definition is specified in the two required attributes type and class.

Modules can declare zero or one lexicons element, which contains zero or more lexicon elements. The lexicon has an optional brand attribute which filters lexicon file usage based on brand. The value of this attribute may contain "*" (string) or "?" (single character) wildcards. Each lexicon will associate a resource file containing lexicon properties with a specific module. Typically modules containing lexicons will not contain other elements, but it is possible to include lexicon files in any module. Lexicon information is loaded into a global lexicon database by the registry. This data is used by the lexicon system to apply locale-specific elements (text, icons, etc.) as needed.