X

Step Up to Modern Cloud Development

Announcing Oracle Cloud Infrastructure Modules for the Terraform Modules Registry

Stephen Cross
Director, Partner Enablement

With the newly announced HashiCorp Terraform Module Registry, Oracle is providing an initial set of Verified modules for the Oracle Cloud Infrastructure Classic (OPC) Provider that have undergone certification and compatibility testing by HashiCorp.

Terraform Modules encapsulate reusable fragments of Terraform configuration as self contained packages. Using Terraform Modules can aid with both the reusability and maintainability of an overall infrastructure configuration, and allows for consist use of tested configuration patterns.

Using the Terraform Module Registry provides a easy and convenient way to discover and use both Verified and Community modules for Oracle Cloud Infrastructure. Below we'll take a closer look at using a two of the initial Oracle Cloud Infrastructure Classic (OPC) modules in a combined configuration.

Oracle Cloud Infrastructure Classic Modules

The Terraform Providers provide the fine grain control over the individual resources that are used to configure and provision compute, networking, storage services etc.

While declaring individual resources can be very powerful for full control over an infrastructure configuration, many times groups of resources are used together in common patterns to provide meet specific configuration requirements, such as launching compute instances, creating networks, and declaring security rules.

Compute Instance Module

The opc_compute_instance resource defaults to creating an ephemeral instance with local boot storage. To create a persistent instance an additional opc_compute_storage_volume resource must be declared for the boot volume and attached to the instance at creation time.

By using the compute-instance module, the creation of both the storage and the instance resources are combined in a single re-usable component, the details for defining and associating the multiple resources are encapsulated into a single, concise, instance definition.

Lets start with the most simple compute-instance module definition

module "persistent-instance1" {
  source           = "oracle/compute-instance/opc"
  instance_name    = "instance1"
  instance_shape   = "oc3"
}

This minimal configuration creates the instance with a persistent bootable storage volume, using common defaults and derived values for many of the attributes that would normally need to be explicitly defined.

Now lets compare with having to fully declare the equivalent set of base resources

resource "opc_compute_instance" "persistent-instance1" {
  name                = "instance1"
  hostname            = "instance1"
  label               = "instance1"
  shape               = "oc3"

  networking_info {
    index          = 0
    shared_network = true
  }

  storage {
    index  = 1
    volume = "${opc_compute_storage_volume.boot-volume.name}"
  }

  boot_order = [1]
}

resource "opc_compute_storage_volume" "boot-volume" {
  name             = "instance1-boot"
  description      = "$instance1 boot storage volume "
  image_list       = "/oracle/public/OL_7.2_UEKR4_x86_64"
  image_list_entry = 1
  size             = 12
  bootable         = true
}

IP Networks Modules

The second module we'll look at is the ip-networks module. This helper module simplifies the creation of multiple IP Networks that are all interconnected through a shared IP Network Exchange. This can be useful for declaring multiple subnets used for different application deployment tiers.

The ip-networks module is instantiated with an name for the IP Network Exchange, and list of subnets and corresponding sub network names.

module "ip-networks" {
    source = "oracle/ip-networks/opc"
    ip_exchange_name = "example"
    subnet_cidrs = [ "192.168.1.0/24", "192.168.2.0/24", "192.168.3.0/24" ]
    subnet_names = [ "network1", "network2", "network3" ]
}

Again lets looks at the equivalent base resource definitions for the same configuration.

resource "opc_compute_ip_network_exchange" "exchange" {
  name = "example"
}

resource "opc_compute_ip_network" "network" {
  name                = "network1"
  ip_address_prefix   = "192.168.1.0/24"
  ip_network_exchange = "${opc_compute_ip_network_exchange.exchange.name}"
}

resource "opc_compute_ip_network" "network" {
  name                = "network2"
  ip_address_prefix   = "192.168.2.0/24"
  ip_network_exchange = "${opc_compute_ip_network_exchange.exchange.name}"
}

resource "opc_compute_ip_network" "network" {
  name                = "network3"
  ip_address_prefix   = "192.168.3.0/24"
  ip_network_exchange = "${opc_compute_ip_network_exchange.exchange.name}"
}

Using Modules as part of a complete configuration

Now lets look at combining the two modules described above. We'll create two interconnected IP Network subnetworks, and create one Compute Instance in each subnet. A couple of additional resources are created to complete the configuration, and SSH Key is created to enable access the running instance. and a Public IP Address reservation is associated to one of the instance.

module "ip-networks" {
    source = "oracle/ip-networks/opc"
    ip_exchange_name = "example"
    subnet_cidrs = [ "192.168.1.0/24", "192.168.2.0/24" ]
    subnet_names = [ "network1", "network2" ]
}

module "persistent-instance1" {
  source           = "oracle/compute-instance/opc"
  instance_name    = "instance1"
  instance_shape   = "oc3"
  ip_network       = "${module.ip-networks.ip_networks[0]}"
  ssh_key          = "${opc_compute_ssh_key.ssh-key.name}"
}

module "persistent-instance2" {
  source           = "oracle/compute-instance/opc"
  instance_name    = "instance1"
  instance_shape   = "oc3"
  ip_network       = "${module.ip-networks.ip_networks[1]}"
  ip_reservation   = "${opc_compute_ip_address_reservation.ip-reservation.name}"
  ssh_key          = "${opc_compute_ssh_key.ssh-key.name}"
}

resource "opc_compute_ssh_key" "ssh-key" {
  name    = "example-sshkey1"
  key     = "${file("~/.ssh/id_rsa.pub")}"
  enabled = true
}

resource "opc_compute_ip_address_reservation" "ip-reservation" {
  name            = "example-ip-reservation"
  ip_address_pool = "public-ippool"
}

For this example, as we are creating the instances on an IP Network, an opc_compute_ip_address_reservation Public IP Address Reservation is used. If no IP Network was provided then a opc_compute_ip_reservation would need to be used instead to create the IP Reservation on the Shared Network interface.

Summary

With any programming language, encapsulation and decomposition into reusable code elements can significantly aid development and maintenance. This same principle applies equally in the realm infrastructure-as-code, where cloud infrastructure can be defined using declarative and functional constructs. Using Terraform Modules and the Terraform Modules Repository provides for a reliable way to adopt both vendor supplied and community provided modules to speed up initial configuration creation.

More Information

Related Content

Be the first to comment

Comments ( 0 )
Please enter your name.Please provide a valid email address.Please enter a comment.CAPTCHA challenge response provided was incorrect. Please try again.Captcha
Oracle

Integrated Cloud Applications & Platform Services