Skip to content

Instantly share code, notes, and snippets.

@darksinge
Last active September 18, 2024 15:13
Show Gist options
  • Save darksinge/3d35243c3b968b9d1d883680ec0ea2fe to your computer and use it in GitHub Desktop.
Save darksinge/3d35243c3b968b9d1d883680ec0ea2fe to your computer and use it in GitHub Desktop.
A script to look up lambda functions belonging to a Cloudformation stack and open it in a browser window.
#!/usr/bin/env bash
set -e
export DEBUG=0
export AWS_REGION="us-east-1"
function debug() {
if [ $DEBUG -eq 1 ]; then
echo "ERROR: $@" >&2
fi
}
function info() {
echo "INFO: $@" >&2
}
NO_CACHE=0
CLEAN=0
OPEN_LOG_GROUP=0
help() {
cat << EOF
Usage: $(basename "$0") [OPTIONS]
This script helps you find and open an AWS Lambda function in the AWS Console.
Options:
-p, --profile PROFILE Specify the AWS profile to use
-r, --region REGION Specify the AWS region to use (default: us-east-1)
--no-cache Disable caching of AWS resources
--clean Clear out cached responses from AWS API calls
--stage STAGE Specify the stage (dev/stage/prod/other)
--stack-name STACK_NAME Specify the CloudFormation stack name
-n, --application-name PREFIX Specify the stack name prefix
--debug Enable debug mode
--open-log-group Open the CloudWatch log group instead of the Lambda function
-h, --help Display this help message and exit
The script will prompt you to:
1. Choose or enter a stage (dev/stage/prod/other)
2. Select a CloudFormation stack
3. Choose a Lambda function from the selected stack
It will then open the chosen Lambda function in your default web browser.
Note: This script requires the following tools to be installed:
- AWS CLI
- jq
- gum (for interactive prompts)
EOF
}
if ! gum -v >/dev/null 2>&1; then
echo "The 'gum' command was not found."
echo "Visit https://github.com/charmbracelet/gum for installation instructions."
exit 1
fi
while [[ $# -gt 0 ]]; do
case $1 in
-p|--profile)
export AWS_PROFILE="$2"
shift 2
;;
--no-cache)
export NO_CACHE=1
shift
;;
--region)
export AWS_REGION="$2"
shift 2
;;
--clean)
CLEAN=1
shift
;;
-s|--stage)
STAGE="$2"
shift 2
;;
--stack-name)
STACK_NAME="$2"
shift 2
;;
-n|--application-name)
STACK_PREFIX="$2"
shift 2
;;
--debug)
export DEBUG=1
shift
;;
--open-log-group)
OPEN_LOG_GROUP=1
shift
;;
-h|--help)
help
exit 0
;;
*)
help
exit 1
;;
esac
done
CACHE_DIR="$HOME/.cache/find-fn"
debug "CACHE_DIR: $CACHE_DIR"
if [ ! -d "$CACHE_DIR" ]; then
mkdir -p "$CACHE_DIR"
fi
if [ $CLEAN -eq 1 ]; then
rm -rf "$CACHE_DIR" >/dev/null 2>&1
mkdir -p "$CACHE_DIR"
info "Cache cleared..."
exit 0
fi
if [ -z "$STAGE" ]; then
STAGE=$(gum choose "dev" "stage" "prod" "other")
if [ "$STAGE" == "other" ]; then
STAGE=$(gum input --placeholder "stage name?")
fi
fi
function _make_temp() {
type="$1"
fcache="$CACHE_DIR/$STAGE-$type"
if [ $NO_CACHE -eq 1 ]; then
echo "$(mktemp)"
return 0
fi
local tmp=""
if [ -f "$fcache" ]; then
tmp=$(cat "$fcache")
fi
if [ ! -f "$tmp" ]; then
tmp=$(mktemp)
echo "$tmp" > "$fcache"
else
tmp=$(cat "$fcache")
fi
echo "$tmp"
}
function make_temp() {
set +e
echo $(_make_temp "$1")
set -e
}
stack_list_cache=$(make_temp "stacks_$STACK_PREFIX")
debug "stack_list_cache: $stack_list_cache"
if [ -f "$stack_list_cache" ]; then
STACKS=$(cat "$stack_list_cache")
debug "Found cached stacks list in '$stack_list_cache'"
fi
if [ -z "$STACKS" ]; then
debug "Stacks list is empty..."
if [ -n "$STACK_PREFIX" ]; then
stack_prefix="$STAGE-$STACK_PREFIX-"
else
stack_prefix="$STAGE-"
fi
QUERY="StackSummaries[?starts_with(StackName, '$stack_prefix')].StackName"
debug "Query: \"$QUERY\""
STACKS=$(gum spin --spinner dot --title 'Fetching stacks' --show-output -- \
aws cloudformation list-stacks \
--query "$QUERY" \
--output json)
debug "Fetched stacks: $(echo $STACKS | jq -c '.')"
echo "$STACKS" > "$stack_list_cache"
fi
if [ -z "$STACK_NAME" ]; then
STACK_NAME=$(gum filter --limit 1 $(echo "$STACKS" | jq -r '.[]'))
fi
resource_cache=$(make_temp "$STACK_NAME-resources")
if [ -f "$resource_cache" ]; then
RESOURCES=$(cat "$resource_cache")
fi
debug "resource_cache: $resource_cache"
if [ -z "$RESOURCES" ]; then
RESOURCES=$(gum spin --spinner dot --title 'Fetching resources' --show-output -- \
aws cloudformation list-stack-resources --stack-name "$STACK_NAME" \
--output json)
echo "$RESOURCES" > "$resource_cache"
fi
RESOURCES=$(cat "$resource_cache" | jq '.StackResourceSummaries')
LOGICAL_IDS=$(
echo "$RESOURCES" \
| jq -r '.[] | select(.ResourceType == "AWS::Lambda::Function") | .LogicalResourceId' \
| gum filter --no-limit --select-if-one
)
debug "LOGICAL_ID: ${LOGICAL_IDS[*]}"
PHYSICAL_IDS=()
for LOGICAL_ID in $LOGICAL_IDS; do
PHYSICAL_ID=$(
echo "$RESOURCES" \
| jq -r ".[] | select(.LogicalResourceId == \"$LOGICAL_ID\") | .PhysicalResourceId"
)
PHYSICAL_IDS+=("$PHYSICAL_ID")
done
debug "PHYSICAL_IDS: ${PHYSICAL_IDS[*]}"
for ID in "${PHYSICAL_IDS[@]}"; do
info "Opening Lambda function: $ID"
if [ $OPEN_LOG_GROUP -eq 1 ]; then
open "https://$AWS_REGION.console.aws.amazon.com/cloudwatch/home?region=us-east-1#logsV2:log-groups/log-group/%2Faws%2Flambda%2F$ID"
else
open "https://$AWS_REGION.console.aws.amazon.com/lambda/home?region=$AWS_REGION#/functions/$ID?tab=monitoring"
fi
done
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment