Skip to content
This repository has been archived by the owner on Nov 14, 2020. It is now read-only.

rabbitmq: bindings not being stored in state #2

Closed
hashibot opened this issue Jun 13, 2017 · 3 comments · Fixed by #8
Closed

rabbitmq: bindings not being stored in state #2

hashibot opened this issue Jun 13, 2017 · 3 comments · Fixed by #8
Labels

Comments

@hashibot
Copy link

This issue was originally opened by @jason-archidera as hashicorp/terraform#12782. It was migrated here as part of the provider split. The original body of the issue is below.


I seem to have an issue and it seems to be in saving state.
Version: 0.9
Resource: rabbitmq_binding

I've setup my project with a main.tf:

terraform {
    required_version = ">= 0.9"
    backend "consul" {
      address = "XXXXXXXX"
      path    = "tfstate/vhost/xxxxx-development"
  }
}

#######VARIABLES########
variable "endpoint" {
  default = "http://127.0.0.1:15672"
}

variable "username" {
  default = "XXXXX"
}

variable "password" {
  default = "XXXXXX"
}

variable "usersuffix" {
  default = "DEVELOPMENT"
}

variable "vhost" {
  default = "XXXX-DEVELOPMENT-TF"
}

# Configure the RabbitMQ provider
provider "rabbitmq" {
  endpoint = "${var.endpoint}"
  username = "${var.username}"
  password = "${var.password}"
  insecure = true
}

########GET MODULES########
module "create-all" {
    source="./../modules"
    vhost = "${var.vhost}"
    usersuffix = "${var.usersuffix}"
}

#######OUTPUT FOR CONSOLE#######
output "endpoint" {
  value = "${var.endpoint}"
}

output "vhost" {
  value = "${var.vhost}"
}

output "usersuffix" {
  value = "${var.usersuffix}"
}

My modules folder has several tf files and all is well except for any binding with a routing key that isn't "#". For example:

resource "rabbitmq_binding" "xxxx_to_zzzz" {
    depends_on = ["rabbitmq_exchange.xxxx", "rabbitmq_queue.zzzzz"]
    source = "XXXX.XXXX"
    vhost = "${rabbitmq_vhost.vhost.name}"
    destination = "XXXX.ZZZZ.Queue"
    destination_type = "queue"
    routing_key = "ZZ.#"
    #routing_key = "#"
    properties_key = "%23"
}

I run the commands, everything seems to work, except for the bindings with anything other than "#" are not stored in the remote state (Consul). This causes each time I run plan or apply, it thinks these bindings are new.

- terraform init -get=true -backend=true

- terraform plan

- terraform apply

It's either a bug in the RabbitMQ provider or perhaps in state? The interesting part is that the bindings are created in RabbitMQ, but the state is not saved.

@hashibot hashibot added the bug label Jun 13, 2017
@sgarlick987
Copy link
Contributor

sgarlick987 commented Sep 18, 2017

I just debugged a similar issue with bindings not being stored in the state file and here's my findings.

According to https://raw.githack.com/rabbitmq/rabbitmq-management/rabbitmq_v3_6_7/priv/www/api/index.html a binding's properties_key in rabbitmq is a combination if its routing key and a hash of the arguments and it separates them with ~. It comes out something like ~U71-Q7rVcYLiGY8sYgmeCQ in our case when we have a blank routing key with arguments supplied. As far as I can tell, whatever you supply in properties_keys isn't actually used in rabbitmq, but is used incorrectly as part of the id in terraform.

In https://github.com/terraform-providers/terraform-provider-rabbitmq/blob/master/rabbitmq/resource_binding.go#L85 the properties_key in the template resource is used as part of the id of the binding, but the one supplied in the template is not necessarily what it gets created as. That id is then used again later at https://github.com/terraform-providers/terraform-provider-rabbitmq/blob/master/rabbitmq/resource_binding.go#L99 and then split to compare it against all the bindings returned for a vhost. In this case, everything else matches properly, except properties_key which causes the lookup to fail, and thus return nil and not get stored in the statefile.

Some logs and values to backup my findings

Blank Routing Key
properties_key SOMEVALUE
Argument Param
{
      network = "SOMEVALUE"
      type = "SOMEVALUE"
      x-match = "all"
}
Create logs

2017-09-18T13:43:40.151-0400 [DEBUG] plugin.terraform-provider-rabbitmq_v0.1.0_x4: 2017/09/18 13:43:40 [DEBUG] RabbitMQ: Binding declare response: &http.Response{Status:"201 Created", StatusCode:201, Proto:"HTTP/1.1", ProtoMajor:1, ProtoMinor:1, Header:http.Header{"Content-Type":[]string{"application/json"}, "Date":[]string{"Mon, 18 Sep 2017 17:43:40 GMT"}, "Location":[]string{"palm/~s9-ryeWLJbsYU-fol9tCPQ"}, "Server":[]string{"Cowboy"}, "Vary":[]string{"accept-encoding, origin"}, "Content-Length":[]string{"0"}}, Body:http.noBody{}, ContentLength:0, TransferEncoding:[]string(nil), Close:true, Uncompressed:false, Trailer:http.Header(nil), Request:(*http.Request)(0xc42024c700), TLS:(*tls.ConnectionState)(0xc4202b00b0)}

Binding retrieve for vhost logs

2017-09-18T13:43:40.213-0400 [DEBUG] plugin.terraform-provider-rabbitmq_v0.1.0_x4: 2017/09/18 13:43:40 [DEBUG] RabbitMQ: Bindings retrieved: []rabbithole.BindingInfo{Source:"app", Vhost:"app-dev", Destination:"dest", DestinationType:"queue", RoutingKey:"", Arguments:map[string]interface {}{"network":"SOMEVALUE", "type":"SOMEVALUE", "x-match":"all"}, PropertiesKey:"~s9-ryeWLJbsYU-fol9tCPQ"}

Notice how the PropertiesKey is nothing like the one I supplied of SOMEVALUE and how it matches the Location header in the response to the create.

If I'm understanding everything correctly, then the solution would be to use the value returned in the Location field, and take everything after the / as the binding properties_key and to remove the properties_key from the template resource object completely.

Note, I am able to work around this by supplying the generated value ~s9-ryeWLJbsYU-fol9tCPQ as the properties_key in my template and then the state gets saved properly since the lookup after create is successful.

I'm going to try to take a minute today to submit a PR assuming the above analysis is right, and you guys like the approach towards fixing it.

Thanks.

@jtopjian
Copy link
Contributor

@sgarlick987 Thank you for the detailed analysis of this issue. If you submit a PR, I'd be happy to review it.

@sgarlick987
Copy link
Contributor

Ok sounds good. I have something working now, but need to update tests/docs and then I'll submit.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants