TypeDB 3.0 is live! Get started for free.

Define query

Define queries are used to add new types, constraints, or functions to the schema.

Syntax

Define queries start with the define keyword following by definition statements.

define
  <definition_statements>

Definition statement can consist of any number of schema-related statements, simple or composite. Statements should be separated by semicolons. Schema statements in a define query cannot use variables or values, except for functions.

Behavior

A define query adds schema statements to an existing schema. These statements can add new types and functions, or they can add new traits and annotations to existing types. Define queries cannot change schema statements already existing in a schema.

Define queries are idempotent, meaning they can be applied multiple times without changing the result of the initial application.

An error is returned (on execution or on commit), and no changes are preserved, if:

  • A definition conflicts with an existing definition.

  • The query results in an invalid schema.

Statements

  • entity statements define new entity types. This statement should be provided for every new type of kind entity.

  • relation statements define new relation types. This statement should be provided for every new type of kind relation.

  • attribute statements define new attribute types. This statement should be provided for every new type of kind attribute.

  • relates statements define new role types for relations. It can be followed by the as keyword to define a specialization for two role types.

  • plays statements define new roleplayings between types and relation types. Only entity and relation types can play roles.

  • owns statements define new ownerships between types and attribute types. Only entity and relation types can own attributes.

  • value statements define new value types of attribute types. An attribute type can only have up to one value type. If another value is already defined for the subject type, an error is returned.

  • sub statements define new subtyping between two types. Those types should be of the same kind: entity, relation, or attribute. If another sub is already defined for the subject type, an error is returned.

  • @annotations define new annotations. If another annotation of the same type but with different arguments is already defined, an error is returned. Can be applied to:

    • Type labels for entities, relations, attributes.

    • Traits: relates, plays, owns.

    • Attribute value types: value.

  • fun statements define new functions.

Examples

Defining types

Defining entity types
define entity user;
Defining relation types
define relation parentship;
Defining attribute types
define attribute email;

Defining traits

Defining relation type’s relates
define parentship relates parent, relates child;
Defining relation types with subtyping
define relation fathership sub parentship;
Defining relates with role type specializing
define fathership relates father as parent;
Defining roleplaying for multiple roles
define user plays parentship:parent, plays parentship:child;
Defining attribute type’s value type
define email value string;
Defining type’s ownership
define user owns email;

Defining annotations

Defining type’s annotation without arguments
define parentship @abstract;
Defining attribute type’s annotation and value type’s annotation with arguments
define email @independent, value string @regex("^.*@\w+\.\w+$");
Defining type’s ownership’s annotation with arguments
define user owns email @card(0..2);
Defining annotations for specializing relates
define fathership relates father as parent @abstract;

Defining functions

define
  fun karma_with_squared_value($user: user) -> karma, double:
    match
      $user has karma $karma;
      let $karma-squared = $karma * $karma;
    return first $karma, $karma-squared;