How to access a service from other machine in LAN?

3.5k views Asked by At

Hello Im learning kubernetes with the minikube. I can access a service via minikubeip:NodePort on the machine where the minikube is running and now I want to access the Service via LAN from other machine. I tried ingress but it didn't work for me.

Deployment file:

---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: aspnetapp-deployment
  labels:
    app: aspnetapp
spec:
  replicas: 2
  selector:
    matchLabels:
      app: aspnetapp
  template:
    metadata:
      labels:
        app: aspnetapp
    spec:
      containers:
        - name: aspnetapp-cn
          image: localhost:5000/aspnetapp
          ports: 
            - containerPort: 80

Service file:

---
apiVersion: v1
kind: Service
metadata:
    name: aspnetapp-service
spec:
    type: NodePort
    ports:
    - name: http
      targetport: 80      
      port: 80
      protocol: TCP
    selector:
      app: aspnetapp

Ingress file:

---
apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
  name: aspnetapp-ingress
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /$1
spec:
  rules:
    - host:
      http:
        paths:
        - path: /aspnetapp
          backend:
            serviceName: aspnetapp-service
            servicePort: 80
3

There are 3 answers

1
Dawid Kruk On

To expose your application to LAN with Ubuntu with a --docker driver you can use:

  • $ kubectl port-forward ...

Disclaimer!

  1. Your $ kubectl port-forward should be run on a host running minikube.
  2. Command above will operate continuously (& can be used to run it in a background)

Example:

Let's assume that you have an Ubuntu machine with IP: 192.168.0.115.

I've created an example using nginx image:

Deployment.yaml

apiVersion: apps/v1 # for versions before 1.9.0 use apps/v1beta2
kind: Deployment
metadata:
  name: nginx
spec:
  selector:
    matchLabels:
      app: nginx
  replicas: 1
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx
        ports:
        - containerPort: 80

As for the service exposing your Deployment you can either:

  • Use following command:
    • $ kubectl expose deployment nginx --port=80 --type=NodePort
  • Use definition below:
apiVersion: v1
kind: Service
metadata:
  name: nginx
spec:
  type: NodePort
  selector:
    app: nginx
  ports:
    - protocol: TCP
      port: 80
      targetPort: 80   


You can expose your nginx in two ways:

  • Directly with $ kubectl port-forward.
  • Directing the traffic to the Ingress controller.

Direct access

You can expose your Service directly without using Ingress by:

  • $ kubectl port-forward --address=0.0.0.0 deployment/nginx 10000:80

Dissecting above command:

  • --address=0.0.0.0 - expose outside of localhost
  • deployment/nginx - resource/resource_name
  • 10000:80 - port on host machine/port on pod to send the traffic to

Assigning local ports under 1024 will need root access!

You will need to login to root and either copy .kube/config to /root/ directory or specify where kubectl should look for config!

After running above command you should be able to run:

  • curl 192.168.1.115:10000

Command $ kubectl port-forward will generate:

Forwarding from 0.0.0.0:10000 -> 80 # AT THE START
Handling connection for 10000 # CURL FROM 192.168.0.2

Directing the traffic to the Ingress controller

You need to run $ minikube addons enable ingress to have functionalities of Ingress resource

In your example you used Ingress resource. In this situation you should:

  • Create Ingress resource (as you did).
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: ingress
spec:
  rules:
  - host:
    http:
      paths:
      - path: /
        backend:
          serviceName: nginx
          servicePort: 80
  • Forward the traffic to the Ingress controller!

Ingress controller after receiving the traffic will forward it further (to your Service and then to Pod)

To forward the traffic to your Ingress controller run this command:

  • kubectl port-forward --address=0.0.0.0 --namespace=kube-system deployment/ingress-nginx-controller 80:80

Dissecting above command once more:

  • --address=0.0.0.0 - expose outside of localhost
  • --namespace=kube-system - namespace that the Deployment of Ingress controller resides in
  • deployment/ingress-nginx-controller - resource/resource-name
  • 80:80 - port on host machine/port on pod to send the traffic to

Command $ kubectl port-forward will generate:

Forwarding from 0.0.0.0:80 -> 80 # AT THE START 
Handling connection for 80 # CURL FROM 192.168.0.2

I also encourage you to use different --driver like for example Virtualbox. You will be able to expose your application without $ kubectl port-forward (NAT).

Additional resources:

3
turbosree On

The ingress option seems not working: kubectl port-forward --address=0.0.0.0 --namespace=kube-system deployment/ingress-nginx-controller 80:80

I get the following error: error: unable to forward port because pod is not running. Current status=Pending

minikube version is v1.20.0 ingress controller version is v0.44.0

Example setup: Trying to access web services deployed in a minikube cluster from another machine in the same LAN. In the host machine, the service is accessed like, 'http://express.api/users'. 'express.api' is resolved using an entry in hosts file to ingress IP address.

0
Madhusudanan K K C On

well if you are on doker desktop based kubernetes, this hacked worked for me 127.0.0.1:6443 works, but where as yourlapip:6443 from remote machine does not work.. quick easy work around is to manage it in windows host machine. by port forwarding

netsh interface portproxy add v4tov4 listenport=4000 listenaddress=0.0.0.0 connectport=6443 connectaddress=127.0.0.1

then access k8s api from remote machine (connected to your network through) https://machinesnetworkip:4000