The OCI Landing Zones Networking module is a Terraform networking core module that facilitates, in an optional fashion, the provisioning of a CIS compliant network topology for the entire topology or for specific areas of the topology.
It aims to facilitate the provisioning of any OCI networking topology, covering the internal OCI networking, entirely, and the edge networking, partially.
Check module specification for a full description of module requirements, supported variables, managed resources and outputs.
- CIS OCI Foundations Benchmark Modules Collection
- Requirements
- How to Invoke the Module
- Module Functioning
- Related Documentation
- Known Issues
This module uses Terraform complex types and optional attributes, in order to create a new abstraction layer on top of Terraform. This abstraction layer allows the specification of any networking topology containing any number of networking resources like VCNs, subnets, DRGs and others and mapping those on any existing compartments topology.
It allows both creating a complex networking topology from scratch and also injecting resources into any existing networking topology by following the same abstraction layer format.
The abstraction layer format can be HCL (*.tfvars
or *.auto.tfvars
) or JSON (*.tfvars.json
or *.auto.tfvars.json
).
This approach represents an excellent tool for templating. The templating will be made outside of the code, in the configurations files themselves. The *.tfvars.*
can be used as sharable templates that define different and complex topologies.
The main advantage of this approach is that there will be one single code repository for any networking configuration. Creation of a new networking configuration will not have any impact on the Terraform code, it will just impact the configuration files (*.tfvars.*
files).
The separation of code and configuration supports DevOps key concepts for operations design, change management, pipelines.
This repository is part of a broader collection of repositories containing modules that help customers align their OCI implementations with the CIS OCI Foundations Benchmark recommendations:
- Identity & Access Management
- Networking - current repository
- Governance
- Security
- Observability & Monitoring
- Secure Workloads
The modules in this collection are designed for flexibility, are straightforward to use, and enforce CIS OCI Foundations Benchmark recommendations when possible.
Using these modules does not require a user extensive knowledge of Terraform or OCI resource types usage. Users declare a JSON object describing the OCI resources according to each module’s specification and minimal Terraform code to invoke the modules. The modules generate outputs that can be consumed by other modules as inputs, allowing for the creation of independently managed operational stacks to automate your entire OCI infrastructure.
This module requires the following OCI IAM permissions:
Allow group <group-name> to manage virtual-network-family in compartment <compartment-name>
Allow group <group-name> to manage drgs in compartment <compartment-name>
This module relies on Terraform Optional Object Type Attributes feature, which is experimental from Terraform 0.14.x to 1.2.x. It shortens the amount of input values in complex object types, by having Terraform automatically inserting a default value for any missing optional attributes. The feature has been promoted and it is no longer experimental in Terraform 1.3.x.
Upon running terraform plan with Terraform versions prior to 1.3.x, Terraform displays the following warning:
Warning: Experimental feature "module_variable_optional_attrs" is active
Note the warning is harmless. The code has been tested with Terraform 1.3.x and the implementation is fully compatible.
If you really want to use Terraform 1.3.x, in providers.tf:
- Change the terraform version requirement to:
required_version = ">= 1.3.0"
- Remove the line:
experiments = [module_variable_optional_attrs]
Terraform modules can be invoked locally or remotely.
For invoking the module locally, just set the module source attribute to the module file path (relative path works). The following example assumes the module is two folders up in the file system.
module "terraform-oci-landing-zones-networking" {
source = "../.."
network_configuration = var.network_configuration
}
For invoking the module remotely, set the module source attribute to the networking module repository, as shown:
module "terraform-oci-cis-landing-zone-networking" {
source = "github.com/oracle-quickstart/terraform-oci-cis-landing-zone-networking"
network_configuration = var.network_configuration
}
For referring to a specific module version, append ref=<version> to the source attribute value, as in:
source = "github.com/oracle-quickstart/terraform-oci-cis-landing-zone-networking?ref=v0.1.0"
For an ad-hoc use where you can select your resources, follow these guidelines:
- Accept terms, wait for the configuration to load.
- Set the working directory to “orm-facade”.
- Set the stack name you prefer.
- Set the terraform version to 1.2.x. Click Next.
- Add your json/yaml configuration files. Click Next.
- Un-check run apply. Click Create.
The input parameters for the module can be divided into two categories, for which we recommend to create two different *.tfvars.*
files:
- OCI REST API authentication information (secrets) -
terraform.tfvars
(HCL) orterraform.tfvars.json
(JSON):tenancy_ocid
user_ocid
fingerprint
private_key_path
region
- Network configuration single complex type:
network_configuration.auto.tfvars
(HCL) ornetwork_configuration.auto.tfvars.json
(JSON):network_configuration
The network_configuration
complex type can accept any new networking topology together or separated with injecting resources into existing networking topologies, and all those can map on any compartments topology.
The network_configuration
complex type fully supports optional attributes as long as they do not break any dependency imposed by OCI.
The network_configuration
is a multidimensional complex object:
default_compartment_id
holds the compartment id that will be used if no compartment id has been set at the specific resource or category (seenetwork_configuration_categories
for details) level.default_defined_tags
anddefault_freeform_tags
hold the defined_tags and freeform_tags to be used if no specific defined_tags and freeform_tags have been set at the resource or category* level. Those will be merged with the values provided at their higher levels, including the highest level:default_defined_tags
anddefault_freeform_tags
.default_enable_cis_checks
when set totrue
the module will validate the entire configuration for CIS compliancy by checking the network security and NSG rules for specific configurations. It can can be overwritten at the category* level. It will default totrue
if not set or set tonull
. Setting this tofalse
will disable the CIS checks.default_ssh_ports_to_check
defines the ports the CIS validation mechanism will check for. If not set or set tonull
it will default to[22, 3389]
.network_configuration_categories
represents a construct that will not be directly reflected into OCI but it will have indirect configurations consequences and it will facilitate the grouping of networking resources based on compartments allocation and CIS enablement. This attribte allows any number of catogeries. For each category these attributes can be specified:category_compartment_id
will override thedefault_compartment_id
.category_defined_tags
andcategory_freeform_tags
will be merged withdefault_defined_tags
and, respectively, withdefault_freeform_tags
.category_enable_cis_checks
will override thedefault_enable_cis_checks
.category_ssh_ports_to_check
will override thedefault_ssh_ports_to_check
.vcns
defines any number of VCNs to be created for this category.will enable one to specify any number of vcns he wants to create under one category. Eachvcn
can have any number of:-
security_lists
, -
route_tables
,- For route rules we support the following:
destination
supported values:a cidr block
objectstorage
orall-services
- only forSERVICE_CIDR_BLOCK
destination_type
supported values:CIDR_BLOCK
SERVICE_CIDR_BLOCK
- only for SGW
- For route rules we support the following:
-
dhcp_options
, -
subnets
, -
network_security_groups
and -
vcn_specific_gateways
like:internet_gateways
,nat_gateways
,service_gateways
- SGW services value:
objectstorage
- for object storage accessall-services
- for all OCI internal network services access
- SGW services value:
local_peering_gateways
.
-
All the resources of a
vcn
(including the VCN) are created from scratch. To refer to a resource a key is used to refer to the related resource. Here is an example for specifying a security list, attached to a subnet:... security_lists = { SECLIST_LB_KEY = { display_name = "sl-lb" ... } } ... subnets = { PUBLIC_LB_SUBNET_KEY = { ... security_list_keys = ["SECLIST_LB_KEY"] } ... }
NOTE: It is strongly recommended not to change a resource key after the first provisioning. Once a key has been defined and applied the configuration, changing the key will result in resource re-creation. As the key does not play any role in the configuration that will be pushed to OCI, it will have no impact on the deployment. To distinguish keys from resource names it is recommended to use this convention (using capital characters):
{RESOURCE_NAME}-KEY
.There will be one exception to the rule above. For the
local_peering
it possible to peer to an existing Local Peering Gateway (LPG) created outside this automation. In this case thepeer_id
attribute must be set to the OCID of the acceptor LPG. If no OCID is specified, the acceptor LPG created during the automation must be referred by a key specified inpeer_key
. The value ofpeer_id
will be checked first, if null the value ofpeer_key
will be used. If both values are null, the LPG created will be an acceptor LPG.
-
inject_into_existing_vcns
this attribute is used similarly to thevcns
attribute. It will not create any new resources but will inject them in existing VCNs.-
vcn_id
represents the OCID of a VCN to inject new resources to.- Any number these attributes can be specified:
security_lists
,route_tables
,- For route rules we support the following:
destination
supported values:a cidr block
objectstorage
orall-services
- only forSERVICE_CIDR_BLOCK
destination_type
supported values:CIDR_BLOCK
SERVICE_CIDR_BLOCK
- only for SGW
- For route rules we support the following:
dhcp_options
,subnets
,network_security_groups
andvcn_specific_gateways
like:internet_gateways
,nat_gateways
,service_gateways
- SGW services value:
objectstorage
- for object storage accessall-services
- for all OCI internal network services access
- SGW services value:
local_peering_gateways
.
- Any number these attributes can be specified:
-
To refer a resource within a resource, the following options are available:
- To use the referend object key when the refered object was created as part of the same automation.
- To use the refered object OCID when the refered object already existed as it was created outside this automation.
See the comments above for
local_peering_gateways
and extrapolate to other similar models like adding security lists and route tables to subnets, specifying gateways as next hops in route rules, etc.
-
non_vcn_specific_gateways
allows the configuration of any number of dynamic routing gateways (DRGs), Network Firewalls (NFWs) and inject resources into any number of existing DRGs.-
The
dynamic_routing_gateways
attribute can have any number of DRGs to be created. Each entry can have any number ofremote_peering_connections
,drg_attachments
,drg_route_tables
anddrg_route_distributions
.
-
The
inject_into_existing_drgs
attribute can inject resources in any number of existing drgs. Any number of the following attributes are supported:remote_peering_connections
,drg_attachments
,drg_route_tables
drg_route_distributions
.
-
ipsecs
attribute can define any number(0, 1 or multiple) of ipsec connections, and inside the ipsec connection definition, the correspondingipsec_tunnel_management
can be defined. Bothipsec
andipsec_tunnels_management
are exposing all the attributes of their corresponding OCI REST API objects through the OCI Terraform provider resources. For reference, the following documentation can be used:- OCI IPSEC:
- OCI IPSEC Tunnel Management:
-
fast_connect_virtual_circuits
attribute can define any number(0, 1 or multiple) of OCI fast connect virtual circuits. This attribute exposes all the attributes of the corresponding OCI REST API object through the OCI Terraform provider resource. For reference, the following documentation can be used: - REST API - Terraform ResourcesPlease note the following 2 bool attributes of a fast connect virtual circuit:
provision_fc_virtual_circuit
andshow_available_fc_virtual_circuit_providers
:provision_fc_virtual_circuit
:- set it to
false
when you want just to define a draft fast connect configuration without applying and provisione it. - set it to
true
when you want to apply and provision the defined fast connect configuration.
- set it to
show_available_fc_virtual_circuit_providers
:- set it to
true
when you want to see the available fast connect providers for the current configuration; - set it to
false
when you do not want to see the available fast connect providers for the current configuration;
- set it to
The recommendation will be to use the above 2 attributes, in conjunction, in the following 2 use cases:
- When you do not know the available fast connect partners for a certain draft configuration, define the configuration, set the
provision_fc_virtual_circuit = false
andshow_available_fc_virtual_circuit_providers = true
and runterraform apply
. This will generate in the terraform ouput, for each and every draft fast connect virtual circuit that you've defined, all the available fast connect providers and their details. Pick the provider of your choice and note down either the provider ocid or the provider key. - Once you have the provider ocid and/or the provider key update the corresponding fast connect virtual cirtcuit with those and set the
provision_fc_virtual_circuit = true
andshow_available_fc_virtual_circuit_providers = false
. This will provision the configured virtual circuit and will not show anymore all the available providers for that draft fast connect virtual circuit configuration.
-
cross_connect_groups
attribute can define any number(0, 1 or multiple) of cross connect groups, and inside a cross connect group definition, any number(0, 1 or multiple) ofcross_connects
can be defined. Bothcross_connect_groups
andcross_connects
expose all the attributes of their corresponding OCI REST API objects through the OCI Terraform provider resources. For reference, the following documentation can be used:- OCI Cross Connect Group:
- OCI Cross Connect:
-
The
network_firewalls_configuration
attribute can be used to inject any number ofnetwork_firewalls
and/ornetwork_firewall_policies
. Existing policies or newly created policies can be specified. When updating an attached network firewall policy, a copy of the attached policy will be created, updated with the new values. When done the copy will replace the existing policy. -
l7_load_balancers
is a multidimensional attribute that:compartment_id
holds the compartment id that will be useddisplay_name
load balancer displayed nameshape
LBaaS shapesubnet_ids
andsubnet_keys
the ocids of the subnets that will be used by the LBaaS. If thesubnet_ids
are empty than the automation will try to search the subnets by the providedsubnet_keys
.defined_tags
LBaaS defined tagsfreeform_tags
LBaaS freeform tags- All the OCI LBaaS resource attributes are supported by this configuration:
ip_mode
,is_private
,network_security_group_ids/network_security_group_keys
,reserved_ips_ids/reserved_ips_keys
andshape_details
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes. backend_sets
represents an optional attribute that allows the definition of zero, one or multiple backend sets that will be associated with the current load balancer. All the OCIbackend_set attributes
are covered:health_checker
,name
,policy
,lb_cookie_session_persistence_configuration
,session_persistence_configuration
,ssl_configuration
andbackends
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes.path_route_sets
represents an optional attribute that allows the definition of zero, one or multiple path route sets that will be associated with the current load balancer. All the OCIpath_route_sets
attributes are covered:name
,path_routes
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes.host_names
represents an optional attribute that allows the definition of zero, one or multiple host names that will be associated with the current load balancer. All the OCIhost_names
attributes are covered:hostname
andname
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes.routing_policies
represents an optional attribute that allows the definition of zero, one or multiple routing policies that will be associated with the current load balancer. All the OCIrouting_policies
attributes are covered:condition_language_version
,name
, andcondition
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes.rule_sets
represents an optional attribute that allows the definition of zero, one or multiple rules sets that will be associated with the current load balancer. All the OCIrule_sets
attributes are covered:name
anditems
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes.certificates
represents an optional attribute that allows the definition of zero, one or multiple certificates that will be associated with the current load balancer. All the OCIcertificates
attributes are covered:certificate_name
,ca_certificate
,passphrase
,private_key
andpublic_certificate
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes.listeners
represents an optional attribute that allows the definition of zero, one or multiple listeners that will be associated with the current load balancer. All the OCIlisteners
attributes are covered:default_backend_set_key
,name
,port
,protocol
,connection_configuration
,hostname_keys
,path_route_set_key
,routing_policy_key
,rule_set_keys
andssl_configuration
. Please refer to the OCI LBaaS documentation that is covering all the upper mentioned resource attributes.
-
An optional feature, external dependencies are resources managed elsewhere that resources managed by this module depends on. The following dependencies are supported:
A map of objects containing the externally managed compartments this module may depend on. All map objects must have the same type and must contain at least an id attribute with the compartment OCID. This mechanism allows for the usage of referring keys (instead of OCIDs) in default_compartment_id and compartment_id attributes. The module replaces the keys by the OCIDs provided within compartments_dependency map. Contents of compartments_dependency is typically the output of a Compartments module client.
Example:
{
"NETWORK-CMP": {
id": "ocid1.compartment.oc1..aaaaaaaa...7xq"
}
}
Attributes that support a compartment referring key:
- default_compartment_id
- compartment_id
A map of map of objects containing the externally managed network resources this module may depend on. This mechanism allows for the usage of referring keys (instead of OCIDs) in some attributes. The module replaces the keys by the OCIDs provided within network_dependency map. Contents of network_dependency is typically the output of a client of this module. Within network_dependency, VCNs must be indexed with the vcns key, DRGs indexed with the dynamic_routing_gateways key, DRG attachments indexed with drg_attachments key, Local Peering Gateways (LPG) indexed with local_peering_gateways, Remote Peering Connections (RPC) indexed with remote_peering_connections key. Each VCN, DRG, DRG attachment, LPG and RPC must contain the id attribute (to which the actual OCID is assigned). RPCs must also pass the peer region name in the region_name attribute.
network_dependency example:
{
"vcns" : {
"XYZ-VCN" : {
"id" : "ocid1.vcn.oc1.iad.aaaaaaaax...e7a"
}
},
"dynamic_routing_gateways" : {
"XYZ-DRG" : {
"id" : "ocid1.drg.oc1.iad.aaaaaaaa...xlq"
}
},
"drg_attachments" : {
"XYZ-DRG-ATTACH" : {
"id" : "ocid1.drgattachment.oc1.iad.aaaaaaa...xla"
}
},
"local_peering_gateways" : {
"XYZ-LPG" : {
"id" : "ocid1.localpeeringgateway.oc1.us-ashburn-1.aaaaaaaa...3oa"
}
},
"remote_peering_connections" : {
"XYZ-RPC" : {
"id" : "ocid1.remotepeeringconnection.oc1.us-ashburn-1.aaaaaaaa...4rt",
"region_name" : "us-ashburn-1"
}
}
}
Note: vcns, dynamic_routing_gateways, drg_attachments, local_peering_gateways, and remote_peering_connections attributes are all optional. They only become mandatory if the network_configuration refers to one of these resources through a referring key. Below are the attributes where a referring key is supported:
network_dependency attribute | Attribute names in network_configuration where the referring key can be utilized |
---|---|
vcns | vcn_id in inject_into_existing_vcns |
dynamic_routing_gateways | drg_id in inject_into_existing_drgs, network_entity_key in route_tables' route_rules |
drg_attachments | drg_attachment_key |
local_peering_gateways | peer_key in local_peering_gateways |
remote_peering_connections | peer_key in remote_peering_connections |
A map of map of objects containing the externally managed private IP resources this module may depend on. This mechanism allows for the usage of referring keys (instead of OCIDs) in some attributes. The module replaces the keys by the OCIDs provided within private_ips_dependency map. Each private IP must contain the "id" attribute (to which the actual OCID is assigned), as in the example below:
Example:
{
"INDOOR-NLB": {
"id": "ocid1.privateip.oc1.iad.abyhql...nrq"
}
}
Attributes that support a private IP referring key:
- network_entity_key in route_tables' route_rules
Note how the network_configuration snippet example below refers to keys in compartments_dependency (NETWORK-CMP) and network_dependency (XYZ-VCN):
network_configuration = {
default_compartment_id = "NETWORK-CMP" # This key is defined in compartments_dependency
network_configuration_categories = {
production = {
inject_into_existing_vcns = {
VISION-VCN-INJECTED = {
vcn_id = "XYZ-VCN" # This key is defined in network_dependency, under the vcns attribute.
subnets = {
SUPPLEMENT-SUBNET = {
display_name = "supplement-subnet"
cidr_block = "10.0.0.96/27"
}
}
}
}
}
}
}
See external-dependency example for a functional example.
- Simple Three-Tier VCN - Vision
- External Dependency
- Simple Example
- Provision a load balancer on top of an existing VCN
- Provision a complete VCN and a load balancer
- Edge Connectivity
- Local Peering Gateways
- Remote Peering Connections
Open an issue in this repository.
This project welcomes contributions from the community. Before submitting a pull request, please review our contribution guide.
Please consult the security guide for our responsible security vulnerability disclosure process.
Copyright (c) 2023,2024 Oracle and/or its affiliates.
Replace this statement if your project is not licensed under the UPL
Released under the Universal Permissive License v1.0 as shown at https://oss.oracle.com/licenses/upl/.
- On some corner case situations, a
cycle-graph
exception might be raised when using route tables attached to GWs. This issue will be addressed in one of the next releases.