How it Works
Contents
Even though SIL™ works just fine as a standalone scripting language outside Jira (for example our installers use SIL™ to copy the apps to your Jira directory), but it really makes a difference inside Jira.
Architecture
The SIL™ language is actually independent from Jira. It can be used for any purpose, for instance to be applied for Confluence. It can be applied for anything. On top of the basic interpreter we've also added a Jira specific interpreter that predefines the standard variables, the key variable for instance that represents the key of the issue.
Jira SIL™ interpreter basically extends the capabilities of the standard interpreter. The standard SIL™ Interpreter provides a registry for all functions and the Issue SIL™ Interpreter adds the additional functions into this registry including Jira interactions.
Contexts
Just like any other programming language, a standalone SIL™ program contains variables, functions, and conditional and repetitive clauses. Putting this inside a Jira context enables you to use Jira related functions like createIssue or linkIssue (so the script "has Jira context"). Adding an issue context inside the Jira context (so the script "has an issue context"), enables you to use field values stored on the issue, regardless of whether they are standard fields like summary, description, assignee, or custom fields.
These will be predefined and ready to be used without any need for variable definition. When the interpreter finds a variable, it looks for it similar as any other language would. Each block of code is a variable context. Nested blocks will push these contexts to a stack. When looking for a variable, it starts from the current block of code and moves down the stack. If the variable is not found, it will attempt to match it against the fields on the issue (consider this at the bottom of the stack). Let's make it visual using pseudocode.
Outside Jira | Inside Jira |
---|---|
start block // context_0 - this is your program
declare variable a;
start block // push context_1
declare variable b;
start block // push context_2
declare variable c;
use variable b; // from context_1
end block // pop context_2
// no more variable c here
end block // pop context_2
// no more variable b here
end block
| start block // JIRA context
// defines JIRA-related functions like createIssue(...)
start block // issue context - transparent to the user
// this context contains the issue field definitions
// you can imagine this contains instructions like
// string summary = "the summary of the issue";
start block
// context_0 - this is your program
declare variable a;
start block // push context_1
declare variable b;
start block // push context_2
declare variable c;
use variable b; // from context_1
end block // pop context_2
// no more variable c here
end block // pop context_2
// no more variable b here
end block // this is the end of the program
// behind-the-scene post-processing
end block // pop the issue context
end block // pop the JIRA context |
You might notice that SIL™ works mostly the same inside and outside of an issue context. The two additional contexts (Jira and issue) bring more functionality that you can instantly use inside your program.
The context rule
All scripts used by our Jira apps have Jira context, but not necessarily an issue context. This is important because without an issue context you will not be able to use such variables like summary, assignee, or custom fields right away.
Post processing
Note when running inside a Jira context, there is a step called "behind-the-scene post-processing". During the interpretation of the script, the SIL Engine™ (or Interpreter) creates volatile clones (not persistent) of all issues that were modified and the respective changes. This enables us to control the following aspects of a program:
Should the program be read-only? If a program is read-only like a workflow condition or a validator, then the changes recorded by the Interpreter will not be persisted to the database / index. Otherwise, the "behind-the-scene post-processing" will ensure that all the recorded changes are persisted to the database / index.
What happens in case of an error? If a program throws an exception, we do not want to corrupt the issue data by storing only the changes that were made before the error occurred, so we just throw it all out and report the error, leaving the issue as it was.
Functions exception
At the moment certain functions (like createIssue) cannot be undone automatically and will persist their changes regardless of whether the script was read-only or if there was an error.