What Conventions Does Riddl Use?
RIDDL is a language and therefore adopts some syntax and semantic conventions. RIDDL tries to keep its syntax and semantics very simple and tolerant of user omissions and formatting. It is intentionally simple and readable for author and reader comprehension. The following language conventions are adhered to throughout the language for ease of use because special cases and rule contraventions may cause confusion.
The language is free in its formatting. Indentation is not required and its various definitions can be arranged on any line with any amount of white space.
RIDDL supports the definition of a variety of concepts (domain, bounded context, entity, message, repository, etc.) taken directly from Domain Driven Design and the Unified Modeling Language.
Most things in RIDDL are consistent throughout the language. We believe this makes learning the language easier since there are no exceptions to fundamental constructs and syntax. The sections below define the consistent language features.
The language is based on declarative definitions. All that means, syntactically, is that you name something of a given type, like this:
domain Engineering is { ??? }
In this example the type is domain
and the name is Engineering
. The
rest of the definition, ???
, contains more definitions specific to the
domain
kind of definition. You don’t say how to do something, you specify
the end result you want. The language aims to capture a detailed and
concise definition of the abstractions that a complex system will require. It
does not specify how those abstractions should be built. RIDDL is not a
programming language, but its compiler can generate structurally sound code
that can be completed by a software engineer or AI.
You may have noticed in the preceding example, the use of a special sequence, ???
.
This is a language operator that says “this definition is empty and that’s okay”.
The alternative, { }
, is not permitted. The three question marks indicate that the
definition is a work in progress. Modelling a domain can be hard work. New ideas
come up that must be flushed out at a later time. Sometimes things get left
undefined. That’s okay! This operator can be used as the body of
any definition.
Containers are definitions that contain other, nested, definitions. Between the
{
and the }
that define the boundaries of a definition, you may place other
definitions. Such nested definitions are deemed to be contained.
Not every definition is a container.
Definitions that have no content (nested definitions) are referred to
as leaf definitions
or leaves
because, like tree leaves, they occur at the
extremities of the hierarchy of definitions.
Definitions are specified in a strict containment hierarchy. Definitions that can contain other definitions are known as containers. For example, a domain definition is a recursively nested definition, as follows:
domain root is {
domain branch is {
domain leaf { ??? }
}
}
That is, domains are definitions that can contain the definition of (sub)
domains. Similarly context
can define entity
context foo is {
entity bar is { ??? }
}
Every thing you can define can optionally be documented in a variety of
ways. Documentation should conform to the
syntax of the Common Markdown format.
We call these
descriptions or explanations because this is the text that is
used to describe or explain the RIDDL definition, and it is used to generate
documentation for the definition. A description occurs directly after the
definition’s closing curly bracket and is preceded using keywords as
detailed in the subsections below
Pretty simple, like this:
domain Engineering is { ??? } described by "Stuff about engineering"
domain SomeDomain is { ??? } explained as "Too vague to have a good name"
Allowing markdown syntax, like this:
domain SomeDomain is { ??? } explained as {
|## Overview
|This domain is rather vague, it has no content.
|## Utility
|The utility of this domain is dubious because:
|* It has no content
|* Its name is not useful
|* It is only an example of RIDDL syntax
}
domain Engineering is { ??? } described in file "engineering.md"
or
domain Engineering is { ??? } described at https://en.wikipedia.org/wiki/Engineering
Every definition in RIDDL can have a briefly
or brief
suffix that in one
short string describes the definition, such as:
domain Engineering is { ??? } briefly "The discipline of using natural science, mathematics,
and design processes to create or improve systems that solve technical problems,
or increase efficiency and productivity."
Brief descriptions should be short and concise, like a dictionary, and useful in a glossary of terms. Brief descriptions must precede the other kinds of descriptions, like this:
domain Engineering is { ??? } briefly "The discipline of using natural science, mathematics,
and design processes to create or improve systems that solve technical problems,
or increase efficiency and productivity." described at https://en.wikipedia.org/wiki/Engineering
A definition introduces a named instance of some RIDDL concept (such as domain
,
context
or entity
as we have seen previously). Sometimes, we need to refer
to our definitions when defining something else.
For example, if RIDDL supported the concepts of a Cat and a Person, then you might specify a cat named “Smudge” with an owner named “Reid” like this:
person Reid is { ??? }
cat Smudge {
owner: person Reid
}
Here is an explanation of each of these tokens:
person
is the concept of a human being, intrinsic to RIDDL (its not, this is just an example)Reid
is the name (identifier) of the person being definedis
is an optional keyword for readability to introduce a definition{
is a required token that starts the definition ofReid
theperson
???
is syntactic sugar meaning “the details of this definition will be determined later”}
is a required token that finishes the definition ofReid
theperson
cat
is the concept of a feline being, if it were intrinsic to RIDDLSmudge
is the name the author wants to give to thiscat
concept{
is a required token that starts the definition of Smudge the catowner
is the name of a property that all “cat” concepts have:
is a required token to separate the property name from its valueperson Reid
is a reference to an instance of a concept, aperson
, with nameReid
.}
completes the definition of Smudge the cat.
References to every kind of RIDDL concepts are made in this way, by stating
the name of the concept (cat
or person
here) followed by the specific instance of
that concept’s name. This is a simple convention used throughout the language for all
concept types and references to them.
RIDDL allows source input to be included, inline, from other files. That is,
the parser will substitute the text of an included file, replacing the include
directive. This is much like the C preprocessor #include
directive. RIDDL
always parses the entire specification but the include
directive allows you to
organize that specification into many (even nested) files. Note that include
directives are only permitted within container definitions. Doing so prevents
fragments of definitions from being separated into individual files.
For example, this is allowed:
domain ThingAmaJig {
#include "thingamajig/thing-context"
#include "thingamajig/ama-topic"
#include "thingamajig/jig-context"
}
while this is not:
domain
#include "ThingAmaJig-domain"
because it is not specified within the contained portion of a container. A
domain
is a container, but it needs a name and that name cannot be buried in
an include file. As a rule of thumb, you can always use #include
right after
an opening curly brace of a container definition.
RIDDL supports the notion of directives that are specified as a complete line whose first character is the hash mark. The directive extends to the end of that line. Hash marks at other locations on a line are not recognized as directives. The subsections below define the kinds of directives supported by RIDDL’s compiler.
Directives have not yet been implemented in RIDDL
For example:
#define x = expialidocious
defines a symbol x that has the value expialidocious
. Wherever $x
is seen
in the input it will be replaced with expialidocious
before being lexically
interpreted by the compiler.
Substitutions have not yet been implemented in RIDDL