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

Add ingress class docs #811

Merged
merged 20 commits into from
Sep 14, 2020
Merged
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
7 changes: 7 additions & 0 deletions docs/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
- [Custom Resources](#custom-resources)
- [Deployment methods](#deployment-methods)
- [High-availability and scaling](#high-availability-and-scaling)
- [Resource classes](#resource-classes)
- [Security](#security)
- [Guides and Tutorials](#guides-and-tutorials)
- [Configuration reference](#configuration-reference)
Expand Down Expand Up @@ -48,6 +49,12 @@ and infrastructure.
Please refer to [this document](concepts/ha-and-scaling.md) to understand
failures scenarios, recovery methods, as well as scaling considerations.

### Ingress classes

[Ingress classes](concepts/ingress-classes.md) filter which resources the
controller loads. They ensure that Kong Ingress Controller instances do not
load configuration intended for other instances or other ingress controllers.

### Security

Please refer to [this document](concepts/security.md) to understand the
Expand Down
12 changes: 11 additions & 1 deletion docs/concepts/custom-resources.md
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ Once this resource is created, the resource needs to be associated with an
`Ingress`, `Service`, or `KongConsumer` resource in Kubernetes.
For more details, please read the reference documentation on `KongPlugin`.

The below diagram shows how the `KongPlugin` resource can be linked to an
The below diagram shows how you can link `KongPlugin` resource to an
`Ingress`, `Service`, or `KongConsumer`:

| | |
Expand All @@ -73,6 +73,8 @@ The below diagram shows how the `KongPlugin` resource can be linked to an

rainest marked this conversation as resolved.
Show resolved Hide resolved
## KongClusterPlugin

_This resource requires the [`kubernetes.io/ingress.class` annotation](../README.md#resource-classes)._

KongClusterPlugin resource is exactly same as KongPlugin, except that it is a
Kubernetes cluster-level resources instead of being a namespaced resource.
This can help when the configuration of the plugin needs to be centralized
Expand All @@ -87,12 +89,20 @@ KongClusterPlugin with the same name.

## KongConsumer

_This resource requires the `kubernetes.io/ingress.class` annotation. Its value
must match the value of the controller's `--ingress-class` argument, which is
"kong" by default._

This custom resource configures `Consumers` in Kong.
Every `KongConsumer` resource in Kubernetes directly translates to a
[Consumer][kong-consumer] object in Kong.

## TCPIngress

_This resource requires the `kubernetes.io/ingress.class` annotation. Its value
must match the value of the controller's `--ingress-class` argument, which is
"kong" by default._

This Custom Resource is used for exposing non-HTTP
and non-GRPC services running inside Kubernetes to
the outside world via Kong. This proves to be useful when
Expand Down
183 changes: 183 additions & 0 deletions docs/concepts/ingress-classes.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,183 @@
# Kong Ingress Controller and ingress class


## Table of Contents

- [**Introduction**](#introduction)
- [**Configuring the controller class**](#configuring-the-controller-ingress-class)
- [**Loading resources by class**](#loading-resouces-by-class)
- [**When to use a custom class**](#when-to-use-a-custom-class)
- [**Legacy behavior**](#legacy-behavior)
- [**Examples**](#examples)

## Introduction

The Kong Ingress Controller uses ingress classes to filter Kubernetes Ingress
objects and other resources before converting them into Kong configuration.
This allows it to coexist with other ingress controllers and/or other
deployments of the Kong Ingress Controller in the same cluster: a Kong Ingress
Controller will only process configuration marked for its use.

## Configuring the controller ingress class

The `--ingress-class` flag (or `CONTROLLER_INGRESS_CLASS` environment variable)
specify the ingress class expected by the Kong Ingress Controller. By default,
it expects the `kong` class.

## Loading resources by class

The Kong Ingress Controller translates a variety of Kubernetes resources into
Kong configuration. Broadly speaking, we can separate these resources into two
categories:

- Resources that the controller translates directly into Kong configuration.
- Resources referenced by some other resource, where the other resource is
directly translated into Kong configuration.

For example, an Ingress is translated directly into a Kong route, and a
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
For example, an Ingress is translated directly into a Kong route, and a
For example, an Ingress is translated directly into a [Kong route](https://docs.konghq.com/latest/admin-api/#route-object), and a

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unnecessary here. The focus of this content isn't to discuss basic Kong proxy concepts, and we may reasonably assume many readers are familiar with them: they're part of the basic set of configuration introduced in our getting started guides.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Three arguments against not including it here:

  1. It costs nothing to add (because the link just changes a term into a hyperlink, and the likelihood of the link rotting is low)

  2. we may reasonably assume many readers are familiar with them

    This is a harmful and (imo unnecessary) assumption: some people will come here from a Google search, some people will be only 90% sure about the relationships between routes, services and upstreams.

  3. Wikipedia would cross-link in such situation. Take for example the Molotov-Ribbentrop pact article. The reader may be reasonably assumed to be familiar with terms "Soviet Union" and "Germany", but the article has them linked nonetheless.

KongConsumer is translated directly into a [Kong consumer](https://docs.konghq.com/latest/admin-api/#consumer-object). A Secret containing
an authentication plugin credential is _not_ translated directly: it is only
translated into Kong configuration if a KongConsumer resource references it.

Because they create Kong configuration indenpendent of any other resources,
directly-translated resources require an ingress class, and their class must
match the class configured for the controller. Referenced resources do not
require a class, but must be referenced by a directly-translated resource
that matches the controller.

### Adding class information to resources

Most resources use a [kubernetes.io/ingress-class annotation][class-annotation]
to indicate their class. There are several exceptions:

- v1 Ingress resources have a dedicated `class` field.
- Knative Services [use the class specifed][knative-class] by the
`ingress.class` key of the Knative installation's `config-network` ConfigMap.
You can optionally [override this on a per-Service basis][knative-override]
by adding a `networking.knative.dev/ingress.class` annotation to the Service.

### Enabling support for classless resources

Specifying a class is optional for some resources. Although specifying a class
is recommended, you can instruct the controller to process resources without a
class annotation using flags:

- `--process-classless-ingress-v1beta1` instructs the controller to translate
v1beta1 Ingress resources with no class annotation.
- `--process-classless-kong-consumer` instructs the controller to translate
KongConsumer resources with no class annotation.

These flags are primarily intended for compatibility with older configuration
(Kong Ingress Controller before 0.10 had less strict class
requirements, and it was common to omit class annotations). If you are creating
new configuration and do not have older configuration without class
annotations, recommended best practice is to add class information to Ingress
and KongConsumer resources and not set the above flags. Doing so avoids
accidentally creating duplicate configuration in other ingress controller
instances.

These flags do not _ignore_ `ingress.class` annotations: they allow resources
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
These flags do not _ignore_ `ingress.class` annotations: they allow resources
The flags mentioned above do not _ignore_ `ingress.class` annotations. They allow resources

I allowed myself to make a typographical suggestion because a : after These flags ... suggests that a list of flags will follow.

For added clarity, made a more direct reference.

nit: the expression "flags ignore an annotation" is incorrect, because in fact these flags make Kong ignore an annotation.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Dismissed. A colon is a valid option for separating two independent, related clauses. The flags are the focus of the section, and there is only one set of flags within this section. The distinction would be warranted if there were a list of flags both above and below that statement, but that's not the case here.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A colon is a valid option for separating two independent, related clauses.

I agree, but other than being valid it's ambiguous if read in isolation. I'm still asking that we apply the suggestion because it disambiguates at a minimal cost.

If you're still not convinced, I won't block you on this because it's on the pedantic side, I agree. I do not understand reasons for not applying this (if it's 1 click away), though.

with no such annotation, but will not allow resource that have a non-matching
`ingress.class` annotation.

## When to use a custom class

Using the default `kong` class is fine for simpler deployments, where only one
Kong Ingress Controller instance is running in a cluster. Changing the class is
typical when:

- You install multiple Kong environments in one Kubernetes cluster to handle
different types of ingress traffic, e.g. when using separate Kong instances
to handle traffic on internal and external load balancers, or deploying
different types of non-production environments in a single test cluster.
- You install multiple controller instances alongside a single Kong cluster to
separate configuration into different Kong workspaces (using the
`--kong-workspace` flag) or to restrict which Kubernetes namespaces any one
controller instance has access to.

## Legacy behavior

This overview covers behavior in Kong Ingress Controller version 0.10.0 onward.
rainest marked this conversation as resolved.
Show resolved Hide resolved
Earlier versions had a special case for the default class and a bug affecting
rainest marked this conversation as resolved.
Show resolved Hide resolved
custom classes:
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Having no insider context, it would be not absolutely clear to me that custom class means other than the default kong. This is not about the lexical definition of the word custom but about defining the boundary between custom and... standard? default?

Suggestion: make it clear somehow that custom means other than the default kong.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Confusion noted, but I believe this to be reasonably clear, and personally value succinctness when I do not consider it overly vague. We do not have established terminology here, and I reserve the right to choose a term I feel appropriate.


- When using the default `kong` class, the controller would always process
classless resources in addition to `kong`-class resources. When using a
non-default controller class, the controller would only process resources
with that class, not classless resources. Although this was by design, it was
a source of user confusion.
- When using a custom controller class, some resources that should not have
required a class (because they were referenced by other resources)
effectively did require a class: while these resources were loaded initially,
the controller would not track updates to them unless they had a class
annotation.

In versions 0.10.0+ you must instruct the controller to load classless
resources, which is allowed (but not recommended) for either the default or
custom classes. Resources referenced by another resource are always loaded and
updated correctly regardless of which class you set on the controller; you do
not need to add class annotations to these resources when using a custom class.

## Examples

Typical configurations will include a mix of resources that have class
information and resources that are referenced by them. For example, consider
the following configuration for authenticating a request, using a KongConsumer,
credential Secret, Ingress, and KongPlugin (a Service is implied, but not
shown):

```yaml
kind: KongConsumer
metadata:
name: dyadya-styopa
annotations:
kubernetes.io/ingress.class: "kong"
username: styopa
credentials:
- styopa-key

---

kind: Secret
apiVersion: v1
stringData:
key: bylkogdatomoryakom
kongCredType: key-auth
metadata:
name: styopa-key
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
name: styopa-key
name: styopa-key
# note: no ingress class annotation, because this Secret is referenced by a KongConsumer

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Dismissed. This is covered below, and I find that fully sufficient to achieve my objectives with this example.


---

kind: Ingress
apiVersion: extensions/v1beta1
metadata:
name: ktonezhnaet
annotations:
kubernetes.io/ingress.class: "kong"
konghq.com/plugins: "key-auth-example"
spec:
rules:
- http:
paths:
- path: /vsemznakom
backend:
serviceName: httpbin
servicePort: 80

---

apiVersion: configuration.konghq.com/v1
kind: KongPlugin
metadata:
name: key-auth-example
rainest marked this conversation as resolved.
Show resolved Hide resolved
plugin: key-auth
```

The KongConsumer and Ingress resources both have class annotations, as they are
resources that the controller uses as a basis for building Kong configuration.
The Secret and KongPlugin _do not_ have class annotations, as they are
referenced by other resources that do.

[class-annotation]: ../references/annotations.md#kubernetesioingressclass
[knative-class]: ../guides/using-kong-with-knative.md#ingress-class
[knative-override]: https://knative.tips/networking/ingress-override/
4 changes: 4 additions & 0 deletions docs/deployment/admission-webhook.md
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,8 @@ $ echo "apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: harry
annotations:
kubernetes.io/ingress.class: kong
username: harry" | kubectl apply -f -
kongconsumer.configuration.konghq.com/harry created
```
Expand All @@ -153,6 +155,8 @@ $ echo "apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: harry2
annotations:
kubernetes.io/ingress.class: kong
username: harry" | kubectl apply -f -
Error from server: error when creating "STDIN": admission webhook "validations.kong.konghq.com" denied the request: consumer already exists
```
Expand Down
3 changes: 3 additions & 0 deletions docs/guides/cert-manager.md
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,8 @@ apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: demo-yolo42-com
annotations:
kubernetes.io/ingress.class: kong
spec:
rules:
- host: demo.yolo42.com
Expand Down Expand Up @@ -190,6 +192,7 @@ metadata:
annotations:
kubernetes.io/tls-acme: "true"
cert-manager.io/cluster-issuer: letsencrypt-prod
kubernetes.io/ingress.class: kong
spec:
tls:
- secretName: demo-yolo42-com
Expand Down
18 changes: 18 additions & 0 deletions docs/guides/configure-acl-plugin.md
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ metadata:
name: demo-get
annotations:
konghq.com/strip-path: "false"
kubernetes.io/ingress.class: kong
spec:
rules:
- http:
Expand All @@ -71,6 +72,7 @@ metadata:
name: demo-post
annotations:
konghq.com/strip-path: "false"
kubernetes.io/ingress.class: kong
spec:
rules:
- http:
Expand Down Expand Up @@ -161,6 +163,7 @@ metadata:
annotations:
plugins.konghq.com: app-jwt
konghq.com/strip-path: "false"
kubernetes.io/ingress.class: kong
spec:
rules:
- http:
Expand All @@ -179,6 +182,7 @@ metadata:
annotations:
plugins.konghq.com: app-jwt
konghq.com/strip-path: "false"
kubernetes.io/ingress.class: kong
spec:
rules:
- http:
Expand Down Expand Up @@ -234,6 +238,8 @@ apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: admin
annotations:
kubernetes.io/ingress.class: kong
username: admin
" | kubectl apply -f -

Expand All @@ -242,6 +248,8 @@ apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: plain-user
annotations:
kubernetes.io/ingress.class: kong
username: plain-user
" | kubectl apply -f -
```
Expand Down Expand Up @@ -299,6 +307,8 @@ apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: admin
annotations:
kubernetes.io/ingress.class: kong
username: admin
credentials:
- app-admin-jwt
Expand All @@ -309,6 +319,8 @@ apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: plain-user
annotations:
kubernetes.io/ingress.class: kong
username: plain-user
credentials:
- app-user-jwt
Expand Down Expand Up @@ -536,6 +548,8 @@ apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: admin
annotations:
kubernetes.io/ingress.class: kong
username: admin
credentials:
- app-admin-jwt
Expand All @@ -547,6 +561,8 @@ apiVersion: configuration.konghq.com/v1
kind: KongConsumer
metadata:
name: plain-user
annotations:
kubernetes.io/ingress.class: kong
username: plain-user
credentials:
- app-user-jwt
Expand All @@ -567,6 +583,7 @@ metadata:
annotations:
plugins.konghq.com: app-jwt,plain-user-acl
konghq.com/strip-path: "false"
kubernetes.io/ingress.class: kong
spec:
rules:
- http:
Expand All @@ -585,6 +602,7 @@ metadata:
annotations:
plugins.konghq.com: app-jwt,admin-acl
konghq.com/strip-path: "false"
kubernetes.io/ingress.class: kong
spec:
rules:
- http:
Expand Down
3 changes: 3 additions & 0 deletions docs/guides/configuring-fallback-service.md
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ metadata:
name: demo
annotations:
konghq.com/strip-path: "true"
kubernetes.io/ingress.class: kong
spec:
rules:
- http:
Expand Down Expand Up @@ -104,6 +105,8 @@ apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: fallback
annotations:
kubernetes.io/ingress.class: kong
spec:
backend:
serviceName: fallback-svc
Expand Down
Loading