Calculated fields in Ardoq makes it possible to collect and process information across everything you have stored in Ardoq, and store the result as a field value on components and references. The calculated value is read-only, but apart from that, it behaves like any other Ardoq field. Calculated field values can be used for filtering, grouping and conditional formatting as you can with regular Ardoq field values.

In our APM bundle, we use a calculated field to weight and sum the six underlaying dimensions for business and technical fit into two dimensions for display in a Gartner TIME quadrant. In our upcoming Risk analysis, the risk score will be based on calculated fields.

All calculations are scheduled to run nightly. You can also trigger calculations manually via the calculation editor, the sidebar menu (workspace options), or the Ardoq API.

Setting up a calculated field

NB 1! Creating a calculated field involves Gremlin graph queries code. If you need to read up on that, here is a good place to start. You can also copy/paste from the examples below, if you find an example that is close to what you're trying to achieve.  

NB 2! Since calculated fields are based on graph queries, and these have access to the whole graph, you need to be an Ardoq organization-admin to configure calculated fields.

Step 1: Create the field

Open the sidebar menu on the right, choose the "Workspace" section, then "Manage Field Types". Click "Add Field". Select "Calculated number" from the bottom of the field type list.

Step 2: Select where the field should apply

Step 3: Create the field

This will take you to a Gremlin Query editor.

Step 4: Edit the query 

Calculations are performed in the Ardoq Graph Engine and are programmed in the graph query language Gremlin.
NB! All calculated field queries start have the first line injected with an array of all the IDs of the components or references the field applies to. This serves as a starting point for the traversal.

It is recommended to not modify the code on lines 0 to 4 shown above. Because the calculations are expected to be in the format seen below, you typically only need to modify the last line (the value-calculation).

Calculated fields expect a return value of this shape:

[
{"id": "<component-id-1>", "value":1},
{"id": "<component-id-2>", "value":2}
]

Step 5: Test, save and apply the query

Once you've modified the query to your liking, test the calculation, and then try to apply it. If there are no warnings, save and exit the editor. 

The calculation will run every night, and you can trigger it from the Workspace sidebar when the workspace is open.

Example queries

This example uses a function to calculate risk, using an existing "risk factor" value for components:

def riskCalculator = {
  component = it.get()
  if (component.property("risk_factor").isPresent()) {
    component.property("risk_factor").value() > 5 ? "high" : "low"
  } else {
    "none"
  }
}

g.V(ids)
.project('id', 'name', 'value')
.by(id)
.by('name')
.by(map(riskCalculator))

This example aggregates cost one level up to the components the calculated field applies to (in this case we set the field to apply to Applications), showing graph traversals can be performed:

g.V(ids).
  project('id', 'name', 'value').
    by(id).
    by('name').
    by(inE().hasLabel('Relates to').otherV().values("cost").sum())

The following example provides a more flexible query that traverses the graph, collecting the cost of all components encountered along the way. Here we only go in one reference-direction, meaning components must have an outgoing reference towards the component that has this calculated field:

g.V(ids).
  project('id', 'name', 'value').
  by(id).
  by('name').
  by(emit().repeat( // Emit includes all components encountered
    inE().otherV()
    ).timeLimit(1000).dedup() // remove duplicate components
    .values("cost").sum() // sum up cost of all found components
  )

FAQ

What is the "ids"-value used for?

The "ids"-value is automatically generated and contains the unique ids of all components and/or references the calculated field is set to apply to. This means that you can modify the field so that it applies to a different set of references or components, without modifying the query.

Why are my calculated fields not showing in the "editor/views"? 

This is likely because of values returned by the query. Calculated number-fields, for example, expects a number to be returned. For instance, this query for a calculated number will fail:

[
  {"id": "fb3f69b7798", "value": 1234}, <--- OK, NUMBER 👍
  {"id": "86e95ce6b5c", "value": "high"}, <--- NOT A NUMBER 👎
]

Please ensure all values returned matches the field type (calculated number, calculated text, calculated date time, calculated checkbox (boolean))!

Can I reuse the calculated field?

By "reuse", we mean modifying the field to apply to new component or reference types. This is possible, but if you want to do so, you must ensure that the query is not too specific. For example, if the query is written to traverse the graph via specific reference types, the query might not work for other component types that don't have connections using the same reference type.

Why is my calculated query missing/deleted? 

If the field the calculated query is connected to is removed, the query will also be deleted.

Did this answer your question?