关于kubernetes:验证Kubernetes-YAML的最佳实践和策略

53次阅读

共计 17129 个字符,预计需要花费 43 分钟才能阅读完成。

本文来自 Rancher Labs

Kubernetes 工作负载最常见的定义是 YAML 格局的文件。应用 YAML 所面临的挑战之一是,它相当难以表白 manifest 文件之间的束缚或关系。

如果你想查看所有部署到集群中的镜像是否从受信赖的镜像仓库中提取应该怎么做?如何避免没有 PodDisruptionBudgets 的部署被提交到集群?

集成动态查看能够在靠近开发生命周期的时候发现错误和策略违规。而且因为围绕资源定义的有效性和安全性的保障失去了改善,你能够置信生产工作负载是遵循最佳实际的。

Kubernetes YAML 文件动态查看的生态系统能够分为以下几类:

API 验证器:这一类工具能够针对 Kubernetes API 服务器验证给定的 YAML manifest。

内置查看器:这一类工具捆绑了平安、最佳实际等方面的意见查看。

自定义验证器:这一类工具容许用几种语言编写自定义查看,如 Rego 和 Javascript。

在本文中,你将学习并比拟六种不同的工具:

  • Kubeval
  • Kube-score
  • Config-lint
  • Copper
  • Conftest
  • Polaris

让咱们开始吧!

验证 Deployment

在开始比拟工具之前,你应该设置一个基准。以下 manifest 并没有遵循最佳实际,可能存在一些问题,你能发现几个问题呢?

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  selector:
    matchLabels:
      app: http-echo
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
        image: hashicorp/http-echo
        args: ["-text", "hello-world"]
        ports:
        - containerPort: 5678
---
apiVersion: v1
kind: Service
metadata:
  name: http-echo
spec:
  ports:
  - port: 5678
    protocol: TCP
    targetPort: 5678
  selector:
    app: http-echo

咱们将会应用这个 YAML 文件来比照不同的工具。

你能够在这个 git 仓库中找到下面的 YAML 清单、文件 base-valid.yaml 以及文章中提到的其余 manifest:

https://github.com/amitsaha/k…

manifest 形容了一个总是在 5678 端口回复“Hello World”音讯的 web 应用程序。

你能够通过以下形式部署该应用程序:

kubectl apply -f hello-world.yaml

你能够应用以下命令测试它:

kubectl port-forward svc/http-echo 8080:5678

你能够拜访 http://localhost:8080 并确认该应用程序是否依照预期运行。然而它是否遵循了最佳实际呢?

让咱们往下看。

Kubeval

主页:https://www.kubeval.com/

Kubeval 的前提是,与 Kubernetes 的任何交互都要通过它的 REST API。因而,你能够应用 API 模式来验证一个给定的 YAML 输出是否合乎该模式。咱们来看看一个例子。

你能够依照我的项目网站上的阐明来装置 kubeval,撰写此文时最新版本 是 0.15.0。装置实现之后,让咱们用前文探讨的 manifest 来运行它:

kubeval base-valid.yaml
PASS - base-valid.yaml contains a valid Deployment (http-echo)
PASS - base-valid.yaml contains a valid Service (http-echo)

当胜利之后,kubeval 退出时代码为 0。你能够应用以下代码验证退出代码:

echo $?
0

当初,让咱们应用另一个 manifest 来测试 kubeval:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
        image: hashicorp/http-echo
        args: ["-text", "hello-world"]
        ports:
        - containerPort: 5678
---
apiVersion: v1
kind: Service
metadata:
  name: http-echo
spec:
  ports:
  - port: 5678
    protocol: TCP
    targetPort: 5678
  selector:
    app: http-echo

你能发现问题吗?

让咱们运行 kubeval:

kubeval kubeval-invalid.yaml
WARN - kubeval-invalid.yaml contains an invalid Deployment (http-echo) - selector: selector is required
PASS - kubeval-invalid.yaml contains a valid Service (http-echo)

# let's check the return value
echo $?
1

资源并没有通过验证。应用app/v1 API 版本的 Deployment 必须蕴含一个匹配 Pod 标签的 selector。下面的 manifest 没有蕴含 selector,针对 manifest 运行 kubeval 报告了一个谬误和一个非零的退出代码。

你可能想晓得,当你用下面的 manifest 运行 kubectl apply -f 时会产生什么?

让咱们试一试:

kubectl apply -f kubeval-invalid.yaml
error: error validating "kubeval-invalid.yaml": error validating data: ValidationError(Deployment.spec):
missing required field "selector" in io.k8s.api.apps.v1.DeploymentSpec; if you choose to ignore these errors,
turn validation off with --validate=false

这正是 kubeval 正告你的谬误。你能够通过增加像这样的 selector 来修复资源。

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  selector:
    matchLabels:
      app: http-echo
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
        image: hashicorp/http-echo
        args: ["-text", "hello-world"]
        ports:
        - containerPort: 5678
---
apiVersion: v1
kind: Service
metadata:
  name: http-echo
spec:
  ports:
  - port: 5678
    protocol: TCP
    targetPort: 5678
  selector:
    app: http-echo

像 kubeval 这样的工具的益处是,你能够在部署周期的晚期发现这样的谬误。此外,你不须要拜访集群来运行查看——它们能够离线运行。默认状况下,kubeval 会依据最新的未公布的 Kubernetes API 模式验证资源。然而,在大多数状况下,你可能心愿依据特定的 Kubernetes 版本运行验证。你能够应用标记 --kubernetes-version 来测试特定的 API 版本:

kubeval --kubernetes-version 1.16.1 base-valid.yaml

请留神,版本应该是 Major.Minor.Patch. 的模式。要查看可用于验证的版本,请查看 GitHub 上的 JSON schema,kubeval 应用它来执行验证。

如果你须要离线运行 kubeval,你能够下载 schemas,而后应用 --schema-location 标记来应用本地目录。除了单个 YAML 文件,你还能够针对目录以及规范输出运行 kubeval。你还应该晓得,Kubeval 易于与你的继续集成流水线集成。如果你想在提交你的 manifest 到集群之前蕴含查看,那么 kubeval 反对三种输入格局兴许可能对你有所帮忙。

  • 纯文本
  • JSON
  • 测试任何货色协定(TAP)

而且你能够应用其中一种格局来进一步解析输入,以创立一个自定义的后果摘要。然而,kubeval 存在一个局限性,就是它目前还不能对自定义资源定义(CRD)进行验证。不过 kubeval 能够疏忽它们。

只管 Kubeval 是检查和验证资源的绝佳抉择,但请留神,通过测试的资源并不能保障合乎最佳实际。举个例子,在容器镜像中应用最新的标签被认为不是最佳实际。然而,Kubeval 并不会将其作为错误报告,它会在没有正告的状况下验证 YAML。

如果你想对 YAML 进行打分,并抓住诸如应用最新的标签这样的违规行为怎么办?如何依据最佳实际查看你的 YAML 文件?

Kube-score

主页:https://github.com/zegl/kube-…

Kube-score 剖析 YAML 清单,并依据内置的查看进行评分。这些查看是依据平安倡议和最佳实际而抉择的,例如:

  • 以非 root 用户身份运行容器。
  • 为 pods 指定健康检查。
  • 定义资源申请和限度。
  • 查看的后果能够是 OK、WARNING 或 CRITICAL。

你能够在线试用 kube-score,也能够在本地装置。在写这篇文章时,最新的版本是 1.7.0 让咱们试着用之前的 manifest base-valid.yaml 来运行它:

apps/v1/Deployment http-echo
[CRITICAL] Container Image Tag
  · http-echo -> Image with latest tag
      Using a fixed tag is recommended to avoid accidental upgrades
[CRITICAL] Pod NetworkPolicy
  · The pod does not have a matching network policy
      Create a NetworkPolicy that targets this pod
[CRITICAL] Pod Probes
  · Container is missing a readinessProbe
      A readinessProbe should be used to indicate when the service is ready to receive traffic.
      Without it, the Pod is risking to receive traffic before it has booted. It is also used during
      rollouts, and can prevent downtime if a new version of the application is failing.
      More information: https://github.com/zegl/kube-score/blob/master/README_PROBES.md
[CRITICAL] Container Security Context
  · http-echo -> Container has no configured security context
      Set securityContext to run the container in a more secure context.
[CRITICAL] Container Resources
  · http-echo -> CPU limit is not set
      Resource limits are recommended to avoid resource DDOS. Set resources.limits.cpu
  · http-echo -> Memory limit is not set
      Resource limits are recommended to avoid resource DDOS. Set resources.limits.memory
  · http-echo -> CPU request is not set
      Resource requests are recommended to make sure that the application can start and run without
      crashing. Set resources.requests.cpu
  · http-echo -> Memory request is not set
      Resource requests are recommended to make sure that the application can start and run without crashing.
      Set resources.requests.memory
[CRITICAL] Deployment has PodDisruptionBudget
  · No matching PodDisruptionBudget was found
      It is recommended to define a PodDisruptionBudget to avoid unexpected downtime during Kubernetes
      maintenance operations, such as when draining a node.
[WARNING] Deployment has host PodAntiAffinity
  · Deployment does not have a host podAntiAffinity set
      It is recommended to set a podAntiAffinity that stops multiple pods from a deployment from
      being scheduled on the same node. This increases availability in case the node becomes unavailable.

YAML 文件通过了 kubeval 查看,但 kube-score 指出了几个不足之处。

  • 短少了 readiness probe
  • 短少内存和 CPU 申请和限度。
  • 短少 Poddisruptionbudgets
  • 短少反亲和规定以最大化可用性。
  • 容器以 root 身份运行。

这些都是你应该解决的无效点,以使你的部署更加强壮和牢靠。kube-score命令会输入一个可读性高的后果,蕴含所有的 WARNING 和 CRITICAL 违规行为,这在开发过程中是十分好的。如果你打算把它作为继续集成流水线的一部分,你能够用 --output-format ci 这个标记来应用更简洁的输入,它还能够打印级别为 OK 的查看:

kube-score score base-valid.yaml --output-format ci
[OK] http-echo apps/v1/Deployment
[OK] http-echo apps/v1/Deployment
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) CPU limit is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Memory limit is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) CPU request is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Memory request is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Image with latest tag
[OK] http-echo apps/v1/Deployment
[CRITICAL] http-echo apps/v1/Deployment: The pod does not have a matching network policy
[CRITICAL] http-echo apps/v1/Deployment: Container is missing a readinessProbe
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Container has no configured security context
[CRITICAL] http-echo apps/v1/Deployment: No matching PodDisruptionBudget was found
[WARNING] http-echo apps/v1/Deployment: Deployment does not have a host podAntiAffinity set
[OK] http-echo v1/Service
[OK] http-echo v1/Service
[OK] http-echo v1/Service
[OK] http-echo v1/Service

与 kubeval 相似,当有一个 CRITICAL 查看失败时,kube-score会返回一个非零的退出代码,但你配置它在 WARNINGs 时也会失败。还有一个内置的查看来验证不同 API 版本的资源,相似于 kubeval。然而,这些信息是硬编码在 kube-score 自身,你不能抉择不同的 Kubernetes 版本。因而,如果你降级你的集群或你有几个不同的集群运行不同的版本,这可能会限度你应用这一工具。

请留神,有一个 open issue 能够实现这个性能。你能够在官方网站上理解更多对于 kube-score 的信息:https://github.com/zegl/kube-…

Kube-score 查看是执行最佳实际的优良工具,但如果你想自定义,或者增加本人的规定呢?临时不能够,Kube-score 的设计不是可扩大的,你不能增加或调整政策。如果你想写自定义查看来恪守你的组织政策,你能够应用接下来的四个选项之——config-lint、copper、conftest 或 polaris。

Config-lint

Config-lint 是一个旨在验证以 YAML、JSON、Terraform、CSV 和 Kubernetes manifest 编写的配置文件的工具。你能够应用我的项目网站上的阐明装置它:

https://stelligent.github.io/…

在撰写本文时,最新的版本是 1.5.0。

Config-lint 没有内置对 Kubernetes manifest 的查看。你必须编写本人的规定来执行验证。这些规定被写成 YAML 文件,称为规定集,具备以下构造:

version: 1
description: Rules for Kubernetes spec files
type: Kubernetes
files:
  - "*.yaml"
rules:
   # list of rules

让咱们来具体看看。type字段示意你将用 config-lint 查看什么类型的配置——个别是 Kubernetes manifest。

files 字段除了承受单个文件外,还承受一个目录作为输出。

rules 字段是你能够定义自定义查看的中央。比方说,你心愿查看 Deployment 中的镜像是否总是从受信赖的镜像仓库(如my-company.com/myapp:1.0)中提取。实现这种查看的 config-lint 规定能够是这样的:

- id: MY_DEPLOYMENT_IMAGE_TAG
  severity: FAILURE
  message: Deployment must use a valid image tag
  resource: Deployment
  assertions:
    - every:
        key: spec.template.spec.containers
        expressions:
          - key: image
            op: starts-with
            value: "my-company.com/"

每条规定必须具备以下属性。

  • id——这是对规定的惟一标识。
  • severity——它必须是 FAILURE、WARNING 和 NON_COMPLIANT 中的一个。
  • message——如果违反了一个规定,这个字符串的内容会被显示进去。
  • resource——你心愿这个规定被利用到的资源品种。
  • assertions——将对指定资源进行评估的条件列表。

在下面的规定中,every assertion 查看每个容器中的 Deployment(key:spec.templates.spec.contains)是否应用受信赖的镜像(即以 "my-company.com/" 结尾的镜像)。

残缺的规定集看起来如下:

version: 1
description: Rules for Kubernetes spec files
type: Kubernetes
files:
  - "*.yaml"
rules:
  - id: DEPLOYMENT_IMAGE_REPOSITORY
    severity: FAILURE
    message: Deployment must use a valid image repository
    resource: Deployment
    assertions:
      - every:
          key: spec.template.spec.containers
          expressions:
            - key: image
              op: starts-with
              value: "my-company.com/"

如果你想要测试查看,你能够将规定集保留为check_image_repo.yaml

当初,让咱们对 base-valid.yaml 文件进行验证。


config-lint -rules check_image_repo.yaml base-valid.yaml
[
  {
  "AssertionMessage": "Every expression fails: And expression fails: image does not start with my-company.com/",
  "Category": "","CreatedAt":"2020-06-04T01:29:25Z","Filename":"test-data/base-valid.yaml","LineNumber": 0,"ResourceID":"http-echo","ResourceType":"Deployment","RuleID":"DEPLOYMENT_IMAGE_REPOSITORY","RuleMessage":"Deployment must use a valid image repository","Status":"FAILURE"
  }
]

它失败了。当初,让咱们思考以下 manifest 和无效的镜像仓库:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  selector:
    matchLabels:
      app: http-echo
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
        image: my-company.com/http-echo:1.0
        args: ["-text", "hello-world"]
        ports:
        - containerPort: 5678

应用以上 manifest 运行雷同的查看并且将不会报告违规:

config-lint -rules check_image_repo.yaml image-valid-mycompany.yaml
[]

Config-lint 是一个很有前途的框架,它能够让你应用 YAML DSL 为 Kubernetes YAML manifest 编写自定义查看。但如果你想表白更简单的逻辑和查看呢?是不是 YAML 的限制性太大?如果你能用真正的编程语言来表白这些查看呢?

Copper

主页:https://github.com/cloud66-os…

Copper V2 是一个应用自定义查看来验证清单的框架——就像 config-lint 一样。然而,Copper 并没有应用 YAML 来定义查看。取而代之的是,测试是用 JavaScript 编写的,Copper 提供了一个库,外面有一些根本的帮忙程序来帮助读取 Kubernetes 对象和报告谬误。

你能够依照官网文档来装置 Copper。在写这篇文章的时候,最新的版本是 2.0.1:

https://github.com/cloud66-os…

与 config-lint 相似,Copper 没有内置查看。让咱们写一个查看,以确保部署只能从受信赖的仓库(如my-company.com)拉取容器镜像。创立一个新文件check_image_repo.js,内容如下:

$$.forEach(function($){if ($.kind === 'Deployment') {$.spec.template.spec.containers.forEach(function(container) {var image = new DockerImage(container.image);
            if (image.registry.lastIndexOf('my-company.com/') != 0) {errors.add_error('no_company_repo',"Image" + $.metadata.name + "is not from my-company.com repo", 1)
            }
        });
    }
});

当初,要依据咱们的 base-valid.yaml manifest 运行这项查看,能够应用 copper validate 命令:

copper validate --in=base-valid.yaml --validator=check_image_tag.js
Check no_company_repo failed with severity 1 due to Image http-echo is not from my-company.com repo
Validation failed

正如你所想的,你能够编写更简单的查看,比方验证 Ingress manifest 的域名,或者回绝任何作为特权运行的 Pod。Copper 有一些内置的助手:

DockerImage 函数读取指定的输出文件并创立一个蕴含以下属性的对象:

  • name- 蕴含镜像名称
  • tag- 蕴含镜像 tag
  • registry- 镜像仓库
  • registry_url- 蕴含协定和镜像仓库
  • fqin代表整个齐全合格的镜像地位。
  • findByName函数能够帮忙从输出文件中找到给定 kind 和 name 的资源。
  • findByLabels函数能够帮忙查找资源提供的 kindlabels

你能够在这里看到所有可用的帮忙程序:

https://github.com/cloud66-os…

默认状况下,它将整个输出的 YAML 文件加载到 $$ 变量中,并使其在你的脚本中可用(如果你过来应用 jQuery,你可能会发现这个模式很相熟)。

除了不必学习自定义语言外,你还能够应用整个 JavaScript 语言来编写你的查看,如字符串插值、函数等。值得注意的是,目前的 copper 版本嵌入了 ES5 版本的 JavaScript 引擎,而不是 ES6。想要理解更多,能够拜访我的项目官网:

https://github.com/cloud66-os…

如果 Javascript 不是你的首选语言,或者你更喜爱用于查问和形容策略的语言,你应该看看 conftest。

Conftest

Conftest 是一个配置数据的测试框架,可用于检查和验证 Kubernetes manifest。测试应用专门构建的查询语言 Rego 编写。

你能够依照我的项目网站上的阐明装置 conftest,在撰写本文时,最新的版本是 0.18.2:

https://www.conftest.dev/inst…

与 config-lint 和 copper 相似,conftest 也没有任何内置的查看。所以咱们通过编写一个策略来试试。和后面的例子一样,你将查看容器是否来自一个可信的起源。

创立一个新的目录,conftest-checks和一个名为 check_image_registry.rego 的文件,内容如下:

package main

deny[msg] {

  input.kind == "Deployment"
  image := input.spec.template.spec.containers[_].image
  not startswith(image, "my-company.com/")
  msg := sprintf("image'%v'doesn't come from my-company.com repository", [image])
}

当初让咱们运行 conftest 来验证manifest base-valid.yaml

conftest test --policy ./conftest-checks base-valid.yaml
FAIL - base-valid.yaml - image 'hashicorp/http-echo' doesn't come from my-company.com repository
1 tests, 1 passed, 0 warnings, 1 failure

当然,它是失败的,因为镜像不受信赖。下面的 Rego 文件指定了一个 deny 块,当为 true 时就会评估为违规。当你有多个 deny 块时,conftest 会独立查看它们,总体后果是任何一个块的违规都会导致整体违规。

除了默认的输入格局外,conftest 还反对 JSON、TAP 和通过 --output 标记的表格格局,如果你心愿将报告与现有的继续集成流水线集成,那么这些格局将会很有帮忙。为了帮忙调试策略,conftest 有一个不便的 --trace 标记,它能够打印 conftest 如何解析指定策略文件的跟踪。

Conftest 策略能够作为 artefacts 在 OCI(Open Container Initiative)仓库中公布和共享。命令 push 和 pull 容许公布一个工件和从近程仓库中提取一个现有的 artefact。

让咱们看看应用 conftest push 将上述策略公布到本地 docker 仓库的演示。应用以下命令启动本地 docker 仓库:

docker run -it --rm -p 5000:5000 registry

从另一个终端,导航到下面创立的 conftest-checks 目录,并运行以下命令:

conftest push 127.0.0.1:5000/amitsaha/opa-bundle-example:latest

该命令应胜利实现,并显示以下信息:

2020/06/10 14:25:43 pushed bundle with digest: sha256:e9765f201364c1a8a182ca637bc88201db3417bacc091e7ef8211f6c2fd2609c

当初,创立一个长期目录,运行 conftest pull 命令,将上述 bundle 下载到长期目录中:

cd $(mktemp -d)
conftest pull 127.0.0.1:5000/amitsaha/opa-bundle-example:latest

你会看到,在蕴含之前 push 的策略文件的长期目录中,有一个新的子目录策略:

tree
.
└── policy
  └── check_image_registry.rego

你甚至能够间接从仓库中运行测试:

conftest test --update 127.0.0.1:5000/amitsaha/opa-bundle-example:latest base-valid.yaml
..
FAIL - base-valid.yaml - image 'hashicorp/http-echo' doesn't come from my-company.com repository
2 tests, 1 passed, 0 warnings, 1 failure

可怜的是,DockerHub 还不是反对的镜像仓库之一。然而,如果你正在应用 Azure 容器仓库(ACR)或运行你的容器仓库,可能会通过测试。

artefact 格局与凋谢策略代理 (OPA) 绑定应用的格局雷同,这使得应用 conftest 从现有的 OPA 绑定中运行测试成为可能。

你能够在官方网站上理解更多对于共享策略和 conftest 的其余性能:

https://www.conftest.dev/

Polaris

主页:https://github.com/FairwindsO…

本文将探讨的最初一个工具是 polaris。Polaris 既能够装置在集群外部,也能够作为命令行工具动态地剖析 Kubernetes manifest。当作为命令行工具运行时,它包含几个内置的查看,涵盖平安和最佳实际等畛域,相似于 kube-score。此外,你还能够用它来编写相似 config-lint、copper 和 conftest 的自定义查看。换句话说,polaris 联合了两个类别中最好的:内置和自定义查看器。

你能够依照我的项目网站上的阐明装置 polaris 命令行工具。在写这篇文章的时候,最新的版本是 1.0.3:

https://github.com/FairwindsO…

装置实现后,你能够应用以下命令针对base-valid.yaml manifest 运行 polaris:

polaris audit --audit-path base-valid.yam

上述命令将打印一个 JSON 格局的字符串,具体阐明运行的检查和每个测试的后果。输入后果的构造如下:

{
  "PolarisOutputVersion": "1.0",
  "AuditTime": "0001-01-01T00:00:00Z",
  "SourceType": "Path",
  "SourceName": "test-data/base-valid.yaml",
  "DisplayName": "test-data/base-valid.yaml",
  "ClusterInfo": {
    "Version": "unknown",
    "Nodes": 0,
    "Pods": 2,
    "Namespaces": 0,
    "Controllers": 2
  },
  "Results": [/* long list */]
}

你能够在下方链接中获取残缺的输入:

https://github.com/amitsaha/k…

与 kube-score 相似,polaris 也发现了一些 manifest 未达到倡议的最佳实际的状况,其中包含:

  • 短少健康检查的 pod。
  • 容器镜像没有指定标签。
  • 容器以 root 身份运行。
  • 没有设置 CPU 和内存申请和限度。
  • 每项查看都被划分为正告或危险的重大水平。

要理解无关以后内置查看的更多信息,请参阅文档:

https://github.com/FairwindsO…

如果你对具体的后果不感兴趣,传递标记 --format score 会打印一个范畴为 1 -100 的数字,polaris 将其称为分数(score):

polaris audit --audit-path test-data/base-valid.yaml --format score
68

分数越靠近 100,合乎度越高。如果你查看 polaris audit 命令的退出代码,你会发现它是 0。要使 polaris 审计退出时的代码是非 0,能够利用另外两个标记。

--set-exit-code-below-score标记承受范畴为 1 -100 的阈值分数,当分数低于阈值时,将以 4 的退出代码退出。当你的基线分数是 75 分,而你想在分数低于 75 分时收回警报时,这十分有用。

当任何危险查看失败时,--set-exit-code-on-danger标记将以 3 的退出代码退出。

当初让咱们看看如何为 polaris 定义一个自定义查看,以测试 Deployment 中的容器镜像是否来自可信赖的镜像仓库。自定义查看以 YAML 格局定义,测试自身应用 JSON Schema 形容。上面的 YAML 代码段定义了一个新的查看 checkImageRepo:

checkImageRepo:
  successMessage: Image registry is valid
  failureMessage: Image registry is not valid
  category: Images
  target: Container
  schema:
    '$schema': http://json-schema.org/draft-07/schema
    type: object
    properties:
      image:
        type: string
        pattern: ^my-company.com/.+$

让咱们认真看看:

  • successMessage是查看胜利时显示的字符串。
  • failureMessage是指当测试不胜利时显示的信息。
  • category指的是其中一个类别—镜像、健康检查、平安、网络和资源。
  • target是一个字符串,用于确定查看所针对的标准对象,应该是 Container、Pod 或 Controller 中的一个。
  • 测试自身是在 schema 对象中应用 JSON 模式定义的。这里的查看应用模式关键字来匹配镜像是否来自容许的仓库。

要运行下面定义的查看,你须要创立一个 Polaris 配置文件,如下所示:

checks:
  checkImageRepo: danger
customChecks:
  checkImageRepo:
    successMessage: Image registry is valid
    failureMessage: Image registry is not valid
    category: Images
    target: Container
    schema:
      '$schema': http://json-schema.org/draft-07/schema
      type: object
      properties:
        image:
          type: string
          pattern: ^my-company.com/.+$

让咱们来剖析一下这个文件。

  • check 字段指定了检查和它们的严重性。因为你想在镜像不受信赖时收回警报,所以 checkImageRepo 被调配了一个 danger 重大水平。
  • 而后在 customChecks 对象中定义 checkImageRepo 查看自身。

你能够将下面的文件保留为custom_check.yaml,而后用你想要验证的 YAML manifest 运行polaris audit

你能够用base-valid.yaml manifest 进行测试:

polaris audit --config custom_check.yaml --audit-path base-valid.yaml

你会发现,polaris audit只运行了下面定义的自定义查看,但没有胜利。如果你将容器镜像批改为my-company.com/http-echo:1.0,polaris 将报告胜利。Github 仓库中蕴含了批改后的 manifest,所以你能够依据image-valid-mycompany.yaml manifest 测试后面的命令。

然而如何同时运行内置和自定义查看呢?下面的配置文件应该更新所有内置的查看标识符,看起来应该如下:

checks:
  cpuRequestsMissing: warning
  cpuLimitsMissing: warning
  # Other inbuilt checks..
  # ..
  # custom checks
  checkImageRepo: danger
customChecks:
  checkImageRepo:
    successMessage: Image registry is valid
    failureMessage: Image registry is not valid
    category: Images
    target: Container
    schema:
      '$schema': http://json-schema.org/draft-07/schema
      type: object
      properties:
        image:
          type: string
          pattern: ^my-company.com/.+$

你能够在这里看到一个残缺的配置文件的例子:

https://github.com/amitsaha/k…

你能够用自定义和内置查看来测试base-valid.yaml manifest:

polaris audit --config config_with_custom_check.yaml --audit-path base-valid.yaml

Polaris 用你的自定义查看加强了内置查看,从而联合了两种形式的最佳状态。然而,如果不能应用更弱小的语言,如 Rego 或 JavaScript,可能会限度编写更简单的查看。

要理解更多对于 polaris 的信息,请查看我的项目网站:

https://github.com/FairwindsO…

总 结

尽管有很多工具能够验证、打分和精简 Kubernetes YAML 文件,但重要的是要有一个心理模型来理解你将如何设计和执行查看。举个例子,如果你想让 Kubernetes manifest 通过一个流水线,kubeval 能够是这样一个流水线的第一步,因为它验证对象定义是否合乎 Kubernetes API 模式。一旦这项查看胜利,兴许你能够持续进行更具体的测试,比方规范最佳实际和自定义策略。Kube-score 和 polaris 在这里是最优良的抉择。

如果你有简单的需要,并且想要自定义查看的细节,你应该思考 copper、config-lint 和 conftest。尽管 conftest 和 config-lint 都应用了更多的 YAML 来定义自定义验证规定,但 copper 给你提供了一个真正的编程语言,使其相当有吸引力。然而,你应该应用其中的一个,从头开始写所有的查看,还是应该应用 Polaris,只写额定的自定义查看?这要依据状况而定。

正文完
 0