mattermost/server/public/pluginapi/grpc/proto/common.proto
Nick Misasi 54d0d6cc8b feat(02-01): add PluginAPI proto skeleton and parity verifier
- Create api.proto with PluginAPI service definition covering all 236
  methods from server/public/plugin/api.go
- Create api_user_team.proto with User, Session, and Team request/response
  messages with placeholder fields
- Create api_channel_post.proto with Channel, Post, and Emoji messages
- Create api_kv_config.proto with KV store, config, plugin, and logging
  messages
- Create api_file_bot.proto with File, Upload, and Bot messages
- Create api_remaining.proto with Server, Command, Preference, OAuth,
  Group, SharedChannel, Property, and Audit messages
- Add ViewUsersRestrictions to common.proto
- Add apiverify tool that parses Go API interface and proto service
  to ensure parity
- Update Makefile with new proto file mappings

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-16 11:24:09 -05:00

146 lines
5.5 KiB
Protocol Buffer

// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.
syntax = "proto3";
package mattermost.pluginapi.v1;
option go_package = "github.com/mattermost/mattermost/server/public/pluginapi/grpc/generated/go/pluginapiv1";
import "google/protobuf/struct.proto";
// ==============================================================================
// RPC ENVELOPE CONVENTIONS
// ==============================================================================
//
// This file defines the common types and conventions used across all Plugin API
// and Hook RPCs. All service definitions in Phase 2 (API) and Phase 3 (Hooks)
// MUST follow these conventions for consistency.
//
// ERROR HANDLING STRATEGY:
// ------------------------
// We use Response-embedded AppError (Option B) rather than gRPC status codes.
// - Business errors are encoded in the response message's `error` field
// - gRPC status codes are reserved for transport-level failures only
// (timeouts, connection errors, unavailable plugin, etc.)
// - This preserves full AppError semantics (id, message, detailed_error,
// request_id, status_code, where, params) across language boundaries
//
// REQUEST CONVENTIONS:
// --------------------
// Every RPC request message MUST:
// - Be named `{MethodName}Request` (e.g., GetUserRequest, CreatePostRequest)
// - Include `RequestContext context = 1;` as the first field (reserved tag 1)
// - Include method-specific parameters as subsequent fields
//
// Example:
// message GetUserRequest {
// RequestContext context = 1; // Required: request metadata
// string user_id = 2; // Method-specific parameter
// }
//
// RESPONSE CONVENTIONS:
// ---------------------
// Every RPC response message MUST:
// - Be named `{MethodName}Response` (e.g., GetUserResponse, CreatePostResponse)
// - Include `AppError error = 1;` as the first field (reserved tag 1)
// - If error is set (non-null), the operation failed
// - If error is null/empty, the operation succeeded
// - Include the result value(s) as subsequent fields
//
// Example:
// message GetUserResponse {
// AppError error = 1; // Null on success, populated on failure
// User user = 2; // Result value (only valid if error is null)
// }
//
// For methods returning multiple values or complex results, use additional fields:
// message ListUsersResponse {
// AppError error = 1;
// repeated User users = 2;
// int32 total_count = 3;
// }
//
// For methods returning bool + error (like KVCompareAndSet):
// message KVCompareAndSetResponse {
// AppError error = 1;
// bool success = 2;
// }
//
// ==============================================================================
// Empty is a placeholder message used for methods with no request/response data.
message Empty {}
// StringMap represents a map of string to string values.
// Used for User.Props, User.NotifyProps, User.Timezone, etc.
message StringMap {
map<string, string> values = 1;
}
// RequestContext contains metadata for every RPC request.
// This MUST be embedded as the first field (tag 1) in every request message.
// Provides correlation IDs for logging, tracing, and debugging across
// the Go server and Python plugin boundary.
message RequestContext {
// plugin_id is the logical plugin identifier (from manifest.id).
// Used for routing, logging, and permission checks.
string plugin_id = 1;
// request_id is a unique identifier for this request.
// Used to correlate logs across Go server and Python plugin.
// Should be generated by the caller and propagated through the call chain.
string request_id = 2;
// session_id is the optional session identifier for the user making the request.
// May be empty for plugin-initiated requests not tied to a user session.
string session_id = 3;
// user_id is the optional user identifier for auditing purposes.
// May be empty for system-level operations.
string user_id = 4;
}
// AppError represents an error returned by the Mattermost server.
// Maps to model.AppError in Go.
//
// This is embedded in every response message as field 1 to indicate
// operation failure. A null/empty AppError indicates success.
message AppError {
// A unique error identifier (e.g., "api.user.create.email_taken.app_error")
// Used for error categorization and i18n lookup.
string id = 1;
// Human-readable error message (may be translated)
// This is the user-facing message.
string message = 2;
// Internal error details for debugging
// Contains technical details not shown to end users.
string detailed_error = 3;
// The request ID for tracing
// Matches RequestContext.request_id for correlation.
string request_id = 4;
// HTTP status code (maps to standard HTTP codes)
// Examples: 400 (Bad Request), 404 (Not Found), 500 (Internal Server Error)
int32 status_code = 5;
// The function/method where the error originated (e.g., "UserStore.Get")
// Useful for debugging and error reporting.
string where = 6;
// Optional parameters for error message interpolation.
// Used when the error message is a template requiring variable substitution.
// Example: {"field": "email", "value": "invalid@"} for validation errors.
// Uses google.protobuf.Struct for flexible map[string]any representation.
google.protobuf.Struct params = 7;
}
// ViewUsersRestrictions restricts which users can be viewed.
// Maps to model.ViewUsersRestrictions in Go.
message ViewUsersRestrictions {
repeated string teams = 1;
repeated string channels = 2;
}