// Package route includes the test cases for testing different proxy routes.
package route

import (
	"encoding/base64"
	"fmt"

	. "github.com/onsi/ginkgo/v2"
	. "github.com/onsi/gomega"

	"github.com/tidbcloud/clusterproxy/test/context"
)

var _ = Describe("proxy routes test", func() {
	var (
		ctx *context.Context
		err error
	)
	It("should create context successfully", func() {
		ctx, err = context.New()
		Expect(err).To(Succeed())
		Expect(ctx).NotTo(BeNil())
	})

	Context("test cluster proxy", func() {
		const (
			promQueryRoute = "/proxy/cluster/%d/prometheus/api/v1/query"
			promMetricKey  = "tidb_server_connections"
			expectedStatus = `"status":"success"`
		)
		It("should get the Prometheus metric", func() {
			body, err := ctx.ProxyGet(
				fmt.Sprintf(promQueryRoute, ctx.ClusterId),
				map[string]string{
					"query": promMetricKey,
				}, nil, nil,
			)
			Expect(err).To(Succeed())
			Expect(string(body)).Should(ContainSubstring(expectedStatus))
		})

		const (
			promQueryRouteByNamespacedName = "/proxy/namespace/%s/cluster/%s/prometheus/api/v1/query"
			clusterNamespace               = "tidb42"
			clusterName                    = "db"
		)
		It("should get the Prometheus metric with the namespaced name path", func() {
			body, err := ctx.ProxyGet(
				fmt.Sprintf(promQueryRouteByNamespacedName, clusterNamespace, clusterName),
				map[string]string{
					"query": promMetricKey,
				}, nil, nil,
			)
			Expect(err).To(Succeed())
			Expect(string(body)).Should(ContainSubstring(expectedStatus))
		})

		const (
			promQueryRouteByNamespacedMonitorName = "/proxy/namespace/%s/tidbmonitor/%s/prometheus/api/v1/query"
			monitorName                           = "db"
		)
		It("should get the Prometheus metric with the namespaced monitor name path", func() {
			body, err := ctx.ProxyGet(
				fmt.Sprintf(promQueryRouteByNamespacedMonitorName, clusterNamespace, monitorName),
				map[string]string{
					"query": promMetricKey,
				}, nil, nil,
			)
			Expect(err).To(Succeed())
			Expect(string(body)).Should(ContainSubstring(expectedStatus))
		})

		It("should get the PD keyvisual config", func() {
			const (
				pdConfigRoute = "/proxy/cluster/%d/pd/dashboard/api/keyvisual/config"
				pdConfigKey   = "auto_collection_disabled"
			)
			params := map[string]string{
				"password": base64.URLEncoding.EncodeToString([]byte("password")),
			}
			body, err := ctx.ProxyGet(
				fmt.Sprintf(pdConfigRoute, ctx.ClusterId),
				params, nil, nil,
			)
			Expect(err).To(Succeed(), "key visual config")
			Expect(string(body)).Should(ContainSubstring(pdConfigKey))
		})
	})

	Context("test terminal proxy", func() {
		const (
			terminalRoute = "/proxy/cluster/%d/terminal/root"
			terminalTitle = "<title>/client-loop@shell-db-1-root"
		)
		It("should get the remote terminal", func() {
			body, err := ctx.ProxyGet(
				fmt.Sprintf(terminalRoute, ctx.ClusterId),
				nil,
				map[string]string{
					// Insert the user id of root to the header.
					"X-USER-ID": "1",
				},
				nil,
			)
			Expect(err).To(Succeed())
			Expect(string(body)).Should(ContainSubstring(terminalTitle))
		})
	})
})
