Deploying bulletproof PAM with Gravitational Teleport
Tags: docker, devops, tutorial, kubernetes
Published: 2020-04-13 15:51:20

#Introduction#

According to one study, there is a cybersecurity attack every [39 seconds](https://www.securitymagazine.com/gdpr-policy?url=https%3A%2F%2Fwww.securitymagazine.com%2Farticles%2F87787-hackers-attack-every-39-seconds). Defending against such attacks has become of paramount importance to how businesses operate today. The traditional approach to securing IT infrastructure is perimeter-oriented solutions such as firewalls, VPNs, and password policies. While these are all good and necessary, they don’t speak to the security vectors that are “built-in” to an organization at the code or infrastructure level.

Many companies are solving these issues by leveraging more non-traditional cloud security solutions such as compliance, DevOps, and engineering. Many companies have found that at the DevOps level, protecting infrastructure starts and ends with a Secure Shell (SSH) protocol.

In this tutorial, we are going to take you through the steps of deploying a PAM system with Gravitational's Teleport. Teleport is a compliance and SSH gateway for multi-cloud privileged access. It allows you to isolate secure infrastructure and enforce security best practices such as 2FA. 

#Install Teleport#

To get started, head over to the Teleport [Downloads](https://gravitational.com/teleport/download/) page and grab the latest binary. You can also install it via the [AWS Marketplace](https://gravitational.com/teleport/download-aws/). Next, open up a terminal and run: 

```
$ tar -xzf teleport-binary-release.tar.gz
$ sudo make install
```

Another option is installing via source. Teleport is written in Go language. It requires the prerequisite of Golang v1.8.3 or newer to install. To install via source, you'll want to run these commands: 

```
# get the source & build:
$ mkdir -p $GOPATH/src/github.com/gravitational
$ cd $GOPATH/src/github.com/gravitational
$ git clone https://github.com/gravitational/teleport.git
$ cd teleport
$ make full

# create the default data directory before starting:
$ sudo mkdir -p /var/lib/teleport
```

#Start Teleport#

Next, create a directory for Teleport to keep its data. By default it's `/var/lib/teleport/`. Then start the `teleport` daemon. 

```
$ mkdir -p /var/lib/teleport
```
![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/fjhkks3gzz1eas04f22r.png)

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/u41ke4catzigasiox5v6.png)

```
$ teleport start # if you are not `root` you may need `sudo`
```

By default Teleport services bind to 0.0.0.0. If you ran teleport without any configuration or flags you should see this output in your console or logfile.

```
[AUTH]  Auth service is starting on 0.0.0.0:3025
[PROXY] Reverse tunnel service is starting on 0.0.0.0:3024
[PROXY] Web proxy service is starting on 0.0.0.0:3080
[PROXY] SSH proxy service is starting on 0.0.0.0:3023
[SSH]   Service is starting on 0.0.0.0:3022
```

Congratulations - you are now running Teleport!

#Create a user signup token#

So, we've got Teleport running but there aren't any users recognized by Teleport Auth yet! We need to create one for your OS user. In this example the OS user is `teleport` and the hostname of the node is `grav-00` .

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/4jwrcenxpaghpd125iz9.png)

```
# A new Teleport user will be assigned a
# mapping to an OS user of the same name
# This is the same as running `tctl users add teleport teleport`
[teleport@grav-00 ~]$ tctl users add teleport
Signup token has been created and is valid for 1 hours. Share this URL with the user:
https://grav-00:3080/web/newuser/3a8e9fb6a5093a47b547c0f32e3a98d4

NOTE: Make sure grav-00:3080 points at a Teleport proxy which users can access.
```

If you want to map to a different OS user, `james` for instance, you can specify like so: `tctl users add teleport james` . You can also add assign multiple mappings like this `tctl users add teleport james,joe,root` .

You now have a signup token for the Teleport User `teleport` and will need to open this URL in a web browser to complete the registration process.

#Register a user#

* If the machine where you ran these commands has a web browser installed you should be able to open the browser and connect to Teleport Proxy via URL right away. 

* If the machine you are working on is a remote machine you may need to access the Teleport

Proxy via the host machine and port `3080` in a web browser. One simple way to do this is to temporarily append `[HOST_IP] grav-00` to `/etc/hosts`

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/f8iksob4f8fgazy2ij2r.png)

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/hz6a55ii8j7e7b3rpq2q.png)

Teleport enforces two-factor authentication by default. If you do not already have [Google Authenticator](https://en.wikipedia.org/wiki/Google_Authenticator), [Authy](https://authy.com/) or another 2FA client installed, you will need to install it on your smartphone. Then you can scan the QR code on the Teleport login web page, pick a password and enter the two-factor token.

After completing the registration you will be logged in automatically.

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/yzhk22ennch764bx0yah.png)

#Log in via CLI#

Let's login using the `tsh` command-line tool. Just as in the previous step, you will need to be able to resolve the **hostname** of the cluster to a network-accessible IP.

```
# here grav-00 is a resolvable hostname on the same network
# --proxy can be an IP, hostname, or URL
[teleport@grav-00 ~]$ tsh --proxy=grav-00 --insecure login
WARNING: You are using insecure connection to SSH proxy https://grav-00:3080
Enter password for Teleport user teleport:
Enter your OTP token:
XXXXXX
WARNING: You are using insecure connection to SSH proxy https://grav-00:3080
> Profile URL:  https://grav-00:3080
  Logged in as: teleport
  Cluster:      grav-00
  Roles:        admin*
  Logins:       teleport
  Valid until:  2019-10-05 02:01:36 +0000 UTC [valid for 12h0m0s]
  Extensions:   permit-agent-forwarding, permit-port-forwarding, permit-pty

* RBAC is only available in Teleport Enterprise

  https://gravitational.com/teleport/docs/enterprise
```

#Start a recorded session#

At this point, you have authenticated with Teleport Auth and can now start a recorded SSH session. You logged in as the `teleport` user in the last step so the `--user` is defaulted to `teleport`.

```
$ tsh ssh --proxy=grav-00 grav-00
$ echo 'howdy'
howdy
# run whatever you want here, this is a regular SSH session.
```

*Note: The `tsh` client always requires the `--proxy` flag*

Your command prompt may not look different, but you are now in a new SSH session which has been authenticated by Teleport!

Try a few things to get familiar with recorded sessions:

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/okwcgm9y7j3mvrfadcq0.png)

1. Navigate to `https://[HOST]:3080/web/sessions` in your web browser to see the list of current and past sessions on the cluster. The session you just created should be listed.
2. After you end a session, replay it in your browser.
3. Join the session in your web browser.

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/pqk2uqs1v2n33yctrkj8.png)

Here we've started two recorded sessions on the node `grav-00`: one via the web browser and one in the command line. Notice that there are distinct SSH sessions even though we logged in with the `root` user. In the next step, you'll learn how to join a shared session.

#Join a session on the CLI#

One of the most important features of Teleport is the ability to share a session between users. If you joined your active session in your browser in the previous step you will see the complete session history of the recorded session in the web terminal.

Joining a session via a browser is often the easiest way to see what another user is up to, but if you have access to the proxy server from your local machine (or any machine) you can also join a session on the CLI.

```
# This is the recorded session you started in Step 6
$ tsh ssh --proxy=grav-00 grav-00
$ echo 'howdy'
howdy
# you might have run more stuff here...
$ teleport status
Cluster Name: grav-00
Host UUID   : a3f67090-99cc-45cf-8f70-478d176b970e
Session ID  : cd908432-950a-4493-a561-9c272b0e0ea6
Session URL : https://grav-00:3080/web/cluster/grav-00/node/a3f67090-99cc-45cf-8f70-478d176b970e/teleport/cd908432-950a-4493-a561-9c272b0e0ea6
```

Copy the Session ID and open a new SSH session.

```
%~$ tsh join -d --proxy grav-00 --insecure
cd908432-950a-4493-a561-9c272b0e0ea6
# you will be asked to re-authenticate your user
$ echo 'howdy'
howdy
# you might have run more stuff here...
$ teleport status
Cluster Name: grav-00
Host UUID   : a3f67090-99cc-45cf-8f70-478d176b970e
Session ID  : cd908432-950a-4493-a561-9c272b0e0ea6
Session URL : https://grav-00:3080/web/cluster/grav-00/node/a3f67090-99cc-45cf-8f70-478d176b970e/teleport/cd908432-950a-4493-a561-9c272b0e0ea6
$ echo "Awesome!"
# check out your shared ssh session between two CLI windows
```

#Authentication#

Teleport uses the concept of "authentication connectors" to authenticate users when they execute `tsh login` command. There are three types of authentication connectors:

###LOCAL CONNECTOR###

Local authentication is used to authenticate against a local Teleport user database. This database is managed by `tctl users` command. Teleport also supports second factor authentication (2FA) for the local connector. There are three possible values (types) of 2FA:

* `otp` is the default. It implements [TOTP](https://en.wikipedia.org/wiki/Time-based_One-time_Password_algorithm) standard. You can use [Google Authenticator](https://en.wikipedia.org/wiki/Google_Authenticator) or [Authy](https://authy.com/) or any other TOTP client.

* `u2f` implements [U2F](https://en.wikipedia.org/wiki/Universal_2nd_Factor) standard for utilizing hardware (USB) keys for second factor.

* `off` turns off second factor authentication.

Here is an example of this setting in the `teleport.yaml` :

```
auth_service:
  authentication:
    type: local
    second_factor: off
```

###GITHUB OAUTH 2.0 CONNECTOR###

This connector implements Github OAuth 2.0 authentication flow. Please refer to Github documentation on [Creating an OAuth App](https://developer.github.com/apps/building-oauth-apps/creating-an-oauth-app/) to learn how to create and register an OAuth app. The Community edition of Teleport only supports this authentication flow. 

Here is an example of this setting in the `teleport.yaml` :

```
auth_service:
  authentication:
    type: github
```

See [Github OAuth 2.0](https://gravitational.com/teleport/docs/admin-guide/#github-oauth-20) for details on how to configure it.

###SAML###

This connector type implements SAML authentication. It can be configured against any external identity manager like Okta or Auth0. This feature is only available for Teleport Enterprise.

Here is an example of this setting in the `teleport.yaml` :

```
auth_service:
  authentication:
    type: saml
```

###OIDC###

Teleport implements OpenID Connect (OIDC) authentication, which is similar to SAML in principle. This feature is only available for Teleport Enterprise.

Here is an example of this setting in the `teleport.yaml` :

```
auth_service:
  authentication:
    type: oidc
```

###FIDO U2F###

Teleport supports [FIDO U2F](https://www.yubico.com/about/background/fido/) hardware keys as a second authentication factor. By default U2F is disabled. To start using U2F:

* Enable U2F in Teleport configuration `/etc/teleport.yaml`.
* For CLI-based logins you have to install [u2f-host](https://developers.yubico.com/libu2f-host/) utility.
* For web-based logins you have to use Google Chrome, as it is the only browser supporting U2F at this time.

```
# snippet from /etc/teleport.yaml to show an example configuration of U2F:
auth_service:
  authentication:
    type: local
    second_factor: u2f
    # this section is needed only if second_factor is set to 'u2f'
    u2f:
       # app_id must point to the URL of the Teleport Web UI (proxy) accessible
       # by the end users
       app_id: https://localhost:3080
       # facets must list all proxy servers if there are more than one deployed
       facets:
       - https://localhost:3080
```

For single-proxy setups, the `app_id` setting can be equal to the domain name of the proxy, but this will prevent you from adding more proxies without changing the `app_id`. For multi-proxy setups, the `app_id` should be an HTTPS URL pointing to a JSON file that mirrors `facets` in the auth config.

**Logging in with U2F**

For logging in via the CLI, you must first install [u2f-host](https://developers.yubico.com/libu2f-host/). Installing:

```
# OSX:
$ brew install libu2f-host

# Ubuntu 16.04 LTS:
$ apt-get install u2f-host
```

Then invoke `tsh ssh` as usual to authenticate:

```
tsh --proxy <proxy-addr> ssh <hostname>
```

#Next steps#

Congratulations! You now are prepared with the basic principles of working with Teleport in production and should be ready to secure your SSH infrastructure in a more practical manner. Your next steps could be to check out the [Admin Guide](https://gravitational.com/teleport/docs/admin-guide/) in the Teleport docs and take a deep dive into the configuration of Teleport. I hope you enjoyed this tutorial!