github.com/minamijoyo/terraform@v0.7.8-0.20161029001309-18b3736ba44b/builtin/providers/aws/resource_aws_sqs_queue.go (about)

     1  package aws
     2  
     3  import (
     4  	"fmt"
     5  	"log"
     6  	"net/url"
     7  	"strconv"
     8  
     9  	"github.com/hashicorp/terraform/helper/schema"
    10  
    11  	"strings"
    12  
    13  	"github.com/aws/aws-sdk-go/aws"
    14  	"github.com/aws/aws-sdk-go/aws/awserr"
    15  	"github.com/aws/aws-sdk-go/service/sqs"
    16  )
    17  
    18  var AttributeMap = map[string]string{
    19  	"delay_seconds":              "DelaySeconds",
    20  	"max_message_size":           "MaximumMessageSize",
    21  	"message_retention_seconds":  "MessageRetentionPeriod",
    22  	"receive_wait_time_seconds":  "ReceiveMessageWaitTimeSeconds",
    23  	"visibility_timeout_seconds": "VisibilityTimeout",
    24  	"policy":                     "Policy",
    25  	"redrive_policy":             "RedrivePolicy",
    26  	"arn":                        "QueueArn",
    27  }
    28  
    29  // A number of these are marked as computed because if you don't
    30  // provide a value, SQS will provide you with defaults (which are the
    31  // default values specified below)
    32  func resourceAwsSqsQueue() *schema.Resource {
    33  	return &schema.Resource{
    34  		Create: resourceAwsSqsQueueCreate,
    35  		Read:   resourceAwsSqsQueueRead,
    36  		Update: resourceAwsSqsQueueUpdate,
    37  		Delete: resourceAwsSqsQueueDelete,
    38  		Importer: &schema.ResourceImporter{
    39  			State: schema.ImportStatePassthrough,
    40  		},
    41  
    42  		Schema: map[string]*schema.Schema{
    43  			"name": {
    44  				Type:     schema.TypeString,
    45  				Required: true,
    46  				ForceNew: true,
    47  			},
    48  			"delay_seconds": {
    49  				Type:     schema.TypeInt,
    50  				Optional: true,
    51  				Default:  0,
    52  			},
    53  			"max_message_size": {
    54  				Type:     schema.TypeInt,
    55  				Optional: true,
    56  				Default:  262144,
    57  			},
    58  			"message_retention_seconds": {
    59  				Type:     schema.TypeInt,
    60  				Optional: true,
    61  				Default:  345600,
    62  			},
    63  			"receive_wait_time_seconds": {
    64  				Type:     schema.TypeInt,
    65  				Optional: true,
    66  				Default:  0,
    67  			},
    68  			"visibility_timeout_seconds": {
    69  				Type:     schema.TypeInt,
    70  				Optional: true,
    71  				Default:  30,
    72  			},
    73  			"policy": {
    74  				Type:             schema.TypeString,
    75  				Optional:         true,
    76  				Computed:         true,
    77  				ValidateFunc:     validateJsonString,
    78  				DiffSuppressFunc: suppressEquivalentAwsPolicyDiffs,
    79  			},
    80  			"redrive_policy": {
    81  				Type:         schema.TypeString,
    82  				Optional:     true,
    83  				ValidateFunc: validateJsonString,
    84  				StateFunc: func(v interface{}) string {
    85  					json, _ := normalizeJsonString(v)
    86  					return json
    87  				},
    88  			},
    89  			"arn": {
    90  				Type:     schema.TypeString,
    91  				Computed: true,
    92  			},
    93  		},
    94  	}
    95  }
    96  
    97  func resourceAwsSqsQueueCreate(d *schema.ResourceData, meta interface{}) error {
    98  	sqsconn := meta.(*AWSClient).sqsconn
    99  
   100  	name := d.Get("name").(string)
   101  
   102  	log.Printf("[DEBUG] SQS queue create: %s", name)
   103  
   104  	req := &sqs.CreateQueueInput{
   105  		QueueName: aws.String(name),
   106  	}
   107  
   108  	attributes := make(map[string]*string)
   109  
   110  	resource := *resourceAwsSqsQueue()
   111  
   112  	for k, s := range resource.Schema {
   113  		if attrKey, ok := AttributeMap[k]; ok {
   114  			if value, ok := d.GetOk(k); ok {
   115  				if s.Type == schema.TypeInt {
   116  					attributes[attrKey] = aws.String(strconv.Itoa(value.(int)))
   117  				} else {
   118  					attributes[attrKey] = aws.String(value.(string))
   119  				}
   120  			}
   121  
   122  		}
   123  	}
   124  
   125  	if len(attributes) > 0 {
   126  		req.Attributes = attributes
   127  	}
   128  
   129  	output, err := sqsconn.CreateQueue(req)
   130  	if err != nil {
   131  		return fmt.Errorf("Error creating SQS queue: %s", err)
   132  	}
   133  
   134  	d.SetId(*output.QueueUrl)
   135  
   136  	return resourceAwsSqsQueueUpdate(d, meta)
   137  }
   138  
   139  func resourceAwsSqsQueueUpdate(d *schema.ResourceData, meta interface{}) error {
   140  	sqsconn := meta.(*AWSClient).sqsconn
   141  	attributes := make(map[string]*string)
   142  
   143  	resource := *resourceAwsSqsQueue()
   144  
   145  	for k, s := range resource.Schema {
   146  		if attrKey, ok := AttributeMap[k]; ok {
   147  			if d.HasChange(k) {
   148  				log.Printf("[DEBUG] Updating %s", attrKey)
   149  				_, n := d.GetChange(k)
   150  				if s.Type == schema.TypeInt {
   151  					attributes[attrKey] = aws.String(strconv.Itoa(n.(int)))
   152  				} else {
   153  					attributes[attrKey] = aws.String(n.(string))
   154  				}
   155  			}
   156  		}
   157  	}
   158  
   159  	if len(attributes) > 0 {
   160  		req := &sqs.SetQueueAttributesInput{
   161  			QueueUrl:   aws.String(d.Id()),
   162  			Attributes: attributes,
   163  		}
   164  		if _, err := sqsconn.SetQueueAttributes(req); err != nil {
   165  			return fmt.Errorf("[ERR] Error updating SQS attributes: %s", err)
   166  		}
   167  	}
   168  
   169  	return resourceAwsSqsQueueRead(d, meta)
   170  }
   171  
   172  func resourceAwsSqsQueueRead(d *schema.ResourceData, meta interface{}) error {
   173  	sqsconn := meta.(*AWSClient).sqsconn
   174  
   175  	attributeOutput, err := sqsconn.GetQueueAttributes(&sqs.GetQueueAttributesInput{
   176  		QueueUrl:       aws.String(d.Id()),
   177  		AttributeNames: []*string{aws.String("All")},
   178  	})
   179  
   180  	if err != nil {
   181  		if awsErr, ok := err.(awserr.Error); ok {
   182  			log.Printf("ERROR Found %s", awsErr.Code())
   183  			if "AWS.SimpleQueueService.NonExistentQueue" == awsErr.Code() {
   184  				d.SetId("")
   185  				log.Printf("[DEBUG] SQS Queue (%s) not found", d.Get("name").(string))
   186  				return nil
   187  			}
   188  		}
   189  		return err
   190  	}
   191  
   192  	name, err := extractNameFromSqsQueueUrl(d.Id())
   193  	if err != nil {
   194  		return err
   195  	}
   196  	d.Set("name", name)
   197  
   198  	if attributeOutput.Attributes != nil && len(attributeOutput.Attributes) > 0 {
   199  		attrmap := attributeOutput.Attributes
   200  		resource := *resourceAwsSqsQueue()
   201  		// iKey = internal struct key, oKey = AWS Attribute Map key
   202  		for iKey, oKey := range AttributeMap {
   203  			if attrmap[oKey] != nil {
   204  				if resource.Schema[iKey].Type == schema.TypeInt {
   205  					value, err := strconv.Atoi(*attrmap[oKey])
   206  					if err != nil {
   207  						return err
   208  					}
   209  					d.Set(iKey, value)
   210  					log.Printf("[DEBUG] Reading %s => %s -> %d", iKey, oKey, value)
   211  				} else {
   212  					log.Printf("[DEBUG] Reading %s => %s -> %s", iKey, oKey, *attrmap[oKey])
   213  					d.Set(iKey, *attrmap[oKey])
   214  				}
   215  			}
   216  		}
   217  	}
   218  
   219  	return nil
   220  }
   221  
   222  func resourceAwsSqsQueueDelete(d *schema.ResourceData, meta interface{}) error {
   223  	sqsconn := meta.(*AWSClient).sqsconn
   224  
   225  	log.Printf("[DEBUG] SQS Delete Queue: %s", d.Id())
   226  	_, err := sqsconn.DeleteQueue(&sqs.DeleteQueueInput{
   227  		QueueUrl: aws.String(d.Id()),
   228  	})
   229  	if err != nil {
   230  		return err
   231  	}
   232  	return nil
   233  }
   234  
   235  func extractNameFromSqsQueueUrl(queue string) (string, error) {
   236  	//http://sqs.us-west-2.amazonaws.com/123456789012/queueName
   237  	u, err := url.Parse(queue)
   238  	if err != nil {
   239  		return "", err
   240  	}
   241  	segments := strings.Split(u.Path, "/")
   242  	if len(segments) != 3 {
   243  		return "", fmt.Errorf("SQS Url not parsed correctly")
   244  	}
   245  
   246  	return segments[2], nil
   247  
   248  }