This is setup.tf
data "google_compute_network" "selected" {
name = "${var.network}"
}
It's very basic. I just want to create a network in Google Cloud.
I run this with:
terraform apply -var 'network=net1'
But I still got an error like:
Error: resource 'data.google_compute_network.selected' config: unknown variable referenced: 'network'; define it with a 'variable' block
When I don't use variables in works like expected.
I guess you should have the variable defined to get terraform not complain about it.
variable "network" {
description = "your description goes here"
type = "string/map/list/boolean"
default = "default value here"
}
You can put this in your main file or may be in a separate file called input.tf but it just has to be present in the same directory.
terraform apply -var 'your-var=your-value' will override the value of the default in the variable section.
Terraform Doc: https://www.terraform.io/docs/configuration/variables.html
Related
I'm learning more about terraform and AWS. I've seen a code in Stack overflow- Outputs not displaying when using modules
Main.tf
module "identity-provider" {
source = "./modules/identity-provider"
}
module "saml-role1" {
source = "./modules/saml-roles/"
}
Module file
resource "aws_iam_role" "role1" {
name = "saml-role1"
description = "Blah Blah"
path = "/"
assume_role_policy = "${data.aws_iam_policy_document.assume_role.json}"
permissions_boundary = ""
max_session_duration = 43200
resource "aws_iam_role_policy_attachment" "Read-Only" {
role = "${aws_iam_role.role1.name}"
policy_arn = "arn:aws:iam::aws:policy/ReadOnlyAccess"
}
Output.tf
output "Role1-ARN" {
value = "${module.saml-role1.arn}"
}
My doubt is
What is the significance of output.tf file and how will it affect our code if such a file doesn't exist??
Why output is used (my view):-
Terraform output values allow you to export structured data about your resources.
Outputs are also necessary to share data from a child module to your root module.
to get information about the resources you have deployed.
Output values are similar to return values in programming languages.
What is the significance of output.tf file, According to docs
Output values have several uses:
A child module can use outputs to expose a subset of its resource attributes to a parent module.
A root module can use outputs to print certain values in the CLI output after running terraform apply.
When using remote state, root module outputs can be accessed by other configurations via a terraform_remote_state data source.
Output declarations can appear anywhere in Terraform configuration files. However putting them into a separate file called outputs.tf to make it easier for users to understand your configuration and what outputs to expect from it.
When you apply you can see those values on your terminal, they will be also present in your project's state, use the terraform output command to query all of them using terraform output command
how will it affect our code if such a file doesn't exist??
It will simple not output resource info on command line or a module won't be able to use it, if child module is referencing from parent module
Putting outputs in a file called outputs.tf is just a convention. You don't have to do it. You may as well put your outputs in main.tf. But using outputs.tf can be convenient if your tf scripts are large. Its easy to find and inspects your outputs.
I'm creating a lambda function using an existing module. Currently I refer the static arn inside the step function definition json file. I need to refer it dynamically i.e. at runtime whatever is the arn created. Here's the code:
module "student_lambda"{
source = git#github...// Some git repo
//Other info like vpc, runtime, memory, etc
}
How can I refer this student_lambda arn in my json file for step function?
Here's the json file snippet
"Student lambda response": {
"Type":"Task",
"Resource":"arn:aws:states:::lambda:invoke",
"Parameters":{
"Payload"......// Generic code
"FunctionName":"arn:aws:lambda:us-east-2:..."// Here I want to use something like Student_Lmabda.arn
}}
Note: module is declared in main.tf file. The step function json file is in another folder.
I am assuming the file structure is something like this.
=====================
main.tf
variables.tf
folder with json/
-json file
modules
=====================
In order for us to achieve this, we can create an output of the lambda function that we are creating within the output.tf file in the module.
output "lambda_arn" {
value = aws_lambda.<name of the lambda fn>.arn
}
once this is done we can refer the variable using
"Student lambda response": {
"Type":"Task",
"Resource":"arn:aws:states:::lambda:invoke",
"Parameters":{
"Payload"......
"FunctionName":"${module.student_lambda.lambda_arn}"
}}
I am calling a module (Terraform v0.13.7) and have this statement to determine an AWS SNS Alarm action (if environment is production, use this, otherwise use this):
alarm_sns_topic_arn = var.environment == "production" ? data.terraform_remote_state.outputs.alarm_sns_topic_arn["foo1"] : data.terraform_remote_state.outputs.alarm_sns_topic_arn["foo2"]
When run, I get an error Error: Incorrect attribute value type. The variable alarm_sns_topic_arn is a string type. foo1 and foo2 should resolve to the correct ARN values, and I confirmed that when hardcoding the values it fails as well.
The full error reads:
Error: Incorrect attribute value type
on ../../../modules/aws/elasticache_cluster/cloudwatch.tf line 70, in resource "aws_cloudwatch_metric_alarm" "elasticache_alarm":
70: alarm_actions = var.alarm_sns_topic_arn # This variable is currently a null default
Inappropriate value for attribute "alarm_actions": set of string required.
Banging my head against the wall — what am I missing?
Well, this is embarrassing, and of course makes sense in light of the error:
alarm_actions - (Optional) The list of actions to execute when this alarm transitions into an ALARM state from any other state. Each action is specified as an Amazon Resource Name (ARN).
I simply needed to specify a list type for my variable and enclose the statement in [].
I am trying to define scope in Terraform. I can launch managed rule without scope, it works. But when I am trying to define scope got some error:
Inappropriate value for attribute "compliance_resource_types": set of string
required.
Maybe someone can help to write the scope correctly?
Here is the code for scope :
scope {
compliance_resource_types = "AWS::EC2::SecurityGroup"
}
As the documentation states for compliance_resource_types of resource aws_config_config_rule:
A list of resource types of only those AWS resources that you want to trigger an evaluation for the rule. e.g. AWS::EC2::Instance. You can only specify one type if you also specify a resource ID for compliance_resource_id. See relevant part of AWS Docs for available types.
You are using a single string instead of a list of strings.
The following change should fix your issue:
resource "aws_config_config_rule" "example" {
# ... other configuration ...
scope {
compliance_resource_types = ["AWS::EC2::SecurityGroup"]
}
}
I am trying to do the following:
module “git_file” {
source = "git::https://githubXX.com/abc.js"
}
data "archive_file" “init” {
type = "zip"
git_file = "${module.git_file.source}"
}
I am not able to make the above work. No matter if use https:// or ssh://
How do you source a JS file as a module in terraform?
A module block is for loading Terraform modules and their attending resources into your module under a particular module path. It cannot be used the way you intend.
To call a module means to include the contents of that module into the
configuration with specific values for its input variables. Modules
are called from within other modules using module blocks:
module "servers" {
source = "./app-cluster"
servers = 5
}
Source: Calling a Child Module - Modules- Configuration Language - Terraform Docs
It's somewhat like import, require, or include in other languages. It cannot be used to download a file for use in a Terraform module.
You could use the http data source to do what you describe:
data "http" "git_file" {
url = "https://githubXX.com/abc.js"
}
data "archive_file" “init” {
type = "zip"
git_file = data.http.git_file.body
}
This is also unlikely to work as you expect. You would definitely need a raw source link to GitHub for it.
You should consider an alternative solution involving having abc.js in the same repository or using a null_resource with a local_exec provisioner to download it with a script.
resource "null_resource" "" {
provisioner "local-exec" {
command = "git clone https://github.com/..."
}
}
Then you'll have the files locally for your use the same way you would if you git cloned on your own shell. I don't recommend this. It is brittle and will likely interact strangely with other tools.