/*
 * Copyright 2020-2020 Exactpro (Exactpro Systems Limited)
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

syntax = "proto3";

package th2.data_provider;

import "th2_grpc_common/common.proto";
import "google/protobuf/timestamp.proto";
import "google/protobuf/any.proto";
import "google/protobuf/wrappers.proto";

option java_multiple_files = true;
option java_package = "com.exactpro.th2.dataprovider.grpc";


service DataProvider {

  /* returns a single event with the specified id */
  rpc getEvent (EventID) returns (EventResponse) {
  }

  /* returns a list of events with the specified ids */
  rpc getEvents (BulkEventRequest) returns (BulkEventResponse) {
  }

  /* returns a single message with the specified id */
  rpc getMessage (MessageID) returns (MessageGroupResponse) {
  }

  /* returns a list of message stream names */
  rpc getMessageStreams (MessageStreamsRequest) returns (MessageStreamsResponse) {
  }

  /* creates a message stream that matches the filter. */
  rpc searchMessages (MessageSearchRequest) returns (stream MessageSearchResponse) {

  }

  /* creates an event or an event metadata stream that matches the filter. */
  rpc searchEvents (EventSearchRequest) returns (stream EventSearchResponse) {

  }

  /* returns available message filters */
  rpc getMessagesFilters (MessageFiltersRequest) returns (FilterNamesResponse) {
  }

  /* returns available event filters */
  rpc getEventsFilters (EventFiltersRequest) returns (FilterNamesResponse) {
  }

  /* returns available filter parameters */
  rpc getEventFilterInfo (FilterInfoRequest) returns (FilterInfoResponse) {
  }

  /* returns available filter parameters */
  rpc getMessageFilterInfo (FilterInfoRequest) returns (FilterInfoResponse) {
  }

  /* checks if the specified event matches the filter */
  rpc matchEvent (EventMatchRequest) returns (MatchResponse) {
  }

  /* checks if the specified message matches the filter */
  rpc matchMessage (MessageMatchRequest) returns (MatchResponse) {
  }
}

message MessageStreamsRequest {

}

message MessageFiltersRequest {

}

message EventFiltersRequest {

}

message EventResponse {
  EventID event_id = 1; // Current event id
  EventID parent_event_id = 2; // Event id of a parent event. It is absent for root event

  EventID batch_id = 3; // Event id of a parent event. It is absent for root event

  bool is_batched = 4; // Flag indicating that the event is in batch

  google.protobuf.Timestamp start_timestamp = 5;
  google.protobuf.Timestamp end_timestamp = 6; // May be absent.
  EventStatus status = 7; // Aggregated status of current and children events which sync written.
  string event_name = 8;
  string event_type = 9; // May be absent.
  bytes body = 10; // May be absent.
  repeated MessageID attached_message_id = 11; // ids of messages linked to this event
}

message EventMetadata {
  EventID event_id = 1; // Current event id
  EventID parent_event_id = 2; // Event id of a parent event. It is absent for root event

  google.protobuf.Timestamp start_timestamp = 3;
  EventStatus status = 4; // Aggregated status of current and children events which sync written.
  string event_name = 5;
  string event_type = 6;
}

message BulkEventRequest {
  repeated EventID id = 1;
}

message BulkEventResponse {
  repeated EventResponse event = 1;
}

message MessageGroupItem {
  Message message = 1;
  bool match = 2;
}

message MessageGroupResponse {
  MessageID message_id = 1; // Message id should be unique in session
  google.protobuf.Timestamp timestamp = 2; // Message creation timestamp
  bytes body_raw = 3;
  repeated EventID attached_event_id = 4; // ids of events linked to this message group
  repeated MessageGroupItem message_item = 5; // May be absent.
}

message FilterInfoRequest {
  FilterName filter_name = 1;
}

message FilterName {
  string name = 1;
}

message FilterNamesResponse {
  repeated FilterName filter_name = 1;
}

message FilterParameter {
  string name = 1;
  FilterParameterType type = 2;
  google.protobuf.Any default_value = 3;
  string hint = 4;
}

enum FilterParameterType {
  NUMBER = 0;
  BOOLEAN = 1;
  STRING = 2;
  STRING_LIST = 3;
}

message FilterInfoResponse {
  FilterName name = 1;
  string hint = 2;
  repeated FilterParameter parameter = 3;
}

message MessageMatchRequest {
  MessageID message_id = 1;
  repeated Filter filter = 2;
}

message EventMatchRequest {
  EventID event_id = 1;
  repeated Filter filter = 2;
}

message MatchResponse {
  bool match = 1;
}

message Filter {
  FilterName name = 1;
  bool negative = 2;
  repeated string value = 3;
  bool conjunct = 4;
}

message EventSearchRequest {
  google.protobuf.Timestamp start_timestamp = 1; // unix timestamp - Sets the search starting point. One of the 'start_timestamp' or 'resume_from_id' must not absent
  google.protobuf.Timestamp end_timestamp = 2; // unix timestamp - Sets the timestamp to which the search will be performed, starting with 'start_timestamp'. When 'search_direction' is previous, end_timestamp must be less than start_timestamp. By default it is absent (the search is carried out endlessly into the past or into the future).

  EventID parent_event = 3; // Match events to the specified parent. Only the immediate children of the specified event will be returned.
  TimeRelation search_direction = 4; // Sets the lookup direction. Can be used for pagination. Set by default to NEXT.

  EventID resume_from_id = 5; // last event id. In order to continue the execution of an interrupted sse request, you need to send exactly the same request with an indication of the element ID, from which the data transfer will be resumed. By default it is absent. One of the 'start_timestamp' or 'resume_from_id' must not absent

  google.protobuf.Int32Value result_count_limit = 6; // Sets the maximum amount of events to return. By default it is absent (unlimited).

  google.protobuf.BoolValue keep_open = 7; // If the search has reached the current moment, it is necessary to wait further for the appearance of new data. Set to false by default.

  google.protobuf.Int64Value limit_for_parent = 8; // How many children events for each parent do we want to request. By default it is absent (unlimited).

  google.protobuf.BoolValue metadata_only = 9; //  Receive only metadata (true) or entire event (false) (without attachedMessageIds). Set by default to true.

  google.protobuf.BoolValue attached_messages = 10; // If the metadataOnly is false, it will additionally load attachedMessageIds. Set by default to false.

  repeated Filter filter = 11; // List of event search filters. (See 'search/sse/events' HTTP method https://github.com/th2-net/th2-rpt-data-provider)
}

message EventSearchResponse {
  oneof data {
    EventResponse event = 1;
    EventMetadata event_metadata = 2;
    EventStreamPointer event_stream_pointer = 3;
  }
}

message EventStreamPointer {
  bool has_started = 1;
  bool has_ended = 2;
  EventID last_id = 3;
}

message MessageSearchRequest {
  google.protobuf.Timestamp start_timestamp = 1; // unix timestamp - Sets the search starting point. One of the 'start_timestamp' or 'resume_from_id' or 'message_id' must not absent
  google.protobuf.Timestamp end_timestamp = 2; // unix timestamp - Sets the timestamp to which the search will be performed, starting with 'start_timestamp'. When search_direction is 'previous', 'end_timestamp' must be less than 'start_timestamp'. By default it is absent (the search is carried out endlessly into the past or into the future).

  TimeRelation search_direction = 3; // Sets the lookup direction. Can be used for pagination. Set by default to NEXT.

  google.protobuf.Int32Value result_count_limit = 4; // Sets the maximum amount of messages to return. By default it is absent (unlimited)

  repeated MessageStream stream = 5; // Sets the stream names and directions to search in. Case-sensitive. Required.
  google.protobuf.BoolValue keep_open = 6; //  If the search has reached the current moment, it is necessary to wait further for the appearance of new data. Set by default to false.

  repeated MessageStreamPointer stream_pointer = 7; // List of stream pointers to restore the search from. start_timestamp will be ignored if this parameter is specified. By default it is absent.

  repeated Filter filter = 8; // List of message search filters. (See 'search/sse/message' HTTP method https://github.com/th2-net/th2-rpt-data-provider)
  google.protobuf.BoolValue attached_events = 9; // If true, it will additionally load attachedEventsIds. Set by default to false.
}

message MessageSearchResponse {
  oneof data {
    MessageGroupResponse message = 1;
    MessageStreamPointers message_stream_pointers = 2;
  }
}

message MessageStreamPointers {
  repeated MessageStreamPointer message_stream_pointer = 1;
}

/* This object contains the data of the last message in the stream on which
 * the search has stopped, it is necessary to continue the search from the same point */
 message MessageStreamPointer {
  MessageStream message_stream = 1;
  bool has_started = 2;
  bool has_ended = 3;
  MessageID last_id = 4; // Might be abscent if the stream has no messages
}

message MessageStream {
  string name = 1; // Case sensitive. Required.
  Direction direction = 2; // Required.
}

message MessageStreamsResponse {
  repeated MessageStream messageStream = 1;
}

enum TimeRelation {
  NEXT = 0;
  PREVIOUS = 1;
}