【问题标题】:Use client-go to simulate 'kubectl wait' for a pod to be ready使用 client-go 模拟 'kubectl wait' 等待 pod 准备就绪
【发布时间】:2020-12-06 03:41:45
【问题描述】:

在 bash 脚本中,我通常使用 'kubectl wait' 来阻止,直到某个 pod 资源准备好,例如类似的东西:

kubectl wait --for=condition=Ready --timeout=2m -n mynamespace pod -l myselector

这很有效,因为我经常不知道我需要等待的 pod 的确切名称,而“kubectl wait”允许我根据选择器定位 pod,然后阻塞直到它准备好。

现在我需要在 golang 代码中做一些类似的事情。我已经看到使用 client-go 库通过名称来验证和“获取”特定 pod 的示例。但是我有几个关于如何最好地使这个例子适应我的需要的问题......

  1. 我不知道能够“Get()”它的 pod 的确切/全名,这就是为什么“kubectl wait”是完美的,因为它允许我使用选择器找到 pod。我假设我应该使用 client-go 库来代替调用 CoreV1().Pods().List() 而不是 Get(),以便让我使用选择器找到我想要的 pod?

  2. 此外,pod 可能不会立即存在,并且可能仅在 1 分钟左右后创建,“kubectl wait”为我处理。在代码中,我是否需要循环/睡眠并继续执行 List() 直到 pod 存在?

  3. 与 #2 类似的问题...一旦 List() 返回一个 pod 名称,在 golang 中“等待”该 pod 处于“就绪”状态的最佳方式是什么?如果可以避免的话,我不想对睡眠进行任何丑陋的民意调查......那么使用 golang 'wait' 包或类似包有更好的选择吗?你有什么推荐的?

【问题讨论】:

    标签: go kubernetes client-go


    【解决方案1】:

    完全按照kubectl 的方式进行操作怎么样?基本上,使用List(...) 根据字段选择器列出,然后使用Watch(...)

    片段:

    ...
            // List with a name field selector to get the current resourceVersion to watch from (not the object's resourceVersion)
            gottenObjList, err := o.DynamicClient.Resource(info.Mapping.Resource).Namespace(info.Namespace).List(context.TODO(), metav1.ListOptions{FieldSelector: nameSelector})
            if apierrors.IsNotFound(err) {
                return info.Object, true, nil
            }
            if err != nil {
                // TODO this could do something slightly fancier if we wish
                return info.Object, false, err
            }
            if len(gottenObjList.Items) != 1 {
                return info.Object, true, nil
            }
            gottenObj := &gottenObjList.Items[0]
            resourceLocation := ResourceLocation{
                GroupResource: info.Mapping.Resource.GroupResource(),
                Namespace:     gottenObj.GetNamespace(),
                Name:          gottenObj.GetName(),
            }
            if uid, ok := o.UIDMap[resourceLocation]; ok {
                if gottenObj.GetUID() != uid {
                    return gottenObj, true, nil
                }
            }
    
            watchOptions := metav1.ListOptions{}
            watchOptions.FieldSelector = nameSelector
            watchOptions.ResourceVersion = gottenObjList.GetResourceVersion()
            objWatch, err := o.DynamicClient.Resource(info.Mapping.Resource).Namespace(info.Namespace).Watch(context.TODO(), watchOptions)
            if err != nil {
                return gottenObj, false, err
            }
    ...
    

    ✌️

    【讨论】:

      猜你喜欢
      • 2020-06-27
      • 1970-01-01
      • 2019-10-09
      • 1970-01-01
      • 1970-01-01
      • 2014-03-29
      • 2019-08-13
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多