How to verify working Traefik installation? - kubernetes

I'm in the process of setting up Traefik on a Kubernetes cluster, but I can't get it to work, so I need some troubleshooting help. The first thing I would like to verify is that the basic installation is successful.
The guide I'm following is this one:
https://docs.traefik.io/user-guide/kubernetes/
But, I'm installing on a 3-machine cluster (Master + 2x Nodes).
I have setup RBAC and create a Deployment / Service for Traefik. The Pod is up and running:
$ kubectl get pods --namespace kube-system
NAME READY STATUS RESTARTS AGE
traefik-ingress-controller-7cf98d69cf-n2trx 1/1 Running 0 1h
This is the Service:
$ kubectl get services --namespace kube-system
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
traefik-ingress-service NodePort 10.107.17.76 <none> 80:30820/TCP,8080: 31362/TCP 1h
Should I be able to access the Traefik Web UI now?
I tried to access "http://192.168.1.11:31362" from a web browser and it behaves a bit strange. I get a "404 page not found" error in the browser window, but the address bar in the browser changes to: "http://192.168.1.11:31362/dashboard/". That tells me that something is responding at that address / port.
This is the result of a Curl to the same address:
$ curl http://192.168.1.11:31362/
Found.
Is this normal behaviour at this step in the process?
I have also tried to test with an Service / Ingress like this:
apiVersion: v1
kind: Service
metadata:
name: test-service
spec:
selector:
app: homeautomationweb
ports:
- port: 80
targetPort: 31047
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: test-ingress
annotations:
kubernetes.io/ingress.class: traefik
spec:
rules:
- host: test.no
http:
paths:
- backend:
serviceName: test-service
servicePort: 80
I have a working web application running in the cluster exposed on a node port and is accessible outside the cluster at http://http://192.168.1.11:31047/.
The DNS name "test.no" is defined in /etc/hosts as 192.168.1.11
But, when I try to access http://test.no, I get:
"test.no refused to connect"
The details of what I'm doing and the exact content of the Kubernetes Yaml files can be found at the end of this article:
https://github.com/olavt/KubernetesRaspberryPI

Related

Application not accessible using ingress but works with LoadBalancer GKE

I am trying to configure a hello world application using ingress in GKE. I have been referring a GCP official documentation to deploy an application using Ingress.
Deploying an app using ingress
But this does not work i have tried to refer several documents but none of those work. I have installed the ingress controller in my kubernetes cluster.
kubectl get svc -n ingress-nginx returns below output
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S)
AGE
ingress-nginx-controller LoadBalancer 10.125.177.232 35.232.139.102 80:31835/TCP,443:31583/TCP 7h24m
kubectl get pods-n ingress-nginx returns
NAME READY STATUS RESTARTS AGE
ingress-nginx-admission-create-jj72r 0/1 Completed 0 7h24m
ingress-nginx-admission-patch-pktz6 0/1 Completed 0 7h24m
ingress-nginx-controller-5cb8d9c6dd-vptkh 1/1 Running 0 7h24m
kubectl get ingress returns below output
NAME CLASS HOSTS ADDRESS PORTS AGE
ingress-resource <none> 35.232.139.102.nip.io 34.69.2.173 80 7h48m
kubectl get pods returns below output
NAME READY STATUS RESTARTS AGE
hello-app-6d7bb985fd-x5qpn 1/1 Running 0 43m
kubect get svc returns below output
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
hello-app ClusterIP 10.125.187.239 <none> 8080/TCP 43m
Ingress resource yml file used
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ingress-resource
annotations:
kubernetes.io/ingress.class: "nginx"
nginx.ingress.kubernetes.io/ssl-redirect: "false"
spec:
rules:
- host: 35.232.139.102.nip.io
http:
paths:
- pathType: Prefix
path: "/hello"
backend:
service:
name: hello-app
port:
number: 8080
Can someone tell me what i am doing wrong ? When i try to reach the application its not working.
So I have installed Ingress-controller and used ingress controller ip as the host in my ingress file.
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ingress-resource
annotations:
kubernetes.io/ingress.class: "nginx"
nginx.ingress.kubernetes.io/ssl-redirect: "false"
spec:
rules:
- host: "35.232.139.102.nip.io"
http:
paths:
- pathType: Prefix
path: "/hello"
backend:
service:
name: hello-app
port:
number: 8080
Issue here was I forgot to add the IP from which I was accessing the application. When you create a GKE cluster there will be a firewall with the cluster-name-all in this firewall you will need to add your IP address of the machine from which you are trying to access the application. Also ensure that the port number is also exposed in my case both were not provided hence it was failing.

ERR_CONNECTION_TIMED_OUT kubernetes minikube service

I am getting ERR_CONNECTION_TIMED_OUT when trying to access minikube service in localhost.
apiVersion: apps/v1
kind: Deployment
metadata:
name: identityserver
spec:
selector:
matchLabels:
app: identityserver
template:
metadata:
labels:
app: identityserver
spec:
containers:
- name: identityserver
image: identityserver:0
ports:
- containerPort: 5001
imagePullPolicy: "Never"
I have created service as following.
apiVersion: v1
kind: Service
metadata:
name: identityserver
spec:
type: NodePort
selector:
app: identityserver
ports:
- port: 5001
nodePort: 30002
I am trying to load in my local browser using following command. But it is not getting accessible in localhost. Internal kubernetes apps are able to communicate with service but not externally.
minikube service identityserver
I tried making type as clusterip and then it worked with port forwarding and only nodeport is having issue accessing.
kubectl port-forward service/identityserver 18080:5001 --address 0.0.0.0
This seems to be an issue with the Docker driver. I was able to run this with VirtualBox driver.
So I just had to start using VirtualBox driver (Even though virtualization was enabled in my machine it was giving an error. so had to append the --no-vtx-check flag, you can skip that if not facing an error without that flag)
minikube start --driver=virtualbox --no-vtx-check
There are several ways of trying minikube on Windows + docker:
Docker Desktop app (with Enable Kubernetes option)
Docker Desktop app (without enabling Kubernetes option) and installing minikube to wsl2
No Docker Desktop at all, installing docker and minikube in wsl2
Let's test it with the link you gave in comments - Set up Ingress on Minikube with the NGINX Ingress Controller.
Docker Desktop v.20.10.12 (with Enable Kubernetes option v.1.22.5), Win10, wsl2 backend.
Enable Kubernetes in Docker Desktop.
Check if ingress-controller is installed:
$ kubectl get pods -n ingress-nginx
The output should be similar to:
NAME READY STATUS RESTARTS AGE
ingress-nginx-admission-create-g9g49 0/1 Completed 0 11m
ingress-nginx-admission-patch-rqp78 0/1 Completed 1 11m
ingress-nginx-controller-59b45fb494-26npt 1/1 Running 0 11m
Create a Deployment using the following command:
kubectl create deployment web --image=gcr.io/google-samples/hello-app:1.0
Expose the Deployment:
kubectl expose deployment web --type=NodePort --port=8080
Create example-ingress.yaml from the following file:
$ kubectl apply -f example-ingress.yaml
$ cat example-ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: example-ingress
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /$1
spec:
ingressClassName: nginx # this line is essential!
rules:
- host: hello-world.info
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: web
port:
number: 8080
Verify the IP address is set:
NAME CLASS HOSTS ADDRESS PORTS AGE
example-ingress <none> hello-world.info localhost 80 38s
Add the following line to the bottom of the C:\Windows\System32\drivers\etc\hosts file on your computer (you will need administrator access):
127.0.0.1 hello-world.info
DONE. Open hello-world.info in a browser.
How to access the NodePort service? In C:\Windows\System32\drivers\etc\hosts find these lines:
# Added by Docker Desktop
192.168.1.179 host.docker.internal
192.168.1.179 gateway.docker.internal
Use this IP and node port: curl 192.168.1.179:portNumber

Find why i am getting 502 Bad gateway error on kubernetes

I am using kubernetes. I have Ingress service which talks my container service. We have exposed a webapi which works all fine. But we keep getting 502 bad gateway error. I am new to kubernetes and i have no clue how to go about debugging this issue. Server is a nodejs server connected to database. Is there anything wrong with configuration?
My Deployment file--
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: my-pod
spec:
replicas: 1
template:
metadata:
labels:
app: my-pod
spec:
containers:
- name: my-pod
image: my-image
ports:
- name: "http"
containerPort: 8086
resources:
limits:
memory: 2048Mi
cpu: 1020m
---
apiVersion: v1
kind: Service
metadata:
name: my-pod-serv
spec:
ports:
- port: 80
targetPort: "http"
selector:
app: my-pod
My Ingress Service:
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: gateway
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /
spec:
rules:
- host: abc.test.com
http:
paths:
- path: /abc
backend:
serviceName: my-pod-serv
servicePort: 80
In Your case:
I think that you get this 502 gateway error because you don't have Ingress controller configured correctly.
Please try do do it with installed Ingress like in example below. It will do all automatically.
Nginx Ingress step by step:
1) Install helm
2) Install nginx controller using helm
$ helm install stable/nginx-ingress --name nginx-ingress
It will create 2 services. You can get their details via
$ kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.39.240.1 <none> 443/TCP 29d
nginx-ingress-controller LoadBalancer 10.39.243.140 35.X.X.15 80:32324/TCP,443:31425/TCP 19m
nginx-ingress-default-backend ClusterIP 10.39.252.175 <none> 80/TCP 19m
nginx-ingress-controller - in short, it's dealing with requests to Ingress and directing
nginx-ingress-default-backend - in short, default backend is a service which handles all URL paths and hosts the nginx controller doesn't understand
3) Create 2 deployments (or use yours)
$ kubectl run my-pod --image=nginx
deployment.apps/my-pod created
$ kubectl run nginx1 --image=nginx
deployment.apps/nginx1 created
4) Connect to one of the pods
$ kubectl exec -ti my-pod-675799d7b-95gph bash
And add additional line to the output to see which one we will try to connect later.
$ echo "HELLO THIS IS INGRESS TEST" >> /usr/share/nginx/html/index.html
$ exit
5) Expose deployments.
$ kubectl expose deploy nginx1 --port 80
service/nginx1 exposed
$ kubectl expose deploy my-pod --port 80
service/my-pod exposed
This will automatically create service and will looks like
apiVersion: v1
kind: Service
metadata:
labels:
app: my-pod
name: my-pod
selfLink: /api/v1/namespaces/default/services/my-pod
spec:
ports:
- port: 80
protocol: TCP
targetPort: 80
selector:
app: my-pod
sessionAffinity: None
type: ClusterIP
status:
loadBalancer: {}
6) Now its the time to create Ingress.yaml and deploy it. Each rule in ingress need to be specified. Here I have 2 services. Each service specification starts with -host under rule parameter.
Ingress.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: two-svc-ingress
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /
spec:
rules:
- host: my.pod.svc
http:
paths:
- path: /pod
backend:
serviceName: my-pod
servicePort: 80
- host: nginx.test.svc
http:
paths:
- path: /abc
backend:
serviceName: nginx1
servicePort: 80
$ kubectl apply -f Ingress.yaml
ingress.extensions/two-svc-ingress created
7) You can check Ingress and hosts
$ kubectl get ingress
NAME HOSTS ADDRESS PORTS AGE
two-svc-ingress my.pod.svc,nginx.test.svc 35.228.230.6 80 57m
8) Eplanation why I installed Ingress.
Connect to the ingress controller pod
$ kubectl exec -ti nginx-ingress-controller-76bf4c745c-prp8h bash
www-data#nginx-ingress-controller-76bf4c745c-prp8h:/etc/nginx$ cat /etc/nginx/nginx.conf
Because I have installed nginx ingress earlier, after deploying Ingress.yaml, the nginx-ingress-controller found changes and automatically added necessary code.
In this file you should be able to find whole configuration for two services. I will not copy configuration but only headers.
start server my.pod.svc
start server nginx.test.svc
www-data#nginx-ingress-controller-76bf4c745c-prp8h:/etc/nginx$ exit
9) Test
$ kubectl get svc to get your nginx-ingress-controller external IP
$ curl -H "HOST: my.pod.svc" http://35.X.X.15/
default backend - 404
$ curl -H "HOST: my.pod.svc" http://35.X.X.15/pod
<!DOCTYPE html>
...
</html>
HELLO THIS IS INGRESS TEST
Please keep in mind Ingress needs to be in the same namespace like services. If you have a few services in many namespace you need to create Ingress for each namespace.
I would need to set up a cluster in order to test your yml files.
Just to help you debugging, follow this steps:
1- get the logs of the my-pod container using kubectl logs my-pod-container-name, make sure everything is working
2- Use port-forward to expose your container and test it.
3- Make sure the service is working properly, change its type to load balancer, so you can reach it from outside the cluster.
If the three things are working there is a problem with your ingress configuration.
I am not sure if I explained it in a detailed way, let me know if something is not clear

Expose service on local kubernetes

I'm running a local kubernetes bundled with docker on Mac OS.
How can I expose a service, so that I can access the service via a browser on my Mac?
I've created:
a) deployment including apache httpd.
b) service via yaml:
apiVersion: v1
kind: Service
metadata:
name: apaches
spec:
selector:
app: web
type: NodePort
ports:
- protocol: TCP
port: 80
externalIPs:
- 192.168.1.10 # Network IP of my Mac
My service looks like:
$ kubectl get service apaches
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
apaches NodePort 10.102.106.158 192.168.1.10 80:31137/TCP 14m
I can locally access the service in my kubernetes cluster by wget $CLUSTER-IP
I tried to call http://192.168.1.10/ on my Mac, but it doesn't work.
This question deals to a similar issue. But the solution does not help, because I do not know which IP I can use.
Update
Thanks to Michael Hausenblas I worked out a solution using Ingress.
Nevertheless there are still some open questions:
What is the meaning of a service's externalIP? Why do I need an externalIP when I do not directly access a service from external?
What is the meaning of the service port 31137?
The kubernetes docs describe a method to [publish a service in minikube via NodePort][4]. Is this also possible with kubernetes bundled on docker?
There are several solutions to expose services in kubernetes:
http://alesnosek.com/blog/2017/02/14/accessing-kubernetes-pods-from-outside-of-the-cluster/
Here are my solutions according to alesnosek for a local kubernetes bundled with docker:
1. hostNetwork
hostNetwork: true
Dirty (the host network should not be shared for security reasons) => I did not check this solution.
2. hostPort
hostPort: 8086
Does not apply to services => I did not check this solution.
3. NodePort
Expose the service by defining a nodePort:
apiVersion: v1
kind: Service
metadata:
name: apaches
spec:
type: NodePort
ports:
- port: 80
nodePort: 30000
selector:
app: apache
4. LoadBalancer
EDIT
#MathObsessed posted the solution in his anwer.
5. Ingress
a. Install Ingress Controller
git clone https://github.com/jnewland/local-dev-with-docker-for-mac-kubernetes.git
kubectl apply -f nginx-ingress/namespaces/nginx-ingress.yaml -Rf nginx-ingress
b. Configure Ingress
kubectl apply -f apache-ing.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: apache-ingress
spec:
rules:
- host: localhost
http:
paths:
- path: /
backend:
serviceName: apaches
servicePort: 80
Now I can access my apache deployed with kubernetes by calling http://localhost/
Remarks for using local-dev-with-docker-for-mac-kubernetes
The repo simplifies the deployment of the offical ingress-nginx controller
For production use I would follow the official guide.
The repos ships with a tiny full featured ingress example. Very useful for getting quickly a working example application.
Further documentation
https://kubernetes.io/docs/concepts/services-networking/ingress
For those still looking for an answer. I've managed to achieve this by adding another Kube service just to expose my app to localhost calls (via browser or Postman):
kind: Service
apiVersion: v1
metadata:
name: apaches-published
spec:
ports:
- name: http
port: 8080
targetPort: 80
protocol: TCP
selector:
app: web
type: LoadBalancer
Try it now on: http://localhost:8080
Really simple example
METHOD1
$ kubectl create deployment nginx-dep --image=nginx --replicas=2
Get the pods
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
nginx-dep-5c5477cb4-76t9q 1/1 Running 0 7h5m
nginx-dep-5c5477cb4-9g84j 1/1 Running 0 7h5m
Access the pod using kubectl port
$ kubectl port-forward nginx-dep-5c5477cb4-9g84j 8888:80
Forwarding from 127.0.0.1:8888 -> 80
Forwarding from [::1]:8888 -> 80
Now do a curl to the localhost:8888
$ curl -v http://localhost:8888
METHOD2
You can expose port 80 of the deployment (where the application is runnin i.e. nginx port)
via a NodePort
$ kubectl expose deployment nginx-dep --name=nginx-dep-svc --type=NodePort --port=80
Get the service
$ kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 31d
nginx-dep-svc NodePort 10.110.80.21 <none> 80:31239/TCP 21m
Access the deployment using hte NodePort
$ curl http://localhost:31239
As already mentioned in Matthias Ms answer there are several ways.
As the offical Kubernetes documentation specifically describes using a Service with a type NodePort I wanted to describe the workflow.
NodePort: Exposes the Service on each Node’s IP at a static port (the NodePort). A ClusterIP Service, to which the NodePort Service routes, is automatically created. You’ll be able to contact the NodePort Service, from outside the cluster, by requesting <NodeIP>:<NodePort>.
If you set the type field to NodePort, the Kubernetes control plane allocates a port from a range specified by --service-node-port-range flag (default: 30000-32767). Each node proxies that port (the same port number on every Node) into your Service. Your Service reports the allocated port in its .spec.ports[*].nodePort field.
Setup a Service with a type of NodePort
apiVersion: v1
kind: Service
metadata:
name: my-service
spec:
selector:
app: MyApp
ports:
- protocol: TCP
port: 80
targetPort: 9376
clusterIP: 10.0.171.239
type: NodePort
Then you can check on which port the Service is exposed to via
kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
my-service NodePort 10.103.218.215 <none> 9376:31040/TCP 52s
and access it via localhost using the exposed port. E.g.
curl http://localhost:31040

How to access dashboard service internal use Kubernetes

I have kubernetes-dashboard service with type is ClusterIP. How can I access dashboard internal? I use Alibaba Cloud.
My service.yml
---
kind: Service
apiVersion: v1
metadata:
labels:
kubernetes.io/cluster-service: "true"
app: kubernetes-dashboard
name: kubernetes-dashboard
namespace: kube-system
spec:
type: ClusterIP
ports:
- port: 80
targetPort: 9090
selector:
app: kubernetes-dashboard
I would like to run my dashboard at http://MASTER_IP:80
The status when running kubectl cluster-info:
Kubernetes master is running at https://MASTER_IP:6443
Heapster is running at https://MASTER_IP:6443/api/v1/namespaces/kube-system/services/heapster/proxy
KubeDNS is running at https://MASTER_IP:6443/api/v1/namespaces/kube-system/services/kube-dns/proxy
kubernetes-dashboard is running at https://MASTER_IP:6443/api/v1/namespaces/kube-system/services/kubernetes-dashboard/proxy
monitoring-influxdb is running at https://MASTER_IP:6443/api/v1/namespaces/kube-system/services/monitoring-influxdb/proxy
When I access https://MASTER_IP:6443, I got the error default backend - 404.
Note: Don't use NodePort and kubectl proxy.
Many thanks.
Change the dashboard service type to NodePort then you can access dashboard with any cluster :
change service type from ClusterIP to NodePort
kubectl -n kube-system edit svc kubernetes-dashboard
Get the service port number.
kubectl -n kube-system get svc kubernetes-dashboard -o yaml |grep nodePort
Access dahboard with https://masererverIP:nodeportnumber
In this answer you can find the different ways to access the dashboard.
If you are not using NodePort or kubectl proxy, your best options are
API Server
In case Kubernetes API server is exposed and accessible from outside you can directly access dashboard at: https://<master-ip>:<apiserver-port>/api/v1/namespaces/kube-system/services/https:kubernetes-dashboard:/proxy/
Ingress
Dashboard can be also exposed using Ingress resource. For example
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: kubernetes-dashboard-ingress
namespace: kube-system
spec:
rules:
— host: kubernetes
http:
paths:
— path: /ui
backend:
serviceName: kubernetes-dashboard
servicePort: 80