k9s

derailedApache-2.0活跃维护

终端里的 Kubernetes 集群管理工具,用彩色 TUI 界面实时查看和操作 Pod、日志、资源,省去反复敲 kubectl 命令。

🐶 Kubernetes CLI To Manage Your Clusters In Style!

v0.51.0发布于 2026-06-06 14:13 UTC34,955star +19 / 7 天2,345fork同步于 2026-11-10 17:20 UTC

怎么上手

由 README 提炼,执行前请确认
brew install derailed/k9s/k9s
硬件要求按 README 说明

README 未说明;仅要求 256 色终端,K8s 建议 1.28+,源码构建需 Go 1.23.X 以上

有 Docker 镜像
下载:源码 zip·GitHub Releases(安装包)本站不镜像安装包

项目说明

由 README 自动翻译提炼

终端里的 Kubernetes 集群管理 UI,实时观察并操作集群资源

终端里的 Kubernetes 集群管理工具,用彩色 TUI 界面实时查看和操作 Pod、日志、资源,省去反复敲 kubectl 命令。

核心能力

  • 持续 watch 集群变化并实时刷新资源视图
  • 用别名和 : 命令快速跳转各类 K8s 资源
  • 支持按命名空间、标签、上下文过滤资源
  • 提供只读模式禁用所有集群修改命令
  • 可自定义皮肤、插件、热键与别名配置

容易踩的坑

需先设置 TERM=xterm-256color,否则终端颜色显示异常;执行资源编辑前要设置 EDITOR 或 KUBE_EDITOR 环境变量;用 go install 安装会得到 dev 版本而非稳定版

内容由模型根据 README 生成,可能不完整或不准确,以官方文档为准。看原文 README

最近发版

5 个版本v0.51.0
  1. v0.51.0最新正式版2026-06-06 · 2026-06-06 14:13 UTC

    Release v0.51.0

    Notes

    Thank you to all that contributed with flushing out issues and enhancements for K9s! I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev and see if we're happier with some of the fixes! If you've filed an issue please help me verify and close.

    Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated! Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

    As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our sponsorship program and/or make some noise on social! @kitesurfer

    On Slack? Please join us K9slackers


    ♫ Sounds Behind The Release ♭


    Maintenance Release!

    Please help me welcome Ümüt Özalp as a core contributor to K9s! Ümüt has been instrumental in helping this project grow. I trust you will help Ümüt triage issues and prs reviews and show him the kindness and patience all k9sers are famous for!

    Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig k9s and want to help the project, please consider paying it forward! and don't become just another satisfied, non paying customer!. K9s does take a lot of my free time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the freezer as I just can't budget them in. I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

    Thank you!


    Contributed PRs

    Please be sure to give Big Thanks! and ATTA Girls/Boys! to all the fine contributors for making K9s better for all of us!!

    • #4026 fix(xray): disable edit/delete actions in XRay view when readonly mode is enabled
    • #4024 Fix 'J'umping to owner of cluster scoped resources
    • #4005 Fix pod status for sidecar init containers
    • #4001 Adjust namespace handling for RBAC checks in CanForResource and CanForInstance
    • #3997 chore: fix wrong function name in comment
    • #3993 fix(browser): show syncing status instead of spurious no-resources warning
    • #3989 perf: skip reconcile cycle when informer data is unchanged
    • #3988 perf: raise default client QPS from 5 to 50
    • #3987 fix: paginate metrics API calls to prevent timeout on large clusters
    • #3986 perf: batch Hydrate workers to eliminate per-item goroutine overhead
    • #3917 Respect wide columns in default view
    • #3911 fix: reset styles before loading skin on context switch
    • #3908 fix: populate pod count in Node.Get() for single-node
  2. v0.50.182026-01-11 · 2026-01-11 20:19 UTC
    查看更新说明

    Release v0.50.18

    Notes

    🥳🎉 Happy new year fellow k9ers!🎊🍾 Hoping 2026 will bring good health and great success to you and yours...

    Thank you to all that contributed with flushing out issues and enhancements for K9s! I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev and see if we're happier with some of the fixes! If you've filed an issue please help me verify and close.

    Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated! Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

    As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our sponsorship program and/or make some noise on social! @kitesurfer

    On Slack? Please join us K9slackers


    ♫ Sounds Behind The Release ♭


    Maintenance Release!

    Oops! I've missed a PR in the v0.50.17 excitement ;( Dropping v0.50.18 with feelings...

    Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig k9s and want to help the project, please consider paying it forward! and don't become just another satisfied, non paying customer!. K9s does take a lot of my free time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the freezer as I just can't budget them in. I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

    Thank you!


    A Word From Our Sponsors...

    To all the good folks and orgs below that opted to pay it forward and join our sponsorship program, I salute you!!

    Sponsorship cancellations since the last release: 17! 🥹

    Resolved Issues

    • #3765 quay.io docker images not up to date but referenced in README.md
  3. v0.50.172026-01-11 · 2026-01-11 19:44 UTC
    查看更新说明

    Release v0.50.17

    Notes

    🥳🎉 Happy new year fellow k9ers!🎊🍾 Hoping 2026 will bring good health and great success to you and yours...

    Thank you to all that contributed with flushing out issues and enhancements for K9s! I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev and see if we're happier with some of the fixes! If you've filed an issue please help me verify and close.

    Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated! Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

    As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our sponsorship program and/or make some noise on social! @kitesurfer

    On Slack? Please join us K9slackers


    ♫ Sounds Behind The Release ♭


    Maintenance Release!

    Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig k9s and want to help the project, please consider paying it forward! and don't become just another satisfied, non paying customer!. K9s does take a lot of my free time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the freezer as I just can't budget them in. I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

    Thank you!

    A Word From Our Sponsors...

    To all the good folks and orgs below that opted to pay it forward and join our sponsorship program, I salute you!!

    Sponsorship cancellations since the last release: 17! 🥹

    Resolved Issues

    • #3765 quay.io docker images not up to date but referenced in README.md
    • #3762 Copy multiple selected items
    • [#3751](h
  4. v0.50.162025-10-19 · 2025-10-19 16:01 UTC
    查看更新说明

    Release v0.50.16

    Notes

    Thank you to all that contributed with flushing out issues and enhancements for K9s! I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev and see if we're happier with some of the fixes! If you've filed an issue please help me verify and close.

    Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated! Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

    As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our sponsorship program and/or make some noise on social! @kitesurfer

    On Slack? Please join us K9slackers

    Maintenance Release!

    Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig k9s and want to help the project, please consider paying it forward! and don't become just another satisfied, non paying customer!. K9s does take a lot of my free time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the freezer as I just can't budget them in. I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

    Thank you!

    Warp Speed Scotty!

    As of this drop, we are introducing namespace warp via shortcut w. This affords to view all resources of that type based on the currently selected resource namespace. This command is only available on namespaced resources. For example, if you are in pod view and select pod-xxx in namespace bozo, hitting w will warp you to view all pods in namespace bozo.

    Resolved Issues

    • #3629 vulnerability in k9s project
    • #3621 Switching to ":Deploy" sends you to deployments from namespace "deploy"
    • #3620 Trying to show pod yaml using custom views.yaml crashes k9s
    • #3608 k9s crashes when :namespaces used
    • #3601 Can't delete namespace
    • #3595 Toggle Namespace Filter in Pods View with 'n' Key
    • #3576 Custom alias/view not working anymore since v0.50.10

    Contributed PRs

    Please be sure to give Big Thanks! and ATTA Girls/Boys! to all the fine contributors for making K9s better for all of us!!

    • #3625 fix: debug-container plugin when KUBECONFIG has multiple files
    • #3623 bugfix: fix panic in BenchmarkPodRender by using NewPod() constructor
    • #3619 feat: plugin to list all resources by namespace
    • #3605 browser: do not prevent redraw when connection unavailable
    • #3600 fix(shell): set linux when OS detection fails
    • #3588 fix: do not error out of shellIn if OS detection fails

    © 2025 Imhotep Software LLC. All materials licensed under Apache v2.0#

  5. v0.50.152025-10-07 · 2025-10-07 13:34 UTC
    查看更新说明

    Release v0.50.15

    Notes

    Thank you to all that contributed with flushing out issues and enhancements for K9s! I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev and see if we're happier with some of the fixes! If you've filed an issue please help me verify and close.

    Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated! Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

    As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our sponsorship program and/or make some noise on social! @kitesurfer

    On Slack? Please join us K9slackers

    Maintenance Release!

    Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig k9s and want to help the project, please consider paying it forward! and don't become just another satisfied, non paying customer!. K9s does take a lot of my free time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the freezer as I just can't budget them in. I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

    Thank you!

    Resolved Issues

    • #3591 REVERTED! Accept suggestion with enter (without having to "tab")

    © 2025 Imhotep Software LLC. All materials licensed under Apache v2.0#

用户点评

登录用户的真实使用记录,可按版本和硬件筛选
共 0 条

    还没有人点评。第一个说出真实体验的人最有价值。

    README 原文

    未翻译

    K9s - Kubernetes CLI To Manage Your Clusters In Style!

    K9s provides a terminal UI to interact with your Kubernetes clusters. The aim of this project is to make it easier to navigate, observe and manage your applications in the wild. K9s continually watches Kubernetes for changes and offers subsequent commands to interact with your observed resources.


    Note...

    K9s is not pimped out by a big corporation with deep pockets. It is a complex OSS project that demands a lot of my time to maintain and support. K9s will always remain OSS and therefore free! That said, if you feel k9s makes your day to day Kubernetes journey a tad brighter, saves you time and makes you more productive, please consider sponsoring us! Your donations will go a long way in keeping our servers lights on and beers in our fridge!

    Thank you!


    Go Report Card golangci badge Docker Pulls release License Releases


    Screenshots

    1. Pods
    2. Logs
    3. Deployments

    Demo Videos/Recordings


    Documentation

    Please refer to our K9s documentation site for installation, usage, customization and tips.


    Slack Channel

    Wanna discuss K9s features with your fellow K9sers or simply show your support for this tool?


    Installation

    K9s is available on Linux, macOS and Windows platforms. Binaries for Linux, Windows and Mac are available as tarballs in the release page.

    • Via Homebrew for macOS or Linux

      brew install derailed/k9s/k9s
      
    • Via MacPorts

      sudo port install k9s
      
    • Via snap for Linux

      snap install k9s --devmode
      
    • On Arch Linux

      pacman -S k9s
      
    • On OpenSUSE Linux distribution

      zypper install k9s
      
    • On FreeBSD

      pkg install k9s
      
    • On Ubuntu

      wget https://github.com/derailed/k9s/releases/latest/download/k9s_linux_amd64.deb && sudo apt install ./k9s_linux_amd64.deb && rm k9s_linux_amd64.deb
      
    • On Fedora (42+)

      dnf install k9s
      
    • Via Winget for Windows

      winget install k9s
      
    • Via Scoop for Windows

      scoop install k9s
      
    • Via Chocolatey for Windows

      choco install k9s
      
    • Via a GO install

      # NOTE: The dev version will be in effect!
      go install github.com/derailed/k9s@latest
      
    • Via Webi for Linux and macOS

      curl -sS https://webinstall.dev/k9s | bash
      
    • Via pkgx for Linux and macOS

      pkgx k9s
      
    • Via gah for Linux and macOS

      gah install k9s
      
    • Via Webi for Windows

      curl.exe -A MS https://webinstall.dev/k9s | powershell
      
    • As a Docker Desktop Extension (for the Docker Desktop built in Kubernetes Server)

      docker extension install spurin/k9s-dd-extension:latest
      

    Building From Source

    K9s is currently using GO v1.23.X or above. In order to build K9s from source you must:

    1. Clone the repo

    2. Build and run the executable

      make build && ./execs/k9s
      

    Running with Docker

    Running the official Docker image

    You can run k9s as a Docker container by mounting your KUBECONFIG:

    docker run --rm -it -v $KUBECONFIG:/root/.kube/config derailed/k9s
    

    For default path it would be:

    docker run --rm -it -v ~/.kube/config:/root/.kube/config derailed/k9s
    

    Building your own Docker image

    You can build your own Docker image of k9s from the Dockerfile with the following:

    docker build -t k9s-docker:v0.0.1 .
    

    You can get the latest stable kubectl version and pass it to the docker build command with the --build-arg option. You can use the --build-arg option to pass any valid kubectl version (like v1.18.0 or v1.19.1).

    KUBECTL_VERSION=$(make kubectl-stable-version 2>/dev/null)
    docker build --build-arg KUBECTL_VERSION=${KUBECTL_VERSION} -t k9s-docker:0.1 .
    

    Run your container:

    docker run --rm -it -v ~/.kube/config:/root/.kube/config k9s-docker:0.1
    
    Building a multi-platform image

    The make imgx target builds for linux/amd64 and linux/arm64 via Docker buildx. Both imgx and pushx always tag the image with latest and the explicit VERSION in the same build, so a release can be pinned to a specific tag instead of only latest:

    make imgx
    

    Cross-architecture builds rely on QEMU emulation. Docker Desktop includes this out of the box. On a plain Docker Engine install, see the buildx multi-platform docs for enabling emulation.

    Override the defaults with BUILD_PLATFORMS, IMG_NAME and VERSION:

    make imgx BUILD_PLATFORMS=linux/amd64,linux/arm64 IMG_NAME=your-org/k9s VERSION=v0.0.1
    

    PreFlight Checks

    • K9s uses 256 colors terminal mode. On `Nix system make sure TERM is set accordingly.

      export TERM=xterm-256color
      
    • In order to issue resource edit commands make sure your EDITOR and KUBE_EDITOR env vars are set.

      # Kubectl edit command will use this env var.
      export KUBE_EDITOR=my_fav_editor
      
    • K9s prefers recent kubernetes versions ie 1.28+


    K8S Compatibility Matrix

    k9sk8s client
    >= v0.27.01.26.1
    v0.26.7 - v0.26.61.25.3
    v0.26.5 - v0.26.41.25.1
    v0.26.3 - v0.26.11.24.3
    v0.26.0 - v0.25.191.24.2
    v0.25.18 - v0.25.31.22.3
    v0.25.2 - v0.25.01.22.0
    <= v0.241.21.3

    The Command Line

    # List current version
    k9s version
    
    # To get info about K9s runtime (logs, configs, etc..)
    k9s info
    
    # List all available CLI options
    k9s help
    
    # To run K9s in a given namespace
    k9s -n mycoolns
    
    # Start K9s in an existing KubeConfig context
    k9s --context coolCtx
    
    # Start K9s in readonly mode - with all cluster modification commands disabled
    k9s --readonly
    

    Logs And Debug Logs

    Given the nature of the ui k9s does produce logs to a specific location. To view the logs and turn on debug mode, use the following commands:

    # Find out where the logs are stored
    k9s info
    
     ____  __.________
    |    |/ _/   __   \______
    |      < \____    /  ___/
    |    |  \   /    /\___ \
    |____|__ \ /____//____  >
            \/            \/
    
    Version:           vX.Y.Z
    Config:            /Users/fernand/.config/k9s/config.yaml
    Logs:              /Users/fernand/.local/state/k9s/k9s.log
    Dumps dir:         /Users/fernand/.local/state/k9s/screen-dumps
    Benchmarks dir:    /Users/fernand/.local/state/k9s/benchmarks
    Skins dir:         /Users/fernand/.local/share/k9s/skins
    Contexts dir:      /Users/fernand/.local/share/k9s/clusters
    Custom views file: /Users/fernand/.local/share/k9s/views.yaml
    Plugins file:      /Users/fernand/.local/share/k9s/plugins.yaml
    Hotkeys file:      /Users/fernand/.local/share/k9s/hotkeys.yaml
    Alias file:        /Users/fernand/.local/share/k9s/aliases.yaml
    

    View K9s logs

    tail -f /Users/fernand/.local/data/k9s/k9s.log
    

    Start K9s in debug mode

    k9s -l debug
    

    Customize logs destination

    You can override the default log file destination either with the --logFile argument:

    k9s --logFile /tmp/k9s.log
    less /tmp/k9s.log
    

    Or through the K9S_LOGS_DIR environment variable:

    K9S_LOGS_DIR=/var/log k9s
    less /var/log/k9s.log
    

    Key Bindings

    K9s uses aliases to navigate most K8s resources.

    ActionCommandComment
    Show active keyboard mnemonics and help?
    Show all available resource aliasctrl-a
    To bail out of K9s:quit, :q, ctrl-c
    To go up/back to the previous viewescIf you have crumbs on, this will go to the previous one
    View a Kubernetes resource using singular/plural or short-name:pod⏎accepts singular, plural, short-name or alias ie pod or pods
    View a Kubernetes resource in a given namespace:pod ns-x⏎
    View filtered pods (New v0.30.0!):pod /fred⏎View all pods filtered by fred
    View labeled pods (New v0.30.0!):pod app=fred,env=dev⏎View all pods with labels matching app=fred and env=dev
    View pods in a given context (New v0.30.0!):pod @ctx1⏎View all pods in context ctx1. Switches out your current k9s context!
    Filter out a resource view given a filter/filter⏎Regex2 supported ie `fred
    Inverse regex filter/! filter⏎Keep everything that doesn't match.
    Filter resource view by labels/-l label-selector⏎
    Fuzzy find a resource given a filter/-f filter⏎
    Bails out of view/command/filter mode<esc>
    To view and switch to another Kubernetes context (Pod view):ctx⏎
    To view and switch directly to another Kubernetes context (Last used view):ctx context-name⏎
    To view and switch to another Kubernetes namespace:ns⏎
    To switch back to the last active command (like how "cd -" works)-Navigation that adds breadcrumbs to the bottom are not commands
    To go back and forward through the command historyback: [, forward: ]Same as above
    To view all saved resources:screendump or sd⏎
    To delete a resource (TAB and ENTER to confirm)ctrl-d
    To kill a resource (no confirmation dialog, equivalent to kubectl delete --now)ctrl-k
    Launch pulses view:pulses or pu⏎
    Launch XRay view:xray RESOURCE [NAMESPACE]⏎RESOURCE can be one of po, svc, dp, rs, sts, ds, NAMESPACE is optional
    Launch Popeye view:popeye or pop⏎See popeye
    Mark resourcespace
    Mark range of resourcesctrl-space
    Clear all marksctrl-\
    Save resources to filectrl-s
    Toggle faults/error displayctrl-z
    Toggle wide columnsctrl-w
    Toggle headerctrl-e
    Toggle breadcrumbsctrl-g
    Move selected column leftshift-left arrow
    Move selected column rightshift-right arrow
    Sort by selected columnshift-o
    Sort by Nameshift-n
    Sort by Ageshift-a
    Sort by Namespaceshift-pOnly when viewing all namespaces
    Sort by Statusshift-s
    Copy resource namec
    Copy namespacen
    View YAMLy
    View logslResource specific
    View previous logspResource specific
    Shell into containersPods only
    Attach to containeraPods only
    Describe resourced
    Edit resourceeNot available in read-only mode
    Show port-forwardsfPods/Services/Containers
    Port forwardshift-fPods/Services/Containers
    Warp to namespacewWhen namespace column is available
    Jump to ownershift-jWhen resource has an owner
    Use/switch namespaceuNamespace view
    UsedBy (show resources using this)uServiceAccounts/PVCs/Secrets/ConfigMaps
    Benchmark (run/stop)bServices/Port-forwards
    Toggle text wrapwLog view
    Toggle timestamptLog view
    Toggle fullscreenfLog/YAML/Details view
    Refresh/reload viewctrl-r
    Trigger (CronJob)tCronJob view
    Cordon/Uncordon nodeuNode view
    Drain noderNode view
    Restart resourcerDeployments/DaemonSets/StatefulSets
    Rollback resourcectrl-lReplicaSets
    View ReplicaSetszDeployment view

    K9s Configuration

    K9s keeps its configurations as YAML files inside of a k9s directory and the location depends on your operating system. K9s leverages XDG to load its various configurations files. For information on the default locations for your OS please see this link. If you are still confused a quick k9s info will reveal where k9s is loading its configurations from. Alternatively, you can set K9S_CONFIG_DIR to tell K9s the directory location to pull its configurations from.

    UnixmacOSWindows
    ~/.config/k9s~/Library/Application Support/k9s%LOCALAPPDATA%\k9s

    NOTE: This is still in flux and will change while in pre-release stage!

    You can now override the context portForward default address configuration by setting an env variable that can override all clusters portForward local address using K9S_DEFAULT_PF_ADDRESS=a.b.c.d

    Clipboard behavior can also be controlled via environment variables:

    • K9S_CLIPBOARD=auto|native|osc52 (default auto)

      • auto: try native clipboard utilities first, then fall back to OSC52 when available.
      • native: only use native clipboard utilities (xclip/xsel/wl-clipboard/etc).
      • osc52: force OSC52 clipboard writes.
    • K9S_OSC52_MAX=<encoded-bytes> sets the maximum allowed OSC52 payload size before k9s rejects the copy operation. Default is 74994.

      # $XDG_CONFIG_HOME/k9s/config.yaml
      k9s:
        # Enable periodic refresh of resource browser windows. Default false
        liveViewAutoRefresh: false
        # !!New!! v0.50.8...
        # Extends the list of supported GPU vendors. The key is the vendor name, the value must correspond to k8s resource driver designation.
        # Default known GPU vendors:
        # nvidia: nvidia.com/gpu
          # nvidia-shared: nvidia.com/gpu.shared
          # amd: amd.com/gpu
          # intel: gpu.intel.com/i915
        gpuVendors:
          bozo: bozo/gpu  # extends the gpu vendor and add "bozo"
        # The path to screen dump. Default: '%temp_dir%/k9s-screens-%username%' (k9s info)
        screenDumpDir: /tmp/dumps
        # Represents ui poll intervals in seconds. Default 2.0 secs. Minimum value is 2.0 - values below will be capped to the minimum.
        refreshRate: 2
        # Overrides the default k8s api server requests timeout. Defaults 120s
        apiServerTimeout: 15s
        # Number of retries once the connection to the api-server is lost. Default 15.
        maxConnRetry: 5
        # Indicates whether modification commands like delete/kill/edit are disabled. Default is false
        readOnly: false
        # This setting allows users to specify the default view, but it is not set by default.
        defaultView: ""
        # Toggles whether k9s should exit when CTRL-C is pressed. When set to true, you will need to exit k9s via the :quit command. Default is false.
        noExitOnCtrlC: false
        #UI settings
        ui:
          # Enable mouse support. Default false
          enableMouse: false
          # Set to true to hide K9s header. Default false
          headless: false
          # Set to true to hide the K9S logo Default false
          logoless: false
          # Set to true to hide K9s crumbs. Default false
          crumbsless: false
          # Set to true to suppress the K9s splash screen on start. Default false. Note that for larger clusters or higher latency connections, there may be no resources visible initially until local caches have finished populating.
          splashless: false
          # Toggles icons display as not all terminal support these chars. Default: true
          noIcons: false
          # Toggles reactive UI. This option provide for watching on disk artifacts changes and update the UI live Defaults to false.
          reactive: false
          # By default all contexts will use the dracula skin unless explicitly overridden in the context config file.
          skin: dracula # => assumes the file skins/dracula.yaml is present in the  $XDG_DATA_HOME/k9s/skins directory. Can be overridden with K9S_SKIN.
          # Replaces the K9s header logo with custom ascii art. Can be overridden per context.
          logo: |
            MY
            K9S
          # Convert dark skins to light, or vice versa, preserving hue. Default: false
          invert: false
          # Allows to set certain views default fullscreen mode. (yaml, helm history, describe, value_extender, details, logs) Default false
          defaultsToFullScreen: false
          # Show full resource GVR (Group/Version/Resource) vs just R. Default: false.
          useFullGVRTitle: false
        # Toggles icons display as not all terminal support these chars.
        noIcons: false
        # Toggles whether k9s should check for the latest revision from the GitHub repository releases. Default is false.
        skipLatestRevCheck: false
        # Logs configuration
        logger:
          # Defines the number of lines to return. Default 100
          tail: 200
          # Defines the total number of log lines to allow in the view. Default 1000
          buffer: 500
          # Represents how far to go back in the log timeline in seconds. Setting to -1 will tail logs. Default is -1.
          sinceSeconds: 300 # => tail the last 5 mins.
          # Toggles log line wrap. Default false
          textWrap: false
          # Autoscroll in logs will be disabled. Default is false.
          disableAutoscroll: false
          # Enable column locking when autoscroll is enabled. Default is false.
          columnLock: false
          # Toggles log line timestamp info. Default false
          showTime: false
          # Sets the internal log channel buffer size. Increase when log lines are dropped under high throughput. Default 50
          logBufferSize: 100
        # Provide shell pod customization when nodeShell feature gate is enabled!
        shellPod:
          # The shell pod image to use.
          image: killerAdmin
          # The namespace to launch to shell pod into.
          namespace: default
          # The resource limit to set on the shell pod.
          limits:
            cpu: 100m
            memory: 100Mi
          # Enable TTY
          tty: true
          hostPathVolume:
          - name: docker-socket
            # Mount the Docker socket into the shell pod
            mountPath: /var/run/docker.sock
            # The path on the host to mount
            hostPath: /var/run/docker.sock
            readOnly: true
      

    Popeye Configuration

    K9s has integration with Popeye, which is a Kubernetes cluster sanitizer. Popeye itself uses a configuration called spinach.yml, but when integrating with K9s the cluster-specific file should be name $XDG_CONFIG_HOME/share/k9s/clusters/clusterX/contextY/spinach.yml. This allows you to have a different spinach config per cluster.


    Node Shell

    By enabling the nodeShell feature gate on a given cluster, K9s allows you to shell into your cluster nodes. Once enabled, you will have a new s for shell menu option while in node view. K9s will launch a pod on the selected node using a special k9s_shell pod. Furthermore, you can refine your shell pod by using a custom docker image preloaded with the shell tools you love. By default k9s uses a BusyBox image, but you can configure it as follows:

    Alternatively, you can now override the context configuration by setting an env variable that can override all clusters node shell gate using K9S_FEATURE_GATE_NODE_SHELL=true|false

    # $XDG_CONFIG_HOME/k9s/config.yaml
    k9s:
      # You can also further tune the shell pod specification
      shellPod:
        image: cool_kid_admin:42
        namespace: blee
        limits:
          cpu: 100m
          memory: 100Mi
    

    Then in your cluster configuration file...

    # $XDG_DATA_HOME/k9s/clusters/cluster-1/context-1
    k9s:
      cluster: cluster-1
      readOnly: false
      namespace:
        active: default
        lockFavorites: false
        favorites:
        - kube-system
        - default
      view:
        active: po
      featureGates:
        nodeShell: true # => Enable this feature gate to make nodeShell available on this cluster
    

    Customizing the Shell Pod

    You can also customize the shell pod by adding a hostPathVolume to your shell pod. This allows you to mount a local directory or file into the shell pod. For example, if you want to mount the Docker socket into the shell pod, you can do so as follows:

    k9s:
      shellPod:
        hostPathVolume:
        - name: docker-socket
          # Mount the Docker socket into the shell pod
          mountPath: /var/run/docker.sock
          # The path on the host to mount
          hostPath: /var/run/docker.sock
          readOnly: true
    

    This will mount the Docker socket into the shell pod at /var/run/docker.sock and make it read-only. You can also mount any other directory or file in a similar way.


    Command Aliases

    In K9s, you can define your very own command aliases (shortnames) to access your resources. In your $HOME/.config/k9s define a file called aliases.yaml. A K9s alias defines pairs of alias:gvr. A gvr (Group/Version/Resource) represents a fully qualified Kubernetes resource identifier. Here is an example of an alias file:

    #  $XDG_DATA_HOME/k9s/aliases.yaml
    aliases:
      pp: v1/pods
      crb: rbac.authorization.k8s.io/v1/clusterrolebindings
      # As of v0.30.0 you can also refer to another command alias...
      fred: pod fred app=blee # => view pods in namespace fred with labels matching app=blee
    

    Using this aliases file, you can now type :pp or :crb or :fred to activate their respective commands.


    HotKey Support

    Entering the command mode and typing a resource name or alias, could be cumbersome for navigating thru often used resources. We're introducing hotkeys that allow users to define their own key combination to activate their favorite resource views.

    Additionally, you can define context specific hotkeys by add a context level configuration file in $XDG_DATA_HOME/k9s/clusters/clusterX/contextY/hotkeys.yaml

    In order to surface hotkeys globally please follow these steps:

    1. Create a file named $XDG_CONFIG_HOME/k9s/hotkeys.yaml

    2. Add the following to your hotkeys.yaml. You can use resource name/short name to specify a command ie same as typing it while in command mode.

      #  $XDG_CONFIG_HOME/k9s/hotkeys.yaml
      hotKeys:
        # Hitting Shift-0 navigates to your pod view
        shift-0:
          shortCut:    Shift-0
          description: Viewing pods
          command:     pods
        # Hitting Shift-1 navigates to your deployments
        shift-1:
          shortCut:    Shift-1
          description: View deployments
          command:     dp
        # Hitting Shift-2 navigates to your xray deployments
        shift-2:
          shortCut:    Shift-2
          description: Xray Deployments
          command:     xray deploy
        # Hitting Shift-S view the resources in the namespace of your current selection
        shift-s:
          shortCut:    Shift-S
          override:    true # => will override the default shortcut related action if set to true (default to false)
          description: Namespaced resources
          command:     "$RESOURCE_NAME $NAMESPACE"
          keepHistory: true # whether you can return to the previous view
      

    Not feeling so hot? Your custom hotkeys will be listed in the help view ?. Also your hotkeys file will be automatically reloaded so you can readily use your hotkeys as you define them.

    You can choose any keyboard shortcuts that make sense to you, provided they are not part of the standard K9s shortcuts list.

    Similarly, referencing environment variables in hotkeys is also supported. The available environment variables can refer to the description in the Plugins section.

    NOTE: This feature/configuration might change in future releases!


    Port Forwarding over websockets

    K9s follows kubectl feature flag environment variables to enable/disable port-forwarding over websockets. (default enabled in >1.30) To disable Websocket support, set KUBECTL_PORT_FORWARD_WEBSOCKETS=false


    FastForwards

    As of v0.25.0, you can leverage the FastForwards feature to tell K9s how to default port-forwards. In situations where you are dealing with multiple containers or containers exposing multiple ports, it can be cumbersome to specify the desired port-forward from the dialog as in most cases, you already know which container/port tuple you desire. For these use cases, you can now annotate your manifests with the following annotations:

    @ k9scli.io/auto-port-forwards activates one or more port-forwards directly bypassing the port-forward dialog all together. @ k9scli.io/port-forwards pre-selects one or more port-forwards when launching the port-forward dialog.

    The annotation value takes on the shape container-name::[local-port:]container-port

    NOTE: for either cases above you can specify the container port by name or number in your annotation!

    Example

    # Pod fred
    apiVersion: v1
    kind: Pod
    metadata:
      name: fred
      annotations:
        k9scli.io/auto-port-forwards: zorg::5556        # => will default to container zorg port 5556 and local port 5566. No port-forward dialog will be shown.
        # Or...
        k9scli.io/port-forwards: bozo::9090:p1          # => launches the port-forward dialog selecting default port-forward on container bozo port named p1(8081)
                                                        # mapping to local port 9090.
        ...
    spec:
      containers:
      - name: zorg
        ports:
        - name: p1
          containerPort: 5556
        ...
      - name: bozo
        ports:
        - name: p1
          containerPort: 8081
        - name: p2
          containerPort: 5555
        ...
    

    The annotation value must specify a container to forward to as well as a local port and container port. The container port may be specified as either a port number or port name. If the local port is omitted then the local port will default to the container port number. Here are a few examples:

    1. bozo::http - creates a pf on container bozo with port name http. If http specifies port number 8080 then the local port will be 8080 as well.
    2. bozo::9090:http - creates a pf on container bozo mapping local port 9090->http(8080)
    3. bozo::9090:8080 - creates a pf on container bozo mapping local port 9090->8080

    Custom Views

    SneakCast v0.17.0 on The Beach! - Yup! sound is sucking but what a setting!

    You can change which columns shows up for a given resource via custom views. To surface this feature, you will need to create a new configuration file, namely $XDG_CONFIG_HOME/k9s/views.yaml. This file leverages GVR (Group/Version/Resource) to configure the associated table view columns. If no GVR is found for a view the default rendering will take over (ie what we have now). Going wide will add all the remaining columns that are available on the given resource after your custom columns. To boot, you can edit your views config file and tune your resources views live!

    Use version/resource for resources in the core API group and group/version/resource for resources in a named API group. For example, pods use v1/pods, while mutating webhook configurations use admissionregistration.k8s.io/v1/mutatingwebhookconfigurations.

    📢 🎉 As of release v0.40.0 you can specify json parse expressions to further customize your resources rendering.

    The new column syntax is as follows:

    COLUMN_NAME<:json_parse_expression><|column_attributes>

    Where :json_parse_expression represents an expression to pull a specific snippet out of the resource manifest. Similar to kubectl -o custom-columns command. This expression is optional.

    IMPORTANT! Columns must be valid YAML strings. Thus if your column definition contains non-alpha chars they must figure with either single/double quotes or escaped via \

    NOTE! Be sure to watch k9s logs as any issues with the custom views specification are only surfaced in the logs.

    Additionally, you can specify column attributes to further tailor the column rendering. To use this you will need to add a | indicator followed by your rendering bits. You can have one or more of the following attributes:

    • T -> time column indicator
    • N -> number column indicator
    • W -> turns on wide column aka only shows while in wide mode. Defaults to the standard resource definition when present.
    • S -> Ensures a column is visible and not wide. Overrides wide std resource definition if present.
    • H -> Hides the column
    • L -> Left align (default)
    • R -> Right align

    Here is a sample views configuration that customize a pods and services views.

    # $XDG_CONFIG_HOME/k9s/views.yaml
    views:
      v1/pods:
        columns:
          - AGE
          - NAMESPACE|WR                                     # => 🌚 Specifies the NAMESPACE column to be right aligned and only visible while in wide mode
          - ZORG:.metadata.labels.fred\.io\.kubernetes\.blee # => 🌚 extract fred.io.kubernetes.blee label into it's own column
          - BLEE:.metadata.annotations.blee|R                # => 🌚 extract annotation blee into it's own column and right align it
          - NAME
          - IP
          - NODE
          - STATUS
          - READY
          - MEM/RL|S                                         # => 🌚 Overrides std resource default wide attribute via `S` for `Show`
          - '%MEM/R|'                                        # => NOTE! column names with non alpha names need to be quoted as columns must be strings!
    
      v1/pods@fred:                                          # => 🌚 New v0.40.6! Customize columns for a given resource and namespace!
        columns:
          - AGE
          - NAME|WR
    
      v1/pods@kube*:                                         # => 🌚 New v0.40.6! You can also specify a namespace using a regular expression.
        columns:
          - NAME
          - AGE
          - LABELS
    
      cool-kid:                                              # => 🌚 New v0.40.8! You can also reference a specific alias and display a custom view for it
        columns:
          - AGE
          - NAMESPACE|WR
    
      v1/services:
        columns:
          - AGE
          - NAMESPACE
          - NAME
          - TYPE
          - CLUSTER-IP
    
      admissionregistration.k8s.io/v1/mutatingwebhookconfigurations:
        columns:
          - NAME
          - WEBHOOKS|N
          - AGE
          - POLICY:.webhooks[*].failurePolicy
          - TIMEOUT:.webhooks[*].timeoutSeconds|N
    

    🩻 NOTE: This is experimental and will most likely change as we iron this out!


    Resource Jumps

    K9s allows you to define custom jump shortcuts between Custom Resource Definitions (CRDs) and their related resources. This feature enables you to quickly jump from one CRD to its dependent or associated resources, similar to the built-in "jump to owner" behavior.

    By default, K9s provides built-in jumps for standard Kubernetes resources (e.g., Deployment → Pods, Node → Pods). With custom jumps, you can extend this behavior to your own CRDs without modifying k9s source code.

    To use this feature, create a configuration file at $XDG_CONFIG_HOME/k9s/jumps.yaml.

    Configuration Format

    # $XDG_CONFIG_HOME/k9s/jumps.yaml
    jumps:
      # Define jump from source GVR to target GVR
      "myoperator.io/v1/patchplans":
        targetGVR: "myoperator.io/v1/patchjobs"
        fieldSelector: "spec.patchPlanRef={{.metadata.name}}"
    

    Configuration Fields

    • Source GVR (map key): The Group/Version/Resource of the source CRD in format group/version/resource or version/resource for core resources
    • targetGVR: The target resource to jump to
    • labelSelector (optional): Kubernetes label selector to filter target resources. Supports Go template syntax
    • fieldSelector (optional): Kubernetes field selector to filter target resources. Supports Go template syntax
    • targetNamespace (optional): Controls namespace behavior:
      • Empty (default): Use the source resource's namespace (or cluster-scoped if source is cluster-scoped)
      • all: View resources across all namespaces
      • <namespace-name>: Jump to a specific namespace
      • {{.spec.field}}: Use template expression to extract namespace from source resource

    Template Syntax

    Both labelSelector and fieldSelector support Go template syntax to dynamically reference fields from the selected (source) resource. Any field of the source object can be used on the value side of a selector:

    • {{.metadata.name}} - The resource name
    • {{.metadata.namespace}} - The resource namespace
    • {{.metadata.labels.key}} - A specific label value
    • {{.spec.fieldName}} - Any field from the source resource spec
    • {{.status.field}} - Any field from the source resource status

    Note: The template above only controls the selector value (the right-hand side, computed from the source resource). For label selectors, the key can be any label and is matched server side. For field selectors, k9s applies the selector as a local (client-side) filter on the target resources, so the key may be any field path present in the target object (e.g. metadata.name, spec.volumeName), not just the API-selectable fields. This means field-selector jumps work even for resources whose fields are not server-side selectable. Field values are compared as strings, and the path is matched against the target object's manifest. For background on which fields the API server itself treats as selectable, see the Kubernetes docs on CRD selectable fields.

    Examples

    Jump between custom operator resources
    jumps:
      "myoperator.io/v1/patchplans":
        targetGVR: "myoperator.io/v1/patchjobs"
        fieldSelector: "spec.patchPlanRef={{.metadata.name}}"
    
    Jump from ArgoCD Application to Deployments
    jumps:
      "argoproj.io/v1alpha1/applications":
        targetGVR: "apps/v1/deployments"
        labelSelector: "app.kubernetes.io/instance={{.metadata.name}}"
    
    Jump from Karpenter NodePool to Nodes
    jumps:
      "karpenter.sh/v1/nodepools":
        targetGVR: "v1/nodes"
        labelSelector: "karpenter.sh/nodepool={{.metadata.name}}"
        targetNamespace: "all"  # Nodes are cluster-scoped
    

    How It Works

    1. When viewing a resource that has a custom jump rule defined

    2. Pressing Enter on a selected item will:

      • Apply the template expressions using the selected resource's data
      • Jump to the target resource view with filters applied
      • Automatically apply the label/field selectors to show only related resources
      • Adjust the namespace context as configured
    3. If no custom jump is defined, the default behavior applies (describe view or built-in jump)


    Plugins

    K9s allows you to extend your command line and tooling by defining your very own cluster commands via plugins. Minimally we look at $XDG_CONFIG_HOME/k9s/plugins.yaml to locate all available plugins. Additionally, K9s will scan the following directories for additional plugins:

    • $XDG_CONFIG_HOME/k9s/plugins
    • $XDG_DATA_HOME/k9s/plugins
    • $XDG_DATA_DIRS/k9s/plugins

    The plugin file content can be either a single plugin snippet, a collections of snippets or a complete plugins definition (see examples below...).

    A plugin is defined as follows:

    • Shortcut option represents the key combination a user would type to activate the plugin. Valid values are [a-z], Shift-[A-Z], Ctrl-[A-Z].
    • Override option make that the default action related to the shortcut will be overridden by the plugin
    • Confirm option (when enabled) lets you see the command that is going to be executed and gives you an option to confirm or prevent execution
    • Description will be printed next to the shortcut in the k9s menu
    • Scopes defines a collection of resources names/short-names for the views associated with the plugin. You can specify all to provide this shortcut for all views.
    • Command represents ad-hoc commands the plugin runs upon activation
    • Background specifies whether or not the command runs in the background
    • Args specifies the various arguments that should apply to the command above
    • OverwriteOutput boolean option allows plugin developers to provide custom messages on plugin stdout execution. See example in #2644
    • Dangerous boolean option enables disabling the plugin when read-only mode is set. See #2604
    • Inputs defines a list of input fields to prompt the user for before executing the plugin (see below)
    Plugin Inputs

    Plugins can define input fields that prompt users for values before execution. This is useful when you need dynamic values like replica counts, environment variables, or profile selections. A maximum of 5 inputs per plugin is allowed.

    Each input has the following properties:

    • name (required) -- the input identifier used to reference the value in args as $INPUT_<NAME> (uppercase)
    • label -- the label shown to the user in the input dialog
    • type (required) -- the input type: string, number, bool, or dropdown
    • required -- when true, the user must provide a value before the plugin can execute
    • default -- a default value pre-filled in the input field (must be a valid option for dropdown, "true"/"false" for bool, or a valid number for number)
    • options -- for dropdown type only, defines the list of available choices

    Input values are available in plugin args using the format $INPUT_<NAME> where <NAME> is the uppercase version of the input name.

    Input Types:

    TypeDescriptionUI Element
    stringFree-form text inputText field
    numberNumeric input (integers and floats)Text field with numeric validation
    boolBoolean toggleCheckbox
    dropdownSelection from predefined optionsDropdown menu

    Example:

    plugins:
      demo-inputs:
        shortCut: Ctrl-Y
        description: Demo all input types
        scopes:
          - po
        command: bash
        background: false
        args:
          - -c
          - >-
            echo "=== Plugin input demo ===" &&
            echo "" &&
            echo "Pod: $NAME" &&
            echo "Namespace: $NAMESPACE" &&
            echo "Context: $CONTEXT" &&
            echo "" &&
            echo "=== Your inputs ===" &&
            if [ -n "$INPUT_MESSAGE" ]; then echo "Message: $INPUT_MESSAGE (set)"; else echo "Message: (not set)"; fi &&
            if [ -n "$INPUT_COUNT" ]; then echo "Count: $INPUT_COUNT (set)"; else echo "Count: (not set)"; fi &&
            if [ -n "$INPUT_ENABLED" ]; then echo "Enabled: $INPUT_ENABLED (set)"; else echo "Enabled: (not set)"; fi &&
            if [ -n "$INPUT_ENVIRONMENT" ]; then echo "Environment: $INPUT_ENVIRONMENT (set)"; else echo "Environment: (not set)"; fi &&
            echo "" &&
            read -p "Press Enter to return to k9s..."
        inputs:
          - name: message
            label: Enter a message
            type: string
            required: true
            default: hello world
          - name: count
            label: Enter a number
            type: number
            required: true
            default: 3
          - name: enabled
            label: Enable feature
            type: bool
            required: false
            default: true
          - name: environment
            label: Select environment
            type: dropdown
            required: true
            default: staging
            options:
              - development
              - staging
              - production
    

    For a real-world example of plugin inputs, see pvc-resize.yaml which prompts the user for a new PVC size before resizing.

    K9s does provide additional environment variables for you to customize your plugins arguments. Currently, the available environment variables are as follows:

    • $RESOURCE_GROUP -- the selected resource group
    • $RESOURCE_VERSION -- the selected resource api version
    • $RESOURCE_NAME -- the selected resource name
    • $NAMESPACE -- the selected resource namespace
    • $NAME -- the selected resource name
    • $CONTAINER -- the current container if applicable
    • $FILTER -- the current filter if any
    • $KUBECONFIG -- the KubeConfig location.
    • $CLUSTER the active cluster name
    • $CONTEXT the active context name
    • $USER the active user
    • $GROUPS the active groups
    • $POD while in a container view
    • $COL-<RESOURCE_COLUMN_NAME> use a given column name for a viewed resource. Must be prefixed by COL-!

    Curly braces can be used to embed an environment variable inside another string, or if the column name contains special characters. (e.g. ${NAME}-example or ${COL-%CPU/L})

    Plugin Examples

    Define several plugins and host them in a single file. These can leave in the K9s root config so that they are available on any clusters. Additionally, you can define cluster/context specific plugins for your clusters of choice by adding clusterA/contextB/plugins.yaml file.

    The following defines a plugin for viewing logs on a selected pod using ctrl-l as shortcut.

    # Define several plugins in a single file in the K9s root configuration
    # $XDG_DATA_HOME/k9s/plugins.yaml
    plugins:
      # Defines a plugin to provide a `ctrl-l` shortcut to tail the logs while in pod view.
      fred:
        shortCut: Ctrl-L
        override: false
        overwriteOutput: false
        confirm: false
        dangerous: false
        description: Pod logs
        scopes:
        - pods
        command: kubectl
        background: false
        args:
        - logs
        - -f
        - $NAME
        - -n
        - $NAMESPACE
        - --context
        - $CONTEXT
    

    Similarly you can define the plugin above in a directory using either a file per plugin or several plugins per files as follow...

    The following defines two plugins namely fred and zorg.

    # Multiple plugins in a single file...
    # Note: as of v0.40.9 you can have ad-hoc plugin dirs
    # Loads plugins fred and zorg
    # $XDG_DATA_HOME/k9s/plugins/misc-plugins/blee.yaml
    fred:
      shortCut: Shift-B
      description: Bozo
      scopes:
      - deploy
      command: bozo
    
    zorg:
      shortCut: Shift-Z
      description: Pod logs
      scopes:
      - svc
      command: zorg
    

    Lastly you can define plugin snippets in their own file. The snippet will be named from the file name. In this case, we define a bozo plugin using a plugin snippet.

    # $XDG_DATA_HOME/k9s/plugins/schtuff/bozo.yaml
    shortCut: Shift-B
    description: Bozo
    scopes:
    - deploy
    command: bozo
    

    NOTE: This is an experimental feature! Options and layout may change in future K9s releases as this feature solidifies.


    Benchmark Your Applications

    K9s integrates Hey from the brilliant and super talented Jaana Dogan. Hey is a CLI tool to benchmark HTTP endpoints similar to AB bench. This preliminary feature currently supports benchmarking port-forwards and services (Read the paint on this is way fresh!).

    To setup a port-forward, you will need to navigate to the PodView, select a pod and a container that exposes a given port. Using SHIFT-F a dialog comes up to allow you to specify a local port to forward. Once acknowledged, you can navigate to the PortForward view (alias pf) listing out your active port-forwards. Selecting a port-forward and using CTRL-B will run a benchmark on that HTTP endpoint. To view the results of your benchmark runs, go to the Benchmarks view (alias be). You should now be able to select a benchmark and view the run stats details by pressing <ENTER>. NOTE: Port-forwards only last for the duration of the K9s session and will be terminated upon exit.

    Initially, the benchmarks will run with the following defaults:

    • Concurrency Level: 1
    • Number of Requests: 200
    • HTTP Verb: GET
    • Path: /

    The PortForward view is backed by a new K9s config file namely: $XDG_DATA_HOME/k9s/clusters/clusterX/contextY/benchmarks.yaml. Each cluster you connect to will have its own bench config file, containing the name of the K8s context for the cluster. Changes to this file should automatically update the PortForward view to indicate how you want to run your benchmarks.

    Benchmarks result reports are stored in $XDG_STATE_HOME/k9s/clusters/clusterX/contextY

    Here is a sample benchmarks.yaml configuration. Please keep in mind this file will likely change in subsequent releases!

    # This file resides in  $XDG_DATA_HOME/k9s/clusters/clusterX/contextY/benchmarks.yaml
    benchmarks:
      # Indicates the default concurrency and number of requests setting if a container or service rule does not match.
      defaults:
        # One concurrent connection
        concurrency: 1
        # Number of requests that will be sent to an endpoint
        requests: 500
      containers:
        # Containers section allows you to configure your http container's endpoints and benchmarking settings.
        # NOTE: the container ID syntax uses namespace/pod-name:container-name
        default/nginx:nginx:
          # Benchmark a container named nginx using POST HTTP verb using http://localhost:port/bozo URL and headers.
          concurrency: 1
          requests: 10000
          http:
            path: /bozo
            method: POST
            body:
              {"fred":"blee"}
            header:
              Accept:
                - text/html
              Content-Type:
                - application/json
      services:
        # Similarly you can Benchmark an HTTP service exposed either via NodePort, LoadBalancer types.
        # Service ID is ns/svc-name
        default/nginx:
          # Set the concurrency level
          concurrency: 5
          # Number of requests to be sent
          requests: 500
          http:
            method: GET
            # This setting will depend on whether service is NodePort or LoadBalancer. NodePort may require vendor port tunneling setting.
            # Set this to a node if NodePort or LB if applicable. IP or dns name.
            host: A.B.C.D
            path: /bumblebeetuna
          auth:
            user: jean-baptiste-emmanuel
            password: Zorg!
    

    K9s RBAC FU

    On RBAC enabled clusters, you would need to give your users/groups capabilities so that they can use K9s to explore their Kubernetes cluster. K9s needs minimally read privileges at both the cluster and namespace level to display resources and metrics.

    These rules below are just suggestions. You will need to customize them based on your environment policies. If you need to edit/delete resources extra Fu will be necessary.

    NOTE! Cluster/Namespace access may change in the future as K9s evolves. NOTE! We expect K9s to keep running even in atrophied clusters/namespaces. Please file issues if this is not the case!

    Cluster RBAC scope

    ---
    # K9s Reader ClusterRole
    kind: ClusterRole
    apiVersion: rbac.authorization.k8s.io/v1
    metadata:
      name: k9s
    rules:
      # Grants RO access to cluster resources node and namespace
      - apiGroups: [""]
        resources: ["nodes", "namespaces"]
        verbs: ["get", "list", "watch"]
      # Grants RO access to RBAC resources
      - apiGroups: ["rbac.authorization.k8s.io"]
        resources: ["clusterroles", "roles", "clusterrolebindings", "rolebindings"]
        verbs: ["get", "list", "watch"]
      # Grants RO access to CRD resources
      - apiGroups: ["apiextensions.k8s.io"]
        resources: ["customresourcedefinitions"]
        verbs: ["get", "list", "watch"]
      # Grants RO access to metric server (if present)
      - apiGroups: ["metrics.k8s.io"]
        resources: ["nodes", "pods"]
        verbs: ["get", "list", "watch"]
    
    ---
    # Sample K9s user ClusterRoleBinding
    apiVersion: rbac.authorization.k8s.io/v1
    kind: ClusterRoleBinding
    metadata:
      name: k9s
    subjects:
      - kind: User
        name: fernand
        apiGroup: rbac.authorization.k8s.io
    roleRef:
      kind: ClusterRole
      name: k9s
      apiGroup: rbac.authorization.k8s.io
    

    Namespace RBAC scope

    If your users are constrained to certain namespaces, K9s will need to following role to enable read access to namespaced resources.

    ---
    # K9s Reader Role (default namespace)
    kind: Role
    apiVersion: rbac.authorization.k8s.io/v1
    metadata:
      name: k9s
      namespace: default
    rules:
      # Grants RO access to most namespaced resources
      - apiGroups: ["", "apps", "autoscaling", "batch", "extensions"]
        resources: ["*"]
        verbs: ["get", "list", "watch"]
      # Grants RO access to metric server
      - apiGroups: ["metrics.k8s.io"]
        resources: ["pods", "nodes"]
        verbs:
          - get
          - list
          - watch
    
    ---
    # Sample K9s user RoleBinding
    apiVersion: rbac.authorization.k8s.io/v1
    kind: RoleBinding
    metadata:
      name: k9s
      namespace: default
    subjects:
      - kind: User
        name: fernand
        apiGroup: rbac.authorization.k8s.io
    roleRef:
      kind: Role
      name: k9s
      apiGroup: rbac.authorization.k8s.io
    

    Skins

    Example: Dracula Skin ;)

    You can style K9s based on your own sense of look and style. Skins are YAML files, that enable a user to change the K9s presentation layer. See this repo skins directory for examples. You can skin k9s by default by specifying a UI.skin attribute. You can also change K9s skins based on the context you are connecting too. In this case, you can specify a skin field on your cluster config aka skin: dracula (just the name of the skin file without the extension!) and copy t