terraform-template-renderer 0.1.0 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: cef4859595c7d96c5122dbe5b058da92806f7905
4
- data.tar.gz: 162af8691305d44a0cb024d1f2ceac8efe83a5a4
3
+ metadata.gz: 48bac62d1bd59cb46a67cfcc05d0a3a92a5d2300
4
+ data.tar.gz: 3ca5b7f8ce549c3a498bd688e8b9e2b83df16f35
5
5
  SHA512:
6
- metadata.gz: e221e4184fa8e12e9ce5c0c850071bcdf1a5a84e734872790ba3cb5250112f08547babeab991e13a951aa5246e6d1099c13d310ab4ad0562876446657b13870d
7
- data.tar.gz: 372ebfe28e1e7d077c0ea60ed8827410e4d1a6c45c17c39721a684b5af8a025c3ea016ff4b39823baf8c1f4d21839aa38e1eec14d8b602d787c5d320e889f87a
6
+ metadata.gz: 05208a74a1873f77c36647a90edc1407fe5856b54bb41398f14839256bc8c47152a3ae49c59062ac145d29b71ccb388c1f52bec5ab370377dc61f7e878396453
7
+ data.tar.gz: 7666c567d1a7c0973ae06b9df0dbf155d6feae5f31ebb2bbb8bc53da5cb4f6cc16c7e11b08591b155aabfa2f2a4c627832735a788f25b187688bc42436ea38f5
data/.gitignore CHANGED
@@ -10,6 +10,10 @@
10
10
  # rspec failure tracking
11
11
  .rspec_status
12
12
 
13
- Gemfile.lock
13
+ /Gemfile.lock
14
14
 
15
15
  .ruby-version
16
+
17
+ examples/*/.terraform/
18
+ examples/*/terraform.tfstate*
19
+ examples/*/sample_output
@@ -1,3 +1,11 @@
1
+ ## 0.2.0 (2018-01-29)
2
+
3
+ Features:
4
+
5
+ - Enabled trim mode for ERB templates using a hyphen (e.g. `<%- code -%>` will remove preceeding indentation and a
6
+ following newline).
7
+ - Example directory giving real usage examples in terraform.
8
+
1
9
  ## 0.1.0 (2018-01-28)
2
10
 
3
11
  Features:
data/README.md CHANGED
@@ -22,3 +22,22 @@ The purpose for this strange behaviour is to be a [terraform external
22
22
  provider](https://www.terraform.io/docs/providers/external/data_source.html) to render arbitrarily complex templates,
23
23
  terraform passes in the variables to render as a json blob to stdin as described above and expects a json blob
24
24
  back.
25
+
26
+ ## ERB Template notes
27
+
28
+ Trim mode is enabled and the trim character is a hyphen `-`.
29
+
30
+ ## Examples
31
+
32
+ There are a number of examples in the examples folder. To run these examples you will need terraform 0.11, you can run
33
+ the example as follows:
34
+
35
+ cd examples/simple_strings
36
+ terraform init
37
+ terraform apply
38
+
39
+ In each example there is an erb template and a terraform file, applying the terraform code will produce a file called
40
+ `example_output`.
41
+
42
+ ___WARNING___: Some of the examples incur AWS costs, _ALWAYS_ remember to `terraform destroy` after you have finished
43
+ running the example. You are solely responsible for any AWS costs incurred running these examples.
@@ -0,0 +1 @@
1
+ gem "terraform-template-renderer", path: "../"
@@ -0,0 +1,17 @@
1
+ PATH
2
+ remote: ..
3
+ specs:
4
+ terraform-template-renderer (0.2.0)
5
+
6
+ GEM
7
+ remote: https://rubygems.org/
8
+ specs:
9
+
10
+ PLATFORMS
11
+ ruby
12
+
13
+ DEPENDENCIES
14
+ terraform-template-renderer!
15
+
16
+ BUNDLED WITH
17
+ 1.16.1
@@ -0,0 +1,17 @@
1
+ # Multi Resource Lookup example
2
+
3
+ This example requires applying the terraform in 2 stages. The easiest way to do this is to comment
4
+ out everything in `cloudwatch_dashboard.tf` run `terraform apply`, allow the aws instances to be created,
5
+ and then uncomment `cloudwatch_dashboard.tf`
6
+
7
+ This example directory includes a screenshot of the resultant dashboard which was a result of running terraform
8
+ apply as described above.
9
+
10
+ ## COSTS!
11
+
12
+ Be warned, this example will cost money to perform, it requires starting up 2 t2.nano instances and an ELB.
13
+ You are solely responsible for any resources created and costs incurred.
14
+
15
+ I strongly recommend running `terraform destroy` once you have finished running the test to remove all the resources
16
+ that the test created.
17
+
@@ -0,0 +1,136 @@
1
+ <%
2
+ def instances_by_name_list_for(statistic)
3
+ rows = JSON.parse(@instances_by_name).map do |instance|
4
+ row = ["AWS/EC2", statistic, "InstanceId", instance["id"], { label: instance["name"] }]
5
+ JSON.dump(row)
6
+ end
7
+ rows.join(",")
8
+ end
9
+
10
+ def instances_by_id_list_for(statistic)
11
+ rows = JSON.parse(@instances_by_id).map do |instance|
12
+ row = ["AWS/EC2", statistic, "InstanceId", instance]
13
+ JSON.dump(row)
14
+ end
15
+ rows.join(",")
16
+ end
17
+
18
+ -%>
19
+ {
20
+ "widgets": [
21
+ {
22
+ "type": "text",
23
+ "x": 0,
24
+ "y": 0,
25
+ "width": 24,
26
+ "height": 1,
27
+ "properties": {
28
+ "markdown": "## Instances"
29
+ }
30
+ },
31
+ {
32
+ "type": "metric",
33
+ "x": 0,
34
+ "y": 1,
35
+ "width": 12,
36
+ "height": 5,
37
+ "properties": {
38
+ "metrics": [<%=instances_by_name_list_for("NetworkIn")%>],
39
+ "period": 300,
40
+ "stat": "Maximum",
41
+ "region": "eu-west-1",
42
+ "title": "Network In"
43
+ }
44
+ },
45
+ {
46
+ "type": "metric",
47
+ "x": 12,
48
+ "y": 1,
49
+ "width": 12,
50
+ "height": 5,
51
+ "properties": {
52
+ "metrics": [<%=instances_by_name_list_for("NetworkOut")%>],
53
+ "period": 300,
54
+ "stat": "Maximum",
55
+ "region": "eu-west-1",
56
+ "title": "Network Out"
57
+ }
58
+ },
59
+ {
60
+ "type": "metric",
61
+ "x": 0,
62
+ "y": 6,
63
+ "width": 24,
64
+ "height": 5,
65
+ "properties": {
66
+ "metrics": [<%=instances_by_id_list_for("CPUUtilization")%>],
67
+ "period": 300,
68
+ "stat": "Maximum",
69
+ "region": "eu-west-1",
70
+ "title": "EC2 Instance CPU"
71
+ }
72
+ },
73
+ {
74
+ "type": "text",
75
+ "x": 0,
76
+ "y": 11,
77
+ "width": 24,
78
+ "height": 1,
79
+ "properties": {
80
+ "markdown": "## ELB"
81
+ }
82
+ },
83
+ {
84
+ "type": "metric",
85
+ "x": 0,
86
+ "y": 12,
87
+ "width": 8,
88
+ "height": 5,
89
+ "properties": {
90
+ "metrics": [
91
+ [ "AWS/ELB", "HealthyHostCount", "LoadBalancerName", "<%=@elb_name%>" ],
92
+ [ "AWS/ELB", "UnHealthyHostCount", "LoadBalancerName", "<%=@elb_name%>" ]
93
+ ],
94
+ "period": 300,
95
+ "stat": "Maximum",
96
+ "region": "eu-west-1",
97
+ "title": "Host Health"
98
+ }
99
+ },
100
+ {
101
+ "type": "metric",
102
+ "x": 8,
103
+ "y": 12,
104
+ "width": 8,
105
+ "height": 5,
106
+ "properties": {
107
+ "metrics": [
108
+ [ "AWS/ELB", "RequestCount", "LoadBalancerName", "<%=@elb_name%>" ]
109
+ ],
110
+ "period": 300,
111
+ "stat": "Maximum",
112
+ "region": "eu-west-1",
113
+ "title": "Request Latency"
114
+ }
115
+ },
116
+ {
117
+ "type": "metric",
118
+ "x": 16,
119
+ "y": 12,
120
+ "width": 8,
121
+ "height": 5,
122
+ "properties": {
123
+ "metrics": [
124
+ [ "AWS/ELB", "HTTPCode_Backend_2XX", "LoadBalancerName", "<%=@elb_name%>", { "label": "2xx responses" } ],
125
+ [ "AWS/ELB", "HTTPCode_Backend_3XX", "LoadBalancerName", "<%=@elb_name%>", { "label": "3xx responses" } ],
126
+ [ "AWS/ELB", "HTTPCode_Backend_4XX", "LoadBalancerName", "<%=@elb_name%>", { "label": "4xx responses" } ],
127
+ [ "AWS/ELB", "HTTPCode_Backend_5XX", "LoadBalancerName", "<%=@elb_name%>", { "label": "5xx responses" } ]
128
+ ],
129
+ "period": 300,
130
+ "stat": "Maximum",
131
+ "region": "eu-west-1",
132
+ "title": "Request Latency"
133
+ }
134
+ }
135
+ ]
136
+ }
@@ -0,0 +1,32 @@
1
+ data "aws_instances" "cloudwatch_dashboard" {
2
+ instance_tags {
3
+ Stage = "Development"
4
+ }
5
+ }
6
+
7
+ locals {
8
+ aws_instances_by_name = [
9
+ { name = "${aws_instance.cloudwatch_dashboard_1.tags.Name}", id = "${aws_instance.cloudwatch_dashboard_1.id}" },
10
+ { name = "${aws_instance.cloudwatch_dashboard_2.tags.Name}", id = "${aws_instance.cloudwatch_dashboard_2.id}" }
11
+ ]
12
+ }
13
+
14
+ data "external" "cloudwatch_dashboard" {
15
+ program = ["bundle", "exec", "render-template", "cloudwatch_dashboard.erb"]
16
+
17
+ query {
18
+ instances_by_name = "${jsonencode(local.aws_instances_by_name)}"
19
+ instances_by_id = "${jsonencode(data.aws_instances.cloudwatch_dashboard.ids)}"
20
+ elb_name = "${aws_elb.cloudwatch_dashboard.name}"
21
+ }
22
+ }
23
+
24
+ resource "aws_cloudwatch_dashboard" "cloudwatch_dashboard" {
25
+ dashboard_name = "TerraformTemplateRendererExample"
26
+ dashboard_body = "${data.external.cloudwatch_dashboard.result.rendered}"
27
+ }
28
+
29
+ resource "local_file" "cloudwatch_dashboard" {
30
+ content = "${data.external.cloudwatch_dashboard.result.rendered}"
31
+ filename = "sample_output"
32
+ }
@@ -0,0 +1,97 @@
1
+ terraform {
2
+ required_version = "~> 0.11.1"
3
+ }
4
+
5
+ provider "external" {
6
+ version = "~> 1.0.0"
7
+ }
8
+
9
+ provider "aws" {
10
+ version = "~> 1.7"
11
+ region = "eu-west-1"
12
+ }
13
+
14
+ resource "aws_vpc" "cloudwatch_dashboard" {
15
+ cidr_block = "10.254.254.0/24"
16
+
17
+ tags {
18
+ Name = "terraform-template-renderer-example"
19
+ }
20
+ }
21
+
22
+ resource "aws_internet_gateway" "cloudwatch_dashboard" {
23
+ vpc_id = "${aws_vpc.cloudwatch_dashboard.id}"
24
+
25
+ tags {
26
+ Name = "terraform-template-renderer-example"
27
+ }
28
+ }
29
+
30
+ resource "aws_subnet" "cloudwatch_dashboard" {
31
+ vpc_id = "${aws_vpc.cloudwatch_dashboard.id}"
32
+ cidr_block = "10.254.254.0/24"
33
+ availability_zone = "eu-west-1a"
34
+
35
+ tags {
36
+ Name = "terraform-template-renderer-example"
37
+ }
38
+ }
39
+
40
+ data "aws_ami" "cloudwatch_dashboard" {
41
+ most_recent = true
42
+
43
+ filter {
44
+ name = "name"
45
+ values = ["amzn-ami-2017.09.*-amazon-ecs-optimized"]
46
+ }
47
+
48
+ owners = ["amazon"]
49
+ }
50
+
51
+ resource "aws_instance" "cloudwatch_dashboard_1" {
52
+ ami = "${data.aws_ami.cloudwatch_dashboard.id}"
53
+ instance_type = "t2.nano"
54
+ subnet_id = "${aws_subnet.cloudwatch_dashboard.id}"
55
+
56
+ tags {
57
+ Name = "terraform-template-renderer-example-1"
58
+ Stage = "Development"
59
+ }
60
+ }
61
+
62
+ resource "aws_instance" "cloudwatch_dashboard_2" {
63
+ ami = "${data.aws_ami.cloudwatch_dashboard.id}"
64
+ instance_type = "t2.nano"
65
+ subnet_id = "${aws_subnet.cloudwatch_dashboard.id}"
66
+
67
+ tags {
68
+ Name = "terraform-template-renderer-example-2"
69
+ Stage = "Development"
70
+ }
71
+ }
72
+
73
+ resource "aws_elb" "cloudwatch_dashboard" {
74
+ name = "terraform-template-renderer-ex"
75
+ subnets = ["${aws_subnet.cloudwatch_dashboard.id}"]
76
+
77
+ instances = [
78
+ "${aws_instance.cloudwatch_dashboard_1.id}",
79
+ "${aws_instance.cloudwatch_dashboard_2.id}"
80
+ ]
81
+
82
+ listener {
83
+ instance_port = 80
84
+ instance_protocol = "HTTP"
85
+ lb_port = 80
86
+ lb_protocol = "HTTP"
87
+ }
88
+
89
+ tags {
90
+ Name = "terraform-template-renderer-example"
91
+ Stage = "Development"
92
+ }
93
+
94
+ depends_on = [
95
+ "aws_internet_gateway.cloudwatch_dashboard"
96
+ ]
97
+ }
@@ -0,0 +1,3 @@
1
+ <% hash = JSON.parse(@hash) %>
2
+ KEY1 [<%=hash["key1"]%>]
3
+ KEY2 [<%=hash["key2"]%>]
@@ -0,0 +1,25 @@
1
+ terraform {
2
+ required_version = "~> 0.11.1"
3
+ }
4
+
5
+ provider "external" {
6
+ version = "~> 1.0.0"
7
+ }
8
+
9
+ data "external" "json_encoded_hash" {
10
+ program = ["bundle", "exec", "render-template", "json_encoded_hash.erb"]
11
+
12
+ query {
13
+ hash = <<EOF
14
+ {
15
+ "key1": "value1",
16
+ "key2": "value2"
17
+ }
18
+ EOF
19
+ }
20
+ }
21
+
22
+ resource "local_file" "json_encoded_hash" {
23
+ content = "${data.external.json_encoded_hash.result.rendered}"
24
+ filename = "sample_output"
25
+ }
@@ -0,0 +1,14 @@
1
+ # Multi Resource Lookup example
2
+
3
+ This example requires applying the terraform in 2 stages. The easiest way to do this is to comment
4
+ out everything in `multi_resource_lookup.tf` run `terraform apply`, allow the aws instances to be created,
5
+ and then uncomment `multi_resource_lookup.tf`
6
+
7
+ ## COSTS!
8
+
9
+ Be warned, this example will cost money to perform, it requires starting up 2 t2.nano instances. You are solely
10
+ responsible for any resources created or costs incurred.
11
+
12
+ I strongly recommend running `terraform destroy` once you have finished running the test to remove all the resources
13
+ that the test created.
14
+
@@ -0,0 +1,7 @@
1
+ <%=
2
+ lines = JSON.parse(@instances).map.with_index do |instance_id, index|
3
+ "#{index} [#{instance_id}]"
4
+ end
5
+
6
+ lines.join("\n")
7
+ %>
@@ -0,0 +1,18 @@
1
+ data "aws_instances" "multi_resource_lookup" {
2
+ instance_tags {
3
+ Stage = "Development"
4
+ }
5
+ }
6
+
7
+ data "external" "multi_resource_lookup" {
8
+ program = ["bundle", "exec", "render-template", "multi_resource_lookup.erb"]
9
+
10
+ query {
11
+ instances = "${jsonencode(data.aws_instances.multi_resource_lookup.ids)}"
12
+ }
13
+ }
14
+
15
+ resource "local_file" "multi_resource_lookup" {
16
+ content = "${data.external.multi_resource_lookup.result.rendered}"
17
+ filename = "sample_output"
18
+ }
@@ -0,0 +1,63 @@
1
+ terraform {
2
+ required_version = "~> 0.11.1"
3
+ }
4
+
5
+ provider "external" {
6
+ version = "~> 1.0.0"
7
+ }
8
+
9
+ provider "aws" {
10
+ version = "~> 1.7"
11
+ region = "eu-west-1"
12
+ }
13
+
14
+ resource "aws_vpc" "multi_resource_lookup" {
15
+ cidr_block = "10.254.254.0/24"
16
+
17
+ tags {
18
+ Name = "terraform-template-renderer-example"
19
+ }
20
+ }
21
+
22
+ resource "aws_subnet" "multi_resource_lookup" {
23
+ vpc_id = "${aws_vpc.multi_resource_lookup.id}"
24
+ cidr_block = "10.254.254.0/24"
25
+ availability_zone = "eu-west-1a"
26
+
27
+ tags {
28
+ Name = "terraform-template-renderer-example"
29
+ }
30
+ }
31
+
32
+ data "aws_ami" "multi_resource_lookup" {
33
+ most_recent = true
34
+
35
+ filter {
36
+ name = "name"
37
+ values = ["amzn-ami-2017.09.*-amazon-ecs-optimized"]
38
+ }
39
+
40
+ owners = ["amazon"]
41
+ }
42
+
43
+ resource "aws_instance" "multi_resource_lookup_1" {
44
+ ami = "${data.aws_ami.multi_resource_lookup.id}"
45
+ instance_type = "t2.nano"
46
+ subnet_id = "${aws_subnet.multi_resource_lookup.id}"
47
+
48
+ tags {
49
+ Name = "terraform-template-renderer-example"
50
+ Stage = "Development"
51
+ }
52
+ }
53
+
54
+ resource "aws_instance" "multi_resource_lookup_2" {
55
+ ami = "${data.aws_ami.multi_resource_lookup.id}"
56
+ instance_type = "t2.nano"
57
+ subnet_id = "${aws_subnet.multi_resource_lookup.id}"
58
+
59
+ tags {
60
+ Name = "terraform-template-renderer-example"
61
+ Stage = "Development"
62
+ }
63
+ }
@@ -0,0 +1,7 @@
1
+ <%=
2
+ lines = JSON.parse(@list).map.with_index do |item, index|
3
+ "KEY#{index} [#{item}]"
4
+ end
5
+
6
+ lines.join("\n")
7
+ %>
@@ -0,0 +1,22 @@
1
+ terraform {
2
+ required_version = "~> 0.11.1"
3
+ }
4
+
5
+ provider "external" {
6
+ version = "~> 1.0.0"
7
+ }
8
+
9
+ variable "simple_list" { default = ["list_value_a", "list_value_2"] }
10
+
11
+ data "external" "simple_list" {
12
+ program = ["bundle", "exec", "render-template", "simple_list.erb"]
13
+
14
+ query {
15
+ list = "${jsonencode(var.simple_list)}"
16
+ }
17
+ }
18
+
19
+ resource "local_file" "simple_list" {
20
+ content = "${data.external.simple_list.result.rendered}"
21
+ filename = "sample_output"
22
+ }
@@ -0,0 +1,7 @@
1
+ <%=
2
+ lines = JSON.parse(@map).map do |key, value|
3
+ "#{key} [#{value}]"
4
+ end
5
+
6
+ lines.join("\n")
7
+ %>
@@ -0,0 +1,27 @@
1
+ terraform {
2
+ required_version = "~> 0.11.1"
3
+ }
4
+
5
+ provider "external" {
6
+ version = "~> 1.0.0"
7
+ }
8
+
9
+ variable "simple_map" {
10
+ default = {
11
+ key1 = "value1"
12
+ key2 = "value2"
13
+ }
14
+ }
15
+
16
+ data "external" "simple_map" {
17
+ program = ["bundle", "exec", "render-template", "simple_map.erb"]
18
+
19
+ query {
20
+ map = "${jsonencode(var.simple_map)}"
21
+ }
22
+ }
23
+
24
+ resource "local_file" "simple_map" {
25
+ content = "${data.external.simple_map.result.rendered}"
26
+ filename = "sample_output"
27
+ }
@@ -0,0 +1,2 @@
1
+ KEY1 [<%=@key1%>]
2
+ KEY2 [<%=@key2%>]
@@ -0,0 +1,21 @@
1
+ terraform {
2
+ required_version = "~> 0.11.1"
3
+ }
4
+
5
+ provider "external" {
6
+ version = "~> 1.0.0"
7
+ }
8
+
9
+ data "external" "simple_strings" {
10
+ program = ["bundle", "exec", "render-template", "simple_strings.erb"]
11
+
12
+ query {
13
+ key1 = "value1"
14
+ key2 = "value2"
15
+ }
16
+ }
17
+
18
+ resource "local_file" "simple_strings" {
19
+ content = "${data.external.simple_strings.result.rendered}"
20
+ filename = "sample_output"
21
+ }
@@ -4,7 +4,8 @@ require "json"
4
4
  module TerraformTemplateRenderer
5
5
  class Renderer
6
6
  def initialize(template)
7
- @erb_template = ERB.new(template)
7
+ # The third argument enables trim mode using a hyphen
8
+ @erb_template = ERB.new(template, nil, "-")
8
9
  end
9
10
 
10
11
  # The passed in json_variables needs to be a JSON object (not array), all the keys will be used
@@ -1,3 +1,3 @@
1
1
  module TerraformTemplateRenderer
2
- VERSION = "0.1.0"
2
+ VERSION = "0.2.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: terraform-template-renderer
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jonathan Harden
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2018-01-28 00:00:00.000000000 Z
11
+ date: 2018-01-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: aruba
@@ -104,6 +104,25 @@ files:
104
104
  - Rakefile
105
105
  - bin/rake
106
106
  - bin/rspec
107
+ - examples/Gemfile
108
+ - examples/Gemfile.lock
109
+ - examples/cloudwatch_dashboard/README.md
110
+ - examples/cloudwatch_dashboard/cloudwatch_dashboard.erb
111
+ - examples/cloudwatch_dashboard/cloudwatch_dashboard.png
112
+ - examples/cloudwatch_dashboard/cloudwatch_dashboard.tf
113
+ - examples/cloudwatch_dashboard/terraform_setup.tf
114
+ - examples/json_encoded_hash/json_encoded_hash.erb
115
+ - examples/json_encoded_hash/json_encoded_hash.tf
116
+ - examples/multi_resource_lookup/README.md
117
+ - examples/multi_resource_lookup/multi_resource_lookup.erb
118
+ - examples/multi_resource_lookup/multi_resource_lookup.tf
119
+ - examples/multi_resource_lookup/terraform_setup.tf
120
+ - examples/simple_list/simple_list.erb
121
+ - examples/simple_list/simple_list.tf
122
+ - examples/simple_map/simple_map.erb
123
+ - examples/simple_map/simple_map.tf
124
+ - examples/simple_strings/simple_strings.erb
125
+ - examples/simple_strings/simple_strings.tf
107
126
  - exe/render-template
108
127
  - lib/terraform_template_renderer.rb
109
128
  - lib/terraform_template_renderer/binding.rb