Starting with version 0.5 of the Logic Module, users may define rules, which are saved in the database. The logic module has built-in support for writing rules in Groovy and Java, while other modules may add other languages by overriding the org.openmrs.logic.rule.definition.LanguageHandler interface.
At present you have to look in your server logs to see compile errors if you've written a rule incorrectly.
Groovy Rules
When defining a Groovy rule, you are defining the contents of the rule's eval method. Precisely, the code you are writing is enclosed in
Code Block |
---|
|
import java.util.Map;
import org.openmrs.Patient;
import org.openmrs.logic.*;
import org.openmrs.logic.rule.*;
import org.openmrs.logic.result.*;
public class GENERATED-NAME extends AbstractRule {
public Result eval(LogicContext context, Integer patientId,
Map<String, Object> parameters) throws LogicException {
// YOUR-CONTENT-INSERTED-HERE
}
} |
...
Code Block |
---|
|
def square = { x ->
x * x
}
def myString = [2, 4, 6].collect { "${ it } squared is ${ square(it) }" }.join("\n")
return new Result(myString) |
A more useful rule, to fetch the patient's age, would be:
Code Block |
---|
|
return new Result(context.getPatient(patientId).getAge(context.indexDate))
|
Here's a verbose version of that same age logic
Code Block |
---|
|
/*
* In order to add as little overhead as possible, allowing rules to be run
* relatively efficiently on very large cohorts, the rule framework does not
* automatically provide us with a Patient object, but just a patientId.
* This line fetches that Patient object. (It actually fetches all patients
* in the cohort the rule is being evaluated on.)
*/
def patient = context.getPatient(patientId)
/*
* We want this rule to work correctly if you evaluate it as-of some other
* date. So we fetch the index date from the LogicContext. "context.indexDate"
* is groovy shorthand for "context.getIndexDate()"
*/
def age = patient.getAge(context.indexDate)
/*
* We need to wrap our returned value in a logic Result.
*/
return new Result(age)
|
Java Rules
These "work", but are very hard to use. (Why A later logic module release will make these easier to use. (But why not use Groovy instead? It's better...)
...
For example, the following would work (if it is the rule with id=3):
Code Block |
---|
|
package org.openmrs.module.logic.rule;
import java.util.Map;
import org.openmrs.Patient;
import org.openmrs.logic.*;
import org.openmrs.logic.rule.*;
import org.openmrs.logic.result.*;
public class CompiledRule3 extends AbstractRule {
public Result eval(LogicContext context, Integer patientId,
Map<String, Object> parameters) {
return new Result("I would recommend Groovy instead");
}
}
|