使用 Kubernetes API 访问集群

本页面介绍如何使用 Kubernetes API 访问集群。

准备工作

您需要有一个 Kubernetes 集群,并且 kubectl 命令行工具必须配置为与您的集群通信。建议在至少有两个节点不充当控制平面主机的集群上运行本教程。如果您还没有集群,则可以使用 minikube 创建一个,或者可以使用以下 Kubernetes 游乐场之一

要检查版本,请输入 kubectl version

访问 Kubernetes API

首次使用 kubectl 访问

首次访问 Kubernetes API 时,请使用 Kubernetes 命令行工具 kubectl

要访问集群,您需要知道集群的位置并拥有访问它的凭据。通常,当您完成 入门指南 时,或者其他人设置了集群并为您提供了凭据和位置时,会自动设置此项。

使用以下命令检查 kubectl 知道的位置和凭据

kubectl config view

许多 示例 都提供了使用 kubectl 的介绍。完整的文档可在 kubectl 手册 中找到。

直接访问 REST API

kubectl 处理定位 API 服务器和向其进行身份验证。如果您想使用 curlwget 等 http 客户端或浏览器直接访问 REST API,则可以通过多种方式定位 API 服务器并对其进行身份验证

  1. 在代理模式下运行 kubectl(推荐)。建议使用此方法,因为它使用存储的 API 服务器位置并使用自签名证书验证 API 服务器的身份。使用此方法不可能进行中间人 (MITM) 攻击。
  2. 或者,您可以直接向 http 客户端提供位置和凭据。这适用于对代理感到困惑的客户端代码。为了防止中间人攻击,您需要将根证书导入浏览器。

使用 Go 或 Python 客户端库可以在代理模式下访问 kubectl。

使用 kubectl proxy

以下命令以充当反向代理的模式运行 kubectl。它处理定位 API 服务器和进行身份验证。

像这样运行它

kubectl proxy --port=8080 &

有关更多详细信息,请参阅 kubectl proxy

然后,您可以使用 curl、wget 或浏览器浏览 API,如下所示

curl http://localhost:8080/api/

输出类似于以下内容

{
  "versions": [
    "v1"
  ],
  "serverAddressByClientCIDRs": [
    {
      "clientCIDR": "0.0.0.0/0",
      "serverAddress": "10.0.1.149:443"
    }
  ]
}

不使用 kubectl proxy

可以通过将身份验证令牌直接传递给 API 服务器来避免使用 kubectl proxy,如下所示

使用 grep/cut 方法

# Check all possible clusters, as your .KUBECONFIG may have multiple contexts:
kubectl config view -o jsonpath='{"Cluster name\tServer\n"}{range .clusters[*]}{.name}{"\t"}{.cluster.server}{"\n"}{end}'

# Select name of cluster you want to interact with from above output:
export CLUSTER_NAME="some_server_name"

# Point to the API server referring the cluster name
APISERVER=$(kubectl config view -o jsonpath="{.clusters[?(@.name==\"$CLUSTER_NAME\")].cluster.server}")

# Create a secret to hold a token for the default service account
kubectl apply -f - <<EOF
apiVersion: v1
kind: Secret
metadata:
  name: default-token
  annotations:
    kubernetes.io/service-account.name: default
type: kubernetes.io/service-account-token
EOF

# Wait for the token controller to populate the secret with a token:
while ! kubectl describe secret default-token | grep -E '^token' >/dev/null; do
  echo "waiting for token..." >&2
  sleep 1
done

# Get the token value
TOKEN=$(kubectl get secret default-token -o jsonpath='{.data.token}' | base64 --decode)

# Explore the API with TOKEN
curl -X GET $APISERVER/api --header "Authorization: Bearer $TOKEN" --insecure

输出类似于以下内容

{
  "kind": "APIVersions",
  "versions": [
    "v1"
  ],
  "serverAddressByClientCIDRs": [
    {
      "clientCIDR": "0.0.0.0/0",
      "serverAddress": "10.0.1.149:443"
    }
  ]
}

上面的示例使用了 --insecure 标志。这使其容易受到 MITM 攻击。当 kubectl 访问集群时,它使用存储的根证书和客户端证书来访问服务器。(这些安装在 ~/.kube 目录中)。由于集群证书通常是自签名的,因此可能需要特殊配置才能使您的 http 客户端使用根证书。

在某些集群上,API 服务器不需要身份验证;它可以在 localhost 上提供服务,或者受到防火墙的保护。对此没有标准。 控制对 Kubernetes API 的访问 描述了如何以集群管理员身份配置此项。

以编程方式访问 API

Kubernetes 正式支持 GoPythonJavadotnetJavaScriptHaskell 的客户端库。还有其他客户端库由其作者提供和维护,而不是 Kubernetes 团队。有关从其他语言访问 API 及其身份验证方式,请参阅 客户端库

Go 客户端

  • 要获取库,请运行以下命令:go get k8s.io/client-go@kubernetes-<kubernetes-version-number> 请参阅 https://github.com/kubernetes/client-go/releases 以查看支持哪些版本。
  • 在 client-go 客户端之上编写应用程序。

Go 客户端可以使用与 kubectl CLI 相同的 kubeconfig 文件 来定位 API 服务器并对其进行身份验证。请参阅此 示例

package main

import (
  "context"
  "fmt"
  "k8s.io/apimachinery/pkg/apis/meta/v1"
  "k8s.io/client-go/kubernetes"
  "k8s.io/client-go/tools/clientcmd"
)

func main() {
  // uses the current context in kubeconfig
  // path-to-kubeconfig -- for example, /root/.kube/config
  config, _ := clientcmd.BuildConfigFromFlags("", "<path-to-kubeconfig>")
  // creates the clientset
  clientset, _ := kubernetes.NewForConfig(config)
  // access the API to list pods
  pods, _ := clientset.CoreV1().Pods("").List(context.TODO(), v1.ListOptions{})
  fmt.Printf("There are %d pods in the cluster\n", len(pods.Items))
}

如果应用程序作为 Pod 部署在集群中,请参阅 从 Pod 中访问 API

Python 客户端

要使用 Python 客户端,请运行以下命令:pip install kubernetes。有关更多安装选项,请参阅 Python 客户端库页面

Python 客户端可以使用与 kubectl CLI 相同的 kubeconfig 文件 来定位 API 服务器并对其进行身份验证。请参阅此 示例

from kubernetes import client, config

config.load_kube_config()

v1=client.CoreV1Api()
print("Listing pods with their IPs:")
ret = v1.list_pod_for_all_namespaces(watch=False)
for i in ret.items:
    print("%s\t%s\t%s" % (i.status.pod_ip, i.metadata.namespace, i.metadata.name))

Java 客户端

要安装 Java 客户端,请运行

# Clone java library
git clone --recursive https://github.com/kubernetes-client/java

# Installing project artifacts, POM etc:
cd java
mvn install

请参阅 https://github.com/kubernetes-client/java/releases 以查看支持哪些版本。

Java 客户端可以使用与 kubectl CLI 相同的 kubeconfig 文件 来定位 API 服务器并对其进行身份验证。请参阅此 示例

package io.kubernetes.client.examples;

import io.kubernetes.client.ApiClient;
import io.kubernetes.client.ApiException;
import io.kubernetes.client.Configuration;
import io.kubernetes.client.apis.CoreV1Api;
import io.kubernetes.client.models.V1Pod;
import io.kubernetes.client.models.V1PodList;
import io.kubernetes.client.util.ClientBuilder;
import io.kubernetes.client.util.KubeConfig;
import java.io.FileReader;
import java.io.IOException;

/**
 * A simple example of how to use the Java API from an application outside a kubernetes cluster
 *
 * <p>Easiest way to run this: mvn exec:java
 * -Dexec.mainClass="io.kubernetes.client.examples.KubeConfigFileClientExample"
 *
 */
public class KubeConfigFileClientExample {
  public static void main(String[] args) throws IOException, ApiException {

    // file path to your KubeConfig
    String kubeConfigPath = "~/.kube/config";

    // loading the out-of-cluster config, a kubeconfig from file-system
    ApiClient client =
        ClientBuilder.kubeconfig(KubeConfig.loadKubeConfig(new FileReader(kubeConfigPath))).build();

    // set the global default api-client to the in-cluster one from above
    Configuration.setDefaultApiClient(client);

    // the CoreV1Api loads default api-client from global configuration.
    CoreV1Api api = new CoreV1Api();

    // invokes the CoreV1Api client
    V1PodList list = api.listPodForAllNamespaces(null, null, null, null, null, null, null, null, null);
    System.out.println("Listing all pods: ");
    for (V1Pod item : list.getItems()) {
      System.out.println(item.getMetadata().getName());
    }
  }
}

dotnet 客户端

要使用 dotnet 客户端,请运行以下命令:dotnet add package KubernetesClient --version 1.6.1。有关更多安装选项,请参阅 dotnet 客户端库页面。请参阅 https://github.com/kubernetes-client/csharp/releases 以查看支持哪些版本。

dotnet 客户端可以使用与 kubectl CLI 相同的 kubeconfig 文件 来定位 API 服务器并对其进行身份验证。请参阅此 示例

using System;
using k8s;

namespace simple
{
    internal class PodList
    {
        private static void Main(string[] args)
        {
            var config = KubernetesClientConfiguration.BuildDefaultConfig();
            IKubernetes client = new Kubernetes(config);
            Console.WriteLine("Starting Request!");

            var list = client.ListNamespacedPod("default");
            foreach (var item in list.Items)
            {
                Console.WriteLine(item.Metadata.Name);
            }
            if (list.Items.Count == 0)
            {
                Console.WriteLine("Empty!");
            }
        }
    }
}

JavaScript 客户端

要安装 JavaScript 客户端,请运行以下命令:npm install @kubernetes/client-node。请参阅 https://github.com/kubernetes-client/javascript/releases 以查看支持哪些版本。

JavaScript 客户端可以使用与 kubectl CLI 相同的 kubeconfig 文件 来定位 API 服务器并对其进行身份验证。请参阅此 示例

const k8s = require('@kubernetes/client-node');

const kc = new k8s.KubeConfig();
kc.loadFromDefault();

const k8sApi = kc.makeApiClient(k8s.CoreV1Api);

k8sApi.listNamespacedPod('default').then((res) => {
    console.log(res.body);
});

Haskell 客户端

请参阅 https://github.com/kubernetes-client/haskell/releases 以查看支持哪些版本。

Haskell 客户端 可以使用与 kubectl CLI 相同的 kubeconfig 文件 来定位 API 服务器并对其进行身份验证。请参阅此 示例

exampleWithKubeConfig :: IO ()
exampleWithKubeConfig = do
    oidcCache <- atomically $ newTVar $ Map.fromList []
    (mgr, kcfg) <- mkKubeClientConfig oidcCache $ KubeConfigFile "/path/to/kubeconfig"
    dispatchMime
            mgr
            kcfg
            (CoreV1.listPodForAllNamespaces (Accept MimeJSON))
        >>= print

后续步骤

上次修改时间:2023 年 12 月 6 日下午 5:05 PST:清理 change-default-storage-class.md (d1d6eda640)