From 89d820bf3d77fee1b627c9a88760dd6baa223a62 Mon Sep 17 00:00:00 2001 From: R-Lawton Date: Wed, 18 Dec 2024 17:30:13 +0000 Subject: [PATCH 1/2] Combining the two scp into the one document rather then per enviroment Signed-off-by: R-Lawton --- .../secure-protect-connect-k8s.md | 508 ------------------ ...openshift.md => secure-protect-connect.md} | 3 +- 2 files changed, 2 insertions(+), 509 deletions(-) delete mode 100644 doc/user-guides/full-walkthrough/secure-protect-connect-k8s.md rename doc/user-guides/full-walkthrough/{secure-protect-connect-openshift.md => secure-protect-connect.md} (98%) diff --git a/doc/user-guides/full-walkthrough/secure-protect-connect-k8s.md b/doc/user-guides/full-walkthrough/secure-protect-connect-k8s.md deleted file mode 100644 index aaa80e3f3..000000000 --- a/doc/user-guides/full-walkthrough/secure-protect-connect-k8s.md +++ /dev/null @@ -1,508 +0,0 @@ -# Secure, protect, and connect services with Kuadrant on Kubernetes - -## Prerequisites - -- You have completed the [Single-cluster Quick Start](https://docs.kuadrant.io/latest/getting-started-single-cluster/) or [Multi-cluster Quick Start](https://docs.kuadrant.io/latest/getting-started-multi-cluster/). - -### Local Cluster (metallb) - -> **Note:** If you are running on a local kind cluster, it is also recommended you use [metallb](https://metallb.universe.tf/) to setup an IP address pool to use with loadbalancer services for your gateways. An example script for configuring metallb based on the docker network once installed can be found [here](https://github.com/Kuadrant/kuadrant-operator/blob/main/utils/docker-network-ipaddresspool.sh). - -``` -./utils/docker-network-ipaddresspool.sh kind yq 1 | kubectl apply -n metallb-system -f - -``` - -## Overview - -In this guide, we will cover the different policies from Kuadrant and how you can use them to secure, protect and connect an Istio-controlled gateway in a single cluster, and how you can set more refined protection on the HTTPRoutes exposed by that gateway. - -Here are the steps we will go through: - -1. [Deploy a sample application](#deploy-the-example-app-we-will-serve-via-our-gateway) - -2. [Define a new Gateway](#define-a-new-istio-managed-gateway) - -3. [Ensure TLS-based secure connectivity to the gateway with a TLSPolicy](#define-the-tlspolicy) - -4. [Define a default RateLimitPolicy to set some infrastructure limits on your gateway](#define-infrastructure-rate-limiting) - -5. [Define a default AuthPolicy to deny all access to the gateway](#define-the-gateway-authpolicy) - -6. [Define a DNSPolicy to bring traffic to the gateway](#define-the-dnspolicy) - -7. [Override the Gateway's deny-all AuthPolicy with an endpoint-specific policy](#override-the-gateways-deny-all-authpolicy) - -8. [Override the Gateway rate limits with an endpoint-specific policy](#override-the-gateways-ratelimitpolicy) - -You will need to set the `KUBECTL_CONTEXT` environment variable for the kubectl context of the cluster you are targeting. - -If you have followed the single cluster setup, it should be something like below. -Adjust the name of the cluster accordingly to match the kubernetes cluster you are targeting. -You can get the current context with `kubectl config current-context` - -We use the namespace `kuadrant-system` in this tutorial so ensure that namespace exists before continuing - -```sh -# Typical single cluster context -export KUBECTL_CONTEXT=kind-kuadrant-local - -# Example context for additional 'multi cluster' clusters -# export KUBECTL_CONTEXT=kind-kuadrant-local-1 -``` - -To help with this walk through, you should also set a `KUADRANT_ZONE_ROOT_DOMAIN` environment variable to a domain you want to use. If you want to try DNSPolicy, this should also be a domain you have access to the DNS for in AWS Route53 or GCP. E.g.: - -```sh -export KUADRANT_ZONE_ROOT_DOMAIN=my.domain.iown -``` - -### Deploy the example app we will serve via our gateway - -```sh -kubectl --context $KUBECTL_CONTEXT apply -f https://raw.githubusercontent.com/Kuadrant/kuadrant-operator/main/examples/toystore/toystore.yaml -``` - -### Define a new Istio-managed gateway - -```sh -kubectl --context $KUBECTL_CONTEXT apply -f - < **Note:** You may have to create a cluster issuer in the Kubernetes cluster, depending on if one was created during your initial cluster setup or not. Here is an example of how to create a self-signed CA as a cluster issuer. This is a self signed issuer for simplicity, but you can use other issuers such as [letsencrypt](https://letsencrypt.org/). Refer to the [cert-manager docs](https://cert-manager.io/docs/configuration/acme/dns01/route53/#iam-user-with-long-term-access-key) - -```sh -kubectl --context $KUBECTL_CONTEXT apply -f - < **Note:** It may take a couple of minutes for the RateLimitPolicy to be applied depending on your cluster. - -The limit here is artificially low in order for us to show it working easily. Let's test it with our endpoint: - -```sh -for i in {1..10}; do curl -k --resolve api.${KUADRANT_ZONE_ROOT_DOMAIN}:443:${INGRESS_HOST} "https://api.$KUADRANT_ZONE_ROOT_DOMAIN/cars" && sleep 1; done -``` - -We should see `409 Too Many Requests`s start returning after the 5th request. - -### Define the Gateway AuthPolicy - -Communication is secured and we have some protection for our infrastructure, but we do not trust any client to access our endpoints. By default, we want to allow only authenticated access. To protect our gateway, we will add a _deny-all_ AuthPolicy. Later, we will override this with a more specific AuthPolicy for the API. - -```sh -kubectl --context $KUBECTL_CONTEXT apply -f - < **Note:** You may need to create a DNS Provider Secret resource depending on if one was created during your initial cluster setup or not. You should have an `aws-credentials` Secret already created in the `kuadrant-system` namespace. However, if it doesn't exist, you can follow these commands to create one: - -```sh -export AWS_ACCESS_KEY_ID=xxxxxxx # Key ID from AWS with Route 53 access -export AWS_SECRET_ACCESS_KEY=xxxxxxx # Access key from AWS with Route 53 access - -kubectl -n kuadrant-system create secret generic aws-credentials \ - --type=kuadrant.io/aws \ - --from-literal=AWS_ACCESS_KEY_ID=$AWS_ACCESS_KEY_ID \ - --from-literal=AWS_SECRET_ACCESS_KEY=$AWS_SECRET_ACCESS_KEY -``` - -Next, create the DNSPolicy. There are two options here. - - **Single gateway with no shared hostnames:** - -```sh -kubectl --context $KUBECTL_CONTEXT apply -f - < **Note:** This configuration will work fine for a single gateway also, but does create some additional records. - -```sh -kubectl --context $KUBECTL_CONTEXT apply -f - < **Note:** This resource is managed by kuadrant and so shouldn't be changed directly. - -```sh -kubectl --context $KUBECTL_CONTEXT get dnsrecord.kuadrant.io api-gateway-api -n kuadrant-system -o=yaml -``` - -With DNS in place, let's test it again. This time we expect a `403` still as the _deny-all_ policy is still in effect. Notice we no longer need to set the Host header directly. - -> **Note:** If you have followed through this guide on more than 1 cluster, the DNS record for the HTTPRoute hostname will have multiple IP addresses. This means that requests will be made in a round robin pattern across clusters as your DNS provider sends different responses to lookups. You may need to send multiple requests before one hits the cluster you are currently configuring. - -```sh -curl -k "https://api.$KUADRANT_ZONE_ROOT_DOMAIN/cars" -i -``` - -### Override the Gateway's deny-all AuthPolicy - -Next, we are going to allow authenticated access to our Toystore API. To do this, we will define an AuthPolicy that targets the HTTPRoute. Note that any new HTTPRoutes will still be affected by the gateway-level policy, but as we want users to now access this API, we need to override that policy. For simplicity, we will use API keys to authenticate the requests, though many other options are available. - -Let's define an API Key for users **bob** and **alice**. - -```sh -kubectl --context $KUBECTL_CONTEXT apply -f - < **Note:** It may take a couple of minutes for the RateLimitPolicy to be applied depending on your cluster. - -As just another example, we have given **bob** twice as many requests to use compared to everyone else. - -Let's test this new setup. - -By sending requests as **alice**: - -```sh -while :; do curl -k --resolve api.${KUADRANT_ZONE_ROOT_DOMAIN}:443:${INGRESS_HOST} --write-out '%{http_code}\n' --silent --output /dev/null -H 'Authorization: APIKEY IAMALICE' "https://api.$KUADRANT_ZONE_ROOT_DOMAIN/cars" | grep -E --color "\b(429)\b|$"; sleep 1; done -``` - -By sending requests as **bob**: - -```sh -while :; do curl -k --resolve api.${KUADRANT_ZONE_ROOT_DOMAIN}:443:${INGRESS_HOST} --write-out '%{http_code}\n' --silent --output /dev/null -H 'Authorization: APIKEY IAMBOB' "https://api.$KUADRANT_ZONE_ROOT_DOMAIN/cars" | grep -E --color "\b(429)\b|$"; sleep 1; done -``` - -> **Note:** If you configured a DNS provider during the setup and defined the DNSPolicy as described in one of the previous chapters you can omit the `--resolve api.${KUADRANT_ZONE_ROOT_DOMAIN}:443:${INGRESS_HOST}` flag. - -> **Note:** If you have followed through this guide on more than 1 cluster, the DNS record for the HTTPRoute hostname will have multiple IP addresses. This means that requests will be made in a round robin pattern across clusters as your DNS provider sends different responses to lookups. - -```sh -while :; do curl -k --write-out '%{http_code}\n' --silent --output /dev/null -H 'Authorization: APIKEY IAMALICE' "https://api.$KUADRANT_ZONE_ROOT_DOMAIN/cars" | grep -E --color "\b(429)\b|$"; sleep 1; done -``` - -```sh -while :; do curl -k --write-out '%{http_code}\n' --silent --output /dev/null -H 'Authorization: APIKEY IAMBOB' "https://api.$KUADRANT_ZONE_ROOT_DOMAIN/cars" | grep -E --color "\b(429)\b|$"; sleep 1; done -``` - -## Next Steps - -- [mTLS Configuration](../../install/mtls-configuration.md) diff --git a/doc/user-guides/full-walkthrough/secure-protect-connect-openshift.md b/doc/user-guides/full-walkthrough/secure-protect-connect.md similarity index 98% rename from doc/user-guides/full-walkthrough/secure-protect-connect-openshift.md rename to doc/user-guides/full-walkthrough/secure-protect-connect.md index 08f45fcb8..57b856524 100644 --- a/doc/user-guides/full-walkthrough/secure-protect-connect-openshift.md +++ b/doc/user-guides/full-walkthrough/secure-protect-connect.md @@ -6,7 +6,8 @@ This guide walks you through using Kuadrant to secure, protect, and connect an A ## Prerequisites -- Completed the steps in [Install Kuadrant on an OpenShift cluster](../../install/install-openshift.md). +- Have a cluster with Kuadrant operator installed. + - Either [Kubernetes installation guide](../../install/install-kubernetes.md) or [Openshift installation guide](../../install/install-openshift.md) - [kubectl](https://kubernetes.io/docs/tasks/tools/#kubectl) command line tool. - AWS/Azure or GCP with DNS capabilities. From 7f96cb6cd1800aa846c2e20d5a8c600b124a1de1 Mon Sep 17 00:00:00 2001 From: R-Lawton Date: Wed, 18 Dec 2024 17:38:58 +0000 Subject: [PATCH 2/2] updating paths Signed-off-by: R-Lawton --- doc/install/install-kubernetes.md | 2 +- doc/install/install-openshift.md | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/doc/install/install-kubernetes.md b/doc/install/install-kubernetes.md index da3246686..52c66d6ed 100644 --- a/doc/install/install-kubernetes.md +++ b/doc/install/install-kubernetes.md @@ -206,4 +206,4 @@ If you are using a local kind cluster, we recommend using [metallb](https://meta ## Next Steps -- [Secure, protect, and connect APIs with Kuadrant on Kubernetes](../user-guides/full-walkthrough/secure-protect-connect-k8s.md) +- [Secure, protect, and connect APIs with Kuadrant on Kubernetes](../user-guides/full-walkthrough/secure-protect-connect.md) diff --git a/doc/install/install-openshift.md b/doc/install/install-openshift.md index f06e3a417..aac5217b2 100644 --- a/doc/install/install-openshift.md +++ b/doc/install/install-openshift.md @@ -221,7 +221,7 @@ kubectl apply -f https://raw.githubusercontent.com/Kuadrant/kuadrant-operator/re There is 1 more metrics configuration that needs to be applied so that all relevant metrics are being scraped. That configuration depends on where you deploy your Gateway later. - The steps to configure that are detailed in the follow on [Secure, protect, and connect](../user-guides/full-walkthrough/secure-protect-connect-openshift.md) guide. + The steps to configure that are detailed in the follow on [Secure, protect, and connect](../user-guides/full-walkthrough/secure-protect-connect.md) guide. The [example Grafana dashboards and alerts](https://docs.kuadrant.io/latest/kuadrant-operator/doc/observability/examples/) for observing Kuadrant functionality use low-level CPU metrics and network metrics available from the user monitoring stack in OpenShift. They also use resource state metrics from Gateway API and Kuadrant resources. @@ -412,4 +412,4 @@ Once the plugin is loaded, refresh the console. You should see a new **Kuadrant* ## Next steps -- [Secure, protect, and connect APIs with Kuadrant on OpenShift](../user-guides/full-walkthrough/secure-protect-connect-openshift.md) +- [Secure, protect, and connect APIs with Kuadrant on OpenShift](../user-guides/full-walkthrough/secure-protect-connect.md)