package main

import (
	"crypto/rand"
	"fmt"
	"github.com/rackspace/gophercloud"
	"os"
	"time"
)

// getCredentials will verify existence of needed credential information
// provided through environment variables.  This function will not return
// if at least one piece of required information is missing.
func getCredentials() (provider, username, password, apiKey string) {
	provider = os.Getenv("SDK_PROVIDER")
	username = os.Getenv("SDK_USERNAME")
	password = os.Getenv("SDK_PASSWORD")
	apiKey = os.Getenv("SDK_API_KEY")

	if (provider == "") || (username == "") || (password == "") {
		fmt.Fprintf(os.Stderr, "One or more of the following environment variables aren't set:\n")
		fmt.Fprintf(os.Stderr, "  SDK_PROVIDER=\"%s\"\n", provider)
		fmt.Fprintf(os.Stderr, "  SDK_USERNAME=\"%s\"\n", username)
		fmt.Fprintf(os.Stderr, "  SDK_PASSWORD=\"%s\"\n", password)
		os.Exit(1)
	}

	return
}

// randomString generates a string of given length, but random content.
// All content will be within the ASCII graphic character set.
// (Implementation from Even Shaw's contribution on
// http://stackoverflow.com/questions/12771930/what-is-the-fastest-way-to-generate-a-long-random-string-in-go).
func randomString(prefix string, n int) string {
	const alphanum = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
	var bytes = make([]byte, n)
	rand.Read(bytes)
	for i, b := range bytes {
		bytes[i] = alphanum[b%byte(len(alphanum))]
	}
	return prefix + string(bytes)
}

// aSuitableImage finds a minimal image for use in dynamically creating servers.
// If none can be found, this function will panic.
func aSuitableImage(api gophercloud.CloudServersProvider) string {
	images, err := api.ListImages()
	if err != nil {
		panic(err)
	}

	// TODO(sfalvo):
	// Works for Rackspace, might not work for your provider!
	// Need to figure out why ListImages() provides 0 values for
	// Ram and Disk fields.
	//
	// Until then, just return Ubuntu 12.04 LTS.
	for i := 0; i < len(images); i++ {
		if images[i].Id == "23b564c9-c3e6-49f9-bc68-86c7a9ab5018" {
			return images[i].Id
		}
	}
	panic("Image 23b564c9-c3e6-49f9-bc68-86c7a9ab5018 (Ubuntu 12.04 LTS) not found.")
}

// aSuitableFlavor finds the minimum flavor capable of running the test image
// chosen by aSuitableImage.  If none can be found, this function will panic.
func aSuitableFlavor(api gophercloud.CloudServersProvider) string {
	flavors, err := api.ListFlavors()
	if err != nil {
		panic(err)
	}

	// TODO(sfalvo):
	// Works for Rackspace, might not work for your provider!
	// Need to figure out why ListFlavors() provides 0 values for
	// Ram and Disk fields.
	//
	// Until then, just return Ubuntu 12.04 LTS.
	for i := 0; i < len(flavors); i++ {
		if flavors[i].Id == "2" {
			return flavors[i].Id
		}
	}
	panic("Flavor 2 (512MB 1-core 20GB machine) not found.")
}

// createServer creates a new server in a manner compatible with acceptance testing.
// In particular, it ensures that the name of the server always starts with "ACPTTEST--",
// which the delete servers acceptance test relies on to identify servers to delete.
// Passing in empty image and flavor references will force the use of reasonable defaults.
// An empty name string will result in a dynamically created name prefixed with "ACPTTEST--".
// A blank admin password will cause a password to be automatically generated; however,
// at present no means of recovering this password exists, as no acceptance tests yet require
// this data.
func createServer(servers gophercloud.CloudServersProvider, imageRef, flavorRef, name, adminPass string) (string, error) {
	if imageRef == "" {
		imageRef = aSuitableImage(servers)
	}

	if flavorRef == "" {
		flavorRef = aSuitableFlavor(servers)
	}

	if len(name) < 1 {
		name = randomString("ACPTTEST", 16)
	}

	if (len(name) < 8) || (name[0:8] != "ACPTTEST") {
		name = fmt.Sprintf("ACPTTEST--%s", name)
	}

	newServer, err := servers.CreateServer(gophercloud.NewServer{
		Name:      name,
		ImageRef:  imageRef,
		FlavorRef: flavorRef,
		AdminPass: adminPass,
	})

	if err != nil {
		return "", err
	}

	return newServer.Id, nil
}

// findAlternativeFlavor locates a flavor to resize a server to.  It is guaranteed to be different
// than what aSuitableFlavor() returns.  If none could be found, this function will panic.
func findAlternativeFlavor() string {
	return "3" // 1GB image, up from 512MB image
}

// findAlternativeImage locates an image to resize or rebuild a server with.  It is guaranteed to be
// different than what aSuitableImage() returns.  If none could be found, this function will panic.
func findAlternativeImage() string {
	return "c6f9c411-e708-4952-91e5-62ded5ea4d3e"
}

// withIdentity authenticates the user against the provider's identity service, and provides an
// accessor for additional services.
func withIdentity(ar bool, f func(gophercloud.AccessProvider)) {
	provider, username, password, _ := getCredentials()
	acc, err := gophercloud.Authenticate(
		provider,
		gophercloud.AuthOptions{
			Username:    username,
			Password:    password,
			AllowReauth: ar,
		},
	)
	if err != nil {
		panic(err)
	}

	f(acc)
}

// withServerApi acquires the cloud servers API.
func withServerApi(acc gophercloud.AccessProvider, f func(gophercloud.CloudServersProvider)) {
	api, err := gophercloud.ServersApi(acc, gophercloud.ApiCriteria{
		Name:      "cloudServersOpenStack",
		VersionId: "2",
		UrlChoice: gophercloud.PublicURL,
	})
	if err != nil {
		panic(err)
	}

	f(api)
}

// waitForServerState polls, every 10 seconds, for a given server to appear in the indicated state.
// This call will block forever if it never appears in the desired state, so if a timeout is required,
// make sure to call this function in a goroutine.
func waitForServerState(api gophercloud.CloudServersProvider, id, state string) error {
	for {
		s, err := api.ServerById(id)
		if err != nil {
			return err
		}
		if s.Status == state {
			return nil
		}
		time.Sleep(10 * time.Second)
	}
	panic("Impossible")
}

// waitForImageState polls, every 10 seconds, for a given image to appear in the indicated state.
// This call will block forever if it never appears in the desired state, so if a timeout is required,
// make sure to call this function in a goroutine.
func waitForImageState(api gophercloud.CloudServersProvider, id, state string) error {
	for {
		s, err := api.ImageById(id)
		if err != nil {
			return err
		}
		if s.Status == state {
			return nil
		}
		time.Sleep(10 * time.Second)
	}
	panic("Impossible")
}
