github.com/jmbataller/terraform@v0.6.8-0.20151125192640-b7a12e3a580c/website/source/docs/modules/create.html.markdown (about) 1 --- 2 layout: "docs" 3 page_title: "Creating Modules" 4 sidebar_current: "docs-modules-create" 5 description: |- 6 Creating modules in Terraform is easy. You may want to do this to better organize your code, to make a reusable component, or just to learn more about Terraform. For any reason, if you already know the basics of Terraform, creating a module is a piece of cake. 7 --- 8 9 # Creating Modules 10 11 Creating modules in Terraform is easy. You may want to do this to better 12 organize your code, to make a reusable component, or just to learn more about 13 Terraform. For any reason, if you already know the basics of Terraform, 14 creating a module is a piece of cake. 15 16 Modules in Terraform are just folders with Terraform files. In fact, 17 when you run `terraform apply`, the current working directory holding 18 the Terraform files you're applying comprise what is called the 19 _root module_. It itself is a valid module. 20 21 Therefore, you can enter the source of any module, run `terraform apply`, 22 and expect it to work (assuming you satisfy the required variables, if any). 23 24 ## An Example 25 26 Within a folder containing Terraform configurations, create a subfolder 27 "child". In this subfolder, make one empty "main.tf" file. Then, back in 28 the root folder containing the "child" folder, add this to one of the 29 Terraform files: 30 31 ``` 32 module "child" { 33 source = "./child" 34 } 35 ``` 36 37 This will work. You've created your first module! You can add resources 38 to the child module to see how that interaction works. 39 40 Note: Prior to running the above, you'll have to run 41 [the get command](/docs/commands/get.html) for Terraform to sync 42 your modules. This should be instant since the module is just a local path. 43 44 ## Inputs/Outputs 45 46 To make modules more useful than simple isolated containers of Terraform 47 configurations, modules can be configured and also have outputs that can be 48 consumed by the configuration using the module. 49 50 Inputs of a module are [variables](/docs/configuration/variables.html) 51 and outputs are [outputs](/docs/configuration/outputs.html). There is no 52 special syntax to define these, they're defined just like any other 53 variables or outputs. 54 55 In the "child" module we created above, add the following: 56 57 ``` 58 variable "memory" {} 59 60 output "received" { 61 value = "${var.memory}" 62 } 63 ``` 64 65 This will create a required variable "memory" and then an output "received" 66 that will simply be the value of the memory variable. 67 68 You can then configure the module and use the output like so: 69 70 ``` 71 module "child" { 72 source = "./child" 73 74 memory = "1G" 75 } 76 77 output "child_memory" { 78 value = "${module.child.received}" 79 } 80 ``` 81 82 If you run `apply`, you'll again see that this works. 83 84 And that is all there is to it. Variables and outputs are used to configure 85 modules and provide results. Resources within a module are isolated, 86 and the whole thing is managed as a single unit. 87 88 ## Paths and Embedded Files 89 90 It is sometimes useful to embed files within the module that aren't 91 Terraform configuration files, such as a script to provision a resource 92 or a file to upload. 93 94 In these cases, you can't use a relative path, since paths in Terraform 95 are generally relative to the working directory that Terraform was executed 96 from. Instead, you want to use a module-relative path. To do this, use 97 the [path interpolated variables](/docs/configuration/interpolation.html). 98 99 An example is shown below: 100 101 ``` 102 resource "aws_instance" "server" { 103 ... 104 105 provisioner "remote-exec" { 106 script = "${path.module}/script.sh" 107 } 108 } 109 ``` 110 111 In the above, we use `${path.module}` to get a module-relative path. This 112 is usually what you'll want in any case. 113 114 ## Nested Modules 115 116 You can use a module within a module just like you would anywhere else. 117 This module will be hidden from the root user, so you'll have re-expose any 118 variables if you need to, as well as outputs. 119 120 The [get command](/docs/commands/get.html) will automatically get all 121 nested modules as well. 122 123 You don't have to worry about conflicting versions of modules, since 124 Terraform builds isolated subtrees of all dependencies. For example, 125 one module might use version 1.0 of module "foo" and another module 126 might use version 2.0 of module "foo", and this would all work fine 127 within Terraform since the modules are created separately.