ADOxx AdoScript Extension
The extension focuses on the static aspects of the AdoScript language and others used by the ADOxx platform, providing syntax highlighting, code snippets, comment toggling, code block folding and specific editors.
The syntax highlighting focuses on recognizing the right concepts and displaying them according to the used theme. Additionally it tries to identify illegal code where possible and mark it accordingly, like use of variables where they aren't allowed or having lower-case characters in a procedure name.
Authors / Contributors
- Patrik Burzynski (coordinator)
- Vicente Ferrari
- Sunghyun Lee
- Junsup Song
- Wilfrid Utz
ToC
Features
- Highlighting of, AdoScript code, LEO programs, ADOxx Query Language (AQL) and the ADOxx Library Language (ALL), with some help for noticing errors: if something isn't highlighted properly or even marked as illegal then there's probably some syntax error, like missing closing brackets or unintentional escaping of double quotes. Note: the debug modifier is marked as illegal.deprecated so it can be quickly identified in the code.
- Any LEO-program (e.g. GRAPHREP, ATTRREP, EXPRESSION-type attributes etc.) now has basic code highlighting as long as it doesn't deviate from the LEO grammar. Bracketed LEO expressions can also be directly used for code highlightin.
- Additionally AdoScript specific code highlighting is provided for its additional keywords and API-commands.
- An editor and syntax highlighting for AQL queries is available.
- Basic syntax highlighting for ADOxx Library Language or parts of it.
- Code snippets for typical LEO and AdoScript patterns, like conditional or loop statements and the AdoScript message port calls. All snippets in alphabetical order:
- AdoScript - ccacq, ccado, ccana, ccapp, ccaql, cccore, cccui, ccdb, ccdoc, ccdraw, cceval, ccexp, ccimp, ccmod, ccsim, ccuser, fornum, fortok, else, elsif, if, while
- LEO - cond, fornum, fortok, while
- Support for other common features like bracket matching / autoclosing, comment toggling, folding etc.
(back to ToC)
Use
Syntax Highlighting
Features for syntax highlighting are available by using files with the specific extensions (.asc for AdoScript, .leo for LEO, .aql for AQL, .all for ALL) or explicitly setting the used language for a file.
AQL Query Editor
The AQL Query editor is available through the "AQL Query Editor: Start the Query Editor" command, accessible using the Command Palette or using the default shortcut Ctrl+Shift+A. This will open a new separate window with the editor. Any selected code, like an already available AQL query string, will be copied into the editor where it can be adapted.
The "Insert AQL" button will replace the curent selection in the origin2al window, ensuring that characters are properly escaped. The "Generate AQL String button writes the AQL query as a string with characters escaped where necessary into the field below, ready to be copied and pasted into the AdoScirpt code.
It is possible to write variables as placeholders in the query using a syntax like ${variablen-name}$ . Variables found in the file are made available in the editor through the "Show/Hide Variables" button.
(back to ToC)
The Short Version of Recommendations and Restrictions
Add theme customization for AdoScript specific concepts through local settings. More about how, what and some settings that can simply be copied are found under Recommendations.
Four restrictions have to be considered when writing AdoScript code with this Extension (more details can be found under Restrictions:
- Only use the "new" style of IF-ELSIF-ELSE with curly brackets (
IF (...) { ... } ELSE { ... } ).
- Avoid using built-in variable / function names (lower-case identifiers), keywords and API-commands (upper-case identifiers) for self defined variables, functions and procedures.
- Don't split a parameter definition / assignment (
name:type , type:name , get-str-value:fname:"firstname" ) into several lines. It's fine to put different parameter definitions / assignments in separate lines or split a bracketed LEO expressions into several lines.
- When using
CC "Application" EXIT then write it in one line.
(back to ToC)
Recommendations
The syntax highlighting assigns scopes to the different parts of the code, which are then colored and styled according to the selected theme. While the syntax highlighting mostly relies on scopes commonly found in the available themes, it is possible to further fine-tune some of the formatting to better visualize some of the special AdoScript cases.
It is not necessary to directly edit the used themes, since own customizations can be provided through the settings JSON file (settings.json accessible through the command palette, F1 or CTRL+SHIFT+P on Windows). There the editor.tokenColorCustomizations key can be used to specify text colors and styles for the different scopes which are then applied on top of the used theme. See below for a recommended code snippet that formats built-in functions, procedures and the debug modifier in italics and the TODO in comments in bold.
More information on what scopes are made available by the syntax highlighting and for which parts of code can be found under Used Syntax Highlighting Scopes.
{ // Copy into settings.json
"editor.tokenColorCustomizations": {
"textMateRules": [
{
"name": "built-in LEO functions",
"scope": [
"support.function",
"keyword.operator.new"
],
"settings": { "fontStyle": "italic" }
}, {
"name": "API-commands in AdoScript",
"scope": "support.function.api-command",
"settings": { "fontStyle": "italic" }
}, {
"name": "the debug modifier",
"scope": "invalid.deprecated.debug",
"settings": { "fontStyle": "italic" }
}, {
"name": "the TODO in comments",
"scope": "comment.todo",
"settings": { "fontStyle": "bold" }
}
]
}
}
While the style for support.function applies to both the built-in LEO functions and the API-commands, the more specific support.function.api-command scope is also added to allow applying a different style for API-commands.
(back to ToC)
Restrictions
Don't worry, there's a lot of text, but it's only just 4 easy to follow restrictions.
The syntax highlighting can't cover everything that is technically allowed as valid code in AdoScript, due to how the two systems work. However, some of the cases that can't be covered by this extension could be regarded as bad practices and should be avoided. To ensure that everything works fine please consider the following list as a set of best practices when writing AdoScript code using this extension:
- Only the new style of IF-ELSIF-ELSE using curly brackets is supported (
IF (...) { ... } ELSE { ... } ).
- Don't use any of the data type names (like
integer , reference , map etc.) or built-in function names (aappend , array , map , abs , cond , lower , etc.) as the exact identifier for your variable or function (lower-case identifiers). Also try to avoid using variable names that are used as parameters or return values (objid , objids , attrid , return , result etc.). While the code might work in some or even most cases, there is the danger that your variable will be overwritten by a command (for example a CC ). For procedures avoid any exact matches with names used by an available API-command (upper-case identifiers, INFOBOX , GET_ATTR_VAL , EVAL_AQL_EXPRESSION etc.). Consider using meaningful prefixes in the names / identifiers you assign. See the following good and bad examples:
# Good examples:
SETL int_count:(10)
SETL map_message:({"header": {"Content-Type": "text/plain"}, "body": "..."})
SETL i:0
SETL str_name:"AdoScript"
FUNCTION my_token:global src:string tok:integer return:((* code ... *))
FUNCTION array_init_zeroes return:((* code ... *))
PROCEDURE BEEUP_INFOBOX { (* code ... *) }
# Bad examples:
SETL reference:(3)
SETL abs:("absolutely")
SETL type:("AB+")
FUNCTION token:global src:string tok:integer return:((* code ... *))
FUNCTION array return:((* code ... *))
PROCEDURE INFOBOX { (* code ... *) }
- Definition of or value assignment to a parameter (for procedures, functions, basic commands like
SEND and CALL etc.) should not be split into several lines. Basically this means that definitions like name:type or type:name or for example the LEO parameters like get-str-value:fname:"firstname" should be in the same line. Putting different parameter definitions / assignments in separate lines or spreading a bracketed LEO expressions among several lines is however fine. Consider the following good and bad examples:
# Good examples:
PROCEDURE MY_PROCEDURE integer:int_main str_separator:string {
(* code ... *)
}
PROCEDURE MY_OTHER_PROCEDURE string:str_main
int_from:integer
int_to:integer
{
(* code ... *)
}
MC_OTHER_PROCEDURE ("imagine this string " +
"being too long for " +
"one line")
# Bad examples:
PROCEDURE MY_OTHER_PROCEDURE string:
str_main
int_increment:
integer
{
(* code ... *)
}
- When using
CC "Application" EXIT write the API-command in the same line as the CC if you want it to highlight properly. This is necessary, because AdoScript uses EXIT both as an API-command (exit the application) and a normal command (exit a code block / script). Putting the API-command in the same line allows to distinguish the two from one another. Consider the following good and bad examples:
# Good examples:
CC "Application" EXIT
CC "Application" debug EXIT
# Bad examples:
CC "Application"
EXIT
CC
"Application"
EXIT
(back to ToC)
Requirements
Currently there are none. AdoScript knowledge helps though.
(back to ToC)
Extension Settings
Currently there are none.
(back to ToC)
Known Issues
- More complex LEO grammar: The documentation mentions some additional parts for the "LEO grammar" for which we currently don't know any cases or are unsure about. They have been skipped for now since we don't quite know where to use them. Kindly help us understand these better or even provide some cases and examples for them. These include:
- Function calls with more parameters beyond the normal brackets. According to the grammar they would look something like
function(para1, para2, ...) {expr1} {expr2, expr3, ...} (expr4) {expr5, ...} ... . The parts in questions are after the first (para1, para2, ...) list and are basically an unrestricted amount of lists in curly or round brackets containing comma separated expressions.
(back to ToC)
Release Notes
See changelog for details on minor releases (increasing the right most number).
1.2.0
Added support for the ADOxx Query Language (.aql files) and an AQL editor. Bug fixes.
1.1.0
Added support for the ADOxx Library Language (.all files). Bug fixes.
1.0.0
Initial release, providing syntax highlighting, code snippets and other basic features for both LEO programs (.leo files) and AdoScript (.asc files).
(back to ToC)
Used Syntax Highlighting Scopes
The following scopes are set by this extension for code highlighting and can be used for further customizing of a theme. It's easiest to think of a single scope as multiple classes in CSS. Therefore, when providing a style it is usually enough to only provide a part of the scope. For example constant.numeric would apply to decimals, hexadecimals, measures and time/durations unless there is a more specific style overriding it, like constant.numeric.hex for hexadecimals. Additionally several scopes can apply to the same part of the code, especially when it is nested. For example the 9 inside of (sqrt(9)) has the scopes (from highest to lowest priority): constant.numeric.decimal.leo, meta.call.function.built-in.leo, meta.embedded.leo-expression.leo and source.leo assigned to it.
(... I also might've gone a bit mental with the meta scopes ...)
The lists are sorted in alphabetical order.
LEO
Note: all of the scopes end with .leo which will be omitted in the following list.
Note: meta. generally covers the entire part of a specific code structure from start to finish (e.g. entire function call including parameters).
- comment.block - a multi-line comment
- comment.line.number-sign - single line comment
- comment.todo - the TODO keyword in a comment
- constant.character.escape - the escape character used in strings
- constant.language.modifier.assignment - used for modifiers used in a variable assignment.
- constant.numeric.decimal - a constant decimal number (e.g. 3, 5.3)
- constant.numeric.hex - a constant hexadecimal number (e.g. $6fa)
- constant.numeric.measure - a numeric constant denoting a measure (e.g. 3cm)
- constant.numeric.time - a numeric constant denoting a time or duration (e.g. 0:002:12:30:02)
- entity.name.function - the name of a non-built-in function
- invalid.illegal - anything that seems to be something that's not allowed at the place it is
- keyword.control.pass-on - the one commands that pass on the control flow to a different part of code (i.e. @INCLUDE)
- keyword.operator.new - functions for creating more complex values (arrays(), maps(), lambdas())
- keyword.operator.arithmetic - arithmetic operators including the unary negation (e.g. +, -, *)
- keyword.operator.comparison - operators for comparison (e.g. =, <>, <)
- keyword.other - the keywords used in a LEO program
- meta.call.function - the entire call of a function, especially non-built-in functions
- meta.call.function.built-in - the entire call of a built-in function, including parameters etc.
- meta.definition.body - the body that can be part in a LEO Program
- meta.definition.sequence - the entire direct definition of an array or map, which uses curly brackets
- meta.embedded.leo-expression - an entire embedded "LEO sub-expression" inside of another LEO expression, generally between two round brackets
- meta.subscription - the entire subscription for an array or map including any contained expression through square brackets
- punctuation.section.block.begin - the { at the beginning of a body block
- punctuation.section.block.end - the } at the end of a body block
- punctuation.section.comment.begin - characters indicating the start of a multi-line comment
- punctuation.section.comment.end - characters indicating the end of a multi-line comment
- punctuation.section.comment.line - character indicating the start of a line comment
- punctuation.section.expression.begin - the ( at the beginning of an embedded "LEO sub-expression"
- punctuation.section.expression.end - the ) at the end of an embedded "LEO sub-expression"
- punctuation.section.parameters.begin - the ( at the beginning of a function's parameters list
- punctuation.section.parameters.end - the ) at the end of a function's parameter list
- punctuation.section.sequence.begin - the { at the beginning of an array or map definition
- punctuation.section.sequence.end - the } at the end of an array or map definition
- punctuation.section.subscription.begin - the [ at the beginning of a subscription for an array or map
- punctuation.section.subscription.end - the ] at the end of a subscription for an array or map
- source - anything that's considered a LEO expression
- string.quoted.double - a string using double-quotes
- string.quoted.double.begin - the beginning double-quote of a string
- string.quoted.double.end - the ending double-quote of a string
- support.function.arithmetic - arithmetic functions (e.g. CEIL, FLOOR, MOD, sin(), cos(), max())
- support.function.assignment - the single function used to assign values to a variable (set())
- support.function.color - functions that deal with the manipulation of color values (e.g. byte(), hsv2rgb())
- support.function.control - functions that behave like control structures (e.g. cond(), while(), for())
- support.function.conversion - functions for conversion of values (e.g. STR, VAL, CM, toutf8(), base64encode())
- support.function.dynamic - functions for dynamically getting information about the executed code, kind of like reflection (e.g. curlineno(), eval())
- support.function.error - functions for handling errors (error(), try())
- support.function.logical - logical operators more reminiscent of functions (AND, OR, NOT)
- support.function.other - functions that didn't fit any of the other types (e.g. getTickCount(), set())
- support.function.sequence - functions that are used for "sequence" data-types, like arrays, maps and strings (e.g. aappend, merase, .length)
- support.function.string - functions specifically for strings (e.g. search, token, tokcat)
- variable.other - the identifier of a variable, which is used as a parameter in a function that's pretty much the only place a variable is used in a LEO expression
- variable.parameter.assignment - the name of a parameter that gets a value assigned and isn't directly provided by the language (e.g. assignment of parameters for a self defined procedure)
AdoScript
Note: AdoScript code can contain LEO expressions at many places and thus it is possible to encounter all of the scopes used in LEO where constants, strings, expressions or comments are encountered. For example single-line comments in AdoScript get the comment.line.number-sign.leo scope assigned.
Note: all of the scopes end with .asc which will be omitted in the following list.
Note: meta. generally covers the entire part of a specific code structure from start to finish (e.g. entire function call including parameters, entire procedure definition including the body).
- constant.language.assignment - constants used to be assigned to specific command parameters (e.g. child, same, separate for scope of EXECUTE)
- constant.language.system - constants used as flags to modify the behavior of the SYSTEM command
- entity.name.function - the name of a non-built-in function
- entity.name.function.procedure - the name of a non-built-in procedure (under this scope because procedures behave like functions in other languages)
- invalid.deprecated.debug - used to distinguish the debug modifier from its surroundings
- invalid.illegal - anything that seems to be something that's not allowed at the place it is
- keyword.control.internal - commands that control the flow inside the code without really passing it outside of the execution scope (e.g. IF, ELSE, FOR, WHILE, NEXT, BREAK)
- keyword.control.pass-on - commands that pass on the control flow to a different part of code or entity (e.g. START, EXIT, CC)
- keyword.other.assignment - commands that deal with assigning values to variables (SET, SETL, SETG, LEO)
- meta.assignment - everything that is considered part of an assignment using a SET, SETL or SETG command
- meta.assignment.leo - everything that is considered part of parsing and an assignment using a LEO command
- meta.call.api-command - everything that is considered part of an API-command call, both through SEND and CC
- meta.call.dll - everything that is considered part of a CALL command
- meta.control.body.else - the body of commands in an ELSE control structure
- meta.control.body.elsif - the body of commands in an ELSIF control structure
- meta.control.body.for - the body of commands in an FOR loop
- meta.control.body.if - the body of commands in an IF control structure
- meta.control.body.while - the body of commands in an WHILE loop
- meta.control.else - everything that falls under the ELSE control structure, including the body
- meta.control.elsif - everything that falls under the ELSIF control structure, including the body
- meta.control.for - everything that falls under the FOR loop, including the body
- meta.control.if - everything that falls under the IF control structure, including the body
- meta.control.while - everything that falls under the WHILE loop, including the body
- meta.definition.body.function - the body of commands in a function definition
- meta.definition.body.procedure - the body of commands in a procedure definition
- meta.definition.body.onevent - the body of commands in an ON_EVENT definition
- meta.definition.function - everything that falls under the definition of a new function, including the body
- meta.definition.procedure - everything that falls under the definition of a new procedure, including the body
- meta.definition.onevent - everything that is considered part of specifying an ON_EVENT, including the body
- meta.execute - everything that is considered part of a EXECUTE command
- meta.exit- everything that is considered part of an EXIT command
- meta.include - everything that is considered part of a @INCLUDE command
- meta.start - everything that is considered part of a START command
- meta.system - everything that is considered part of a SYSTEM command
- punctuation.section.block.begin - the { at the beginning of a command block
- punctuation.section.block.end - the } at the end of a command block
- source - anything that's considered AdoScript code
- storage.modifier - keywords that act as modifiers for the storage of something else (e.g. raw in a CC, reference for a functions parameter)
- storage.modifier.global - a modifier that defines a function or procedure as globally available (global)
- storage.type - the built-in types (e.g. integer, real, string, array, map, lambda)
- storage.type.function - the keyword to define a new function
- storage.type.procedure - the keyword to define a new procedure
- storage.type.onevent - the keyword to define what happens on a specific event
- support.class.message-port - the message ports which can be accessed using CC and SEND (e.g. "AdoScript", "Core")
- support.class.onevent - the events available which can be used with ON_EVENT (e.g. "AppInitialized", "CreateModel")
- support.function.api-command.adoscript - the API-commands made available by the AdoScript message port
- support.function.api-command.analysis - the API-commands made available by the Analysis message port
- support.function.api-command.application - the API-commands made available by the Application message port
- support.function.api-command.aql - the API-commands made available by the AQL message port
- support.function.api-command.core - the API-commands made available by the Core message port
- support.function.api-command.coreui - the API-commands made available by the CoreUI message port
- support.function.api-command.db - the API-commands made available by the DB message port
- support.function.api-command.documentation - the API-commands made available by the Documentation message port
- support.function.api-command.drawing - the API-commands made available by the Drawing message port
- support.function.api-command.evaluation - the API-commands made available by the Evaluation message port
- support.function.api-command.explorer - the API-commands made available by the Explorer message port
- support.function.api-command.importexport - the API-commands made available by the ImportExport message port
- support.function.api-command.modeling - the API-commands made available by the Modeling message port
- support.function.api-command.simulation - the API-commands made available by the Simulation message port
- support.function.api-command.usermgt - the API-commands made available by the UserMgt message port
- variable.language.assignment - the name of a parameter from a command that gets a value assigned (e.g. file, scope for EXECUTE; result for SYSTEM)
- variable.other.assignment - the name of a variable (can also be an array or map) that gets a value assigned through using SET, SETL, SETG or LEO
- variable.parameter.definition - the name of a parameter that is defined (e.g. in a function or procedure definition)
ALL
Note: all of the scopes end with .all which will be omitted in the following list.
Note: meta. generally covers the entire part of a specific code structure from start to finish (e.g. entire definition of a class).
- comment.line.double-slash - single line comment
- comment.todo - the TODO keyword in a comment
- constant.character.escape - the escape character used in strings
- constant.numeric.decimal - a constant decimal number (e.g. 3, 5.3)
- constant.numeric.hex - a constant hexadecimal number (e.g. $6fa)
- constant.numeric.version-number - the used ALL version
- entity.name.file - the name of a file in the library
- entity.name.type.application-library - the name of an application library
- entity.name.type.attributeprofile-class - the name of an attributeprofile class
- entity.name.type.bp-library - the name of a business process library
- entity.name.type.class - the name of a (modeling) class
- entity.name.type.record-class - the name of a record class
- entity.name.type.relationclass - the name of a relation class
- entity.name.type.we-library - the name of a working environment library
- entity.name.type.inheritance.attributeprofile-class - the name of an attributeprofile class from which aspects are inherited
- entity.name.type.inheritance.bp-library - the name of a business process library from which aspects are inherited
- entity.name.type.inheritance.class - the name of a (modeling) class from which aspects are inherited
- entity.name.type.inheritance.record-class - the name of a record class from which aspects are inherited
- entity.name.type.inheritance.we-library - the name of a working environment library from which aspects are inherited
- invalid.illegal - anything that seems to be something that's not allowed at the place it is
- keyword.operator.arithmetic - the unary negation operator -
- keyword.operator.inheritance - the : character used for inheritance
- keyword.other.content - keyword used to specify the content of a file
- keyword.other.end - keyword used to indicate the end of defining a default RECORD attribute
- keyword.other.facet - keyword used to specify a facet of an attribute
- keyword.other.from - keyword used to define the source of a relation class
- keyword.other.record-value - keyword used to define the default value for an attribute of type RECORD
- keyword.other.value - keyword used to specify the default value of an attribute of one of its facets
- keyword.other.version - keyword for indicating the used ALL version
- keyword.other.to - keyword used to define the target of a relation class
- meta.definition.app-library - everything that defines an application library
- meta.definition.attributeprofile-class - everything that defines an attributeprofile class
- meta.definition.bp-library - everything that defines a business process library
- meta.definition.class - everything that defines a (modeling) class
- meta.definition.class-attribute - everything that specifies an class attribute (static)
- meta.definition.facet - everything that specifies the facet of an attribute
- meta.definition.file - everything that specifies the contents of a file
- meta.definition.instance-attribute - everything that specifies an instance attribute
- meta.definition.record-class - everything that defines a record class
- meta.definition.record-value - everything that defines the default values for an attribute of type RECORD
- meta.definition.relationclass - everything that defines a relation class
- meta.definition.value - everything that defines the default value of an attribute or one of its facets
- meta.definition.we-library - everything that defines a working environment library
- meta.version - everything that specifies the used ALL version
- punctuation.section.comment.line - character indicating the start of a line comment
- punctuation.section.identifier - characters indicating the start or end of an identifier (i.e. < and > )
- source - anything that is considered a definition in ALL
- storage.file - the keyword used to specify the contents of a file
- storage.type - the type of an attribute (e.g. STRING, INTEGER, ENUMERATION, INTERREF)
- storage.type.application-library - the keyword to define a new application library
- storage.type.attributeprofile - the keyword to define a new attributeprofile class
- storage.type.bp-library - the keyword to define a new business process library
- storage.type.class - the keyword to define a new (modeling) class
- storage.type.class-attribute - the keyword to define a new class attribute (static)
- storage.type.instance-attribute - the keyword to define a new instance attribute
- storage.type.keyword - the keyword to specify the type of an attribute
- storage.type.record - the keyword to define a new record class
- storage.type.relationclass - the keyword to define a new relation class
- storage.type.we-library - the keyword to define a new working environment library
- string.quoted.double - a string using double-quotes
- string.quoted.double.begin - the beginning double-quote of a string
- string.quoted.double.end - the ending double-quote of a string
- support.variable.facet - the name of a facet
- variable.other.definition.attribute - the name of an attribute (instance or class)
AQL
Note: all of the scopes end with .all which will be omitted in the following list.
Note: meta. generally covers the entire part of a specific code structure from start to finish (e.g. entire definition of a class).
Note: These details will be published at a later date.
(back to ToC)
| |