CCNA Terraform Modules Questions

65 questions · Terraform Modules topic · All types, answers revealed

1
MCQhard

You have two modules that create resources in different providers. Module A creates a VPC in AWS, Module B creates a Kubernetes cluster that requires the VPC ID. You want to ensure Module B runs after Module A but avoid hardcoding the VPC ID. Which approach is most appropriate?

A.Use a data source in Module B to look up the VPC.
B.Output the VPC ID from Module A and pass it as input to Module B.
C.Use terraform graph to order modules.
D.Use module dependency via depends_on in the root module.
AnswerB

This creates both a data dependency and an ordering requirement, ensuring Module B receives the correct VPC ID.

Why this answer

Option B is correct because using outputs from Module A and passing them as inputs to Module B establishes both ordering and data flow. Option A (depends_on) ensures ordering but does not pass data. Option C (data source) would require the VPC to already exist.

Option D (terraform graph) only visualizes, not enforces.

2
MCQmedium

You have a list of VPC configurations and want to create multiple VPCs using a single module block with for_each. Which statement is true?

A.for_each on a module is not supported.
B.You can use for_each on a module block only if the module is published in the registry.
C.When using for_each, the module's outputs will be a map of output values for each instance.
D.for_each on a module block requires the module to support count.
AnswerC

Each instance's outputs are collected into a map with keys matching the for_each keys.

Why this answer

Option C is correct. When using for_each on a module block, the module's outputs become a map of output values keyed by the for_each keys. Option A is false; for_each works with any module.

Option B is false; for_each does not require count support. Option D is false; for_each is supported on module blocks since Terraform 0.13.

3
MCQhard

An organization stores their Terraform modules in a private Git repository. They need to reference a module that resides in a subdirectory called 'modules/rds' within the repository 'infra-modules' on the main branch. Which source argument should be used?

A.source = "git::https://github.com/org/infra-modules.git//modules/rds"
B.source = "git::https://github.com/org/infra-modules.git"
C.source = "git::https://github.com/org/infra-modules.git:modules/rds"
D.source = "git::https://github.com/org/infra-modules.git//rds"
AnswerA

Correct format: double-slash // separates repository URL from subdirectory path.

Why this answer

The generic Git source format with a double-slash (//) to specify a subdirectory is correct. Option A is wrong because it uses a single slash and would reference the root of the repository. Option C is wrong because the subdirectory path should come after // not before.

Option D is wrong because it uses an incorrect format with a colon before the //.

4
MCQmedium

What is the most likely cause of this error?

A.The module requires a version constraint.
B.The module source path does not exist.
C.The required_version is incompatible with the module.
D.The module input variable 'vpc_id' is not defined in the module.
AnswerB

Correct: the module directory './modules/networking' is missing.

Why this answer

Option C is correct because the error message indicates the module directory does not exist. Option A is incorrect because a version constraint is not relevant for local paths. Option B is incorrect because the required_version is satisfied.

Option D is incorrect because the error is about module sourcing, not variable definition.

5
Multi-Selecthard

Which THREE of the following are valid ways to reference a module output value within the same Terraform configuration?

Select 3 answers
A.In the count or for_each of another module or resource.
B.In a resource argument, e.g., subnet_id = module.vpc.public_subnet_ids
C.In a data source definition as a filter.
D.In a provider block to set endpoints.
E.In a locals block to perform transformations.
AnswersA, B, E

Module outputs can control the number of instances or the iteration set of other resources.

Why this answer

Options A, B, and D are correct. A: Direct reference in resource arguments. B: Use in count or for_each arguments of resources.

D: Use in locals block for complex expressions. C is wrong because module outputs aren't used in provider configurations. E is wrong because data sources are for external data, not module outputs.

6
MCQhard

A large organization uses Terraform to manage infrastructure across multiple AWS accounts. They have a shared module for VPC stored in a private Git repository (git::https://github.com/org/terraform-aws-vpc.git?ref=v1.0.0). After updating the module source to ref=v1.2.0, they run terraform init and then terraform plan. The plan still shows the old module's resources and behavior. They confirm the new tag exists and the module code has changed. The root module source line is correct. What is the most likely cause?

A.They forgot to run terraform get.
B.The module source URL is incorrect.
C.Terraform cached the previous module version and did not download the new one.
D.The module's outputs changed and they need to update the root module.
AnswerC

Terraform caches modules; running terraform init with -upgrade or clearing the .terraform directory forces a fresh download.

Why this answer

Option C is correct. Terraform caches modules locally; after changing the source ref, terraform init must be run to download the new version. If the user forgot to include the -upgrade flag or did not clean the cache, Terraform may use the cached version.

Option A is not a standard command. Option B would cause an error. Option D (output changes) would not cause the plan to show old behavior if the module code is new.

7
Multi-Selectmedium

Which TWO module source types support version constraints in Terraform?

Select 2 answers
A.HTTP URL to a zip archive
B.Terraform Public Registry
C.Local file path
D.Git URL with a branch reference
E.Terraform Cloud Private Registry
AnswersB, E

The public registry allows version constraints like >= 1.0.0, ~> 2.0.

Why this answer

Only module registries (public and private) support version constraints. Local paths, Git URLs with branches, and HTTP URLs do not support version constraints because they point directly to a specific version. Option C and D and E are wrong for not supporting version constraints.

8
MCQhard

A DevOps team manages Terraform configurations for a multi-environment infrastructure (dev, staging, prod). They maintain a central repository of reusable modules stored in a Git repository. Developers often update modules in the master branch to add features or fix bugs. Recently, after a developer updated the 'vpc' module in the master branch, the staging environment's infrastructure was destroyed and recreated during a terraform apply, causing an outage. The team needs to prevent such unintended changes across environments. They currently reference modules using the source argument with a git URL pointing to the master branch: source = "git::https://github.com/org/terraform-modules//vpc?ref=master". The team is looking for a solution that allows controlled updates and ensures each environment uses a fixed version of a module until explicitly upgraded.

A.Use module version constraints in the configuration, such as source = "git::https://github.com/org/terraform-modules//vpc?ref=v1.0.0" and update the ref tag when ready.
B.Create separate Git branches for each environment and reference the branch in the module source.
C.Use Terragrunt to manage module dependencies and lock versions.
D.Use the Terraform Registry to host modules with semantic versioning and pin versions.
AnswerA

Correct: pinning to a specific tag ensures each environment uses a fixed version until explicitly updated.

Why this answer

Option D is correct because pinning to a specific Git tag ensures that each environment uses a known, fixed version of the module until the tag is updated. Option A is incorrect because using separate branches still exposes environments to changes in those branches. Option B is incorrect because setting up a registry is a larger undertaking and not an immediate fix.

Option C is incorrect because Terragrunt is an external tool that adds complexity without directly solving the version pinning issue in a native Terraform way.

9
MCQmedium

Your company manages infrastructure for multiple environments (dev, staging, prod) using Terraform. You have a shared networking module stored in a private Git repository. The module is used by several root configurations. The current workflow requires developers to manually update the module version in each root module's source attribute when a new version is tagged. This has led to configuration drift and occasional use of incompatible module versions. You want to implement a more reliable approach that ensures all environments use the same consistent version of the module, while still allowing controlled upgrades. Which approach best addresses this concern?

A.Publish the module to the public Terraform Registry and use a version constraint in each root module.
B.Pin each root module to a specific Git tag (e.g., ref=v1.2.3) and manually update each root module when a new tag is created.
C.Remove the version constraint from the module source so that Terraform always fetches the latest commit from the default branch.
D.Use a version constraint like "~> 1.2" in the module source and adopt a workflow to update the constraint across all root modules simultaneously only when ready.
AnswerD

This allows controlled updates: patch updates are automatic, but major/minor updates require explicit version constraint changes across all environments.

Why this answer

Option D is correct because it uses a version constraint (e.g., `~> 1.2`) to allow automatic patch-level updates while preventing major or minor breaking changes, and it enforces a coordinated workflow where all root modules update the constraint simultaneously. This eliminates configuration drift and ensures consistent module versions across environments, while still enabling controlled upgrades. The approach leverages Terraform's built-in version constraint syntax to balance consistency with flexibility.

Exam trap

HashiCorp often tests the misconception that removing version constraints or using the latest commit is a valid way to ensure consistency, but the trap here is that this actually introduces unpredictability and breaks controlled upgrades, which is the opposite of what the scenario requires.

How to eliminate wrong answers

Option A is wrong because publishing to the public Terraform Registry is not required for version control; it also introduces security and compliance risks by exposing private infrastructure code publicly. Option B is wrong because pinning each root module to a specific Git tag and manually updating each one does not solve the drift problem—it perpetuates the same manual, error-prone process described in the scenario. Option C is wrong because removing the version constraint and always fetching the latest commit from the default branch eliminates all control over upgrades, leading to unpredictable breaking changes and no ability to coordinate updates across environments.

10
MCQhard

A module block references a module with version constraint '>= 2.0, < 3.0'. An older version 1.5 is already cached from a previous init. The team wants to ensure they use a newer version. After running terraform init -upgrade, what happens?

A.Terraform upgrades to version 3.0 because it is the latest.
B.Terraform returns an error because version 1.5 is incompatible with the constraint.
C.Terraform uses the cached version 1.5 because it is already present.
D.Terraform upgrades to the latest version in the range 2.x that is not yet cached.
AnswerD

The -upgrade flag forces Terraform to download the newest version matching the constraint.

Why this answer

Option B is correct because terraform init -upgrade re-checks the source and uses the latest version matching the constraint. Option A is wrong because it ignores the cache if -upgrade is used. Option C is wrong because it will upgrade within constraint.

Option D is wrong because no error occurs.

11
MCQhard

A team renamed a module from 'module.network' to 'module.vpc' in their configuration. They run 'terraform plan' and see that Terraform wants to destroy the old network resources and create new ones. They want to preserve the existing resources without downtime. What should they do?

A.Add a 'moved' block to the configuration to map the old module address to the new one.
B.Use 'terraform state mv' to move the resources to the new module address.
C.Update the module source to a new version.
D.Accept the destroy and recreate since it's the only way.
AnswerA

The 'moved' block tells Terraform to treat the renamed module as the same set of resources, preventing destroy/recreate.

Why this answer

Using the 'moved' block is the recommended way to refactor module names without destroying/recreating resources. Option A is wrong because 'terraform state mv' would also work but requires manual commands; 'moved' is declarative. Option B is wrong because changing the source would change the module content, not just the name.

Option C is wrong because destroying and recreating causes downtime.

12
MCQhard

Which module source type does NOT support version constraints?

A.Local path
B.HTTP URL
C.Git repository
D.Terraform Registry
AnswerA

Local paths are not versioned; they reference a specific directory without version constraints.

Why this answer

Option B is correct. Local path sources (e.g., ./modules/foo) do not support version constraints because they are directly referenced without versioning. Registry, Git, and HTTP sources all support version constraints (via ref, tag, or semver).

13
MCQhard

A developer runs `terraform plan` and receives the error: "Error: Unsupported argument; An argument named 'enable_vpn_gateway' is not expected here." What is the most likely cause?

A.The source address is misspelled 'vpc' instead of 'vpc/aws'.
B.The source module is not pinned to a specific version, so it may have changed.
C.The module must be sourced from a different registry or repository.
D.The module version 5.0.0 does not support the 'enable_vpn_gateway' argument.
AnswerD

The error clearly states the argument is not expected; it was likely removed in that version.

Why this answer

Option D is correct because the error 'Unsupported argument' indicates that the module version currently in use does not define an input variable named 'enable_vpn_gateway'. In Terraform, each module version has a fixed set of input variables; if you attempt to pass an argument that is not declared in the module's variables.tf, Terraform will reject it. The most common reason for this is that the module version has been updated or changed, and the argument was removed or renamed in that version.

Exam trap

HashiCorp often tests the distinction between errors caused by module version changes versus errors caused by source configuration issues, trapping candidates who confuse a missing variable error with a source path or registry problem.

How to eliminate wrong answers

Option A is wrong because the error message specifically says 'An argument named 'enable_vpn_gateway' is not expected here', which is about an unexpected argument, not about a misspelled source address; a misspelled source would cause a 'source not found' or 'module not found' error. Option B is wrong because while not pinning a version can lead to unexpected changes, the error itself is about the current module's input schema, not about version drift; the error would occur even if the version is pinned to a version that lacks the argument. Option C is wrong because the source registry or repository does not affect which arguments are supported; the argument support is determined by the module's code, not its location.

14
MCQmedium

A developer creates a module in a subdirectory of their Terraform configuration and wants to reference it from the root module. The directory structure is: /terraform-project/modules/networking. Which source argument should they use in the module block?

A.source = "file:///terraform-project/modules/networking"
B.source = "/terraform-project/modules/networking"
C.source = "./modules/networking"
D.source = "hashicorp/networking/aws"
AnswerC

Correct relative path to the local module subdirectory.

Why this answer

A relative path starting with ./ is the correct way to reference a local module in a subdirectory of the root configuration. Option B is wrong because absolute paths are platform-dependent and not recommended. Option C is wrong because file:/// scheme is used for absolute file URIs, not relative.

Option D is wrong because using the registry path would try to download from an external source, not local.

15
MCQmedium

A developer creates a directory structure with a module located at './modules/networking'. The root configuration references it with source = './modules/networking'. What is the behavior when running terraform init from the root directory?

A.Terraform uses the module directly from the local filesystem.
B.Terraform requires a network connection to verify the module.
C.Terraform attempts to download the module from the public registry.
D.Terraform returns an error because the module path is not absolute.
AnswerA

When the source is a relative or absolute path, Terraform reads the module from that directory.

Why this answer

Option C is correct because local path modules are detected automatically without registry. Option A is wrong because local paths don't require registry. Option B is wrong because no internet needed.

Option D is wrong because it will be found.

16
MCQeasy

A Terraform module defines an output 'instance_ips'. In the root module, how should this value be referenced?

A.var.instance_ips
B.local.instance_ips
C.resource.my_module.instance_ips
D.module.my_module.instance_ips
AnswerD

This is the correct syntax to access an output from a module named 'my_module'.

Why this answer

Option A is correct because module outputs are referenced as module.<module_name>.<output_name>. Option B is wrong because var is for input variables. Option C is wrong because resource references are different.

Option D is wrong because local is for local values.

17
MCQmedium

A team is using a private module registry from a third-party vendor. When running terraform init, they receive an error: 'Error downloading module: could not download module... server responded with 401 Unauthorized'. What is the most likely cause?

A.The module source URL is incorrect.
B.The registry credentials are missing or invalid.
C.The Terraform version is too old for the module.
D.The network firewall is blocking outbound connections.
AnswerB

A 401 response specifically indicates authentication failure; the client must provide valid credentials to access the registry.

Why this answer

The 401 Unauthorized error indicates authentication failure. Option B is correct because the module registry requires valid credentials, and they are missing or incorrect. Option A is wrong because registry URL typo usually gives a 404 or connection timeout.

Option C is wrong because network firewall usually gives connection refused or timeout. Option D is wrong because Terraform version incompatibility gives a different error about required_version.

18
MCQhard

What is the correct way to resolve this provider version conflict?

A.Ignore the module's required_providers and force install the root version.
B.Remove the required_providers block from the root module.
C.Change the root module's required version to ~> 2.70.
D.Manually edit the .terraform/modules/consul/main.tf to change the version.
AnswerC

This aligns the root with the module's requirement, solving the conflict.

Why this answer

The conflict arises because the module requires a provider version (~> 2.70) that is incompatible with the root's requirement (>= 3.0). The best solution is to update the module's required provider version, if possible, to be compatible with the root. Option A is wrong because removing the root constraint may allow a version that satisfies both, but it's better to update the module.

Option B is wrong because downgrading the root version to 2.x may lose features. Option D is wrong because manually editing .terraform is not supported.

19
MCQeasy

A developer wants to create multiple instances of a module that provisions a single EC2 instance. They want to create 3 EC2 instances. Which approach is most efficient and concise?

A.Set the source argument to a list of three URLs.
B.Use the 'count' meta-argument in the module block.
C.Use the 'for_each' meta-argument with a list of numbers.
D.Copy the module block three times with different names.
AnswerB

count allows creating multiple instances of the module efficiently.

Why this answer

Using 'count' in the module block is the recommended way to create multiple instances of a module. Option B is wrong because copying the module block three times is not DRY. Option C is wrong because for_each requires a map or set of strings, not just a number.

Option D is wrong because a module can only have one source; you cannot specify a list of sources.

20
MCQeasy

After adding a new module sourced from a Git repository with a specific tag, terraform init reports that the module is being downloaded. What is the best practice to ensure the team uses the same version of this module consistently?

A.Use a version constraint in the module block, e.g., version = 1.0.0.
B.Specify the source as the branch name 'main'.
C.Use the 'latest' tag in the source URL.
D.Use a Git tag, like '?ref=v1.0.0', to pin the version.
AnswerD

Tags are immutable references in Git; pinning to a specific tag ensures every team member uses the exact same code.

Why this answer

Option C is correct because using a specific Git tag ensures version control and reproducibility. Option A is wrong because 'latest' tag is not deterministic. Option B is wrong because branch names change over time.

Option D is wrong although version constraints work with registries, not Git sources directly without metadata.

21
Multi-Selecthard

Which THREE practices are recommended when using Terraform modules? (Select THREE.)

Select 3 answers
A.Design modules to have a single clear purpose.
B.Use version constraints when referencing modules from a registry.
C.Output important resource attributes that consumers may need.
D.Hardcode provider-specific details like region inside the module to simplify usage.
E.Create a new module for each individual resource type.
AnswersA, B, C

Single-responsibility modules are easier to reuse and test.

Why this answer

Option A is correct because Terraform modules should follow the single-responsibility principle: each module should encapsulate a clear, focused purpose (e.g., provisioning a VPC, an EC2 instance, or a database). This makes modules reusable, testable, and easier to compose. A module that tries to do too many things becomes brittle and hard to maintain.

Exam trap

HashiCorp often tests the misconception that modules should be as granular as possible (one per resource type) or that hardcoding provider details simplifies usage, when in fact both practices reduce reusability and violate Terraform best practices.

22
Multi-Selecthard

Which THREE statements about module configuration are correct?

Select 3 answers
A.Module sources can be local paths or remote URLs.
B.Version constraints can be specified for any module source.
C.The outputs of a module are available after apply only.
D.A module block can contain multiple resources and child modules.
E.Module inputs can be optional if the module uses a default.
AnswersA, D, E

Terraform supports various source types including local, registry, Git, HTTP, etc.

Why this answer

Options A, B, and E are correct. Module sources can be local paths or remote URLs (A). A module block can contain multiple resources and even child modules (B).

Module inputs can be optional if the module defines a default value (E). Option C is false because outputs from a module can be known during planning (using terraform plan) if the values are deterministic. Option D is false because not all source types support version constraints (e.g., local paths).

23
Multi-Selectmedium

Which TWO statements are correct when refactoring a monolithic Terraform configuration into modules?

Select 2 answers
A.All modules must reside in a separate directory outside the root module.
B.A module should contain only one resource to keep it simple.
C.Module outputs are necessary to expose values to the root module.
D.Variables are optional in modules if hardcoded values are acceptable.
E.Modules help to organize and reuse infrastructure code.
AnswersC, E

Outputs are the mechanism for a module to return values to the calling module.

Why this answer

Options A and D are correct. A: Moving related resources into modules encapsulates complexity. D: Outputs allow root module to access values.

B is wrong because modules can be in same directory; C is wrong because variables are required for customization. E is wrong because modules can have many resources.

24
Multi-Selecteasy

Which TWO options are valid ways to reference a Terraform module from a registry?

Select 2 answers
A.source = "hashicorp/consul/aws"
B.source = "consul/aws"
C.source = "hashicorp/consul/aws" version = "~> 0.1"
D.from = "hashicorp/consul/aws"
E.source = "hashicorp/consul/aws?ref=v1.0.0"
AnswersA, C

Correct; omitting the version defaults to the latest.

Why this answer

Option A is correct because the Terraform registry module source syntax requires the format `namespace/name/provider`, and `hashicorp/consul/aws` follows this exactly. This tells Terraform to fetch the module from the public registry, using the `hashicorp` namespace, the `consul` module name, and the `aws` provider. The `version` constraint in option C is also valid, as it pins the module to a compatible version range using the `~>` operator, which is a standard Terraform version constraint syntax.

Exam trap

HashiCorp often tests the distinction between registry module syntax and Git-based module references, so the trap here is that candidates mistakenly apply Git-style `?ref=` syntax to registry modules, not realizing that registry modules require the `version` argument instead.

25
MCQhard

A module defines an input variable with 'sensitive = true'. The root module tries to use that variable in an output block. What happens when running 'terraform apply'?

A.The output value is hidden in the CLI output but still available in the state.
B.The apply fails with an error because sensitive variables cannot be used in outputs.
C.The output is displayed normally because outputs are always visible.
D.The output is removed from the plan entirely to protect the sensitive value.
AnswerA

Terraform masks sensitive values in CLI output, but they are stored in the state.

Why this answer

Sensitive variables are obfuscated in the command line output. Option A is wrong because terraform apply will succeed; the value is just hidden. Option B is wrong because the output is not removed, just masked.

Option D is wrong because the variable is still available programmatically.

26
MCQhard

After running 'terraform apply', the user sees that the 'aws_s3_bucket_object' is created successfully, but the bucket name is not as expected. What is the most likely reason?

A.The module variable 'bucket_name' is not consumed by the resource; the resource uses a hardcoded name.
B.The module output is incorrectly defined; it should use 'bucket' attribute instead of 'id'.
C.The module does not have an output for the bucket name, so the reference fails silently.
D.The output 'bucket_name' in the module is set to 'aws_s3_bucket.this.id', which is the bucket name, so the bucket name should be as expected.
AnswerD

The configuration appears correct; if the bucket name is not as expected, the issue might be elsewhere, but the output is correct.

Why this answer

Option D is correct because the module output 'bucket_name' is defined as 'aws_s3_bucket.this.id', and in Terraform, the 'id' attribute of an 'aws_s3_bucket' resource is exactly the bucket name (not a generated ID). Since the user sees the object created successfully, the module is being called and the output is correctly referencing the bucket name, so the bucket name should be as expected. The question implies the user's expectation is wrong or the bucket name is actually correct, making D the only statement that aligns with Terraform's behavior.

Exam trap

HashiCorp often tests the misconception that 'id' is a random or internal identifier rather than the actual resource name, leading candidates to incorrectly think the output is wrong when it is actually correct.

How to eliminate wrong answers

Option A is wrong because if the resource used a hardcoded name, the bucket would still be created with that name, but the user would see a mismatch only if they expected a different name; the module variable not being consumed would cause a different bucket name, but the question states the bucket name is 'not as expected', not that it failed. Option B is wrong because the 'bucket' attribute of 'aws_s3_bucket' is the bucket name as well, but using 'id' is also correct and does not cause a mismatch; the output definition is not the issue here. Option C is wrong because if the module had no output for the bucket name, the reference would fail with an error during 'terraform apply', not silently succeed; Terraform requires explicit outputs to be defined for module references.

27
MCQmedium

A root module uses a module that creates an AWS EC2 instance. The module outputs the instance ID. The root module then uses this output in a null_resource provisioner. After modifying the module, terraform plan shows that the EC2 instance will be destroyed and recreated. What is the impact on the null_resource?

A.The null_resource prompts the user to confirm before any changes.
B.The null_resource will remain unchanged because it is not directly attached to the module.
C.The null_resource will fail to run because the output is temporarily unavailable during destroy.
D.The null_resource will be destroyed and recreated alongside the EC2 instance.
AnswerD

The null_resource depends on the module output, so any change in the output value forces recreation.

Why this answer

Option A is correct because the null_resource depends on the output, so when the module instance is destroyed and recreated, the output value changes, triggering destruction and recreation of the null_resource. Option B is wrong because it will be recreated. Option C is wrong because the dependency is implicit through the output.

Option D is wrong because module dependency is automatically inferred.

28
MCQeasy

A company uses a Terraform module from the registry for AWS VPC (source = "terraform-aws-modules/vpc/aws", version = "3.0.0"). They updated the module version to "3.1.0" and ran terraform plan. To their surprise, the plan shows that all VPC resources will be replaced (destroyed and recreated) instead of updated in place. They did not change any input variables. The module's release notes mention only bug fixes and minor improvements. What is most likely causing the full resource replacement?

A.The module's new version introduced a new required variable.
B.The module's new version changed the default CIDR block.
C.The module's new version uses a different provider version.
D.The module's new version changed the resource names or identifiers.
AnswerD

Renaming resources within a module causes them to be seen as entirely new, triggering destroy and create.

Why this answer

Option A is most likely because the newer version might have changed resource names (e.g., from aws_vpc.main to aws_vpc.this), causing Terraform to see old resources as removed and new ones to create. Option B would only cause replacement if they changed the CIDR variable, which they did not. Option C (provider version) usually does not force replacement unless there are incompatible schema changes.

Option D (new required variable) would cause an error, not a plan showing changes.

29
Multi-Selectmedium

Which TWO statements about Terraform module sources are correct? (Select TWO.)

Select 2 answers
A.A module source can be a local file system path.
B.Modules can only be sourced from the public Terraform Registry.
C.Running 'terraform plan' automatically downloads any missing modules.
D.A module source can be a Git repository URL using the SSH protocol.
E.The module source is defined in a separate 'source' block within the module.
AnswersA, D

Local paths are valid module sources.

Why this answer

Option A is correct because Terraform allows module sources to be local file system paths, enabling you to reference modules stored on your local machine. This is useful for developing and testing modules before publishing them, and the path can be relative or absolute, such as `./modules/my-module` or `/home/user/modules/my-module`.

Exam trap

HashiCorp often tests the misconception that `terraform plan` handles module downloads, when in fact only `terraform init` performs this action, and that modules are limited to the public registry, ignoring local paths and private Git sources.

30
MCQhard

Your team is developing a custom module for creating EC2 instances with attached EBS volumes. The module variables are: instance_type (default "t2.micro"), ami (required), volume_size (default 8), volume_type (default "gp2"). Another team uses this module to create a web server. In their root module, they call the module without any explicit instance_type override, but they do set other variables. After applying, the web server is created with instance_type "t2.nano" instead of the expected "t2.micro". They confirm that the module still has the default "t2.micro". What is the most likely explanation?

A.The module's instance_type variable uses a default that is "t2.nano" but the root module overrode it with a variable from its own context.
B.The instance_type variable is not defined in the module's variables.tf, so it uses a default from the AWS provider.
C.The root module has a variable called instance_type set to "t2.nano" that is being passed to the module.
D.The module's variable default was changed to "t2.nano" in a new version.
AnswerC

If the root module defines or inherits an instance_type variable with value "t2.nano", and the module block passes it (e.g., instance_type = var.instance_type), that overrides the module's default.

Why this answer

Option B is correct. The root module likely has a variable named instance_type (perhaps declared elsewhere or from a parent module) that is being passed implicitly or explicitly to the module. Even if not explicitly set in the module block, if the root module's configuration includes something like `instance_type = var.instance_type` and that variable defaults to "t2.nano", it would override the module's default.

Option A is contradicted by the scenario. Option C would cause an error. Option D is confusing; the module default is not being used.

31
MCQeasy

A module 'web_app' defines an input variable 'instance_count' with type = number and a validation block ensuring it is between 1 and 10. What happens if a user sets instance_count = 0?

A.Terraform returns an error during validation and stops execution.
B.Terraform applies the module with zero instances, as a value of 0 is allowed.
C.Terraform ignores the validation if the variable is explicitly set.
D.Terraform uses the default value for instance_count from the module.
AnswerA

Custom validation conditions are checked during planning; if the condition fails, Terraform outputs an error.

Why this answer

Option B is correct because the validation rule will fail, causing Terraform to return an error during plan or apply. Option A is wrong because validation occurs before apply. Option C is wrong because the validation block overrides default.

Option D is wrong because the default is irrelevant if a value is provided.

32
MCQeasy

Refer to the exhibit. The configuration fails with an error indicating that the module does not support the 'enable_vpn_gateway' argument. What is the most likely cause?

A.The argument name is misspelled; it should be 'enable_vpn' instead.
B.The module version '3.18.0' does not include the 'enable_vpn_gateway' variable; it was added in a later version.
C.The module does not support VPN gateways at all.
D.The module source is incorrectly specified; it should use a git URL instead of the registry path.
AnswerB

Pinning to an exact older version causes missing variable error.

Why this answer

Option B is correct because the error message indicates that the module does not support the 'enable_vpn_gateway' argument. In Terraform, module arguments are defined by the module's published variables. The module version '3.18.0' predates the introduction of the 'enable_vpn_gateway' variable, which was added in a later version.

Upgrading the module version to one that includes this variable resolves the error.

Exam trap

HashiCorp often tests the concept that module arguments are version-dependent, and the trap here is that candidates may assume the argument name is misspelled or that the module lacks the feature entirely, rather than recognizing that the module version simply does not include that variable yet.

How to eliminate wrong answers

Option A is wrong because the argument name 'enable_vpn_gateway' is not a misspelling of 'enable_vpn'; the error specifically states the module does not support the argument, not that the name is incorrect. Option C is wrong because the module does support VPN gateways, but the specific variable 'enable_vpn_gateway' was not available in version 3.18.0. Option D is wrong because the module source (registry path) is correctly specified; using a git URL would not change the available variables for a given module version.

33
Multi-Selectmedium

You are developing a module. Which TWO actions are recommended best practices?

Select 2 answers
A.Use the same provider configuration as the root module.
B.Use local values to simplify expressions.
C.Hardcode default values for all variables.
D.Define outputs for all resources created.
E.Use absolute paths in module source.
AnswersB, D

Locals help avoid repeating complex expressions and improve code readability.

Why this answer

Options B and C are correct. Defining outputs for important resources (B) allows consumers to access module results. Using local values (C) simplifies expressions and improves readability.

Option A (hardcoding defaults) reduces flexibility. Option D (absolute paths) makes modules less portable. Option E is unnecessary because provider configurations are inherited.

34
MCQeasy

Which version of the module was downloaded and why?

A.3.0.0, because ~> 3.0 only allows the exact version 3.0.0.
B.3.19.0, because it is the latest version and version constraints are ignored.
C.3.19.0, because it is the latest version matching the constraint ~> 3.0, which allows any 3.x version.
D.3.0.0, because ~> 3.0 is limited to patch updates within 3.0.x.
AnswerC

The constraint ~> 3.0 permits all versions 3.0.0 up to (but not including) 4.0.0.

Why this answer

The version constraint ~> 3.0 allows any version in the 3.x range, and 3.19.0 is the latest version within that constraint at the time of init. Option B is wrong because '~> 3.0' does not allow 3.0.0 only; it allows all 3.x versions. Option C is wrong because 3.19.0 is higher than 3.0.0, but still matches.

Option D is wrong because the constraint does not limit to patch updates; it allows minor updates as well (since '~> 3.0' is equivalent to '>= 3.0, < 4.0').

35
MCQeasy

After applying a module that creates a VPC, a user wants to use the VPC ID in another resource within the root configuration. How should they reference the output from the module?

A.vpc_id = module.vpc.vpc_id
B.vpc_id = module_vpc.vpc_id
C.vpc_id = data.module.vpc.vpc_id
D.vpc_id = local.vpc_id
AnswerA

Correct syntax to reference an output named 'vpc_id' from a module named 'vpc'.

Why this answer

Module outputs are accessed using the syntax module.<MODULE_NAME>.<OUTPUT_NAME>. Option A is wrong because it uses a dot but without the module prefix. Option B is wrong because it uses a local variable syntax.

Option D is wrong because it uses data source syntax.

36
Multi-Selecteasy

Which TWO of the following are valid ways to reference a module from the Terraform Registry?

Select 2 answers
A.source = "hashicorp/consul"
B.source = "github.com/hashicorp/terraform-aws-consul"
C.source = "hashicorp/consul/aws"
D.source = "terraform-aws-modules/vpc/aws"
E.source = "./modules/consul"
AnswersC, D

This is a valid registry module reference with namespace, module, and provider.

Why this answer

Options A and C are correct because the Terraform Registry uses the format <namespace>/<module>/<provider>. Option A (hashicorp/consul/aws) and C (terraform-aws-modules/vpc/aws) follow this pattern. Option B is a Git URL.

Option D is a local path. Option E is missing the provider component.

37
MCQhard

You are managing a Terraform configuration that uses a public module from the registry to deploy an AWS VPC. The module is defined with a version constraint of '~> 3.0'. After running 'terraform init', you run 'terraform plan' and notice that the plan output indicates the module will be updated from version 3.18.0 to 3.20.1. However, you are concerned because the module's changelog shows that version 3.19.0 introduced a breaking change: it removed the 'enable_dns_hostnames' variable and replaced it with 'enable_dns_support'. Your configuration currently uses the 'enable_dns_hostnames' variable. You want to avoid any breaking changes in the production environment while still receiving non-breaking updates. What should you do?

A.Fork the module repository and maintain a custom version that retains the 'enable_dns_hostnames' variable.
B.Change the version constraint to ">= 3.0.0, < 3.19.0" and run 'terraform init -upgrade'.
C.Change the version constraint to "~> 3.18.0" to stay within the 3.18.x releases.
D.Update the configuration to use the new 'enable_dns_support' variable and update the module to version 3.20.1.
AnswerC

This pins to the 3.18.x range, avoiding the breaking change in 3.19.0 while still getting patch updates.

Why this answer

Option C is correct because the version constraint '~> 3.18.0' restricts updates to only patch versions within the 3.18.x series (e.g., 3.18.1, 3.18.2), which will never include the breaking change introduced in 3.19.0. This allows you to receive non-breaking bug fixes and security patches while avoiding the removal of the 'enable_dns_hostnames' variable. The pessimistic version constraint operator (~>) in Terraform locks the major and minor version when specified with three segments, ensuring no unexpected breaking changes from higher minor versions.

Exam trap

HashiCorp often tests the nuance of the pessimistic version constraint operator (~>) in Terraform, specifically that '~> 3.0' and '~> 3.18.0' have very different behaviors, and candidates mistakenly assume both only allow patch updates.

How to eliminate wrong answers

Option A is wrong because forking the module and maintaining a custom version introduces unnecessary overhead and defeats the purpose of using a public module; it also bypasses the version constraint mechanism entirely. Option B is wrong because the constraint '>= 3.0.0, < 3.19.0' would still allow Terraform to upgrade to any version from 3.0.0 up to 3.18.x, but running 'terraform init -upgrade' would upgrade to the latest allowed version (3.18.x), which is safe, but the constraint is overly broad and does not leverage the pessimistic operator for precise control; more importantly, it would not prevent a future upgrade to 3.19.0 if the upper bound were accidentally removed. Option D is wrong because updating the configuration to use 'enable_dns_support' and upgrading to 3.20.1 would require rewriting your code to adapt to the breaking change, which contradicts the goal of avoiding breaking changes in production.

38
Multi-Selecteasy

Which TWO statements about Terraform modules are correct?

Select 2 answers
A.The count meta-argument is not supported on module blocks.
B.Module outputs are automatically available as inputs to other modules in the same configuration.
C.Module sources must include a version constraint to ensure reproducibility.
D.A module can be called multiple times in the same configuration with different input variables.
E.The source attribute of a module can be a Git repository URL with a specific commit SHA.
AnswersD, E

Correct: modules can be invoked multiple times with different inputs.

Why this answer

Option A is correct because a module can be called multiple times with different inputs. Option E is correct because Git URLs with a commit SHA are valid module sources. Option B is incorrect because version constraints are optional.

Option C is incorrect because count and for_each are supported on module blocks. Option D is incorrect because module outputs must be explicitly referenced.

39
MCQeasy

A team is using a module from the Terraform Registry and wants to ensure they always get the latest patch version of the 3.2.x series. Which version constraint should they use?

A.~> 3.2
B.3.2.*
C.~> 3.2.0
D.>= 3.2, < 4.0
AnswerC

This allows only patch-level increments within 3.2.x (e.g., 3.2.0 to 3.2.1).

Why this answer

Option C is correct because the pessimistic constraint operator ~> with three parts (e.g., ~> 3.2.0) allows only patch-level changes (3.2.0, 3.2.1, etc.). Option A (~> 3.2) allows minor version updates (3.3, 3.4). Option B (>= 3.2, < 4.0) also allows minor updates.

Option D is invalid syntax.

40
MCQhard

A developer creates a module that provisions an AWS EC2 instance and an S3 bucket. The module outputs the instance ID and bucket ARN. When using this module, the root configuration references module.my_module.instance_id and module.my_module.bucket_arn. After running terraform apply, they notice that the bucket ARN is empty. What is the most likely cause?

A.The output is defined in the module but not in the root configuration.
B.The S3 bucket creation depends on another resource that hasn't been created yet.
C.The output value in the module is defined incorrectly, e.g., referencing a non-existent attribute.
D.The IAM role used by Terraform does not have permission to read the bucket ARN.
AnswerC

A misdefined output evaluates to empty or null, leading to an empty value.

Why this answer

Option C is correct because the most likely cause of an empty output value is that the output block in the module references an attribute that does not exist on the resource. For example, if the output is defined as `output "bucket_arn" { value = aws_s3_bucket.my_bucket.arn }` but the resource is actually `aws_s3_bucket.my_bucket` and the correct attribute is `arn`, a typo like `arnn` or `id` would cause Terraform to return an empty string (or an error during plan). Terraform validates attribute references at plan time, but if the attribute is missing or misspelled, the output value will be empty or cause a failure.

Exam trap

HashiCorp often tests the misconception that missing outputs in the root configuration cause empty values, but the real issue is almost always a misconfigured output block in the module itself, such as referencing a wrong attribute name.

How to eliminate wrong answers

Option A is wrong because outputs defined in the root configuration are not required to reference module outputs; the root configuration can directly use module outputs without redefining them. Option B is wrong because dependency ordering does not cause an output to be empty; if the S3 bucket depends on another resource, Terraform will wait for that resource to be created before reading the bucket's attributes, so the output would still be populated. Option D is wrong because IAM permissions affect the ability to create or describe resources, not the ability to read an attribute that is already part of the Terraform state; the bucket ARN is computed by the provider and stored in state, so no read permission is needed to output it.

41
MCQmedium

A team has a root module that calls a local module using count to conditionally create an AWS RDS instance based on a boolean variable `rds_enabled`. The root module sets `rds_enabled` to the value of a data source that checks if a tag exists on an S3 bucket. The relevant code is: `count = var.rds_enabled ? 1 : 0`. When they run terraform plan, they receive the error: "Error: Invalid count argument: The count value is not yet known". The S3 bucket already exists. What is the underlying issue?

A.Data sources cannot be used in a count condition.
B.The count in a module block cannot depend on a data source.
C.The count value must be known before planning, but data sources are not evaluated until apply without a refresh.
D.The module does not support count.
AnswerC

Terraform needs a known value for count during planning; data sources are not refreshed until apply by default, causing unknown values.

Why this answer

Option C is correct. The count value must be known during planning, but data sources are typically read during the refresh phase of apply (or plan if -refresh-only is used), and if the data source depends on managed resources, it may be unknown. However, in this case, the S3 bucket exists, but Terraform still cannot guarantee the value without refreshing.

The root cause is that data sources are not evaluated before planning unless Terraform performs a refresh, which may require existing state. Option A is false because data sources can be used in count. Option B is false because count works with modules.

Option D is false because modules do support count.

42
Multi-Selectmedium

Which three of the following describe correct practices or behaviors when interacting with Terraform modules? (Choose three.)

Select 3 answers
.A module source can be a local file path, such as './modules/networking'.
.The `terraform get` command downloads and updates module sources from remote registries.
.Module outputs are accessible from the root configuration using the syntax `module.<MODULE_NAME>.<OUTPUT_NAME>`.
.Terraform modules can only be sourced from the public Terraform Registry.
.When using a module from a Git repository, Terraform automatically applies any local changes made inside the `.terraform/modules` directory.
.Module input variables are automatically populated from environment variables without explicit variable declarations.

Why this answer

Option null is correct because Terraform modules can be sourced from a local file path using the `source` argument, such as `'./modules/networking'`, which allows referencing modules stored within the same repository or filesystem. This is a fundamental feature for organizing infrastructure code without relying on remote registries.

Exam trap

HashiCorp often tests the misconception that modules can only come from the public Terraform Registry, but the exam expects you to know that local paths, Git repos, and HTTP URLs are also valid sources.

43
MCQeasy

Based on the error, what is the most likely reason the 'acl' argument is not expected?

A.The module version currently installed does not have an 'acl' variable.
B.The argument name is misspelled; it should be 'acl_control'.
C.The module requires the 'acl' to be set inside a separate block.
D.The 'bucket' argument is missing; 'acl' must follow it.
AnswerA

Module versions may deprecate or remove input variables; the error indicates the variable is not defined in that version.

Why this answer

Option A is correct because the module version does not support the 'acl' argument; it may have been removed. Option B is wrong because typically the registry would show supported arguments. Option C is wrong because other arguments may still be valid.

Option D is wrong because the error is about an unexpected argument, not missing required.

44
MCQmedium

After running `terraform plan`, the user receives an error: `Error: Missing required variable`. The variable 'vpc_cidr' is provided. What is the most likely cause?

A.The module requires a variable 'environment' that is not passed.
B.The module block syntax is incorrect.
C.The variable 'vpc_cidr' is misspelled.
D.The variable 'vpc_cidr' conflicts with a provider variable.
AnswerA

The module's variables.tf declares 'environment' without a default, so it must be set.

Why this answer

The module defines a second required variable 'environment' that has no default value and is not set in the module block, causing the error. Option B is wrong because 'vpc_cidr' is provided. Option C is wrong because syntax is correct.

Option D is wrong because there is no conflict; the variable is simply unset.

45
MCQmedium

An engineer is refactoring a monolithic Terraform configuration into reusable modules. One module outputs a list of subnet IDs. Another module needs to use these subnet IDs to create resources. What is the best way to pass this data between modules?

A.Use a Terraform data source in the second module to query the subnets directly.
B.Define the subnet IDs as a variable in the first module and pass them to the second module via a remote state data source.
C.Store the subnet IDs in a local file and use the 'file' function to read them in the second module.
D.Output the subnet IDs from the first module and reference that output as an input variable in the second module's block.
AnswerD

This is the correct pattern: module outputs are consumed as module input variables.

Why this answer

Option D is correct because Terraform modules communicate through explicit input and output variables. By outputting the subnet IDs from the first module and then referencing that output as an input variable in the second module's block, you create a clear, versionable, and dependency-aware data flow. This approach avoids hidden dependencies and ensures Terraform can properly graph the resource dependencies for parallel execution.

Exam trap

HashiCorp often tests the misconception that remote state data sources are the only way to pass data between modules, when in fact direct output-to-variable passing is the simplest and most maintainable approach within a single Terraform configuration.

How to eliminate wrong answers

Option A is wrong because using a data source in the second module to query subnets directly reintroduces tight coupling to the underlying infrastructure and bypasses the modular abstraction, defeating the purpose of refactoring into reusable modules. Option B is wrong because defining subnet IDs as a variable in the first module is nonsensical—variables are inputs, not outputs; the correct mechanism is to output the IDs from the first module and then use a remote state data source only if the modules are in separate configurations, but here they are in the same configuration, so direct output-to-variable passing is simpler and more idiomatic. Option C is wrong because storing data in a local file introduces an external, non-versioned artifact that can become stale, breaks Terraform's dependency tracking, and is an anti-pattern for passing runtime data between modules.

46
MCQmedium

A developer creates a module in a subdirectory called 'networking' relative to the root module. How should the module source be specified in the root module?

A../networking
B../modules/networking
C.../networking
D.networking
AnswerA

The path starts with './' indicating a relative path from the current directory.

Why this answer

Option A is correct because local module paths must start with './' or '../'. './networking' correctly references the 'networking' subdirectory relative to the root. Option B (../networking) would go up one level. Option C assumes a 'modules' subdirectory.

Option D is not a valid relative path.

47
Matchingmedium

Match each Terraform function to its category.

Drag a concept onto its matching description — or click a concept then click the description.

Concepts
Matches

List function

Map function

IP network function

Encoding function

Date and time function

Why these pairings

Terraform functions are grouped by type.

48
MCQeasy

A team is using a module from the public Terraform Registry. They want to ensure that the module is pinned to a specific version to avoid unexpected changes. Which approach should they use?

A.Use 'required_providers' block in the root module to lock the module version.
B.Add a 'version' argument inside the module block.
C.Set 'version' in the module's source attribute, e.g., source = "terraform-aws-modules/vpc/aws" with version = "3.2.0".
D.Store the module locally in a vendor directory and reference it by path.
AnswerC

Correct. The version constraint is specified as an argument in the module block alongside the source.

Why this answer

Option C is correct because the Terraform Registry module syntax requires the version constraint to be specified as a separate argument within the module block, not embedded in the source string. Pinning to a specific version (e.g., "3.2.0") ensures that only that exact module version is used, preventing unexpected changes from upstream updates. This is the standard approach for versioning public registry modules in Terraform.

Exam trap

HashiCorp often tests the distinction between provider versioning (required_providers) and module versioning (version argument in the module block), and the trap here is that candidates confuse the two or think the version can be embedded in the source string.

How to eliminate wrong answers

Option A is wrong because the 'required_providers' block is used to specify provider version constraints, not module version constraints; modules are versioned independently of providers. Option B is wrong because the 'version' argument cannot be placed inside the module block as a top-level attribute; it must be specified as a separate argument alongside the source, not as a nested block. Option D is wrong because while storing a module locally avoids version drift, it is not the standard approach for pinning a public registry module and introduces manual maintenance overhead; the question specifically asks about using a module from the public Terraform Registry, where the version argument is the intended mechanism.

49
MCQmedium

A team is using a module from the Terraform Registry. When they run 'terraform init', they receive an error stating that the module source cannot be downloaded. The module source is correct. What is the most likely cause?

A.The module output variable names are misspelled.
B.The provider version in the module conflicts with the root provider version.
C.The internet connection is down.
D.The user forgot to run 'terraform init' before 'terraform plan' or 'apply'.
AnswerD

Modules must be initialized first; if init hasn't been run, Terraform cannot download the module.

Why this answer

The most common cause is that the user forgot to run 'terraform init' before attempting to use the module, as modules must be downloaded first. Option A is wrong because if the source is correct, a network issue might cause a different error (timeout, 404). Option C is wrong because provider version issues are separate from module download errors.

Option D is wrong because output variable names don't affect init.

50
MCQhard

An organization uses Terraform modules to provision multiple environments. They have a module 'vpc' that uses a for_each argument in the root module to create VPCs per environment. Each VPC requires a unique CIDR block passed via variable. What is the best practice to pass different CIDRs per instance?

A.Define a map variable with environment names as keys and CIDRs as values, then pass the entire map to the module.
B.Hardcode the CIDR within each module block.
C.Use a list variable for CIDRs and reference them with count.index and element().
D.Use a module output to fetch the CIDR from a data source.
AnswerA

Using a map variable allows clear association between each module instance and its CIDR; it integrates naturally with for_each.

Why this answer

Option D is correct because using a map variable with for_each allows each instance to receive its own CIDR. Option A is wrong because count combined with element() on a list works but is less clear than a map. Option B is wrong because a map already provides key-value association.

Option C is wrong because hardcoding is not scalable.

51
MCQeasy

Which of the following files is NOT required in a Terraform module?

A.providers.tf
B.outputs.tf
C.variables.tf
D.main.tf
AnswerA

A module does not need its own providers.tf; it uses the provider configuration from the root module.

Why this answer

Option D is correct because a module does not require its own providers.tf; it inherits provider configurations from the root module. Options A, B, and C are all standard files commonly found in a module (main.tf, variables.tf, outputs.tf).

52
MCQmedium

A module outputs a map of security group IDs keyed by name. In the root module, a resource needs to reference the security group ID for the name 'web-sg'. How should the root configuration access this value?

A.module.sg["web-sg"]
B.module.sg.web-sg
C.data.module.sg["web-sg"]
D.module.sg[0]
AnswerA

Correct map index syntax to retrieve the value for key 'web-sg'.

Why this answer

Using a 'for' expression with a condition is the correct way to filter a map. Option A is wrong because map syntax uses brackets, not dot notation. Option B is wrong because you need to look up by key, not index.

Option D is wrong because module outputs are not accessed via data sources.

53
Multi-Selectmedium

Which four of the following statements about interacting with Terraform modules are correct? (Choose four.)

Select 4 answers
.A module can reference outputs from another module using the syntax module.<MODULE_NAME>.<OUTPUT_NAME>.
.The source attribute in a module block can reference a local file path, a Git repository, the Terraform Registry, or an HTTP URL.
.Terraform automatically downloads module dependencies when running terraform init, including nested modules from the root module.
.Module inputs are defined as variables in the module's root directory, and outputs are defined as output values that can be consumed by the calling configuration.
.To use a module from a private registry, you must always specify a version constraint in the source attribute of the module block.
.A module can be used to create resources only in the same provider configuration as the root module; it cannot define its own provider configurations.

Why this answer

This statement is correct because Terraform modules expose outputs that can be referenced by the calling configuration using the syntax `module.<MODULE_NAME>.<OUTPUT_NAME>`. This allows values computed inside a module to be used elsewhere in the root module, enabling modular composition and data sharing between modules.

Exam trap

HashiCorp often tests the distinction between `source` and `version` attributes in module blocks, and the misconception that modules cannot override provider configurations, which leads candidates to incorrectly select the two wrong options.

54
Multi-Selecteasy

Which TWO module source types are supported by Terraform natively?

Select 2 answers
A.Terraform Registry (e.g., hashicorp/consul/aws)
B.Docker Hub repositories
C.Local file paths (e.g., ./modules/vpc)
D.Jenkins plugin repository
E.npm packages
AnswersA, C

The Terraform Registry is a native source for published modules.

Why this answer

Options A and D are correct. A: Local paths are supported. D: Terraform Registry is supported.

B is wrong because npm is not a Terraform source. C is wrong because Docker Hub is not a Terraform source. E is wrong because there is no built-in Jenkins module source.

55
MCQhard

In the configuration, what is the likely result of the resource block 'aws_flow_log'?

A.Terraform will error because for_each cannot be used with module outputs.
B.The resource will be created only for the last module instance due to overwriting.
C.It will create one flow log per network module instance, using the vpc_id output from each.
D.It will create one flow log for each VPC using a count based on length of module.networks.
AnswerC

for_each = module.networks iterates over each module instance, allowing access to its outputs via each.value.

Why this answer

Option B is correct because module.networks is a map of module instances, each with outputs; the resource uses for_each over that map, referencing each.value.vpc_id. Option A is wrong because the module does not produce a list of VPC IDs. Option C is wrong because the resource will have two instances.

Option D is wrong because it is fine.

56
MCQhard

A module requires a specific provider configuration with aliases. The root module has two provider configurations: provider 'aws' (default) and provider 'aws' with alias = 'uswest'. The module uses the us-west alias. How should the module block be configured to ensure the correct provider is used?

A.Set required_providers inside the module to include the alias.
B.Use the providers argument in the module block: providers = { aws = aws.uswest }.
C.Include a provider block inside the module block with alias = 'uswest'.
D.Do nothing; Terraform automatically uses the default provider.
AnswerB

The providers argument explicitly maps the module's provider requirements to root module provider configurations.

Why this answer

Option D is correct because providers argument within module block allows mapping aliases to provider configurations. Option A is wrong because required_providers is for provider requirements, not provider selection. Option B is wrong because provider block is not allowed inside module block.

Option C is wrong because the module will use the default provider if not specified.

57
Drag & Dropmedium

Drag and drop the steps to manage Terraform state locking with a backend in the correct order.

Drag steps to the numbered slots on the right, or tap a step then tap a slot.

Steps
Order

Why this order

Backend config must include locking mechanism; init sets up backend, apply uses lock.

58
MCQmedium

The above configuration references a module from the Terraform Registry. After running 'terraform init', the user runs 'terraform plan' and gets an error: 'Error: Unsupported argument' for 'version'. What is the most likely cause?

A.The 'version' argument is not supported for this module because the source is not a registry module.
B.The 'version' argument must be specified as a constraint like '>= 3.19.0' instead of an exact version.
C.The module source is from a Git repository, which does not support the 'version' argument.
D.The 'version' argument should be placed inside a 'required_providers' block.
AnswerA, C

The version argument is only valid for registry modules. If the source is misconfigured, Terraform might treat it as a non-registry source.

Why this answer

The error 'Unsupported argument' for 'version' occurs because the module source is not from a Terraform Registry. The 'version' argument is only valid when the source is a registry module (e.g., 'hashicorp/consul/aws'). If the source is a local path, Git URL, or other non-registry source, Terraform does not support the 'version' argument, as versioning is managed by the registry's metadata.

Exam trap

HashiCorp often tests the distinction between registry and non-registry module sources, trapping candidates who assume the 'version' argument is universally supported across all module source types.

How to eliminate wrong answers

Option B is wrong because the 'version' argument can accept both exact versions and constraint strings like '>= 3.19.0'; the error is not about the format of the version string but about the argument being unsupported entirely. Option D is wrong because the 'version' argument for a module is placed in the module block, not inside a 'required_providers' block, which is used for provider version constraints.

59
MCQmedium

A team is using a module from the Terraform Registry. They want to ensure that changes to the module's source version are tested in a non-production environment before being applied to production. Which approach best supports this workflow?

A.Fork the module repository and manage the module internally as a private module.
B.Pin the module to an exact version (e.g., version = "1.2.3") and update it manually after testing in isolation.
C.Configure the module source to reference the latest commit from the default branch of the repository.
D.Use a version constraint like ~> 1.0 in the module configuration and test the module in a non-production workspace before promoting to production.
AnswerD

This allows controlled updates and testing before production.

Why this answer

Option D is correct because using a version constraint like `~> 1.0` allows Terraform to automatically select the latest compatible patch version within the specified minor version range. This enables safe, incremental updates that can be tested in a non-production workspace first, and then promoted to production by simply applying the same configuration. The constraint ensures that breaking changes (major version bumps) are not automatically pulled in, giving the team control over when to adopt them.

Exam trap

HashiCorp often tests the misconception that pinning to an exact version (Option B) is the safest approach for controlled testing, but the question specifically asks for a workflow that supports testing changes *before* production, which the pessimistic constraint enables automatically without manual version bumps.

How to eliminate wrong answers

Option A is wrong because forking the module repository and managing it internally as a private module adds significant overhead and defeats the purpose of using a public registry module; it also bypasses the version constraint workflow entirely. Option B is wrong because pinning to an exact version (e.g., version = "1.2.3") requires manual updates and does not automatically test newer compatible versions in a non-production environment before promotion. Option C is wrong because referencing the latest commit from the default branch introduces uncontrolled, potentially breaking changes directly into the configuration, with no versioning or testing gate before production.

60
MCQmedium

Given the plan output, how is the module 'instances' configured in the root module?

A.The root module uses for_each in the module block with a map variable.
B.The module uses count with a list variable.
C.The module is declared twice with different names.
D.The module contains a resource with for_each inside.
AnswerA

for_each on a module block creates multiple module instances, each keyed by the map keys, allowing different variable values per instance.

Why this answer

Option D is correct because for_each with a map creates one instance per key, and each instance can have different variables like ami and instance_type. Option A is wrong because count would show index numbers, not keys. Option B is wrong because using module multiple times would show different module addresses.

Option C is wrong because a module with a single resource but for_each inside would still show one instance per key.

61
MCQeasy

A team wants to use a networking module from the public Terraform Registry. They need to ensure they always get the latest patch version within the 1.2.x series. Which version constraint should they use in the module block?

A.version = "= 1.2.0"
B.version = ">= 1.2.0, < 2.0.0"
C.version = ">= 1.2.0"
D.version = "~> 1.2"
AnswerD

Allows only patch version updates within the 1.2.x series, e.g., 1.2.0 to 1.2.9.

Why this answer

The ~> 1.2 constraint allows only patch version updates (e.g., 1.2.0 to 1.2.9), which matches the requirement. Option A is wrong because = 1.2.0 pins to an exact version, not allowing patch updates. Option C is wrong because >= 1.2.0, < 2.0.0 allows minor version updates (e.g., 1.3.0), which is too broad.

Option D is wrong because >= 1.2.0 allows any version 1.2.0 or higher, including 2.0.0.

62
Multi-Selecthard

Which THREE files are considered part of the standard module structure?

Select 3 answers
A.main.tf
B.outputs.tf
C.backend.tf
D.terraform.tfvars
E.variables.tf
AnswersA, B, E

Main resource definitions are typically in main.tf.

Why this answer

The standard module structure includes main.tf, variables.tf, and outputs.tf. Option C is wrong because terraform.tfvars is used to assign values, not part of module definition. Option E is wrong because backend.tf is for state configuration, which belongs in the root module.

63
Multi-Selecteasy

Which TWO are benefits of using Terraform modules?

Select 2 answers
A.Encapsulation of complexity, providing a clean interface.
B.Faster execution of terraform plan and apply.
C.Reusability of infrastructure configurations across projects.
D.Reduction in state file size.
E.Enhanced security by automatically encrypting state files.
AnswersA, C

Modules hide internal details and expose only necessary inputs and outputs.

Why this answer

Modules promote reusability and encapsulation of complex infrastructure components. Option C is wrong because modules do not inherently improve performance; they add overhead. Option D is wrong because modules are not specifically for security; they can be used for any resource.

Option E is wrong because modules do not reduce state file size; they may increase it.

64
MCQhard

You are a DevOps engineer at a company that manages infrastructure for multiple environments (dev, staging, prod) using Terraform. The team has created a reusable module for deploying an AWS ECS Fargate service. The module accepts variables for environment name, container image tag, and desired count. The module is stored in a private Git repository. The root configurations for each environment are stored in separate directories, each with its own backend configuration. Recently, a developer added a new feature to the module that requires a new variable 'enable_xray' (boolean, default false). After updating the module source to point to the new commit, the developer runs 'terraform init' and 'terraform plan' in the dev environment. The plan shows that the ECS service will be updated, but the output does not show any changes related to X-Ray. The developer expected that setting 'enable_xray = true' in the dev root module would enable X-Ray tracing. However, the plan shows no changes to the task definition. What is the most likely cause?

A.The module source was not updated correctly; it still points to the old commit.
B.The developer forgot to run 'terraform init' after changing the module source.
C.The variable 'enable_xray' is not declared in the module's variables.tf file.
D.The module does not reference the 'enable_xray' variable in any resource, so setting it has no effect.
AnswerD

The variable was added but not used in the module's resources, so no changes occur.

Why this answer

Option D is correct because the `enable_xray` variable, even when set to `true` in the root module, will not cause any changes in the plan unless the module's resources actually reference that variable. In Terraform, a variable declared in a module has no effect on infrastructure unless it is used in a resource argument. The developer saw no changes to the task definition because the module's code likely does not include a condition or argument that uses `enable_xray` to enable X-Ray tracing on the ECS task definition.

Exam trap

The trap here is that candidates assume declaring a variable and setting its value automatically triggers infrastructure changes, but Terraform only applies changes when the variable is actually consumed by a resource argument.

How to eliminate wrong answers

Option A is wrong because if the module source still pointed to the old commit, `terraform init` would not fetch the new variable definition, but the developer already ran `terraform init` and the plan showed an update to the ECS service, indicating the new module version was loaded. Option B is wrong because the developer explicitly ran `terraform init` after updating the module source, so the module was correctly initialized. Option C is wrong because the variable `enable_xray` is declared in the module's `variables.tf` (as stated in the scenario: 'requires a new variable'), and the developer set it to `true` in the root module; the issue is not the declaration but the lack of usage in resources.

65
Multi-Selecthard

Which TWO statements about Terraform module structure and best practices are correct? (Choose two.)

Select 2 answers
A.A module should define variables for any values that need to be customized by the calling configuration.
B.A module should assume the calling configuration will provide all necessary provider configurations.
C.A module must have all Terraform code in a single main.tf file.
D.A module can be sourced from the same repository as the root module using a relative path.
E.A module should rely on direct attribute references to resources in the calling configuration.
AnswersA, D

This is a best practice for reusability.

Why this answer

Option A is correct because Terraform modules are designed to be reusable and configurable. By defining input variables for any customizable values (e.g., resource names, sizes, regions), the module abstracts away hardcoded details and allows the calling configuration to pass in specific values via variable assignments. This follows the principle of encapsulation, where the module's internal logic remains unchanged while its behavior adapts to the caller's needs.

Exam trap

HashiCorp often tests the misconception that modules must be stored in separate repositories or that they cannot reference resources from the calling configuration, but the real trap is that candidates confuse 'direct attribute references' (which are forbidden) with 'outputs' (which are the correct way to expose values), leading them to select option E as correct.

Ready to test yourself?

Try a timed practice session using only Terraform Modules questions.