` |
| DESCRIPTION | Informative description of the system. |
The SERVICE\_PORT attribute applies to the internal network. For external network service connection, the port number in the EXTERNAL\_SERVICE\_NET attribute may be different.
#### SYSMGR MODIFY
This command modifies attributes of the System Manager.
**Synopsis**
```text wrap theme={null}
MANAGE SYSMGR MODIFY
[ NETWORK { ADD | REMOVE | SET } net_address [, ...] ]
[ DESCRIPTION free_text ]
where net_address is:
( EXTERNAL IP ip_addr PORT port_num )
```
This command is allowed only when the system state is `SETUP`.
**Parameters**
`NETWORK`
The NETWORK clause includes one or more network addresses. It can come with either of the following directives:
* `ADD `– Adds the given network addresses to the list of existing addresses.
* `REMOVE `– Remove each given network address from the list of existing addresses. Each removed network address must be an exact match to an existing one.
* `SET `– Remove all the existing network addresses and replace them with the given network addresses.
`DESCRIPTION`
Optional parameter. Free text that is added to the module.
# System States and Commands
Source: https://docs.regatta.dev/sql/system-management/system-states-and-commands
## System States
**The Regatta system has a state, which could be one of the following:**
**DOWN**: The system is not operational – the RDB modules don’t accept client connections and system configuration commands are not available. The system can be queried (using the `MANAGE `… `SHOW `commands) but the only two operations accepted in this state are to activate the system or to enter the SETUP state.
**SETUP**: The system is not operational – the RDB modules don’t accept client connections. System configuration commands are allowed.
**STARTING**: The system is in the process of becoming active. The RDB modules may start accepting client connections but are not yet fully operational. System configuration commands are not allowed.
**ACTIVE**: The system is operational, accepting client connections. Some system configuration commands are allowed.
**SHUTTING DOWN**: The system is in the process of shutting down. The RDB modules close all the client connections and stop accepting new connections. System configuration commands are not allowed.
```mermaid placement="top-left" actions={false} theme={null}
flowchart RL
SETUP([SETUP])
subgraph MainLoop [ ]
ACTIVE([ACTIVE])
STARTING([STARTING])
SHUTTING_DOWN([SHUTTING DOWN])
DOWN([DOWN])
STARTING -.-> ACTIVE
ACTIVE -->|Shutdown| SHUTTING_DOWN
STARTING -->|Shutdown| SHUTTING_DOWN
SHUTTING_DOWN -.-> DOWN
DOWN -->|Start| STARTING
end
SETUP <-->|Enter/Exit Setup| DOWN
%% This makes the MainLoop box invisible
style MainLoop fill:none,stroke:none
```
### System Commands
All the system-wide commands begin with the prefix `MANAGE SYSTEM`
#### SYSTEM START
Synopsis
```text theme={null}
MANAGE SYSTEM START
```
The command is accepted only if the current system state is `DOWN`. The result of executing the command is a state change to `STARTING`.
#### SYSTEM SHUTDOWN
**Synopsis**
```text theme={null}
MANAGE SYSTEM SHUTDOWN [ WAIT seconds ]
```
The command is accepted only if the current system state is either `ACTIVE `or `STARTING`.
The shutdown process is performed asynchronously. The command returns when the system state has changed to `SHUTTING DOWN` .
**Parameters**
`WAIT seconds`
Optional parameter. The system will wait up to the specified number of seconds for ongoing transactions to finish before shutting down. If any transaction remains active after that time elapsed, it will be aborted. By default, ongoing transactions are immediately aborted.
#### SYSTEM ENTER SETUP
**Synopsis**
```text theme={null}
MANAGE SYSTEM ENTER SETUP
```
The command is accepted only if the current system state is `DOWN`. The result of executing the command is a state change to `SETUP`.
#### SYSTEM EXIT SETUP
**Synopsis**
```text theme={null}
MANAGE SYSTEM EXIT SETUP
```
The command is accepted only if the current system state is `SETUP`. The result of executing the command is a state change to `DOWN`.
#### SYSTEM MODIFY
This command modifies parameters of the system.
**Synopsis**
```text theme={null}
MANAGE SYSTEM MODIFY
[ RDB_FAILURE_THRESHOLD (FAILURES num_failures DURATION time_window) [ , ... ] ]
[ DCM_FAILURE_THRESHOLD (FAILURES num_failures DURATION time_window) [ , ... ] ]
[ GDD_FAILURE_THRESHOLD (FAILURES num_failures DURATION time_window) [ , ... ] ]
[ SEQUENCER_FAILURE_THRESHOLD (FAILURES num_failures DURATION time_window) [ , ... ] ]
```
**Parameters**
`RDB_FAILURE_THRESHOLD`
Optional parameter. Specify up to 4 failure thresholds for each RDB module. Each threshold is specified by a number of failures and time window (in seconds). A module is restarted automatically when it fails, as long as it hasn’t reached the threshold. Once a threshold is reached, the module is not restarted, and it remains in state `DOWN `until it is started with the `MODULE START` command.
For example, when specifying `RDB_FAILURE_THRESHOLD (FAILURES 3 DURATION 60), (FAILURES 5 DURATION 3600)`, an RDB module will move to state `DOWN `if it fails 3 times within 60 seconds, or if it fails 5 times within an hour.
The specified failure thresholds replace the existing set of thresholds.
`DCM_FAILURE_THRESHOLD, GDD_FAILURE_THRESHOLD, SEQUENCER_FAILURE_THRESHOLD`
Optional parameters. These parameters specify up to 4 failure thresholds for the DCM, GDD and SEQUENCER modules, respectively. See description of RDB\_FAILURE\_THRESHOLD above.
#### SYSTEM SHOW
This command shows the state and other attributes of the system.
**Synopsis**
```text theme={null}
MANAGE SYSTEM SHOW [ DETAILED ]
```
**Output**
The output of the command is tabular, containing a single row. The following table lists the columns of the output. The columns marked as “Basic” appear in the basic output, the other columns appear only in the detailed output.
| Name | Type | Basic | Description |
| - | - | :- | - |
| STATE | String | | The state of the system. |
| NUM\_NODES | Number | | The number of nodes. |
| NUM\_RDB\_MODULES | Number | | The number of RDB modules. |
| NUM\_UNAVAILABLE\_NODES | Number | | The number of nodes in state `NOT AVAILABLE` |
| NUM\_INACTIVE\_MODULES | Number | | The number of modules that are not in `ACTIVE `state |
See description of the failure thresholds in the [SYSTEM MODIFY](#system-modify) command.
# Database Catalog Data
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/database-catalog
The database catalog views maintain information about the database objects (tables, indexes, etc.).
# SHOW COLUMNS
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/show-columns
This view has a row for every column in every table in the database.
The output is ordered by the (`table_name, column_name`) columns.
Data can be filtered with `IN TABLE` table\_name syntax.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| TABLE\_NAME | `VARCHAR(127)` | The table name |
| COLUMN\_NAME | `VARCHAR(127)` | The column name. This is the filter column |
| DATA\_TYPE | `VARCHAR(30)` | The column data type. One of the supported data types ([Data Types](/sql/data-types)) |
| COLUMN\_SIZE | `INT` | The number of chars for CHAR, the maximum number of chars for VARCHAR, the precision of the column for NUMERIC, REAL or DOUBLE PRECISION, the number of fractional digits retained in the seconds field for TIME or TIMESTAMP.
Null for all other types. |
| SCALE | `INT` | The number of digits to the right of the decimal point in a number.
Null when not relevant |
| NOT\_NULL | `BOOLEAN` | True if defined as NOT NULL. |
| DEFAULT | `VARCHAR(8000)` | The column's default value (NULL if there is no default value). |
| ORDINAL\_POSITION | `INT` | Ordinal position of the column within the table (count starts at 1) |
# SHOW CONSTRAINTS
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/show-constraints
This view has a row for every constraint in every table in the database, except for `NULL` constraints. Those are presented as the column `IS_NULLABLE` at `SHOW COLUMNS` view.
The output is ordered by the `table_name` column.
Data can be filtered with `IN TABLE` table\_name syntax.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| TABLE\_NAME | `VARCHAR(127)` | The table name. This is the filter column. |
| COLUMN\_NAME | `VARCHAR(127)` | The column the constraint is set on |
| CONSTRAINT\_TYPE | `CHAR(1)` | `r` = foreign key constraint, `p` = primary key constraint, `u` = unique constraint |
| REF\_TABLE\_NAME | `VARCHAR(127)` | For foreign key constraint: The referenced table the foreign key is pointing to. Otherwise null. |
| REF\_COL\_NAME | `VARCHAR(127)` | For foreign key constraint: The column in the reference table the foreign key is referring to. Otherwise null. |
# SHOW INDEXES
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/show-index
This view has a single row for each index in the database. The output is ordered by the
(`table_name,index_name`) columns.
Data can be filtered with `IN TABLE` table\_name syntax.
Note, this view contains both indexes created explicitly by the user and indexes created implicitly for `PRIMARY
KEY` and `UNIQUE` and `REFERENCES` constraints.
The following table lists the output’s columns:
| Column name | Data type | Description |
| - | - | - |
| TABLE\_NAME | VARCHAR(127) | The table name |
| INDEX\_NAME | VARCHAR(127) | The index name. This is the filter column. |
| IS\_UNIQUE | BOOLEAN | True if the index is unique. False if not. |
| COLUMN\_NAME | VARCHAR(127) | The index column name |
| DEVICES | VARCHAR(1000) | List of devices on which the index is stored, separated by comma.
Note: The output is trimmed after 1000 chars. To see the full list of devices use [SHOW INDEX DEVICES](/sql/system-monitoring/database-catalog/show-index-devices). |
| RANGE\_SEPARATORS | VARCHAR | Separators of the key ranges of the segments, if any.
The column output max size is limited by the [Max SQL statement length](/sql/appendices/database-limitations). |
# SHOW INDEX DEVICES
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/show-index-devices
This view returns the list of devices per index in the database.
Note that in this view, specifying the `IN INDEX` index\_name is mandatory.
The output is ordered by the `device_id` column.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| DEVICE\_ID | `VARCHAR(32)` | The unique device identifier. This is the filter column |
| MODULE\_ID | `INT` | The identifier of the module |
| DEVICE\_TOTAL\_CAPACITY | `BIGINT` | Total size in bytes |
For example:
```sql theme={null}
SHOW INDEX DEVICES IN INDEX 'my_table_idx';
```
# SHOW TABLE DEVICES
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/show-table-devices
This view returns the list of devices per table in the database.
Note that in this view, specifying the `IN TABLE` table\_name is mandatory.
The output is ordered by the `device_id` column.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| DEVICE\_ID | `VARCHAR(32)` | The unique device identifier. Filter column |
| MODULE\_ID | `INT` | The identifier of the module |
| CAPACITY | `BIGINT` | Total capacity of the device in bytes |
For example:
```sql theme={null}
SHOW TABLE DEVICES IN TABLE 'my_table';
```
# SHOW TABLES
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/show-tables
This view has a single row for each table in the database.
The output is ordered by the `table_name` column.
The following table lists the output’s columns:
## Output Columns
| Column name | Data type | Description |
| :- | :- | :- |
| TABLE\_NAME | VARCHAR(127) | The table name. This is the view filter column. |
| IS\_READY | BOOLEAN | True if `READY`, False if `NOT READY` |
| PRIMARY\_KEY\_COLUMN | VARCHAR(127) | The primary key column name. (`NULL` if the table has no primary key.) |
| DEVICES | VARCHAR(1000) | List of devices on which the table is stored, separated by comma.
Note: The output is trimmed after 1000 chars. To see the full number of devices see [SHOW TABLE DEVICES](/sql/system-monitoring/database-catalog/show-table-devices).
Customers can identify that the value was trimmed by finding '...' as the last 3 chars of the value. |
| TABLE\_METADATA | VARCHAR | The `CREATE TABLE` command to use to recreate the table if needed with all its columns/constraint/indexes.
This output should include the table indexes as well. The column output max size is limited by the [Max SQL statement length](/sql/appendices/database-limitations). |
# SHOW USERS
Source: https://docs.regatta.dev/sql/system-monitoring/database-catalog/show-users
This view has a row for every user in the database.
The output is ordered by the `user_name` column.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| USER\_NAME | `VARCHAR(64)` | The username. This is the filter column. |
# Dynamic System Data
Source: https://docs.regatta.dev/sql/system-monitoring/dynamic-system/dynamic-system
These views are dynamic and are being updated in high frequency.
# SHOW DATABASE METRICS
Source: https://docs.regatta.dev/sql/system-monitoring/dynamic-system/show-database-metric
This view returns all the metrics related to the database, meaning that it presents the aggregated metrics for
the whole cluster
The output is ordered by the `metric_name` column.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| METRIC\_NAME | `VARCHAR(255)` | Unique short name for the metric. This is the filter column. |
| METRIC\_ID | `INT` | The unique metric identifier. Correlates to [SHOW METRIC DESCRIPTION](/sql/system-monitoring/dynamic-system/show-metric-description). |
| VALUE | `INT` | Current value for the metric (rounded up) |
| QUERY\_TIMESTAMP | `TIMESTAMP` | Represent the query time. The output of `current_timestamp` function. |
# SHOW DEVICE METRICS
Source: https://docs.regatta.dev/sql/system-monitoring/dynamic-system/show-device-metrics
This view returns the current metrics of the cluster devices.
Ordered by the (`metric_name, device_id`) columns.
Data can be filtered with the `IN DEVICE device_id` parameter.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| METRIC\_NAME | `VARCHAR(255)` | Unique short name for the metric. This is the filter column. |
| METRIC\_ID | `INT` | The unique metric identifier. Correlates to [SHOW METRIC DESCRIPTION](/sql/system-monitoring/dynamic-system/show-metric-description). |
| MODULE\_ID | `INT` | The identifier of the module |
| DEVICE\_ID | `VARCHAR(32)` | The unique device identifier. |
| VALUE | `INT` | Current value for the metric (rounded up) |
| QUERY\_TIMESTAMP | `TIMESTAMP` | Represent the query time. The output of `current_timestamp` function. |
# SHOW METRIC DESCRIPTION
Source: https://docs.regatta.dev/sql/system-monitoring/dynamic-system/show-metric-description
Contains information about the dynamic system data metrics (see [Dynamic System Data](/sql/system-monitoring/dynamic-system)).
The output is ordered by the `metric_name` column.
Note: All the metrics are for the current time and not historical or cumulative.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| METRIC\_NAME | `VARCHAR(255)` | Unique short name for the metric. This is the filter column.
Note that some metrics appear in more than 1 view (in both SHOW DATABASE METRICS and SHOW MODULE METRICS).
|
| METRIC\_ID | `INT` | The unique metric identifier. |
| DESCRIPTION | `VARCHAR(4000)` | Metric description. |
The following table lists the available metrics and their descriptions:
| Metric id | Name in SHOW METRIC DESCRIPTION view | Description in SHOW METRIC DESCRIPTION view |
| :- | :- | :- |
| 23 | Average CPU usage percentage | The average CPU usage percentage |
| 22 | Average memory usage percentage | The average memory usage percentage |
| 0 | Deadlock detections rate | The deadlock detections rate per second |
| 1 | DELETE statements average latency | The average execution time of successful DELETE statements in milliseconds |
| 2 | DELETE statements rate | The rate of successful DELETE statements per second |
| 1000 | Device row data consumption percentage | The amount of space used for table rows data, as percentage of the device capacity. (This metric includes capacity reserved for internal operations.) |
| 1001 | Device metadata consumption percentage | The amount of space used for metadata associated with table rows, including indexes, as percentage of the device capacity. |
| 3 | Inbound network throughput | The inbound (from the Client to Regatta) network throughput in bytes per second |
| 4 | Index entry reads rate | The rate of index entry reads per second |
| 5 | Index updates rate | The index updates rate per second |
| 6 | INSERT statements average latency | The average execution time of successful INSERT statements in milliseconds |
| 7 | INSERT statements rate | The rate of successful INSERT statements per second |
| 8 | Longest active statement time | The time of the longest currently active statement in seconds |
| 9 | Number of active transactions | The number of active transactions |
| 10 | Number of open clients connections | The number of open clients connections |
| 11 | Outbound network throughput | The outbound (from Regatta to the Client) network throughput in bytes per second |
| 12 | Row deletions rate | The rate of row deletions per second |
| 13 | Row insertions rate | The rate of row insertions per second |
| 14 | Row output rate | The rate of rows returned in result sets per second |
| 15 | Row updates rate | The rate of row updates per second |
| 16 | Statements error rate | The rate of failed statements per second |
| 24 | SELECT statements average latency | The average execution time of successful SELECT statements in milliseconds |
| 25 | SELECT statements rate | The rate of successful SELECT statements per second |
| 17 | Table row reads rate | The rate of row reads per second |
| 28 | Transaction aborts rate | The rate of transactions aborted per second |
| 19 | Transactions in conflict wait rate | The rate of transactions waiting to commit, due to conflicts with other transactions, per second |
| 20 | UPDATE statements average latency | The average execution time of successful UPDATE statements in milliseconds |
| 21 | UPDATE statements rate | The rate of successful UPDATE statements per second |
Note that `INSERT AS SELECT` is counted as both `INSERT` and `SELECT` statements.
# SHOW MODULE METRICS
Source: https://docs.regatta.dev/sql/system-monitoring/dynamic-system/show-module-metrics
This view returns all the metrics related to the module level meaning that it presents multiple rows per metric\_id, according to the number of the RDB modules in the cluster.
The output is ordered by the (`metric_name, module_id`) columns.
Data can be filtered with the `IN MODULE module_id` parameter.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| METRIC\_NAME | `VARCHAR(255)` | Unique short name for the metric. This is the filter column. |
| METRIC\_ID | `INT` | The unique metric identifier. Correlates to [SHOW METRIC DESCRIPTION](/sql/system-monitoring/dynamic-system/show-metric-description). |
| MODULE\_ID | `INT` | The identifier of the module |
| VALUE | `INT` | Current value for the metric (rounded up) |
| QUERY\_TIMESTAMP | `TIMESTAMP` | Represent the query time. The output of `current_timestamp` function. |
# SHOW SYSTEM VIEWS
Source: https://docs.regatta.dev/sql/system-monitoring/show-system-views
This view has a single row for every system view and a short description of its content.
The output is ordered by the `view_name` column.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| `VIEW_NAME` | `VARCHAR(127)` | The system view name. A filter column. |
| `FILTER_COLUMN` | `VARCHAR(127)` | The column by which clients can filter the view |
| `IN_PARAM` | `VARCHAR(20)` | The object type by which the view can be filtered (`TABLE` \| `INDEX` \| `DEVICE` \| `NULL`) |
| `ORDER_BY_COLUMNS` | `VARCHAR(127)` | The columns by which the view is ordered |
| `DESCRIPTION` | `VARCHAR(1000)` | A short description on the view content |
The following table lists the available system views and their description:
| view name | filter column | IN\_param | ordered by columns | description |
| :- | :- | :- | :- | :- |
| `show columns` | `column_name` | `TABLE` | `table_name,column_name` | show the columns of all the tables in the database |
| `show constraints` | `table_name` | `TABLE` | `table_name` | show all the constraints in the database |
| `show database metrics` | `metric_name` | `DEVICE` | `metric_name` | shows all the database metrics and their values |
| `show device metrics` | `metric_name` | `DEVICE` | `metric_name,device_id` | show all the devices metrics and their values |
| `show devices` | `device_id` | `--` | `device_id` | show all the devices of the database |
| `show index devices` | `device_id` | `INDEX` | `device_id` | show all the devices of a specific index |
| `show indexes` | `index_name` | `TABLE` | `table_name,index_name` | show all the indexes in the database |
| `show metric description` | `metric_name` | `--` | `metric_name` | show all the database metrics and their description |
| `show module metrics` | `metric_name` | `--` | `metric_name,module_id` | show all the modules metrics and their values |
| `show modules` | `Module_role` | `--` | `Module_role,node_name` | show all the modules in the cluster |
| `show nodes` | `node_name` | `--` | `node_name` | show all the nodes in the cluster |
| `show system views` | `view_name` | `--` | `view_name` | show this view |
| `show table devices` | `device_id` | `TABLE` | `device_id` | show the devices of a specific table |
| `show tables` | `table_name` | `--` | `table_name` | show all the tables in the database |
| `show users` | `user_name` | `--` | `user_name` | show all the users in the database |
# SHOW DEVICES
Source: https://docs.regatta.dev/sql/system-monitoring/system-catalog/show-devices
This view returns a row for every device in the cluster.
The output is ordered by the `device_id` column.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| DEVICE\_ID | `VARCHAR(32)` | The device unique identifier for the device. This is the filter column. |
| MODULE\_ID | `INT` | The module the device is attached to |
| CAPACITY | `BIGINT` | Total device capacity in bytes |
| TYPE | `VARCHAR(100)` | The device type |
# SHOW MODULES
Source: https://docs.regatta.dev/sql/system-monitoring/system-catalog/show-modules
Contains information about existing modules in the cluster.
Note that several modules with the same role can exist in the cluster, in the same or different nodes.
The output is ordered by the (`module_role, node_name`) columns.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| MODULE\_ROLE | `VARCHAR(50)` | The module role. This is the filter column. E.g: Sequencer, RDB. |
| MODULE\_ID | `INT` | The unique module identifier. |
| NODE\_NAME | `VARCHAR(8)` | The name of the node the module is running on |
| MODULE\_VERSION | `VARCHAR(20)` | The module version |
# SHOW NODES
Source: https://docs.regatta.dev/sql/system-monitoring/system-catalog/show-nodes
Contains information about the nodes which participate in the cluster.
The output is ordered by the `node_name` column.
The following table lists the output’s columns:
| Column name | Data type | Description |
| :- | :- | :- |
| NODE\_NAME | `VARCHAR(8)` | The identifier of the node. This is the filter column. |
| RAM\_SIZE | `BIGINT` | The memory size in bytes |
| NUMBER\_OF\_CPUS | `INT` | The number of logical CPU in the node |
| CPU\_TYPE | `VARCHAR(20)` | The CPU type |
| CPU\_MODEL | `VARCHAR(20)` | The CPU model |
| IP\_ADDRESS | `VARCHAR(200)` | Node’s IP (list of IPs separated by comma if there are more than 1). |
# The SYSTEM Command
Source: https://docs.regatta.dev/sql/system-monitoring/system-management/system-command
## Synopsis
```
SYSTEM command [ option ... ]
where command is: SHUTDOWN (future commands will be added if needed)
```
## Description
The system commands are used for system management and control. The command follows the `SYSTEM` keyword, and the options vary by command. Currently the only supported command is `SHUTDOWN`.
# SYSTEM SHUTDOWN
Source: https://docs.regatta.dev/sql/system-monitoring/system-management/system-shutdown
## Synopsis
```
SYSTEM SHUTDOWN [ WAIT N ]
```
## Description
This command begins the shutdown of the system. The shutdown process proceeds asynchronously after the command completes. The system will start rejecting new transactions, all the outstanding transactions will be aborted, and the system will shut down.
## Parameters
**`WAIT N`**
Wait up to N seconds to allow ongoing transactions to complete. Any transaction that is still active after N seconds will be aborted. If this parameter is not specified – ongoing transactions will be aborted immediately.
# SHOW SYSTEM STATE
Source: https://docs.regatta.dev/sql/system-monitoring/system-management/system-state
## Synopsis
```
SHOW SYSTEM STATE [ DETAILED ]
```
## Description
This command is used to query the operational state of the system.
The command returns a single row. In its basic form, the row contains a single `STATE` field, which can take one of the following values: `{ACTIVE, SHUTTING DOWN}`. With the `DETAILED` parameter specified, additional fields are included.
## Parameters
**`DETAILED`**
With this optional parameter, the result contains additional columns.
The following table lists the columns of the result, including the ones appearing in the basic view and the ones that are included only in the detailed view.
| Column name | Data type | Included in basic view | Description |
| :- | :- | :- | :- |
| STATE | `VARCHAR(16)` | Yes | The operational state of the system. |
| PHASE | `VARCHAR(32)` | No | In `ACTIVE` state: `NULL`.
In `SHUTTING_DOWN` state: the current shutdown phase out of the total number of phases in the form "i / n" (e.g., "2 / 4"). |
| NUMBER OF MODULES | `INT` | No | In `ACTIVE` state: The number of active modules.
In `SHUTTING DOWN` state: The number of modules that haven't finished the current shutdown phase. |
# Using System Monitoring Views
Source: https://docs.regatta.dev/sql/system-monitoring/system-monitoring-views/system-monitoring-views
System views are used to track database objects (as part of the [Database Catalog Data](/sql/system-monitoring/database-catalog)), system static configuration (as part of the [System Catalog Data](/sql/system-monitoring/system-catalog)) and dynamic metrics on the system performance (as part of the [Dynamic System Data](/sql/system-monitoring/dynamic-system)).
The system monitoring views are exposed by the `SHOW` commands. Those `SHOW` commands are Regatta proprietary commands and support the options listed below.
## Synopsis
```sql theme={null}
SHOW view_name [ LIKE 'pattern' ][ IN object_type object_name ] [ ROWS BETWEEN n AND m ]
where object_type is:
{ TABLE | INDEX | DEVICE }
```
## Parameters
**`view_name`**
The system catalog view name.
**`LIKE ''`**
Filters the view output by its main object (e.g filter by table name in `SHOW TABLES` view, filter by index name in `SHOW INDEXES` view). The filter uses case-sensitive pattern matching, with the support of optional leading and/or trailing percent signs.
The percent sign (%) stands for sequences of zero or more characters.
**`IN object_type object_name`**
Show only results within the scope of a specific object in the relevant system view data. Possible object types and the views to which they apply:
| Object type | System view |
| :- | :- |
| `IN TABLE` | `SHOW INDEXES`,
`SHOW COLUMNS`,
`SHOW TABLE DEVICES`,
`SHOW CONSTRAINTS` |
| `IN INDEX` | `SHOW INDEX DEVICES` |
| `IN DEVICE` | `SHOW DEVICE METRICS` |
| `IN MODULE` | `SHOW MODULE METRICS` |
The **table\_name/index\_name/device\_id** should be the fully-qualified name.
Note that input names are converted to lower-case unless enclosed by double quotes. Therefore: `IN TABLE 'Employees'` and `IN TABLE 'employees'` both refer to the table\
named employees, while `IN TABLE '“Employees”'` refers to the table named\
`Employees`.
**`ROWS BETWEEN n AND m`**
Used to return only part of the output rows. This can be used to retrieve the results in parts and avoid exceeding the client's memory limitations.
Note:
* If the size of the output exceeds the client memory, an error is returned.
* If objects are added and/or removed from the view in between two queries of consequent row ranges, an existing object may be returned in both queries or missing from both queries.
* If the number of requested rows is larger than the actual number of rows in the view, the command should succeed and return only the existing rows.
* The row number is zero-based.
## Examples
```sql theme={null}
SHOW TABLES;
SHOW TABLES LIKE 'my%';
SHOW COLUMNS IN TABLE "my_table";
SHOW COLUMNS LIKE '%product%' IN TABLE "my_table";
SHOW TABLES LIKE '%my' ROWS BETWEEN 100 AND 150;
```
# SET TRANSACTION
Source: https://docs.regatta.dev/sql/tcl-commands/set-transaction
Define the characteristics of the current transaction.
## Synopsis
```
SET TRANSACTION transaction_mode [, ...]
where transaction_mode is one of:
ISOLATION LEVEL { SERIALIZABLE |
REPEATABLE READ |
READ COMMITTED }
{ READ WRITE | READ ONLY }
```
## Description
The `SET TRANSACTION` command defines the characteristics of the current transaction. It has no effect on any subsequent transactions.
Note that this command should be the first statement in the transaction (after `BEGIN/START TRANSACTION`). If this is not the case, an error is returned.
## Parameters
**ISOLATION LEVEL**
Defines how the transaction is isolated from other transactions. When not specified in the `SET TRANSACTION` command, the transaction isolation level is the level that was defined for the client connection or the database default.
Note that in all isolation levels, transactions always see their own (uncommitted) changes.
**`READ COMMITTED`**
Each statement sees only data committed before it started execution; it never sees either uncommitted data or changes committed by concurrent transactions during the statement's execution.
Note that two statements can see different data, even though they are within a single transaction, if other transactions commit changes after the first statement starts and before the second statement starts.
This is the database default isolation level.
**`REPEATABLE READ`**
Statements within the transaction only see data committed before the transaction began; it never sees either uncommitted data or changes committed by concurrent transactions during the transaction's execution.
In contrast to `READ COMMITTED` level, in this level all the statements within a transaction see the same version of the data.
**`SERIALIZABLE`**
Each statement within the transaction reads the last committed version of any row. Regatta provides that any concurrent execution of a set of serializable transactions is guaranteed to produce the same effect as running them one at a time in some order. In addition, in Regatta this mode provides *external consistency*: The order of execution of transactions as it appears to any other transaction is the commitment order.
**`READ WRITE`**
Define the transaction as capable of both read and write changes in the database. This is the default.
**`READ ONLY`**
Define the transaction as capable of only reading data from the database. Attempts to write will fail the statement and the transaction.
## Examples
**Start a transaction and set its isolation mode:**
```sql theme={null}
SET TRANSACTION ISOLATION LEVEL READ COMMITTED;
INSERT INTO customers (c_custkey, c_name, c_gender)
VALUES (1, 'John Doe1', 'M');
```
**Start a transaction, set its isolation level and set it to READ ONLY:**
```sql theme={null}
SET TRANSACTION ISOLATION LEVEL REPEATABLE READ , READ ONLY;
SELECT * FROM customers;
```
## Compatibility
The `SET TRANSACTION` command conforms to the SQL standard.
# Transaction Control Language Commands
Source: https://docs.regatta.dev/sql/tcl-commands/tcl-commands
Transactions are the basis of concurrency control, providing strong consistency and preserving the ACID guarantees: Atomicity, Consistency, Isolation and Durability. A transaction is a sequence of SQL statements that is committed or rolled back as a whole, in a single operation. The intermediate states between the statements of a transaction are not visible to other concurrent transactions, and if some failure occurs that prevents the transaction from being completed, then none of its statements affect the database at all.
An active transaction ends either by successful commit, or rollback (abort). Rollback can happen either by the client request, or by the Regatta system itself if it encounters an error or if it detects that the transaction entered a deadlock with other transactions.
The transaction control commands aren’t regular SQL statements. They are executed by calling specific API on the Regatta client drivers. The only exception is the `SET TRANSACTION` command, which can be executed as a statement, provided that it’s the first statement in the transaction. The specification of that command is detailed below.
The Regatta client driver has an `AUTOCOMMIT` mode which can be turned ON/OFF via the client driver API. The `AUTOCOMMIT` mode defines how transaction control is managed:
* When `AUTOCOMMIT` mode is set to ON, the driver receives the statements and automatically starts a transaction for each statement. Once the statement’s execution is complete, the driver automatically commits the transaction. This mode doesn’t support multi-statement transactions.
* When `AUTOCOMMIT` mode is set to OFF, each transaction has to be started and committed (or rolled back) explicitly by using the driver API.
By default, the Regatta client driver `AUTOCOMMIT` mode is set to ON.
Important note: Passing through transaction control commands (`BEGIN/COMMIT/ROLLBACK`) as strings through the regular SQL statement API would result in an error.
### Transaction control and DDL
DDL commands don't conform to the standard transaction ACID rules, therefore, they cannot be executed as part of a transaction like other SQL commands. Technically, they are executed in single-statement pseudo transactions to retain the basic protocol that encapsulates statements within transactions. But those transactions don’t provide the isolation guarantee among transactions.
A DDL statement must be the first statement in a transaction, and it causes an immediate commit of the transaction after its completion, even if `AUTOCOMMIT` mode is set to OFF.
Other concurrent transactions are not isolated from changes made by DDLs, and they may be exposed to changes made by a DDL even before the DDL is completed and even if they run in snapshot-based isolation mode.
For example, a statement that performs a full scan on a table and a DROP TABLE is issued concurrently to the scan execution, may either complete successfully or fail depending on the timing of execution (even if the scan is snapshot-based). However, Regatta guarantees that if it succeeds, it won’t return partial results.
# Creating a Vector Index
Source: https://docs.regatta.dev/sql/vector-index/ddl/creating-vector-index
The following command creates a vector index.
## Synopsis
```sql theme={null}
CREATE VECTOR INDEX [ index_name ] ON table_name
USING { HNSW | IVFFLAT } (column_name distance_metric)
[ WITH ( option [, ... ] ) ]
where distance_metric is one of {COSINE, L2, IP}
and option is in the form of =
The following options apply to any vector index:
parallelism = {FULL, HIGH, MEDIUM, LOW}
modules = ((module_idname [, parallelism]), ...)
Other options are specific to the index type and are listed below.
```
## Description
A vector index can be created on a vector column to provide appropriate searches for vectors that are “close” to a given vector according to one of the distance metrics described in the previous section. Regatta supports two types of vector indexes: `HNSW `and `IVFFLAT`.
Each index type supports all the distance metrics, but each index uses a single distance metric and supports approximate searches only for that metric. Multiple vector indexes can be created for the same vector column, as long as they differ in the combination of index type and distance metric.
An index vector is created for all the rows of a table, or only for rows residing in specific modules. Modules can be added to and removed from the index at any time using the `ALTER VECTOR INDEX` command (see [Modify Vector Indexes](/sql/vector-index/ddl/modifying-vector-index)). However, once the index was built for a specific module, it does not change – it is not updated when rows are inserted or updated. In order to update the index for the rows residing in a module, the module should be removed from the index and added back. This will result in rebuilding the index for the module’s rows.
The `CREATE VECTOR INDEX` command creates the index and initiates the build process. It returns once the index was created and the build process was initiated. Only after the build process is completed, the index becomes usable for approximate vector search. The `SHOW VECTOR INDEXES` command (see [Show Vector Indexes](/sql/vector-index/show-commands#show-vector-indexes)) can be used to query the status of the index.
## Parameters
***index\_name***
The name of the index. If not specified, RegattaDB generates a name.
`ON table_name`
Specifies the table containing the vector column to be indexed.
`USING { HNSW | IVFFLAT } `
This parameter indicates that the index is a vector index that supports approximate search.
***column\_name***
Specifies the column to be indexed. The column must be of type vector.
***distance\_metric***
This parameter can be one of the following:
`COSINE `– Cosine similarity between vectors.
`L2 `– Euclidean distance.
`IP` – Inner product (also known as dot product)
`WITH ( option [, ... ] )`
Specifies various options for the index creation. The options are listed below. Some of them apply to any vector index type, and some are specific to a certain type.
## General Options
`parallelism = {FULL, HIGH, MEDIUM, LOW} `
This is a hint for determining the number of CPU cores that participate in the construction of the index in each module. The default value is FULL, which is the highest level of parallelism. The actual number of cores participating in the index construction is determined by an internal RegattaDB algorithm and depends on the actual number of cores.
The higher the parallelism is set, the faster the index will be built. On the other hand, highly-parallel build can potentially impact transaction performance, especially when that processing is CPU-intensive. If you create a vector index while the system is running a high load of mission-critical transaction processing, consider using this parameter to lower the parallelism of the index build to avoid impact to the transactions performance.
`Modules = ((module_name [, parallelism]), ...)`
Specifies a list of modules for which the vector index should be built, out of the modules in which the table resides. The index will be built only for rows residing in those modules. If this option is not specified, the index is built for all the table rows.
When modules are specified, an optional parallelism parameter can be used for each specified module. This allows setting parallelism on a per-module basis, overriding the index-wide parameter.
Modules can be added and removed using the `ALTER VECTOR INDEX` command (see [Modify Vector Indexes](/sql/vector-index/ddl/modifying-vector-index))
### Options for the HNSW Index Type
| Name(s) | Value Range | Default Value | Description |
| - | - | - | - |
| `m connectivity` | `[2, 64]` | 16 | The maximum number of connections per layer for all the layers other than layer 0. |
| `m_0 connectivity_base` | `[m, 64]` | The minimum between 2m and 64 | The maximum number of connections in layer 0. |
| `ef_construction` | `[m_0, 65535]` | max(m\_0, 40) | The size of the dynamic candidate list for constructing the graph. |
### Options for the IVFFLAT Index Type
There is currently one option that applies only to `IVFFLAT `Index type.
`lists | num_clusters `
This option is applied in each module according to the number of rows residing in the module. The following values can be specified:
`FUNCTION SQRT [ (c) ] `
The number of clusters is the square root of the number of the rows, multiplied by a constant c. The argument c is optional, the default for c is 1.
`FUNCTION DIV(n) `
The number of clusters is the number of rows divided by n.
`FUNCTION MIN_DIV_SQRT(n [, c]) `
The number of clusters is the minimum between `DIV(n)` and `SQRT(c) `
This parameter is optional. The default is `FUNCTION MIN_DIV_SQRT(1000) `
Example:
```sql theme={null}
-- Create an IVEFLAT vector index with default parameters and system- generated name on all the modules the table resides in
CREATE VECTOR INDEX ON mytable USING IVEFLAT (mycol IP);
-- Create an HNSW vector index with your own name and parameter values on a selected set of modules, parallelism control and other options
CREATE VECTOR INDEX mytable_mycol_hnsw_ip ON mytable USING HNSW (mycol L2)
WITH (parallelisn = HIGH,
modules = ((module_a), (module_b, MEDIUM),
ef_construction = 32,
m = 10
);
```
# Deleting a Vector Index
Source: https://docs.regatta.dev/sql/vector-index/ddl/deleting-vector-index
The following command deletes a vector index.
## Synopsis
```sql theme={null}
DROP VECTOR INDEX index_name
```
# Modifying a Vector Index
Source: https://docs.regatta.dev/sql/vector-index/ddl/modifying-vector-index
The following command alters a vector index.
## Synopsis
```sql theme={null}
ALTER VECTOR INDEX index_name
action [, ...]
where action is one of the following:
ADD MODULE module_idname [ parallelism ]
DROP MODULE module_idname
ABORT MODULE ALL
```
## Description
This command can be used to add modules to and remove modules from an existing vector index. It can also be used to abort the build process for modules on which the index is currently being built.
Each `ALTER VECTOR INDEX` command may include only one type of clause out of `ADD`, `DROP `and `ABORT`. It can include multiple clauses of the same type.
Adding modules initiates the build process for the rows residing in the specified modules. The command returns once the build process has been initiated. Only after the build process is completed, the rows residing on those modules are included in approximate vector search. The `SHOW VECTOR INDEX MODULES` command (see [Show Vector Index Modules](/sql/vector-index/show-commands#show-vector-index-modules)) can be used to query the status of the build process on the modules.
Dropped modules must be in final state, i.e. `COMPLETE `or `FAILED`. (See [Show Vector Index Modules](/sql/vector-index/show-commands#show-vector-index-modules) command for description of module states). Aborted modules must be in state `BUILDING`, i.e., during the build process.
Dropping all the modules of a vector index does not cause dropping of the index. The index remains with zero modules, and it’s a valid state. However, trying to perform approximate search queries on the index will result in an error.
The `ABORT `clause aborts index build processes that are in progress. The aborted modules are removed from the index.
The following limitations apply:
* The `ABORT `clause cannot specify specific modules – it must specify `ALL`and all the modules that have a build process in progress will be aborted. The pertinent modules are removed from the index.
* While there is a build process in progress in any of the modules, adding and dropping modules is not allowed.
Examples:
```plsql theme={null}
-- Add two modules
ALTER VECTOR INDEX my_table_vec1_hnsw_ip
ADD MODULE module_c
ADD MODULE module_d MEDIUM;
-- Remove one module
ALTER VECTOR INDEX my_table_vec1_hnsw_ip DROP MODULE module_b;
-- Abort any module im which the build process is in the progress
ALTER VECTOR INDEX my_table_vec1_hnsw_ip ABORT MODULE ALL;
```
# Introduction
Source: https://docs.regatta.dev/sql/vector-index/introduction
This section describes the RegattaDB SQL specification for vector indexing.
The RegattaDB specification follows the style of the `pgvector `extension of PostgreSQL. As in other parts of the SQL specification, there are deviations from PostgreSQL where needed to support RegattaDB’s performance and functionality.
## The Vector Data Type
In order to support vector indexing and searches, we introduce the `VECTOR `type. This type is not a generic vector. A `VECTOR `column has one parameter that defines the dimension of all the vectors in the table column. In addition, the following applies to vector columns:
* A vector column’s dimension can be any integer between 1 and 2048 (inclusive).
* The data type of the vector elements is` REAL (FLOAT4) `
* Elements of the vector cannot be `NULL` and cannot have any of the values Infinity, -Infinity or NaN.
* A vector column can be nullable. The `NOT NULL` constraint is supported.
* `UNIQUE `and `PRIMARY KEY` constraints are not supported.
* A vector column cannot be a foreign key or target of a foreign key.
* Regular index for a vector column is not supported.
* Vector values are passed as strings following `pgvector `syntax.
For example:
```sql theme={null}
CREATE TABLE my_table (id INTEGER PRIMARY KEY INDEX, vec VECTOR(4));
INSERT INTO my_table VALUES (1, '[1,2,3,4]'), (2, '[1.4, 1.8, 2, 2.66]');
```
## Vector Index Operators
The following are binary operators that return the distance between two vectors. The vectors must be of the same dimension.
L2 distance
(negative) Inner product
Cosine distance
* No other operators or functions are supported for the vector type (e.g., no vector arithmetic such as adding vectors or multiplying a vector by a scalar).
* No aggregations are supported on vector columns.
# Performing Approximate Vector Searches
Source: https://docs.regatta.dev/sql/vector-index/performing-approximate-vector-searches
## Select Statements
When vector-distance operators appear within a `SELECT `statement, the following behavior applies:
When the operator is not combined with `ORDER BY` and `LIMIT`, an exact match is applied. That implies full table (or index) scan.
Examples:
```sql theme={null}
-- Select rows within a certain distance
SELECT * FROM table WHERE vec <-> '[1,2,3]' < 5;
-- Select all rows ordered by their distance from a given vector
SELECT * FROM table ORDER BY vec <=> '[1,2,3]';
-- Returns the distances of all the rows from a given vector
SELECT vec <#> '[1,2,3]' FROM table;
```
When combined with `ORDER_BY` and `LIMIT` , the following rules apply:
* If there is **no** vector index for that distance metric, exact match is applied. That implies full table (or index) scan.
* If there is **one** vector index for that distance metric, approximate match is applied.
* If there is **more than one** vector index for that distance metric, the query must specify which vector index to use using the `index_type` param described below.
For example:
```sql theme={null}
-- Select the closest 5 rows, perform approximate search if index exists
SELECT * FROM table ORDER BY vec <-> '[1,2,3]' LIMIT 5;
```
## Query Parameters
### The Supported query parameters
The following are query parameters specific to vector index searches.
`search_type = { EXACT | IVEFLAT }`
Specifies whether the approximate or exact search should be done. Note that this can be used to override the rules defined above. In particular, it can be used to force an exact search where otherwise an approximate search would be performed.
`Index_type = { HNSW | IVFFLAT } `
Specifies which index type to use. This is required when there are two vector indexes for the same column and the same distance metric.
`hnsw_ef_search = number `
This parameter is relevant to search using HNSW index. It specifies the size of the dynamic candidate list for searching the graph. Valid values are integers from 1 to 65535 inclusive. If not specified, it defaults to 64.
`ivfflat_probes = number `
This parameter is relevant to search using IVFFLAT index. Specifies the number of clusters to search in. Valid values are integers from 1 to the number of clusters (which was determined in creation). If not specified, it defaults to 1.
`modules = (module_name [, ...])`
By default, a vector index search is performed on all the modules that have a complete vector index. You may specify specific module(s) and limit the query to those modules.
### Examples
In the following examples, assume all vector columns have vector indexes.
```sql theme={null}
SELECT * FROM table
ORDER BY vec <-> '[1,2,3]' LIMIT 5
PARAMS (search_type = EXACT); -- override default
SELECT * FROM table
ORDER BY vec <-> '[1,2,3]' LIMIT 5
PARAMS (search_type = APPROX); -- this is actually the default
-- approximate search on a vector when there are two vector indexes
-- with the same distance metrics
SELECT * FROM table
ORDER BY vec <-> '[1,2,3]' LIMIT 5
PARAMS (index_type = HNSW);
-- perform the query only on a specific set of modules
SELECT * FROM table
ORDER BY vec <-> '[1,2,3]' LIMIT 5
PARAMS (hnsw_ef_search = 32, modules = (module_a, module_b));
```
### Limitations for Approximate Search Queries
The following limitations apply to approximate search queries:
* `OFFSET `is not supported with approximate search queries.
* `LIMIT `is limited to 65535 with approximate search queries. If a higher number is specified, exact search is performed. Specifying a `LIMIT `higher than 65535 and parameter `search_type = APPROX` is not allowed.
* It is not allowed to include a vector distance expressions in a hierarchical `ORDER BY `with `LIMIT `using approximate search.
For example, the following queries are not supported and would result in an error:
```sql theme={null}
SELECT * FROM table
ORDER BY vec1 <-> '[1,2,3]', vec2 <-> '[5,6,7]' LIMIT 5
PARAMS (search_type = APPROX);
SELECT * FROM table1 JOIN table2 ON table1.id = table2.id
ORDER BY table1.vec <-> '[1,2,3]', table2.vec <-> '[5,6,7]' LIMIT 5
PARAMS (search_type = APPROX);
SELECT * FROM table
ORDER BY vec1 <-> '[1,2,3]', color LIMIT 50
PARAMS (search_type = APPROX);
SELECT * FROM table
ORDER BY color, vec1 <-> '[1,2,3]', LIMIT 50
PARAMS (search_type = APPROX);
```
All those queries can be performed with exact search by omitting the `PARAMS (search_type = APPROX)` clause.
Note that a table **can** have more than one indexed vector column, the limitation applies only to a query that includes a vector column in combination with other columns in the same `ORDER BY` clause. Such query cannot use approximate search.
Approximate search is not allowed on intermediate results such as join queries, only on table queries. For example:
```sql theme={null}
-- this will result in an error
SELECT * FROM table1 JOIN table2 ON table1.color = table2.color
ORDER BY table1.vec1 <-> '[1,2,3]' LIMIT 10
-- this will work
SELECT * FROM
(SELECT * from table1 ORDER BY table1.vec1 <-> '[1,2,3]' LIMIT 10
PARAMS (search_type = APPROX) as t1
JOIN table2 ON t1.color = table2.color;
```
# Show Commands
Source: https://docs.regatta.dev/sql/vector-index/show-commands
The following commands are available to query vector indexes.
## Show Vector Indexes
This command shows all the vector indexes in the system.
### Synopsis
```sql theme={null}
SHOW VECTOR INDEXES [LIKE 'pattern' ] [ IN TABLE table_name ]
```
### Parameters
`LIKE 'pattern'`
Filter indexes by names matching the given pattern.
The pattern is case-sensitive with optional leading and/or trailing ‘%’ signs. The ‘%’ sign stands for a sequence of zero or more characters of any kind. For example, ‘foo%’ will match all the index names beginning with “foo” and ‘%foo%’ will match all the indexes that have “foo” anywhere in their name.
`IN TABLE table_name `
Show only the indexes in the given table.
### Output
The output is tabular, each row represents a vector index. The following table lists the columns.
The output is ordered by `TABLE_NAME`, `INDEX_NAME`
| Name | Type | Description |
| - | - | - |
| `TABLE_NAME` | `VARCHAR(127)` | The name of the table |
| `INDEX_NAME` | `VARCHAR(127)` | The name of the vector index |
| `COLUMN_NAME` | `VARCHAR(127)` | The name of the indexed column |
| `INDEX_TYPE` | `VARCHAR(16)` | The vector index type – either ‘`HNSW`’ or ‘`IVFFLAT`’ |
| `DISTANCE_METRIC` | `VARCHAR(16)` | The distance metric – one of ‘`COSINE`’, ‘`L2`’, ‘`IP`’ |
| `PARAMETERS` | `VARCHAR(127)` | Parameters of the index. |
| `MODULES` | `VARCHAR(1000)` | Comma-separated list of module names. If it doesn’t fit in 1000 characters, includes a partial trimmed list. |
| `STATE` | `VARCHAR(16)` | One of the following: *FAILED* – The index build had failed on at least one module. *BUILDING* – Index build in progress on any of the modules. *COMPLETE* – The index build is complete on all the modules. |
| `FAILURE_REASON` | `VARCHAR(128)` | In case the state is *FAILED*, provides information about the failure. |
## Show Vector Index Modules
This command shows the modules included in a vector index and their states.
### Synopsis
```sql theme={null}
SHOW VECTOR INDEX MODULES IN INDEX index_name [ ALL ]
```
### Parameters
`IN INDEX index_name`
Specifies the index to show. This is a mandatory parameter.
`ALL`
If this optional parameter is specified, all the modules in which the table may have rows are listed. By default, only the modules that were added to this vector index are included in the output.
### Output
The output is tabular, each row represents a module. The following table lists the columns.
The output is ordered by `NAME`.
| Name | Type | Description |
| - | - | - |
| `NAME` | `VARCHAR(128)` | The name of the module. |
| `STATE` | `VARCHAR(16)` | One of the following:
*COMPLETE* - The build is complete, rows included in searches.
*BUILDING* - The build is in progress.
*FAILED* - The build failed.
*NONE* -The module was not added to the vector index. |
| `FAILURE_REASON` | `VARCHAR(128)` | In case the state is *FAILED*, provides information about the failure. |
# Closing remarks
Source: https://docs.regatta.dev/tuning-performance/closing-remarks
Sometimes things don’t work as expected. Sometimes it’s as simple as a syntax error. Sometimes it’s a little more complex like an index that should have been used but instead a full scan is done. Perhaps a sub-query with an `IN` needs to replace a join. Or a statement is taking a lot longer than it should.
Finding out what is going on can be as simple as prefixing the statement with `EXPLAIN VERBOSE`.
In any event, please feel free to contact Regatta support.
# Distributing Indexes
Source: https://docs.regatta.dev/tuning-performance/distributing-indexes
### Index creation with default data distribution
When a column is denoted as having an index on it, by default, only one index segment is created. This segment is placed on a device chosen in a random manner. An example command that creates a table with an index with default data distribution:
```sql theme={null}
CREATE TABLE table_w_index (col1 int INDEX, col2 dec(5,4));
```
As can be seen using `SHOW TABLES`, Regatta adds a device and empty range separators:
```sql theme={null}
CREATE TABLE "table_w_index" (
"col1" int DEFAULT NULL INDEX WITH (devices = (m4d2),range_separators = ()), …)
```
### Overriding the default index creation parameters
While creating a default index is good for a quick start, it won’t necessarily provide optimal performance. The entire index will be stored in the one index segment. All index queries and scans run on the same segment, potentially making it a performance bottleneck.
In order to optimize index layouts, you can specify a list of devices on which to place the index segments and the range separators that divide the key range between the different index segments.
The index may be given segments on multiple devices and distributed to multiple nodes to get more parallelism and performance. If the index segments all contain roughly the same number of entries, this will also spread the load evenly, parallelizing scans optimally and making key lookups quickest on average. On the other hand, having too many small index segments can lead to excess operators.
On a particular device, experience with the current version has shown that 3 index segments is optimal in terms of maximizing IOs to the device and CPU usage.
Once the number of index segments has been decided, it is necessary to figure out the separators between them. If it is possible to gain insight into the distribution of values in the indexed column, this information can be used to find separators that divide that distribution roughly equally. Total precision is not necessary. If the distribution is unknown, use your best guess.
Reusing the earlier example of the person table with columns name and age, with a non-unique index on age with range separators (20, 40, 55, 70) and 5 data segments, this is what its `CREATE TABLE` might look like:
```sql theme={null}
CREATE TABLE index_seps (
name VARCHAR(20),
age int INDEX WITH (
DEVICES = (m3d0, m4d0, m5d0, m3d1, m4d1),
RANGE_SEPARATORS = (20, 40, 55, 70)))
WITH (DEVICES = (m5d1, m3d2, m4d2, m5d2, m3d0));
```
When specifiying the index structure in this way, both the `RANGE_SEPARATORS` and `DEVICES` clauses must be specified. If the `WITH DEVICES` clause is not specified for the table, it will still receive the default layout.
Note: distribution helps parallelization of operations. However, in the case
of a small table, you should consider placing the data and index segments of
the table on one and the same device.
# Distributing Tables
Source: https://docs.regatta.dev/tuning-performance/distributing-tables
### Table creation with default data distribution
There is a default placement of the data segments of new tables on the devices in a cluster. The default is that new tables are given 3 data segments on every device.
As an example, this is a `CREATE TABLE` statement with default data segment placement:
```sql theme={null}
CREATE TABLE default_table (col1 int, col2 dec(5,4));
```
The resulting layout can be displayed using a `SHOW TABLES` statement. The `--output-file` option of the `client_cli` command can be used to get untruncated output. The `TABLE_METADATA` field shows the equivalent `CREATE TABLE` statement that would explicitly define the table layout. In the example cluster that has 3 nodes each with 3 devices, the above `CREATE TABLE` command is equivalent to the following command that specifies the segments and their locations explicitly:
```sql theme={null}
CREATE TABLE "default_table" ("col1" int DEFAULT NULL, "col2" numeric(5,4) DEFAULT NULL)
WITH (devices =
(m3d0,m3d0,m3d0,m3d1,m3d1,m3d1,m3d2,m3d2,m3d2,
m4d0,m4d0,m4d0,m4d1,m4d1,m4d1,m4d2,m4d2,m4d2,
m5d0,m5d0,m5d0,m5d1,m5d1,m5d1,m5d2,m5d2,m5d2));
```
As you can see, each device is specified 3 times, thus creating 3 segments on each device.
### Overriding the default table creation parameters
You can override those defaults. You can decide to place more or fewer segments on a device, or place segments only on a subset of the devices. For example, this may be done in order to avoid using a device which is already nearly full. As another example, you may know that a table will always remain small, in which case the wide distribution of data across many nodes/devices creates more overhead that outweighs the parallel execution in terms of performance.
To take control of the distribution of segments to devices, a `WITH DEVICES` clause is added to the `CREATE TABLE`, as shown in the output of `SHOW TABLES` above. Below is an example of a `CREATE TABLE` command with a `WITH DEVICES` clause specifying 3 data segments on 2 storage devices:
```sql theme={null}
CREATE TABLE placed_table (col1 int, col2 dec(5, 4))
WITH (DEVICES = (m5d0, m5d0, m5d2));
```
A large table will get higher performance when its data segments are spread on multiple nodes and on multiple devices. On the other hand, a small table would do better on just one device. For the purpose of this discussion, small is up to a few thousand rows.
As described in [Data distribution of a table](/table-index-best-practices/introduction/data-distribution-table) above, parallel processing on a single segment is maximized when it reaches a few 10s of millions of rows. If the data distribution scheme of a table does not reach that scale, consider creating 3 segments on each device (by specifying the same device 3 times in the command). Note that any number beyond 3 segments per device won’t increase performance and should be avoided.
# Data distribution of an index
Source: https://docs.regatta.dev/tuning-performance/introduction/data-distribution-index
Regatta implements indexes using a high-performance proprietary B-tree variant. This means that the keys are maintained in order, facilitating fast and efficient range scans.
Indexes are stored in **index segments** which are distributed across storage devices. Each index segment resides on a specific device and stores a sub-range of the overall key range in its own independent B-tree. The overall index layout can be thought of as a forest of B-trees. This allows Regatta to distribute the operations on the index across multiple modules and devices. The boundaries between the index segment ranges are called **range separators**. The first index segment indexes all the rows whose values in the indexed column are strictly less than the first range separator. Each range separator in turn is then the lower bound for the next index segment. This means that the number of segments is one more than the number of range separators.
There are many implications of this index distribution. An index lookup (also known as a “point query”) needs to be sent only to one index segment. A range scan executes in parallel in all the index segments whose sub-ranges overlap that of the scan.
In the current release, the boundaries between index segments must be specified manually during index creation. It is the responsibility of the user to choose the range separators in such a way that the index segments will be roughly the same size. The number of index segments is also important as this determines the parallelism of range scans and the total throughput of multiple queries and scans. More segments across more nodes/devices lead to higher parallel processing, which is important with big tables and/or high workloads (many small transactions and/or large queries). Both lookups (queries) and inserts (when rows are inserted) are affected by the choice of the number of index segments and their key ranges. Imbalanced index segment sizes lead to an imbalance of the workload during scans, which could impact performance. Also, the larger an index segment, the higher the latency of index lookup.
# Data distribution of a table
Source: https://docs.regatta.dev/tuning-performance/introduction/data-distribution-table
The rows of a table are stored on devices in structures called data segments. A data segment resides on a specific device and contains a subset of the table’s rows. It is the basic unit of table storage and has dynamic, variable size.
When Regatta runs an operation on the rows of a table, it sends an operator to the relevant data segments of that table. This makes the number of data segments pivotal in the overall parallelism that the operations will achieve across the cluster.
On insert, new rows are distributed approximately evenly between all the data segments of a table, keeping them all roughly the same size. When a row is updated, the update takes place in the data segment that contains the row.
In addition to running big queries and inserts in a distributed and parallel manner across the data segments of a table, Regatta also applies parallel processing of transactions on each data segment. As the number of rows in a data segment increases, Regatta increases the parallelism of operators that operate on that data segment. The per-segment throughput reaches its maximum when a data segment reaches 10s of millions of rows.
# Introduction
Source: https://docs.regatta.dev/tuning-performance/introduction/introduction
Regatta is a scale-out distributed database that is designed for elasticity, including the dynamic distribution and location of table and index data. Regatta also provides optional manual parameters to further optimize data distribution of tables and indexes. This section aims to provide insights and information about this. Most of the manual configuration options described in this document will become obsolete with the release of enhanced automation and dynamic adaptation features in future Regatta versions.
The rest of this introduction provides a brief outline of Regatta’s components and processes. For more details about Regatta’s architecture, please refer to the documentation.
# How a SQL statement executes
Source: https://docs.regatta.dev/tuning-performance/introduction/sql-statement
This section will take the briefest of looks at a range query to give a quick understanding of what is going on under the hood. The purpose is to give an understanding of the effect of distribution.
Say there is a `person` table with a string column name and an integer column age, with a non-unique index on age. Suppose that the table has row segments on devices 1 through 5, and that the index has range separators (20, 40, 55, 70), with index segments on devices 6 through 10. This means that the index segment on device 6 indexes all the ages from 0 (technically, from the negative infinity value of the integral type) up to 19, the index segment on device 7 indexes all the ages from 20 to 39 and so on. The last segment starts at 70 and continues up to the positive infinity value.
Consider the execution of the following query:
```sql theme={null}
SELECT name FROM person WHERE age BETWEEN 30 AND 49;
```
The range \[30, 49] overlaps with only 2 sub-ranges, those of the index segments on devices 7 and 8. A range scan would be performed on only those 2 index segments. Index scans execute in parallel on all the involved index segments. The range scan would retrieve the row identifiers of rows in its range and each row identifier would be sent to the relevant data segment. In each data segment, further operators would retrieve the rows and project the result onto the requested field, which would then be sent back to the client.
Only 2 index segments handled the query. If the range separators had been, say, (…, 30, 35, 40, 45, 50, …), then the query would have been handled in parallel by 4 index segments. The index scan part of the query could run up to twice as fast.
In addition, the more data segments, the more parallelism is applied in the data retrieval phase.
# Structure of a Regatta cluster
Source: https://docs.regatta.dev/tuning-performance/introduction/structure-regatta-cluster
A Regatta cluster runs on one or more nodes. A node may be a bare-metal server or a virtual machine.
Within the nodes, a cluster of software modules runs the database operations. One or more modules may be placed in each node. Regatta has several different module types performing different functionalities. The *RDB* module holds tables and indexes and runs transactions. For best performance, we recommend using symmetric nodes for RDB modules, ensuring they match in CPU, RAM, disk capacity, and network specifications. There are several other modules dedicated to other cluster-wide tasks but for the sake of this document we only care about the RDB modules. Each RDB module runs on a separate Regatta node.
The storage devices on the nodes running the RDB modules are used for storing table data (rows) and indexes. In the example cluster below, devices are named by their module number and then the device number within that module. For example, m3d2 is a device attached to the node running module number 3.
### Finding information on nodes, modules and devices
The example output below shows a cluster with 3 RDB modules on 3 nodes. The RDB modules have IDs 3, 4 and 5, running on nodes 0, 1 and 2 respectively.
```sql theme={null}
rdb> show modules;
statement executed successfully
| MODULE_ROLE | MODULE_ID | NODE_NAME | MODULE_VERSION |
--------------------------------------------------------
| DCM | 2 | node_0 | 0.0.0.0 |
| GDD | 1 | node_0 | 0.0.0.0 |
| RDB | 3 | node_0 | 0.0.0.0 |
| RDB | 4 | node_1 | 0.0.0.0 |
| RDB | 5 | node_2 | 0.0.0.0 |
| Sequencer | 0 | node_0 | 0.0.0.0 |
rdb>
```
In this cluster, each RDB module has 3 devices, each 64TB, as can be seen in the following query:
```sql theme={null}
rdb> show devices;
statement executed successfully
| DEVICE_ID | MODULE_ID | CAPACITY | TYPE |
------------------------------------------------------
| m3d0 | 3 | 64424509440 | fast_devices |
| m3d1 | 3 | 64424509440 | fast_devices |
| m3d2 | 3 | 64424509440 | fast_devices |
| m4d0 | 4 | 64424509440 | fast_devices |
| m4d1 | 4 | 64424509440 | fast_devices |
| m4d2 | 4 | 64424509440 | fast_devices |
| m5d0 | 5 | 64424509440 | fast_devices |
| m5d1 | 5 | 64424509440 | fast_devices |
| m5d2 | 5 | 64424509440 | fast_devices |
rdb>
```
The following query shows the current metrics for device m3d1. The values for both its “metadata consumption percentage” and “row data consumption percentage” are 0, meaning the device is currently empty. The device would be full when these two metrics sum to 100. As shown in the other fields, the device is currently performing 342 writes per second with 1,274 KB/sec throughput, and no reads.
```sql theme={null}
rdb> show device metrics in device m3d1;
statement executed successfully
| METRIC_NAME | METRIC_ID | MODULE_ID | DEVICE_ID | VALUE | …
-------------------------------------------------------------------------------------- …
| Device metadata consumption percentage | 1001 | 3 | 1 | 0 | …
| Device read rate | 1002 | 3 | 1 | 0 | …
| Device read throughput | 1004 | 3 | 1 | 0 | …
| Device row data consumption percentage | 1000 | 3 | 1 | 0 | …
| Device write rate | 1003 | 3 | 1 | 342 | …
| Device write throughput | 1005 | 3 | 1 | 1274 | …
rdb>
```
(Output truncated to make the lines presentable here.)
# Other Index Consideration
Source: https://docs.regatta.dev/tuning-performance/other-index
### Indexing nullable columns
When a nullable column is indexed, the `NULL` value is considered to be lower than any value of the type of the column. This means that it is possible to have an index segment with only the NULL values by specifying a first range separator that is smaller than any expected value of that column. (Note: In the case of a string type, the minimal possible value is the empty string `''`.)
### Indexing high frequency values
Sometimes, in the case of a non-unique index, the indexed column has a few values that appear a large number of times. It is possible, using range separators, to index each such value in an index segment of their own. This has an advantage that values that collate close to those values will not be in large index segments.
As an (artificial) example, consider an `orders` table that has an `order_status` column.\
Suppose that there is a large number of possible values that `order_status` could have.\
Also, there is a large number of rows with status `delivered` and `returned`.\
There are also an unknown number of `orders` that don’t have a status, that is, their status is `NULL`. Without getting into too much business logic in this artificial example, suppose that scans are likely over `order_status` values that are not `delivered` or `returned`. For example, periodically the application may want to send reminders for orders that are `unpaid`. The following definition of the range separators would put the index for rows with `order_status` of `NULL`, `delivered` and `returned` into separate index segments that contain only those values:
```sql theme={null}
CREATE TABLE orders (
…,
order_status VARCHAR(11) INDEX WITH (
DEVICES = (m3d0, m3d1, m3d2, m4d0, m4d1, m4d2),
RANGE_SEPARATORS = ('', 'delivered', 'delivered ', 'returned', 'returned ')),
…
);
```
Note that this example has 6 devices for the 5 range separators, as required. The index segment on the first device holds the index for all the values strictly less than the first range separator. In this example, the first range separator is the empty string, `''`. As explained in above, all the rows that have a `NULL order_status` will be indexed in this index segment (and only those rows).
There is a subtle difference between the range separators `'delivered'` and `'delivered '`. The difference is the extra space at the end of the second. The only strings that are greater than or equal to the first but less than the second are those that are exactly `'delivered'`, so only rows with this value as their `order_status` will be indexed in this index segment. The same logic holds for `'returned'` and `'returned '`.
# Other Limitations
Source: https://docs.regatta.dev/tuning-performance/other-limitations
### Fully define a new table before using it
The current release of Regatta does not support `ALTER TABLE` operations after the table has been created. It is still possible to split the table creation into multiple statements if the first statement contains the `SET NOT READY` clause:
```sql theme={null}
CREATE TABLE SET NOT READY …
```
It is then possible to use `ALTER TABLE` statements with this table. For example:
```sql theme={null}
ALTER TABLE ADD COLUMN …
```
The last statement in the table creation sequence should then be
```sql theme={null}
ALTER TABLE SET READY;
```
Note that the table cannot be used (rows cannot be inserted), until after the completion of the `SET READY` command. That command declares that the table is fully defined and available for use.
### Index on a single column only
The current release of Regatta supports indexes only on a single column. In the case that a combination of columns needs to be indexed, a compound field may be created and maintained, with the index on the compound field.
### PRIMARY KEY INDEX
Note that in the current release, Regatta requires the keyword `INDEX` after the constraint `PRIMARY KEY`.