ID | IEP-76 |
Author | |
Sponsor | |
Created | |
Status | DRAFT |
Motivation
Thin client protocol will be the primary way to interact with Ignite 3.0 from code.
Description
Adapt Ignite 2.x protocol for Ignite 3.0. Main differences are:
TCP Socket
- Every Ignite node listens on a TCP port. Thin client implementations connect to any node in the cluster (possibly multiple nodes) through a TCP socket and perform Ignite operations using a well-defined binary protocol.
- Server-side connection parameters are defined in
ClientConnectorConfiguration
class.- Default port is 10800.
- Connector is enabled by default, no configuration changes needed.
- Netty is used on the server for network IO.
MsgPack is used for data serialization.
Data Types Mapping
Ignite data types defined in IEP-54 map to MsgPack data types the following way:
Ignite Type | Size | MsgPack Type | Notes |
---|
Bitmask(n) | ⌈n/8⌉ bytes | bin8 / bin16 / bin32 |
|
IntX, UintX | 1-8 bytes | fixint / intX / uintX | Integer types are interchangeable when possible. fixint (1 byte) can be passed as a value for uint64 column. |
Float | 4 bytes | float32 |
|
Double | 8 bytes | float64 |
|
Number([n]) | Variable | ext16 (up to 2^8 - 1 bytes) | Extension 1 |
Decimal | Variable | ext16 (up to 2^8 - 1 bytes) | Extension 2 |
UUID | 16 bytes | fixext16 | Extension 3 |
String | Variable | str |
|
Date | 3 bytes | fixext4 | Extension 4 |
Time | 4 bytes | fixext4 | Extension 5 |
Datetime | 7 bytes | fixext8 | Extension 6 |
Timestamp | 8 bytes | timestamp 64 |
|
Binary | Variable | bin32 (up to 2^32 - 1 bytes) |
|
"Extension X" is a MsgPack extension type (up to 128 extension types are allowed).
Integer data types, varint encoding
MsgPack provides multiple data types for integer values. When encoding a value, smallest data type for that value is picked automatically.
"int" is used below to denote int format family. Values such as payload size, request ID, error codes, are encoded this way - using variable number of bytes based on the value.
All messages, request and response, except handshake, start with int message length (excluding the length itself).
- Any MsgPack int type can be used (see varint above). Empty message will be single 0 byte.
- Maximum message length is 2147483647 (Integer.MAX_VALUE and maximum byte array length in Java)
int | Length of Payload |
... | Payload |
Handshake
Request |
---|
4 bytes | Magic number 49 47 4E 49, or "IGNI". Helps identifying misconfigured SSL or other apps probing the port. |
int | Payload length |
int | Version major |
int | Version minor |
int | Version patch |
int | Client code (1 for JDBC, 2 for general-purpose client) |
bin | Features (bitmask) |
map (string → any) | Extensions (auth, attributes, etc). Server can skip unknown extension data (when client is newer). |
Response |
---|
4 bytes | Magic number 49 47 4E 49, or "IGNI". Helps identifying misconfigured SSL or different server on the port. |
int | Payload length |
int | Server version major |
int | Server version minor |
int | Server version patch |
int | Error code (0 for success) |
string | Error message (when error code is not 0) |
bin | When error code is 0: Server features (bitmask) |
map (string → any) | When error code is 0: Extensions (auth, attributes, etc). Client can skip unknown extension data (when server is newer). |
Client Operations
Upon successful handshake client can start performing operations by sending a request with specific op code. Each operation has it's own request and response format, with a common header.
Request |
int | Operation code |
int | Request id, generated by client and returned as-is in response |
... | Operation-specific data |
Response |
int | Type = 0 |
int | Request id |
int | Error code (0 for success) |
string | Error message (when error code is not 0) |
... | Operation-specific data |
Request or response without operation-specific data is called basic request or basic response below.
Notifications
Clients should expect notification messages at any moment after the successful handshake.
Notification |
int | Type = 1 |
int | Notification code |
... | Notification-specific data |
Operation codes and request ids are omitted everywhere below for brevity.
TABLE_CREATE = 1
TABLE_DROP = 2
Basic response.
TABLES_GET = 3
Basic request.
Response |
---|
int | N = table count |
N * (UUID + string) | pairs of tables ids and names |
TABLE_GET = 4
Response |
---|
UUID or nil | table ID or null when table with the given name does not exist |
SCHEMAS_GET = 5
Request |
---|
UUID | table ID |
arr or nil | schema IDs, or null to get all |
Response |
---|
map (int → array (array)) | Map from schema ID to columns. Column is represented by an array of values for: name, type, isKey. The array can contain extra data in future for additional properties. |
TUPLE_UPSERT = 10
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Basic response.
Client side is supposed to match provided columns against the latest known schema. If columns don't match, request the latest schema and try again.
TUPLE_GET = 11
Request |
---|
UUID | table ID |
int | schema ID |
arr or nil | values for key columns (in schema order), or null when there is no record with the given key |
Response |
---|
int | schema id for the current tuple |
arr | tuple values in schema order |
Clients should retrieve schemas with SCHEMAS_GET and cache them per table.
TUPLE_UPSERT_ALL = 12
Request |
---|
UUID | table ID |
int | schema ID |
arr of arr | array of rows with values for all columns in given schema (nil when value is missing for a column) |
Basic response.
TUPLE_GET_ALL = 13
Request |
---|
UUID | table ID |
int | schema ID |
arr of arr | array of rows with values for key columns (in schema order) |
Response |
---|
int | schema ID (for all tuples in response) |
arr of arr | array of rows with values in schema order. Any row can be null |
TUPLE_GET_AND_UPSERT = 14
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
int | schema id for the current tuple |
arr or nil | tuple values in schema order, or null when there was no matching record |
TUPLE_INSERT = 15
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Basic response.
TUPLE_INSERT_ALL = 16
Request |
---|
UUID | table ID |
int | schema ID |
arr of arr | array of rows with values for all columns in given schema (nil when value is missing for a column) |
Basic response.
TUPLE_REPLACE = 17
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
bool | Replace result |
TUPLE_REPLACE2 = 18
Request |
---|
UUID | table ID |
int | schema ID |
arr | oldRec: values for all columns in given schema (nil when value is missing for a column) |
arr | newRec: values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
bool | Replace result |
TUPLE_GET_AND_REPLACE = 19
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
int | schema id for the current tuple |
arr or nil | tuple values in schema order, or null when there was no matching record |
TUPLE_DELETE = 20
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
bool | Delete result |
TUPLE_DELETE_ALL = 21
Request |
---|
UUID | table ID |
int | schema ID |
arr of arr | array of rows with values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
int | schema ID (for all tuples in response) |
arr of arr | Records that were not deleted: array of rows with values in schema order. |
TUPLE_DELETE_EXACT = 22
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
bool | Delete result |
TUPLE_DELETE_ALL_EXACT = 23
Request |
---|
UUID | table ID |
int | schema ID |
arr of arr | array of rows with values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
int | schema ID (for all tuples in response) |
arr of arr | Records that were not deleted: array of rows with values in schema order. |
TUPLE_GET_AND_DELETE = 24
Request |
---|
UUID | table ID |
int | schema ID |
arr | values for all columns in given schema (nil when value is missing for a column) |
Response |
---|
int | schema id for the current tuple |
arr or nil | tuple values in schema order, or null when there was no matching record |
Risks and Assumptions
- This IEP covers handshake and Tables API, which is the only public API available at the moment.
- Invoke API is out of scope: code deployment and processor serialization should be designed separately.
Discussion Links
Reference Links
Tickets
key |
summary |
type |
created |
updated |
due |
assignee |
reporter |
priority |
status |
resolution |
JQL and issue key arguments for this macro require at least one Jira application link to be configured
|