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

syntax = "proto3";

package buf.alpha.registry.v1alpha1;

// DocService defines a set of APIs that are intended for use by bufwebd only.
// This is not intended for general use; changes and use cases are subject to executive approval.
service DocService {
  // GetSourceDirectoryInfo retrieves the directory and file structure for the
  // given owner, repository and reference.
  //
  // The purpose of this is to get a representation of the file tree for a given
  // module to enable exploring the module by navigating through its contents.
  rpc GetSourceDirectoryInfo(GetSourceDirectoryInfoRequest) returns (GetSourceDirectoryInfoResponse) {
    option idempotency_level = NO_SIDE_EFFECTS;
  }
  // GetSourceFile retrieves the source contents for the given owner, repository,
  // reference, and path.
  rpc GetSourceFile(GetSourceFileRequest) returns (GetSourceFileResponse) {
    option idempotency_level = NO_SIDE_EFFECTS;
  }
  // GetModulePackages retrieves the list of packages for the module based on the given
  // owner, repository, and reference.
  rpc GetModulePackages(GetModulePackagesRequest) returns (GetModulePackagesResponse) {
    option idempotency_level = NO_SIDE_EFFECTS;
  }
  // GetModuleDocumentation retrieves the documentations including buf.md and LICENSE files
  // for module based on the given owner, repository, and reference.
  rpc GetModuleDocumentation(GetModuleDocumentationRequest) returns (GetModuleDocumentationResponse) {
    option idempotency_level = NO_SIDE_EFFECTS;
  }
  // GetPackageDocumentation retrieves a a slice of documentation structures
  // for the given owner, repository, reference, and package name.
  rpc GetPackageDocumentation(GetPackageDocumentationRequest) returns (GetPackageDocumentationResponse) {
    option idempotency_level = NO_SIDE_EFFECTS;
  }
}

// GetSourceDirectoryInfoRequest takes an owner, repository, and reference.
message GetSourceDirectoryInfoRequest {
  string owner = 1;
  string repository = 2;
  // Optional reference (if unspecified, will use the repository's default_branch).
  string reference = 3;
}

// GetSourceDirectoryInfoResponse returns the root FileInfo for the requested module.
message GetSourceDirectoryInfoResponse {
  FileInfo root = 1;
}

// FileInfo is a nested structure that contains the file path, whether or not it's a directory,
// and if so, the FileInfo children of that directory.
message FileInfo {
  // the normalized path of the directory, relative to the root of the module.
  string path = 1;
  bool is_dir = 2;
  repeated FileInfo children = 3;
}

// GetSourceFileRequest takes an owner, repository, reference, and normalized path.
message GetSourceFileRequest {
  string owner = 1;
  string repository = 2;
  // Optional reference (if unspecified, will use the repository's default_branch).
  string reference = 3;
  // the normalized path to the requested file, relative to the root of the module.
  string path = 4;
}

// GetSourceFileResponse returns the source code contents of the requested file.
message GetSourceFileResponse {
  // content is the content of the file.
  bytes content = 1;
}

// GetModulePackagesRequest takes an owner, repository, and reference.
message GetModulePackagesRequest {
  string owner = 1;
  string repository = 2;
  // Optional reference (if unspecified, will use the repository's default_branch).
  string reference = 3;
}

// GetModulePackagesResponse returns the list of ModulePackages for the requested module.
message GetModulePackagesResponse {
  string name = 1;
  repeated ModulePackage module_packages = 2;
}

// ModulePackage provides the details about a module's associated package.
message ModulePackage {
  string name = 1;
  string description = 2;
}

// GetModuleDocumentationRequest takes an owner, repository, and reference.
message GetModuleDocumentationRequest {
  string owner = 1;
  string repository = 2;
  // Optional reference (if unspecified, will use the repository's default_branch).
  string reference = 3;
}

// GetModuleDocumentationResponse returns the ModuleDocumentation for the requested module.
message GetModuleDocumentationResponse {
  ModuleDocumentation module_documentation = 1;
}

// ModuleDocumentation provides the name of the module and associated documentations.
message ModuleDocumentation {
  string name = 1;
  // This is the string representation of the contents of the buf.md file for module-level documentation.
  //
  // The buf.md file is a part of the module.
  // string is used to enforce UTF-8 encoding or 7-bit ASCII text.
  string documentation = 3;
  // This is the string representation of the contents of the LICENSE file for module-level license.
  //
  // The LICENSE file is a part of the module.
  // string is used to enforce UTF-8 encoding or 7-bit ASCII text.
  string license = 4;
  // documentation_path is the path of the file which contains the module documentation.
  //
  // either `buf.md`, `README.md` or `README.markdown`.
  // if empty, assumes buf.md.
  string documentation_path = 5;
}

// GetPackageDocumentationRequest takes an owner, repository, reference, and package name.
message GetPackageDocumentationRequest {
  string owner = 1;
  string repository = 2;
  // Optional reference (if unspecified, will use the repository's default_branch).
  string reference = 3;
  // this is the fully qualified package name.
  string package_name = 4;
}

// GetPackageDocumentationResponse returns the documentation for the requested package.
message GetPackageDocumentationResponse {
  PackageDocumentation package_documentation = 1;
}

// PackageDocumentation provides the name, description, and top level types defined in the package.
message PackageDocumentation {
  string name = 1;
  // comments contains the package-level comment documentation.
  // There is currently no convention for this.
  //
  // This is derived from the leading comments at the top level of the package.
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 2;
  // services contains all the services defined in the package in alphabetical order.
  repeated Service services = 3;
  // enums contains all the enums defined in the package in alphabetical order.
  repeated Enum enums = 4;
  // messages contains all the messages defined in the package in alphabetical order.
  repeated Message messages = 5;
  // extensions contains all the file level extensions in the package in alphabetical order.
  repeated FileExtension file_extensions = 6;
}

// Location provides the location information for the source code.
//
// This does not provide the leading or trailing comments as these will
// be parsed into descriptions or dropped respectively.
message Location {
  int32 start_line = 1;
  int32 start_column = 2;
  int32 end_line = 3;
  int32 end_column = 4;
}

// Service provides information for the documentation for a given service type in a file.
message Service {
  string name = 1;
  // nested_name includes the nested types for a given type definition.
  string nested_name = 2;
  // full_name includes the package name and nested types for a given type definition.
  string full_name = 3;
  // comments is derived from the leading comments of a given service.
  //
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 4;
  // file_path is the normalized path of the file containing the service.
  // This is used for navigating to the source code for the service.
  string file_path = 5;
  Location location = 6;
  repeated Method methods = 7;
  // implicitly_deprecated is true if its enclosing file is deprecated.
  bool implicitly_deprecated = 9;
  // All options that are present on the service. This is a super-set of
  // service_options and uses a dynamic representation so it can also
  // accommodate custom options with arbitrary types.
  // This supersedes service_options.
  repeated FieldLiteral options = 10;
  // Use options instead.
  ServiceOptions service_options = 8 [deprecated = true];
}

// ServiceOptions provides information for the documentation of options for a given service.
message ServiceOptions {
  option deprecated = true;
  bool deprecated = 1;
}

// Method provides information for the documentation for a method of a given service.
message Method {
  string name = 1;
  // comments is derived from the leading comments of a given method.
  //
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 2;
  MethodRequestResponse request = 3;
  MethodRequestResponse response = 4;
  // implicitly_deprecated is true if its enclosing file or parent element is deprecated.
  bool implicitly_deprecated = 6;
  // All options that are present on the method. This is a super-set of
  // method_options and uses a dynamic representation so it can also
  // accommodate custom options with arbitrary types.
  // This supersedes method_options.
  repeated FieldLiteral options = 7;
  // Use options instead.
  MethodOptions method_options = 5 [deprecated = true];
}

// MethodOptions provides information for the documentation of options for a method.
message MethodOptions {
  option deprecated = true;
  bool deprecated = 1;
  // idempotency_level holds a value of the enumeration `google.protobuf.MethodOptions.IdempotencyLevel.
  int32 idempotency_level = 2;
}

// MethodRequestResponse provides information for the documentation of a Method request or response message.
message MethodRequestResponse {
  // nested_type is the nested name of the message of the request or response. This includes nested definitions.
  string nested_type = 1;
  // full_type is the fully qualified name of the message of the request or response. This includes package and nested definitions.
  string full_type = 2;
  // boolean flag for whether the streaming label is set on an method request or response.
  bool streaming = 3;
  Message message = 4;
  // import_module_ref is included if the request or response is an imported type.
  // It contains all the metadata for the import.
  ImportModuleRef import_module_ref = 5;
}

// Enum provides information for the documentation of an enum.
message Enum {
  string name = 1;
  // nested_name includes the nested types for a given type definition.
  string nested_name = 2;
  // full_name includes the package name and nested types for a given type definition.
  string full_name = 3;
  // comments is derived from the leading comments of a given Enum.
  //
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 4;
  // file_path is the normalized path of the file containing the enum.
  string file_path = 5;
  Location location = 6;
  repeated EnumValue values = 7;
  // implicitly_deprecated is true if its enclosing file or parent element is deprecated.
  bool implicitly_deprecated = 9;
  // All options that are present on the enum. This is a super-set of
  // enum_options and uses a dynamic representation so it can also
  // accommodate custom options with arbitrary types.
  // // This supersedes enum_options.
  repeated FieldLiteral options = 10;
  // Use options instead.
  EnumOptions enum_options = 8 [deprecated = true];
}

// EnumOptions provides information for the documentation of options for an enum.
message EnumOptions {
  option deprecated = true;
  bool deprecated = 1;
  bool allow_alias = 2;
}

// EnumValue provides information for the documentation of an enum value.
message EnumValue {
  string name = 1;
  int32 number = 2;
  // comments is derived from the leading comments of a given enum value.
  //
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 3;
  // All options that are present on the enum. This is a super-set of
  // enum_value_options and uses a dynamic representation so it can also
  // accommodate custom options with arbitrary types.
  // // This supersedes enum_value_options.
  repeated FieldLiteral options = 5;
  // Use options instead.
  EnumValueOptions enum_value_options = 4 [deprecated = true];
}

// EnumValueOptions provides information for the documentation of options for an enum value.
message EnumValueOptions {
  option deprecated = true;
  bool deprecated = 1;
}

// ImportRef provides the import metadata if a type is imported.
message ImportModuleRef {
  string remote = 1;
  string owner = 2;
  string repository = 3;
  // the commit is based on the module commit of the imported type provided
  // by the image.
  string commit = 4;
  string package_name = 5;
}

// Message provides information for the documentation of a protobuf message.
message Message {
  string name = 1;
  // nested_name includes the nested types for a given type definition.
  string nested_name = 2;
  // full_name includes the package name and nested types for a given type definition.
  string full_name = 3;
  // comments is derived from the leading comments of a given message.
  //
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 4;
  // file_path is the normalized path of the file containing the message.
  string file_path = 5;
  bool is_map_entry = 6;
  repeated MessageField fields = 7;
  Location location = 8;
  repeated Field message_extensions = 9;
  // implicitly_deprecated is true if its enclosing file or parent element is deprecated.
  bool implicitly_deprecated = 11;
  // All options that are present on the message. This is a super-set of
  // message_options and uses a dynamic representation so it can also
  // accommodate custom options with arbitrary types.
  // // This supersedes message_options.
  repeated FieldLiteral options = 12;
  // Use options instead.
  MessageOptions message_options = 10 [deprecated = true];
}

// MessageField can be either a single field or a oneof set of fields.
message MessageField {
  oneof message_field {
    Field field = 1;
    Oneof oneof = 2;
  }
}

// MessageOptions provides information for the documentation of options for a message.
message MessageOptions {
  option deprecated = true;
  bool deprecated = 1;
}

// Oneof represents a oneof set of fields.
message Oneof {
  string name = 1;
  repeated Field fields = 2;
  // All options that are present on the OneOf.
  // This is a dynamic representation so it can also
  // accommodate custom options with arbitrary types.
  repeated FieldLiteral options = 3;
}

// Field provides information for the documentation of a message field.
message Field {
  string name = 1;
  // comments is derived from the leading comments of a given message field.
  //
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 2;
  string label = 3;
  // string representation of the nested name of the field type, which includes nested definitions.
  string nested_type = 4;
  // string representation of the full name of the field type, which includes package name
  // and nested definitions.
  string full_type = 5;
  uint32 tag = 6;
  // MapEntry is present if the field is a map type.
  MapEntry map_entry = 7;
  // import_module_ref is included if the field is an imported type.
  // It contains all the metadata for the import.
  ImportModuleRef import_module_ref = 8;
  // Extendee is the name of the type that is being ext if the field is an extension.
  // This is an empty string for fields that are not extensions.
  string extendee = 9;
  // All options that are present on the field. This is a super-set of
  // field_options and uses a dynamic representation so it can also
  // accommodate custom options with arbitrary types.
  // This supersedes field_options.
  repeated FieldLiteral options = 11;
  // Use options instead.
  FieldOptions field_options = 10 [deprecated = true];
}

// FieldOptions provides information for the documentation of options for a field.
message FieldOptions {
  option deprecated = true;
  bool deprecated = 1;
  optional bool packed = 2;
  // ctype holds a value of the enumeration `google.protobuf.FieldOptions.CType.
  int32 ctype = 3;
  // jstype holds a value of the enumeration `google.protobuf.FieldOptions.JSType.
  int32 jstype = 4;
}

// FieldType indicates whether a field is a normal, an extension or an any.
enum FieldType {
  FIELD_TYPE_UNSPECIFIED = 0;
  FIELD_TYPE_NORMAL = 1;
  FIELD_TYPE_EXTENSION = 2;
  FIELD_TYPE_ANY = 3;
}

// FieldLiteral represents a field and its value. It can be used to model descriptor options.
message FieldLiteral {
  // When is_extension is true, name is the fully-qualified name of the
  // extension. Otherwise, it is the simple name of the field.
  string name = 1;
  // The unique field number associated with the field.
  int32 tag = 2;
  // Indicates whether this is an extension or not.
  FieldType field_type = 3;
  // The field's value.
  LiteralValue value = 4;
  // This is the module where the extension is defined if the field type
  // is extension or the module where the messages is defined for field type any.
  ImportModuleRef import_module_ref = 5;
}

// MessageLiteral represents an option value for a type that is a message.
message MessageLiteral {
  // Map of field names to value. Extension field names will be in the form:
  // [fully.qualified.extension.Name].
  repeated FieldLiteral fields = 1;
}

// ArrayLiteral represents an option value for a type that is a repeated field.
// Maps are also represented using an ArrayLiteral, where each map entry is a MessageLiteral
// that contains a key and value field.
message ArrayLiteral {
  repeated LiteralValue elements = 1;
}

// LiteralValue represents the actual value of the extension.
message LiteralValue {
  oneof value {
    string string_value = 2;
    int64 int_value = 3;
    uint64 uint_value = 4;
    double double_value = 5;
    bool bool_value = 6;
    string enum_value_name_value = 7;
    ArrayLiteral array_value = 8;
    MessageLiteral message_value = 9;
  }
  string comments = 10;
}

// MapEntry provides the key and value types for the MapEntry type for a map field.
message MapEntry {
  // string representation of the full name of the type for the map key. keys can only be
  // scalar types: https://developers.google.com/protocol-buffers/docs/overview#maps
  string key_full_type = 1;
  // string representation of the nested name of the type for the map value.
  string value_nested_type = 2;
  // string representation of the full name of the type for the map value.
  string value_full_type = 3;
  // if the value is an imported type, this is the import module ref
  ImportModuleRef value_import_module_ref = 4;
}

// FileExtension provides the information for the documentation of a file extension.
message FileExtension {
  // extension_type is the string representation of the type being extended.
  string extension_type = 1;
  // comments is derived from the leading comments of a given message field.
  //
  // Paragraph newlines (double new lines) are respected, however single newlines are not.
  // Note that any leading and trailing `//` or spaces within a `/* */` block will be stripped.
  string comments = 2;
  // file_path is the normalized path of the file containing the message.
  string file_path = 3;
  Location location = 4;
  // fields are all the fields that are associated with the extension.
  repeated Field fields = 5;
  // implicitly_deprecated is true if its enclosing file or parent element is deprecated.
  bool implicitly_deprecated = 6;
}
