|
1 | 1 | # reach |
2 | 2 |
|
3 | | -A tool for examining network reachability issues in AWS. |
4 | | - |
5 | 3 | [](https://circleci.com/gh/luhring/reach) |
6 | | -[](https://goreportcard.com/report/github.com/luhring/reach) |
7 | 4 | [](https://github.com/luhring/reach/blob/master/LICENSE) |
8 | 5 |
|
9 | | -**IMPORTANT: THIS IS STILL IN DEVELOPMENT! USE AT YOUR OWN RISK!** |
| 6 | +Reach is a tool for discovering the impact your AWS configuration has on the flow of network traffic. |
10 | 7 |
|
11 | | -## Overview |
| 8 | +## Getting Started |
12 | 9 |
|
13 | | -reach evaluates the potential for network connectivity between EC2 instances by querying the AWS API for network configuration data. |
| 10 | +To perform an analysis, specify a **source** EC2 instance and a **destination** EC2 instance: |
14 | 11 |
|
15 | | -reach determines the ports on an EC2 instance that can be accessed by another EC2 instance, taking into consideration security group rules, instance subnet placements, instance running states, network ACL rules, and route tables. |
| 12 | +```Text |
| 13 | +$ reach <source> <destination> |
| 14 | +``` |
16 | 15 |
|
17 | | -reach doesn't need to run on any EC2 instance, it just needs to run on a system that has access to the AWS API. |
| 16 | + |
18 | 17 |
|
19 | | -**Disclaimer:** Because reach gets all of its information from the AWS API, reach makes no guarantees about network service accessibility with respect to the operating system or applications running on an EC2 instance. In other words, reach can tell you if your VPC resources and EC2 instances are configured correctly, but reach _can't_ tell you if an OS firewall is blocking network traffic, or if an application listening on a port has crashed. |
| 18 | +Reach uses your AWS configuration to analyze the potential for network connectivity between two EC2 instances in your AWS account. This means **you don't need to install Reach on any servers** — you just need access to the AWS API. |
20 | 19 |
|
21 | | -## Uses |
| 20 | +The key benefits of Reach are: |
22 | 21 |
|
23 | | -You can ask what ports are reachable on an EC2 instance from the perspective of another instance. |
| 22 | +- **Solve problems faster:** Find missing links in a network path in _seconds_, not hours. |
24 | 23 |
|
25 | | -```ShellSession |
26 | | -$ reach "client instance" "server instance" |
27 | | -✔ TCP 80 |
28 | | -✔ TCP 443 |
29 | | -``` |
| 24 | +- **Don't compromise on security:** Secure your network without worrying about impacting any required network flows. |
| 25 | + |
| 26 | +- **Learn about your network:** Gain better insight into currently allowed network flows, and discover new consequences of your network design. |
| 27 | + |
| 28 | +- **Build better pipelines:** Discover network-level problems before running application integration or end-to-end tests by adding Reach to your CI/CD pipelines. |
30 | 29 |
|
31 | | -You can ask about just one specific port. |
| 30 | +## Basic Usage |
32 | 31 |
|
33 | | -```ShellSession |
34 | | -$ reach "web-server" "db-server" --port 1433 |
35 | | -analysis scope: TCP 1433 |
36 | | -not reachable |
| 32 | +The values for `source` and `destination` should each uniquely identify an EC2 instance in your AWS account. You can use an **instance ID** or a **name tag**, and you can enter just the first few characters instead of the entire value, as long as what you've entered matches exactly one EC2 instance. |
| 33 | + |
| 34 | +Some examples: |
| 35 | + |
| 36 | +```Text |
| 37 | +$ reach i-0452993c7efa3a314 i-02b8dfb5537e80860 |
37 | 38 | ``` |
38 | 39 |
|
39 | | -You can ask reach to explain its logic for its evaluation: |
| 40 | +```Text |
| 41 | +$ reach i-04 i-02 |
| 42 | +``` |
40 | 43 |
|
41 | | -```ShellSession |
42 | | -$ reach "web-server" "db-server" --port 1433 --explain |
43 | | -not reachable |
| 44 | +```Text |
| 45 | +$ reach web-instance database-instance |
| 46 | +``` |
44 | 47 |
|
45 | | -- The instance "db-server" doesn't have any security groups with an inbound rule that allows access on port TCP 1433. |
46 | | -- The subnet "database-private-subnet" in which the instance "db-server" resides doesn't have any network ACL rules that allow inbound traffic on port TCP 1433. |
| 48 | +```Text |
| 49 | +$ reach web data |
47 | 50 | ``` |
48 | 51 |
|
49 | | -## CLI Syntax |
| 52 | +**Note:** Right now, Reach can only analyze the path between two EC2 instances when the instances are **in the same subnet**. Adding support for multiple subnets is the top priority and is currently in development. |
50 | 53 |
|
51 | | -`reach "first-instance" ["second-instance"] [OPTIONS]` |
| 54 | +## Initial Setup |
52 | 55 |
|
53 | | -### Options |
| 56 | +If you've never used Reach before, download the latest version for your platform from the [Releases](https://github.com/luhring/reach/releases) page. (Alternatively, if you've installed the [Go tools](https://golang.org/dl/), you can clone this repository and build from source.) |
54 | 57 |
|
55 | | -`--port`, `-p` Restrict analysis to a specified TCP port. |
| 58 | +You need to run Reach from somewhere where you've saved AWS credentials for your AWS account. Reach follows the standard process for locating and using AWS credentials, similar to the [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/cli-chap-welcome.html) tool and other AWS-capable tools (e.g. Terraform). If you're not sure how to set up AWS credentials, check out [AWS's documentation for setting up credentials](https://docs.aws.amazon.com/cli/latest/userguide/cli-chap-configure.html). |
56 | 59 |
|
57 | | -`--assert-reachable` Exit non-zero if no traffic is allowed from source to destination (within analysis scope, if specified). |
| 60 | +Once you've set up AWS credentials, you'll need to make sure your IAM user or role has permission to access the necessary resources in your AWS account. Reach only ever needs **read-only** access, it never modifies any resources in your AWS account. Reach makes various requests to the AWS API to describe various network-related resources, such as EC2 instances, VPCs, subnets, security groups, etc. |
58 | 61 |
|
59 | | -`--assert-not-reachable` Exit non-zero if any traffic can reach destination from source (within analysis scope, if specified). |
| 62 | +## More Features |
60 | 63 |
|
61 | | -`--explain` Explain how the configuration was analyzed. |
| 64 | +### Assertions |
62 | 65 |
|
63 | | -### Specifying an instance |
| 66 | +If you deploy infrastructure via CI/CD pipelines, it can be helpful to validate the network design itself before running any tests that rely on a correct network configuration. |
64 | 67 |
|
65 | | -reach is able to handle various methods of specifying an EC2 instance. |
| 68 | +You can use assertion flags to ensure that your source **can** or **cannot** reach your destination. |
66 | 69 |
|
67 | | -- **By Name tag.** Most people assign a descriptive name to each of their EC2 instances via a "Name" [tag](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/Using_Tags.html). Example: `"my-database-server"`. |
68 | | -- **By Instance ID.** This is a reliably unique identifier within the EC2 service, and it's assigned by AWS. Example: `"i-08a43985c56df54e4"`. |
| 70 | +If an assertion succeeds, Reach exits `0`. If an assertion fails, Reach exits `2`. |
69 | 71 |
|
70 | | -#### Notes about instance specification strings |
| 72 | +To confirm that the source **can** reach the destination: |
71 | 73 |
|
72 | | -1. **Quotes:** Use quotes to surround instance specification strings as necessary within your shell environment. Quotes never hurt, but sometimes they can be left off -- for example, when using an instance name tag that contains no spaces, only letters and hyphens. |
| 74 | +```Text |
| 75 | +$ reach web-server database-server --assert-reachable |
| 76 | +``` |
| 77 | + |
| 78 | +To confirm that the source **cannot** reach the destination: |
73 | 79 |
|
74 | | -1. **Shortened strings:** To make CLI text entry less tedious, reach only requires enough of an instance specification string to be unique within the current AWS account and region. For example, let's say you have three EC2 instances in a particular region in your AWS account, and these instances are named "web-01", "web-02", and "db-master". You could refer to the "db-master" instance by typing just `"db"`, since no other instance begins with the same text. This would let you type the command `reach db --inbound`, and reach would understand that you were asking about inbound access to the "db-master" instance. However, it would not be sufficient to use the string `"web"`, since multiple instances have name tags that begin with the text "web". The rules for shortened strings apply to both name tags and instance IDs. |
| 80 | +```Text |
| 81 | +$ reach some-server super-sensitive-server --assert-not-reachable |
| 82 | +``` |
75 | 83 |
|
76 | | -## Benefits |
| 84 | +### Explanations |
77 | 85 |
|
78 | | -**Instant diagnosis.** Instantly pinpoint missing links in a network setup in AWS. |
| 86 | +Normally, Reach's output is very basic. It displays a simple list of zero or more kinds of network traffic that are allowed to flow from the source to the destination. However, the process Reach uses to perform its analysis is more complex. |
79 | 87 |
|
80 | | -**Learn about your network.** Gain better insight into currently allowed network flows, and learn how resource configuration affects larger picture. |
| 88 | +If you're troubleshooting a network problem in AWS, it's probably more helpful to see _"why"_ the analysis result is what it is. |
81 | 89 |
|
82 | | -**Stay secure.** Tighten security without worrying about impacting any required network flows. |
| 90 | +You can tell Reach to expose the reasoning behind the displayed result by using the `--explain` flag: |
| 91 | + |
| 92 | +```Text |
| 93 | +$ reach web-instance db-instance --explain |
| 94 | +``` |
83 | 95 |
|
84 | | -**Better deployment pipelines.** Add into CI/CD pipelines alongside infrastructure as code (IaC) deployments to assert business expectations for your network, so you can confirm (or rule out) network-level problems before running integration or end-to-end tests. |
| 96 | +In this case, Reach will provide significantly more detail about the analysis. Specificially, the output will also show you: |
85 | 97 |
|
86 | | -## Road map |
| 98 | +- Exactly which "network points" were used in the analysis (not just the EC2 instance, but the EC2 instance's specific network interface, and the specific IP address attached to the network interface) |
| 99 | +- All of the "factors" (relevant aspects of your configuration) Reach used to figure out what traffic is being allowed by specific properties of your resources (e.g. security group rules, instance state, etc.) |
87 | 100 |
|
88 | | -- ~~Analyze traffic allowed from one EC2 instance to another, within the same subnet~~ |
89 | | -- Analyze traffic allowed from an EC2 instance in one subnet to an EC2 instance in another subnet, within the same VPC **<-- MVP** |
90 | | -- Analyze traffic allowed between an EC2 instance and a specified IP address (e.g. user's IP address, specified hostname, etc.) |
91 | | -- Support for non-EC2 resources within AWS (e.g. ELB, Lambda, gateways, etc.) |
92 | | -- Support for VPC peering |
| 101 | +## Feature Ideas |
| 102 | + |
| 103 | +- ~~**Same-subnet analysis:** Between two EC2 instances within the same subnet~~ (done!) |
| 104 | +- **Same-VPC analysis:** Between two EC2 instances within the same VPC, including for EC2 instances in separate subnets |
| 105 | +- **IP address analysis:** Between an EC2 instance and a specified IP address that may be outside of AWS entirely (enhancement idea: provide shortcuts for things like the user's own IP address, a specified hostname's resolved IP address, etc.) |
| 106 | +- **Filtered analysis:** Specify a particular kind of network traffic to analyze (e.g. a single TCP port) and return results only for that filter |
| 107 | +- **Other AWS resources:** Analyze other kinds of AWS resources than just EC2 instances (e.g. ELB, Lambda, VPC endpoints, etc.) |
| 108 | +- **Peered VPC analysis**: Between resources from separate but peered VPCs |
93 | 109 | - Other things! Your ideas are welcome! |
| 110 | + |
| 111 | +## Disclaimers |
| 112 | + |
| 113 | +- This tool is a work in progress! Use at your own risk, and please submit issues as you encounter bugs or have feature requests. |
| 114 | + |
| 115 | +- Because Reach gets all of its information from the AWS API, Reach makes no guarantees about network service accessibility with respect to the operating system or applications running on a host within the cloud environment. In other words, Reach can tell you if your VPC resources and EC2 instances are configured correctly, but Reach _cannot_ tell you if an OS firewall is blocking network traffic, or if an application listening on a port has crashed. |
0 commit comments