// Copyright 2020 The Monogon Project Authors.
//
// SPDX-License-Identifier: Apache-2.0
//
// 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 metropolis.proto.api;
option go_package = "source.monogon.dev/metropolis/proto/api";

import "google/protobuf/timestamp.proto";

// NodeDebugService exposes debug and testing endpoints that allow introspection into a running Metropolis node.
// It is not authenticated and will be disabled in production. It is currently consumed by metropolis/cli/dbg and
// by tests.
service NodeDebugService {
    // GetDebugKubeconfig issues kubeconfigs with arbitrary identities and groups for debugging
    rpc GetDebugKubeconfig(GetDebugKubeconfigRequest) returns (GetDebugKubeconfigResponse);

    // GetLogs Returns historical and/or streaming logs for a given DN with given filters from the system global
    // LogTree.
    //
    // For more information about this API, see //metropolis/pkg/logtree. But, in summary:
    //   - All logging is performed to a DN (distinguished name), which is a dot-delimited string like foo.bar.baz.
    //   - Log entries can be either raw (coming from unstructured logging from an external service, like a running
    //     process) or leveled (emitted by Metropolis code with a source line, timestamp, and severity).
    //   - The DNs form a tree of logging nodes - and when requesting logs, a given subtree of DNs can be requested,
    //     instead of just a given DN.
    //   - All supervised processes live at `root.<supervisor DN>`. For more example paths, see the console logs of
    //     a running Metropolis node, or request all logs (at DN "").
    //
    // TODO(q3k): move method and its related messages to the non-debug node endpoint once we have one.
    rpc GetLogs(GetLogsRequest) returns (stream GetLogsResponse);

    // Trace enables tracing of Metropolis using the Linux ftrace infrastructure.
    rpc Trace(TraceRequest) returns (stream TraceEvent);

    // LoadImage loads an uncompressed tarball containing a Docker v1.1, v1.2 or OCI v1 image into the local
    // containerd image store. The client streams the tarball in arbitrary-sized chunks and closes the sending side
    // once it has sent the entire image. The server then either returns an empty response if successful or a gRPC error.
    rpc LoadImage(stream ImagePart) returns (LoadImageResponse);
}

message ImagePart {
    bytes data_part = 1;
}

message LoadImageResponse {
}

message GetDebugKubeconfigRequest {
    string id = 1; // Kubernetes identity (user)
    repeated string groups = 2; // Kubernetes groups
}

message GetDebugKubeconfigResponse {
    string debug_kubeconfig = 1;
}

// Severity level corresponding to //metropolis/pkg/logtree.Severity.
enum LeveledLogSeverity {
    INVALID = 0;
    INFO = 1;
    WARNING = 2;
    ERROR = 3;
    FATAL = 4;
}

// Filter set when requesting logs for a given DN. This message is equivalent to the following GADT enum:
// data LogFilter = WithChildren
//                | OnlyRaw
//                | OnlyLeveled
//                | LeveledWithMinimumSeverity(Severity)
//
// Multiple LogFilters can be chained/combined when requesting logs, as long as they do not conflict.
message LogFilter {
    // Entries will be returned not only for the given DN, but all child DNs as well. For instance, if the
    // requested DN is foo, entries logged to foo, foo.bar and foo.bar.baz will all be returned.
    message WithChildren {
    }
    // Only raw logging entries will be returned. Conflicts with OnlyLeveled filters.
    message OnlyRaw {
    }
    // Only leveled logging entries will be returned. Conflicts with OnlyRaw filters.
    message OnlyLeveled {
    }
    // If leveled logs are returned, all entries at severity lower than `minimum` will be discarded.
    message LeveledWithMinimumSeverity {
        LeveledLogSeverity minimum = 1;
    }
    oneof filter {
        WithChildren with_children = 1;
        OnlyRaw only_raw = 3;
        OnlyLeveled only_leveled = 4;
        LeveledWithMinimumSeverity leveled_with_minimum_severity = 5;
    }
}

message GetLogsRequest {
    // DN from which to request logs. All supervised runnables live at `root.`, the init code lives at `init.`.
    string dn = 1;
    // Filters to apply to returned data.
    repeated LogFilter filters = 2;

    enum BacklogMode {
        BACKLOG_INVALID = 0;
        // No historic data will be returned.
        BACKLOG_DISABLE = 1;
        // All available historic data will be returned.
        BACKLOG_ALL = 2;
        // At most backlog_count entries will be returned, if available.
        BACKLOG_COUNT = 3;
    }
    BacklogMode backlog_mode = 3;
    int64 backlog_count = 4;

    enum StreamMode {
        STREAM_INVALID = 0;
        // No streaming entries, gRPC stream will be closed as soon as all backlog data is served.
        STREAM_DISABLE = 1;
        // Entries will be streamed as early as available right after all backlog data is served.
        STREAM_UNBUFFERED = 2;
    }
    StreamMode stream_mode = 5;
}

message GetLogsResponse {
    // Entries from the requested historical entries (via WithBackLog). They will all be served before the first
    // stream_entries are served (if any).
    repeated LogEntry backlog_entries = 1;
    // Entries streamed as they arrive. Currently no server-side buffering is enabled, instead every line is served
    // as early as it arrives. However, this might change in the future, so this behaviour cannot be depended
    // upon.
    repeated LogEntry stream_entries = 2;
}

message LogEntry {
    message Leveled {
        repeated string lines = 1;
        google.protobuf.Timestamp timestamp = 2;
        LeveledLogSeverity severity = 3;
        string location = 4;
    }
    message Raw {
        string data = 1;
        int64 original_length = 2;
    }

    string dn = 1;
    oneof kind {
        Leveled leveled = 2;
        Raw raw = 3;
    }
}

message TraceRequest {
    // Name of the tracer to use. Defined in https://www.kernel.org/doc/html/latest/trace/ftrace.html#the-tracers.
    // Useful ones enabled in Metropolis: function_graph, function.
    // Gets reset to nop automatically after the stream is terminated.
    string tracer = 1;

    // List of functions to trace. Accepts wildcards using the '*' character. If left empty traces all functions.
    repeated string function_filter = 2;

    // List of functions and their descendants to trace with the function_graph tracer.
    repeated string graph_function_filter = 3;
}

message TraceEvent {
    // Currently we do not parse the event data and just return what the kernel outputs, line-by-line.
    string raw_line = 1;
}
