github.com/openshift/installer@v1.4.17/upi/vsphere/ipam/cidr_to_ip.sh (about)

     1  #!/bin/bash
     2  # cidr_to_ip -
     3  #  https://www.terraform.io/docs/providers/external/data_source.html
     4  #  Based on info from here: https://gist.github.com/irvingpop/968464132ded25a206ced835d50afa6b
     5  #  This script takes requests an IP address from an IPAM server
     6  #  echo '{"network": "139.178.89.192", "hostname": "control-plane-0.dphillip.devcluster.openshift.com", "ipam": "ipam_address", "ipam_token", "api_token" }' | ./cidr_to_ip.sh
     7  function error_exit() {
     8    echo "$1" 1>&2
     9    exit 1
    10  }
    11  
    12  function check_deps() {
    13    test -f "$(command -v jq)" || error_exit "jq command not detected in path, please install it"
    14  
    15  }
    16  
    17  function parse_input() {
    18    input=$(jq .)
    19    network=$(echo "$input" | jq -r .network)
    20    hostname=$(echo "$input" | jq -r .hostname)
    21    ipam=$(echo "$input" | jq -r .ipam)
    22    ipam_token=$(echo "$input" | jq -r .ipam_token)
    23  }
    24  
    25  is_ip_address() {
    26    if [[ $1 =~ ^[0-9]{1,3}(\.[0-9]{1,3}){3}$ ]]; then
    27      echo "true"
    28    else
    29      echo "false"
    30    fi
    31  }
    32  
    33  get_reservation() {
    34    reservation=$(curl -s "http://${ipam}/api/getIPs.php?apiapp=address&apitoken=${ipam_token}&domain=${hostname}")
    35    if [[ "${reservation}" == "[]" ]]; then
    36      echo "empty"
    37    else
    38      reserved_ip=$(echo "${reservation}" | jq -r ".\"${hostname}\"")
    39      if [ "$(is_ip_address "${reserved_ip}")" == "false" ]; then
    40        echo "malformed data: ${ip_address}"
    41      else
    42        echo "$reserved_ip"
    43      fi
    44    fi
    45  }
    46  
    47  function produce_output() {
    48    if [[ "${network}" == "null" ]]; then
    49      jq -n \
    50        --arg ip_address "$(get_reservation)" \
    51        '{"ip_address":$ip_address}'
    52      exit 0
    53    fi
    54  
    55    timeout=$((SECONDS + 60))
    56  
    57    # Request an IP address. Verify that the IP address reserved matches the IP
    58    # address returned. Loop until the reservation matches the address returned.
    59    # The verification and looping is a crude way of overcoming the lack of
    60    # currency safety in the IPAM server.
    61    while [[ $SECONDS -lt $timeout ]]
    62    do
    63      ip_address=$(curl -s "http://$ipam/api/getFreeIP.php?apiapp=address&apitoken=$ipam_token&subnet=${network}&host=${hostname}")
    64  
    65      if [[ "$(is_ip_address "${ip_address}")" != "true" ]]; then 
    66        error_exit "could not reserve an IP address: malformed data: ${ip_address}"
    67      fi
    68  
    69      reservation=$(get_reservation)
    70      if [[ "$ip_address" == "$reservation" ]]; then
    71        jq -n \
    72          --arg ip_address "$ip_address" \
    73          '{"ip_address":$ip_address}'
    74        exit 0
    75      elif [[ "$reservation" == "empty" ]]; then
    76        echo "received IP address reservation is empty. Retrying..."
    77      elif [[ "$(is_ip_address "${reservation}")" != "true" ]]; then
    78        echo "received invalid IP address reservation: $reservation. Retrying..."
    79      else
    80        echo "received IP address $ip_address does not equal reservation $reservation. Retrying..."
    81      fi
    82  
    83      sleep 3
    84    done
    85  
    86    # IPAM server responds with 0.0.0.0 when there are no available addresses
    87    if [[ "${ip_address}" =~ ^0 ]]; then
    88      error_exit "could not reserve IP address $ip_address with reservation $reservation: no available addresses"
    89    else
    90      error_exit "could not reserve IP address $ip_address with reservation $reservation: timed out waiting for a reservation"
    91    fi
    92  }
    93  
    94  # main()
    95  check_deps
    96  parse_input
    97  produce_output