235 lines
7.3 KiB
Go
235 lines
7.3 KiB
Go
package azure
|
|
|
|
import (
|
|
"fmt"
|
|
"log"
|
|
"strconv"
|
|
"strings"
|
|
|
|
"github.com/Azure/azure-sdk-for-go/management/sql"
|
|
"github.com/hashicorp/terraform/helper/schema"
|
|
)
|
|
|
|
// resourceAzureSqlDatabaseService returns the *schema.Resource
|
|
// associated to an SQL Database Service on Azure.
|
|
func resourceAzureSqlDatabaseService() *schema.Resource {
|
|
return &schema.Resource{
|
|
Create: resourceAzureSqlDatabaseServiceCreate,
|
|
Read: resourceAzureSqlDatabaseServiceRead,
|
|
Update: resourceAzureSqlDatabaseServiceUpdate,
|
|
Exists: resourceAzureSqlDatabaseServiceExists,
|
|
Delete: resourceAzureSqlDatabaseServiceDelete,
|
|
|
|
Schema: map[string]*schema.Schema{
|
|
"name": &schema.Schema{
|
|
Type: schema.TypeString,
|
|
Required: true,
|
|
},
|
|
"database_server_name": &schema.Schema{
|
|
Type: schema.TypeString,
|
|
Required: true,
|
|
ForceNew: true,
|
|
},
|
|
"collation": &schema.Schema{
|
|
Type: schema.TypeString,
|
|
Optional: true,
|
|
Computed: true,
|
|
ForceNew: true,
|
|
},
|
|
"edition": &schema.Schema{
|
|
Type: schema.TypeString,
|
|
Optional: true,
|
|
Computed: true,
|
|
},
|
|
"max_size_bytes": &schema.Schema{
|
|
Type: schema.TypeString,
|
|
Optional: true,
|
|
Computed: true,
|
|
},
|
|
"service_level_id": &schema.Schema{
|
|
Type: schema.TypeString,
|
|
Optional: true,
|
|
Computed: true,
|
|
},
|
|
},
|
|
}
|
|
}
|
|
|
|
// resourceAzureSqlDatabaseServiceCreate does all the necessary API calls to
|
|
// create an SQL Database Service on Azure.
|
|
func resourceAzureSqlDatabaseServiceCreate(d *schema.ResourceData, meta interface{}) error {
|
|
sqlClient := meta.(*Client).sqlClient
|
|
|
|
log.Println("[INFO] Creating Azure SQL Database service creation request.")
|
|
name := d.Get("name").(string)
|
|
serverName := d.Get("database_server_name").(string)
|
|
params := sql.DatabaseCreateParams{
|
|
Name: name,
|
|
Edition: d.Get("edition").(string),
|
|
CollationName: d.Get("collation").(string),
|
|
ServiceObjectiveID: d.Get("service_level_id").(string),
|
|
}
|
|
|
|
if maxSize, ok := d.GetOk("max_size_bytes"); ok {
|
|
val, err := strconv.ParseInt(maxSize.(string), 10, 64)
|
|
if err != nil {
|
|
return fmt.Errorf("Provided max_size_bytes is not an integer: %s", err)
|
|
}
|
|
params.MaxSizeBytes = val
|
|
}
|
|
|
|
log.Println("[INFO] Sending SQL Database Service creation request to Azure.")
|
|
err := sqlClient.CreateDatabase(serverName, params)
|
|
if err != nil {
|
|
return fmt.Errorf("Error issuing Azure SQL Database Service creation: %s", err)
|
|
}
|
|
|
|
log.Println("[INFO] Beginning wait for Azure SQL Database Service creation.")
|
|
err = sqlClient.WaitForDatabaseCreation(serverName, name, nil)
|
|
if err != nil {
|
|
return fmt.Errorf("Error whilst waiting for Azure SQL Database Service creation: %s", err)
|
|
}
|
|
|
|
d.SetId(name)
|
|
|
|
return resourceAzureSqlDatabaseServiceRead(d, meta)
|
|
}
|
|
|
|
// resourceAzureSqlDatabaseServiceRead does all the necessary API calls to
|
|
// read the state of the SQL Database Service off Azure.
|
|
func resourceAzureSqlDatabaseServiceRead(d *schema.ResourceData, meta interface{}) error {
|
|
sqlClient := meta.(*Client).sqlClient
|
|
|
|
log.Println("[INFO] Issuing Azure SQL Database Services list operation.")
|
|
serverName := d.Get("database_server_name").(string)
|
|
dbs, err := sqlClient.ListDatabases(serverName)
|
|
if err != nil {
|
|
return fmt.Errorf("Error whilst listing Database Services off Azure: %s", err)
|
|
}
|
|
|
|
// search for our database:
|
|
var found bool
|
|
name := d.Get("name").(string)
|
|
for _, db := range dbs.ServiceResources {
|
|
if db.Name == name {
|
|
found = true
|
|
d.Set("edition", db.Edition)
|
|
d.Set("collation", db.CollationName)
|
|
d.Set("max_size_bytes", strconv.FormatInt(db.MaxSizeBytes, 10))
|
|
d.Set("service_level_id", db.ServiceObjectiveID)
|
|
break
|
|
}
|
|
}
|
|
|
|
// if not found; we must untrack the resource:
|
|
if !found {
|
|
d.SetId("")
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
// resourceAzureSqlDatabaseServiceUpdate does all the necessary API calls to
|
|
// update the state of the SQL Database Service off Azure.
|
|
func resourceAzureSqlDatabaseServiceUpdate(d *schema.ResourceData, meta interface{}) error {
|
|
azureClient := meta.(*Client)
|
|
mgmtClient := azureClient.mgmtClient
|
|
sqlClient := azureClient.sqlClient
|
|
serverName := d.Get("database_server_name").(string)
|
|
|
|
// changes to the name must occur separately from changes to the attributes:
|
|
if d.HasChange("name") {
|
|
oldv, newv := d.GetChange("name")
|
|
|
|
// issue the update request:
|
|
log.Println("[INFO] Issuing Azure Database Service name change.")
|
|
reqID, err := sqlClient.UpdateDatabase(serverName, oldv.(string),
|
|
sql.ServiceResourceUpdateParams{
|
|
Name: newv.(string),
|
|
})
|
|
|
|
// wait for the update to occur:
|
|
log.Println("[INFO] Waiting for Azure SQL Database Service name change.")
|
|
err = mgmtClient.WaitForOperation(reqID, nil)
|
|
if err != nil {
|
|
return fmt.Errorf("Error waiting for Azure SQL Database Service name update: %s", err)
|
|
}
|
|
|
|
// set the new name as the ID:
|
|
d.SetId(newv.(string))
|
|
}
|
|
|
|
name := d.Get("name").(string)
|
|
cedition := d.HasChange("edition")
|
|
cmaxsize := d.HasChange("max_size_bytes")
|
|
clevel := d.HasChange("service_level_id")
|
|
if cedition || cmaxsize || clevel {
|
|
updateParams := sql.ServiceResourceUpdateParams{
|
|
// we still have to stick the name in here for good measure:
|
|
Name: name,
|
|
}
|
|
|
|
// build the update request:
|
|
if cedition {
|
|
updateParams.Edition = d.Get("edition").(string)
|
|
}
|
|
if maxSize, ok := d.GetOk("max_size_bytes"); cmaxsize && ok && maxSize.(string) != "" {
|
|
val, err := strconv.ParseInt(maxSize.(string), 10, 64)
|
|
if err != nil {
|
|
return fmt.Errorf("Provided max_size_bytes is not an integer: %s", err)
|
|
}
|
|
updateParams.MaxSizeBytes = val
|
|
}
|
|
if clevel {
|
|
updateParams.ServiceObjectiveID = d.Get("service_level_id").(string)
|
|
}
|
|
|
|
// issue the update:
|
|
log.Println("[INFO] Issuing Azure Database Service parameter update.")
|
|
reqID, err := sqlClient.UpdateDatabase(serverName, name, updateParams)
|
|
if err != nil {
|
|
return fmt.Errorf("Failed issuing Azure SQL Service parameter update: %s", err)
|
|
}
|
|
|
|
log.Println("[INFO] Waiting for Azure SQL Database Service parameter update.")
|
|
err = mgmtClient.WaitForOperation(reqID, nil)
|
|
if err != nil {
|
|
return fmt.Errorf("Error waiting for Azure SQL Database Service parameter update: %s", err)
|
|
}
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
// resourceAzureSqlDatabaseServiceExists does all the necessary API calls to
|
|
// check for the existence of the SQL Database Service off Azure.
|
|
func resourceAzureSqlDatabaseServiceExists(d *schema.ResourceData, meta interface{}) (bool, error) {
|
|
sqlClient := meta.(*Client).sqlClient
|
|
|
|
log.Println("[INFO] Issuing Azure SQL Database Service get request.")
|
|
name := d.Get("name").(string)
|
|
serverName := d.Get("database_server_name").(string)
|
|
_, err := sqlClient.GetDatabase(serverName, name)
|
|
if err != nil {
|
|
if strings.Contains(err.Error(), "does not exist") {
|
|
d.SetId("")
|
|
return false, nil
|
|
} else {
|
|
return false, fmt.Errorf("Error whilst getting Azure SQL Database Service info: %s", err)
|
|
}
|
|
}
|
|
|
|
return true, nil
|
|
}
|
|
|
|
// resourceAzureSqlDatabaseServiceDelete does all the necessary API calls to
|
|
// delete the SQL Database Service off Azure.
|
|
func resourceAzureSqlDatabaseServiceDelete(d *schema.ResourceData, meta interface{}) error {
|
|
sqlClient := meta.(*Client).sqlClient
|
|
|
|
log.Println("[INFO] Issuing Azure SQL Database deletion request.")
|
|
name := d.Get("name").(string)
|
|
serverName := d.Get("database_server_name").(string)
|
|
return sqlClient.DeleteDatabase(serverName, name)
|
|
}
|