// Copyright 2018 Google LLC
//
// 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
//
//     https://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";

import "google/api/annotations.proto";
import "google/api/client.proto";
import "google/api/field_behavior.proto";
import "google/api/resource.proto";
import "google/longrunning/operations.proto";
import "google/protobuf/empty.proto";
import "google/protobuf/field_mask.proto";
import "google/protobuf/timestamp.proto";
import "google/rpc/error_details.proto";

package google.showcase.v1beta1;

option go_package = "github.com/googleapis/gapic-showcase/server/genproto";
option java_package = "com.google.showcase.v1beta1";
option java_multiple_files = true;
option ruby_package = "Google::Showcase::V1beta1";

// A simple messaging service that implements chat rooms and profile posts.
//
// This messaging service showcases the features that API clients
// generated by gapic-generators implement.
service Messaging {
  // This service is meant to only run locally on the port 7469 (keypad digits
  // for "show").
  option (google.api.default_host) = "localhost:7469";

  // Creates a room.
  rpc CreateRoom(CreateRoomRequest) returns (Room) {
    option (google.api.http) = {
      post: "/v1beta1/rooms"
      body: "*"
    };
    option (google.api.method_signature) = "room.display_name,room.description";
  }

  // Retrieves the Room with the given resource name.
  rpc GetRoom(GetRoomRequest) returns (Room) {
    option (google.api.http) = {
      get: "/v1beta1/{name=rooms/*}"
    };
    option (google.api.method_signature) = "name";
  }

  // Updates a room.
  rpc UpdateRoom(UpdateRoomRequest) returns (Room) {
    option (google.api.http) = {
      patch: "/v1beta1/{room.name=rooms/*}"
      body: "room"
    };
  }

  // Deletes a room and all of its blurbs.
  rpc DeleteRoom(DeleteRoomRequest) returns (google.protobuf.Empty) {
    option (google.api.http) = {
      delete: "/v1beta1/{name=rooms/*}"
    };
    option (google.api.method_signature) = "name";
  }

  // Lists all chat rooms.
  rpc ListRooms(ListRoomsRequest) returns (ListRoomsResponse) {
    option (google.api.http) = {
      get: "/v1beta1/rooms"
    };
  }

  // Creates a blurb. If the parent is a room, the blurb is understood to be a
  // message in that room. If the parent is a profile, the blurb is understood
  // to be a post on the profile.
  rpc CreateBlurb(CreateBlurbRequest) returns (Blurb) {
    option (google.api.http) = {
      post: "/v1beta1/{parent=rooms/*}/blurbs"
      body: "*"
      additional_bindings: {
        post: "/v1beta1/{parent=users/*/profile}/blurbs"
        body: "*"
      }
    };
    option (google.api.method_signature) = "parent,blurb.user,blurb.text";
    option (google.api.method_signature) = "parent,blurb.user,blurb.image";
  }

  // Retrieves the Blurb with the given resource name.
  rpc GetBlurb(GetBlurbRequest) returns (Blurb) {
    option (google.api.http) = {
      get: "/v1beta1/{name=rooms/*/blurbs/*}"
      additional_bindings: { get: "/v1beta1/{name=users/*/profile/blurbs/*}" }
    };
    option (google.api.method_signature) = "name";
  }

  // Updates a blurb.
  rpc UpdateBlurb(UpdateBlurbRequest) returns (Blurb) {
    option (google.api.http) = {
      patch: "/v1beta1/{blurb.name=rooms/*/blurbs/*}"
      body: "blurb"
      additional_bindings: {
        patch: "/v1beta1/{blurb.name=users/*/profile/blurbs/*}"
        body: "blurb"
      }
    };
  }

  // Deletes a blurb.
  rpc DeleteBlurb(DeleteBlurbRequest) returns (google.protobuf.Empty) {
    option (google.api.http) = {
      delete: "/v1beta1/{name=rooms/*/blurbs/*}"
      additional_bindings: {
        delete: "/v1beta1/{name=users/*/profile/blurbs/*}"
      }
    };
    option (google.api.method_signature) = "name";
  }

  // Lists blurbs for a specific chat room or user profile depending on the
  // parent resource name.
  rpc ListBlurbs(ListBlurbsRequest) returns (ListBlurbsResponse) {
    option (google.api.http) = {
      get: "/v1beta1/{parent=rooms/*}/blurbs"
      additional_bindings: { get: "/v1beta1/{parent=users/*/profile}/blurbs" }
    };
    option (google.api.method_signature) = "parent";
  }

  // This method searches through all blurbs across all rooms and profiles
  // for blurbs containing to words found in the query. Only posts that
  // contain an exact match of a queried word will be returned.
  rpc SearchBlurbs(SearchBlurbsRequest) returns (google.longrunning.Operation) {
    option (google.api.http) = {
      post: "/v1beta1/{parent=rooms/*}/blurbs:search"
      body: "*"
      additional_bindings: {
        post: "/v1beta1/{parent=users/*/profile}/blurbs:search"
      }
    };
    option (google.longrunning.operation_info) = {
      response_type: "SearchBlurbsResponse"
      metadata_type: "SearchBlurbsMetadata"
    };
    option (google.api.method_signature) = "parent,query";
  }

  // This returns a stream that emits the blurbs that are created for a
  // particular chat room or user profile.
  rpc StreamBlurbs(StreamBlurbsRequest) returns (stream StreamBlurbsResponse) {
    option (google.api.http) = {
      post: "/v1beta1/{name=rooms/*}/blurbs:stream"
      body: "*"
      additional_bindings: {
        post: "/v1beta1/{name=users/*/profile}/blurbs:stream"
        body: "*"
      }
    };
  }

  // This is a stream to create multiple blurbs. If an invalid blurb is
  // requested to be created, the stream will close with an error.
  rpc SendBlurbs(stream CreateBlurbRequest) returns (SendBlurbsResponse) {
    option (google.api.http) = {
      post: "/v1beta1/{parent=rooms/*}/blurbs:send"
      body: "*"
      additional_bindings: {
        post: "/v1beta1/{parent=users/*/profile}/blurbs:send"
        body: "*"
      }
    };
  }

  // This method starts a bidirectional stream that receives all blurbs that
  // are being created after the stream has started and sends requests to create
  // blurbs. If an invalid blurb is requested to be created, the stream will
  // close with an error.
  rpc Connect(stream ConnectRequest) returns (stream StreamBlurbsResponse);
}

// A chat room.
message Room {
  option (google.api.resource) = {
    type: "showcase.googleapis.com/Room"
    pattern: "rooms/{room}"
  };

  // The resource name of the chat room.
  string name = 1;

  // The human readable name of the chat room.
  string display_name = 2 [(google.api.field_behavior) = REQUIRED];

  // The description of the chat room.
  string description = 3;

  // The timestamp at which the room was created.
  google.protobuf.Timestamp create_time = 4
      [(google.api.field_behavior) = OUTPUT_ONLY];

  // The latest timestamp at which the room was updated.
  google.protobuf.Timestamp update_time = 5
      [(google.api.field_behavior) = OUTPUT_ONLY];
}

// The request message for the google.showcase.v1beta1.Messaging\CreateRoom
// method.
message CreateRoomRequest {
  // The room to create.
  Room room = 1;
}

// The request message for the google.showcase.v1beta1.Messaging\GetRoom
// method.
message GetRoomRequest {
  // The resource name of the requested room.
  string name = 1 [
    (google.api.resource_reference).type = "showcase.googleapis.com/Room",
    (google.api.field_behavior) = REQUIRED
  ];
}

// The request message for the google.showcase.v1beta1.Messaging\UpdateRoom
// method.
message UpdateRoomRequest {
  // The room to update.
  Room room = 1;

  // The field mask to determine which fields are to be updated. If empty, the
  // server will assume all fields are to be updated.
  google.protobuf.FieldMask update_mask = 2;
}

// The request message for the google.showcase.v1beta1.Messaging\DeleteRoom
// method.
message DeleteRoomRequest {
  // The resource name of the requested room.
  string name = 1 [
    (google.api.resource_reference).type = "showcase.googleapis.com/Room",
    (google.api.field_behavior) = REQUIRED
  ];
}

// The request message for the google.showcase.v1beta1.Messaging\ListRooms
// method.
message ListRoomsRequest {
  // The maximum number of rooms return. Server may return fewer rooms
  // than requested. If unspecified, server will pick an appropriate default.
  int32 page_size = 1;

  // The value of google.showcase.v1beta1.ListRoomsResponse.next_page_token
  // returned from the previous call to
  // `google.showcase.v1beta1.Messaging\ListRooms` method.
  string page_token = 2;
}

// The response message for the google.showcase.v1beta1.Messaging\ListRooms
// method.
message ListRoomsResponse {
  // The list of rooms.
  repeated Room rooms = 1;

  // A token to retrieve next page of results.
  // Pass this value in ListRoomsRequest.page_token field in the subsequent
  // call to `google.showcase.v1beta1.Messaging\ListRooms` method to retrieve
  // the next page of results.
  string next_page_token = 2;
}

// This protocol buffer message represents a blurb sent to a chat room or
// posted on a user profile.
message Blurb {
  option (google.api.resource) = {
    type: "showcase.googleapis.com/Blurb"
    pattern: "users/{user}/profile/blurbs/legacy/{legacy_user}~{blurb}"
    pattern: "users/{user}/profile/blurbs/{blurb}"
    pattern: "rooms/{room}/blurbs/{blurb}"
    pattern: "rooms/{room}/blurbs/legacy/{legacy_room}.{blurb}"
  };

  // The resource name of the chat room.
  string name = 1;

  // The resource name of the blurb's author.
  string user = 2 [
    (google.api.resource_reference).type = "showcase.googleapis.com/User",
    (google.api.field_behavior) = REQUIRED
  ];

  oneof content {
    // The textual content of this blurb.
    string text = 3;

    // The image content of this blurb.
    bytes image = 4;
  }

  // The timestamp at which the blurb was created.
  google.protobuf.Timestamp create_time = 5
      [(google.api.field_behavior) = OUTPUT_ONLY];

  // The latest timestamp at which the blurb was updated.
  google.protobuf.Timestamp update_time = 6
      [(google.api.field_behavior) = OUTPUT_ONLY];

  // (-- aip.dev/not-precedent: This is designed for testing non-slash
  //     resource patterns. Ordinarily, non-slash separators are discouraged.
  //     --)
  oneof legacy_id {
    // The legacy id of the room. This field is used to signal
    // the use of the compound resource pattern
    // `rooms/{room}/blurbs/legacy/{legacy_room}.{blurb}`
    string legacy_room_id = 7;

    // The legacy id of the user. This field is used to signal
    // the use of the compound resource pattern
    // `users/{user}/profile/blurbs/legacy/{legacy_user}~{blurb}`
    string legacy_user_id = 8;
  }
}

// The request message for the google.showcase.v1beta1.Messaging\CreateBlurb
// method.
message CreateBlurbRequest {
  // The resource name of the chat room or user profile that this blurb will
  // be tied to.
  string parent = 1 [
    (google.api.resource_reference).child_type =
        "showcase.googleapis.com/Blurb",
    (google.api.field_behavior) = REQUIRED
  ];

  // The blurb to create.
  Blurb blurb = 2;
}

// The request message for the google.showcase.v1beta1.Messaging\GetBlurb
// method.
message GetBlurbRequest {
  // The resource name of the requested blurb.
  string name = 1 [
    (google.api.resource_reference).type = "showcase.googleapis.com/Blurb",
    (google.api.field_behavior) = REQUIRED
  ];
}

// The request message for the google.showcase.v1beta1.Messaging\UpdateBlurb
// method.
message UpdateBlurbRequest {
  // The blurb to update.
  Blurb blurb = 1;

  // The field mask to determine which fields are to be updated. If empty, the
  // server will assume all fields are to be updated.
  google.protobuf.FieldMask update_mask = 2;
}

// The request message for the google.showcase.v1beta1.Messaging\DeleteBlurb
// method.
message DeleteBlurbRequest {
  // The resource name of the requested blurb.
  string name = 1 [
    (google.api.resource_reference).type = "showcase.googleapis.com/Blurb",
    (google.api.field_behavior) = REQUIRED
  ];
}

// The request message for the google.showcase.v1beta1.Messaging\ListBlurbs
// method.
message ListBlurbsRequest {
  // The resource name of the requested room or profile who blurbs to list.
  string parent = 1 [
    (google.api.resource_reference).child_type =
        "showcase.googleapis.com/Blurb",
    (google.api.field_behavior) = REQUIRED
  ];

  // The maximum number of blurbs to return. Server may return fewer
  // blurbs than requested. If unspecified, server will pick an appropriate
  // default.
  int32 page_size = 2;

  // The value of google.showcase.v1beta1.ListBlurbsResponse.next_page_token
  // returned from the previous call to
  // `google.showcase.v1beta1.Messaging\ListBlurbs` method.
  string page_token = 3;
}

// The response message for the google.showcase.v1beta1.Messaging\ListBlurbs
// method.
message ListBlurbsResponse {
  // The list of blurbs.
  repeated Blurb blurbs = 1;

  // A token to retrieve next page of results.
  // Pass this value in ListBlurbsRequest.page_token field in the subsequent
  // call to `google.showcase.v1beta1.Blurb\ListBlurbs` method to retrieve
  // the next page of results.
  string next_page_token = 2;
}

// The request message for the google.showcase.v1beta1.Messaging\SearchBlurbs
// method.
message SearchBlurbsRequest {
  // The query used to search for blurbs containing to words of this string.
  // Only posts that contain an exact match of a queried word will be returned.
  string query = 1 [(google.api.field_behavior) = REQUIRED];

  // The rooms or profiles to search. If unset, `SearchBlurbs` will search all
  // rooms and all profiles.
  string parent = 2 [(google.api.resource_reference).child_type =
                         "showcase.googleapis.com/Blurb"];

  // The maximum number of blurbs return. Server may return fewer
  // blurbs than requested. If unspecified, server will pick an appropriate
  // default.
  int32 page_size = 3;

  // The value of
  // google.showcase.v1beta1.SearchBlurbsResponse.next_page_token
  // returned from the previous call to
  // `google.showcase.v1beta1.Messaging\SearchBlurbs` method.
  string page_token = 4;
}

// The operation metadata message for the
// google.showcase.v1beta1.Messaging\SearchBlurbs method.
message SearchBlurbsMetadata {
  // This signals to the client when to next poll for response.
  google.rpc.RetryInfo retry_info = 1;
}

// The operation response message for the
// google.showcase.v1beta1.Messaging\SearchBlurbs method.
message SearchBlurbsResponse {
  // Blurbs that matched the search query.
  repeated Blurb blurbs = 1;

  // A token to retrieve next page of results.
  // Pass this value in SearchBlurbsRequest.page_token field in the subsequent
  // call to `google.showcase.v1beta1.Blurb\SearchBlurbs` method to
  // retrieve the next page of results.
  string next_page_token = 2;
}

// The request message for the google.showcase.v1beta1.Messaging\StreamBlurbs
// method.
message StreamBlurbsRequest {
  // The resource name of a chat room or user profile whose blurbs to stream.
  string name = 1 [
    (google.api.resource_reference).child_type =
        "showcase.googleapis.com/Blurb",
    (google.api.field_behavior) = REQUIRED
  ];

  // The time at which this stream will close.
  google.protobuf.Timestamp expire_time = 2
      [(google.api.field_behavior) = REQUIRED];
}

// The response message for the google.showcase.v1beta1.Messaging\StreamBlurbs
// method.
message StreamBlurbsResponse {
  // The blurb that was either created, updated, or deleted.
  Blurb blurb = 1;

  // The action that triggered the blurb to be returned.
  enum Action {
    ACTION_UNSPECIFIED = 0;

    // Specifies that the blurb was created.
    CREATE = 1;

    // Specifies that the blurb was updated.
    UPDATE = 2;

    // Specifies that the blurb was deleted.
    DELETE = 3;
  }

  // The action that triggered the blurb to be returned.
  Action action = 2;
}

// The response message for the google.showcase.v1beta1.Messaging\SendBlurbs
// method.
message SendBlurbsResponse {
  // The names of successful blurb creations.
  repeated string names = 1;
}

// The request message for the google.showcase.v1beta1.Messaging\Connect
// method.
message ConnectRequest {
  message ConnectConfig {
    // The room or profile to follow and create messages for.
    string parent = 1 [(google.api.resource_reference).child_type =
                           "showcase.googleapis.com/Blurb"];
  }

  oneof request {
    // Provides information that specifies how to process subsequent requests.
    // The first `ConnectRequest` message must contain a `config`  message.
    ConnectConfig config = 1;

    // The blurb to be created.
    Blurb blurb = 2;
  }
}
