-
-
Save azilber/f94c02cab19d74c8d94e56d38404dd4d to your computer and use it in GitHub Desktop.
Script to assign Public IP from Elastic IP pool for instances hosted in AWS. 'ec2-utils' and AWS CLI packages required. Instance role or access keys need to allow at least next EC2 actions: describe-addresses, associate-address and disassociate-address. Shell script is designed to be integrated with instance start-up
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #!/bin/bash | |
| # chkconfig: 2345 99 10 | |
| # description: Auto assigns free EIP | |
| # processname: ipassign | |
| # Provides: ipassign | |
| # Required-Start: | |
| # Required-Stop: | |
| # Default-Start: 2 3 4 5 | |
| # Default-Stop: | |
| # Short-Description: Set Public IP from ElasticIP pool during start-up | |
| OUTPUT="text" | |
| REGION="eu-west-1" | |
| IPLOGFILE="/var/log/ipassign.log" | |
| export PATH=/usr/share/pear:/usr/local/bin:/bin:/usr/bin:/usr/local/sbin:/usr/sbin:/sbin:/opt/aws/bin:/home/ec2-user/bin | |
| timestamp() { | |
| TIMESTAMP=`date -u +"%Y-%m-%dT%H:%M:%S.000Z"` | |
| } | |
| usage() { | |
| echo "$0 {start|stop|status}" | |
| exit 255 | |
| } | |
| write_log() { | |
| timestamp | |
| echo "${TIMESTAMP} - ${LOG}" >> ${IPLOGFILE} | |
| } | |
| valid_ip() { | |
| RX='([1-9]?[0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])' | |
| if [[ ${EC2PUBLICIP} =~ ^${RX}\.${RX}\.${RX}\.${RX}$ ]] | |
| then | |
| VALIDIP=1 | |
| else | |
| VALIDIP=0 | |
| fi | |
| } | |
| check_ec2metadata() { | |
| ec2-metadata >/dev/null 2>&1 | |
| if [ $? -eq 0 ] | |
| then | |
| # Amazon Linux ec2-metadata command found | |
| EC2INSTANCE=`ec2-metadata -i | awk '{ print $NF; }'` | |
| EC2PUBLICIP=`ec2-metadata -v | awk '{ print $NF; }'` | |
| else | |
| # Checking ec2metadata command | |
| ec2metadata >/dev/null 2>&1 | |
| if [ $? -eq 0 ] | |
| then | |
| # ec2metadata command found | |
| EC2INSTANCE=`ec2metadata --instance-id` | |
| EC2PUBLICIP=`ec2metadata --public-ipv4` | |
| else | |
| # No ec2metadata command found | |
| LOG="ERROR: No ec2metadata or ec2-metadata command found"; write_log | |
| exit 127 | |
| fi | |
| fi | |
| } | |
| check_awscli() { | |
| aws ec2 describe-addresses >/dev/null 2>&1 | |
| if [ $? -ne 0 ] | |
| then | |
| # Incorrect instance role or no valid AWS CLI configuration found | |
| LOG="ERROR: AWS CLI commands not available. Check AWS CLI installation or configuration"; write_log | |
| exit 128 | |
| fi | |
| } | |
| start() { | |
| # EC2 metadata: public IP and Instance ID | |
| check_ec2metadata | |
| # Checking if any Public IP is assigned | |
| valid_ip | |
| if [ ${VALIDIP} -eq 0 ] | |
| then | |
| # No Public IP available. Can't execute AWS CLI command | |
| LOG="ERROR: There is no Public IP address assigned. Can't run AWS CLI commands"; write_log | |
| exit 3 | |
| fi | |
| # Check if AWS CLI commands are available | |
| check_awscli | |
| # Checking if instance has a public IP from Elastic pool assigned | |
| PUBLICIPASSIGNED=`aws ec2 describe-addresses --output ${OUTPUT} --region ${REGION} | grep ${EC2INSTANCE} | wc -l` | |
| if [ ${PUBLICIPASSIGNED} -gt 0 ] | |
| then | |
| # Instance has at least one Pulic IP associated from Elastic pool | |
| IP=`aws ec2 describe-addresses --output ${OUTPUT} --region ${REGION} | grep ${EC2INSTANCE} | head -1 | awk '{ print $NF; }'` | |
| LOG="Instance ${EC2INSTANCE} has a Public IP address from Elastic pool in ${REGION} region (${IP})"; write_log | |
| exit 4 | |
| else | |
| # Get IP address from Elastic pool | |
| IP=`aws ec2 describe-addresses --output ${OUTPUT} --region ${REGION} | grep -v 'i-' | head -1 | awk '{ print $NF; }'` | |
| if [ "${IP}" = "" ] | |
| then | |
| # No unassigned Public IP on pool | |
| LOG="ERROR: No free Public IP from Elastic pool in ${REGION} region available"; write_log | |
| exit 5 | |
| else | |
| # Attach Public IP from Elastic pool | |
| BOOL=0 | |
| aws ec2 associate-address --output ${OUTPUT} --region ${REGION} --instance-id ${EC2INSTANCE} --public-ip ${IP} >/dev/null 2>&1 | |
| EXITCODE=$? | |
| if [ ${EXITCODE} -eq 0 ] | |
| then | |
| LOG="${IP} Public IP from pool assigned to ${EC2INSTANCE} instance"; write_log | |
| else | |
| LOG="ERROR: (${EXITCODE}) Unable to associate ${IP} Public IP from Elastic pool to ${EC2INSTANCE} instance"; write_log | |
| BOOL=1 | |
| fi | |
| if [ ${BOOL} -eq 0 ] | |
| then | |
| # Detaching default Public IP | |
| aws ec2 disassociate-address --output ${OUTPUT} --region ${REGION} --instance-id ${EC2INSTANCE} --public-ip ${EC2PUBLICIP} >/dev/null 2>&1 | |
| EXITCODE=$? | |
| if [ ${EXITCODE} -eq 0 ] || [ ${EXITCODE} -eq 255 ] | |
| then | |
| LOG="Default public IP ${EC2PUBLICIP} not from pool disassociated in ${EC2INSTANCE} instance"; write_log | |
| else | |
| LOG="ERROR: (${EXITCODE}) Unable to disassociate default public IP ${EC2PUBLICIP} in ${EC2INSTANCE} instance"; write_log | |
| BOOL=2 | |
| fi | |
| fi | |
| exit ${BOOL} | |
| fi | |
| fi | |
| } | |
| stop() { | |
| exit 6 | |
| } | |
| status () { | |
| check_ec2metadata | |
| valid_ip | |
| if [ ${VALIDIP} -eq 0 ] | |
| then | |
| echo "No Public IP address assigned to ${EC2INSTANCE} instance." | |
| exit 1 | |
| fi | |
| check_awscli | |
| IPPRESENTINPOOL=`aws ec2 describe-addresses --output ${OUTPUT} --region ${REGION} | grep "${EC2INSTANCE}" | grep ${EC2PUBLICIP} | wc -l` | |
| if [ ${IPPRESENTINPOOL} -eq 1 ] | |
| then | |
| echo "Public IP ${EC2PUBLICIP} assigned to ${EC2INSTANCE} instance is part of the ElasticIP pool" | |
| exit 0 | |
| else | |
| echo "Public IP ${EC2PUBLICIP} assigned to ${EC2INSTANCE} instance is a generic public IP NOT present in ElasticIP pool" | |
| exit 2 | |
| fi | |
| } | |
| case "$1" in | |
| start) | |
| start | |
| ;; | |
| stop) | |
| stop | |
| ;; | |
| status) | |
| status | |
| ;; | |
| *) | |
| usage | |
| ;; | |
| esac |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment