# Run the PagerDuty Access Request Plugin

With Teleport's PagerDuty integration, engineers can access the infrastructure they need to resolve incidents quickly—without longstanding admin permissions that can become a vector for attacks. This guide explains how to set up Teleport's Access Request plugin for PagerDuty.

## How it works

Teleport's PagerDuty integration allows you to treat Teleport Role Access Requests as PagerDuty incidents, notify the appropriate on-call team, and approve or deny the requests via Teleport. You can also configure the plugin to approve Role Access Requests automatically if the user making the request is on the on-call team for a service affected by an incident.

This integration is hosted on Teleport Cloud

In Teleport Enterprise Cloud, Teleport manages the PagerDuty integration for you, and you can enroll the PagerDuty integration from the Teleport Web UI.

Visit the Teleport Web UI and on the left sidebar, click **Add New** followed by **Integration**:

![Enroll an Access Request plugin](/docs/assets/images/enroll-ee64e35054da594e264c55422bf39c7b.png)

On the "Select Integration Type" menu, click the tile for your integration. You will see a page with instructions to set up the integration, as well as a form that you can use to configure the integration.

![PagerDuty plugin architecture](/docs/assets/images/diagram-284c7b132128f9c899cf155b89d26faf.png)

## Prerequisites

- A running Teleport Enterprise cluster. If you want to get started with Teleport, [sign up](https://goteleport.com/signup) for a free trial or [set up a demo environment](https://goteleport.com/docs/get-started/deploy-community.md).

- The `tctl` and `tsh` clients.

  Installing `tctl` and `tsh` clients

  1. Determine the version of your Teleport cluster. The `tctl` and `tsh` clients must be at most one major version behind your Teleport cluster version. Send a GET request to the Proxy Service at `/v1/webapi/find` and use a JSON query tool to obtain your cluster version. Replace teleport.example.com:443 with the web address of your Teleport Proxy Service:

     ```
     $ TELEPORT_DOMAIN=teleport.example.com:443
     $ TELEPORT_VERSION="$(curl -s https://$TELEPORT_DOMAIN/v1/webapi/find | jq -r '.server_version')"
     ```

  2. Follow the instructions for your platform to install `tctl` and `tsh` clients:

     **Mac**

     Download the signed macOS .pkg installer for Teleport, which includes the `tctl` and `tsh` clients:

     ```
     $ curl -O https://cdn.teleport.dev/teleport-${TELEPORT_VERSION?}.pkg
     ```

     In Finder double-click the `pkg` file to begin installation.

     ---

     DANGER

     Using Homebrew to install Teleport is not supported. The Teleport package in Homebrew is not maintained by Teleport and we can't guarantee its reliability or security.

     ---

     **Windows - Powershell**

     ```
     $ curl.exe -O https://cdn.teleport.dev/teleport-v${TELEPORT_VERSION?}-windows-amd64-bin.zip
     Unzip the archive and move the `tctl` and `tsh` clients to your %PATH%
     NOTE: Do not place the `tctl` and `tsh` clients in the System32 directory, as this can cause issues when using WinSCP.
     Use %SystemRoot% (C:\Windows) or %USERPROFILE% (C:\Users\<username>) instead.
     ```

     **Linux**

     All of the Teleport binaries in Linux installations include the `tctl` and `tsh` clients. For more options (including RPM/DEB packages and downloads for i386/ARM/ARM64) see our [installation page](https://goteleport.com/docs/installation.md).

     ```
     $ curl -O https://cdn.teleport.dev/teleport-v${TELEPORT_VERSION?}-linux-amd64-bin.tar.gz
     $ tar -xzf teleport-v${TELEPORT_VERSION?}-linux-amd64-bin.tar.gz
     $ cd teleport
     $ sudo ./install
     Teleport binaries have been copied to /usr/local/bin
     ```

**Recommended:** Configure Machine & Workload Identity to provide short-lived Teleport credentials to the plugin. Before following this guide, follow a Machine & Workload Identity [deployment guide](https://goteleport.com/docs/machine-workload-identity/deployment.md) to run the `tbot` binary on your infrastructure.

- A PagerDuty account with the "Admin", "Global Admin", or "Account Owner" roles. These roles are necessary for generating an API token that can list and look up user profiles.

  You can see your role by visiting your user page in PagerDuty, navigating to the "Permissions & Teams" tab, and checking the value of the "Base Role" field.

- Either a Linux host or Kubernetes cluster where you will run the PagerDuty plugin.

- To check that you can connect to your Teleport cluster, sign in with `tsh login`, then verify that you can run `tctl` commands using your current credentials.

  For example, run the following command, assigning teleport.example.com to the domain name of the Teleport Proxy Service in your cluster and email\@example.com to your Teleport username:

  ```
  $ tsh login --proxy=teleport.example.com --user=email@example.com
  $ tctl status
  Cluster  teleport.example.com
  Version  19.0.0-dev
  CA pin   sha256:abdc1245efgh5678abdc1245efgh5678abdc1245efgh5678abdc1245efgh5678
  ```

  If you can connect to the cluster and run the `tctl status` command, you can use your current credentials to run subsequent `tctl` commands from your workstation. If you host your own Teleport cluster, you can also run `tctl` commands on the computer that hosts the Teleport Auth Service for full permissions.

## Step 1/8. Create services

To demonstrate the PagerDuty plugin, create two services in PagerDuty. For each service, fill in only the "Name" field and skip all other configuration screens, leaving options as the defaults:

- `Teleport Access Request Notifications`
- `My Critical Service`

We will configure the PagerDuty plugin to create an incident in the `Teleport Access Request Notifications` service when certain users create an Access Request.

For users on the on-call team for `My Critical Service` (in this case, your PagerDuty user), we will configure the PagerDuty plugin to approve Access Requests automatically, letting them investigate incidents on the service quickly.

## Step 2/8. Define RBAC resources

The Teleport PagerDuty plugin works by receiving Access Request events from the Teleport Auth Service and, based on these events, interacting with the PagerDuty API.

In this section, we will show you how to configure the PagerDuty plugin by defining the following RBAC resources:

- A role called `editor-requester`, which can request the built-in `editor` role. We will configure this role to open a PagerDuty incident whenever a user requests it, notifying the on-call team for the `Teleport Access Request Notifications` service.
- A role called `demo-role-requester`, which can request a role called `demo-role`. We will configure the PagerDuty plugin to auto-approve this request whenever the user making it is on the on-call team for `My Critical Service`.
- A user and role called `access-plugin` that the PagerDuty plugin will assume in order to authenticate to the Teleport Auth Service. This role will have permissions to approve Access Requests from users on the on-call team for `My Critical Service` automatically.
- A role called `access-plugin-impersonator` that allows you to generate signed credentials that the PagerDuty plugin can use to authenticate with your Teleport cluster.

### `editor-requester`

Create a file called `editor-request-rbac.yaml` with the following content, which defines a role called `editor-reviewer` that can review requests for the `editor` role, plus an `editor-requester` role that can request this role.

```
kind: role
version: v5
metadata:
  name: editor-reviewer
spec:
  allow:
    review_requests:
      roles: ['editor']
---
kind: role
version: v5
metadata:
  name: editor-requester
spec:
  allow:
    request:
      roles: ['editor']
      thresholds:
        - approve: 1
          deny: 1
      annotations:
        pagerduty_notify_service: ["Teleport Access Request Notifications"]

```

The Teleport Auth Service *annotates* Access Request events with metadata based on the roles of the Teleport user submitting the Access Request. The PagerDuty plugin reads these annotations to determine how to respond to a new Access Request event.

Whenever a user with the `editor-requester` role requests the `editor` role, the PagerDuty plugin will read the `pagerduty_notify_service` annotation and notify PagerDuty to open an incident in the specified service, `Teleport Access Request Notifications`, until someone with the `editor-reviewer` role approves or denies the request.

Create the roles you defined:

```
$ tctl create -f editor-request-rbac.yaml
role 'editor-reviewer' has been created
role 'editor-requester' has been created
```

---

TIP

You can also create and edit roles using the Web UI. Go to **Access -> Roles** and click **Create New Role** or pick an existing role to edit.

---

### `demo-role-requester`

Create a file called `demo-role-requester.yaml` with the following content:

```
kind: role
version: v5
metadata:
  name: demo-role
---
kind: role
version: v5
metadata:
  name: demo-role-requester
spec:
  allow:
    request:
      roles: ['demo-role']
      thresholds:
        - approve: 1
          deny: 1
      annotations:
        pagerduty_services: ["My Critical Service"]

```

Users with the `demo-role-requester` role can request the `demo-role` role. When such a user makes this request, the PagerDuty plugin will read the `pagerduty_services` annotation. If the user making the request is on the on-call team for a service listed as a value for the annotation, the plugin will approve the Access Request automatically.

In this case, the PagerDuty plugin will approve any requests from users on the on-call team for `My Critical Service`.

Create the resources:

```
$ tctl create -f demo-role-requester.yaml;
```

---

WARNING

For auto-approval to work, the user creating an Access Request must have a Teleport username that is also the email address associated with a PagerDuty account. In this guide, we will add the `demo-role-requester` role to your own Teleport account—which we assume is also your email address for PagerDuty—so you can request the `demo-role` role.

---

### `access-plugin`

Teleport's Access Request plugins authenticate to your Teleport cluster as a user with permissions to list, read, and update Access Requests. This way, plugins can retrieve Access Requests from the Teleport Auth Service, present them to reviewers, and modify them after a review.

Define a user and role called `access-plugin` by adding the following content to a file called `access-plugin.yaml`:

```
kind: role
version: v5
metadata:
  name: access-plugin
spec:
  allow:
    rules:
      - resources: ['access_request']
        verbs: ['list', 'read']
      - resources: ['access_plugin_data']
        verbs: ['update']
    review_requests:
      roles: ['demo-role']
      where: 'contains(request.system_annotations["pagerduty_services"], "My Critical Service")'
---
kind: user
metadata:
  name: access-plugin
spec:
  roles: ['access-plugin']
version: v2

```

Notice that the `access-plugin` role includes an `allow.review_requests.roles` field with `demo-role` as a value. This allows the plugin to review requests for the `demo-role` role.

We are also restricting the `access-plugin` role to reviewing only Access Requests associated with `My Critical Service`. To do so, we have defined a *predicate expression* in the `review_requests.where` field. This expression indicates that the plugin *cannot* review requests for `demo-role` unless the request contains an annotation with the key `pagerduty_services` and the value `My Critical Service`.

How "where" conditions work

The `where` field includes a predicate expression that determines whether a reviewer is allowed to review a specific request. You can include two functions in a predicate expression:

| Function   | Description                         | Example                                         |
| ---------- | ----------------------------------- | ----------------------------------------------- |
| `equals`   | A field is equivalent to a value.   | `equals(request.reason, "resolve an incident")` |
| `contains` | A list of strings includes a value. | `contains(reviewer.traits["team"], "devops")`   |

When you use the `where` field, you can include the following fields in your predicate expression:

| Field                        | Type                  | Description                                                                        |
| ---------------------------- | --------------------- | ---------------------------------------------------------------------------------- |
| `reviewer.roles`             | `[]string`            | A list of the reviewer's Teleport role names                                       |
| `reviewer.traits`            | `map[string][]string` | A map of the reviewer's Teleport traits by the name of the trait                   |
| `request.roles`              | `[]string`            | A list of the Teleport roles a user is requesting                                  |
| `request.reason`             | `string`              | The reason attached to the request                                                 |
| `request.system_annotations` | `map[string][]string` | A map of annotations for the request by annotation key, e.g., `pagerduty_services` |

You can combine functions using the following operators:

| Operator | Format                   | Description                                                        |
| -------- | ------------------------ | ------------------------------------------------------------------ |
| `&&`     | `function && function`   | Evaluates to true if both functions evaluate to true               |
| `\|\|`   | `function \|\| function` | Evaluates to true if either one or both functions evaluate to true |
| `!`      | `!function`              | Evaluates to true if the function evaluates to false               |

An example of a function is `equals(request.reason, "resolve an incident")`. To configure an `allow` condition to match any Access Request that does not include the reason, "resolve an incident", you could use the function, `!equals(request.reason, "resolve an incident")`.

Create the user and role:

```
$ tctl create -f access-plugin.yaml
```

### `access-plugin-impersonator`

As with all Teleport users, the Teleport Auth Service authenticates the `access-plugin` user by issuing short-lived TLS credentials. In this case, we will need to request the credentials manually by *impersonating* the `access-plugin` role and user.

If you are running a self-hosted Teleport Enterprise cluster and are using `tctl` from the Auth Service host, you will already have impersonation privileges.

To grant your user impersonation privileges for `access-plugin`, define a role called `access-plugin-impersonator` by pasting the following YAML document into a file called `access-plugin-impersonator.yaml`:

```
kind: role
version: v5
metadata:
  name: access-plugin-impersonator
spec:
  allow:
    impersonate:
      roles:
      - access-plugin
      users:
      - access-plugin

```

Create the `access-plugin-impersonator` role:

```
$ tctl create -f access-plugin-impersonator.yaml
```

### Add roles to your user

Later in this guide, your Teleport user will take three actions that require additional permissions:

- Generate signed credentials that the PagerDuty plugin will use to connect to your Teleport Cluster
- Manually review an Access Request for the `editor` role
- Create an Access Request for the `demo-role` role

To grant these permissions to your user, give your user the `editor-reviewer`, `access-plugin-impersonator`, and `demo-role-requester` roles we defined earlier.

Open your user definition in an editor:

```
$ TELEPORT_USER=$(tsh status --format=json | jq -r .active.username)
$ tctl edit users/${TELEPORT_USER?}
```

Edit the user to include the roles you just created:

```
  roles:
   - access
   - auditor
   - editor
+  - editor-reviewer
+  - access-plugin-impersonator
+  - demo-role-requester

```

Apply your changes by saving and closing the file in your editor.

Log out of your Teleport cluster and log in again. You will now be able to review requests for the `editor` role, request the `demo-role` role, and generate signed certificates for the `access-plugin` role and user.

### Create a user who will request access

Create a user called `myuser` who has the `editor-requester` role. Later in this guide, you will create an Access Request as this user to test the PagerDuty plugin:

```
$ tctl users add myuser --roles=editor-requester
```

`tctl` will print an invitation URL to your terminal. Visit the URL and log in as `myuser` for the first time, registering credentials as configured for your Teleport cluster.

## Step 3/8. Install the Teleport PagerDuty plugin

**Download**

Access Request Plugins are available as `amd64` and `arm64` Linux binaries for downloading. Replace `ARCH` with your required version.

```
$ curl -L -O https://cdn.teleport.dev/teleport-access-pagerduty-v13.3.7-linux-ARCH-bin.tar.gz
$ tar -xzf teleport-access-pagerduty-v13.3.7-linux-ARCH-bin.tar.gz
$ cd teleport-access-pagerduty
$ sudo ./install
```

Make sure the binary is installed:

```
$ teleport-pagerduty version
teleport-pagerduty v13.3.7 git:teleport-pagerduty-v13.3.7-fffffffff go1.25.9
```

**Docker Image**

```
$ docker pull public.ecr.aws/gravitational/teleport-plugin-pagerduty:13.3.7
```

Make sure the plugin is installed by running the following command:

```
$ docker run public.ecr.aws/gravitational/teleport-plugin-pagerduty:13.3.7 version
teleport-pagerduty v13.3.7 1.25.9
```

For a list of available tags, visit [Amazon ECR Public Gallery](https://gallery.ecr.aws/gravitational/teleport-plugin-pagerduty).

**From Source**

To install from source you need `git` and `go` installed. If you do not have Go installed, visit the Go [downloads page](https://go.dev/dl/).

```
$ git clone https://github.com/gravitational/teleport -b branch/v19
$ cd teleport/integrations/access/pagerduty
$ git checkout v13.3.7
$ make build/teleport-pagerduty
```

Move the `teleport-pagerduty` binary into your PATH.

Make sure the binary is installed:

```
$ teleport-pagerduty version
teleport-pagerduty v13.3.7 git:teleport-pagerduty-v13.3.7-fffffffff go1.25.9
```

**Helm Chart**

Allow Helm to install charts that are hosted in the Teleport Helm repository:

```
$ helm repo add teleport https://charts.releases.teleport.dev
```

Update the cache of charts from the remote repository:

```
$ helm repo update
```

## Step 4/8. Export the access plugin identity

Give the plugin access to a Teleport identity file. We recommend using Machine ID for this in order to produce short-lived identity files that are less dangerous if exfiltrated, though in demo deployments, you can generate longer-lived identity files with `tctl`:

**Machine & Workload Identity**

Configure `tbot` with an output that will produce the credentials needed by the plugin. As the plugin will be accessing the Teleport API, the correct output type to use is `identity`.

For this guide, the `directory` destination will be used. This will write these credentials to a specified directory on disk. Ensure that this directory can be written to by the Linux user that `tbot` runs as, and that it can be read by the Linux user that the plugin will run as.

Modify your `tbot` configuration to add an `identity` output.

If running `tbot` on a Linux server, use the `directory` output to write identity files to the `/opt/machine-id` directory:

```
services:
- type: identity
  destination:
    type: directory
    # For this guide, /opt/machine-id is used as the destination directory.
    # You may wish to customize this. Multiple outputs cannot share the same
    # destination.
    path: /opt/machine-id

```

If running `tbot` on Kubernetes, write the identity file to Kubernetes secret instead:

```
services:
  - type: identity
    destination:
      type: kubernetes_secret
      name: teleport-plugin-pagerduty-identity

```

If operating `tbot` as a background service, restart it. If running `tbot` in one-shot mode, execute it now.

You should now see an `identity` file under `/opt/machine-id` or a Kubernetes secret named `teleport-plugin-pagerduty-identity`. This contains the private key and signed certificates needed by the plugin to authenticate with the Teleport Auth Service.

**Long-lived identity files**

Like all Teleport users, `access-plugin` needs signed credentials in order to connect to your Teleport cluster. You will use the `tctl auth sign` command to request these credentials.

The following `tctl auth sign` command impersonates the `access-plugin` user, generates signed credentials, and writes an identity file to the local directory:

```
$ tctl auth sign --user=access-plugin --out=identity
```

The plugin connects to the Teleport Auth Service's gRPC endpoint over TLS.

The identity file, `identity`, includes both TLS and SSH credentials. The plugin uses the SSH credentials to connect to the Proxy Service, which establishes a reverse tunnel connection to the Auth Service. The plugin uses this reverse tunnel, along with your TLS credentials, to connect to the Auth Service's gRPC endpoint.

Certificate Lifetime

By default, `tctl auth sign` produces certificates with a relatively short lifetime. For production deployments, we suggest using [Machine & Workload Identity](https://goteleport.com/docs/machine-workload-identity/introduction.md) to programmatically issue and renew certificates for your plugin. See our Machine & Workload Identity [getting started guide](https://goteleport.com/docs/machine-workload-identity/getting-started.md) to learn more.

Note that you cannot issue certificates that are valid longer than your existing credentials. For example, to issue certificates with a 1000-hour TTL, you must be logged in with a session that is valid for at least 1000 hours. This means your user must have a role allowing a `max_session_ttl` of at least 1000 hours (60000 minutes), and you must specify a `--ttl` when logging in:

```
$ tsh login --proxy=teleport.example.com --ttl=60060
```

If you are running the plugin on a Linux server, create a data directory to hold certificate files for the plugin:

```
$ sudo mkdir -p /var/lib/teleport/plugins/api-credentials
$ sudo mv identity /var/lib/teleport/plugins/api-credentials
```

If you are running the plugin on Kubernetes, create a Kubernetes secret that contains the Teleport identity file:

```
$ kubectl -n teleport create secret generic --from-file=identity teleport-plugin-pagerduty-identity
```

Once the Teleport credentials expire, you will need to renew them by running the `tctl auth sign` command again.

## Step 5/8. Set up a PagerDuty API key

Generate an API key that the PagerDuty plugin will use to create and modify incidents as well as list users, services, and on-call policies.

In your PagerDuty dashboard, go to **Integrations → API Access Keys** and click **Create New API Key**. Add a key description, e.g., "Teleport integration". Leave "Read-only API Key" unchecked. Copy the key to a file on your local machine. We'll use the key in the plugin config file later.

![Create an API
key](/docs/assets/images/pagerduty-integrations-ce76869bb426258a15e525878c8b2aa2.png)

## Step 6/8. Configure the PagerDuty plugin

At this point, you have generated credentials that the PagerDuty plugin will use to connect to Teleport and the PagerDuty API. You will now configure the PagerDuty plugin to use these credentials, plus adjust any settings required for your environment.

**Executable or Docker**

Teleport's PagerDuty plugin has its own configuration file in TOML format. On the host where you will run the PagerDuty plugin, generate a boilerplate config by running the following commands:

```
$ teleport-pagerduty configure > teleport-pagerduty.toml
$ sudo mv teleport-pagerduty.toml /etc
```

**Helm Chart**

The PagerDuty Helm Chart uses a YAML values file to configure the plugin. On the host where you have Helm installed, create a file called `teleport-pagerduty-values.yaml` based on the following example:

```
teleport:
  address: ""                 # Teleport Auth Service GRPC API address
  identitySecretName: ""      # Identity secret name
  identitySecretPath: ""      # Identity secret path

pagerduty:
  apiKey: ""                  # PagerDuty API Key
  userEmail: ""               # PagerDuty bot user email (Could be admin email)

```

Saving the configuration to another location

The PagerDuty plugin expects the configuration to be in `/etc/teleport-pagerduty.toml`, but you can override this with the `--config` flag when you run the plugin binary later in this guide.

Edit the configuration file in `/etc/teleport-pagerduty.toml` as explained below:

### `[teleport]`

The PagerDuty plugin uses this section to connect to your Teleport cluster:

**Executable**

**`addr`**: Include the hostname and HTTPS port of your Teleport Proxy Service or Teleport Enterprise Cloud account (e.g., `teleport.example.com:443` or `mytenant.teleport.sh:443`).

**`identity`**: Fill this in with the path to the identity file you exported earlier.

**`client_key`**, **`client_crt`**, **`root_cas`**: Comment these out, since we are not using them in this configuration.

**Helm Chart**

**`address`**: Include the hostname and HTTPS port of your Teleport Proxy Service or Teleport Enterprise Cloud tenant (e.g., `teleport.example.com:443` or `mytenant.teleport.sh:443`).

**`identitySecretName`**: Fill in the `identitySecretName` field with the name of the Kubernetes secret you created earlier.

**`identitySecretPath`**: Fill in the `identitySecretPath` field with the path of the identity file within the Kubernetes secret. If you have followed the instructions above, this will be `identity`.

If you are providing credentials to the plugin using a `tbot` binary that runs on a Linux server, make sure the value of `identity` is the same as the path of the identity file you configured `tbot` to generate, `/opt/machine-id/identity`.

Configure the plugin to periodically reload the identity file, ensuring that it does not attempt to connect to the Teleport Auth Service with expired credentials.

Add the following to the `teleport` section of the configuration:

```
refresh_identity = true

```

### `[pagerduty]`

Assign `api_key` to the PagerDuty API key you generated earlier.

Assign `user_email` to the email address of a PagerDuty user on the account associated with your API key. When the PagerDuty plugin creates a new incident, PagerDuty will display this incident as created by that user.

Overriding annotation names

This guide has assumed that the Teleport PagerDuty plugin uses `pagerduty_notify_service` annotation to determine which services to notify of new Access Request events and the `pagerduty_services` annotation to configure auto-approval.

If you would like to use a different name for these annotations in your Teleport roles, you can assign the `pagerduty.notify_service` and `pagerduty.services` fields.

The final configuration should resemble the following:

**Executable or Docker**

```
# example teleport-pagerduty configuration TOML file
[teleport]
auth_server = "myinstance.teleport.sh:443"                  # Teleport Cloud proxy HTTPS address
identity = "/var/lib/teleport/plugins/pagerduty/identity"   # Identity file path
refresh_identity = true                                     # Refresh identity file periodically

[pagerduty]
api_key = "key"               # PagerDuty API Key
user_email = "me@example.com" # PagerDuty bot user email (Could be admin email)

[log]
output = "stderr" # Logger output. Could be "stdout", "stderr" or "/var/lib/teleport/pagerduty.log"
severity = "INFO" # Logger severity. Could be "INFO", "ERROR", "DEBUG" or "WARN".


```

**Helm Chart**

```
teleport:
  # Teleport HTTPS Proxy web address, for Teleport Enterprise Cloud should be in the form "your-account.teleport.sh:443"
  address: "teleport.example.com:443"
  # Secret containing identity
  identitySecretName: teleport-plugin-pagerduty-identity
  # Path within the secret containing the identity file.
  identitySecretPath: identity

pagerduty:
  apiKey: "key"                # PagerDuty API Key
  userEmail: "me@example.com"  # PagerDuty bot user email (Could be admin email)

log:
  output: "stderr"  # Logger output. Could be "stdout", "stderr" or "/var/lib/teleport/pagerduty.log"
  severity: "INFO"  # Logger severity. Could be "INFO", "ERROR", "DEBUG" or "WARN".


```

## Step 7/8. Test the PagerDuty plugin

**Executable**

After you configure the PagerDuty plugin, run the following command to start it. The `-d` flag will provide debug information to ensure that the plugin can connect to PagerDuty and your Teleport cluster:

```
$ teleport-pagerduty start -d
DEBU   DEBUG logging enabled logrus/exported.go:117
INFO   Starting Teleport Access PagerDuty extension 0.1.0-dev.1: pagerduty/main.go:124
DEBU   Checking Teleport server version pagerduty/main.go:226
DEBU   Starting a request watcher... pagerduty/main.go:288
DEBU   Starting PagerDuty API health check... pagerduty/main.go:170
DEBU   Starting secure HTTPS server on :8081 utils/http.go:146
DEBU   Watcher connected pagerduty/main.go:252
DEBU   PagerDuty API health check finished ok pagerduty/main.go:176
DEBU   Setting up the webhook extensions pagerduty/main.go:178
```

**Docker**

Run the plugin:

```
$ docker run -v <path-to-config>:/etc/teleport-pagerduty.toml public.ecr.aws/gravitational/teleport-plugin-pagerduty:19.0.0-dev start
```

**Helm Chart**

After modifying your configuration, run the bot with the following command:

```
$ helm upgrade --install teleport-plugin-pagerduty teleport/teleport-plugin-pagerduty --values teleport-pagerduty-values.yaml
```

To inspect the plugin's logs, use the following command:

```
$ kubectl logs deploy/teleport-plugin-pagerduty
```

Debug logs can be enabled by setting `log.severity` to `DEBUG` in `teleport-pagerduty-values.yaml` and executing the `helm upgrade ...` command above again. Then you can restart the plugin with the following command:

```
$ kubectl rollout restart deployment teleport-plugin-pagerduty
```

### Create an Access Request

As the Teleport user `myuser`, create an Access Request for the `editor` role:

**As an Admin**

A Teleport admin can create an Access Request for another user with `tctl`:

```
$ tctl request create myuser --roles=editor
```

**As a User**

Users can use `tsh` to create an Access Request and log in with approved roles:

```
$ tsh request create --roles=editor
Seeking request approval... (id: 8f77d2d1-2bbf-4031-a300-58926237a807)
```

**From the Web UI**

Users can request access using the Web UI by visiting "Identity", clicking "Access Requests" and then "New Request":

![Creating an Access Request using the Web UI](/docs/assets/images/request-access-be784784ab25db7e651c87817044f082.png)

You should see a log resembling the following on your PagerDuty plugin host:

```
INFO   Successfully created PagerDuty incident pd_incident_id:00000000000000
pd_service_name:Teleport Access Request Notifications
request_id:00000000-0000-0000-0000-000000000000 request_op:put
request_state:PENDING pagerduty/app.go:366

```

In PagerDuty, you will see a new incident containing information about the Access Request:

![PagerDuty dashboard showing an Access
Request](/docs/assets/images/new-access-req-incident-be24454e26357eb84ab794d95f8814fa.png)

### Resolve the request

Once you receive an Access Request message, click the link to visit Teleport and approve or deny the request:

![Reviewing a request](/docs/assets/images/review-request-51dc06eae57234cbbfea4e13f0879884.png)

Reviewing from the command line

You can also review an Access Request from the command line:

**As an Admin**

```
Replace REQUEST_ID with the id of the request
$ tctl request approve REQUEST_ID
$ tctl request deny REQUEST_ID
```

**As a User**

```
Replace REQUEST_ID with the id of the request
$ tsh request review --approve REQUEST_ID
$ tsh request review --deny REQUEST_ID
```

---

AUDITING ACCESS REQUESTS

When the PagerDuty plugin sends a notification, anyone who receives the notification can follow the enclosed link to an Access Request URL. While users must be authorized via their Teleport roles to review Access Request, you should still check the Teleport audit log to ensure that the right users are reviewing the right requests.

When auditing Access Request reviews, check for events with the type `Access Request Reviewed` in the Teleport Web UI.

---

### Trigger an auto-approval

As your Teleport user, create an Access Request for the `demo-role` role.

You will see a log similar to the following on your PagerDuty plugin host:

```
INFO   Successfully submitted a request approval
pd_user_email:myuser@example.com pd_user_name:My User
request_id:00000000-0000-0000-0000-000000000000 request_op:put
request_state:PENDING pagerduty/app.go:511

```

Your Access Request will appear as `APPROVED`:

```
$ tsh requests ls
ID                                   User               Roles     Created (UTC)       Status
------------------------------------ ------------------ --------- ------------------- --------
00000000-0000-0000-0000-000000000000 myuser@example.com demo-role 12 Aug 22 18:30 UTC APPROVED
```

## Step 8/8. Set up systemd

This section is only relevant if you are running the Teleport PagerDuty plugin on a Linux host.

In production, we recommend starting the Teleport plugin daemon via an init system like systemd. Here's the recommended Teleport plugin service unit file for systemd:

```
[Unit]
Description=Teleport Pagerduty Plugin
After=network.target

[Service]
Type=simple
Restart=on-failure
ExecStart=/usr/local/bin/teleport-pagerduty start --config=/etc/teleport-pagerduty.toml
ExecReload=/bin/kill -HUP $MAINPID
PIDFile=/run/teleport-pagerduty.pid

[Install]
WantedBy=multi-user.target

```

Save this as `teleport-pagerduty.service` in either `/usr/lib/systemd/system/` or another [unit file load path](https://www.freedesktop.org/software/systemd/man/systemd.unit.html#unit%20file%20load%20path) supported by systemd.

Enable and start the plugin:

```
$ sudo systemctl enable teleport-pagerduty
$ sudo systemctl start teleport-pagerduty
```

## Troubleshooting

Access Request plugins need permissions to list and read any Teleport resource types included in a request. This is because, when the plugin receives a resource request, it queries the Teleport Auth Service API for data about the requested resources.

If you receive an error message similar to the following, the Teleport roles for the Access Request plugin's identity do not have permissions to perform one or more operations against the Teleport API. In the example below, the Access Request plugin needs `list` and `read` permissions on the `user_group` resource:

```
ERRO   Failed to process request error:[
ERROR REPORT:
Original Error: *interceptors.RemoteError access denied to perform action "list" on "user_group", access denied to perform action "read" on "user_group"

```

Make sure the Teleport roles for the Access Request plugin's identity include permissions to list requested resources. To resolve the error above, for example, you could grant the following role to the Access Request plugin's identity:

```
kind: role
version: v7
metadata:
  name: read-user-groups
spec:
  allow:
    rules:
      - resources: [user_group]
        verbs: [list, read]

```
