Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support forward proxy in oauth2 #2163

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
122 changes: 122 additions & 0 deletions docs/oauth2-examples-forward-proxy.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,122 @@
---
title: Use an explicit forward proxy and Keycloak as OAuth 2.0 server
displayed_sidebar: docsSidebar
---
<!--
Copyright (c) 2005-2024 Broadcom. All Rights Reserved. The term "Broadcom" refers to Broadcom Inc. and/or its subsidiaries.

All rights reserved. This program and the accompanying materials
are made available under the terms of the under the Apache License,
Version 2.0 (the "License”); you may not use this file except in compliance
with the License. You may obtain a copy of the License at

https://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License 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.
-->

# Use an explicit forward proxy and Keycloak as OAuth 2.0 server

:::warning
To run this example you need to use the commercial [Tanzu RabbitMQ docker image](https://techdocs.broadcom.com/us/en/vmware-tanzu/data-solutions/tanzu-rabbitmq-oci/4-0/tanzu-rabbitmq-oci-image/overview.html). Support for **forward proxy** is a commercial feature.
:::

This guide explains how to set up OAuth 2.0 for RabbitMQ to access the Authorization Server via an explicit forward proxy.

* Access the RabbitMQ Management UI using a browser through OAuth2 Proxy

```plain
[ Keycloak ]
/|\
|
2.http request (*) | [ RabbitMQ ]
[ forward-proxy ] <----1. http request (*)--- [ http ]

```

RabbitMQ establishes a http connection with Keycloak via the forward-proxy in any of
these situations:

- You have configured `auth_oauth2.issuer` so that RabbitMQ downloads the OpenID configuration via the OpenID discovery endpoint.
- You have configured `auth_oauth2.issuer` or `auth_oauth2.jwks_url` so that RabbitMQ
downloads the tokens' signing keys.

## Prerequisites for Using OAuth 2 vith a forward proxy

* Docker
* make
* A local clone of a [GitHub repository](https://github.com/rabbitmq/rabbitmq-oauth2-tutorial/tree/next) for branch `next` that contains all the configuration files and scripts used on this example.
* The following entries in your /etc/hosts file. Without these entries you will get DNS errors in the browser.
```
localhost keycloak rabbitmq forward-proxy
```

:::info
`make start-keycloak` will
generate the TLS certificate and private keys necessary. These certificates have an expiration date.

In case of any error messages that hint at expired or invalid certificates, stop Keycloak and run `make clean-certs` to regenerate the certificates and private keys,
then restart Keycloak and the proxy
:::

## Deploy Keycloak

Deploy Keycloak by running the following command which deploys keycloak on its own network called `keycloak_net`:
```bash
PROVIDER_NETWORK=keycloak_net make start-keycloak
```

To access Keycloak Management UI, go to https://keycloak:8443/ and enter `admin` as username and password.

There is a dedicated **Keycloak realm** called `Test` configured as follows:

* [rsa](https://keycloak:8443/admin/master/console/#/realms/test/keys) signing key
* [rsa provider]https://keycloak:8443/admin/master/console/#/realms/test/keys/providers)
* `rabbitmq-proxy-client` client

## Start Forward Proxy

To start the forward proxy, run the following command which deploys forward-proxy in
two networks, `keycloak_net` and `rabbitmq_net`:

```bash
PROVIDER_NETWORK=keycloak_net make start-forward-proxy
```

The forward proxy is configured using [httpd.conf](https://github.com/rabbitmq/rabbitmq-oauth2-tutorial/tree/next/conf/forward-proxy/httpd/httpd.conf). This type of configuration inserts the access token into the HTTP **Authorization** header.


## Start RabbitMQ

To start RabbitMQ run the following command which deploys rabbitmq in its own network `rabbitmq_net`:

```
export IMAGE=<Tanzu RabbitMQ OCI image name>
export IMAGE_TAG=<Tanzu RabbitMQ OCI image tag>
MODE=forward-proxy OAUTH_PROVIDER=keycloak make start-rabbitmq
```

## Access [management UI](./management/)

Go to https://rabbitmq:15671/, proceed to login, and enter the credentials
`rabbit_admin` as username and `rabbit_admin` as password when Keycloak prompts you.
You should be redirected back to RabbitMQ management UI.

Take into account that the management UI running in the browser goes straight to keycloak.
In other words, it does not go via the forward-proxy. If you really want the management UI to
go via the forward-proxy you would have to configure the browser. That is beyond
the scope of this example.

However, in order to validate the token the management UI received from keycloak, RabbitMQ has to connect to keycloak via the forward-proxy. This is necessary in order to download the signing keys and to download the OpenID configuration if you only configured the `issuer` URL.

## Access Management api

To access the management api run the following command. It uses the client [mgt_api_client](https://keycloak:8443/admin/master/console/#/test/clients/c5be3c24-0c88-4672-a77a-79002fcc9a9d/settings) which has the scope [rabbitmq.tag:administrator](https://keycloak:8443/admin/master/console/#/test/client-scopes/f6e6dd62-22bf-4421-910e-e6070908764c/settings).

```bash
make curl-keycloak url=https://localhost:15671/api/overview client_id=mgt_api_client secret=LWOuYqJ8gjKg3D2U8CJZDuID3KiRZVDa realm=test
```
2 changes: 1 addition & 1 deletion docs/oauth2-examples-keycloak.md
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@ RabbitMQ is deployed with TLS enabled and Keycloak is configured with the corres
To access the management api run the following command. It uses the client [mgt_api_client](https://keycloak:8443/admin/master/console/#/test/clients/c5be3c24-0c88-4672-a77a-79002fcc9a9d/settings) which has the scope [rabbitmq.tag:administrator](https://keycloak:8443/admin/master/console/#/test/client-scopes/f6e6dd62-22bf-4421-910e-e6070908764c/settings).

```bash
make curl-keycloak url=https://localhost:15671/api/overview client_id=mgt_api_client secret=LWOuYqJ8gjKg3D2U8CJZDuID3KiRZVDa
make curl-keycloak url=https://localhost:15671/api/overview client_id=mgt_api_client secret=LWOuYqJ8gjKg3D2U8CJZDuID3KiRZVDa realm=test
```

## Application authentication and authorization with PerfTest
Expand Down
4 changes: 4 additions & 0 deletions docs/oauth2-examples/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,10 @@ The guide is accompanied by [a public GitHub repository](https://github.com/rabb
* [Google](./oauth2-examples-google) **NOT SUPPORTED**
* [Multiple OAuth 2.0 servers and/or audiences](./oauth2-examples-multiresource)

### Examples for Tanzu RabbitMQ (commercial-only feature)

* [Forward proxy](./oauth2-examples-forward-proxy)

## Prerequisites Used by the Examples in This Guide {#prerequisites}

* Docker must be installed
Expand Down
7 changes: 4 additions & 3 deletions docs/oauth2.md
Original file line number Diff line number Diff line change
Expand Up @@ -159,6 +159,7 @@ In chronological order, here is the sequence of events that occur when a client
| `auth_oauth2.https.fail_if_no_peer_cert` | Used together with `auth_oauth2.https.peer_verification = verify_peer`. When set to `true`, TLS connection will be rejected if the client fails to provide a certificate. The default value is `false`.
| `auth_oauth2.https.hostname_verification` | Enable wildcard-aware hostname verification for key server. Available values: `wildcard`, `none`. The default value is `none`.
| `auth_oauth2.https.crl_check` | [Perform CRL verification](https://www.erlang.org/doc/man/ssl#type-crl_check) (Certificate Revocation List) verification. Default value is false.
| `auth_oauth2.proxy` | Configures explicit [forward proxy](https://techdocs.broadcom.com/us/en/vmware-tanzu/data-solutions/tanzu-rabbitmq-oci/4-0/tanzu-rabbitmq-oci-image/overview.html) used to connect to the `auth_oauth2.issuer` URL. **This is a commercial-only feature**. More information on how to use it can be found on [this example](./oauth2-examples-forward-proxy).
| `auth_oauth2.algorithms` | Restrict [the usable algorithms](https://github.com/potatosalad/erlang-jose#algorithm-support).
| `auth_oauth2.verify_aud` | Whether to verify the [token's `aud`](#token-validation) field or not. The default value is `true`.
| `auth_oauth2.resource_servers` | [Multiple OAuth 2.0 resources configuration](#multiple-resource-servers-configuration).
Expand Down Expand Up @@ -277,7 +278,6 @@ auth_oauth2.algorithms.1 = HS256
auth_oauth2.algorithms.2 = RS256
```


## Multiple Resource Servers Сonfiguration {#multiple-resource-servers-configuration}

Each `auth_oauth2.resource_servers.<id/index>.` entry has the following variables shown in the table below. Except for the variables `id` and `oauth_provider_id`, if a resource does not configure a variable, RabbitMQ uses the variable configured at the root level. For instance, if the resource `auth_oauth2.resource_servers.prod` does not configure `preferred_username_claims` variable, RabbitMQ uses the value configured in `auth_oauth2.preferred_username_claims` for the resource `prod`.
Expand Down Expand Up @@ -322,8 +322,9 @@ Each `auth_oauth2.oauth_providers.{id/index}` entry has the following sub-keys.
| `https.depth` | The maximum number of non-self-issued intermediate certificates that may follow the peer certificate in a valid [certification path](ssl#peer-verification-depth). The default value is 10.
| `https.verify` | Configures [peer verification](ssl#peer-verification). Available values: `verify_none`, `verify_peer`. The default value is `verify_peer` if there are trusted CA installed in the OS or `auth_oauth2.https.cacertfile` is set.
| `https.fail_if_no_peer_cert` | Used together with `auth_oauth2.https.peer_verification = verify_peer`. When set to `true`, TLS connection will be rejected if the client fails to provide a certificate. The default value is `false`.
| `https.hostname_verification` | Enable wildcard-aware hostname verification for key server. Available values: `wildcard`, `none`. The default value is `none`.
| `https.crl_check` | [Perform CRL verification](https://www.erlang.org/doc/man/ssl#type-crl_check) (Certificate Revocation List) verification. Default value is false.
| `https.hostname_verification`| Enable wildcard-aware hostname verification for key server. Available values: `wildcard`, `none`. The default value is `none`.
| `https.crl_check` | [Perform CRL verification](https://www.erlang.org/doc/man/ssl#type-crl_check) (Certificate Revocation List) verification. Default value is false.
| `auth_oauth2.proxy` | Configures explicit [forward proxy](https://techdocs.broadcom.com/us/en/vmware-tanzu/data-solutions/tanzu-rabbitmq-oci/4-0/tanzu-rabbitmq-oci-image/overview.html) used to connect to the `issuer` URL. **This is a commercial-only feature**. More information on how to use it can be found on [this example](./oauth2-examples-forward-proxy).
| `signing_keys` | Local filesystem paths to the [signing key files](#signing-key-files). The files must exist and be readable.
| `default_key` | ID of the default signing key.
| `algorithms` | Used to restrict [the list of enabled algorithms](https://github.com/potatosalad/erlang-jose#algorithm-support).
Expand Down