Skip to content

Instantly share code, notes, and snippets.

@ueokande
Last active March 2, 2021 08:00
Show Gist options
  • Save ueokande/333e5e6e8ea3a2bdc29345ac8a7b8313 to your computer and use it in GitHub Desktop.
Save ueokande/333e5e6e8ea3a2bdc29345ac8a7b8313 to your computer and use it in GitHub Desktop.
Initialization script for AppMesh network by aws-appmesh-proxy-route-manager (v3-prod)
#!/bin/bash -e
# Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
#
#
# Start of configurable options
#
# Enable routing on the application start.
[ -z "$APPMESH_START_ENABLED" ] && APPMESH_START_ENABLED="0"
# Egress traffic from the processess owned by the following UID/GID will be ignored.
if [ -z "$APPMESH_IGNORE_UID" ] && [ -z "$APPMESH_IGNORE_GID" ]; then
echo "Variables APPMESH_IGNORE_UID and/or APPMESH_IGNORE_GID must be set."
echo "Envoy must run under those IDs to be able to properly route it's egress traffic."
exit 1
fi
# Port numbers Application and Envoy are listening on.
if [ -z "$APPMESH_ENVOY_EGRESS_PORT" ]; then
echo "APPMESH_ENVOY_EGRESS_PORT must be defined to forward traffic from the application to the proxy."
exit 1
fi
# If an app port was specified, then we also need to enforce the proxies ingress port so we know where to forward traffic.
if [ ! -z "$APPMESH_APP_PORTS" ] && [ -z "$APPMESH_ENVOY_INGRESS_PORT" ]; then
echo "APPMESH_ENVOY_INGRESS_PORT must be defined to forward traffic from the APPMESH_APP_PORTS to the proxy."
exit 1
fi
# Comma separated list of ports for which egress traffic will be ignored, we always refuse to route SSH traffic.
if [ -z "$APPMESH_EGRESS_IGNORED_PORTS" ]; then
APPMESH_EGRESS_IGNORED_PORTS="22"
else
APPMESH_EGRESS_IGNORED_PORTS="$APPMESH_EGRESS_IGNORED_PORTS,22"
fi
#
# End of configurable options
#
APPMESH_LOCAL_ROUTE_TABLE_ID="100"
APPMESH_PACKET_MARK="0x1e7700ce"
function initialize() {
echo "=== Initializing ==="
if [ ! -z "$APPMESH_APP_PORTS" ]; then
iptables -t mangle -N APPMESH_INGRESS
iptables -t nat -N APPMESH_INGRESS
fi
iptables -t nat -N APPMESH_EGRESS
ip rule add fwmark "$APPMESH_PACKET_MARK" lookup $APPMESH_LOCAL_ROUTE_TABLE_ID
ip route add local default dev lo table $APPMESH_LOCAL_ROUTE_TABLE_ID
}
function enable_egress_routing() {
# Stuff to ignore
[ ! -z "$APPMESH_IGNORE_UID" ] && \
iptables -t nat -A APPMESH_EGRESS \
-m owner --uid-owner $APPMESH_IGNORE_UID \
-j RETURN
[ ! -z "$APPMESH_IGNORE_GID" ] && \
iptables -t nat -A APPMESH_EGRESS \
-m owner --gid-owner $APPMESH_IGNORE_GID \
-j RETURN
[ ! -z "$APPMESH_EGRESS_IGNORED_PORTS" ] && \
iptables -t nat -A APPMESH_EGRESS \
-p tcp \
-m multiport --dports "$APPMESH_EGRESS_IGNORED_PORTS" \
-j RETURN
[ ! -z "$APPMESH_EGRESS_IGNORED_IP" ] && \
iptables -t nat -A APPMESH_EGRESS \
-p tcp \
-d "$APPMESH_EGRESS_IGNORED_IP" \
-j RETURN
# Redirect everything that is not ignored
iptables -t nat -A APPMESH_EGRESS \
-p tcp \
-j REDIRECT --to $APPMESH_ENVOY_EGRESS_PORT
# Apply APPMESH_EGRESS chain to non local traffic
iptables -t nat -A OUTPUT \
-p tcp \
-m addrtype ! --dst-type LOCAL \
-j APPMESH_EGRESS
}
function enable_ingress_redirect_routing() {
# Route everything arriving at the application port to Envoy
iptables -t nat -A APPMESH_INGRESS \
-p tcp \
-m multiport --dports "$APPMESH_APP_PORTS" \
-j REDIRECT --to-port "$APPMESH_ENVOY_INGRESS_PORT"
# Apply AppMesh ingress chain to everything non-local
iptables -t nat -A PREROUTING \
-p tcp \
-m addrtype ! --src-type LOCAL \
-j APPMESH_INGRESS
}
function enable_routing() {
echo "=== Enabling routing ==="
enable_egress_routing
if [ ! -z "$APPMESH_APP_PORTS" ]; then
enable_ingress_redirect_routing
fi
}
function disable_routing() {
echo "=== Disabling routing ==="
iptables -F
iptables -F -t nat
iptables -F -t mangle
}
function dump_status() {
echo "=== Routing rules ==="
ip rule
echo "=== AppMesh routing table ==="
ip route list table $APPMESH_LOCAL_ROUTE_TABLE_ID
echo "=== iptables FORWARD table ==="
iptables -L -v -n
echo "=== iptables NAT table ==="
iptables -t nat -L -v -n
echo "=== iptables MANGLE table ==="
iptables -t mangle -L -v -n
}
function main_loop() {
echo "=== Entering main loop ==="
while read -p '> ' cmd; do
case "$cmd" in
"quit")
break
;;
"status")
dump_status
;;
"enable")
enable_routing
;;
"disable")
disable_routing
;;
*)
echo "Available commands: quit, status, enable, disable"
;;
esac
done
}
function print_config() {
echo "=== Input configuration ==="
env | grep APPMESH_ || true
}
print_config
initialize
if [ "$APPMESH_START_ENABLED" == "1" ]; then
enable_routing
fi
main_loop
@ueokande
Copy link
Author

This script is provided by aws-appmesh-proxy-route-manager (v3-prod). If your EC2 instance is deployed in Oregon (us-west-2), you can find this script by the following command in your instance:

$ docker run --rm --entrypoint cat 840364872350.dkr.ecr.us-west-2.amazonaws.com/ -- \
    /opt/amazon/bin/sidecar-proxy-route-manager.sh

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment