Tutorial: Hardware Management
This tutorial explains how to build a mobo development model for IT hardware management.
For the final and more complete result, please review the hardware management example.
Set up new project
Create a new empty project and adjust your settings.yaml. Please refer to the manual how do this.
Run mobo the first time
Now run mobo the first time and check that the settings are correct and the upload to the external wiki is working. At your localhost:7000 should be a web application ready.
Conceptualization of the model and its domain
Before heading into the actual model development, some thought should be put into how the domain should be modeled.
Hardware is deployed at Locations
.
There are several types of hardware, like NetworkPrinter
, MultiFunctionUnit
, Workstations
, etc.
Those must be respectivly splitted into -models (the general hardwaremodel) and -installations
(the concrete installation and configuration on a location).
Hardwaremodels can have a Manufacturer
and hardwareinstallations are tied to a location.
The different hardwaremodels will likely share some attributes, so an abstract _HardwareModel
will come in handy.
The same is true for an abstract _HardwareInstallation
.
Creating a location
Create model
Let's start with the simplest part of the model, the location. Personally I do like to start with the model and create the fields and forms afterward. There is no right and wrong with the order, however.
Create /model/Location.yaml
with the following content:
title: Location
description: Location where hardware is deployed
items:
- $extend: /field/streetAdress
- $extend: /field/streetNumber
- $extend: /field/town
- $extend: /field/country
required:
- streetAdress
- streetNumber
- town
Once the file is saved, mobo will automatically run and give some feedback:
[E] (unknown): invalid $extend to missing "/field/streetAdress"!
[E] (unknown): invalid $extend to missing "/field/streetNumber"!
[E] (unknown): invalid $extend to missing "/field/town"!
[E] (unknown): invalid $extend to missing "/field/country"!
[W] /model/Location.yaml is never used.
Create fields
To keep the model better organized, the Location related fields will be stored at /field/Location/*
.
Important Please note that the $extend
path does not include subfolders.
Create /field/Location/streetAdress.yaml
with the following content:
title: Street Adress
type: string
This is the simplest possible field. Only the title and the type is mandatory.
Now create /field/Location/streetNumber.yaml
with the following content:
title: Street Number
type: number
minimum: 0
We've just introduded some basic validation. The Street number should be a number of at least 1.
Create /field/Location/town.yaml
with the following content:
title: Town
type: string
sf_form:
input type: text with autocomplete
Since towns may be referenced more than once, it makes sense to provide autocomplete capabilities.
This is done by setting the sf_form
property,
declaring Semantic Forms settings.
Create /field/Location/country.yaml
with the following content:
title: Country
type: string
enum:
- USA
- UK
- Germany
default: Germany
We want to support only three countries, so an enum is a good solution.
In this field three countries are given and one is set as default.
Enum fields will be displayed as a dropdown menu by default.
If you want to change the widget, use the sf_form
property as learned before.
Create form
The last warning message is giving the hint that model/Location.yaml
is never used:
[W] /model/Location is never used.
This is because there is no form that is including it.
Create /form/Location.yaml
with the following content:
title: Location
items:
- $extend: /model/Location
This is the simplest possible form, referencing the previous model as its sole content. We can now head to the wiki and try the form in action:
Create a HardwareModel
Create models
In the next step, the NetworkPrinterModel
will be created.
It is of the type HardwareModel
and will use object-oriented inheritance.
Create /model/HardwareModel/_HardwareModel.yaml
with the following content:
$abstract: true
title: Hardware Model
items:
- $extend: /field/brand
- $extend: /field/modelName
required:
- brand
- modelName
The abstract model contains two required fields that will be shared by all other Hardware Models.
Since it's defined as $abstract: true
, it will not be created in the wiki.
Create /model/HardwareModel/NetworkPrinterModel.yaml
with the following content:
$extend: /model/_HardwareModel
title: Network Printer Model
description: A Network Printer Model
items:
- $extend: /field/colorPrinting
itemsOrder:
- brand
- modelName
The NetworkPrinterModel
used $extend
to inherit all attributes from the _HardwareModel
.
It overwrites the title attribute and adds a description and the colorPrinting
field.
The colorPrinting
field will by default appear as the first field on the form since it's most recently added.
To keep the brand and modelName on top, the order of the properties has to be set manually.
Please note that not all existing properties have to be included.
Those missing will be added below in their original order.
Create fields
The creation of the fields will be skipped, since they contain no new concepts. Please refer to the example files instead.
Create form
Please refer to the example files.
Create a HardwareInstallation
Create models
Now the actual NetworkPrinterInstallation
can be created.
Create /model/HardwareInstallation/_HardwareInstallation.yaml
with the following content:
$abstract: true
title: Hardware Installation
items:
- $extend: /field/serialNumber
- $extend: /field/freetext
smw_subobject: true
smw_category: false
Since there are Hardwaredevices that are network capable and share therefore some more common properties,
another abstract model will be created that inherits from the HardwareInstallation
.
The property smw_subobject
declares that Hardware Installations will store their semantic properties as subobjects.
This is necessary becasuse we want to define multiple instances of them on a location and the attribute names would duplicate otherwise.
Create /model/HardwareInstallation/_NetworkDeviceInstallation.yaml
with the following content:
$abstract: true
$extend: /model/_HardwareInstallation
title: NetworkDevice Installation
items:
- $extend: /field/ip
recommended:
- ip
Create /model/HardwareInstallation/NetworkPrinterInstallation.yaml
with the following content:
$extend: /model/_NetworkDeviceInstallation
title: Network Printer Installation
items:
- $extend: /field/networkPrinterModel
The NetworkPrinterInstallation
extends from the _NetworkDeviceInstallation
(which itself extends from _HardwareInstallation
) and will define it's network printer model.
Create fields
The field networkPrinterModel
will reference to a NetworkPrinterModel
.
Create /field/HardwareInstallation/_hardwareModelReference.yaml
with the following content:
$abstract: true
title: Model
description: You may only select already existing mardware models!
type: string
sf_form:
max values: 1
input type: combobox
existing values only: true
All hardware model reference fields will now use the input type combobox and allow only one (already existing) value.
Create /field/HardwareInstallation/networkPrinterModel.yaml
with the following content:
$extend: /field/_hardwareModelReference
# Implicit: type: string and format: Page
form: NetworkPrinterModel
sf_form:
values from category: NetworkPrinterModel
This field uses the form
property to defines the NetworkPrinterModel
form as its target.
If the form
property is used, the type
will always be string
and the format
is set to Page
.
This results in a red wiki link that if clicked upon uses the given form to create it by default.
Because it uses implicitly the format "Page", it will be a wiki link.
The values from category
setting will ensure that the combox widget will autocomplete on all previous entered NetworkPrinterModel
.
Extend the location form to include Network Printers
Network Printers should be added at locations through Semantic Forms multiple instance templates.
Add to the existing /form/Location.yaml
the following content:
title: Location
description: This creates a new location where hardware is deployed.
items:
- $extend: /model/Location
- $extend: /smw_template/NetworkPrinterHeader
- type: array
items:
$extend: /model/NetworkPrinterInstallation
Two new $extend
are added.
First, a wikitext template from the folder smw_template
is included.
It will provide a header and is shown in both form and page view:
Create the template at /swm_template/Headers/NetworkPrinterHeader.wikitext
:
NOTE: Don't forget to add a new line after the headline! Wikitext is whitespace sensitive - you might break functions/layout by ommitting whitespaces.
=Network Printer=
The second $extend is an array which contains multiple NetworkPrinterInstallation
and will be implemented as the already mentioned Semantic Forms multiple template instance.
TIPP: You don't need to explicitly define the type
as array, since the existence of items
already implies this.
This is sufficient:
- items:
$extend: /model/NetworkPrinterInstallation
The final form will now look like this:
Create an ASK Query with mobo
Create /smw_query/NetworkPrinterModels.yaml
with the following content:
{{#ask: [[category:NetworkPrinterModel]]
| ?brand
| ?modelName
| limit=999
}}
This will cause mobo to generate the query as a new template with the pagename Template:NetworkPrinterModels-ask
.
If you head there, you will find a small usage snippet for embedding, the query text documented and a live query.
The live query may not work if it's dependend on a specific context, though.
It might make sense to include this query in the already generated Category:NetworkPrinterModel
.
To do this, we need to overwrite the generated wikipage. This can easily be done by creating a .wikitext file in the smw_page
directory:
Create /smw_page/Overwrite/Category___NetworkPrinterModel.wikitext
with the following content:
{{#ask: [[category:NetworkPrinterModel]]
| ?brand
| ?modelName
| limit=999
}}
Note that we can't use :
in filenames, so we have to replace it with ___
.
Now we've overwritten the generated category and embedded our new query in it.
Excourse: Using HeaderTabs Extension
In case the forms are getting more complex, it might be a good idea to seperate them into tabs. The HeaderTabs Extension is supported by mobo.
The support can be enabled in the projects settings.yaml
by adding:
headerTabs: true
The NetworkPrinterHeader
already defines a heading, but the Location model is missing one.
It would be possible to add the header the same way but for single instance templates its more convenient to use mobos "swm_prefix" feature:
Append to your /model/Location.yaml
the following content:
# Prepends a h1 header to both form and page display
# After the header, adds arbitrary wikitext
smw_prepend:
header: 1
wikitext: Some prefix-description for the location
The smw_prepend
property allows to prepend automatically generated headers
(using the title property as name and defining the hierachy through the number),
templates or free wikitext before the template. (There's a smw_append
property, too)
Now the Location form has got two headings of hierachy one. The HeaderTabs Extension will become active: