/*
Copyright 2017 Google 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

https://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.
*/
package main

import (
	"flag"
	"fmt"
	"log"
	"os"
	"path/filepath"
	"time"

	"github.com/maps-booking-v3/api"
	"github.com/maps-booking-v3/utils"

	fpb "github.com/maps-booking-v3/feeds"
	mpb "github.com/maps-booking-v3/v3"
)

const logFile = "http_test_client_log_"

var (
	serverAddr        = flag.String("server_addr", "example.com:80", "Your http server's address in the format of host:port")
	credentialsFile   = flag.String("credentials_file", "", "File containing credentials for your server. Leave blank to bypass authentication.")
	testSlots         = flag.Int("num_test_slots", 10, "Maximum number of slots to test from availability_feed. Slots will be selected randomly")
	allFlows          = flag.Bool("all_tests", false, "Whether to test all endpoints.")
	healthFlow        = flag.Bool("health_check_test", false, "Whether to test the Health endpoint.")
	checkFlow         = flag.Bool("check_availability_test", false, "Whether to test the CheckAvailability endpoint.")
	bookFlow          = flag.Bool("booking_test", false, "Whether to test the CreateBooking endpoint.")
	listFlow          = flag.Bool("list_bookings_test", false, "Whether to test the ListBookings endpoint")
	statusFlow        = flag.Bool("booking_status_test", false, "Whether to test the GetBookingStatus endpoint.")
	rescheduleFlow    = flag.Bool("rescheduling_test", false, "Whether to test the UpdateBooking endpoint.")
	cancelAllBookings = flag.Bool("cancel_all_bookings", false, "This option assumes that the ListBookings and UpdateBooking endpoints are fully functional. This is a convenience flag for purging your system of all previously created bookings.")
	availabilityFeed  = flag.String("availability_feed", "", "Absolute path to availability feed required for all tests except health. Feeds can be in either json or pb3 format")
	outputDir         = flag.String("output_dir", "", "Absolute path of dir to dump log file.")
)

type counters struct {
	TotalSlotsProcessed      int
	HealthCheckSuccess       bool
	CheckAvailabilitySuccess int
	CheckAvailabilityErrors  int
	CreateBookingSuccess     int
	CreateBookingErrors      int
	ListBookingsSuccess      bool
	GetBookingStatusSuccess  int
	GetBookingStatusErrors   int
	CancelBookingsSuccess    int
	CancelBookingsErrors     int
	ReschedulingSuccess      bool
}

// GenerateBookings creates bookings from an availability feed.
func GenerateBookings(av []*fpb.Availability, stats *counters, conn *api.HTTPConnection) api.Bookings {
	log.Println("no previous bookings to use, acquiring new inventory")
	utils.LogFlow("Generate Fresh Inventory", "Start")
	defer utils.LogFlow("Generate Fresh Inventory", "End")

	var out api.Bookings
	totalSlots := len(av)
	for i, a := range av {
		if err := api.CheckAvailability(a, conn); err != nil {
			log.Printf("%s. skipping slot %d/%d", err.Error(), i, totalSlots)
			stats.CheckAvailabilityErrors++
			continue
		}
		stats.CheckAvailabilitySuccess++

		booking, err := api.CreateBooking(a, conn)
		if err != nil {
			log.Printf("%s. skipping slot %d/%d", err.Error(), i, totalSlots)
			stats.CreateBookingErrors++
			continue
		}
		out = append(out, booking)
		stats.CreateBookingSuccess++
	}
	return out
}

func createLogFile() (*os.File, error) {
	var err error
	outPath := *outputDir
	if outPath == "" {
		outPath, err = os.Getwd()
		if err != nil {
			return nil, err
		}
	}

	now := time.Now().UTC()
	nowString := fmt.Sprintf("%d-%02d-%02d_%02d-%02d-%02d", now.Year(), now.Month(), now.Day(), now.Hour(), now.Minute(), now.Second())
	outFile := filepath.Join(outPath, fmt.Sprintf("%s%s", logFile, nowString))

	return os.Create(outFile)
}

func logStats(stats counters) {
	log.Println("\n************* Begin Stats *************\n")
	var totalErrors int
	if *healthFlow || *allFlows {
		if stats.HealthCheckSuccess {
			log.Println("HealthCheck Succeeded")
		} else {
			totalErrors++
			log.Println("HealthCheck Failed")
		}
	}
	if *checkFlow || *allFlows {
		totalErrors += stats.CheckAvailabilityErrors
		log.Printf("CheckAvailability Errors: %d/%d", stats.CheckAvailabilityErrors, stats.CheckAvailabilityErrors+stats.CheckAvailabilitySuccess)
	}
	if *bookFlow || *allFlows {
		totalErrors += stats.CreateBookingErrors
		log.Printf("CreateBooking Errors: %d/%d", stats.CreateBookingErrors, stats.CreateBookingErrors+stats.CreateBookingSuccess)
	}
	if *listFlow || *allFlows {
		if stats.ListBookingsSuccess {
			log.Println("ListBookings Succeeded")
		} else {
			totalErrors++
			log.Println("ListBookings Failed")
		}
	}
	if *statusFlow || *allFlows {
		totalErrors += stats.GetBookingStatusErrors
		log.Printf("GetBookingStatus Errors: %d/%d", stats.GetBookingStatusErrors, stats.GetBookingStatusErrors+stats.GetBookingStatusSuccess)
	}
	if *rescheduleFlow || *allFlows {
		if stats.ReschedulingSuccess {
			log.Println("Rescheduling Succeeded")
		} else {
			totalErrors++
			log.Println("Rescheduling Failed")
		}
	}

	log.Println("\n\n\n")
	if totalErrors == 0 {
		log.Println("All Tests Pass!")
	} else {
		log.Printf("Found %d Errors", totalErrors)
	}

	log.Println("\n************* End Stats *************\n")
	os.Exit(0)
}

func main() {
	flag.Parse()
	var stats counters

	// Set up logging before continuing with flows
	f, err := createLogFile()
	if err != nil {
		log.Fatalf("Failed to create log file %v", err)
	}
	defer f.Close()
	log.SetOutput(f)

	conn, err := api.InitHTTPConnection(*serverAddr, *credentialsFile)
	if err != nil {
		log.Fatalf("Failed to init http connection %v", err)
	}

	// Health check doesn't affect the cancel booking flow so we let it through.
	if *cancelAllBookings && (*allFlows || *checkFlow || *bookFlow || *listFlow || *statusFlow || *rescheduleFlow) {
		log.Fatal("cancel_all_bookings is not supported with other test flows")
	}

	// HealthCheck Flow
	if *healthFlow || *allFlows {
		stats.HealthCheckSuccess = true
		if err := api.HealthCheck(conn); err != nil {
			stats.HealthCheckSuccess = false
			log.Println(err.Error())
		}
		if !*allFlows && !*checkFlow && !*bookFlow &&
			!*listFlow && !*statusFlow && !*rescheduleFlow {
			logStats(stats)
		}
	}

	var av []*fpb.Availability
	if !*cancelAllBookings {
		// Build availablility records.
		if *availabilityFeed == "" {
			log.Fatal("please set availability_feed flag if you wish to test additional flows")
		}
		av, err = utils.AvailabilityFrom(*availabilityFeed, *testSlots)
		if err != nil {
			log.Fatal(err.Error())
		}
		stats.TotalSlotsProcessed += len(av)
	}

	// AvailabilityCheck Flow
	if *checkFlow || *allFlows {
		utils.LogFlow("Availability Check", "Start")
		totalSlots := len(av)

		j := 0
		for i, a := range av {
			if err = api.CheckAvailability(a, conn); err != nil {
				log.Printf("%s. skipping slot %d/%d", err.Error(), i, totalSlots)
				stats.CheckAvailabilityErrors++
				continue
			}
			stats.CheckAvailabilitySuccess++
			av[j] = a
			j++
		}
		av = av[:j]
		utils.LogFlow("Availability Check", "End")
	}
	// CreateBooking Flow.
	var b []*mpb.Booking
	if *bookFlow || *allFlows {
		utils.LogFlow("Booking", "Start")
		totalSlots := len(av)
		for i, a := range av {
			booking, err := api.CreateBooking(a, conn)
			if err != nil {
				log.Printf("%s. skipping slot %d/%d", err.Error(), i, totalSlots)
				stats.CreateBookingErrors++
				continue
			}
			b = append(b, booking)
			stats.CreateBookingSuccess++
		}
		utils.LogFlow("Booking", "End")
	}
	// ListBookings Flow
	if *listFlow || *allFlows || *cancelAllBookings {
		if len(b) == 0 && !*cancelAllBookings {
			b = GenerateBookings(av, &stats, conn)
		}
		utils.LogFlow("List Bookings", "Start")
		b, err = api.ListBookings(b, conn)
		stats.ListBookingsSuccess = true
		if err != nil {
			stats.ListBookingsSuccess = false
			log.Println(err.Error())
		}
		utils.LogFlow("List Bookings", "End")
	}

	// GetBookingStatus Flow
	if *statusFlow || *allFlows {
		if len(b) == 0 {
			b = GenerateBookings(av, &stats, conn)
		}

		utils.LogFlow("BookingStatus", "Start")
		totalBookings := len(b)

		j := 0
		for i, booking := range b {
			if err = api.GetBookingStatus(booking, conn); err != nil {
				log.Printf("%s. abandoning booking %d/%d", err.Error(), i, totalBookings)
				stats.GetBookingStatusErrors++
				continue
			}
			stats.GetBookingStatusSuccess++
			b[j] = booking
			j++
		}
		b = b[:j]
		utils.LogFlow("BookingStatus", "End")
	}
	// CancelBooking Flow
	if len(b) > 0 {
		utils.LogFlow("Cancel Booking", "Start")
		for i, booking := range b {
			if err = api.CancelBooking(booking, conn); err != nil {
				log.Printf("%s. abandoning booking %d/%d", err.Error(), i, len(b))
				stats.CancelBookingsErrors++
				continue
			}
			stats.CancelBookingsSuccess++
		}
		utils.LogFlow("Cancel Booking", "End")
	}

	// Rescheduling is nuanced and can be isolated
	// from the rest of the tests.
	if *rescheduleFlow || *allFlows {
		utils.LogFlow("Rescheduling", "Start")
		stats.ReschedulingSuccess = true
		if err = api.Rescheduling(av, conn); err != nil {
			log.Println(err.Error())
			stats.ReschedulingSuccess = false
		}
		utils.LogFlow("Rescheduling", "End")
	}

	logStats(stats)
}
