diff --git a/api/main.proto b/api/main.proto index d7bc01d..e6baba0 100644 --- a/api/main.proto +++ b/api/main.proto @@ -516,6 +516,18 @@ service EveningDetectiveServer { }; } + rpc IssueGameTickets(IssueGameTicketsReq) returns (IssueGameTicketsRsp) { + option (google.api.http) = { + post: "/api/games/{gameId}/tickets" + body: "*" + }; + option (grpc.gateway.protoc_gen_openapiv2.options.openapiv2_operation) = { + security: { security_requirement: {} } + tags: "Билеты"; + summary: "Выпустить билеты на игру"; + }; + } + // Создать сессию экрана. Экран получает токен и показывает QR для привязки. rpc CreateScreenSession(CreateScreenSessionReq) returns (CreateScreenSessionRsp) { option (google.api.http) = { @@ -1864,3 +1876,18 @@ message UpdateScenarioBackgroundReq { message UpdateScenarioBackgroundRsp { string error = 1; } + +message IssueGameTicketsReq { + int32 gameId = 1; + int32 count = 2; +} + +message IssueGameTicketsRsp { + string error = 1; + repeated Ticket tickets = 2; +} + +message Ticket { + int32 id = 1; + string url = 2; +} diff --git a/cmd/evening_detective_server/main.go b/cmd/evening_detective_server/main.go index 4fa3846..afb021f 100644 --- a/cmd/evening_detective_server/main.go +++ b/cmd/evening_detective_server/main.go @@ -22,6 +22,7 @@ import ( "evening_detective_server/internal/repos/screen_sessions_repo" "evening_detective_server/internal/repos/team_answers_repo" "evening_detective_server/internal/repos/teams_repo" + "evening_detective_server/internal/repos/tickets_repo" "evening_detective_server/internal/repos/users_repo" "evening_detective_server/internal/services/answer_service" "evening_detective_server/internal/services/file_service" @@ -32,6 +33,7 @@ import ( "evening_detective_server/internal/services/participation_service" "evening_detective_server/internal/services/scenarios_service" "evening_detective_server/internal/services/team_service" + "evening_detective_server/internal/services/ticket_service" "evening_detective_server/internal/services/ui_service" "evening_detective_server/internal/services/users_service" proto "evening_detective_server/proto" @@ -130,6 +132,7 @@ func main() { ) gameRepo := games_repo.NewGamesRepo(dbpool) teamRepo := teams_repo.NewTeamsRepo(dbpool) + ticketRepo := tickets_repo.New(dbpool) storyteller := storytelling.NewStory(cleaner) actionsRepo := actions_repo.NewActionsRepo(dbpool) applicationsRepo := applications_repo.NewApplicationsRepo(dbpool) @@ -155,6 +158,7 @@ func main() { teamService := team_service.NewTeamService(gameRepo, teamRepo, passwordGenerator, os.Getenv("APP_BASE_URL"), emailSender) participationService := participation_service.NewParticipationService(teamRepo, os.Getenv("APP_BASE_URL")) + ticketService := ticket_service.New(ticketRepo, os.Getenv("APP_BASE_URL")) go participationService.RunParticipationEmails(context.Background(), emailSender, os.Getenv("PARTICIPATION_SECRET"), os.Getenv("GAME_TIMEZONE")) go reviewService.RunReviewReminderEmails(context.Background(), emailSender) @@ -211,6 +215,7 @@ func main() { answerService, reviewService, teamService, + ticketService, participationService, screenRepo, mapRepo, diff --git a/cmd/evening_detective_server/main.swagger.json b/cmd/evening_detective_server/main.swagger.json index 72446d7..5bbef23 100644 --- a/cmd/evening_detective_server/main.swagger.json +++ b/cmd/evening_detective_server/main.swagger.json @@ -792,6 +792,51 @@ ] } }, + "/api/games/{gameId}/tickets": { + "post": { + "summary": "Выпустить билеты на игру", + "operationId": "EveningDetectiveServer_IssueGameTickets", + "responses": { + "200": { + "description": "A successful response.", + "schema": { + "$ref": "#/definitions/evening_detective_serverIssueGameTicketsRsp" + } + }, + "default": { + "description": "An unexpected error response.", + "schema": { + "$ref": "#/definitions/rpcStatus" + } + } + }, + "parameters": [ + { + "name": "gameId", + "in": "path", + "required": true, + "type": "integer", + "format": "int32" + }, + { + "name": "body", + "in": "body", + "required": true, + "schema": { + "$ref": "#/definitions/EveningDetectiveServerIssueGameTicketsBody" + } + } + ], + "tags": [ + "Билеты" + ], + "security": [ + { + "": [] + } + ] + } + }, "/api/games/{id}": { "get": { "summary": "Получить игру", @@ -2980,6 +3025,15 @@ } } }, + "EveningDetectiveServerIssueGameTicketsBody": { + "type": "object", + "properties": { + "count": { + "type": "integer", + "format": "int32" + } + } + }, "EveningDetectiveServerModerateGameReviewBody": { "type": "object", "properties": { @@ -3976,6 +4030,21 @@ } } }, + "evening_detective_serverIssueGameTicketsRsp": { + "type": "object", + "properties": { + "error": { + "type": "string" + }, + "tickets": { + "type": "array", + "items": { + "type": "object", + "$ref": "#/definitions/evening_detective_serverTicket" + } + } + } + }, "evening_detective_serverKey": { "type": "object", "properties": { @@ -4571,6 +4640,18 @@ }, "description": "Строка итоговой таблицы: команда, баллы по вопросам, сумма и место." }, + "evening_detective_serverTicket": { + "type": "object", + "properties": { + "id": { + "type": "integer", + "format": "int32" + }, + "url": { + "type": "string" + } + } + }, "evening_detective_serverUnbindScreenRsp": { "type": "object", "properties": { diff --git a/internal/app/server.go b/internal/app/server.go index 5d3efef..85496c0 100644 --- a/internal/app/server.go +++ b/internal/app/server.go @@ -11,6 +11,7 @@ import ( "evening_detective_server/internal/services/participation_service" "evening_detective_server/internal/services/scenarios_service" "evening_detective_server/internal/services/team_service" + "evening_detective_server/internal/services/ticket_service" "evening_detective_server/internal/services/ui_service" "evening_detective_server/internal/services/users_service" proto "evening_detective_server/proto" @@ -28,6 +29,7 @@ type server struct { answerService *answer_service.AnswerService reviewService *game_review_service.Service teamService *team_service.TeamService + ticketService *ticket_service.Service participationService *participation_service.ParticipationService screenRepo *screen_sessions_repo.ScreenSessionsRepo mapRepo *game_map_repo.Repo @@ -43,6 +45,7 @@ func NewServer( answerService *answer_service.AnswerService, reviewService *game_review_service.Service, teamService *team_service.TeamService, + ticketService *ticket_service.Service, participationService *participation_service.ParticipationService, screenRepo *screen_sessions_repo.ScreenSessionsRepo, mapRepo *game_map_repo.Repo, @@ -57,6 +60,7 @@ func NewServer( answerService: answerService, reviewService: reviewService, teamService: teamService, + ticketService: ticketService, participationService: participationService, screenRepo: screenRepo, mapRepo: mapRepo, diff --git a/internal/app/tickets.go b/internal/app/tickets.go new file mode 100644 index 0000000..d29139a --- /dev/null +++ b/internal/app/tickets.go @@ -0,0 +1,35 @@ +package app + +import ( + "context" + + "evening_detective_server/internal/modules/processor_jwt" + "evening_detective_server/internal/modules/roles" + "evening_detective_server/proto" + "google.golang.org/grpc/codes" + "google.golang.org/grpc/status" +) + +func (s *server) IssueGameTickets(ctx context.Context, req *proto.IssueGameTicketsReq) (*proto.IssueGameTicketsRsp, error) { + claims, ok := ctx.Value("claims").(*processor_jwt.JWTClaims) + if !ok || claims == nil { + return nil, status.Error(codes.Unauthenticated, "необходима авторизация") + } + if !roles.HasRole(claims, roles.Organizer) && !roles.HasRole(claims, roles.Author) { + return nil, status.Error(codes.PermissionDenied, "permission denied") + } + if req == nil || req.GameId <= 0 { + return nil, status.Error(codes.InvalidArgument, "некорректный идентификатор игры") + } + + tickets, err := s.ticketService.Issue(ctx, int(req.GameId), int(req.Count)) + if err != nil { + return &proto.IssueGameTicketsRsp{Error: err.Error()}, nil + } + + result := make([]*proto.Ticket, 0, len(tickets)) + for _, ticket := range tickets { + result = append(result, &proto.Ticket{Id: int32(ticket.ID), Url: ticket.URL}) + } + return &proto.IssueGameTicketsRsp{Tickets: result}, nil +} diff --git a/internal/repos/tickets_repo/repo.go b/internal/repos/tickets_repo/repo.go new file mode 100644 index 0000000..881bb83 --- /dev/null +++ b/internal/repos/tickets_repo/repo.go @@ -0,0 +1,39 @@ +package tickets_repo + +import ( + "context" + + "github.com/jackc/pgx/v5/pgxpool" +) + +type Repo struct { + pool *pgxpool.Pool +} + +func New(pool *pgxpool.Pool) *Repo { + return &Repo{pool: pool} +} + +func (r *Repo) CreateBatch(ctx context.Context, gameID int, tokenHashes [][]byte) ([]int, error) { + tx, err := r.pool.Begin(ctx) + if err != nil { + return nil, err + } + defer tx.Rollback(ctx) + + ids := make([]int, 0, len(tokenHashes)) + for _, tokenHash := range tokenHashes { + var id int + if err := tx.QueryRow(ctx, + `INSERT INTO tickets (game_id, token_hash) VALUES ($1, $2) RETURNING id`, + gameID, tokenHash, + ).Scan(&id); err != nil { + return nil, err + } + ids = append(ids, id) + } + if err := tx.Commit(ctx); err != nil { + return nil, err + } + return ids, nil +} diff --git a/internal/services/ticket_service/service.go b/internal/services/ticket_service/service.go new file mode 100644 index 0000000..890334f --- /dev/null +++ b/internal/services/ticket_service/service.go @@ -0,0 +1,88 @@ +package ticket_service + +import ( + "context" + "crypto/rand" + "crypto/sha256" + "encoding/base64" + "errors" + "fmt" + "net/url" + "strings" + + "evening_detective_server/internal/repos/tickets_repo" +) + +const maxTicketsPerRequest = 100 + +var ( + ErrInvalidTicketCount = errors.New("количество билетов должно быть от 1 до 100") + ErrInvalidBaseURL = errors.New("необходимо настроить APP_BASE_URL — публичный адрес приложения") +) + +type Ticket struct { + ID int + URL string +} + +type Service struct { + repo *tickets_repo.Repo + appBaseURL string +} + +func New(repo *tickets_repo.Repo, appBaseURL string) *Service { + return &Service{repo: repo, appBaseURL: appBaseURL} +} + +func (s *Service) Issue(ctx context.Context, gameID, count int) ([]*Ticket, error) { + if count < 1 || count > maxTicketsPerRequest { + return nil, ErrInvalidTicketCount + } + + base, err := parseBaseURL(s.appBaseURL) + if err != nil { + return nil, err + } + + hashes := make([][]byte, count) + tokens := make([]string, count) + for i := range count { + token, err := newToken() + if err != nil { + return nil, err + } + hash := sha256.Sum256([]byte(token)) + tokens[i] = token + hashes[i] = hash[:] + } + + ids, err := s.repo.CreateBatch(ctx, gameID, hashes) + if err != nil { + return nil, err + } + + tickets := make([]*Ticket, count) + for i, id := range ids { + link := *base + link.Path = strings.TrimRight(base.Path, "/") + "/tickets/" + tokens[i] + link.RawPath = "" + tickets[i] = &Ticket{ID: id, URL: link.String()} + } + return tickets, nil +} + +func newToken() (string, error) { + data := make([]byte, 32) + if _, err := rand.Read(data); err != nil { + return "", fmt.Errorf("generate ticket token: %w", err) + } + return base64.RawURLEncoding.EncodeToString(data), nil +} + +func parseBaseURL(value string) (*url.URL, error) { + base, err := url.Parse(strings.TrimSpace(value)) + if err != nil || base.Host == "" || (base.Scheme != "http" && base.Scheme != "https") || base.User != nil || base.RawQuery != "" || base.Fragment != "" { + return nil, ErrInvalidBaseURL + } + return base, nil +} diff --git a/internal/services/ticket_service/service_test.go b/internal/services/ticket_service/service_test.go new file mode 100644 index 0000000..18708e0 --- /dev/null +++ b/internal/services/ticket_service/service_test.go @@ -0,0 +1,17 @@ +package ticket_service + +import "testing" + +func TestNewToken(t *testing.T) { + first, err := newToken() + if err != nil { + t.Fatal(err) + } + second, err := newToken() + if err != nil { + t.Fatal(err) + } + if first == second || len(first) != 43 || len(second) != 43 { + t.Fatalf("invalid tokens: %q %q", first, second) + } +} diff --git a/proto/main.pb.go b/proto/main.pb.go index d2fd585..5ac0bd9 100644 --- a/proto/main.pb.go +++ b/proto/main.pb.go @@ -9281,6 +9281,162 @@ func (x *UpdateScenarioBackgroundRsp) GetError() string { return "" } +type IssueGameTicketsReq struct { + state protoimpl.MessageState `protogen:"open.v1"` + GameId int32 `protobuf:"varint,1,opt,name=gameId,proto3" json:"gameId,omitempty"` + Count int32 `protobuf:"varint,2,opt,name=count,proto3" json:"count,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *IssueGameTicketsReq) Reset() { + *x = IssueGameTicketsReq{} + mi := &file_main_proto_msgTypes[171] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *IssueGameTicketsReq) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*IssueGameTicketsReq) ProtoMessage() {} + +func (x *IssueGameTicketsReq) ProtoReflect() protoreflect.Message { + mi := &file_main_proto_msgTypes[171] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use IssueGameTicketsReq.ProtoReflect.Descriptor instead. +func (*IssueGameTicketsReq) Descriptor() ([]byte, []int) { + return file_main_proto_rawDescGZIP(), []int{171} +} + +func (x *IssueGameTicketsReq) GetGameId() int32 { + if x != nil { + return x.GameId + } + return 0 +} + +func (x *IssueGameTicketsReq) GetCount() int32 { + if x != nil { + return x.Count + } + return 0 +} + +type IssueGameTicketsRsp struct { + state protoimpl.MessageState `protogen:"open.v1"` + Error string `protobuf:"bytes,1,opt,name=error,proto3" json:"error,omitempty"` + Tickets []*Ticket `protobuf:"bytes,2,rep,name=tickets,proto3" json:"tickets,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *IssueGameTicketsRsp) Reset() { + *x = IssueGameTicketsRsp{} + mi := &file_main_proto_msgTypes[172] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *IssueGameTicketsRsp) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*IssueGameTicketsRsp) ProtoMessage() {} + +func (x *IssueGameTicketsRsp) ProtoReflect() protoreflect.Message { + mi := &file_main_proto_msgTypes[172] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use IssueGameTicketsRsp.ProtoReflect.Descriptor instead. +func (*IssueGameTicketsRsp) Descriptor() ([]byte, []int) { + return file_main_proto_rawDescGZIP(), []int{172} +} + +func (x *IssueGameTicketsRsp) GetError() string { + if x != nil { + return x.Error + } + return "" +} + +func (x *IssueGameTicketsRsp) GetTickets() []*Ticket { + if x != nil { + return x.Tickets + } + return nil +} + +type Ticket struct { + state protoimpl.MessageState `protogen:"open.v1"` + Id int32 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"` + Url string `protobuf:"bytes,2,opt,name=url,proto3" json:"url,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *Ticket) Reset() { + *x = Ticket{} + mi := &file_main_proto_msgTypes[173] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *Ticket) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*Ticket) ProtoMessage() {} + +func (x *Ticket) ProtoReflect() protoreflect.Message { + mi := &file_main_proto_msgTypes[173] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use Ticket.ProtoReflect.Descriptor instead. +func (*Ticket) Descriptor() ([]byte, []int) { + return file_main_proto_rawDescGZIP(), []int{173} +} + +func (x *Ticket) GetId() int32 { + if x != nil { + return x.Id + } + return 0 +} + +func (x *Ticket) GetUrl() string { + if x != nil { + return x.Url + } + return "" +} + var File_main_proto protoreflect.FileDescriptor const file_main_proto_rawDesc = "" + @@ -9870,7 +10026,16 @@ const file_main_proto_rawDesc = "" + "background\x18\x02 \x01(\tR\n" + "background\"3\n" + "\x1bUpdateScenarioBackgroundRsp\x12\x14\n" + - "\x05error\x18\x01 \x01(\tR\x05error*\xc9\x01\n" + + "\x05error\x18\x01 \x01(\tR\x05error\"C\n" + + "\x13IssueGameTicketsReq\x12\x16\n" + + "\x06gameId\x18\x01 \x01(\x05R\x06gameId\x12\x14\n" + + "\x05count\x18\x02 \x01(\x05R\x05count\"m\n" + + "\x13IssueGameTicketsRsp\x12\x14\n" + + "\x05error\x18\x01 \x01(\tR\x05error\x12@\n" + + "\atickets\x18\x02 \x03(\v2&.crabs.evening_detective_server.TicketR\atickets\"*\n" + + "\x06Ticket\x12\x0e\n" + + "\x02id\x18\x01 \x01(\x05R\x02id\x12\x10\n" + + "\x03url\x18\x02 \x01(\tR\x03url*\xc9\x01\n" + "\n" + "ScreenMode\x12\x1b\n" + "\x17SCREEN_MODE_UNSPECIFIED\x10\x00\x12\x15\n" + @@ -9888,7 +10053,7 @@ const file_main_proto_rawDesc = "" + "\x13SCREEN_COMMAND_STOP\x10\x04\x12\x19\n" + "\x15SCREEN_COMMAND_REPLAY\x10\x05\x12\x17\n" + "\x13SCREEN_COMMAND_SEEK\x10\x06\x12\x19\n" + - "\x15SCREEN_COMMAND_VOLUME\x10\a2\x9e\x9f\x01\n" + + "\x15SCREEN_COMMAND_VOLUME\x10\a2\x8d\xa1\x01\n" + "\x16EveningDetectiveServer\x12\xcc\x05\n" + "\x10GetParticipation\x123.crabs.evening_detective_server.GetParticipationReq\x1a0.crabs.evening_detective_server.ParticipationRsp\"\xd0\x04\x92A\xab\x04\n" + ")Подтверждение участия\x122Получить состояние участия\x1a\xc7\x03Возвращает команду, игру и текущее решение по персональному токену из письма. Авторизация JWT не требуется. Чтение не меняет статус участия. Токен передаётся в теле запроса. Недействительная ссылка и ошибки обработки возвращаются в поле error при HTTP 200.b\x00\x82\xd3\xe4\x93\x02\x1b:\x01*\"\x16/api/participation/get\x12\xf2\b\n" + @@ -9996,7 +10161,11 @@ const file_main_proto_rawDesc = "" + "\bИгры\x12\x19Получить игры\x82\xd3\xe4\x93\x02\f\x12\n" + "/api/games\x12\xa2\x01\n" + "\aGetGame\x12*.crabs.evening_detective_server.GetGameReq\x1a*.crabs.evening_detective_server.GetGameRsp\"?\x92A%\n" + - "\bИгры\x12\x19Получить игру\x82\xd3\xe4\x93\x02\x11\x12\x0f/api/games/{id}\x12\xe1\x01\n" + + "\bИгры\x12\x19Получить игру\x82\xd3\xe4\x93\x02\x11\x12\x0f/api/games/{id}\x12\xec\x01\n" + + "\x10IssueGameTickets\x123.crabs.evening_detective_server.IssueGameTicketsReq\x1a3.crabs.evening_detective_server.IssueGameTicketsRsp\"n\x92AE\n" + + "\fБилеты\x12-Выпустить билеты на игруb\x06\n" + + "\x04\n" + + "\x00\x12\x00\x82\xd3\xe4\x93\x02 :\x01*\"\x1b/api/games/{gameId}/tickets\x12\xe1\x01\n" + "\x13CreateScreenSession\x126.crabs.evening_detective_server.CreateScreenSessionReq\x1a6.crabs.evening_detective_server.CreateScreenSessionRsp\"Z\x92A@\n" + "\fЭкраны\x12(Создать сессию экранаb\x06\n" + "\x04\n" + @@ -10118,7 +10287,7 @@ func file_main_proto_rawDescGZIP() []byte { } var file_main_proto_enumTypes = make([]protoimpl.EnumInfo, 2) -var file_main_proto_msgTypes = make([]protoimpl.MessageInfo, 171) +var file_main_proto_msgTypes = make([]protoimpl.MessageInfo, 174) var file_main_proto_goTypes = []any{ (ScreenMode)(0), // 0: crabs.evening_detective_server.ScreenMode (ScreenCommand)(0), // 1: crabs.evening_detective_server.ScreenCommand @@ -10293,12 +10462,15 @@ var file_main_proto_goTypes = []any{ (*SetTeamAnswerScoreRsp)(nil), // 170: crabs.evening_detective_server.SetTeamAnswerScoreRsp (*UpdateScenarioBackgroundReq)(nil), // 171: crabs.evening_detective_server.UpdateScenarioBackgroundReq (*UpdateScenarioBackgroundRsp)(nil), // 172: crabs.evening_detective_server.UpdateScenarioBackgroundRsp - (*timestamppb.Timestamp)(nil), // 173: google.protobuf.Timestamp - (*httpbody.HttpBody)(nil), // 174: google.api.HttpBody + (*IssueGameTicketsReq)(nil), // 173: crabs.evening_detective_server.IssueGameTicketsReq + (*IssueGameTicketsRsp)(nil), // 174: crabs.evening_detective_server.IssueGameTicketsRsp + (*Ticket)(nil), // 175: crabs.evening_detective_server.Ticket + (*timestamppb.Timestamp)(nil), // 176: google.protobuf.Timestamp + (*httpbody.HttpBody)(nil), // 177: google.api.HttpBody } var file_main_proto_depIdxs = []int32{ 24, // 0: crabs.evening_detective_server.GetUsersRsp.users:type_name -> crabs.evening_detective_server.User - 173, // 1: crabs.evening_detective_server.User.created_at:type_name -> google.protobuf.Timestamp + 176, // 1: crabs.evening_detective_server.User.created_at:type_name -> google.protobuf.Timestamp 24, // 2: crabs.evening_detective_server.GetUserByIdRsp.user:type_name -> crabs.evening_detective_server.User 24, // 3: crabs.evening_detective_server.GetMeRsp.user:type_name -> crabs.evening_detective_server.User 48, // 4: crabs.evening_detective_server.GetMyScenariosRsp.scenarios:type_name -> crabs.evening_detective_server.Scenario @@ -10306,9 +10478,9 @@ var file_main_proto_depIdxs = []int32{ 48, // 6: crabs.evening_detective_server.GetScenarioRsp.scenario:type_name -> crabs.evening_detective_server.Scenario 49, // 7: crabs.evening_detective_server.Scenario.story:type_name -> crabs.evening_detective_server.Story 24, // 8: crabs.evening_detective_server.Scenario.author:type_name -> crabs.evening_detective_server.User - 173, // 9: crabs.evening_detective_server.Scenario.updated_at:type_name -> google.protobuf.Timestamp - 173, // 10: crabs.evening_detective_server.Scenario.created_at:type_name -> google.protobuf.Timestamp - 173, // 11: crabs.evening_detective_server.Scenario.published_at:type_name -> google.protobuf.Timestamp + 176, // 9: crabs.evening_detective_server.Scenario.updated_at:type_name -> google.protobuf.Timestamp + 176, // 10: crabs.evening_detective_server.Scenario.created_at:type_name -> google.protobuf.Timestamp + 176, // 11: crabs.evening_detective_server.Scenario.published_at:type_name -> google.protobuf.Timestamp 50, // 12: crabs.evening_detective_server.Story.conclusion:type_name -> crabs.evening_detective_server.Conclusion 51, // 13: crabs.evening_detective_server.Story.introduction:type_name -> crabs.evening_detective_server.Introduction 52, // 14: crabs.evening_detective_server.Story.places:type_name -> crabs.evening_detective_server.Place @@ -10325,13 +10497,13 @@ var file_main_proto_depIdxs = []int32{ 51, // 25: crabs.evening_detective_server.UpdateScenarioIntroReq.introduction:type_name -> crabs.evening_detective_server.Introduction 56, // 26: crabs.evening_detective_server.AddScenarioQuestionReq.question:type_name -> crabs.evening_detective_server.Question 56, // 27: crabs.evening_detective_server.UpdateScenarioQuestionReq.question:type_name -> crabs.evening_detective_server.Question - 173, // 28: crabs.evening_detective_server.AddGameReq.start_at:type_name -> google.protobuf.Timestamp + 176, // 28: crabs.evening_detective_server.AddGameReq.start_at:type_name -> google.protobuf.Timestamp 90, // 29: crabs.evening_detective_server.GetGamesRsp.games:type_name -> crabs.evening_detective_server.Game - 173, // 30: crabs.evening_detective_server.Game.start_at:type_name -> google.protobuf.Timestamp + 176, // 30: crabs.evening_detective_server.Game.start_at:type_name -> google.protobuf.Timestamp 48, // 31: crabs.evening_detective_server.Game.scenario:type_name -> crabs.evening_detective_server.Scenario 118, // 32: crabs.evening_detective_server.Game.teams:type_name -> crabs.evening_detective_server.Team - 173, // 33: crabs.evening_detective_server.Game.started_at:type_name -> google.protobuf.Timestamp - 173, // 34: crabs.evening_detective_server.Game.ended_at:type_name -> google.protobuf.Timestamp + 176, // 33: crabs.evening_detective_server.Game.started_at:type_name -> google.protobuf.Timestamp + 176, // 34: crabs.evening_detective_server.Game.ended_at:type_name -> google.protobuf.Timestamp 0, // 35: crabs.evening_detective_server.ScreenState.mode:type_name -> crabs.evening_detective_server.ScreenMode 1, // 36: crabs.evening_detective_server.ScreenState.command:type_name -> crabs.evening_detective_server.ScreenCommand 91, // 37: crabs.evening_detective_server.GetScreenStateRsp.state:type_name -> crabs.evening_detective_server.ScreenState @@ -10342,7 +10514,7 @@ var file_main_proto_depIdxs = []int32{ 1, // 42: crabs.evening_detective_server.SendScreenCommandReq.command:type_name -> crabs.evening_detective_server.ScreenCommand 124, // 43: crabs.evening_detective_server.GetScreenResultsRsp.questions:type_name -> crabs.evening_detective_server.ResultsQuestion 125, // 44: crabs.evening_detective_server.GetScreenResultsRsp.teams:type_name -> crabs.evening_detective_server.TeamResult - 173, // 45: crabs.evening_detective_server.ParticipationRsp.start_at:type_name -> google.protobuf.Timestamp + 176, // 45: crabs.evening_detective_server.ParticipationRsp.start_at:type_name -> google.protobuf.Timestamp 53, // 46: crabs.evening_detective_server.Team.applications:type_name -> crabs.evening_detective_server.Application 90, // 47: crabs.evening_detective_server.GetGameRsp.game:type_name -> crabs.evening_detective_server.Game 56, // 48: crabs.evening_detective_server.GetGameAnswersRsp.questions:type_name -> crabs.evening_detective_server.Question @@ -10351,183 +10523,186 @@ var file_main_proto_depIdxs = []int32{ 58, // 51: crabs.evening_detective_server.TeamResult.answers:type_name -> crabs.evening_detective_server.AnswerScore 124, // 52: crabs.evening_detective_server.GetGameResultsRsp.questions:type_name -> crabs.evening_detective_server.ResultsQuestion 125, // 53: crabs.evening_detective_server.GetGameResultsRsp.teams:type_name -> crabs.evening_detective_server.TeamResult - 173, // 54: crabs.evening_detective_server.GameReview.created_at:type_name -> google.protobuf.Timestamp + 176, // 54: crabs.evening_detective_server.GameReview.created_at:type_name -> google.protobuf.Timestamp 127, // 55: crabs.evening_detective_server.CreateGameReviewRsp.review:type_name -> crabs.evening_detective_server.GameReview 127, // 56: crabs.evening_detective_server.GetGameReviewsRsp.reviews:type_name -> crabs.evening_detective_server.GameReview 127, // 57: crabs.evening_detective_server.ModerateGameReviewRsp.review:type_name -> crabs.evening_detective_server.GameReview - 173, // 58: crabs.evening_detective_server.UpdateGameReq.start_at:type_name -> google.protobuf.Timestamp + 176, // 58: crabs.evening_detective_server.UpdateGameReq.start_at:type_name -> google.protobuf.Timestamp 49, // 59: crabs.evening_detective_server.GetTeamStoryRsp.story:type_name -> crabs.evening_detective_server.Story 90, // 60: crabs.evening_detective_server.GetTeamStoryRsp.game:type_name -> crabs.evening_detective_server.Game 160, // 61: crabs.evening_detective_server.GetTeamStoryRsp.actions:type_name -> crabs.evening_detective_server.TeamAction 57, // 62: crabs.evening_detective_server.GetTeamAnswersRsp.answers:type_name -> crabs.evening_detective_server.Answer 57, // 63: crabs.evening_detective_server.SubmitTeamAnswersReq.answers:type_name -> crabs.evening_detective_server.Answer - 115, // 64: crabs.evening_detective_server.EveningDetectiveServer.GetParticipation:input_type -> crabs.evening_detective_server.GetParticipationReq - 116, // 65: crabs.evening_detective_server.EveningDetectiveServer.AnswerParticipation:input_type -> crabs.evening_detective_server.AnswerParticipationReq - 2, // 66: crabs.evening_detective_server.EveningDetectiveServer.Ping:input_type -> crabs.evening_detective_server.PingReq - 4, // 67: crabs.evening_detective_server.EveningDetectiveServer.Echo:input_type -> crabs.evening_detective_server.EchoReq - 6, // 68: crabs.evening_detective_server.EveningDetectiveServer.Signup:input_type -> crabs.evening_detective_server.SignupReq - 8, // 69: crabs.evening_detective_server.EveningDetectiveServer.RefreshPassword:input_type -> crabs.evening_detective_server.RefreshPasswordReq - 10, // 70: crabs.evening_detective_server.EveningDetectiveServer.Login:input_type -> crabs.evening_detective_server.LoginReq - 12, // 71: crabs.evening_detective_server.EveningDetectiveServer.Refresh:input_type -> crabs.evening_detective_server.RefreshReq - 14, // 72: crabs.evening_detective_server.EveningDetectiveServer.DeleteAccount:input_type -> crabs.evening_detective_server.DeleteAccountReq - 16, // 73: crabs.evening_detective_server.EveningDetectiveServer.GetTerms:input_type -> crabs.evening_detective_server.GetTermsReq - 18, // 74: crabs.evening_detective_server.EveningDetectiveServer.GetPrivacy:input_type -> crabs.evening_detective_server.GetPrivacyReq - 20, // 75: crabs.evening_detective_server.EveningDetectiveServer.GetConsent:input_type -> crabs.evening_detective_server.GetConsentReq - 22, // 76: crabs.evening_detective_server.EveningDetectiveServer.GetUsers:input_type -> crabs.evening_detective_server.GetUsersReq - 25, // 77: crabs.evening_detective_server.EveningDetectiveServer.GetUserById:input_type -> crabs.evening_detective_server.GetUserByIdReq - 27, // 78: crabs.evening_detective_server.EveningDetectiveServer.GetMe:input_type -> crabs.evening_detective_server.GetMeReq - 29, // 79: crabs.evening_detective_server.EveningDetectiveServer.ChangeUserPassword:input_type -> crabs.evening_detective_server.ChangeUserPasswordReq - 31, // 80: crabs.evening_detective_server.EveningDetectiveServer.AddUserRole:input_type -> crabs.evening_detective_server.AddUserRoleReq - 33, // 81: crabs.evening_detective_server.EveningDetectiveServer.DeleteUserRole:input_type -> crabs.evening_detective_server.DeleteUserRoleReq - 35, // 82: crabs.evening_detective_server.EveningDetectiveServer.GetPermissions:input_type -> crabs.evening_detective_server.GetPermissionsReq - 37, // 83: crabs.evening_detective_server.EveningDetectiveServer.UploadFile:input_type -> crabs.evening_detective_server.UploadFileReq - 39, // 84: crabs.evening_detective_server.EveningDetectiveServer.DownloadFile:input_type -> crabs.evening_detective_server.DownloadFileReq - 40, // 85: crabs.evening_detective_server.EveningDetectiveServer.AddScenario:input_type -> crabs.evening_detective_server.AddScenarioReq - 42, // 86: crabs.evening_detective_server.EveningDetectiveServer.GetMyScenarios:input_type -> crabs.evening_detective_server.GetMyScenariosReq - 44, // 87: crabs.evening_detective_server.EveningDetectiveServer.GetScenariosCatalog:input_type -> crabs.evening_detective_server.GetScenariosCatalogReq - 46, // 88: crabs.evening_detective_server.EveningDetectiveServer.GetFullScenario:input_type -> crabs.evening_detective_server.GetScenarioReq - 46, // 89: crabs.evening_detective_server.EveningDetectiveServer.GetScenario:input_type -> crabs.evening_detective_server.GetScenarioReq - 60, // 90: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenario:input_type -> crabs.evening_detective_server.UpdateScenarioReq - 62, // 91: crabs.evening_detective_server.EveningDetectiveServer.PublicScenario:input_type -> crabs.evening_detective_server.PublicScenarioReq - 64, // 92: crabs.evening_detective_server.EveningDetectiveServer.DraftScenario:input_type -> crabs.evening_detective_server.DraftScenarioReq - 66, // 93: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenario:input_type -> crabs.evening_detective_server.DeleteScenarioReq - 68, // 94: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioPlace:input_type -> crabs.evening_detective_server.AddScenarioPlaceReq - 70, // 95: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioPlace:input_type -> crabs.evening_detective_server.UpdateScenarioPlaceReq - 72, // 96: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioPlace:input_type -> crabs.evening_detective_server.DeleteScenarioPlaceReq - 78, // 97: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioQuestion:input_type -> crabs.evening_detective_server.AddScenarioQuestionReq - 80, // 98: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioQuestion:input_type -> crabs.evening_detective_server.UpdateScenarioQuestionReq - 82, // 99: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioQuestion:input_type -> crabs.evening_detective_server.DeleteScenarioQuestionReq - 171, // 100: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioBackground:input_type -> crabs.evening_detective_server.UpdateScenarioBackgroundReq - 76, // 101: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioIntro:input_type -> crabs.evening_detective_server.UpdateScenarioIntroReq - 74, // 102: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioConclusion:input_type -> crabs.evening_detective_server.UpdateScenarioConclusionReq - 84, // 103: crabs.evening_detective_server.EveningDetectiveServer.DownloadScenarioArchive:input_type -> crabs.evening_detective_server.DownloadScenarioArchiveReq - 174, // 104: crabs.evening_detective_server.EveningDetectiveServer.UploadScenarioArchive:input_type -> google.api.HttpBody - 86, // 105: crabs.evening_detective_server.EveningDetectiveServer.AddGame:input_type -> crabs.evening_detective_server.AddGameReq - 88, // 106: crabs.evening_detective_server.EveningDetectiveServer.GetGames:input_type -> crabs.evening_detective_server.GetGamesReq - 119, // 107: crabs.evening_detective_server.EveningDetectiveServer.GetGame:input_type -> crabs.evening_detective_server.GetGameReq - 92, // 108: crabs.evening_detective_server.EveningDetectiveServer.CreateScreenSession:input_type -> crabs.evening_detective_server.CreateScreenSessionReq - 94, // 109: crabs.evening_detective_server.EveningDetectiveServer.GetScreenState:input_type -> crabs.evening_detective_server.GetScreenStateReq - 96, // 110: crabs.evening_detective_server.EveningDetectiveServer.GetGameScreens:input_type -> crabs.evening_detective_server.GetGameScreensReq - 98, // 111: crabs.evening_detective_server.EveningDetectiveServer.BindScreen:input_type -> crabs.evening_detective_server.BindScreenReq - 100, // 112: crabs.evening_detective_server.EveningDetectiveServer.UnbindScreen:input_type -> crabs.evening_detective_server.UnbindScreenReq - 102, // 113: crabs.evening_detective_server.EveningDetectiveServer.SetScreenSound:input_type -> crabs.evening_detective_server.SetScreenSoundReq - 105, // 114: crabs.evening_detective_server.EveningDetectiveServer.GetGameMap:input_type -> crabs.evening_detective_server.GetGameMapReq - 107, // 115: crabs.evening_detective_server.EveningDetectiveServer.UpdateGameMapItem:input_type -> crabs.evening_detective_server.UpdateGameMapItemReq - 109, // 116: crabs.evening_detective_server.EveningDetectiveServer.SetScreenMode:input_type -> crabs.evening_detective_server.SetScreenModeReq - 111, // 117: crabs.evening_detective_server.EveningDetectiveServer.SendScreenCommand:input_type -> crabs.evening_detective_server.SendScreenCommandReq - 113, // 118: crabs.evening_detective_server.EveningDetectiveServer.GetScreenResults:input_type -> crabs.evening_detective_server.GetScreenResultsReq - 119, // 119: crabs.evening_detective_server.EveningDetectiveServer.DownloadTeamQR:input_type -> crabs.evening_detective_server.GetGameReq - 121, // 120: crabs.evening_detective_server.EveningDetectiveServer.GetGameAnswers:input_type -> crabs.evening_detective_server.GetGameAnswersReq - 123, // 121: crabs.evening_detective_server.EveningDetectiveServer.GetGameResults:input_type -> crabs.evening_detective_server.GetGameResultsReq - 128, // 122: crabs.evening_detective_server.EveningDetectiveServer.CreateGameReview:input_type -> crabs.evening_detective_server.CreateGameReviewReq - 130, // 123: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviews:input_type -> crabs.evening_detective_server.GetGameReviewsReq - 131, // 124: crabs.evening_detective_server.EveningDetectiveServer.GetScenarioReviews:input_type -> crabs.evening_detective_server.GetScenarioReviewsReq - 130, // 125: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviewsForModeration:input_type -> crabs.evening_detective_server.GetGameReviewsReq - 132, // 126: crabs.evening_detective_server.EveningDetectiveServer.GetReviewsForModeration:input_type -> crabs.evening_detective_server.GetReviewsForModerationReq - 134, // 127: crabs.evening_detective_server.EveningDetectiveServer.ModerateGameReview:input_type -> crabs.evening_detective_server.ModerateGameReviewReq - 136, // 128: crabs.evening_detective_server.EveningDetectiveServer.UpdateGame:input_type -> crabs.evening_detective_server.UpdateGameReq - 138, // 129: crabs.evening_detective_server.EveningDetectiveServer.StartGame:input_type -> crabs.evening_detective_server.StartGameReq - 140, // 130: crabs.evening_detective_server.EveningDetectiveServer.PauseGame:input_type -> crabs.evening_detective_server.PauseGameReq - 142, // 131: crabs.evening_detective_server.EveningDetectiveServer.PlayGame:input_type -> crabs.evening_detective_server.PlayGameReq - 144, // 132: crabs.evening_detective_server.EveningDetectiveServer.FinishGame:input_type -> crabs.evening_detective_server.FinishGameReq - 146, // 133: crabs.evening_detective_server.EveningDetectiveServer.ResetGame:input_type -> crabs.evening_detective_server.ResetGameReq - 148, // 134: crabs.evening_detective_server.EveningDetectiveServer.DeleteGame:input_type -> crabs.evening_detective_server.DeleteGameReq - 150, // 135: crabs.evening_detective_server.EveningDetectiveServer.AddTeam:input_type -> crabs.evening_detective_server.AddTeamReq - 152, // 136: crabs.evening_detective_server.EveningDetectiveServer.UpdateTeam:input_type -> crabs.evening_detective_server.UpdateTeamReq - 154, // 137: crabs.evening_detective_server.EveningDetectiveServer.DeleteTeam:input_type -> crabs.evening_detective_server.DeleteTeamReq - 156, // 138: crabs.evening_detective_server.EveningDetectiveServer.GiveTeamApplications:input_type -> crabs.evening_detective_server.GiveTeamApplicationsReq - 158, // 139: crabs.evening_detective_server.EveningDetectiveServer.GetTeamStory:input_type -> crabs.evening_detective_server.GetTeamStoryReq - 161, // 140: crabs.evening_detective_server.EveningDetectiveServer.AddTeamAction:input_type -> crabs.evening_detective_server.AddTeamActionReq - 163, // 141: crabs.evening_detective_server.EveningDetectiveServer.DeleteLastTeamAction:input_type -> crabs.evening_detective_server.DeleteLastTeamActionReq - 165, // 142: crabs.evening_detective_server.EveningDetectiveServer.GetTeamAnswers:input_type -> crabs.evening_detective_server.GetTeamAnswersReq - 167, // 143: crabs.evening_detective_server.EveningDetectiveServer.SubmitTeamAnswers:input_type -> crabs.evening_detective_server.SubmitTeamAnswersReq - 169, // 144: crabs.evening_detective_server.EveningDetectiveServer.SetTeamAnswerScore:input_type -> crabs.evening_detective_server.SetTeamAnswerScoreReq - 117, // 145: crabs.evening_detective_server.EveningDetectiveServer.GetParticipation:output_type -> crabs.evening_detective_server.ParticipationRsp - 117, // 146: crabs.evening_detective_server.EveningDetectiveServer.AnswerParticipation:output_type -> crabs.evening_detective_server.ParticipationRsp - 3, // 147: crabs.evening_detective_server.EveningDetectiveServer.Ping:output_type -> crabs.evening_detective_server.PingRsp - 5, // 148: crabs.evening_detective_server.EveningDetectiveServer.Echo:output_type -> crabs.evening_detective_server.EchoRsp - 7, // 149: crabs.evening_detective_server.EveningDetectiveServer.Signup:output_type -> crabs.evening_detective_server.SignupRsp - 9, // 150: crabs.evening_detective_server.EveningDetectiveServer.RefreshPassword:output_type -> crabs.evening_detective_server.RefreshPasswordRsp - 11, // 151: crabs.evening_detective_server.EveningDetectiveServer.Login:output_type -> crabs.evening_detective_server.LoginRsp - 13, // 152: crabs.evening_detective_server.EveningDetectiveServer.Refresh:output_type -> crabs.evening_detective_server.RefreshRsp - 15, // 153: crabs.evening_detective_server.EveningDetectiveServer.DeleteAccount:output_type -> crabs.evening_detective_server.DeleteAccountRsp - 17, // 154: crabs.evening_detective_server.EveningDetectiveServer.GetTerms:output_type -> crabs.evening_detective_server.GetTermsRsp - 19, // 155: crabs.evening_detective_server.EveningDetectiveServer.GetPrivacy:output_type -> crabs.evening_detective_server.GetPrivacyRsp - 21, // 156: crabs.evening_detective_server.EveningDetectiveServer.GetConsent:output_type -> crabs.evening_detective_server.GetConsentRsp - 23, // 157: crabs.evening_detective_server.EveningDetectiveServer.GetUsers:output_type -> crabs.evening_detective_server.GetUsersRsp - 26, // 158: crabs.evening_detective_server.EveningDetectiveServer.GetUserById:output_type -> crabs.evening_detective_server.GetUserByIdRsp - 28, // 159: crabs.evening_detective_server.EveningDetectiveServer.GetMe:output_type -> crabs.evening_detective_server.GetMeRsp - 30, // 160: crabs.evening_detective_server.EveningDetectiveServer.ChangeUserPassword:output_type -> crabs.evening_detective_server.ChangeUserPasswordRsp - 32, // 161: crabs.evening_detective_server.EveningDetectiveServer.AddUserRole:output_type -> crabs.evening_detective_server.AddUserRoleRsp - 34, // 162: crabs.evening_detective_server.EveningDetectiveServer.DeleteUserRole:output_type -> crabs.evening_detective_server.DeleteUserRoleRsp - 36, // 163: crabs.evening_detective_server.EveningDetectiveServer.GetPermissions:output_type -> crabs.evening_detective_server.GetPermissionsRsp - 38, // 164: crabs.evening_detective_server.EveningDetectiveServer.UploadFile:output_type -> crabs.evening_detective_server.UploadFileRsp - 174, // 165: crabs.evening_detective_server.EveningDetectiveServer.DownloadFile:output_type -> google.api.HttpBody - 41, // 166: crabs.evening_detective_server.EveningDetectiveServer.AddScenario:output_type -> crabs.evening_detective_server.AddScenarioRsp - 43, // 167: crabs.evening_detective_server.EveningDetectiveServer.GetMyScenarios:output_type -> crabs.evening_detective_server.GetMyScenariosRsp - 45, // 168: crabs.evening_detective_server.EveningDetectiveServer.GetScenariosCatalog:output_type -> crabs.evening_detective_server.GetScenariosCatalogRsp - 47, // 169: crabs.evening_detective_server.EveningDetectiveServer.GetFullScenario:output_type -> crabs.evening_detective_server.GetScenarioRsp - 47, // 170: crabs.evening_detective_server.EveningDetectiveServer.GetScenario:output_type -> crabs.evening_detective_server.GetScenarioRsp - 61, // 171: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenario:output_type -> crabs.evening_detective_server.UpdateScenarioRsp - 63, // 172: crabs.evening_detective_server.EveningDetectiveServer.PublicScenario:output_type -> crabs.evening_detective_server.PublicScenarioRsp - 65, // 173: crabs.evening_detective_server.EveningDetectiveServer.DraftScenario:output_type -> crabs.evening_detective_server.DraftScenarioRsp - 67, // 174: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenario:output_type -> crabs.evening_detective_server.DeleteScenarioRsp - 69, // 175: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioPlace:output_type -> crabs.evening_detective_server.AddScenarioPlaceRsp - 71, // 176: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioPlace:output_type -> crabs.evening_detective_server.UpdateScenarioPlaceRsp - 73, // 177: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioPlace:output_type -> crabs.evening_detective_server.DeleteScenarioPlaceRsp - 79, // 178: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioQuestion:output_type -> crabs.evening_detective_server.AddScenarioQuestionRsp - 81, // 179: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioQuestion:output_type -> crabs.evening_detective_server.UpdateScenarioQuestionRsp - 83, // 180: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioQuestion:output_type -> crabs.evening_detective_server.DeleteScenarioQuestionRsp - 172, // 181: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioBackground:output_type -> crabs.evening_detective_server.UpdateScenarioBackgroundRsp - 77, // 182: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioIntro:output_type -> crabs.evening_detective_server.UpdateScenarioIntroRsp - 75, // 183: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioConclusion:output_type -> crabs.evening_detective_server.UpdateScenarioConclusionRsp - 174, // 184: crabs.evening_detective_server.EveningDetectiveServer.DownloadScenarioArchive:output_type -> google.api.HttpBody - 85, // 185: crabs.evening_detective_server.EveningDetectiveServer.UploadScenarioArchive:output_type -> crabs.evening_detective_server.UploadScenarioArchiveRsp - 87, // 186: crabs.evening_detective_server.EveningDetectiveServer.AddGame:output_type -> crabs.evening_detective_server.AddGameRsp - 89, // 187: crabs.evening_detective_server.EveningDetectiveServer.GetGames:output_type -> crabs.evening_detective_server.GetGamesRsp - 120, // 188: crabs.evening_detective_server.EveningDetectiveServer.GetGame:output_type -> crabs.evening_detective_server.GetGameRsp - 93, // 189: crabs.evening_detective_server.EveningDetectiveServer.CreateScreenSession:output_type -> crabs.evening_detective_server.CreateScreenSessionRsp - 95, // 190: crabs.evening_detective_server.EveningDetectiveServer.GetScreenState:output_type -> crabs.evening_detective_server.GetScreenStateRsp - 97, // 191: crabs.evening_detective_server.EveningDetectiveServer.GetGameScreens:output_type -> crabs.evening_detective_server.GetGameScreensRsp - 99, // 192: crabs.evening_detective_server.EveningDetectiveServer.BindScreen:output_type -> crabs.evening_detective_server.BindScreenRsp - 101, // 193: crabs.evening_detective_server.EveningDetectiveServer.UnbindScreen:output_type -> crabs.evening_detective_server.UnbindScreenRsp - 103, // 194: crabs.evening_detective_server.EveningDetectiveServer.SetScreenSound:output_type -> crabs.evening_detective_server.SetScreenSoundRsp - 106, // 195: crabs.evening_detective_server.EveningDetectiveServer.GetGameMap:output_type -> crabs.evening_detective_server.GetGameMapRsp - 108, // 196: crabs.evening_detective_server.EveningDetectiveServer.UpdateGameMapItem:output_type -> crabs.evening_detective_server.UpdateGameMapItemRsp - 110, // 197: crabs.evening_detective_server.EveningDetectiveServer.SetScreenMode:output_type -> crabs.evening_detective_server.SetScreenModeRsp - 112, // 198: crabs.evening_detective_server.EveningDetectiveServer.SendScreenCommand:output_type -> crabs.evening_detective_server.SendScreenCommandRsp - 114, // 199: crabs.evening_detective_server.EveningDetectiveServer.GetScreenResults:output_type -> crabs.evening_detective_server.GetScreenResultsRsp - 174, // 200: crabs.evening_detective_server.EveningDetectiveServer.DownloadTeamQR:output_type -> google.api.HttpBody - 122, // 201: crabs.evening_detective_server.EveningDetectiveServer.GetGameAnswers:output_type -> crabs.evening_detective_server.GetGameAnswersRsp - 126, // 202: crabs.evening_detective_server.EveningDetectiveServer.GetGameResults:output_type -> crabs.evening_detective_server.GetGameResultsRsp - 129, // 203: crabs.evening_detective_server.EveningDetectiveServer.CreateGameReview:output_type -> crabs.evening_detective_server.CreateGameReviewRsp - 133, // 204: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviews:output_type -> crabs.evening_detective_server.GetGameReviewsRsp - 133, // 205: crabs.evening_detective_server.EveningDetectiveServer.GetScenarioReviews:output_type -> crabs.evening_detective_server.GetGameReviewsRsp - 133, // 206: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviewsForModeration:output_type -> crabs.evening_detective_server.GetGameReviewsRsp - 133, // 207: crabs.evening_detective_server.EveningDetectiveServer.GetReviewsForModeration:output_type -> crabs.evening_detective_server.GetGameReviewsRsp - 135, // 208: crabs.evening_detective_server.EveningDetectiveServer.ModerateGameReview:output_type -> crabs.evening_detective_server.ModerateGameReviewRsp - 137, // 209: crabs.evening_detective_server.EveningDetectiveServer.UpdateGame:output_type -> crabs.evening_detective_server.UpdateGameRsp - 139, // 210: crabs.evening_detective_server.EveningDetectiveServer.StartGame:output_type -> crabs.evening_detective_server.StartGameRsp - 141, // 211: crabs.evening_detective_server.EveningDetectiveServer.PauseGame:output_type -> crabs.evening_detective_server.PauseGameRsp - 143, // 212: crabs.evening_detective_server.EveningDetectiveServer.PlayGame:output_type -> crabs.evening_detective_server.PlayGameRsp - 145, // 213: crabs.evening_detective_server.EveningDetectiveServer.FinishGame:output_type -> crabs.evening_detective_server.FinishGameRsp - 147, // 214: crabs.evening_detective_server.EveningDetectiveServer.ResetGame:output_type -> crabs.evening_detective_server.ResetGameRsp - 149, // 215: crabs.evening_detective_server.EveningDetectiveServer.DeleteGame:output_type -> crabs.evening_detective_server.DeleteGameRsp - 151, // 216: crabs.evening_detective_server.EveningDetectiveServer.AddTeam:output_type -> crabs.evening_detective_server.AddTeamRsp - 153, // 217: crabs.evening_detective_server.EveningDetectiveServer.UpdateTeam:output_type -> crabs.evening_detective_server.UpdateTeamRsp - 155, // 218: crabs.evening_detective_server.EveningDetectiveServer.DeleteTeam:output_type -> crabs.evening_detective_server.DeleteTeamRsp - 157, // 219: crabs.evening_detective_server.EveningDetectiveServer.GiveTeamApplications:output_type -> crabs.evening_detective_server.GiveTeamApplicationsRsp - 159, // 220: crabs.evening_detective_server.EveningDetectiveServer.GetTeamStory:output_type -> crabs.evening_detective_server.GetTeamStoryRsp - 162, // 221: crabs.evening_detective_server.EveningDetectiveServer.AddTeamAction:output_type -> crabs.evening_detective_server.AddTeamActionRsp - 164, // 222: crabs.evening_detective_server.EveningDetectiveServer.DeleteLastTeamAction:output_type -> crabs.evening_detective_server.DeleteLastTeamActionRsp - 166, // 223: crabs.evening_detective_server.EveningDetectiveServer.GetTeamAnswers:output_type -> crabs.evening_detective_server.GetTeamAnswersRsp - 168, // 224: crabs.evening_detective_server.EveningDetectiveServer.SubmitTeamAnswers:output_type -> crabs.evening_detective_server.SubmitTeamAnswersRsp - 170, // 225: crabs.evening_detective_server.EveningDetectiveServer.SetTeamAnswerScore:output_type -> crabs.evening_detective_server.SetTeamAnswerScoreRsp - 145, // [145:226] is the sub-list for method output_type - 64, // [64:145] is the sub-list for method input_type - 64, // [64:64] is the sub-list for extension type_name - 64, // [64:64] is the sub-list for extension extendee - 0, // [0:64] is the sub-list for field type_name + 175, // 64: crabs.evening_detective_server.IssueGameTicketsRsp.tickets:type_name -> crabs.evening_detective_server.Ticket + 115, // 65: crabs.evening_detective_server.EveningDetectiveServer.GetParticipation:input_type -> crabs.evening_detective_server.GetParticipationReq + 116, // 66: crabs.evening_detective_server.EveningDetectiveServer.AnswerParticipation:input_type -> crabs.evening_detective_server.AnswerParticipationReq + 2, // 67: crabs.evening_detective_server.EveningDetectiveServer.Ping:input_type -> crabs.evening_detective_server.PingReq + 4, // 68: crabs.evening_detective_server.EveningDetectiveServer.Echo:input_type -> crabs.evening_detective_server.EchoReq + 6, // 69: crabs.evening_detective_server.EveningDetectiveServer.Signup:input_type -> crabs.evening_detective_server.SignupReq + 8, // 70: crabs.evening_detective_server.EveningDetectiveServer.RefreshPassword:input_type -> crabs.evening_detective_server.RefreshPasswordReq + 10, // 71: crabs.evening_detective_server.EveningDetectiveServer.Login:input_type -> crabs.evening_detective_server.LoginReq + 12, // 72: crabs.evening_detective_server.EveningDetectiveServer.Refresh:input_type -> crabs.evening_detective_server.RefreshReq + 14, // 73: crabs.evening_detective_server.EveningDetectiveServer.DeleteAccount:input_type -> crabs.evening_detective_server.DeleteAccountReq + 16, // 74: crabs.evening_detective_server.EveningDetectiveServer.GetTerms:input_type -> crabs.evening_detective_server.GetTermsReq + 18, // 75: crabs.evening_detective_server.EveningDetectiveServer.GetPrivacy:input_type -> crabs.evening_detective_server.GetPrivacyReq + 20, // 76: crabs.evening_detective_server.EveningDetectiveServer.GetConsent:input_type -> crabs.evening_detective_server.GetConsentReq + 22, // 77: crabs.evening_detective_server.EveningDetectiveServer.GetUsers:input_type -> crabs.evening_detective_server.GetUsersReq + 25, // 78: crabs.evening_detective_server.EveningDetectiveServer.GetUserById:input_type -> crabs.evening_detective_server.GetUserByIdReq + 27, // 79: crabs.evening_detective_server.EveningDetectiveServer.GetMe:input_type -> crabs.evening_detective_server.GetMeReq + 29, // 80: crabs.evening_detective_server.EveningDetectiveServer.ChangeUserPassword:input_type -> crabs.evening_detective_server.ChangeUserPasswordReq + 31, // 81: crabs.evening_detective_server.EveningDetectiveServer.AddUserRole:input_type -> crabs.evening_detective_server.AddUserRoleReq + 33, // 82: crabs.evening_detective_server.EveningDetectiveServer.DeleteUserRole:input_type -> crabs.evening_detective_server.DeleteUserRoleReq + 35, // 83: crabs.evening_detective_server.EveningDetectiveServer.GetPermissions:input_type -> crabs.evening_detective_server.GetPermissionsReq + 37, // 84: crabs.evening_detective_server.EveningDetectiveServer.UploadFile:input_type -> crabs.evening_detective_server.UploadFileReq + 39, // 85: crabs.evening_detective_server.EveningDetectiveServer.DownloadFile:input_type -> crabs.evening_detective_server.DownloadFileReq + 40, // 86: crabs.evening_detective_server.EveningDetectiveServer.AddScenario:input_type -> crabs.evening_detective_server.AddScenarioReq + 42, // 87: crabs.evening_detective_server.EveningDetectiveServer.GetMyScenarios:input_type -> crabs.evening_detective_server.GetMyScenariosReq + 44, // 88: crabs.evening_detective_server.EveningDetectiveServer.GetScenariosCatalog:input_type -> crabs.evening_detective_server.GetScenariosCatalogReq + 46, // 89: crabs.evening_detective_server.EveningDetectiveServer.GetFullScenario:input_type -> crabs.evening_detective_server.GetScenarioReq + 46, // 90: crabs.evening_detective_server.EveningDetectiveServer.GetScenario:input_type -> crabs.evening_detective_server.GetScenarioReq + 60, // 91: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenario:input_type -> crabs.evening_detective_server.UpdateScenarioReq + 62, // 92: crabs.evening_detective_server.EveningDetectiveServer.PublicScenario:input_type -> crabs.evening_detective_server.PublicScenarioReq + 64, // 93: crabs.evening_detective_server.EveningDetectiveServer.DraftScenario:input_type -> crabs.evening_detective_server.DraftScenarioReq + 66, // 94: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenario:input_type -> crabs.evening_detective_server.DeleteScenarioReq + 68, // 95: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioPlace:input_type -> crabs.evening_detective_server.AddScenarioPlaceReq + 70, // 96: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioPlace:input_type -> crabs.evening_detective_server.UpdateScenarioPlaceReq + 72, // 97: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioPlace:input_type -> crabs.evening_detective_server.DeleteScenarioPlaceReq + 78, // 98: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioQuestion:input_type -> crabs.evening_detective_server.AddScenarioQuestionReq + 80, // 99: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioQuestion:input_type -> crabs.evening_detective_server.UpdateScenarioQuestionReq + 82, // 100: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioQuestion:input_type -> crabs.evening_detective_server.DeleteScenarioQuestionReq + 171, // 101: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioBackground:input_type -> crabs.evening_detective_server.UpdateScenarioBackgroundReq + 76, // 102: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioIntro:input_type -> crabs.evening_detective_server.UpdateScenarioIntroReq + 74, // 103: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioConclusion:input_type -> crabs.evening_detective_server.UpdateScenarioConclusionReq + 84, // 104: crabs.evening_detective_server.EveningDetectiveServer.DownloadScenarioArchive:input_type -> crabs.evening_detective_server.DownloadScenarioArchiveReq + 177, // 105: crabs.evening_detective_server.EveningDetectiveServer.UploadScenarioArchive:input_type -> google.api.HttpBody + 86, // 106: crabs.evening_detective_server.EveningDetectiveServer.AddGame:input_type -> crabs.evening_detective_server.AddGameReq + 88, // 107: crabs.evening_detective_server.EveningDetectiveServer.GetGames:input_type -> crabs.evening_detective_server.GetGamesReq + 119, // 108: crabs.evening_detective_server.EveningDetectiveServer.GetGame:input_type -> crabs.evening_detective_server.GetGameReq + 173, // 109: crabs.evening_detective_server.EveningDetectiveServer.IssueGameTickets:input_type -> crabs.evening_detective_server.IssueGameTicketsReq + 92, // 110: crabs.evening_detective_server.EveningDetectiveServer.CreateScreenSession:input_type -> crabs.evening_detective_server.CreateScreenSessionReq + 94, // 111: crabs.evening_detective_server.EveningDetectiveServer.GetScreenState:input_type -> crabs.evening_detective_server.GetScreenStateReq + 96, // 112: crabs.evening_detective_server.EveningDetectiveServer.GetGameScreens:input_type -> crabs.evening_detective_server.GetGameScreensReq + 98, // 113: crabs.evening_detective_server.EveningDetectiveServer.BindScreen:input_type -> crabs.evening_detective_server.BindScreenReq + 100, // 114: crabs.evening_detective_server.EveningDetectiveServer.UnbindScreen:input_type -> crabs.evening_detective_server.UnbindScreenReq + 102, // 115: crabs.evening_detective_server.EveningDetectiveServer.SetScreenSound:input_type -> crabs.evening_detective_server.SetScreenSoundReq + 105, // 116: crabs.evening_detective_server.EveningDetectiveServer.GetGameMap:input_type -> crabs.evening_detective_server.GetGameMapReq + 107, // 117: crabs.evening_detective_server.EveningDetectiveServer.UpdateGameMapItem:input_type -> crabs.evening_detective_server.UpdateGameMapItemReq + 109, // 118: crabs.evening_detective_server.EveningDetectiveServer.SetScreenMode:input_type -> crabs.evening_detective_server.SetScreenModeReq + 111, // 119: crabs.evening_detective_server.EveningDetectiveServer.SendScreenCommand:input_type -> crabs.evening_detective_server.SendScreenCommandReq + 113, // 120: crabs.evening_detective_server.EveningDetectiveServer.GetScreenResults:input_type -> crabs.evening_detective_server.GetScreenResultsReq + 119, // 121: crabs.evening_detective_server.EveningDetectiveServer.DownloadTeamQR:input_type -> crabs.evening_detective_server.GetGameReq + 121, // 122: crabs.evening_detective_server.EveningDetectiveServer.GetGameAnswers:input_type -> crabs.evening_detective_server.GetGameAnswersReq + 123, // 123: crabs.evening_detective_server.EveningDetectiveServer.GetGameResults:input_type -> crabs.evening_detective_server.GetGameResultsReq + 128, // 124: crabs.evening_detective_server.EveningDetectiveServer.CreateGameReview:input_type -> crabs.evening_detective_server.CreateGameReviewReq + 130, // 125: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviews:input_type -> crabs.evening_detective_server.GetGameReviewsReq + 131, // 126: crabs.evening_detective_server.EveningDetectiveServer.GetScenarioReviews:input_type -> crabs.evening_detective_server.GetScenarioReviewsReq + 130, // 127: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviewsForModeration:input_type -> crabs.evening_detective_server.GetGameReviewsReq + 132, // 128: crabs.evening_detective_server.EveningDetectiveServer.GetReviewsForModeration:input_type -> crabs.evening_detective_server.GetReviewsForModerationReq + 134, // 129: crabs.evening_detective_server.EveningDetectiveServer.ModerateGameReview:input_type -> crabs.evening_detective_server.ModerateGameReviewReq + 136, // 130: crabs.evening_detective_server.EveningDetectiveServer.UpdateGame:input_type -> crabs.evening_detective_server.UpdateGameReq + 138, // 131: crabs.evening_detective_server.EveningDetectiveServer.StartGame:input_type -> crabs.evening_detective_server.StartGameReq + 140, // 132: crabs.evening_detective_server.EveningDetectiveServer.PauseGame:input_type -> crabs.evening_detective_server.PauseGameReq + 142, // 133: crabs.evening_detective_server.EveningDetectiveServer.PlayGame:input_type -> crabs.evening_detective_server.PlayGameReq + 144, // 134: crabs.evening_detective_server.EveningDetectiveServer.FinishGame:input_type -> crabs.evening_detective_server.FinishGameReq + 146, // 135: crabs.evening_detective_server.EveningDetectiveServer.ResetGame:input_type -> crabs.evening_detective_server.ResetGameReq + 148, // 136: crabs.evening_detective_server.EveningDetectiveServer.DeleteGame:input_type -> crabs.evening_detective_server.DeleteGameReq + 150, // 137: crabs.evening_detective_server.EveningDetectiveServer.AddTeam:input_type -> crabs.evening_detective_server.AddTeamReq + 152, // 138: crabs.evening_detective_server.EveningDetectiveServer.UpdateTeam:input_type -> crabs.evening_detective_server.UpdateTeamReq + 154, // 139: crabs.evening_detective_server.EveningDetectiveServer.DeleteTeam:input_type -> crabs.evening_detective_server.DeleteTeamReq + 156, // 140: crabs.evening_detective_server.EveningDetectiveServer.GiveTeamApplications:input_type -> crabs.evening_detective_server.GiveTeamApplicationsReq + 158, // 141: crabs.evening_detective_server.EveningDetectiveServer.GetTeamStory:input_type -> crabs.evening_detective_server.GetTeamStoryReq + 161, // 142: crabs.evening_detective_server.EveningDetectiveServer.AddTeamAction:input_type -> crabs.evening_detective_server.AddTeamActionReq + 163, // 143: crabs.evening_detective_server.EveningDetectiveServer.DeleteLastTeamAction:input_type -> crabs.evening_detective_server.DeleteLastTeamActionReq + 165, // 144: crabs.evening_detective_server.EveningDetectiveServer.GetTeamAnswers:input_type -> crabs.evening_detective_server.GetTeamAnswersReq + 167, // 145: crabs.evening_detective_server.EveningDetectiveServer.SubmitTeamAnswers:input_type -> crabs.evening_detective_server.SubmitTeamAnswersReq + 169, // 146: crabs.evening_detective_server.EveningDetectiveServer.SetTeamAnswerScore:input_type -> crabs.evening_detective_server.SetTeamAnswerScoreReq + 117, // 147: crabs.evening_detective_server.EveningDetectiveServer.GetParticipation:output_type -> crabs.evening_detective_server.ParticipationRsp + 117, // 148: crabs.evening_detective_server.EveningDetectiveServer.AnswerParticipation:output_type -> crabs.evening_detective_server.ParticipationRsp + 3, // 149: crabs.evening_detective_server.EveningDetectiveServer.Ping:output_type -> crabs.evening_detective_server.PingRsp + 5, // 150: crabs.evening_detective_server.EveningDetectiveServer.Echo:output_type -> crabs.evening_detective_server.EchoRsp + 7, // 151: crabs.evening_detective_server.EveningDetectiveServer.Signup:output_type -> crabs.evening_detective_server.SignupRsp + 9, // 152: crabs.evening_detective_server.EveningDetectiveServer.RefreshPassword:output_type -> crabs.evening_detective_server.RefreshPasswordRsp + 11, // 153: crabs.evening_detective_server.EveningDetectiveServer.Login:output_type -> crabs.evening_detective_server.LoginRsp + 13, // 154: crabs.evening_detective_server.EveningDetectiveServer.Refresh:output_type -> crabs.evening_detective_server.RefreshRsp + 15, // 155: crabs.evening_detective_server.EveningDetectiveServer.DeleteAccount:output_type -> crabs.evening_detective_server.DeleteAccountRsp + 17, // 156: crabs.evening_detective_server.EveningDetectiveServer.GetTerms:output_type -> crabs.evening_detective_server.GetTermsRsp + 19, // 157: crabs.evening_detective_server.EveningDetectiveServer.GetPrivacy:output_type -> crabs.evening_detective_server.GetPrivacyRsp + 21, // 158: crabs.evening_detective_server.EveningDetectiveServer.GetConsent:output_type -> crabs.evening_detective_server.GetConsentRsp + 23, // 159: crabs.evening_detective_server.EveningDetectiveServer.GetUsers:output_type -> crabs.evening_detective_server.GetUsersRsp + 26, // 160: crabs.evening_detective_server.EveningDetectiveServer.GetUserById:output_type -> crabs.evening_detective_server.GetUserByIdRsp + 28, // 161: crabs.evening_detective_server.EveningDetectiveServer.GetMe:output_type -> crabs.evening_detective_server.GetMeRsp + 30, // 162: crabs.evening_detective_server.EveningDetectiveServer.ChangeUserPassword:output_type -> crabs.evening_detective_server.ChangeUserPasswordRsp + 32, // 163: crabs.evening_detective_server.EveningDetectiveServer.AddUserRole:output_type -> crabs.evening_detective_server.AddUserRoleRsp + 34, // 164: crabs.evening_detective_server.EveningDetectiveServer.DeleteUserRole:output_type -> crabs.evening_detective_server.DeleteUserRoleRsp + 36, // 165: crabs.evening_detective_server.EveningDetectiveServer.GetPermissions:output_type -> crabs.evening_detective_server.GetPermissionsRsp + 38, // 166: crabs.evening_detective_server.EveningDetectiveServer.UploadFile:output_type -> crabs.evening_detective_server.UploadFileRsp + 177, // 167: crabs.evening_detective_server.EveningDetectiveServer.DownloadFile:output_type -> google.api.HttpBody + 41, // 168: crabs.evening_detective_server.EveningDetectiveServer.AddScenario:output_type -> crabs.evening_detective_server.AddScenarioRsp + 43, // 169: crabs.evening_detective_server.EveningDetectiveServer.GetMyScenarios:output_type -> crabs.evening_detective_server.GetMyScenariosRsp + 45, // 170: crabs.evening_detective_server.EveningDetectiveServer.GetScenariosCatalog:output_type -> crabs.evening_detective_server.GetScenariosCatalogRsp + 47, // 171: crabs.evening_detective_server.EveningDetectiveServer.GetFullScenario:output_type -> crabs.evening_detective_server.GetScenarioRsp + 47, // 172: crabs.evening_detective_server.EveningDetectiveServer.GetScenario:output_type -> crabs.evening_detective_server.GetScenarioRsp + 61, // 173: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenario:output_type -> crabs.evening_detective_server.UpdateScenarioRsp + 63, // 174: crabs.evening_detective_server.EveningDetectiveServer.PublicScenario:output_type -> crabs.evening_detective_server.PublicScenarioRsp + 65, // 175: crabs.evening_detective_server.EveningDetectiveServer.DraftScenario:output_type -> crabs.evening_detective_server.DraftScenarioRsp + 67, // 176: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenario:output_type -> crabs.evening_detective_server.DeleteScenarioRsp + 69, // 177: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioPlace:output_type -> crabs.evening_detective_server.AddScenarioPlaceRsp + 71, // 178: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioPlace:output_type -> crabs.evening_detective_server.UpdateScenarioPlaceRsp + 73, // 179: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioPlace:output_type -> crabs.evening_detective_server.DeleteScenarioPlaceRsp + 79, // 180: crabs.evening_detective_server.EveningDetectiveServer.AddScenarioQuestion:output_type -> crabs.evening_detective_server.AddScenarioQuestionRsp + 81, // 181: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioQuestion:output_type -> crabs.evening_detective_server.UpdateScenarioQuestionRsp + 83, // 182: crabs.evening_detective_server.EveningDetectiveServer.DeleteScenarioQuestion:output_type -> crabs.evening_detective_server.DeleteScenarioQuestionRsp + 172, // 183: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioBackground:output_type -> crabs.evening_detective_server.UpdateScenarioBackgroundRsp + 77, // 184: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioIntro:output_type -> crabs.evening_detective_server.UpdateScenarioIntroRsp + 75, // 185: crabs.evening_detective_server.EveningDetectiveServer.UpdateScenarioConclusion:output_type -> crabs.evening_detective_server.UpdateScenarioConclusionRsp + 177, // 186: crabs.evening_detective_server.EveningDetectiveServer.DownloadScenarioArchive:output_type -> google.api.HttpBody + 85, // 187: crabs.evening_detective_server.EveningDetectiveServer.UploadScenarioArchive:output_type -> crabs.evening_detective_server.UploadScenarioArchiveRsp + 87, // 188: crabs.evening_detective_server.EveningDetectiveServer.AddGame:output_type -> crabs.evening_detective_server.AddGameRsp + 89, // 189: crabs.evening_detective_server.EveningDetectiveServer.GetGames:output_type -> crabs.evening_detective_server.GetGamesRsp + 120, // 190: crabs.evening_detective_server.EveningDetectiveServer.GetGame:output_type -> crabs.evening_detective_server.GetGameRsp + 174, // 191: crabs.evening_detective_server.EveningDetectiveServer.IssueGameTickets:output_type -> crabs.evening_detective_server.IssueGameTicketsRsp + 93, // 192: crabs.evening_detective_server.EveningDetectiveServer.CreateScreenSession:output_type -> crabs.evening_detective_server.CreateScreenSessionRsp + 95, // 193: crabs.evening_detective_server.EveningDetectiveServer.GetScreenState:output_type -> crabs.evening_detective_server.GetScreenStateRsp + 97, // 194: crabs.evening_detective_server.EveningDetectiveServer.GetGameScreens:output_type -> crabs.evening_detective_server.GetGameScreensRsp + 99, // 195: crabs.evening_detective_server.EveningDetectiveServer.BindScreen:output_type -> crabs.evening_detective_server.BindScreenRsp + 101, // 196: crabs.evening_detective_server.EveningDetectiveServer.UnbindScreen:output_type -> crabs.evening_detective_server.UnbindScreenRsp + 103, // 197: crabs.evening_detective_server.EveningDetectiveServer.SetScreenSound:output_type -> crabs.evening_detective_server.SetScreenSoundRsp + 106, // 198: crabs.evening_detective_server.EveningDetectiveServer.GetGameMap:output_type -> crabs.evening_detective_server.GetGameMapRsp + 108, // 199: crabs.evening_detective_server.EveningDetectiveServer.UpdateGameMapItem:output_type -> crabs.evening_detective_server.UpdateGameMapItemRsp + 110, // 200: crabs.evening_detective_server.EveningDetectiveServer.SetScreenMode:output_type -> crabs.evening_detective_server.SetScreenModeRsp + 112, // 201: crabs.evening_detective_server.EveningDetectiveServer.SendScreenCommand:output_type -> crabs.evening_detective_server.SendScreenCommandRsp + 114, // 202: crabs.evening_detective_server.EveningDetectiveServer.GetScreenResults:output_type -> crabs.evening_detective_server.GetScreenResultsRsp + 177, // 203: crabs.evening_detective_server.EveningDetectiveServer.DownloadTeamQR:output_type -> google.api.HttpBody + 122, // 204: crabs.evening_detective_server.EveningDetectiveServer.GetGameAnswers:output_type -> crabs.evening_detective_server.GetGameAnswersRsp + 126, // 205: crabs.evening_detective_server.EveningDetectiveServer.GetGameResults:output_type -> crabs.evening_detective_server.GetGameResultsRsp + 129, // 206: crabs.evening_detective_server.EveningDetectiveServer.CreateGameReview:output_type -> crabs.evening_detective_server.CreateGameReviewRsp + 133, // 207: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviews:output_type -> crabs.evening_detective_server.GetGameReviewsRsp + 133, // 208: crabs.evening_detective_server.EveningDetectiveServer.GetScenarioReviews:output_type -> crabs.evening_detective_server.GetGameReviewsRsp + 133, // 209: crabs.evening_detective_server.EveningDetectiveServer.GetGameReviewsForModeration:output_type -> crabs.evening_detective_server.GetGameReviewsRsp + 133, // 210: crabs.evening_detective_server.EveningDetectiveServer.GetReviewsForModeration:output_type -> crabs.evening_detective_server.GetGameReviewsRsp + 135, // 211: crabs.evening_detective_server.EveningDetectiveServer.ModerateGameReview:output_type -> crabs.evening_detective_server.ModerateGameReviewRsp + 137, // 212: crabs.evening_detective_server.EveningDetectiveServer.UpdateGame:output_type -> crabs.evening_detective_server.UpdateGameRsp + 139, // 213: crabs.evening_detective_server.EveningDetectiveServer.StartGame:output_type -> crabs.evening_detective_server.StartGameRsp + 141, // 214: crabs.evening_detective_server.EveningDetectiveServer.PauseGame:output_type -> crabs.evening_detective_server.PauseGameRsp + 143, // 215: crabs.evening_detective_server.EveningDetectiveServer.PlayGame:output_type -> crabs.evening_detective_server.PlayGameRsp + 145, // 216: crabs.evening_detective_server.EveningDetectiveServer.FinishGame:output_type -> crabs.evening_detective_server.FinishGameRsp + 147, // 217: crabs.evening_detective_server.EveningDetectiveServer.ResetGame:output_type -> crabs.evening_detective_server.ResetGameRsp + 149, // 218: crabs.evening_detective_server.EveningDetectiveServer.DeleteGame:output_type -> crabs.evening_detective_server.DeleteGameRsp + 151, // 219: crabs.evening_detective_server.EveningDetectiveServer.AddTeam:output_type -> crabs.evening_detective_server.AddTeamRsp + 153, // 220: crabs.evening_detective_server.EveningDetectiveServer.UpdateTeam:output_type -> crabs.evening_detective_server.UpdateTeamRsp + 155, // 221: crabs.evening_detective_server.EveningDetectiveServer.DeleteTeam:output_type -> crabs.evening_detective_server.DeleteTeamRsp + 157, // 222: crabs.evening_detective_server.EveningDetectiveServer.GiveTeamApplications:output_type -> crabs.evening_detective_server.GiveTeamApplicationsRsp + 159, // 223: crabs.evening_detective_server.EveningDetectiveServer.GetTeamStory:output_type -> crabs.evening_detective_server.GetTeamStoryRsp + 162, // 224: crabs.evening_detective_server.EveningDetectiveServer.AddTeamAction:output_type -> crabs.evening_detective_server.AddTeamActionRsp + 164, // 225: crabs.evening_detective_server.EveningDetectiveServer.DeleteLastTeamAction:output_type -> crabs.evening_detective_server.DeleteLastTeamActionRsp + 166, // 226: crabs.evening_detective_server.EveningDetectiveServer.GetTeamAnswers:output_type -> crabs.evening_detective_server.GetTeamAnswersRsp + 168, // 227: crabs.evening_detective_server.EveningDetectiveServer.SubmitTeamAnswers:output_type -> crabs.evening_detective_server.SubmitTeamAnswersRsp + 170, // 228: crabs.evening_detective_server.EveningDetectiveServer.SetTeamAnswerScore:output_type -> crabs.evening_detective_server.SetTeamAnswerScoreRsp + 147, // [147:229] is the sub-list for method output_type + 65, // [65:147] is the sub-list for method input_type + 65, // [65:65] is the sub-list for extension type_name + 65, // [65:65] is the sub-list for extension extendee + 0, // [0:65] is the sub-list for field type_name } func init() { file_main_proto_init() } @@ -10546,7 +10721,7 @@ func file_main_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: unsafe.Slice(unsafe.StringData(file_main_proto_rawDesc), len(file_main_proto_rawDesc)), NumEnums: 2, - NumMessages: 171, + NumMessages: 174, NumExtensions: 0, NumServices: 1, }, diff --git a/proto/main.pb.gw.go b/proto/main.pb.gw.go index 0555d22..963230a 100644 --- a/proto/main.pb.gw.go +++ b/proto/main.pb.gw.go @@ -1572,6 +1572,51 @@ func local_request_EveningDetectiveServer_GetGame_0(ctx context.Context, marshal return msg, metadata, err } +func request_EveningDetectiveServer_IssueGameTickets_0(ctx context.Context, marshaler runtime.Marshaler, client EveningDetectiveServerClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var ( + protoReq IssueGameTicketsReq + metadata runtime.ServerMetadata + err error + ) + if err := marshaler.NewDecoder(req.Body).Decode(&protoReq); err != nil && !errors.Is(err, io.EOF) { + return nil, metadata, status.Errorf(codes.InvalidArgument, "%v", err) + } + if req.Body != nil { + _, _ = io.Copy(io.Discard, req.Body) + } + val, ok := pathParams["gameId"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "gameId") + } + protoReq.GameId, err = runtime.Int32(val) + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "gameId", err) + } + msg, err := client.IssueGameTickets(ctx, &protoReq, grpc.Header(&metadata.HeaderMD), grpc.Trailer(&metadata.TrailerMD)) + return msg, metadata, err +} + +func local_request_EveningDetectiveServer_IssueGameTickets_0(ctx context.Context, marshaler runtime.Marshaler, server EveningDetectiveServerServer, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { + var ( + protoReq IssueGameTicketsReq + metadata runtime.ServerMetadata + err error + ) + if err := marshaler.NewDecoder(req.Body).Decode(&protoReq); err != nil && !errors.Is(err, io.EOF) { + return nil, metadata, status.Errorf(codes.InvalidArgument, "%v", err) + } + val, ok := pathParams["gameId"] + if !ok { + return nil, metadata, status.Errorf(codes.InvalidArgument, "missing parameter %s", "gameId") + } + protoReq.GameId, err = runtime.Int32(val) + if err != nil { + return nil, metadata, status.Errorf(codes.InvalidArgument, "type mismatch, parameter: %s, error: %v", "gameId", err) + } + msg, err := server.IssueGameTickets(ctx, &protoReq) + return msg, metadata, err +} + func request_EveningDetectiveServer_CreateScreenSession_0(ctx context.Context, marshaler runtime.Marshaler, client EveningDetectiveServerClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) { var ( protoReq CreateScreenSessionReq @@ -4025,6 +4070,26 @@ func RegisterEveningDetectiveServerHandlerServer(ctx context.Context, mux *runti } forward_EveningDetectiveServer_GetGame_0(annotatedContext, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) }) + mux.Handle(http.MethodPost, pattern_EveningDetectiveServer_IssueGameTickets_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + var stream runtime.ServerTransportStream + ctx = grpc.NewContextWithServerTransportStream(ctx, &stream) + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + annotatedContext, err := runtime.AnnotateIncomingContext(ctx, mux, req, "/crabs.evening_detective_server.EveningDetectiveServer/IssueGameTickets", runtime.WithHTTPPathPattern("/api/games/{gameId}/tickets")) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := local_request_EveningDetectiveServer_IssueGameTickets_0(annotatedContext, inboundMarshaler, server, req, pathParams) + md.HeaderMD, md.TrailerMD = metadata.Join(md.HeaderMD, stream.Header()), metadata.Join(md.TrailerMD, stream.Trailer()) + annotatedContext = runtime.NewServerMetadataContext(annotatedContext, md) + if err != nil { + runtime.HTTPError(annotatedContext, mux, outboundMarshaler, w, req, err) + return + } + forward_EveningDetectiveServer_IssueGameTickets_0(annotatedContext, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + }) mux.Handle(http.MethodPost, pattern_EveningDetectiveServer_CreateScreenSession_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { ctx, cancel := context.WithCancel(req.Context()) defer cancel() @@ -5553,6 +5618,23 @@ func RegisterEveningDetectiveServerHandlerClient(ctx context.Context, mux *runti } forward_EveningDetectiveServer_GetGame_0(annotatedContext, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) }) + mux.Handle(http.MethodPost, pattern_EveningDetectiveServer_IssueGameTickets_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { + ctx, cancel := context.WithCancel(req.Context()) + defer cancel() + inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req) + annotatedContext, err := runtime.AnnotateContext(ctx, mux, req, "/crabs.evening_detective_server.EveningDetectiveServer/IssueGameTickets", runtime.WithHTTPPathPattern("/api/games/{gameId}/tickets")) + if err != nil { + runtime.HTTPError(ctx, mux, outboundMarshaler, w, req, err) + return + } + resp, md, err := request_EveningDetectiveServer_IssueGameTickets_0(annotatedContext, inboundMarshaler, client, req, pathParams) + annotatedContext = runtime.NewServerMetadataContext(annotatedContext, md) + if err != nil { + runtime.HTTPError(annotatedContext, mux, outboundMarshaler, w, req, err) + return + } + forward_EveningDetectiveServer_IssueGameTickets_0(annotatedContext, mux, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...) + }) mux.Handle(http.MethodPost, pattern_EveningDetectiveServer_CreateScreenSession_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) { ctx, cancel := context.WithCancel(req.Context()) defer cancel() @@ -6230,6 +6312,7 @@ var ( pattern_EveningDetectiveServer_AddGame_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1}, []string{"api", "games"}, "")) pattern_EveningDetectiveServer_GetGames_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1}, []string{"api", "games"}, "")) pattern_EveningDetectiveServer_GetGame_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 1, 0, 4, 1, 5, 2}, []string{"api", "games", "id"}, "")) + pattern_EveningDetectiveServer_IssueGameTickets_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 1, 0, 4, 1, 5, 2, 2, 3}, []string{"api", "games", "gameId", "tickets"}, "")) pattern_EveningDetectiveServer_CreateScreenSession_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1}, []string{"api", "screens"}, "")) pattern_EveningDetectiveServer_GetScreenState_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2}, []string{"api", "screens", "state"}, "")) pattern_EveningDetectiveServer_GetGameScreens_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 1, 0, 4, 1, 5, 2, 2, 3}, []string{"api", "games", "gameId", "screens"}, "")) @@ -6314,6 +6397,7 @@ var ( forward_EveningDetectiveServer_AddGame_0 = runtime.ForwardResponseMessage forward_EveningDetectiveServer_GetGames_0 = runtime.ForwardResponseMessage forward_EveningDetectiveServer_GetGame_0 = runtime.ForwardResponseMessage + forward_EveningDetectiveServer_IssueGameTickets_0 = runtime.ForwardResponseMessage forward_EveningDetectiveServer_CreateScreenSession_0 = runtime.ForwardResponseMessage forward_EveningDetectiveServer_GetScreenState_0 = runtime.ForwardResponseMessage forward_EveningDetectiveServer_GetGameScreens_0 = runtime.ForwardResponseMessage diff --git a/proto/main_grpc.pb.go b/proto/main_grpc.pb.go index 5fb7309..abb31c4 100644 --- a/proto/main_grpc.pb.go +++ b/proto/main_grpc.pb.go @@ -64,6 +64,7 @@ const ( EveningDetectiveServer_AddGame_FullMethodName = "/crabs.evening_detective_server.EveningDetectiveServer/AddGame" EveningDetectiveServer_GetGames_FullMethodName = "/crabs.evening_detective_server.EveningDetectiveServer/GetGames" EveningDetectiveServer_GetGame_FullMethodName = "/crabs.evening_detective_server.EveningDetectiveServer/GetGame" + EveningDetectiveServer_IssueGameTickets_FullMethodName = "/crabs.evening_detective_server.EveningDetectiveServer/IssueGameTickets" EveningDetectiveServer_CreateScreenSession_FullMethodName = "/crabs.evening_detective_server.EveningDetectiveServer/CreateScreenSession" EveningDetectiveServer_GetScreenState_FullMethodName = "/crabs.evening_detective_server.EveningDetectiveServer/GetScreenState" EveningDetectiveServer_GetGameScreens_FullMethodName = "/crabs.evening_detective_server.EveningDetectiveServer/GetGameScreens" @@ -155,6 +156,7 @@ type EveningDetectiveServerClient interface { AddGame(ctx context.Context, in *AddGameReq, opts ...grpc.CallOption) (*AddGameRsp, error) GetGames(ctx context.Context, in *GetGamesReq, opts ...grpc.CallOption) (*GetGamesRsp, error) GetGame(ctx context.Context, in *GetGameReq, opts ...grpc.CallOption) (*GetGameRsp, error) + IssueGameTickets(ctx context.Context, in *IssueGameTicketsReq, opts ...grpc.CallOption) (*IssueGameTicketsRsp, error) // Создать сессию экрана. Экран получает токен и показывает QR для привязки. CreateScreenSession(ctx context.Context, in *CreateScreenSessionReq, opts ...grpc.CallOption) (*CreateScreenSessionRsp, error) // Получить состояние экрана по его токену. Вызывается самим экраном. @@ -648,6 +650,16 @@ func (c *eveningDetectiveServerClient) GetGame(ctx context.Context, in *GetGameR return out, nil } +func (c *eveningDetectiveServerClient) IssueGameTickets(ctx context.Context, in *IssueGameTicketsReq, opts ...grpc.CallOption) (*IssueGameTicketsRsp, error) { + cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) + out := new(IssueGameTicketsRsp) + err := c.cc.Invoke(ctx, EveningDetectiveServer_IssueGameTickets_FullMethodName, in, out, cOpts...) + if err != nil { + return nil, err + } + return out, nil +} + func (c *eveningDetectiveServerClient) CreateScreenSession(ctx context.Context, in *CreateScreenSessionReq, opts ...grpc.CallOption) (*CreateScreenSessionRsp, error) { cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) out := new(CreateScreenSessionRsp) @@ -1070,6 +1082,7 @@ type EveningDetectiveServerServer interface { AddGame(context.Context, *AddGameReq) (*AddGameRsp, error) GetGames(context.Context, *GetGamesReq) (*GetGamesRsp, error) GetGame(context.Context, *GetGameReq) (*GetGameRsp, error) + IssueGameTickets(context.Context, *IssueGameTicketsReq) (*IssueGameTicketsRsp, error) // Создать сессию экрана. Экран получает токен и показывает QR для привязки. CreateScreenSession(context.Context, *CreateScreenSessionReq) (*CreateScreenSessionRsp, error) // Получить состояние экрана по его токену. Вызывается самим экраном. @@ -1255,6 +1268,9 @@ func (UnimplementedEveningDetectiveServerServer) GetGames(context.Context, *GetG func (UnimplementedEveningDetectiveServerServer) GetGame(context.Context, *GetGameReq) (*GetGameRsp, error) { return nil, status.Error(codes.Unimplemented, "method GetGame not implemented") } +func (UnimplementedEveningDetectiveServerServer) IssueGameTickets(context.Context, *IssueGameTicketsReq) (*IssueGameTicketsRsp, error) { + return nil, status.Error(codes.Unimplemented, "method IssueGameTickets not implemented") +} func (UnimplementedEveningDetectiveServerServer) CreateScreenSession(context.Context, *CreateScreenSessionReq) (*CreateScreenSessionRsp, error) { return nil, status.Error(codes.Unimplemented, "method CreateScreenSession not implemented") } @@ -2180,6 +2196,24 @@ func _EveningDetectiveServer_GetGame_Handler(srv interface{}, ctx context.Contex return interceptor(ctx, in, info, handler) } +func _EveningDetectiveServer_IssueGameTickets_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { + in := new(IssueGameTicketsReq) + if err := dec(in); err != nil { + return nil, err + } + if interceptor == nil { + return srv.(EveningDetectiveServerServer).IssueGameTickets(ctx, in) + } + info := &grpc.UnaryServerInfo{ + Server: srv, + FullMethod: EveningDetectiveServer_IssueGameTickets_FullMethodName, + } + handler := func(ctx context.Context, req interface{}) (interface{}, error) { + return srv.(EveningDetectiveServerServer).IssueGameTickets(ctx, req.(*IssueGameTicketsReq)) + } + return interceptor(ctx, in, info, handler) +} + func _EveningDetectiveServer_CreateScreenSession_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { in := new(CreateScreenSessionReq) if err := dec(in); err != nil { @@ -3029,6 +3063,10 @@ var EveningDetectiveServer_ServiceDesc = grpc.ServiceDesc{ MethodName: "GetGame", Handler: _EveningDetectiveServer_GetGame_Handler, }, + { + MethodName: "IssueGameTickets", + Handler: _EveningDetectiveServer_IssueGameTickets_Handler, + }, { MethodName: "CreateScreenSession", Handler: _EveningDetectiveServer_CreateScreenSession_Handler,