2016-06-10 19:27:57 +02:00
|
|
|
package remote
|
|
|
|
|
|
|
|
import (
|
|
|
|
"fmt"
|
|
|
|
"os"
|
|
|
|
"strings"
|
|
|
|
"testing"
|
|
|
|
|
|
|
|
mainStorage "github.com/Azure/azure-sdk-for-go/storage"
|
2016-11-18 16:26:25 +01:00
|
|
|
"github.com/hashicorp/terraform/helper/acctest"
|
2016-06-10 19:27:57 +02:00
|
|
|
riviera "github.com/jen20/riviera/azure"
|
|
|
|
"github.com/jen20/riviera/storage"
|
2016-11-18 16:26:25 +01:00
|
|
|
"github.com/satori/uuid"
|
2016-06-10 19:27:57 +02:00
|
|
|
)
|
|
|
|
|
2016-06-10 20:04:40 +02:00
|
|
|
func TestAzureClient_impl(t *testing.T) {
|
|
|
|
var _ Client = new(AzureClient)
|
2016-06-10 19:27:57 +02:00
|
|
|
}
|
|
|
|
|
2016-11-18 16:26:25 +01:00
|
|
|
// This test creates a bucket in Azure and populates it.
|
|
|
|
// It may incur costs, so it will only run if Azure credential environment
|
|
|
|
// variables are present.
|
2016-06-10 20:04:40 +02:00
|
|
|
func TestAzureClient(t *testing.T) {
|
2016-11-18 16:26:25 +01:00
|
|
|
config := getAzureConfig(t)
|
2016-06-10 19:27:57 +02:00
|
|
|
|
2016-11-18 16:26:25 +01:00
|
|
|
setup(t, config)
|
|
|
|
defer teardown(t, config)
|
|
|
|
|
|
|
|
client, err := azureFactory(config)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error for valid config: %v", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
testClient(t, client)
|
|
|
|
}
|
|
|
|
|
|
|
|
// This test is the same as TestAzureClient with the addition of passing an
|
|
|
|
// empty string in the lease_id, we expect the client to pass tests
|
|
|
|
func TestAzureClientEmptyLease(t *testing.T) {
|
|
|
|
config := getAzureConfig(t)
|
|
|
|
config["lease_id"] = ""
|
|
|
|
|
|
|
|
setup(t, config)
|
|
|
|
defer teardown(t, config)
|
|
|
|
|
|
|
|
client, err := azureFactory(config)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error for valid config: %v", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
testClient(t, client)
|
|
|
|
}
|
|
|
|
|
|
|
|
// This test is the same as TestAzureClient with the addition of using the
|
|
|
|
// lease_id config option
|
|
|
|
func TestAzureClientLease(t *testing.T) {
|
|
|
|
leaseID := uuid.NewV4().String()
|
|
|
|
config := getAzureConfig(t)
|
|
|
|
config["lease_id"] = leaseID
|
|
|
|
|
|
|
|
setup(t, config)
|
|
|
|
defer teardown(t, config)
|
|
|
|
|
|
|
|
client, err := azureFactory(config)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error for valid config: %v", err)
|
|
|
|
}
|
|
|
|
azureClient := client.(*AzureClient)
|
|
|
|
|
|
|
|
// put empty blob so we can acquire lease against it
|
|
|
|
err = azureClient.blobClient.CreateBlockBlob(azureClient.containerName, azureClient.keyName)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error creating blob for leasing: %v", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
_, err = azureClient.blobClient.AcquireLease(azureClient.containerName, azureClient.keyName, -1, leaseID)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error acquiring lease: %v", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
// no need to release lease as blob is deleted in testing
|
|
|
|
testClient(t, client)
|
|
|
|
}
|
|
|
|
|
|
|
|
func getAzureConfig(t *testing.T) map[string]string {
|
2016-06-10 19:27:57 +02:00
|
|
|
config := map[string]string{
|
|
|
|
"arm_subscription_id": os.Getenv("ARM_SUBSCRIPTION_ID"),
|
|
|
|
"arm_client_id": os.Getenv("ARM_CLIENT_ID"),
|
|
|
|
"arm_client_secret": os.Getenv("ARM_CLIENT_SECRET"),
|
|
|
|
"arm_tenant_id": os.Getenv("ARM_TENANT_ID"),
|
|
|
|
}
|
|
|
|
|
|
|
|
for k, v := range config {
|
|
|
|
if v == "" {
|
|
|
|
t.Skipf("skipping; %s must be set", strings.ToUpper(k))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2016-11-18 16:26:25 +01:00
|
|
|
rs := acctest.RandString(8)
|
|
|
|
|
|
|
|
config["resource_group_name"] = fmt.Sprintf("terraform-%s", rs)
|
|
|
|
config["storage_account_name"] = fmt.Sprintf("terraform%s", rs)
|
2016-06-10 19:27:57 +02:00
|
|
|
config["container_name"] = "terraform"
|
|
|
|
config["key"] = "test.tfstate"
|
|
|
|
|
2016-11-18 16:26:25 +01:00
|
|
|
return config
|
2016-06-10 19:27:57 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
func setup(t *testing.T, conf map[string]string) {
|
|
|
|
creds, err := getCredentialsFromConf(conf)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error getting credentials from conf: %v", err)
|
|
|
|
}
|
|
|
|
rivieraClient, err := getRivieraClient(creds)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error instantiating the riviera client: %v", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
// Create resource group
|
|
|
|
r := rivieraClient.NewRequest()
|
|
|
|
r.Command = riviera.CreateResourceGroup{
|
|
|
|
Name: conf["resource_group_name"],
|
|
|
|
Location: riviera.WestUS,
|
|
|
|
}
|
|
|
|
response, err := r.Execute()
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error creating a resource group: %v", err)
|
|
|
|
}
|
|
|
|
if !response.IsSuccessful() {
|
|
|
|
t.Fatalf("Error creating a resource group: %v", response.Error.Error())
|
|
|
|
}
|
|
|
|
|
|
|
|
// Create storage account
|
|
|
|
r = rivieraClient.NewRequest()
|
|
|
|
r.Command = storage.CreateStorageAccount{
|
|
|
|
ResourceGroupName: conf["resource_group_name"],
|
|
|
|
Name: conf["storage_account_name"],
|
|
|
|
AccountType: riviera.String("Standard_LRS"),
|
|
|
|
Location: riviera.WestUS,
|
|
|
|
}
|
|
|
|
response, err = r.Execute()
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error creating a storage account: %v", err)
|
|
|
|
}
|
|
|
|
if !response.IsSuccessful() {
|
|
|
|
t.Fatalf("Error creating a storage account: %v", response.Error.Error())
|
|
|
|
}
|
|
|
|
|
|
|
|
// Create container
|
|
|
|
accessKey, err := getStorageAccountAccessKey(conf, conf["resource_group_name"], conf["storage_account_name"])
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error creating a storage account: %v", err)
|
|
|
|
}
|
|
|
|
storageClient, err := mainStorage.NewBasicClient(conf["storage_account_name"], accessKey)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error creating storage client for storage account %q: %s", conf["storage_account_name"], err)
|
|
|
|
}
|
|
|
|
blobClient := storageClient.GetBlobService()
|
|
|
|
_, err = blobClient.CreateContainerIfNotExists(conf["container_name"], mainStorage.ContainerAccessTypePrivate)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Couldn't create container with name %s: %s.", conf["container_name"], err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func teardown(t *testing.T, conf map[string]string) {
|
|
|
|
creds, err := getCredentialsFromConf(conf)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error getting credentials from conf: %v", err)
|
|
|
|
}
|
|
|
|
rivieraClient, err := getRivieraClient(creds)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error instantiating the riviera client: %v", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
r := rivieraClient.NewRequest()
|
|
|
|
r.Command = riviera.DeleteResourceGroup{
|
|
|
|
Name: conf["resource_group_name"],
|
|
|
|
}
|
|
|
|
response, err := r.Execute()
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Error deleting the resource group: %v", err)
|
|
|
|
}
|
|
|
|
if !response.IsSuccessful() {
|
|
|
|
t.Fatalf("Error deleting the resource group: %v", err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func getRivieraClient(credentials *riviera.AzureResourceManagerCredentials) (*riviera.Client, error) {
|
|
|
|
rivieraClient, err := riviera.NewClient(credentials)
|
|
|
|
if err != nil {
|
|
|
|
return nil, fmt.Errorf("Error creating Riviera client: %s", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
request := rivieraClient.NewRequest()
|
|
|
|
request.Command = riviera.RegisterResourceProvider{
|
|
|
|
Namespace: "Microsoft.Storage",
|
|
|
|
}
|
|
|
|
|
|
|
|
response, err := request.Execute()
|
|
|
|
if err != nil {
|
|
|
|
return nil, fmt.Errorf("Cannot request provider registration for Azure Resource Manager: %s.", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
if !response.IsSuccessful() {
|
|
|
|
return nil, fmt.Errorf("Credentials for acessing the Azure Resource Manager API are likely " +
|
|
|
|
"to be incorrect, or\n the service principal does not have permission to use " +
|
|
|
|
"the Azure Service Management\n API.")
|
|
|
|
}
|
|
|
|
|
|
|
|
return rivieraClient, nil
|
|
|
|
}
|