// Copyright 2015 The Vanadium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package main

import (
	"fmt"
	"math"
	"strings"

	cloudmonitoring "google.golang.org/api/monitoring/v3"

	"v.io/jiri/tool"
	"v.io/x/devtools/internal/test"
)

type aggregator struct {
	data []float64
	min  float64
	max  float64
	sum  float64
}

func newAggregator() *aggregator {
	return &aggregator{
		data: []float64{},
		min:  math.MaxFloat64,
	}
}

func (a *aggregator) add(v float64) {
	a.data = append(a.data, v)
	a.min = math.Min(a.min, v)
	a.max = math.Max(a.max, v)
	a.sum += v
}

func (a *aggregator) avg() float64 {
	return a.sum / float64(len(a.data))
}

func (a *aggregator) count() float64 {
	return float64(len(a.data))
}

func (a *aggregator) String() string {
	return fmt.Sprintf("min: %f, max: %f, avg: %f", a.min, a.max, a.avg())
}

type statValue struct {
	name  string
	value interface{}
}

func (sv *statValue) getStringValue() string {
	return fmt.Sprint(sv.value)
}

func (sv *statValue) getFloat64Value() (float64, error) {
	switch i := sv.value.(type) {
	case float64:
		return i, nil
	case int64:
		return float64(i), nil
	default:
		return 0, fmt.Errorf("invalid value: %v", sv.value)
	}
}

// sendDataToGCM sends the given metric to Google Cloud Monitoring.
func sendDataToGCM(s *cloudmonitoring.Service, md *cloudmonitoring.MetricDescriptor, value float64, now, instance, zone string, extraLabelKeys ...string) error {
	// Sending value 0 will cause error.
	if math.Abs(value) < 1e-7 {
		return nil
	}

	labels := []string{}
	if instance != "" {
		labels = append(labels, instance)
	}
	if zone != "" {
		labels = append(labels, zone)
	}
	for _, key := range extraLabelKeys {
		labels = append(labels, key)
	}
	if len(labels) != len(md.Labels) {
		return fmt.Errorf("wrong number of label keys: want %d, got %d", len(md.Labels), len(labels))
	}
	labelsMap := map[string]string{}
	for i := range labels {
		labelsMap[md.Labels[i].Key] = labels[i]
	}
	if _, err := s.Projects.TimeSeries.Create(fmt.Sprintf("projects/%s", projectFlag), &cloudmonitoring.CreateTimeSeriesRequest{
		TimeSeries: []*cloudmonitoring.TimeSeries{
			&cloudmonitoring.TimeSeries{
				Metric: &cloudmonitoring.Metric{
					Type:   md.Type,
					Labels: labelsMap,
				},
				Points: []*cloudmonitoring.Point{
					&cloudmonitoring.Point{
						Value: &cloudmonitoring.TypedValue{
							DoubleValue: value,
						},
						Interval: &cloudmonitoring.TimeInterval{
							StartTime: now,
							EndTime:   now,
						},
					},
				},
			},
		}}).Do(); err != nil {
		return fmt.Errorf("Timeseries Write failed for metric %q with value %f: %v", md.Name, value, err)
	}
	return nil
}

func sendAggregatedDataToGCM(ctx *tool.Context, s *cloudmonitoring.Service, md *cloudmonitoring.MetricDescriptor, agg *aggregator, now string, extraLabelKeys ...string) error {
	labels := []string{}
	for _, l := range extraLabelKeys {
		labels = append(labels, l)
	}
	minLabels := append(labels, "min")
	if err := sendDataToGCM(s, md, agg.min, now, "", "", minLabels...); err != nil {
		return err
	}
	maxLabels := append(labels, "max")
	if err := sendDataToGCM(s, md, agg.max, now, "", "", maxLabels...); err != nil {
		return err
	}
	avgLabels := append(labels, "avg")
	if err := sendDataToGCM(s, md, agg.avg(), now, "", "", avgLabels...); err != nil {
		return err
	}
	sumLabels := append(labels, "sum")
	if err := sendDataToGCM(s, md, agg.sum, now, "", "", sumLabels...); err != nil {
		return err
	}
	countLabels := append(labels, "count")
	if err := sendDataToGCM(s, md, agg.count(), now, "", "", countLabels...); err != nil {
		return err
	}
	test.Pass(ctx, "%s: %s\n", strings.Join(extraLabelKeys, " "), agg)
	return nil
}
