-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathhttps.md
137 lines (96 loc) · 4.01 KB
/
https.md
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
# HTTPS
The objective of this scenario is to serve application traffic over HTTPS.
---
## Design decisions
- All traffic should be over HTTPS
- All HTTP requests should be automatically redirected to HTTPS
- App teams should not be able to define routes over HTTP
- The platform team will manage the configuration of TLS termination for the application teams
- App teams continue to have the ability to self-service routes against the shared gateway
We decide to use [cert-manager](https://cert-manager.io/docs/) to generate and otherwise manage certificates.
---
## Deploy `cert-manager`
```shell
helm repo add jetstack https://charts.jetstack.io --force-update
helm repo update
```
```shell
helm upgrade --install --create-namespace --namespace cert-manager \
--set crds.enabled=true \
--set "extraArgs={--enable-gateway-api}" \
cert-manager jetstack/cert-manager
```
---
## Create a self-signed issuer
```yaml linenums="1"
--8<-- "https/selfsigned-issuer.yaml"
```
```shell
kubectl apply -f https/selfsigned-issuer.yaml
```
---
## Update the Gateway configuration
Review the below updated Gateway configuration:
```yaml linenums="1" hl_lines="8 15-17 22-25 36-39"
--8<-- "https/gateway-add-https.yaml"
```
Note the following:
- In addition to the HTTP listener on port 80, we add HTTPS listeners on port 443 for both `httpbin` and the `customers` hostnames.
- The HTTPS listeners are configured to terminate TLS and reference a certificate in Kubernetes secrets: `httpbin-cert` for `httpbin` and `customers-cert` for the `customers` app.
- The `allowedRoutes` configuration that allows app teams to self-service their own routes is now specified at the HTTPS listener level.
- Routes can only be attached to the HTTP listener if they're defined in the _same_ namespace as the Gateway resource (`infra`).
- The annotation on line eight (8) enlists `cert-manager`'s certificate issuer to generate the certificates and store them in the specified secrets.
Apply the configuration:
```shell
kubectl apply -f https/gateway-add-https.yaml
```
---
## :white_check_mark: Test it
Access `httpbin` over TLS:
- A verbose HEAD request showing the TLS handshake:
```shell
curl --insecure -v --head https://httpbin.example.com/ \
--resolve httpbin.example.com:443:$GATEWAY_IP
```
- A call to the `/json` endpoint over https:
```shell
curl --insecure https://httpbin.example.com/json \
--resolve httpbin.example.com:443:$GATEWAY_IP
```
## Configure redirection
The platform team is the only party with the permission to apply this routing rule, to redirect HTTP requests to HTTPS with a [301 (redirected) response code](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/301):
```yaml linenums="1" hl_lines="12"
--8<-- "https/httpbin-to-https.yaml"
```
```shell
kubectl apply -f https/httpbin-to-https.yaml
```
To learn more about HTTPRoute rules and specifically filters, see the [relevant section in the Gateway API documentation](https://gateway-api.sigs.k8s.io/reference/spec/#gateway.networking.k8s.io/v1.HTTPRouteRule).
---
## :white_check_mark: Test
Verify that you get a [301 response](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/301) when curling the http endpoint:
```shell
curl -v http://httpbin.example.com/ --resolve httpbin.example.com:80:$GATEWAY_IP
```
Here is a copy of the captured output:
```console linenums="1" hl_lines="12-13"
* Host httpbin.example.com:80 was resolved.
* IPv6: (none)
* IPv4: 34.121.222.176
* Trying 34.121.222.176:80...
* Connected to httpbin.example.com (34.121.222.176) port 80
> GET / HTTP/1.1
> Host: httpbin.example.com
> User-Agent: curl/8.7.1
> Accept: */*
>
* Request completely sent off
< HTTP/1.1 301 Moved Permanently
< location: https://httpbin.example.com:443/
< date: Tue, 07 May 2024 21:21:19 GMT
< content-length: 0
<
* Connection #0 to host httpbin.example.com left intact
```
# Summary
We now have an ingress configuration that functions over HTTPS using a shared gateway that accommodates the needs of both the platform team and multiple application teams.