Skip to content

Commit

Permalink
Terraform generate iam
Browse files Browse the repository at this point in the history
Signed-off-by: Modular Magician <[email protected]>
  • Loading branch information
slevenick authored and modular-magician committed Jul 10, 2019
1 parent 00b76aa commit 2b6d62e
Show file tree
Hide file tree
Showing 12 changed files with 840 additions and 341 deletions.
20 changes: 20 additions & 0 deletions google-beta/iam_pubsub_subscription.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package google

import (
"fmt"

"github.com/hashicorp/errwrap"
"github.com/hashicorp/terraform/helper/schema"
"google.golang.org/api/cloudresourcemanager/v1"
Expand Down Expand Up @@ -90,3 +91,22 @@ func (u *PubsubSubscriptionIamUpdater) GetMutexKey() string {
func (u *PubsubSubscriptionIamUpdater) DescribeResource() string {
return fmt.Sprintf("pubsub subscription %q", u.subscription)
}

// v1 and v2beta policy are identical
func resourceManagerToPubsubPolicy(in *cloudresourcemanager.Policy) (*pubsub.Policy, error) {
out := &pubsub.Policy{}
err := Convert(in, out)
if err != nil {
return nil, errwrap.Wrapf("Cannot convert a v1 policy to a pubsub policy: {{err}}", err)
}
return out, nil
}

func pubsubToResourceManagerPolicy(in *pubsub.Policy) (*cloudresourcemanager.Policy, error) {
out := &cloudresourcemanager.Policy{}
err := Convert(in, out)
if err != nil {
return nil, errwrap.Wrapf("Cannot convert a pubsub policy to a v1 policy: {{err}}", err)
}
return out, nil
}
130 changes: 82 additions & 48 deletions google-beta/iam_pubsub_topic.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,107 +6,141 @@ import (
"github.com/hashicorp/errwrap"
"github.com/hashicorp/terraform/helper/schema"
"google.golang.org/api/cloudresourcemanager/v1"
"google.golang.org/api/pubsub/v1"
)

var IamPubsubTopicSchema = map[string]*schema.Schema{
var PubsubTopicIamSchema = map[string]*schema.Schema{
"project": {
Type: schema.TypeString,
Computed: true,
Optional: true,
ForceNew: true,
},
"topic": {
Type: schema.TypeString,
Required: true,
ForceNew: true,
DiffSuppressFunc: compareSelfLinkOrResourceName,
},
"project": {
Type: schema.TypeString,
Optional: true,
Computed: true,
ForceNew: true,
},
}

type PubsubTopicIamUpdater struct {
topic string
Config *Config
project string
topic string
d *schema.ResourceData
Config *Config
}

func NewPubsubTopicIamUpdater(d *schema.ResourceData, config *Config) (ResourceIamUpdater, error) {
func PubsubTopicIamUpdaterProducer(d *schema.ResourceData, config *Config) (ResourceIamUpdater, error) {
values := make(map[string]string)

project, err := getProject(d, config)
if err != nil {
return nil, err
}

topic := getComputedTopicName(project, d.Get("topic").(string))
// While this may be overridden by the "project" value from getImportIdQualifiers below,
// setting project here ensures the value is set even if the value set in config is the short
// name or otherwise doesn't include the project.
values["project"] = project

return &PubsubTopicIamUpdater{
topic: topic,
Config: config,
}, nil
m, err := getImportIdQualifiers([]string{"projects/(?P<project>[^/]+)/topics/(?P<topic>[^/]+)", "(?P<project>[^/]+)/(?P<topic>[^/]+)", "(?P<topic>[^/]+)"}, d, config, d.Get("topic").(string))
if err != nil {
return nil, err
}

for k, v := range m {
values[k] = v
}

u := &PubsubTopicIamUpdater{
project: values["project"],
topic: values["topic"],
d: d,
Config: config,
}
d.SetId(u.GetResourceId())

return u, nil
}

func PubsubTopicIdParseFunc(d *schema.ResourceData, _ *Config) error {
d.Set("topic", d.Id())
func PubsubTopicIdParseFunc(d *schema.ResourceData, config *Config) error {
values := make(map[string]string)

project, err := getProject(d, config)
if err != nil {
return err
}

values["project"] = project

m, err := getImportIdQualifiers([]string{"projects/(?P<project>[^/]+)/topics/(?P<topic>[^/]+)", "(?P<project>[^/]+)/(?P<topic>[^/]+)", "(?P<topic>[^/]+)"}, d, config, d.Id())
if err != nil {
return err
}

for k, v := range m {
values[k] = v
}

u := &PubsubTopicIamUpdater{
project: values["project"],
topic: values["topic"],
d: d,
Config: config,
}
d.Set("topic", u.GetResourceId())
d.SetId(u.GetResourceId())
return nil
}

func (u *PubsubTopicIamUpdater) GetResourceIamPolicy() (*cloudresourcemanager.Policy, error) {
p, err := u.Config.clientPubsub.Projects.Topics.GetIamPolicy(u.topic).Do()
url := u.qualifyTopicUrl("getIamPolicy")

policy, err := sendRequest(u.Config, "GET", url, nil)
if err != nil {
return nil, errwrap.Wrapf(fmt.Sprintf("Error retrieving IAM policy for %s: {{err}}", u.DescribeResource()), err)
}

v1Policy, err := pubsubToResourceManagerPolicy(p)
out := &cloudresourcemanager.Policy{}
err = Convert(policy, out)
if err != nil {
return nil, err
return nil, errwrap.Wrapf("Cannot convert a policy to a resource manager policy: {{err}}", err)
}

return v1Policy, nil
return out, nil
}

func (u *PubsubTopicIamUpdater) SetResourceIamPolicy(policy *cloudresourcemanager.Policy) error {
pubsubPolicy, err := resourceManagerToPubsubPolicy(policy)
json, err := ConvertToMap(policy)
if err != nil {
return err
}

_, err = u.Config.clientPubsub.Projects.Topics.SetIamPolicy(u.topic, &pubsub.SetIamPolicyRequest{
Policy: pubsubPolicy,
}).Do()
obj := make(map[string]interface{})
obj["policy"] = json

url := u.qualifyTopicUrl("setIamPolicy")

_, err = sendRequestWithTimeout(u.Config, "POST", url, obj, u.d.Timeout(schema.TimeoutCreate))
if err != nil {
return errwrap.Wrapf(fmt.Sprintf("Error setting IAM policy for %s: {{err}}", u.DescribeResource()), err)
}

return nil
}

func (u *PubsubTopicIamUpdater) qualifyTopicUrl(methodIdentifier string) string {
return fmt.Sprintf("https://pubsub.googleapis.com/v1/%s:%s", fmt.Sprintf("projects/%s/topics/%s", u.project, u.topic), methodIdentifier)
}

func (u *PubsubTopicIamUpdater) GetResourceId() string {
return u.topic
return fmt.Sprintf("projects/%s/topics/%s", u.project, u.topic)
}

func (u *PubsubTopicIamUpdater) GetMutexKey() string {
return fmt.Sprintf("iam-pubsub-topic-%s", u.topic)
return fmt.Sprintf("iam-pubsub-topic-%s", u.GetResourceId())
}

func (u *PubsubTopicIamUpdater) DescribeResource() string {
return fmt.Sprintf("pubsub topic %q", u.topic)
}

// v1 and v2beta policy are identical
func resourceManagerToPubsubPolicy(in *cloudresourcemanager.Policy) (*pubsub.Policy, error) {
out := &pubsub.Policy{}
err := Convert(in, out)
if err != nil {
return nil, errwrap.Wrapf("Cannot convert a v1 policy to a pubsub policy: {{err}}", err)
}
return out, nil
}

func pubsubToResourceManagerPolicy(in *pubsub.Policy) (*cloudresourcemanager.Policy, error) {
out := &cloudresourcemanager.Policy{}
err := Convert(in, out)
if err != nil {
return nil, errwrap.Wrapf("Cannot convert a pubsub policy to a v1 policy: {{err}}", err)
}
return out, nil
return fmt.Sprintf("pubsub topic %q", u.GetResourceId())
}
Loading

0 comments on commit 2b6d62e

Please sign in to comment.