GKE Ingress TLS vs jupyter TLS but not both? - ssl

I'm setting up a jupyter-lab container in a kubernetes cluster and want to enable TLS. I have successfully done this in 2 ways:
Include the certificate and key files inside the container and enable TLS when running the jupyter command. Add a LoadBalancer Service to expose the container.
#Dockerfile
...
CMD jupyter-lab --no-browser --allow-root --ip 0.0.0.0 --port=443 --certfile=<crt path> --keyfile=<key path>
#yaml
apiVersion: v1
kind: Service
metadata:
name: <service-name>
spec:
type: LoadBalancer
selector:
app: <app-name>
ports:
- protocol: TCP
port: 443
targetPort: 443
Run jupyter with no TLS. Add certificate and key in base64 to a Secret. Add NodePort, Ingress and BackendConfig yamls.
#Dockerfile
...
CMD jupyter-lab --no-browser --allow-root --ip 0.0.0.0 --port=443
apiVersion: cloud.google.com/v1
kind: BackendConfig
metadata:
name: http-hc-config
spec:
healthCheck:
checkIntervalSec: 300
timeoutSec: 10
healthyThreshold: 2
unhealthyThreshold: 5
type: HTTP
requestPath: /login
port: 443
---
apiVersion: v1
kind: Service
metadata:
name: <service-name>
annotations:
cloud.google.com/backend-config: '{"ports": {"443":"http-hc-config"}}'
spec:
type: NodePort
selector:
app: <app-name>
ports:
- protocol: TCP
port: 443
targetPort: 443
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: <ingress-name>
annotations:
kubernetes.io/ingress.allow-http: "false"
spec:
tls:
- secretName: <secret-name>
defaultBackend:
service:
name: <service-name>
port:
number: 443
---
apiVersion: v1
data:
tls-crt: <base64 crt>
tls-key: <base64 key>
kind: Secret
metadata:
name: <secret-name>
type: kubernetes.io/tls
However, when I try to combine both (follow steps in 2, but also enable tls in jupyter-lab), I get 502 errors. Why is this?
Also, which setup is better?

If you want TLS between the HTTP(S) LB created by Ingress, you'll need to modify your BackendConfig to specify HTTPS for the healthcheck:
apiVersion: cloud.google.com/v1
kind: BackendConfig
metadata:
name: http-hc-config
spec:
healthCheck:
checkIntervalSec: 300
timeoutSec: 10
healthyThreshold: 2
unhealthyThreshold: 5
type: HTTPS
requestPath: /login
port: 443

Related

traefik always send traffic via tcp to middleware not over TLS

We are trying to encrypt communication between traefik ingress and middleware (forwardauth) & ingress to backend server also.
Forwardauth redirects traffic to authentication server which is running over https and used selfsinged certificate.
In the wireshark i can see that ingress is communicating with authentication server using TCP insted TLS, but the communication between ingress and backend server using tls.
Please help how to enable tls communication between traefik ingress and middleware .
apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
annotations:
kubernetes.io/ingress.class: traefik
name: traefik-tls-1
namespace: sample-domain1-ns
spec:
entryPoints:
- websecure
routes:
- kind: Rule
match: PathPrefix(`/api`)
middlewares:
- name: test-auth-https
namespace: sample-domain1-ns
- name: test-auth
namespace: sample-domain1-ns
services:
- kind: Service
name: sample-svc
port: 8002
scheme: "https"
serversTransport: mytransport
tls:
secretName: domain1-tls-cert
options:
name: mtlsoption-ecprt
namespace: sample-domain1-ns
apiVersion: traefik.containo.us/v1alpha1
kind: Middleware
metadata:
name: test-auth-https
namespace: sample-domain1-ns
spec:
redirectScheme:
scheme: https
permanent: true
apiVersion: traefik.containo.us/v1alpha1
kind: Middleware
metadata:
name: test-auth
namespace: sample-domain1-ns
spec:
forwardAuth:
address: https://s-lb.sample-ns.svc.cluster.local:8080/auth
tls:
insecureSkipVerify: true
communication between traefik ingress and middleware as well as backend server should be on TLS.

ingress controller path based routing for apache applications deployed on kubernetes

I have a tomcat image with deployed SampleWebApp.war in conf/webapps
I am deploying this image inside pod on kubernetes cluster.
I want to expose clusterIP service pointing to tomcat application through ingress controller.
I can't use "/" in my ingress controller for redirection as already another application is using same host and path "/"
I tried giving path as "tomcat" . but it is not accessible when i tried to open UI on web
Below are my yaml's. can someone suggest what can be done here ?
Deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: tomcatinfra
namespace: tomcat
spec:
replicas: 1
selector:
matchLabels:
app: tomcatinfra
template:
metadata:
name: tomcatinfra
labels:
app: tomcatinfra
spec:
containers:
- image: saravak/tomcat8
name: tomcatapp
Sevice.yaml
kind: Service
apiVersion: v1
metadata:
name: tomcat-service
namespace: tomcat
spec:
type: ClusterIP
selector:
app: tomcatinfra
ports:
- protocol: TCP
port: 3000
targetPort: 8080
Ingress :
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: tomcat
namespace: tomcat
spec:
rules:
- host: build.com
http:
paths:
- backend:
serviceName: tomcat-service
servicePort: 8080
path: /tomcat
pathType: ImplementationSpecific
Try adding the annotation of ingress class
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ingress
annotations:
kubernetes.io/ingress.class: "nginx"
spec:
rules:
- host: "foo.bar.com"
http:
paths:
- pathType: Prefix
path: /tomcat
backend:
service:
name: service1
port:
number: 80

why i get the error "backend - 404 error" when trying to deploy tls ingress in kubernetes with no errors on events

I'm trying to deploy a simple Ingress service and works when is Ingress without the Secure function(tls), but when I include the cert tls it always returns me "backend - 404 error"
I already installed "cert manager", "ingress-nginx" and already checked if this install is ok
EDIT: I explained all the steps I'm doing
EDIT2: I updated the cert-manager's version to v1.5.4
these were the steps:
1.- install nginx controller for my ip
helm install bitnami/nginx-ingress-controller --set controller.service.loadBalancerIP="[MY-STATIC-IP]",rbac.create=true --generate-name
2.- Apply deployment and service (app.yaml)
apiVersion: apps/v1
kind: Deployment
metadata:
name: taxisbahiadeploy
labels:
type: endpoints-app
spec:
replicas: 1
selector:
matchLabels:
app: taxisbahiadeploy
template:
metadata:
labels:
app: taxisbahiadeploy
spec:
containers:
- name: taxisbahiadeploy
image: gcr.io/google-samples/hello-app:1.0
imagePullPolicy: Always
ports:
- containerPort: 8080
---
apiVersion: v1
kind: Service
metadata:
name: taxisbahia
spec:
ports:
- port: 8080
targetPort: 8080
selector:
app: taxisbahiadeploy
3.- Configure let's encrypt
kubectl apply -f https://github.com/jetstack/cert-manager/releases/download/v1.5.4/cert-manager.crds.yaml
kubectl create namespace cert-manager
helm repo add jetstack https://charts.jetstack.io
helm repo update
helm install \
cert-manager \
--namespace cert-manager \
--version v1.5.4 \
jetstack/cert-manager
4- Apply the Issuer (issuer.yaml)
apiVersion: cert-manager.io/v1alpha2
kind: Issuer
metadata:
name: letsencrypt-staging
spec:
acme:
server: https://acme-staging-v02.api.letsencrypt.org/directory
email: 'fco#ggggg.com'
privateKeySecretRef:
name: letsencrypt-staging
solvers:
- http01:
ingress:
class: nginx
---
apiVersion: cert-manager.io/v1alpha2
kind: Issuer
metadata:
name: letsencrypt-prod
spec:
acme:
server: https://acme-v02.api.letsencrypt.org/directory
email: 'fco#ggggg.com'
privateKeySecretRef:
name: letsencrypt-prod
solvers:
- http01:
ingress:
class: nginx
5.- Final Step, this is the Ingress where it fails (ingress-tls.yaml)
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: esp-ingress
annotations:
kubernetes.io/ingress.class: nginx
cert-manager.io/issuer: "letsencrypt-staging"
spec:
tls:
- hosts:
- domain.com
secretName: esp-tls
rules:
- host: domain.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: taxisbahia
port:
number: 8080
i think your TLS domain part should be something like check your host
spec:
tls:
- hosts:
- example.example.com
secretName: quickstart-example-tls
Reference : https://cert-manager.io/docs/tutorials/acme/ingress/
First of all make sure that you are actually visiting https://yourapp.com
Had the same issue but then I realized I was actually trying HTTP, which is no longer available after TLS is added.

Can't get kubernetes to pass my tls certificate to browsers

I've been struggling for a while trying to get HTTPS access to my Elasticsearch cluster in Kubernetes.
I think the problem is that Kubernetes doesn't like the TLS certificate I'm trying to use, which is why it's not passing it all the way through to the browser.
Everything else seems to work, since when I accept the Kubernetes Ingress Controller Fake Certificate, the requests go through as expected.
In my attempt to do this I've set up:
The cluster itself
An nginx-ingress controller
An ingress resource
Here's the related yaml:
Cluster:
apiVersion: v1
kind: Service
metadata:
creationTimestamp: 2018-08-03T03:20:47Z
labels:
run: my-es
name: my-es
namespace: default
resourceVersion: "3159488"
selfLink: /api/v1/namespaces/default/services/my-es
uid: 373047e0-96cc-11e8-932b-42010a800043
spec:
clusterIP: 10.63.241.39
ports:
- name: http
port: 8080
protocol: TCP
targetPort: 9200
selector:
run: my-es
sessionAffinity: None
type: ClusterIP
status:
loadBalancer: {}
The ingress resource
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
annotations:kubernetes.io/ingress.class: nginx
nginx.ingress.kubernetes.io/cors-allow-methods: PUT, GET, POST, OPTIONS
nginx.ingress.kubernetes.io/cors-origins: http://localhost:3425 https://mydomain.ca
https://myOtherDomain.ca
nginx.ingress.kubernetes.io/enable-cors: "true"
nginx.ingress.kubernetes.io/rewrite-target: /
creationTimestamp: 2018-08-12T08:44:29Z
generation: 16
name: es-ingress
namespace: default
resourceVersion: "3159625"
selfLink: /apis/extensions/v1beta1/namespaces/default/ingresses/es-ingress
uid: ece0071d-9e0b-11e8-8a45-42001a8000fc
spec:
rules:
- http:
paths:
- backend:
serviceName: my-es
servicePort: 8080
path: /
tls:
- hosts:
- mydomain.ca
secretName: my-tls-secret
status:
loadBalancer:
ingress:
- ip: 130.211.179.225
The nginx-ingress controller:
apiVersion: v1
kind: Service
metadata:
creationTimestamp: 2018-08-12T00:41:32Z
labels:
app: nginx-ingress
chart: nginx-ingress-0.23.0
component: controller
heritage: Tiller
release: nginx-ingress
name: nginx-ingress-controller
namespace: default
resourceVersion: "2781955"
selfLink: /api/v1/namespaces/default/services/nginx-ingress-controller
uid: 755ee4b8-9dc8-11e8-85a4-4201a08000fc
spec:
clusterIP: 10.63.250.256
externalTrafficPolicy: Cluster
ports:
- name: http
nodePort: 32084
port: 80
protocol: TCP
targetPort: http
- name: https
nodePort: 31182
port: 443
protocol: TCP
targetPort: https
selector:
app: nginx-ingress
component: controller
release: nginx-ingress
sessionAffinity: None
type: LoadBalancer
status:
loadBalancer:
ingress:
- ip: 35.212.6.131
I feel like I'm missing something basic, because it doesn't seem like it should be this hard to expose something this simple...
To get my certificate, I just requested one for mydomain.ca from godaddy.
Do I need to somehow get a certificate using my ingress resource's cluster IP as the common name?
It doesn't seem possible to verify ownership of an IP.
I've seen people mention ways for Kubernetes to automatically create certificates for ingress resources, but those seem to be self signed.
Here are some logs from the nginx-controller:
This one is talking about a PEM with the tls-secret, but it's only a warning.
{
insertId: "1kvvhm7g1q7e0ej"
labels: {
compute.googleapis.com/resource_name: "fluentd-gcp-v2.0.17-5b82n"
container.googleapis.com/namespace_name: "default"
container.googleapis.com/pod_name: "nginx-ingress-controller-58f57fc597-zl25s"
container.googleapis.com/stream: "stderr"
}
logName: "projects/project-7d320/logs/nginx-ingress-controller"
receiveTimestamp: "2018-08-14T02:58:42.135388365Z"
resource: {
labels: {
cluster_name: "my-elasticsearch-cluster"
container_name: "nginx-ingress-controller"
instance_id: "2341889542400230234"
namespace_id: "default"
pod_id: "nginx-ingress-controller-58f57fc597-zl25s"
project_id: "project-7d320"
zone: "us-central1-a"
}
type: "container"
}
severity: "WARNING"
textPayload: "error obtaining PEM from secret default/my-tls-cert: error retrieving secret default/my-tls-cert: secret default/my-tls-cert was not found"
timestamp: "2018-08-14T02:58:37Z"
}
I have a few occurences of this handshake error, which may be a result of the last warning...
{
insertId: "148t6rfg1xmz978"
labels: {
compute.googleapis.com/resource_name: "fluentd-gcp-v2.0.17-5b82n"
container.googleapis.com/namespace_name: "default"
container.googleapis.com/pod_name: "nginx-ingress-controller-58f57fc597-zl25s"
container.googleapis.com/stream: "stderr"
}
logName: "projects/project-7d320/logs/nginx-ingress-controller"
receiveTimestamp: "2018-08-14T15:55:52.438035706Z"
resource: {
labels: {
cluster_name: "my-elasticsearch-cluster"
container_name: "nginx-ingress-controller"
instance_id: "2341889542400230234"
namespace_id: "default"
pod_id: "nginx-ingress-controller-58f57fc597-zl25s"
project_id: "project-7d320"
zone: "us-central1-a"
}
type: "container"
}
severity: "ERROR"
textPayload: "2018/08/14 15:55:50 [crit] 1548#1548: *860 SSL_do_handshake() failed (SSL: error:1417D18C:SSL routines:tls_process_client_hello:version too low) while SSL handshaking, client: 127.0.0.1, server: 0.0.0.0:442"
timestamp: "2018-08-14T15:55:50Z"
}
The above logs make it seem like my tls secret isnt working, but when I run kubectl describe ingress, it says my secret terminates.
aaronmw#project-7d320:~$ kubectl describe ing
Name: es-ingress
Namespace: default
Address: 130.221.179.212
Default backend: default-http-backend:80 (10.61.3.7:8080)
TLS:
my-tls-secret terminates mydomain.ca
Rules:
Host Path Backends
---- ---- --------
*
/ my-es:8080 (<none>)
Annotations:
Events: <none>
I figured it out!
What I ended up doing was adding a default ssl certificate to my nginx-ingress controller on creation using the following command
helm install --name nginx-ingress --set controller.extraArgs.default-ssl-certificate=default/search-tls-secret stable/nginx-ingress
Once I had that, it was passing the cert as expected, but I still had the wrong cert as the CN didn't match my load balancer IP.
So what I did was:
Make my load balancer IP static
Add an A record to my domain, to map a subdomain to that IP
Re-key my cert to match that new subdomain
And I'm in business!
Thanks to #Crou, who's comment reminded me to look at the logs and got me on the right track.

Trouble at configuring http(s) for an nginx-ingress

Im currently trying to create an ingress, following the ssl-termination approach, which allows me to connect to a service both via http and https.
I managed to create a working ingress for http, partly for https, but not both together..
heres my config
Ingress Controller: Deployment & Service
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: nginx-ingress-controller
spec:
replicas: 1
revisionHistoryLimit: 3
template:
metadata:
labels:
k8s-app: nginx-ingress-lb
spec:
containers:
- args:
- /nginx-ingress-controller
- "--default-backend-service=$(POD_NAMESPACE)/default-http-backend"
env:
<!-- default-config ommitted -->
image: "quay.io/kubernetes-ingress-controller/nginx-ingress-controller:0.9.0-beta.17"
imagePullPolicy: Always
livenessProbe:
<!-- omitted -->
name: nginx-ingress-controller
ports:
- containerPort: 80
name: http
protocol: TCP
- containerPort: 443
name: https
protocol: TCP
volumeMounts:
- mountPath: /etc/nginx-ssl/tls
name: tls-vol
terminationGracePeriodSeconds: 60
volumes:
- name: tls-vol
secret:
secretName: tls-test-project-secret
---
apiVersion: v1
kind: Service
metadata:
name: nginx-ingress
spec:
type: NodePort
ports:
- name: http
port: 80
targetPort: http
nodePort: 31115
- name: https
port: 443
targetPort: https
nodePort: 31116
selector:
k8s-app: nginx-ingress-lb
Ingress
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: nginx-ingress
annotations:
kubernetes.io/ingress.class: "nginx"
ingress.kubernetes.io/secure-backends: "false"
# modified this to false for http & https-scenario
ingress.kubernetes.io/ssl-redirect: "true"
# modified this to false for http & https-scenario
nginx.ingress.kubernetes.io/force-ssl-redirect: "true"
ingress.kubernetes.io/add-base-url: "true"
spec:
tls:
- hosts:
- author.k8s-test
secretName: tls-test-project-secret
rules:
- host: author.k8s-test
http:
paths:
- path: /
backend:
serviceName: cms-author
servicePort: 8080
Backend - Service
apiVersion: v1
kind: Service
metadata:
name: cms-author
spec:
selector:
run: cms-author
ports:
- name: http
protocol: TCP
port: 8080
targetPort: 8080
Backend-Deployment:
apiVersion: apps/v1
kind: Deployment
metadata:
name: cms-author
spec:
selector:
matchLabels:
run: cms-author
replicas: 1
template:
metadata:
labels:
run: cms-author
spec:
containers:
- name: cms-author
image: <someDockerRegistryUrl>/magnolia:kube-dev
imagePullPolicy: Always
ports:
- containerPort: 8080
I have several issues, when follwing the https only scenario, i can reach the application via the ingress https nodePort, but cant login, as the follwing request goes via http instead of https.. If i put manually https before the url in browser, it is working again and any further request goes via https., but I dont know why :(
The final setting (supporting http and https) is completely not working, as if I try to access the app via http-nodePort of Ingress, it always redirects to ssl, but in this scenario, I configured to ssl-redirect to false, but still not working.
I have read many posts on github, dealing with that, but none of them worked for me
I've changed the nginx-controller images from gce_containers to quay.io, also not working
I've tried some older versions, also not working.
Deploy the nginx ingress controller from the official kubernetes charts repo https://github.com/kubernetes/charts/tree/master/stable/nginx-ingress by setting the helm arguments controller.service.targetPorts.https and controller.service.nodePorts.https. Once they are set, the appropriate NodePort (443) will be configured by helm.
Helm uses the YAML files in https://github.com/kubernetes/charts/tree/master/stable/nginx-ingress/templates.
Along with the nginx ingress controller, you'll need an ingress resource too. Refer https://github.com/nginxinc/kubernetes-ingress/tree/master/examples/complete-example for examples.