Updates to Ingress (#12465)

* Create ingress-minikube.md

* Update ingress.md

* Move Ingress controllers content to own page
* Link to Set up Ingress on Minikube with the NGINX Controller task
* Minor edits

* Create ingress-controllers.md

* Update ingress-controllers.md
pull/12679/head
Cody Clark 2019-02-17 18:36:33 -08:00 committed by Kubernetes Prow Robot
parent 9654ecc44f
commit a96ea24939
3 changed files with 421 additions and 51 deletions

View File

@ -0,0 +1,67 @@
---
title: Ingress Controllers
reviewers:
content_template: templates/concept
toc_hide: true
---
{{% capture body %}}
## Ingress controllers
In order for the Ingress resource to work, the cluster must have an ingress controller running.
This is unlike other types of controllers, which run as part of the `kube-controller-manager` binary,
and are typically started automatically with a cluster. Choose the ingress controller implementation
that best fits your cluster.
* Kubernetes as a project currently supports and maintains [GCE](https://git.k8s.io/ingress-gce/README.md) and
[nginx](https://git.k8s.io/ingress-nginx/README.md) controllers.
### Additional controllers include:
* [Contour](https://github.com/heptio/contour) is an [Envoy](https://www.envoyproxy.io) based ingress controller
provided and supported by Heptio.
* Citrix provides an [Ingress Controller](https://github.com/citrix/citrix-k8s-ingress-controller) for its hardware (MPX), virtualized (VPX) and [free containerized (CPX) ADC](https://www.citrix.com/products/citrix-adc/cpx-express.html) for [baremetal](https://github.com/citrix/citrix-k8s-ingress-controller/tree/master/deployment/baremetal) and [cloud](https://github.com/citrix/citrix-k8s-ingress-controller/tree/master/deployment) deployments.
* F5 Networks provides [support and maintenance](https://support.f5.com/csp/article/K86859508)
for the [F5 BIG-IP Controller for Kubernetes](http://clouddocs.f5.com/products/connectors/k8s-bigip-ctlr/latest).
* [Gloo](https://gloo.solo.io) is an open-source ingress controller based on [Envoy](https://www.envoyproxy.io) which offers API Gateway functionality with enterprise support from [solo.io](https://www.solo.io).
* [HAProxy](http://www.haproxy.org/) based ingress controller
[jcmoraisjr/haproxy-ingress](https://github.com/jcmoraisjr/haproxy-ingress) which is mentioned on the blog post
[HAProxy Ingress Controller for Kubernetes](https://www.haproxy.com/blog/haproxy_ingress_controller_for_kubernetes/).
[HAProxy Technologies](https://www.haproxy.com/) offers support and maintenance for HAProxy Enterprise and
the ingress controller [jcmoraisjr/haproxy-ingress](https://github.com/jcmoraisjr/haproxy-ingress).
* [Istio](https://istio.io/) based ingress controller
[Control Ingress Traffic](https://istio.io/docs/tasks/traffic-management/ingress/).
* [Kong](https://konghq.com/) offers [community](https://discuss.konghq.com/c/kubernetes) or
[commercial](https://konghq.com/kong-enterprise/) support and maintenance for the
[Kong Ingress Controller for Kubernetes](https://github.com/Kong/kubernetes-ingress-controller).
* [NGINX, Inc.](https://www.nginx.com/) offers support and maintenance for the
[NGINX Ingress Controller for Kubernetes](https://www.nginx.com/products/nginx/kubernetes-ingress-controller).
* [Traefik](https://github.com/containous/traefik) is a fully featured ingress controller
([Let's Encrypt](https://letsencrypt.org), secrets, http2, websocket), and it also comes with commercial
support by [Containous](https://containo.us/services).
## Using multiple Ingress controllers
You may deploy [any number of ingress controllers](https://git.k8s.io/ingress-nginx/docs/user-guide/multiple-ingress.md#multiple-ingress-controllers)
within a cluster. When you create an ingress, you should annotate each ingress with the appropriate
[`ingress.class`](https://git.k8s.io/ingress-gce/docs/faq/README.md#how-do-i-run-multiple-ingress-controllers-in-the-same-cluster)
to indicate which ingress controller should be used if more than one exists within your cluster.
If you do not define a class, your cloud provider may use a default ingress provider.
Ideally, all ingress controllers should fulfill this specification, but the various ingress
controllers operate slightly differently.
{{< note >}}
Make sure you review your ingress controller's documentation to understand the caveats of choosing it.
{{< /note >}}
{{% /capture %}}
{{% capture whatsnext %}}
* Learn more about [Ingress](/docs/concepts/services-networking/ingress/).
* [Set up Ingress on Minikube with the NGINX Controller](/docs/tasks/access-application-cluster/ingress-minikube.md).
{{% /capture %}}

View File

@ -25,7 +25,7 @@ For the sake of clarity, this guide defines the following terms:
Ingress, added in Kubernetes v1.1, exposes HTTP and HTTPS routes from outside the cluster to
{{< link text="services" url="/docs/concepts/services-networking/service/" >}} within the cluster.
Traffic routing is controlled by rules defined on the ingress resource.
Traffic routing is controlled by rules defined on the Ingress resource.
```none
internet
@ -35,9 +35,9 @@ Traffic routing is controlled by rules defined on the ingress resource.
[ Services ]
```
An ingress can be configured to give services externally-reachable URLs, load balance traffic, terminate SSL, and offer name based virtual hosting. An [ingress controller](#ingress-controllers) is responsible for fulfilling the ingress, usually with a loadbalancer, though it may also configure your edge router or additional frontends to help handle the traffic.
An Ingress can be configured to give services externally-reachable URLs, load balance traffic, terminate SSL, and offer name based virtual hosting. An [Ingress controller](/docs/concepts/services-networking/ingress-controllers) is responsible for fulfilling the Ingress, usually with a loadbalancer, though it may also configure your edge router or additional frontends to help handle the traffic.
An ingress does not expose arbitrary ports or protocols. Exposing services other than HTTP and HTTPS to the internet typically
An Ingress does not expose arbitrary ports or protocols. Exposing services other than HTTP and HTTPS to the internet typically
uses a service of type [Service.Type=NodePort](/docs/concepts/services-networking/service/#nodeport) or
[Service.Type=LoadBalancer](/docs/concepts/services-networking/service/#loadbalancer).
@ -45,9 +45,13 @@ uses a service of type [Service.Type=NodePort](/docs/concepts/services-networkin
{{< feature-state for_k8s_version="v1.1" state="beta" >}}
Before you start using an ingress, there are a few things you should understand. The ingress is a beta resource. You will need an ingress controller to satisfy an ingress, simply creating the resource will have no effect.
Before you start using an Ingress, there are a few things you should understand. The Ingress is a beta resource.
GCE/Google Kubernetes Engine deploys an [ingress controller](#ingress-controllers) on the master. Review the
{{< note >}}
You must have an [Ingress controller](/docs/concepts/services-networking/ingress-controllers) to satisfy an Ingress. Only creating an Ingress resource has no effect.
{{< /note >}}
GCE/Google Kubernetes Engine deploys an Ingress controller on the master. Review the
[beta limitations](https://github.com/kubernetes/ingress-gce/blob/master/BETA_LIMITATIONS.md#glbc-beta-limitations)
of this controller if you are using GCE/GKE.
@ -125,14 +129,14 @@ spec:
servicePort: 80
```
As with all other Kubernetes resources, an ingress needs `apiVersion`, `kind`, and `metadata` fields.
As with all other Kubernetes resources, an Ingress needs `apiVersion`, `kind`, and `metadata` fields.
For general information about working with config files, see [deploying applications](/docs/tasks/run-application/run-stateless-application-deployment/), [configuring containers](/docs/tasks/configure-pod-container/configure-pod-configmap/), [managing resources](/docs/concepts/cluster-administration/manage-deployment/).
Ingress frequently uses annotations to configure some options depending on the ingress controller, an example of which
Ingress frequently uses annotations to configure some options depending on the Ingress controller, an example of which
is the [rewrite-target annotation](https://github.com/kubernetes/ingress-nginx/blob/master/docs/examples/rewrite/README.md).
Different [ingress controller](#ingress-controllers) support different annotations. Review the documentation for
your choice of ingress controller to learn which annotations are supported.
Different [Ingress controller]((/docs/concepts/services-networking/ingress-controllers)) support different annotations. Review the documentation for
your choice of Ingress controller to learn which annotations are supported.
The ingress [spec](https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-status)
The Ingress [spec](https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-status)
has all the information needed to configure a loadbalancer or proxy server. Most importantly, it
contains a list of rules matched against all incoming requests. Ingress resource only supports rules
for directing HTTP traffic.
@ -149,18 +153,17 @@ Each http rule contains the following information:
loadbalancer will direct traffic to the referenced service.
* A backend is a combination of service and port names as described in the
[services doc](/docs/concepts/services-networking/service/). HTTP (and HTTPS) requests to the
ingress matching the host and path of the rule will be sent to the listed backend.
Ingress matching the host and path of the rule will be sent to the listed backend.
A default backend is often configured in an ingress controller that will service any requests that do not
A default backend is often configured in an Ingress controller that will service any requests that do not
match a path in the spec.
### Default Backend
An ingress with no rules sends all traffic to a single default backend. The default
backend is typically a configuration option of the [ingress controller](#ingress-controllers)
and is not specified in your ingress resources.
An Ingress with no rules sends all traffic to a single default backend. The default
backend is typically a configuration option of the [Ingress controller](/docs/concepts/services-networking/ingress-controllers) and is not specified in your Ingress resources.
If none of the hosts or paths match the HTTP request in the ingress objects, the traffic is
If none of the hosts or paths match the HTTP request in the Ingress objects, the traffic is
routed to your default backend.
## Types of Ingress
@ -168,7 +171,7 @@ routed to your default backend.
### Single Service Ingress
There are existing Kubernetes concepts that allow you to expose a single Service
(see [alternatives](#alternatives)). You can also do this with an ingress by specifying a
(see [alternatives](#alternatives)). You can also do this with an Ingress by specifying a
*default backend* with no rules.
{{< codenew file="service/networking/ingress.yaml" >}}
@ -184,8 +187,8 @@ NAME HOSTS ADDRESS PORTS AGE
test-ingress * 107.178.254.228 80 59s
```
Where `107.178.254.228` is the IP allocated by the ingress controller to satisfy
this ingress.
Where `107.178.254.228` is the IP allocated by the Ingress controller to satisfy
this Ingress.
{{< note >}}
Ingress controllers and load balancers may take a minute or two to allocate an IP address.
@ -195,7 +198,7 @@ Until that time you will often see the address listed as `<pending>`.
### Simple fanout
A fanout configuration routes traffic from a single IP address to more than one service,
based on the HTTP URI being requested. An ingress allows you to keep the number of loadbalancers
based on the HTTP URI being requested. An Ingress allows you to keep the number of loadbalancers
down to a minimum. For example, a setup like:
```shell
@ -203,7 +206,7 @@ foo.bar.com -> 178.91.123.132 -> / foo service1:4200
/ bar service2:8080
```
would require an ingress such as:
would require an Ingress such as:
```yaml
apiVersion: extensions/v1beta1
@ -227,7 +230,7 @@ spec:
servicePort: 8080
```
When you create the ingress with `kubectl create -f`:
When you create the Ingress with `kubectl create -f`:
```shell
kubectl describe ingress simple-fanout-example
@ -252,13 +255,13 @@ Events:
Normal ADD 22s loadbalancer-controller default/test
```
The ingress controller will provision an implementation specific loadbalancer
that satisfies the ingress, as long as the services (`s1`, `s2`) exist.
When it has done so, you will see the address of the loadbalancer at the
The Ingress controller provisions an implementation specific loadbalancer
that satisfies the Ingress, as long as the services (`s1`, `s2`) exist.
When it has done so, you can see the address of the loadbalancer at the
Address field.
{{< note >}}
Depending on the [ingress controller](#ingress-controllers) you are using, you may need to
Depending on the [Ingress controller](/docs/concepts/services-networking/ingress-controllers) you are using, you may need to
create a default-http-backend [Service](/docs/concepts/services-networking/service/).
{{< /note >}}
@ -272,7 +275,7 @@ foo.bar.com --| |-> foo.bar.com s1:80
bar.foo.com --| |-> bar.foo.com s2:80
```
The following ingress tells the backing loadbalancer to route requests based on
The following Ingress tells the backing loadbalancer to route requests based on
the [Host header](https://tools.ietf.org/html/rfc7230#section-5.4).
```yaml
@ -296,9 +299,9 @@ spec:
servicePort: 80
```
If you create an ingress resource without any hosts defined in the rules, then any
web traffic to the IP address of your ingress controller can be matched without a name based
virtual host being required. For example, the following ingress resource will route traffic
If you create an Ingress resource without any hosts defined in the rules, then any
web traffic to the IP address of your Ingress controller can be matched without a name based
virtual host being required. For example, the following Ingress resource will route traffic
requested for `first.bar.com` to `service1`, `second.foo.com` to `service2`, and any traffic
to the IP address without a hostname defined in request (that is, without a request header being
presented) to `service3`.
@ -331,12 +334,12 @@ spec:
### TLS
You can secure an ingress by specifying a [secret](/docs/concepts/configuration/secret)
that contains a TLS private key and certificate. Currently the ingress only
You can secure an Ingress by specifying a [secret](/docs/concepts/configuration/secret)
that contains a TLS private key and certificate. Currently the Ingress only
supports a single TLS port, 443, and assumes TLS termination. If the TLS
configuration section in an ingress specifies different hosts, they will be
configuration section in an Ingress specifies different hosts, they will be
multiplexed on the same port according to the hostname specified through the
SNI TLS extension (provided the ingress controller supports SNI). The TLS secret
SNI TLS extension (provided the Ingress controller supports SNI). The TLS secret
must contain keys named `tls.crt` and `tls.key` that contain the certificate
and private key to use for TLS, e.g.:
@ -352,7 +355,7 @@ metadata:
type: kubernetes.io/tls
```
Referencing this secret in an ingress will tell the ingress controller to
Referencing this secret in an Ingress will tell the Ingress controller to
secure the channel from the client to the loadbalancer using TLS. You need to make
sure the TLS secret you created came from a certificate that contains a CN
for `sslexample.foo.com`.
@ -378,24 +381,24 @@ spec:
```
{{< note >}}
There is a gap between TLS features supported by various ingress
There is a gap between TLS features supported by various Ingress
controllers. Please refer to documentation on
[nginx](https://git.k8s.io/ingress-nginx/README.md#https),
[GCE](https://git.k8s.io/ingress-gce/README.md#frontend-https), or any other
platform specific ingress controller to understand how TLS works in your environment.
platform specific Ingress controller to understand how TLS works in your environment.
{{< /note >}}
### Loadbalancing
An ingress controller is bootstrapped with some load balancing policy settings
that it applies to all ingress, such as the load balancing algorithm, backend
An Ingress controller is bootstrapped with some load balancing policy settings
that it applies to all Ingress, such as the load balancing algorithm, backend
weight scheme, and others. More advanced load balancing concepts
(e.g. persistent sessions, dynamic weights) are not yet exposed through the
ingress. You can still get these features through the
Ingress. You can still get these features through the
[service loadbalancer](https://github.com/kubernetes/ingress-nginx).
It's also worth noting that even though health checks are not exposed directly
through the ingress, there exist parallel concepts in Kubernetes such as
through the Ingress, there exist parallel concepts in Kubernetes such as
[readiness probes](/docs/tasks/configure-pod-container/configure-liveness-readiness-probes/)
which allow you to achieve the same end result. Please review the controller
specific docs to see how they handle health checks (
@ -404,7 +407,7 @@ specific docs to see how they handle health checks (
## Updating an Ingress
To update an existing ingress to add a new Host, you can update it by editing the resource:
To update an existing Ingress to add a new Host, you can update it by editing the resource:
```shell
kubectl describe ingress test
@ -455,7 +458,7 @@ spec:
```
Saving the yaml will update the resource in the API server, which should tell the
ingress controller to reconfigure the loadbalancer.
Ingress controller to reconfigure the loadbalancer.
```shell
kubectl describe ingress test
@ -481,25 +484,24 @@ Events:
Normal ADD 45s loadbalancer-controller default/test
```
You can achieve the same by invoking `kubectl replace -f` on a modified ingress yaml file.
You can achieve the same by invoking `kubectl replace -f` on a modified Ingress yaml file.
## Failing across availability zones
Techniques for spreading traffic across failure domains differs between cloud providers.
Please check the documentation of the relevant [ingress controller](#ingress-controllers) for
details. You can also refer to the [federation documentation](/docs/concepts/cluster-administration/federation/)
for details on deploying ingress in a federated cluster.
Please check the documentation of the relevant [Ingress controller](/docs/concepts/services-networking/ingress-controllers) for details. You can also refer to the [federation documentation](/docs/concepts/cluster-administration/federation/)
for details on deploying Ingress in a federated cluster.
## Future Work
Track [SIG Network](https://github.com/kubernetes/community/tree/master/sig-network)
for more details on the evolution of the ingress and related resources. You may also track the
[ingress repository](https://github.com/kubernetes/ingress/tree/master) for more details on the
evolution of various ingress controllers.
[Ingress repository](https://github.com/kubernetes/ingress/tree/master) for more details on the
evolution of various Ingress controllers.
## Alternatives
You can expose a Service in multiple ways that don't directly involve the ingress resource:
You can expose a Service in multiple ways that don't directly involve the Ingress resource:
* Use [Service.Type=LoadBalancer](/docs/concepts/services-networking/service/#loadbalancer)
* Use [Service.Type=NodePort](/docs/concepts/services-networking/service/#nodeport)
@ -508,6 +510,6 @@ You can expose a Service in multiple ways that don't directly involve the ingres
{{% /capture %}}
{{% capture whatsnext %}}
* [Set up Ingress on Minikube with the NGINX Controller](/docs/tasks/access-application-cluster/ingress-minikube.md)
{{% /capture %}}

View File

@ -0,0 +1,301 @@
---
title: Set up Ingress on Minikube with the NGINX Ingress Controller
content_template: templates/task
weight: 100
---
{{% capture overview %}}
An [Ingress](/docs/concepts/services-networking/ingress/) is an API object that defines rules which allow external access
to services in a cluster. An [Ingress controller](#) fulfills the rules set in the Ingress.
{{< caution >}}
For the Ingress resource to work, the cluster **must** also have an Ingress controller running.
{{< /caution >}}
This page shows you how to set up a simple Ingress which routes requests to Service web or web2 depending on the HTTP URI.
{{% /capture %}}
{{% capture prerequisites %}}
{{< include "task-tutorial-prereqs.md" >}} {{< version-check >}}
{{% /capture %}}
{{% capture steps %}}
## Create a Minikube cluster
1. Click **Launch Terminal**
{{< kat-button >}}
1. (Optional) If you installed Minikube locally, run the following command:
```shell
minikube start
```
## Enable the Ingress controller
1. To enable the NGINX Ingress controller, run the following command:
```shell
minikube addons enable ingress
```
1. Verify that the NGINX Ingress controller is running
```shell
kubectl get pods -n kube-system
```
{{< note >}}
This can take up to a minute.
{{< /note >}}
Output:
```shell
NAME READY STATUS RESTARTS AGE
default-http-backend-59868b7dd6-xb8tq 1/1 Running 0 1m
kube-addon-manager-minikube 1/1 Running 0 3m
kube-dns-6dcb57bcc8-n4xd4 3/3 Running 0 2m
kubernetes-dashboard-5498ccf677-b8p5h 1/1 Running 0 2m
nginx-ingress-controller-5984b97644-rnkrg 1/1 Running 0 1m
storage-provisioner 1/1 Running 0 2m
```
## Deploy a hello, world app
1. Create a Deployment using the following command:
```shell
kubectl run web --image=gcr.io/google-samples/hello-app:1.0 --port=8080
```
Output:
```shell
deployment.apps/web created
```
1. Expose the Deployment:
```shell
kubectl expose deployment web --target-port=8080 --type=NodePort
```
Output:
```shell
service/web exposed
```
1. Verify the Service is created and is available on a node port:
```shell
kubectl get service web
```
Output:
```shell
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
web NodePort 10.104.133.249 <none> 8080:31637/TCP 12m
```
1. Visit the service via NodePort:
```shell
minikube service web --url
```
Output:
```shell
http://172.17.0.15:31637
```
{{< note >}}
Katacoda environment only: at the top of the terminal panel, click the plus sign, and then click
**Select port to view on Host 1**. Enter the NodePort, in this case `31637`, and then click **Display Port**
{{< /note >}}
Output:
```shell
Hello, world!
Version: 1.0.0
Hostname: web-55b8c6998d-8k564
```
You can now access the sample app via the Minikube IP address and NodePort. The next step will let you access
the app using the Ingress resource.
## Create an Ingress resource
The following file is an Ingress resource that sends traffic to your Service via hello-world.info.
1. Create `example-ingress.yaml` from the following file:
```yaml
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: example-ingress
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /
spec:
rules:
- host: hello-world.info
http:
paths:
- path: /*
backend:
serviceName: web
servicePort: 8080
```
1. Create the Ingress resrouce by running the following command:
```shell
kubectl apply -f example-ingress.yaml
```
Output:
```shell
ingress.extensions/example-ingress created
```
1. Verify the IP address is set:
```shell
kubectl get ingress
```
{{< note >}}
This can take a couple of minutes.
{{< /note >}}
```shell
NAME HOSTS ADDRESS PORTS AGE
example-ingress hello-world.info 172.17.0.15 80 38s
```
1. Add the following line to the bottom of the `/etc/hosts` file.
```shell
172.17.0.15 hello-world.info
```
This sends requests from hello-world.info to Minikube.
1. Verify that the Ingress contorller is directing traffic:
```shell
curl hello-world.info
````
Output:
```shell
Hello, world!
Version: 1.0.0
Hostname: web-55b8c6998d-8k564
```
{{< note >}}
If you are running Minikube locally, you can visit hello-world.info from your browser.
{{< /note >}}
## Create Second Deployment
1. Create a v2 Deployment using the following command:
```shell
kubectl run web2 --image=gcr.io/google-samples/hello-app:2.0 --port=8080
```
Output:
```shell
deployment.apps/web2 created
```
1. Expose the Deployment:
```shell
kubectl expose deployment web2 --target-port=8080 --type=NodePort
```
Output:
```shell
service/web2 exposed
```
## Edit Ingress
1. Edit the existing `example-ingress.yaml` and add the following lines:
```yaml
- path: /v2/*
backend:
serviceName: web2
servicePort: 8080
```
1. Apply the changes:
```shell
kubectl apply -f example-ingress.yaml
```
Output:
```shell
ingress.extensions/example-ingress configured
```
## Test Your Ingress
1. Access the 1st version of the Hello World app.
```shell
curl hello-world.info
```
Output:
```shell
Hello, world!
Version: 1.0.0
Hostname: web-55b8c6998d-8k564
```
1. Access the 2nd version of the Hello World app.
```shell
curl hello-world.info/v2
```
Output:
```shell
Hello, world!
Version: 2.0.0
Hostname: web2-75cd47646f-t8cjk
```
{{< note >}}
If you are running Minikube locally, you can visit hello-world.info and hello-world.info/v2 from your browser.
{{< /note >}}
{{% /capture %}}
{{% capture whatsnext %}}
* Read more about [Ingress](/docs/concepts/services-networking/ingress/)
* Read more about [Ingress Controllers](#)
* Read more about [Services](/docs/concepts/services-networking/service/)
{{% /capture %}}