From 4df5e80c505da4ac0c80efaeac046fa32e0aa55a Mon Sep 17 00:00:00 2001 From: Mergen Imeev Date: Wed, 25 Dec 2024 12:58:11 +0300 Subject: [PATCH] proto: split proto-files This patch splits the proto file into multiple specialized proto files. This patch also adds a warning that CRUD operations are experimental. Closes #2 --- aeon_router.proto => aeon_crud.proto | 275 +-------------------------- aeon_ddl.proto | 43 +++++ aeon_diag.proto | 20 ++ aeon_error.proto | 29 +++ aeon_schema.proto | 80 ++++++++ aeon_sql.proto | 44 +++++ aeon_value.proto | 57 ++++++ generate-go.sh | 60 ++++++ 8 files changed, 340 insertions(+), 268 deletions(-) rename aeon_router.proto => aeon_crud.proto (56%) create mode 100644 aeon_ddl.proto create mode 100644 aeon_diag.proto create mode 100644 aeon_error.proto create mode 100644 aeon_schema.proto create mode 100644 aeon_sql.proto create mode 100644 aeon_value.proto create mode 100755 generate-go.sh diff --git a/aeon_router.proto b/aeon_crud.proto similarity index 56% rename from aeon_router.proto rename to aeon_crud.proto index 91dc7f2..3cdee31 100644 --- a/aeon_router.proto +++ b/aeon_crud.proto @@ -1,32 +1,15 @@ syntax = "proto3"; -package aeon_router; +import "aeon_error.proto"; +import "aeon_value.proto"; +import "aeon_schema.proto"; -option go_package = "./pb"; +package aeon; -// API to Aeon - a distributed database based on Tarantool. -service AeonRouterService { - // - // Diagnostic requests. - // - - // Pings the router. - rpc Ping(PingRequest) returns (PingResponse) {} - - // - // DDL requests. - // - - // Creates a space with the given definition. - rpc CreateSpace(CreateSpaceRequest) returns (CreateSpaceResponse) {} - - // Drops a space by name. - rpc DropSpace(DropSpaceRequest) returns (DropSpaceResponse) {} - - // - // DML requests. - // +// ATTENTION: This module is EXPERIMENTAL and we do not recommend using it. +// CRUD API to Aeon - a distributed database based on Tarantool. +service CRUDService { // Transactionally executes a set of read and write operations. rpc Execute(ExecuteRequest) returns (ExecuteResponse) {} @@ -47,222 +30,6 @@ service AeonRouterService { // Non-transactionally select tuples from a space. rpc Select(SelectRequest) returns (stream SelectResponse) {} - - // - // SQL requests. - // - - // Execute a SQL query. - rpc SQL(SQLRequest) returns (SQLResponse) {} - - // Execute a SQL query and return the result using a stream. - rpc SQLStream(SQLRequest) returns (stream SQLResponse) {} - - // Check if an SQL is valid - // We provide the method for database CLI. - rpc SQLCheck(SQLRequest) returns (SQLCheckResponse) {} -} - -// -// Common structures. -// - -// Special value denoting null. -enum NullValue { NULL_VALUE = 0; } - -// Array of arbitrary-typed values. -message ArrayValue { repeated Value fields = 1; } - -// Map with string keys and arbitrary-typed values.. -message MapValue { map fields = 1; } - -// Date time value. -message DateTimeValue { - int64 seconds = 1; - int64 nsec = 2; - string location = 3; -} - -// Date time interval value. -message IntervalValue { - enum IntervalAdjust { - INTERVAL_ADJUST_NONE = 0; - INTERVAL_ADJUST_EXCESS = 1; - INTERVAL_ADJUST_LAST = 2; - } - int64 year = 1; - int64 month = 2; - int64 week = 3; - int64 day = 4; - int64 hour = 5; - int64 min = 6; - int64 sec = 7; - int64 nsec = 8; - IntervalAdjust adjust = 9; -} - -// Arbitrary value that can be serialized to be sent over the network or -// stored in the database. -message Value { - oneof kind { - uint64 unsigned_value = 1; - string string_value = 2; - double number_value = 3; - sint64 integer_value = 4; - bool boolean_value = 5; - bytes varbinary_value = 6; - string decimal_value = 7; - string uuid_value = 8; - DateTimeValue datetime_value = 9; - IntervalValue interval_value = 10; - ArrayValue array_value = 11; - MapValue map_value = 12; - NullValue null_value = 13; - } -} - -// Error information. -message Error { - // Error type. - // * AeonError for core Aeon errors. - // * AeonSQLError for issues with SQL parsing. - // * AeonGRPCError for issues with gRPC encoding. - string type = 1; - // Error name. - string name = 2; - // Error location: file, line. - string file = 3; - uint64 line = 4; - // Human-readable error description. - string msg = 5; - // System errno (usually not set). - uint64 errno = 6; - // Error code. - uint64 code = 7; - // Fields with extra information. - MapValue fields = 8; - // Previous error on the error stack (cause of this error). - Error prev = 9; -} - -// Tuple: array of values. -message Tuple { repeated Value fields = 1; } - -// Tuple format: array of field names. -message TupleFormat { repeated string names = 1; } - -// Read or write operation executed in a transaction. -message Operation { - // Target space name. - string space = 1; - // Target key in the space. Must be full (have all defined key parts). - Tuple key = 2; - // In a request: - // * Ignored for read operations. - // * Specifies the tuple to write in a write operation. - // In a response: - // * Tuple read from or written to the target space. - // The write operation type depends on the tuple value: - // * NOP if the tuple is not set. - // * DELETE if the tuple is set but has no fields. - // * REPLACE otherwise. The tuple must match the target key. - // The tuple may be overwritten by the user-defined function specified in - // a request to change the written value or even operation type depending on - // read values. - Tuple tuple = 3; -} - -// Type a space field can have. -enum FieldType { - FIELD_TYPE_UNSPECIFIED = 0; - FIELD_TYPE_ANY = 1; - FIELD_TYPE_UNSIGNED = 2; - FIELD_TYPE_STRING = 3; - FIELD_TYPE_NUMBER = 4; - FIELD_TYPE_DOUBLE = 5; - FIELD_TYPE_INTEGER = 6; - FIELD_TYPE_BOOLEAN = 7; - FIELD_TYPE_VARBINARY = 8; - FIELD_TYPE_SCALAR = 9; - FIELD_TYPE_DECIMAL = 10; - FIELD_TYPE_UUID = 11; - FIELD_TYPE_DATETIME = 12; - FIELD_TYPE_INTERVAL = 13; - FIELD_TYPE_ARRAY = 14; - FIELD_TYPE_MAP = 15; -} - -// Space field definition. -message FieldDef { - // Field name. - string name = 1; - // Field type. - FieldType type = 2; - // If set to true, the field may store null values. Optional. - bool is_nullable = 3; -} - -// Key part definition. -message KeyPartDef { - enum KeyPartSortOrder { - KEY_PART_SORT_ORDER_ASC = 0; - KEY_PART_SORT_ORDER_DESC = 1; - } - // Indexed field ordinal number (1-based) or name. - oneof field { - uint64 id = 1; - string name = 2; - } - // Key part type. Optional: if omitted, it will be deduced from - // the corresponding space field type. - FieldType type = 3; - // Sorting order: ascending (default) or descending. - KeyPartSortOrder sort_order = 4; -} - -// -// Diagnostic requests. -// - -// Pings the router. - -message PingRequest {} - -message PingResponse { - // Error information. Set only on failure. - Error error = 1; -} - -// -// DDL requests. -// - -// Creates a space with the given definition. - -message CreateSpaceRequest { - // Name of the new space. - string name = 1; - // Format of the new space. - repeated FieldDef format = 2; - // Sorting key definition (indexed fields). - repeated KeyPartDef key_def = 3; -} - -message CreateSpaceResponse { - // Error information. Set only on failure. - Error error = 1; -} - -// Drops a space by name. - -message DropSpaceRequest { - // Name of the space to drop. - string name = 1; -} - -message DropSpaceResponse { - // Error information. Set only on failure. - Error error = 1; } // @@ -496,31 +263,3 @@ message SelectResponse { // Format of the returned tuples. TupleFormat tuple_format = 8; } - -// -// SQL requests. -// - -message SQLRequest { - // SQL query. - string query = 1; - // Bind variables. - map vars = 2; -} - -message SQLResponse { - // Error information. Set only on failure. - Error error = 1; - // Retrieved tuples. - repeated Tuple tuples = 2; - // Format of the returned tuples. - TupleFormat tuple_format = 3; -} - -enum SQLCheckStatus { - SQL_QUERY_VALID = 0; - SQL_QUERY_INCOMPLETE = 1; - SQL_QUERY_INVALID = 2; -} - -message SQLCheckResponse { SQLCheckStatus status = 1; } diff --git a/aeon_ddl.proto b/aeon_ddl.proto new file mode 100644 index 0000000..a92b828 --- /dev/null +++ b/aeon_ddl.proto @@ -0,0 +1,43 @@ +syntax = "proto3"; + +import "aeon_error.proto"; +import "aeon_schema.proto"; + +package aeon; + +// DDL API to Aeon - a distributed database based on Tarantool. +service DDLService { + // Creates a space with the given definition. + rpc CreateSpace(CreateSpaceRequest) returns (CreateSpaceResponse) {} + + // Drops a space by name. + rpc DropSpace(DropSpaceRequest) returns (DropSpaceResponse) {} +} + +// Creates a space with the given definition. + +message CreateSpaceRequest { + // Name of the new space. + string name = 1; + // Format of the new space. + repeated FieldDef format = 2; + // Sorting key definition (indexed fields). + repeated KeyPartDef key_def = 3; +} + +message CreateSpaceResponse { + // Error information. Set only on failure. + Error error = 1; +} + +// Drops a space by name. + +message DropSpaceRequest { + // Name of the space to drop. + string name = 1; +} + +message DropSpaceResponse { + // Error information. Set only on failure. + Error error = 1; +} diff --git a/aeon_diag.proto b/aeon_diag.proto new file mode 100644 index 0000000..acdf014 --- /dev/null +++ b/aeon_diag.proto @@ -0,0 +1,20 @@ +syntax = "proto3"; + +import "aeon_error.proto"; + +package aeon; + +// Diagnostic API to Aeon - a distributed database based on Tarantool. +service DiagService { + // Pings the router. + rpc Ping(PingRequest) returns (PingResponse) {} +} + +// Pings the router. + +message PingRequest {} + +message PingResponse { + // Error information. Set only on failure. + Error error = 1; +} diff --git a/aeon_error.proto b/aeon_error.proto new file mode 100644 index 0000000..24715c0 --- /dev/null +++ b/aeon_error.proto @@ -0,0 +1,29 @@ +syntax = "proto3"; + +import "aeon_value.proto"; + +package aeon; + +// Error information. +message Error { + // Error type. + // * AeonError for core Aeon errors. + // * AeonSQLError for issues with SQL parsing. + // * AeonGRPCError for issues with gRPC encoding. + string type = 1; + // Error name. + string name = 2; + // Error location: file, line. + string file = 3; + uint64 line = 4; + // Human-readable error description. + string msg = 5; + // System errno (usually not set). + uint64 errno = 6; + // Error code. + uint64 code = 7; + // Fields with extra information. + MapValue fields = 8; + // Previous error on the error stack (cause of this error). + Error prev = 9; +} diff --git a/aeon_schema.proto b/aeon_schema.proto new file mode 100644 index 0000000..a1fa02f --- /dev/null +++ b/aeon_schema.proto @@ -0,0 +1,80 @@ +syntax = "proto3"; + +import "aeon_value.proto"; + +package aeon; + +// Tuple: array of values. +message Tuple { repeated Value fields = 1; } + +// Tuple format: array of field names. +message TupleFormat { repeated string names = 1; } + +// Read or write operation executed in a transaction. +message Operation { + // Target space name. + string space = 1; + // Target key in the space. Must be full (have all defined key parts). + Tuple key = 2; + // In a request: + // * Ignored for read operations. + // * Specifies the tuple to write in a write operation. + // In a response: + // * Tuple read from or written to the target space. + // The write operation type depends on the tuple value: + // * NOP if the tuple is not set. + // * DELETE if the tuple is set but has no fields. + // * REPLACE otherwise. The tuple must match the target key. + // The tuple may be overwritten by the user-defined function specified in + // a request to change the written value or even operation type depending on + // read values. + Tuple tuple = 3; +} + +// Type a space field can have. +enum FieldType { + FIELD_TYPE_UNSPECIFIED = 0; + FIELD_TYPE_ANY = 1; + FIELD_TYPE_UNSIGNED = 2; + FIELD_TYPE_STRING = 3; + FIELD_TYPE_NUMBER = 4; + FIELD_TYPE_DOUBLE = 5; + FIELD_TYPE_INTEGER = 6; + FIELD_TYPE_BOOLEAN = 7; + FIELD_TYPE_VARBINARY = 8; + FIELD_TYPE_SCALAR = 9; + FIELD_TYPE_DECIMAL = 10; + FIELD_TYPE_UUID = 11; + FIELD_TYPE_DATETIME = 12; + FIELD_TYPE_INTERVAL = 13; + FIELD_TYPE_ARRAY = 14; + FIELD_TYPE_MAP = 15; +} + +// Space field definition. +message FieldDef { + // Field name. + string name = 1; + // Field type. + FieldType type = 2; + // If set to true, the field may store null values. Optional. + bool is_nullable = 3; +} + +// Key part definition. +message KeyPartDef { + enum KeyPartSortOrder { + KEY_PART_SORT_ORDER_ASC = 0; + KEY_PART_SORT_ORDER_DESC = 1; + } + // Indexed field ordinal number (1-based) or name. + oneof field { + uint64 id = 1; + string name = 2; + } + // Key part type. Optional: if omitted, it will be deduced from + // the corresponding space field type. + FieldType type = 3; + // Sorting order: ascending (default) or descending. + KeyPartSortOrder sort_order = 4; +} diff --git a/aeon_sql.proto b/aeon_sql.proto new file mode 100644 index 0000000..9334353 --- /dev/null +++ b/aeon_sql.proto @@ -0,0 +1,44 @@ +syntax = "proto3"; + +import "aeon_error.proto"; +import "aeon_value.proto"; +import "aeon_schema.proto"; + +package aeon; + +// SQL API to Aeon - a distributed database based on Tarantool. +service SQLService { + // Execute a SQL query. + rpc SQL(SQLRequest) returns (SQLResponse) {} + + // Execute a SQL query and return the result using a stream. + rpc SQLStream(SQLRequest) returns (stream SQLResponse) {} + + // Check if an SQL is valid + // We provide the method for database CLI. + rpc SQLCheck(SQLRequest) returns (SQLCheckResponse) {} +} + +message SQLRequest { + // SQL query. + string query = 1; + // Bind variables. + map vars = 2; +} + +message SQLResponse { + // Error information. Set only on failure. + Error error = 1; + // Retrieved tuples. + repeated Tuple tuples = 2; + // Format of the returned tuples. + TupleFormat tuple_format = 3; +} + +enum SQLCheckStatus { + SQL_QUERY_VALID = 0; + SQL_QUERY_INCOMPLETE = 1; + SQL_QUERY_INVALID = 2; +} + +message SQLCheckResponse { SQLCheckStatus status = 1; } diff --git a/aeon_value.proto b/aeon_value.proto new file mode 100644 index 0000000..958a2af --- /dev/null +++ b/aeon_value.proto @@ -0,0 +1,57 @@ +syntax = "proto3"; + +package aeon; + +// Special value denoting null. +enum NullValue { NULL_VALUE = 0; } + +// Array of arbitrary-typed values. +message ArrayValue { repeated Value fields = 1; } + +// Map with string keys and arbitrary-typed values.. +message MapValue { map fields = 1; } + +// Date time value. +message DateTimeValue { + int64 seconds = 1; + int64 nsec = 2; + string location = 3; +} + +// Date time interval value. +message IntervalValue { + enum IntervalAdjust { + INTERVAL_ADJUST_NONE = 0; + INTERVAL_ADJUST_EXCESS = 1; + INTERVAL_ADJUST_LAST = 2; + } + int64 year = 1; + int64 month = 2; + int64 week = 3; + int64 day = 4; + int64 hour = 5; + int64 min = 6; + int64 sec = 7; + int64 nsec = 8; + IntervalAdjust adjust = 9; +} + +// Arbitrary value that can be serialized to be sent over the network or +// stored in the database. +message Value { + oneof kind { + uint64 unsigned_value = 1; + string string_value = 2; + double number_value = 3; + sint64 integer_value = 4; + bool boolean_value = 5; + bytes varbinary_value = 6; + string decimal_value = 7; + string uuid_value = 8; + DateTimeValue datetime_value = 9; + IntervalValue interval_value = 10; + ArrayValue array_value = 11; + MapValue map_value = 12; + NullValue null_value = 13; + } +} diff --git a/generate-go.sh b/generate-go.sh new file mode 100755 index 0000000..6d92e38 --- /dev/null +++ b/generate-go.sh @@ -0,0 +1,60 @@ +#!/usr/bin/env bash + +usage(){ +>&2 cat << EOF +Usage: $0 -p|--package NAME [-o|--out] PATH +Generate Go bindings for Aeon proto files. + +Options: + --package NAME: Go package name. + --out PATH: Path to the output directory. +EOF +exit 1 +} + +VALID_ARGS=$(getopt -o p:o: --long package:,out: -- "$@") +if [[ $? -ne 0 ]]; then + usage +fi + +eval set -- "$VALID_ARGS" +while [ : ]; do + case "$1" in + -p | --package) + package=$2 + shift 2 + ;; + -o | --out) + out=$2 + shift 2 + ;; + --) shift; + break + ;; + esac +done + +if [[ -z $package ]] +then + usage +fi + +if [[ -z $out ]] +then + out=. +else + mkdir -p $out +fi + +proto_path=$(dirname $(readlink -f $0)) +cmd="protoc --proto_path=$proto_path --go_out=$out --go-grpc_out=$out" +for file in ${proto_path}/* +do + name=$(basename $file) + if [[ $name = *.proto ]] + then + cmd="$cmd --go_opt=M${name}=$package --go-grpc_opt=M${name}=$package $name" + fi +done + +eval $cmd