23

I have a manifest as the following

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: my-redis
spec:
  selector:
    matchLabels:
      app: my-redis
  replicas: 1
  template:
    metadata:
      labels:
        app: my-redis
    spec:
      containers:
       - name: my-redis
         image: redis
         ports:
         - name: redisport1
           containerPort: 6379
           hostPort: 6379

---
apiVersion: v1
kind: Service
metadata:
  name: redis-service
  labels:
    app: my-redis
spec:
  type: NodePort
  selector:
    name: my-redis
  ports:
  - name: redisport1
    port: 6379
    targetPort: 6379
    nodePort: 30036
    protocol: TCP

This is a sample that reproduces my problem. My intention here is to create a simple cluster that has a pod with a redis container in it, and it should be exposed to my localhost. Still, get services gives me the following output:

redis-service   NodePort    10.107.233.66   <none>        6379:30036/TCP   10s

If I swap NodePort with LoadBalancer, I get an external-ip but still port doesn't work.

Can you help me identify why I'm failing to map the 6379 port to my localhost, please?

Thanks,

Akaedintov
  • 747
  • 1
  • 6
  • 17
  • please provide results of `kubectl get pods --all-namespaces, are you using minikube or kubeadm or maybe other tool, is it on-premise or some cloud provider? – aurelius Nov 02 '18 at 16:27

3 Answers3

16

In order to access your app through node port, you have to use this url http://{node ip}:{node port}.

If you are using minikube, your minikube ip is the node ip. You can retrieve it using minikube ip command.

You can also use minikube service redis-service --url command to get the url to access your application through node port.

Emruz Hossain
  • 4,764
  • 18
  • 26
14

For anybody who's interested in the question, I found the problem. After Ijaz's fix, I also needed to change the selector to match the label in the pod, it was a typo on my end!

pod has "app=my-redis" tag, but Service selector had "name=my-redis". Matching them fixed the access problem.

Akaedintov
  • 747
  • 1
  • 6
  • 17
  • 1
    Can you elaborate on this answer? What did you change in your yml file to fix it? – slashdottir Feb 07 '19 at 17:42
  • 2
    Just changed "name: my-redis" on the service selector, to "app: my-redis". Because I set the matchLabels on deployment so. – Akaedintov Feb 08 '19 at 06:12
  • 1
    I made the same typo mistake haha :D For more clearance; if you use 'name' on deployment yaml under selector, you have to use 'name' also on service yaml file. If you use 'app' then you have to use 'app' on the selector part. – ahmet Aug 11 '20 at 13:45
5

Dont need the hostPort:

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: my-redis
spec:
  selector:
    matchLabels:
      app: my-redis
  replicas: 1
  template:
    metadata:
      labels:
        app: my-redis
    spec:
      containers:
       - name: my-redis
         image: redis
         ports:
         - name: redisport1
           containerPort: 6379


---
apiVersion: v1
kind: Service
metadata:
  name: redis-service
  labels:
    app: my-redis
spec:
  type: NodePort
  selector:
    name: my-redis
  ports:
  - name: redisport1
    port: 6379
    targetPort: 6379
    nodePort: 30036
    protocol: TCP

now the nodePort 30036 can be used to access the service on any worker node.

If the cluster node is somewhere else and you want to make the port available on you local client , then just do kubectl port forward

kubectl port-forward svc/redis-service 6379:6379

https://kubernetes.io/docs/tasks/access-application-cluster/port-forward-access-application-cluster/

Notes:

  • On-prem installs of k8s dont support service type of load balancer
  • ClusterIP is the IP on the pod network
  • Node IP is the IP of some machine that is running the k8s cluster
Ijaz Ahmad
  • 11,198
  • 9
  • 53
  • 73
  • Thanks for the answer. But I think I'm getting confused about ips and accesses, so here's my services: $ kubectl get services NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE kubernetes ClusterIP 10.96.0.1 443/TCP 1m redis-service NodePort 10.104.104.6 6379:30036/TCP 1m And I'm failing to access the redis using redis-commander: redis-commander --redis-host 10.104.104.6 --redis-port 30036 – Akaedintov Nov 01 '18 at 16:45
  • ClusterIP is internal to kubernetes , so you can use it if you are running commander inside another pod , if you are running commander on some external system you need to access redis on nodeport 30036 using the ip of the machine on which the k8s is running – Ijaz Ahmad Nov 01 '18 at 16:58
  • @Akaedintov where are you running k8s? update your questiion with kubernetes setup , environment – Ijaz Ahmad Nov 01 '18 at 17:04
  • 1
    hi @IjazAhmadKhan, I am running into this issue as well. My cluster is running on raspberry pi on local network. I am ssh'ing into the master node from my laptop. I have my node-ip of the worker nodes, typed in : for the service, but it doesn't work. When i do `kubectl exec $POD_NAME -it -- curl localhost` I do see the service welcome page (nginx). Any suggestions? Thanks. – Spencer Trinh Mar 01 '21 at 01:19