// ┏━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┓ // ┃ ██████ ██████ ██████ █ █ █ █ █ █▄ ▀███ █ ┃ // ┃ ▄▄▄▄▄█ █▄▄▄▄▄ ▄▄▄▄▄█ ▀▀▀▀▀█▀▀▀▀▀ █ ▀▀▀▀▀█ ████████▌▐███ ███▄ ▀█ █ ▀▀▀▀▀ ┃ // ┃ █▀▀▀▀▀ █▀▀▀▀▀ █▀██▀▀ ▄▄▄▄▄ █ ▄▄▄▄▄█ ▄▄▄▄▄█ ████████▌▐███ █████▄ █ ▄▄▄▄▄ ┃ // ┃ █ ██████ █ ▀█▄ █ ██████ █ ███▌▐███ ███████▄ █ ┃ // ┣━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┫ // ┃ Copyright (c) 2017, the Perspective Authors. ┃ // ┃ ╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌╌ ┃ // ┃ This file is part of the Perspective library, distributed under the terms ┃ // ┃ of the [Apache License 2.0](https://www.apache.org/licenses/LICENSE-2.0). ┃ // ┗━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┛ syntax = "proto3"; import "google/protobuf/struct.proto"; package perspective.proto; option optimize_for = LITE_RUNTIME; //////////////////////////////////////////////////////////////////////////////// // // Common enum StatusCode { SERVER_ERROR = 0; VIEW_NOT_FOUND = 1; TRANSPORT_ERROR = 2; } // Recoverable, user-readable error reporting from the engine. message ServerError { string message = 1; StatusCode status_code = 2; } message Schema { repeated KeyTypePair schema = 1; message KeyTypePair { string name = 1; ColumnType type = 2; } } // The data type constructors Perspective supports. message MakeTableData { oneof data { Schema from_schema = 1; string from_csv = 2; bytes from_arrow = 3; string from_rows = 4; string from_cols = 5; string from_view = 6; string from_ndjson = 7; }; } // Filter type scalars - this is _not_ the same as a Columns scalar, as this // value is used in the view config and must be JSON safe! message Scalar { oneof scalar { bool bool = 1; // int64 date = 2; // TODO these are the wrong type // int64 datetime = 3; double float = 4; // int32 int = 5; string string = 6; google.protobuf.NullValue null = 7; } } // View types enum ColumnType { STRING = 0; DATE = 1; DATETIME = 2; INTEGER = 3; FLOAT = 4; BOOLEAN = 5; } // Options for requresting a slice of data, starting with the rectangular // viewport. message ViewPort { optional uint32 start_row = 1; optional uint32 start_col = 2; optional uint32 end_row = 3; optional uint32 end_col = 4; optional bool emit_legacy_row_path_names = 5; // optional bool id = 5; // optional bool index = 3; // optional bool formatted = 6; // optional bool leaves_only = 7; // optional bool compression = 3; } // TODO This belongs in features enum SortOp { SORT_NONE = 0; SORT_ASC = 1; SORT_DESC = 2; SORT_COL_ASC = 3; SORT_COL_DESC = 4; SORT_ASC_ABS = 5; SORT_DESC_ABS = 6; SORT_COL_ASC_ABS = 7; SORT_COL_DESC_ABS = 8; } //////////////////////////////////////////////////////////////////////////////// // // RPC message Request { uint32 msg_id = 1; string entity_id = 2; oneof client_req { // Minimum Virtual API (theoretical). GetFeaturesReq get_features_req = 3; GetHostedTablesReq get_hosted_tables_req = 4; RemoveHostedTablesUpdateReq remove_hosted_tables_update_req = 37; TableMakePortReq table_make_port_req = 5; TableMakeViewReq table_make_view_req = 6; TableSchemaReq table_schema_req = 7; TableSizeReq table_size_req = 8; TableValidateExprReq table_validate_expr_req = 9; ViewColumnPathsReq view_column_paths_req = 10; ViewDeleteReq view_delete_req = 11; ViewDimensionsReq view_dimensions_req = 12; ViewExpressionSchemaReq view_expression_schema_req = 13; ViewGetConfigReq view_get_config_req = 14; ViewSchemaReq view_schema_req = 15; ViewToArrowReq view_to_arrow_req = 16; // Optional (we can enable real-time/autocomplete/etc with these, but // not required). ServerSystemInfoReq server_system_info_req = 17; ViewCollapseReq view_collapse_req = 18; ViewExpandReq view_expand_req = 19; ViewGetMinMaxReq view_get_min_max_req = 20; ViewOnUpdateReq view_on_update_req = 21; ViewRemoveOnUpdateReq view_remove_on_update_req = 22; ViewSetDepthReq view_set_depth_req = 23; ViewToColumnsStringReq view_to_columns_string_req = 24; ViewToCSVReq view_to_csv_req = 25; ViewToRowsStringReq view_to_rows_string_req = 26; ViewToNdjsonStringReq view_to_ndjson_string_req = 36; // External (we don't need these for viewer, but the developer may). MakeTableReq make_table_req = 27; TableDeleteReq table_delete_req = 28; TableOnDeleteReq table_on_delete_req = 29; TableRemoveDeleteReq table_remove_delete_req = 30; TableRemoveReq table_remove_req = 31; TableReplaceReq table_replace_req = 32; TableUpdateReq table_update_req = 33; ViewOnDeleteReq view_on_delete_req = 34; ViewRemoveDeleteReq view_remove_delete_req = 35; MakeJoinTableReq make_join_table_req = 38; } } message Response { uint32 msg_id = 1; string entity_id = 2; oneof client_resp { GetFeaturesResp get_features_resp = 3; GetHostedTablesResp get_hosted_tables_resp = 4; RemoveHostedTablesUpdateResp remove_hosted_tables_update_resp = 37; TableMakePortResp table_make_port_resp = 5; TableMakeViewResp table_make_view_resp = 6; TableSchemaResp table_schema_resp = 7; TableSizeResp table_size_resp = 8; TableValidateExprResp table_validate_expr_resp = 9; ViewColumnPathsResp view_column_paths_resp = 10; ViewDeleteResp view_delete_resp = 11; ViewDimensionsResp view_dimensions_resp = 12; ViewExpressionSchemaResp view_expression_schema_resp = 13; ViewGetConfigResp view_get_config_resp = 14; ViewSchemaResp view_schema_resp = 15; ViewToArrowResp view_to_arrow_resp = 16; ServerSystemInfoResp server_system_info_resp = 17; ViewCollapseResp view_collapse_resp = 18; ViewExpandResp view_expand_resp = 19; ViewGetMinMaxResp view_get_min_max_resp = 20; ViewOnUpdateResp view_on_update_resp = 21; ViewRemoveOnUpdateResp view_remove_on_update_resp = 22; ViewSetDepthResp view_set_depth_resp = 23; ViewToColumnsStringResp view_to_columns_string_resp = 24; ViewToCSVResp view_to_csv_resp = 25; ViewToRowsStringResp view_to_rows_string_resp = 26; ViewToNdjsonStringResp view_to_ndjson_string_resp = 36; MakeTableResp make_table_resp = 27; TableDeleteResp table_delete_resp = 28; TableOnDeleteResp table_on_delete_resp = 29; TableRemoveDeleteResp table_remove_delete_resp = 30; TableRemoveResp table_remove_resp = 31; TableReplaceResp table_replace_resp = 32; TableUpdateResp table_update_resp = 33; ViewOnDeleteResp view_on_delete_resp = 34; ViewRemoveDeleteResp view_remove_delete_resp = 35; MakeJoinTableResp make_join_table_resp = 38; ServerError server_error = 50; } } //////////////////////////////////////////////////////////////////////////////// // // Virtual API enum GroupRollupMode { ROLLUP = 0; FLAT = 1; TOTAL = 2; } // Informs the client of the feature set, e.g. what to expect in the // `ViewConfig` message. message GetFeaturesReq {} message GetFeaturesResp { bool group_by = 1; bool split_by = 2; bool expressions = 3; bool on_update = 4; bool sort = 5; map filter_ops = 6; map aggregates = 7; repeated GroupRollupMode group_rollup_mode = 8; message ColumnTypeOptions { repeated string options = 1; } message AggregateOptions { repeated AggregateArgs aggregates = 1; } message AggregateArgs { string name = 1; repeated ColumnType args = 2; } } // `Client::get_hosted_tables` message GetHostedTablesReq { bool subscribe = 1; } message GetHostedTablesResp { repeated HostedTable table_infos = 1; } message HostedTable { string entity_id = 1; optional string index = 2; optional uint32 limit = 3; } message RemoveHostedTablesUpdateReq { uint32 id = 1; } message RemoveHostedTablesUpdateResp {} // `Table::size` message TableSizeReq {} message TableSizeResp { uint32 size = 2; } // `Table::schema` message TableSchemaReq {} message TableSchemaResp { Schema schema = 1; } // `Table::validate_expressions` // TODO: This should be just `validate()` message TableValidateExprReq { map column_to_expr = 1; } message TableValidateExprResp { map expression_schema = 1; map errors = 2; map expression_alias = 3; message ExprValidationError { string error_message = 1; uint32 line = 2; uint32 column = 3; } } // `Table::view` message TableMakeViewReq { string view_id = 1; ViewConfig config = 2; } message TableMakeViewResp { string view_id = 1; } // `View::schema` message ViewSchemaReq {} message ViewSchemaResp { map schema = 1; } // `View::dimensions` message ViewDimensionsReq {} message ViewDimensionsResp { uint32 num_table_rows = 1; uint32 num_table_columns = 2; uint32 num_view_rows = 3; uint32 num_view_columns = 4; } // `View::get_config` message ViewGetConfigReq {} message ViewGetConfigResp { ViewConfig config = 1; } //////////////////////////////////////////////////////////////////////////////// // `Client::table`. message MakeTableReq { MakeTableData data = 1; optional MakeTableOptions options = 2; message MakeTableOptions { oneof make_table_type { string make_index_table = 1; uint32 make_limit_table = 2; }; // Back this Table's canonical data with the on-disk storage backend // (memory-mapped file on native; OPFS on WASM) instead of memory. // Orthogonal to `make_table_type`, so it is a standalone field. optional bool page_to_disk = 3; } } message MakeTableResp {} enum JoinType { INNER = 0; LEFT = 1; OUTER = 2; } // `Client::join` — create a read-only table from a JOIN of two tables. message MakeJoinTableReq { string left_table_id = 1; string right_table_id = 2; string on_column = 3; JoinType join_type = 4; string right_on_column = 5; } message MakeJoinTableResp {} // `Table::delete` message TableDeleteReq { bool is_immediate = 1; } message TableDeleteResp {} // `Table::on_delete` message TableOnDeleteReq {} message TableOnDeleteResp {} // `Table::make_port` message TableMakePortReq {} message TableMakePortResp { uint32 port_id = 1; } // `Table::remove_delete` message TableRemoveDeleteReq { uint32 id = 1; } message TableRemoveDeleteResp {} // `Table::update` message TableUpdateReq { MakeTableData data = 1; uint32 port_id = 2; } message TableUpdateResp {} // `Table::replace` message TableReplaceReq { MakeTableData data = 1; } message TableReplaceResp {} // `Table::remove` message TableRemoveReq { MakeTableData data = 1; } message TableRemoveResp {} message ViewOnUpdateReq { enum Mode { ROW = 0; } optional Mode mode = 1; } message ViewOnUpdateResp { optional bytes delta = 1; uint32 port_id = 2; } message ViewOnDeleteReq {} message ViewOnDeleteResp {} message ViewRemoveDeleteReq { uint32 id = 1; } message ViewRemoveDeleteResp {} message ViewToColumnsStringReq { ViewPort viewport = 1; optional bool id = 2; optional bool index = 3; optional bool formatted = 4; } message ViewToColumnsStringResp { string json_string = 1; } message ViewToRowsStringReq { ViewPort viewport = 1; optional bool id = 2; optional bool index = 3; optional bool formatted = 4; } message ViewToRowsStringResp { string json_string = 1; } message ViewToNdjsonStringReq { ViewPort viewport = 1; optional bool id = 2; optional bool index = 3; optional bool formatted = 4; } message ViewToNdjsonStringResp { string ndjson_string = 1; } message ViewToArrowReq { ViewPort viewport = 1; optional string compression = 2; } message ViewToArrowResp { bytes arrow = 1; } message ViewColumnPathsReq { optional uint32 start_col = 1; optional uint32 end_col = 2; } // // TODO This is a better paths representations but its not compatible with // // the legacy API. Let's do this when we can fix the API. // message ColumnPath { // repeated string path = 1; // } message ViewColumnPathsResp { repeated string paths = 1; // repeated ColumnPath paths = 1; } message ViewDeleteReq {} message ViewDeleteResp {} message ViewGetMinMaxReq { string column_name = 1; } message ViewGetMinMaxResp { Scalar min = 1; Scalar max = 2; } message ViewExpressionSchemaReq {} message ViewExpressionSchemaResp { map schema = 1; } message ViewToCSVReq { ViewPort viewport = 1; } message ViewToCSVResp { string csv = 1; } message ViewRemoveOnUpdateReq { uint32 id = 1; } message ViewRemoveOnUpdateResp {} message ViewCollapseReq { uint32 row_index = 1; } message ViewCollapseResp { uint32 num_changed = 1; } message ViewExpandReq { uint32 row_index = 1; } message ViewExpandResp { uint32 num_changed = 1; } // `View::set_depth` message ViewSetDepthReq { uint32 depth = 1; } message ViewSetDepthResp {} message ServerSystemInfoReq {} message ServerSystemInfoResp { uint64 heap_size = 1; uint64 used_size = 2; uint32 cpu_time = 3; uint32 cpu_time_epoch = 4; } message ViewConfig { repeated string group_by = 1; repeated string split_by = 2; ColumnsUpdate columns = 3; repeated Filter filter = 4; repeated Sort sort = 5; map expressions = 6; map aggregates = 7; FilterReducer filter_op = 8; optional uint32 group_by_depth = 9; optional GroupRollupMode group_rollup_mode = 10; message AggList { repeated string aggregations = 1; } message Sort { string column = 1; SortOp op = 2; } message Filter { string column = 1; string op = 2; repeated Scalar value = 3; } enum FilterReducer { AND = 0; OR = 1; } } message ColumnsUpdate { oneof opt_columns { google.protobuf.NullValue default_columns = 1; Columns columns = 2; } message Columns { repeated string columns = 1; } }