<p><em>*Cross-posted from k3d GitHub Discussion: <a href="https://github.com/rancher/k3d/discussions/690" rel="nofollow noreferrer">https://github.com/rancher/k3d/discussions/690</a></em></p>
<p>I am attempting to expose two services over two ports. As an alternative, I'd also love to know how to expose them over the same port and use different routes. I've attempted a few articles and a lot of configurations. Let me know where I'm going wrong with the networking of k3d + k3s / kubernetes + traefik (+ klipper?)...</p>
<p>I posted an example:
<a href="https://github.com/ericis/k3d-networking" rel="nofollow noreferrer">https://github.com/ericis/k3d-networking</a></p>
<h3 id="the-goal-xa62">The goal:</h3>
<ul>
<li>Reach &quot;app-1&quot; on host over port 8080</li>
<li>Reach &quot;app-2&quot; on host over port 8091</li>
</ul>
<h3 id="steps-wa5i">Steps</h3>
<p><em>*See: <a href="https://github.com/ericis/k3d-networking" rel="nofollow noreferrer">files in repo</a></em></p>
<ol>
<li><p>Configure <code>k3d</code> cluster and expose app ports to load balancer</p>
<pre><code>ports:
  # map localhost to loadbalancer
  - port: 8080:80
    nodeFilters:
      - loadbalancer
  # map localhost to loadbalancer
  - port: 8091:80
    nodeFilters:
      - loadbalancer
</code></pre>
</li>
<li><p>Deploy apps with &quot;deployment.yaml&quot; in Kubernetes and expose container ports</p>
<pre><code>ports:
  - containerPort: 80
</code></pre>
</li>
<li><p>Expose services within kubernetes. Here, I've tried two methods.</p>
<ul>
<li><p>Using CLI</p>
<pre><code>$ kubectl create service clusterip app-1 --tcp=8080:80
$ kubectl create service clusterip app-2 --tcp=8091:80
</code></pre>
</li>
<li><p>Using &quot;service.yaml&quot;</p>
<pre><code>spec:
  ports:
  - protocol: TCP
    # expose internally
    port: 8080
    # map to app
    targetPort: 80
  selector:
    run: app-1
</code></pre>
</li>
</ul>
</li>
<li><p>Expose the services outside of kubernetes using &quot;ingress.yaml&quot;</p>
<pre><code>backend:
  service:
    name: app-1
    port:
      # expose from kubernetes
      number: 8080
</code></pre>
</li>
</ol>

<p>You either have to use an ingress, or have to open ports on each individual node (k3d runs on docker, so you have to expose the docker ports)</p>
<p><em>Without opening a port <em>during the creation of the k3d cluster</em>, a nodeport service will not expose your app</em></p>
<p><code>k3d cluster create mycluster -p 8080:30080@agent[0]</code></p>
<p>For example, this would open an &quot;outside&quot; port (on your localhost) 8080 and map it to 30080 on the node - then you can use a NodePort service to actually connect the traffic from that port to your app:</p>
<pre><code>apiVersion: v1
kind: Service
metadata:
 name: some-service
spec:
 ports:
 - protocol: TCP
   port: 80
   targetPort: some-port
   nodePort: 30080
 selector:
   app: pgadmin
 type: NodePort
</code></pre>
<p>You can also open ports on the server node like:
<code>k3d cluster create mycluster -p 8080:30080@server[0]</code></p>
<p>Your apps can get scheduled to run on whatever node, and if you force a pod to appear on a specific node (lets say you open a certain port on agent[0] and set up your .yaml files to work with that certain port), for some reason the local-path rancher storage-class just breaks and will not create a persistent volume for your claim. You kinda have to get lucky &amp; have your pod get scheduled where you need it to. (if you find a way to schedule pods on specific nodes without the storage provisioner breaking, let me know)</p>
<p>You also can map a whole range of ports, like:
<code>k3d cluster create mycluster --servers 1 --agents 1 -p &quot;30000-30100:30000-30100@server[0]&quot;</code>
but be careful with the amount of ports you open, if you open too much, k3d will crash.</p>
<p><em>Using a load balancer</em> - it's similar, you just have to open one port &amp; map to to the load balancer.</p>
<p><code>k3d cluster create my-cluster --port 8080:80@loadbalancer</code></p>
<p>You then <em>have</em> to use an ingress, (or the traffic won't reach)</p>
<pre><code>apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: hello
  annotations:
    ingress.kubernetes.io/ssl-redirect: &quot;false&quot;
spec:
  rules:
  - http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service:
            name: hello
            port:
              number: 80
</code></pre>
<p>I also think that ingress will only route http &amp; https traffic, https should be done on the port <code>443</code>, supposedly you can map both port <code>80</code> and port <code>443</code>, but I haven't been able to get that to work (I think that certificates need to be set up as well).</p>
