package main

import (
	"crypto/x509"
	"errors"
	"fmt"
	"io"

	"github.com/spf13/cobra"

	"source.monogon.dev/metropolis/cli/metroctl/core"
	"source.monogon.dev/metropolis/pkg/logtree"
	"source.monogon.dev/metropolis/proto/api"

	cpb "source.monogon.dev/metropolis/proto/common"
)

type metroctlLogFlags struct {
	// follow (ie. stream) logs live.
	follow bool
	// dn to query.
	dn string
	// exact dn query, i.e. without children/recursion.
	exact bool
	// concise logging output format.
	concise bool
	// backlog: >0 for a concrete limit, -1 for all, 0 for none
	backlog int
}

var logFlags metroctlLogFlags

var nodeLogsCmd = &cobra.Command{
	Short: "Get/stream logs from node",
	Long: `Get or stream logs from node.

Node logs are structured in a 'log tree' structure, in which different subsystems
log to DNs (distinguished names). For example, service 'foo' might log to
root.role.foo, while service 'bar' might log to root.role.bar.

To set the DN you want to request logs from, use --dn. The default is to return
all logs. The default output is also also a good starting point to figure out
what DNs are active in the system.

When requesting logs for a DN by default all sub-DNs will also be returned (ie.
with the above example, when requesting DN 'root.role' logs at root.role.foo and
root.role.bar would also be returned). This behaviour can be disabled by setting
--exact.

To stream logs, use --follow.

By default, all available logs are returned. To limit the number of historical
log lines (a.k.a. 'backlog') to return, set --backlog. This similar to requesting
all lines and then piping the result through 'tail' - but more efficient, as no
unnecessary lines are fetched.
`,
	Use:  "logs [node-id]",
	Args: cobra.MinimumNArgs(1),
	RunE: func(cmd *cobra.Command, args []string) error {
		ctx := cmd.Context()

		// First connect to the main management service and figure out the node's IP
		// address.
		cc := dialAuthenticated(ctx)
		mgmt := api.NewManagementClient(cc)
		nodes, err := core.GetNodes(ctx, mgmt, fmt.Sprintf("node.id == %q", args[0]))
		if err != nil {
			return fmt.Errorf("when getting node info: %w", err)
		}

		if len(nodes) == 0 {
			return fmt.Errorf("no such node")
		}
		if len(nodes) > 1 {
			return fmt.Errorf("expression matched more than one node")
		}
		n := nodes[0]
		if n.Status == nil || n.Status.ExternalAddress == "" {
			return fmt.Errorf("node has no external address")
		}

		// TODO(q3k): save CA certificate on takeover
		info, err := mgmt.GetClusterInfo(ctx, &api.GetClusterInfoRequest{})
		if err != nil {
			return fmt.Errorf("couldn't get cluster info: %w", err)
		}
		cacert, err := x509.ParseCertificate(info.CaCertificate)
		if err != nil {
			return fmt.Errorf("remote CA certificate invalid: %w", err)
		}

		fmt.Printf("=== Logs from %s (%s):\n", n.Id, n.Status.ExternalAddress)
		// Dial the actual node at its management port.
		cl := dialAuthenticatedNode(ctx, n.Id, n.Status.ExternalAddress, cacert)
		nmgmt := api.NewNodeManagementClient(cl)

		streamMode := api.GetLogsRequest_STREAM_DISABLE
		if logFlags.follow {
			streamMode = api.GetLogsRequest_STREAM_UNBUFFERED
		}
		var filters []*cpb.LogFilter
		if !logFlags.exact {
			filters = append(filters, &cpb.LogFilter{
				Filter: &cpb.LogFilter_WithChildren_{
					WithChildren: &cpb.LogFilter_WithChildren{},
				},
			})
		}
		backlogMode := api.GetLogsRequest_BACKLOG_ALL
		var backlogCount int64
		switch {
		case logFlags.backlog > 0:
			backlogMode = api.GetLogsRequest_BACKLOG_COUNT
			backlogCount = int64(logFlags.backlog)
		case logFlags.backlog == 0:
			backlogMode = api.GetLogsRequest_BACKLOG_DISABLE
		}

		srv, err := nmgmt.Logs(ctx, &api.GetLogsRequest{
			Dn:           logFlags.dn,
			BacklogMode:  backlogMode,
			BacklogCount: backlogCount,
			StreamMode:   streamMode,
			Filters:      filters,
		})
		if err != nil {
			return fmt.Errorf("failed to get logs: %w", err)
		}
		for {
			res, err := srv.Recv()
			if errors.Is(err, io.EOF) {
				fmt.Println("=== Done.")
				break
			}
			if err != nil {
				return fmt.Errorf("log stream failed: %w", err)
			}
			for _, entry := range res.BacklogEntries {
				printEntry(entry)
			}
			for _, entry := range res.StreamEntries {
				printEntry(entry)
			}
		}

		return nil
	},
}

func printEntry(e *cpb.LogEntry) {
	entry, err := logtree.LogEntryFromProto(e)
	if err != nil {
		fmt.Printf("invalid stream entry: %v\n", err)
		return
	}
	if logFlags.concise {
		fmt.Println(entry.ConciseString(logtree.MetropolisShortenDict, 0))
	} else {
		fmt.Println(entry.String())
	}
}

func init() {
	nodeLogsCmd.Flags().BoolVarP(&logFlags.follow, "follow", "f", false, "Continue streaming logs after fetching backlog.")
	nodeLogsCmd.Flags().StringVar(&logFlags.dn, "dn", "", "Distinguished Name to get logs from (and children, if --exact is not set). If not set, defaults to '', which is the top-level DN.")
	nodeLogsCmd.Flags().BoolVarP(&logFlags.exact, "exact", "e", false, "Only show logs for exactly the DN, do not recurse down the tree.")
	nodeLogsCmd.Flags().BoolVarP(&logFlags.concise, "concise", "c", false, "Output concise logs.")
	nodeLogsCmd.Flags().IntVar(&logFlags.backlog, "backlog", -1, "How many lines of historical log data to return. The default (-1) returns all available lines. Zero value means no backlog is returned (useful when using --follow).")
	nodeCmd.AddCommand(nodeLogsCmd)
}
