github.com/turtlemonvh/terraform@v0.6.9-0.20151204001754-8e40b6b855e8/builtin/providers/aws/resource_aws_iam_user.go (about) 1 package aws 2 3 import ( 4 "fmt" 5 "log" 6 7 "github.com/aws/aws-sdk-go/aws" 8 "github.com/aws/aws-sdk-go/aws/awserr" 9 "github.com/aws/aws-sdk-go/service/iam" 10 11 "github.com/hashicorp/terraform/helper/schema" 12 ) 13 14 func resourceAwsIamUser() *schema.Resource { 15 return &schema.Resource{ 16 Create: resourceAwsIamUserCreate, 17 Read: resourceAwsIamUserRead, 18 Update: resourceAwsIamUserUpdate, 19 Delete: resourceAwsIamUserDelete, 20 21 Schema: map[string]*schema.Schema{ 22 "arn": &schema.Schema{ 23 Type: schema.TypeString, 24 Computed: true, 25 }, 26 /* 27 The UniqueID could be used as the Id(), but none of the API 28 calls allow specifying a user by the UniqueID: they require the 29 name. The only way to locate a user by UniqueID is to list them 30 all and that would make this provider unnecessarilly complex 31 and inefficient. Still, there are other reasons one might want 32 the UniqueID, so we can make it available. 33 */ 34 "unique_id": &schema.Schema{ 35 Type: schema.TypeString, 36 Computed: true, 37 }, 38 "name": &schema.Schema{ 39 Type: schema.TypeString, 40 Required: true, 41 }, 42 "path": &schema.Schema{ 43 Type: schema.TypeString, 44 Optional: true, 45 Default: "/", 46 ForceNew: true, 47 }, 48 }, 49 } 50 } 51 52 func resourceAwsIamUserCreate(d *schema.ResourceData, meta interface{}) error { 53 iamconn := meta.(*AWSClient).iamconn 54 name := d.Get("name").(string) 55 path := d.Get("path").(string) 56 57 request := &iam.CreateUserInput{ 58 Path: aws.String(path), 59 UserName: aws.String(name), 60 } 61 62 log.Println("[DEBUG] Create IAM User request:", request) 63 createResp, err := iamconn.CreateUser(request) 64 if err != nil { 65 return fmt.Errorf("Error creating IAM User %s: %s", name, err) 66 } 67 return resourceAwsIamUserReadResult(d, createResp.User) 68 } 69 70 func resourceAwsIamUserRead(d *schema.ResourceData, meta interface{}) error { 71 iamconn := meta.(*AWSClient).iamconn 72 name := d.Get("name").(string) 73 request := &iam.GetUserInput{ 74 UserName: aws.String(name), 75 } 76 77 getResp, err := iamconn.GetUser(request) 78 if err != nil { 79 if iamerr, ok := err.(awserr.Error); ok && iamerr.Code() == "NoSuchEntity" { // XXX test me 80 log.Printf("[WARN] No IAM user by name (%s) found", d.Id()) 81 d.SetId("") 82 return nil 83 } 84 return fmt.Errorf("Error reading IAM User %s: %s", d.Id(), err) 85 } 86 return resourceAwsIamUserReadResult(d, getResp.User) 87 } 88 89 func resourceAwsIamUserReadResult(d *schema.ResourceData, user *iam.User) error { 90 d.SetId(*user.UserName) 91 if err := d.Set("name", user.UserName); err != nil { 92 return err 93 } 94 if err := d.Set("arn", user.Arn); err != nil { 95 return err 96 } 97 if err := d.Set("path", user.Path); err != nil { 98 return err 99 } 100 if err := d.Set("unique_id", user.UserId); err != nil { 101 return err 102 } 103 return nil 104 } 105 106 func resourceAwsIamUserUpdate(d *schema.ResourceData, meta interface{}) error { 107 if d.HasChange("name") || d.HasChange("path") { 108 iamconn := meta.(*AWSClient).iamconn 109 on, nn := d.GetChange("name") 110 _, np := d.GetChange("path") 111 112 request := &iam.UpdateUserInput{ 113 UserName: aws.String(on.(string)), 114 NewUserName: aws.String(nn.(string)), 115 NewPath: aws.String(np.(string)), 116 } 117 118 log.Println("[DEBUG] Update IAM User request:", request) 119 _, err := iamconn.UpdateUser(request) 120 if err != nil { 121 if iamerr, ok := err.(awserr.Error); ok && iamerr.Code() == "NoSuchEntity" { 122 log.Printf("[WARN] No IAM user by name (%s) found", d.Id()) 123 d.SetId("") 124 return nil 125 } 126 return fmt.Errorf("Error updating IAM User %s: %s", d.Id(), err) 127 } 128 return resourceAwsIamUserRead(d, meta) 129 } 130 return nil 131 } 132 func resourceAwsIamUserDelete(d *schema.ResourceData, meta interface{}) error { 133 iamconn := meta.(*AWSClient).iamconn 134 135 // IAM Users must be removed from all groups before they can be deleted 136 var groups []string 137 var marker *string 138 truncated := aws.Bool(true) 139 140 for *truncated == true { 141 listOpts := iam.ListGroupsForUserInput{ 142 UserName: aws.String(d.Id()), 143 } 144 145 if marker != nil { 146 listOpts.Marker = marker 147 } 148 149 r, err := iamconn.ListGroupsForUser(&listOpts) 150 if err != nil { 151 return err 152 } 153 154 for _, g := range r.Groups { 155 groups = append(groups, *g.GroupName) 156 } 157 158 // if there's a marker present, we need to save it for pagination 159 if r.Marker != nil { 160 *marker = *r.Marker 161 } 162 *truncated = *r.IsTruncated 163 } 164 165 for _, g := range groups { 166 // use iam group membership func to remove user from all groups 167 log.Printf("[DEBUG] Removing IAM User %s from IAM Group %s", d.Id(), g) 168 if err := removeUsersFromGroup(iamconn, []*string{aws.String(d.Id())}, g); err != nil { 169 return err 170 } 171 } 172 173 request := &iam.DeleteUserInput{ 174 UserName: aws.String(d.Id()), 175 } 176 177 log.Println("[DEBUG] Delete IAM User request:", request) 178 if _, err := iamconn.DeleteUser(request); err != nil { 179 return fmt.Errorf("Error deleting IAM User %s: %s", d.Id(), err) 180 } 181 return nil 182 }