lunakv / oci-terraform-intro

Introduction to Terraform using OCI

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool


title: Introduction to Terraform using OCI author: Vít Kotačka, Ladislav Dobiáš ...

OCI & Terraform & Terratest

Agenda

  • Login to OCI console
  • Prereqisities
  • Setup OCI API key
  • Today's Goals with Terraform
  • Terraform - setup
  • Terraform - first test
  • Terraform - steps
  • Terratest

Login to OCI console

  • OCI - Oracle Cloud Infrastructure

  • console URL: https://console.eu-frankfurt-1.oraclecloud.com/?tenant=czechedu2021

    • user: email
    • password: generated, need to be changed on first login
  • authorization:

    • every student is in one of student* groups
    • every group student* can:
      • do all in their compartment (same name as the group)
      • read all resources
      • (these policies would be too open for real production environment)
  • quota:

    • important:
      • virtual machine shapes: 3x 15 VM.Standard2.1 (1 in each AD), few others, too.
      • loadbalancers: 15 in region (maybe less)

Prereqisities

All commands expect Unix or Linux environment. They will probably not work on Windows.

This you should have installed (can be in docker, too):

  • curl

  • git

  • openssl

  • terraform, e.g.:

    wget https://releases.hashicorp.com/terraform/0.15.3/terraform_0.15.3_linux_amd64.zip
    unzip terraform_0.15.3_linux_amd64.zip
    mv terraform ~/bin
    ln -s terraform ~/bin/tf
    
  • go 1.14+ (for terratest), e.g.:

    wget https://golang.org/dl/go1.16.4.linux-amd64.tar.gz
    rm -rf /usr/local/go && tar -C /usr/local -xzf go1.16.4.linux-amd64.tar.gz
    ln -s ../go/bin/go /usr/local/bin
    

Optional (recommended - for OCI API key setup,...):

Setup OCI API key

For remote access to OCI, e.g. by OCI-CLI or other OCI SDKs, we need to have some access key, or token.

There are 3 possibilities: - just download the key from your profile in OCI Console, and cut&paste proper content to ~/.oci/config to make OCI-CLI work - using OCI cli - generate OCI API key to ~/.oci:

    ```
    oci setup config
    ```

    - provide:
        - user OCID - get it from UI console
        - tenancy OCI (also from UI): `ocid1.tenancy.oc1..aaaaaaaah3b24zkkewpfygiw3rekqn3idilrt2qrjzkcdxbu5yhqpet4ox4a`
        - region: `eu-frankfurt-1`
- manual way:
    - see [https://docs.cloud.oracle.com/iaas/Content/API/Concepts/apisigningkey.htm](https://docs.cloud.oracle.com/iaas/Content/API/Concepts/apisigningkey.htm)
  • add the key via console UI: your user -> API Keys -> Add Public Key (it is already done if you used the 1st way above)

    • paste the contents of ~/.oci/oci_api_key_public.pem there and press Add
  • simple tests using oci cli:

    oci iam region list
    oci compute image list --compartment-id ocid1.tenancy.oc1..aaaaaaaah3b24zkkewpfygiw3rekqn3idilrt2qrjzkcdxbu5yhqpet4ox4a
    
  • example of using jq (useful to get list of available images):

    oci compute image list --compartment-id ocid1.tenancy.oc1..aaaaaaaah3b24zkkewpfygiw3rekqn3idilrt2qrjzkcdxbu5yhqpet4ox4a --all \
      | jq -r '.data[]|"\(.id) \(."display-name")"'
    

Goals with Terraform - simple webserver with bastion

Deployment diagram - simple: Simple web server

This would be achieved at the step #6.

Note: there are some "mistakes" included in several steps. Find them and fix them.

Goals with Terraform - more webservers with bastion and load balancer

Deployment diagram - with LB: Web server with LB

This would be achieved at the last step.

Terraform - setup

  • get sources:

    git clone https://github.com/ladaedu/oci-terraform-intro
    cd oci-terraform-intro/web-server
    
  • edit variables in env-vars.example that are not commented out, copy it first (env-vars is in .git-ignore):

    cp env-vars.example env-vars
    
    • use data from ~/.oci/config (this can be get also from OCI console in API Keys section under user profile)
  • source it:

    . env-vars
    

Terraform - first test

  • list current *.tf files:

    ls *.tf
    
    • output (recommened to look inside the files): network.tf variables.tf
  • init terraform (download providers, modules,...):

    alias tf=terraform
    tf init
    
  • plan

    tf plan
    
  • apply

    tf apply
    

Terraform - steps overview

  1. VCN, gateways
  2. Datasources - ADs, Tenancy
  3. Bastion - network: routing table, seclist, subnet
  4. Bastion VM
  5. Private Subnet for Web servers - network: routing table, seclist, subnet
  6. Web server
  7. Outputs - IP addresses
  8. Load balancer + add some web servers

Terraform - next step

  • rename next steps TF file, e.g. *.tf1 to *.tf:

    orig=$(echo *1);link=${orig%?};echo ln -s $orig $link
    
  • for other steps, replace 1 with next numbers

  • plan

    tf plan
    
  • apply

    tf apply
    
  • check what was created in UI console

Terraform - notes for step 6 - Test ssh to Web Server (optional)

Get from terraform output:

  • bastion public IP
  • web-server private IP

Test ssh - to connect directly via bastion, add similar lines to ~/.ssh/config, replace Hostname/Username/:

Host web-server
    Hostname 10.0.0.231
    User opc
    IdentityFile ~/.ssh/id_rsa
    ProxyCommand ssh bastion -W %h:%p
    ServerAliveInterval 50
    UserKnownHostsFile /dev/null
    StrictHostKeyChecking no
    GSSAPIAuthentication no
Host bastion
    Hostname 130.61.47.195
    User opc
    IdentityFile ~/.ssh/id_rsa
    ServerAliveInterval 50
    UserKnownHostsFile /dev/null
    StrictHostKeyChecking no
    GSSAPIAuthentication no

Run ssh:

ssh web-server

Inside the web-server, try access web server:

curl localhost

Terraform - notes for step 7 - load balancer

  • first try setup with default values (1 web-server, 1 bastion)

  • to add more web server nodes, increase variable WebVMCount for 1 to e.g. 4 in file variables.tf

  • to add more bastion server nodes, increase variable BastionVMCount for 1 to e.g. 2 in file variables.tf (if you enter more, 2 will be used)

  • to test loadbalancer:

    • from CLI:

      lb_address=$(tf output -json|jq -r .lb_ip.value[0])
      echo $lb_address
      curl http://$lb_address
      
      # check that round-robin works:
      for i in $(seq 10);do
          curl -s http://$lb_address
      done | grep name
      
  • or get LB IP address from console UI (Networking/Load Balancers), and test it in browser - and reload the page several time so you can see that web servers are changed in round-robin fashion.

Terratest

In terraform_oci_test.go, there are 4 small tests:

  • ssh to bastion
  • ssh to webserver (via bastion)
  • check that webserver nginx port 80 is open using netstat
  • check that webserver nginx returns status 200

Terratest will create its own environment, so destroy your environment first, to avoid problems with quota.

  • destroy the deployment:

    tf destroy
    
  • run terratest:

    cd terratest
    go test -v -run TestTerraform
    

Thank you

Questions?

Backup slides

Terraform graph

  • generate graph - using Graphviz:

    tf graph
    
  • generate graph with colors:

    ./tf-graph.sh
    

Graph of dependencies of resources, variables, outputs: TF Dependencies graph example

Initial tenancy setup

For creating initial groups, policies, compartments, users, a custom module compartment-group-policy was created, which reuses standard OCI Terraform IAM modules - in terraform-oci-iam directory.

To run these TF script, you must be an administrator (and source correct env-vars file). Steps:

  • create compartments, groups, policies:

    cd admin/groups
    tf init
    tf plan
    tf apply
    
  • create users - define correct variables first, then run terraform:

    cd admin/users
    cat <<EOF > variables-users.tf
    variable "student1_name" { default = "first1.last1@email.cz" }
    variable "student2_name" { default = "first2.last2@email.cz" }
    EOF
    tf init
    tf plan
    tf apply
    
    • then "Create/Reset Password" must be done from console UI for each user

References

About

Introduction to Terraform using OCI


Languages

Language:HCL 70.0%Language:Go 18.2%Language:Shell 11.8%