Skip to content

Instantly share code, notes, and snippets.

@caruccio
Created February 6, 2024 12:13
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save caruccio/32e24c989dc77ed6acd9e4475dfd847d to your computer and use it in GitHub Desktop.
Save caruccio/32e24c989dc77ed6acd9e4475dfd847d to your computer and use it in GitHub Desktop.
Kubectl port-forward with fzf

If you have fuzzy finder, use the following functions to filter for multiple kubernetes services and port-foward using a stable and unique local port.

Put the code below into your ~/.bashrc (or any place you source from)

kpfz ()
{ 
    local svcs=$(FZF_DEFAULT_COMMAND="command kubectl get svc -o json $_NS | svc-ports" fzf -m --ansi --no-preview -1 --exact --select-1 --query="$@");
    if [ -z "$svcs" ]; then
        return;
    fi;
    pids=();
    for svc in $svcs;
    do
        local lport=$(cut -d: -f3 <<< $svc);
        local port=$(cut -d: -f2 <<< $svc);
        local name=$(cut -d: -f1 <<< $svc);
        local cmd="kubectl port-forward $_NS svc/$name $lport:$port";
        echo "+ $cmd";
        command $cmd & pids+=($!);
    done;
    trap "echo Killing pids: ${pids[*]}; kill -INT ${pids[*]}" SIGINT SIGTERM SIGHUP EXIT;
    wait;
    trap - SIGINT SIGTERM SIGHUP EXIT;
    sleep 1
}

kpfzn () 
{ 
    local ns="$1";
    shift;
    _NS="-n $ns" kpfz "$@"
}

Put the file below in your $PATH and make it executable (ex: chmod +x /usr/local/bin/svc-ports). It reads a list of services from stdinand outputs a list of stable (always the same for each service:port) tuples in the format service:port:localport. Try it like this: kubectl get service --all-namespaces -o=json | svc-ports

#!/usr/bin/env python

import json
import sys
import zlib

data = json.load(sys.stdin)

for svc in data.get('items', []):
    metadata = svc['metadata']
    name = metadata['name']
    namespace = metadata['namespace']
    spec = svc['spec']
    lport = zlib.crc32(bytes(metadata['uid'],'utf-8')) >>26 <<10
    for port in spec.get('ports', []):
        print(f'{name}:{port["port"]}:{lport}')

Finally, use it like this:

$ kpfz
$ kpfzn mynamespace

Screenshot-2024-02-06-12-06-55

Use TAB to port-forward MORE THAN ONE SERVICE® at a time!

kpfz[n] stards for Kubectl PortForward fZf [Namespace] which follows the same pattern as kubectl-aliases

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment