mirror of
https://github.com/helm/charts.git
synced 2026-08-23 22:37:45 +00:00
[incubator/anchore-engine] Adds incubator chart for Anchore Engine (#3293)
* Adds incubator chart for Anchore Engine * Fixes linter issues on anchore-engine values.yaml * Fixes truth values for values.yaml * Fixes for truthy values in other yaml configs for anchore-engine chart * Fix ingress spec for anchore-engine chart for easier config with helm cli * Addresses typos and some cleanup as requested in PR review * Adds more startup and config info in NOTES.txt for anchore-engine * Cleanup and make labels consistent in anchore-engine deployments * Move anchore-engine chart from incubator/ to stable/
This commit is contained in:
@@ -0,0 +1,19 @@
|
||||
name: anchore-engine
|
||||
version: 0.1.0
|
||||
appVersion: 0.1.6
|
||||
description: Anchore container analysis and policy evaluation engine service
|
||||
keywords:
|
||||
- analysis
|
||||
- docker
|
||||
- anchore
|
||||
- "anchore-engine"
|
||||
- image
|
||||
- security
|
||||
home: https://anchore.io
|
||||
sources:
|
||||
- https://github.com/anchore/anchore-engine
|
||||
maintainers:
|
||||
- name: zhill
|
||||
email: zach@anchore.com
|
||||
engine: gotpl
|
||||
icon: https://anchore.com/wp-content/uploads/2016/08/anchore.png
|
||||
@@ -0,0 +1,83 @@
|
||||
Anchore Engine Helm Chart
|
||||
=========================
|
||||
|
||||
This chart deploys the Anchore Engine docker container image analysis system. Anchore Engine
|
||||
requires a PostgresSQL database (>=9.6) which may be handled by the chart or supplied externally,
|
||||
and executes in a 2-tier architecture with an api/control layer and a batch execution worker pool layer.
|
||||
|
||||
See [Anchore Engine](https://github.com/anchore/anchore-engine) for more project details.
|
||||
|
||||
|
||||
Chart Details
|
||||
-------------
|
||||
|
||||
The chart is split into three primary sections: GlobalConfig, CoreConfig, WorkerConfig. As the name implies,
|
||||
the GlobalConfig is for configuration values that all components require, while the Core and Worker sections are
|
||||
tier-specific and allow customization for each role.
|
||||
|
||||
|
||||
### Core Role
|
||||
The core services provide the apis and state management for the system. Core services must be available within the cluster
|
||||
for use by the workers.
|
||||
* Core component provides webhook calls to external services for notifications of events:
|
||||
* New images added
|
||||
* CVE changes in images
|
||||
* Policy evaluation state change for an image
|
||||
|
||||
|
||||
### Worker Role
|
||||
The workers download and analyze images and upload results to the core services. The workers poll the queue service and
|
||||
do not have their own external api.
|
||||
|
||||
|
||||
Installing the Chart
|
||||
--------------------
|
||||
|
||||
Deploying PostgreSQL as a dependency managed in the chart:
|
||||
|
||||
`helm install .`
|
||||
|
||||
|
||||
Using and existing/external PostgreSQL service:
|
||||
|
||||
`helm install --name <name> --set postgresql.enabled=False .`
|
||||
|
||||
|
||||
Configuration
|
||||
-------------
|
||||
|
||||
While the configuration options of Anchore Engine are extensive, the options provided by the chart are:
|
||||
|
||||
### Database
|
||||
|
||||
* External Postgres (not managed by helm)
|
||||
* postgresql.enabled=False
|
||||
* postgresql.externalEndpoint=myserver.mypostgres.com:5432
|
||||
* postgresql.postgresUser=username
|
||||
* postgresql.postgresPassword=password
|
||||
* postgresql.postgresDatabase=db name
|
||||
* globalConfig.dbConfig.ssl=True
|
||||
|
||||
|
||||
### Policy Sync from anchore.io
|
||||
anchore.io is a hosted version of anchore engine that includes a UI and policy editor. You can configure a local anchore-engine
|
||||
to download and keep the policy bundles in sync (policies defining how to evaluate images).
|
||||
Simply provide the credentials for your anchore.io account in the values.yaml or using `--set` on CLI to enable:
|
||||
|
||||
* coreConfig.policyBundleSyncEnabled=True
|
||||
* globalConfig.users.admin.anchoreIOCredentials.useAnonymous=False
|
||||
* globalConfig.users.admin.anchoreIOCredentials.user=username
|
||||
* globalConfig.users.admin.anchoreIOCredentials.password=password
|
||||
|
||||
|
||||
Adding Workers
|
||||
--------------
|
||||
|
||||
To set a specific number of workers once the service is running:
|
||||
|
||||
`helm upgrade --set workerConfig.replicaCount=2`
|
||||
|
||||
To launch with more than one worker you can either modify values.yaml or run with:
|
||||
|
||||
`helm install --set workerConfig.replicaCount=2 <chart location>`
|
||||
|
||||
@@ -0,0 +1,5 @@
|
||||
dependencies:
|
||||
- name: postgresql
|
||||
version: "*"
|
||||
repository: "alias:stable"
|
||||
condition: postgresql.enabled
|
||||
@@ -0,0 +1,63 @@
|
||||
To use Anchore Engine you need the URL, username, and password to access the API.
|
||||
|
||||
Anchore Engine can be accessed via port {{ .Values.service.ports.api }} on the following DNS name from within the cluster:
|
||||
{{ template "fullname" . }}.{{ .Release.Namespace }}.svc.cluster.local
|
||||
|
||||
Here are the steps to configure the anchore-cli (`pip install anchorecli`). Use these same values for direct API access as well.
|
||||
|
||||
To configure your anchore-cli run:
|
||||
|
||||
ANCHORE_CLI_USER=admin
|
||||
ANCHORE_CLI_PASS=$(kubectl get secret --namespace {{ .Release.Namespace }} {{ template "fullname" . }} -o jsonpath="{.data.adminPassword}" | base64 --decode; echo)
|
||||
{{ if .Values.ingress.enabled }}
|
||||
ANCHORE_CLI_URL=http://$(kubectl get ingress --namespace {{ .Release.Namespace }} {{ template "fullname" . }} -o jsonpath="{.status.loadBalancer.ingress[0].ip}")
|
||||
{{ else }}
|
||||
Using the service endpoint from within the cluster you can use:
|
||||
ANCHORE_CLI_URL=http://{{ template "fullname" . }}.{{ .Release.Namespace }}.svc.cluster.local:{{ .Values.service.ports.api}}/v1/
|
||||
{{ end }}
|
||||
|
||||
To verify the service is up and running, you can run container for the Anchore Engine CLI:
|
||||
|
||||
kubectl run -i --tty anchore-cli --restart=Never --image anchore/engine-cli --env ANCHORE_CLI_USER=admin --env ANCHORE_CLI_PASS=${ANCHORE_CLI_PASS} --env ANCHORE_CLI_URL=http://{{ template "fullname" . }}.{{ .Release.Namespace }}.svc.cluster.local:{{ .Values.service.ports.api}}/v1/
|
||||
|
||||
from within the container you can use 'anchore-cli' commands.
|
||||
|
||||
* NOTE: On first startup of anchore-engine, it performs a CVE data sync which may take several minutes to complete. During this time the system status will report 'partially_down' and any images added for analysis will stay in the 'not_analyzed' state.
|
||||
Once the sync is complete, any queued images will be analyzed and the system status will change to 'all_up'.
|
||||
|
||||
Initial setup time can be >60sec for postgresql setup and readiness checks to pass for the services as indicated by pod state. You can check with:
|
||||
kubectl get pods -l app={{ template "fullname" .}},component=core
|
||||
|
||||
|
||||
A quick primer on using the Anchore Engine CLI follows. For more info see: https://github.com/anchore/anchore-engine/wiki/Getting-Started
|
||||
|
||||
View system status:
|
||||
|
||||
anchore-cli system status
|
||||
|
||||
Add an image to be analyzed:
|
||||
|
||||
anchore-cli image add <imageref>
|
||||
|
||||
List images and see the analysis status (not_analyzed initially):
|
||||
|
||||
anchore-cli image list
|
||||
|
||||
Once the image is analyzed you'll see status change to 'analyzed'. This may take some time on first execution with a new database because
|
||||
the system must first do a CVE data sync which can take several minutes. Once complete, the image will transition to 'analyzing' state.
|
||||
|
||||
When the image reaches 'analyzed' state, you can view policy evaluation output with:
|
||||
|
||||
anchore-cli evaluate check <imageref>
|
||||
|
||||
List CVEs found in the image with:
|
||||
|
||||
anchore-cli image vuln <imageref> os
|
||||
|
||||
List OS packages found in the image with:
|
||||
anchore-cli image content <imageref> os
|
||||
|
||||
List files found in the image with:
|
||||
anchore-cli image content <imageref> files
|
||||
|
||||
|
||||
Executable
+43
@@ -0,0 +1,43 @@
|
||||
{{/* vim: set filetype=mustache: */}}
|
||||
{{/*
|
||||
Expand the name of the chart.
|
||||
*/}}
|
||||
{{- define "name" -}}
|
||||
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
|
||||
{{- end -}}
|
||||
|
||||
{{/*
|
||||
Create a default fully qualified app name.
|
||||
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
|
||||
*/}}
|
||||
{{- define "fullname" -}}
|
||||
{{- $name := default .Chart.Name .Values.nameOverride -}}
|
||||
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" -}}
|
||||
{{- end -}}
|
||||
|
||||
{{/*
|
||||
Create a default fully qualified app name.
|
||||
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
|
||||
*/}}
|
||||
{{- define "worker.fullname" -}}
|
||||
{{- $name := default .Chart.Name .Values.nameOverride -}}
|
||||
{{- printf "%s-%s-%s" .Release.Name $name "worker"| trunc 63 | trimSuffix "-" -}}
|
||||
{{- end -}}
|
||||
|
||||
{{/*
|
||||
Create a default fully qualified app name.
|
||||
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
|
||||
*/}}
|
||||
{{- define "core.fullname" -}}
|
||||
{{- $name := default .Chart.Name .Values.nameOverride -}}
|
||||
{{- printf "%s-%s-%s" .Release.Name $name "core"| trunc 63 | trimSuffix "-" -}}
|
||||
{{- end -}}
|
||||
|
||||
|
||||
{{/*
|
||||
Create a default fully qualified dependency name for the db.
|
||||
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
|
||||
*/}}
|
||||
{{- define "postgres.fullname" -}}
|
||||
{{- printf "%s-%s" .Release.Name "postgresql" | trunc 63 | trimSuffix "-" -}}
|
||||
{{- end -}}
|
||||
@@ -0,0 +1,131 @@
|
||||
kind: ConfigMap
|
||||
apiVersion: v1
|
||||
metadata:
|
||||
name: "{{ template "core.fullname" . }}"
|
||||
labels:
|
||||
app: "{{ template "fullname" . }}"
|
||||
chart: "{{ .Chart.Name }}-{{ .Chart.Version }}"
|
||||
release: "{{ .Release.Name }}"
|
||||
heritage: "{{ .Release.Service }}"
|
||||
component: core
|
||||
data:
|
||||
config.yaml: |
|
||||
# Anchore Service Configuration File from ConfigMap
|
||||
service_dir: {{ default "/config" .Values.globalConfig.configDir }}
|
||||
tmp_dir: "/tmp"
|
||||
|
||||
allow_awsecr_iam_auto: {{ .Values.globalConfig.allowECRUseIAMRole }}
|
||||
cleanup_images: {{ .Values.globalConfig.cleanupImages }}
|
||||
|
||||
# docker_conn: 'unix://var/run/docker.sock'
|
||||
# docker_conn_timeout: 600
|
||||
|
||||
log_level: {{ .Values.coreConfig.logLevel }}
|
||||
host_id: ${ANCHORE_HOST_ID}
|
||||
internal_ssl_verify: {{ .Values.globalConfig.internalServicesSslVerifyCerts }}
|
||||
|
||||
# Uncomment if you have a local endpoint that can accept
|
||||
# notifications from the anchore-engine, as configured below
|
||||
#
|
||||
{{ if .Values.coreConfig.webhooks.enabled }}
|
||||
webhooks:
|
||||
{{ toYaml .Values.coreConfig.webhooks.config | indent 6 }}
|
||||
{{ end }}
|
||||
|
||||
# A feeds section is available for override, but shouldn't be
|
||||
# needed. By default, the 'admin' credentials are used if present,
|
||||
# otherwise anonymous access for feed sync is used
|
||||
|
||||
#feeds:
|
||||
# selective_sync:
|
||||
# # If enabled only sync specific feeds instead of all.
|
||||
# enabled: True
|
||||
# feeds:
|
||||
# vulnerabilities: True
|
||||
# # Warning: enabling the package sync causes the service to require much
|
||||
# # more memory to do process the significant data volume. We recommend at least 4GB available for the container
|
||||
# packages: False
|
||||
# anonymous_user_username: anon@ancho.re
|
||||
# anonymous_user_password: pbiU2RYZ2XrmYQ
|
||||
# url: 'https://ancho.re/v1/service/feeds'
|
||||
# client_url: 'https://ancho.re/v1/account/users'
|
||||
# token_url: 'https://ancho.re/oauth/token'
|
||||
# connection_timeout_seconds: 3
|
||||
# read_timeout_seconds: 60
|
||||
|
||||
credentials:
|
||||
users:
|
||||
admin:
|
||||
password: ${ANCHORE_ADMIN_PASSWORD}
|
||||
email: {{ .Values.globalConfig.users.admin.email }}
|
||||
external_service_auths:
|
||||
{{ if not .Values.globalConfig.users.admin.anchoreIOCredentials.useAnonymous }}
|
||||
anchoreio:
|
||||
anchorecli:
|
||||
auth: "${ANCHORE_IO_USER}:${ANCHORE_IO_PASSWORD}"
|
||||
{{ end }}
|
||||
auto_policy_sync: {{ .Values.coreConfig.policyBundleSyncEnabled }}
|
||||
|
||||
database:
|
||||
{{ if .Values.postgresql.enabled }}
|
||||
db_connect: 'postgresql+pg8000://${ANCHORE_DB_USER}:${ANCHORE_DB_PASSWORD}@{{ template "postgres.fullname" . }}:5432/{{ .Values.postgresql.postgresDatabase }}'
|
||||
{{ else }}
|
||||
db_connect: 'postgresql+pg8000://${ANCHORE_DB_USER}:${ANCHORE_DB_PASSWORD}@{{ .Values.postgresql.externalEndpoint}}/{{ .Values.postgresql.postgresDatabase }}'
|
||||
{{ end }}
|
||||
db_connect_args:
|
||||
timeout: 120
|
||||
ssl: {{ .Values.postgresql.sslEnabled }}
|
||||
db_pool_size: {{ .Values.globalConfig.dbConfig.connectionPoolSize }}
|
||||
db_pool_max_overflow: {{ .Values.globalConfig.dbConfig.connectionPoolSize }}
|
||||
services:
|
||||
apiext:
|
||||
enabled: True
|
||||
require_auth: True
|
||||
endpoint_hostname: {{ template "fullname" . }}
|
||||
listen: '0.0.0.0'
|
||||
port: {{ .Values.service.ports.api }}
|
||||
ssl_enable: {{ .Values.globalConfig.internalServicesSslEnabled }}
|
||||
ssl_cert: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretCertName }}
|
||||
ssl_key: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretKeyName }}
|
||||
kubernetes_webhook:
|
||||
enabled: True
|
||||
require_auth: False
|
||||
endpoint_hostname: {{ template "fullname" . }}
|
||||
listen: '0.0.0.0'
|
||||
port: {{ .Values.service.ports.k8sImagePolicyWebhook }}
|
||||
ssl_enable: {{ .Values.globalConfig.internalServicesSslEnabled }}
|
||||
ssl_cert: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretCertName }}
|
||||
ssl_key: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretKeyName }}
|
||||
catalog:
|
||||
enabled: True
|
||||
require_auth: True
|
||||
endpoint_hostname: {{ template "fullname" . }}
|
||||
listen: '0.0.0.0'
|
||||
port: {{ .Values.service.ports.catalog }}
|
||||
use_db: True
|
||||
cycle_timer_seconds: '1'
|
||||
cycle_timers:
|
||||
{{ toYaml .Values.globalConfig.cycleTimers | indent 10 }}
|
||||
ssl_enable: {{ .Values.globalConfig.internalServicesSslEnabled }}
|
||||
ssl_cert: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretCertName }}
|
||||
ssl_key: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretKeyName }}
|
||||
simplequeue:
|
||||
enabled: True
|
||||
require_auth: True
|
||||
endpoint_hostname: {{ template "fullname" . }}
|
||||
listen: '0.0.0.0'
|
||||
port: {{ .Values.service.ports.queue }}
|
||||
ssl_enable: {{ .Values.globalConfig.internalServicesSslEnabled }}
|
||||
ssl_cert: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretCertName }}
|
||||
ssl_key: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretKeyName }}
|
||||
analyzer:
|
||||
enabled: False
|
||||
policy_engine:
|
||||
enabled: True
|
||||
require_auth: True
|
||||
endpoint_hostname: {{ template "fullname" . }}
|
||||
listen: '0.0.0.0'
|
||||
port: {{ .Values.service.ports.policy }}
|
||||
ssl_cert: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretCertName }}
|
||||
ssl_key: {{ .Values.coreConfig.ssl.certDir -}}/{{- .Values.coreConfig.ssl.certSecretKeyName }}
|
||||
ssl_enable: {{ .Values.globalConfig.internalServicesSslEnabled }}
|
||||
@@ -0,0 +1,90 @@
|
||||
apiVersion: extensions/v1beta1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: "{{ template "core.fullname" . }}"
|
||||
labels:
|
||||
app: "{{ template "fullname" . }}"
|
||||
component: core
|
||||
chart: "{{ .Chart.Name }}-{{ .Chart.Version }}"
|
||||
release: "{{ .Release.Name }}"
|
||||
heritage: "{{ .Release.Service }}"
|
||||
spec:
|
||||
replicas: {{ .Values.coreConfig.replicaCount }}
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
app: "{{ template "fullname" . }}"
|
||||
component: core
|
||||
spec:
|
||||
volumes:
|
||||
- name: config-volume
|
||||
configMap:
|
||||
name: {{ template "core.fullname" .}}
|
||||
{{- if .Values.globalConfig.internalServicesSslEnabled }}
|
||||
- name: certs
|
||||
secret:
|
||||
secretName: {{ .Values.coreConfig.ssl.certSecret }}
|
||||
{{- end }}
|
||||
containers:
|
||||
- name: {{ .Chart.Name }}-core
|
||||
image: {{ .Values.image.tag }}
|
||||
imagePullPolicy: {{ .Values.image.pullPolicy }}
|
||||
ports:
|
||||
- containerPort: {{ .Values.service.ports.api }}
|
||||
name: external-api
|
||||
- containerPort: {{ .Values.service.ports.queue }}
|
||||
name: queue-service
|
||||
- containerPort: {{ .Values.service.ports.k8sImagePolicyWebhook }}
|
||||
name: webhook-service
|
||||
- containerPort: {{ .Values.service.ports.catalog }}
|
||||
name: catalog
|
||||
- containerPort: {{ .Values.service.ports.policy }}
|
||||
name: policy-engine
|
||||
env:
|
||||
- name: ANCHORE_HOST_ID
|
||||
value: {{ default "anchore_core_service" .Values.service.hostId }}
|
||||
- name: ANCHORE_DB
|
||||
value: {{ .Values.postgresql.postgresDatabase }}
|
||||
- name: ANCHORE_DB_HOST
|
||||
value: {{ template "postgres.fullname" . }}
|
||||
- name: ANCHORE_DB_USER
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: {{ template "fullname" . }}
|
||||
key: dbUser
|
||||
- name: ANCHORE_DB_PASSWORD
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: {{ template "fullname" . }}
|
||||
key: dbPassword
|
||||
- name: ANCHORE_ADMIN_PASSWORD
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: {{ template "fullname" . }}
|
||||
key: adminPassword
|
||||
volumeMounts:
|
||||
- name: config-volume
|
||||
mountPath: /config
|
||||
{{- if .Values.globalConfig.internalServicesSslEnabled }}
|
||||
- name: certs
|
||||
mountPath: {{ default "/certs" .Values.coreConfig.ssl.certDir }}
|
||||
readOnly: true
|
||||
{{- end }}
|
||||
readinessProbe:
|
||||
httpGet:
|
||||
path: /health
|
||||
port: external-api
|
||||
initialDelaySeconds: 60
|
||||
periodSeconds: 10
|
||||
timeoutSeconds: 10
|
||||
failureThreshold: 10
|
||||
livenessProbe:
|
||||
httpGet:
|
||||
path: /health
|
||||
port: external-api
|
||||
timeoutSeconds: 10
|
||||
initialDelaySeconds: 60
|
||||
periodSeconds: 30
|
||||
failureThreshold: 10
|
||||
resources:
|
||||
{{ toYaml .Values.coreConfig.resources | indent 10 }}
|
||||
@@ -0,0 +1,25 @@
|
||||
{{- if .Values.ingress.enabled -}}
|
||||
apiVersion: extensions/v1beta1
|
||||
kind: Ingress
|
||||
metadata:
|
||||
name: "{{ template "fullname" . }}"
|
||||
labels:
|
||||
app: "{{ template "fullname" . }}"
|
||||
chart: "{{ .Chart.Name }}-{{ .Chart.Version }}"
|
||||
release: "{{ .Release.Name }}"
|
||||
heritage: "{{ .Release.Service }}"
|
||||
component: core
|
||||
{{- if .Values.ingress.annotations }}
|
||||
annotations:
|
||||
{{ toYaml .Values.ingress.annotations | indent 4 }}
|
||||
{{- end }}
|
||||
spec:
|
||||
backend:
|
||||
serviceName: {{ template "fullname" . }}
|
||||
servicePort: {{ .Values.service.ports.api }}
|
||||
{{- if .Values.ingress.tls }}
|
||||
tls:
|
||||
{{ toYaml .Values.ingress.tls | indent 2 }}
|
||||
{{- end }}
|
||||
|
||||
{{- end -}}
|
||||
@@ -0,0 +1,16 @@
|
||||
apiVersion: v1
|
||||
kind: Secret
|
||||
metadata:
|
||||
name: {{ template "fullname" . }}
|
||||
labels:
|
||||
app: {{ template "fullname" . }}
|
||||
chart: "{{ .Chart.Name }}-{{ .Chart.Version }}"
|
||||
release: "{{ .Release.Name }}"
|
||||
heritage: "{{ .Release.Service }}"
|
||||
type: Opaque
|
||||
data:
|
||||
adminPassword: {{ .Values.globalConfig.users.admin.password | b64enc | quote }}
|
||||
dbUser: {{ .Values.postgresql.postgresUser | b64enc | quote }}
|
||||
dbPassword: {{ .Values.postgresql.postgresPassword | b64enc | quote }}
|
||||
anchoreIOUser: {{ .Values.globalConfig.users.admin.anchoreIOCredentials.user | b64enc | quote }}
|
||||
anchoreIOPassword: {{ .Values.globalConfig.users.admin.anchoreIOCredentials.password | b64enc | quote }}
|
||||
@@ -0,0 +1,36 @@
|
||||
apiVersion: v1
|
||||
kind: Service
|
||||
metadata:
|
||||
name: {{ template "fullname" . }}
|
||||
labels:
|
||||
app: {{ template "fullname" . }}
|
||||
chart: {{ .Chart.Name }}-{{ .Chart.Version }}
|
||||
release: {{ .Release.Name }}
|
||||
heritage: {{ .Release.Service }}
|
||||
component: core
|
||||
spec:
|
||||
type: {{ .Values.service.type }}
|
||||
ports:
|
||||
- name: anchore-external-api
|
||||
port: {{ .Values.service.ports.api }}
|
||||
targetPort: {{ .Values.service.ports.api }}
|
||||
protocol: TCP
|
||||
- name: anchore-kubewebhook
|
||||
port: {{ .Values.service.ports.k8sImagePolicyWebhook }}
|
||||
targetPort: {{ .Values.service.ports.k8sImagePolicyWebhook }}
|
||||
protocol: TCP
|
||||
- name: anchore-queue
|
||||
port: {{ .Values.service.ports.queue }}
|
||||
targetPort: {{ .Values.service.ports.queue }}
|
||||
protocol: TCP
|
||||
- name: anchore-catalog
|
||||
port: {{ .Values.service.ports.catalog }}
|
||||
targetPort: {{ .Values.service.ports.catalog }}
|
||||
protocol: TCP
|
||||
- name: anchore-policy
|
||||
port: {{ .Values.service.ports.policy }}
|
||||
targetPort: {{ .Values.service.ports.policy }}
|
||||
protocol: TCP
|
||||
selector:
|
||||
app: {{ template "fullname" . }}
|
||||
component: core
|
||||
@@ -0,0 +1,63 @@
|
||||
kind: ConfigMap
|
||||
apiVersion: v1
|
||||
metadata:
|
||||
name: "{{ template "worker.fullname" . }}"
|
||||
labels:
|
||||
app: "{{ template "fullname" . }}"
|
||||
chart: "{{ .Chart.Name }}-{{ .Chart.Version }}"
|
||||
release: "{{ .Release.Name }}"
|
||||
heritage: "{{ .Release.Service }}"
|
||||
component: worker
|
||||
data:
|
||||
config.yaml: |
|
||||
# Anchore Service Configuration File
|
||||
|
||||
# General system-wide configuration options, these should not need to
|
||||
# be altered for basic operation
|
||||
#
|
||||
service_dir: {{ default "/config" .Values.globalConfig.configDir }}
|
||||
tmp_dir: {{ default "/tmp" .Values.workerConfig.analyzerScratchDir }}
|
||||
|
||||
allow_awsecr_iam_auto: {{ .Values.globalConfig.allowECRUseIAMRole }}
|
||||
cleanup_images: {{ .Values.globalConfig.cleanupImages }}
|
||||
|
||||
#docker_conn: 'unix://var/run/docker.sock'
|
||||
#docker_conn_timeout: 600
|
||||
|
||||
log_level: {{ .Values.workerConfig.logLevel }}
|
||||
#host_id: 'e3651c16-5161-412f-a188-2bfae2d2dcf0'
|
||||
internal_ssl_verify: {{ .Values.globalConfig.internalServicesSslVerifyCerts }}
|
||||
|
||||
#
|
||||
# A feeds section is available for override, but shouldn't be
|
||||
# needed. By default, the 'admin' credentials are used if present,
|
||||
# otherwise anonymous access for feed sync is used
|
||||
|
||||
credentials:
|
||||
users:
|
||||
admin:
|
||||
password: ${ANCHORE_ADMIN_PASSWORD}
|
||||
email: 'admin@myemail.com'
|
||||
external_service_auths:
|
||||
# anchoreio:
|
||||
# anchorecli:
|
||||
# auth: 'myanchoreiouser:myanchoreiopass'
|
||||
#auto_policy_sync: true
|
||||
|
||||
database:
|
||||
db_connect: "postgresql+pg8000://${ANCHORE_DB_USER}:${ANCHORE_DB_PASSWORD}@${ANCHORE_DB_HOST}:5432/${ANCHORE_DB}"
|
||||
db_connect_args:
|
||||
timeout: 120
|
||||
ssl: {{ .Values.globalConfig.dbConfig.ssl }}
|
||||
db_pool_size: {{ .Values.globalConfig.dbConfig.connectionPoolSize }}
|
||||
db_pool_max_overflow: {{ .Values.globalConfig.dbConfig.connectionPoolSize }}
|
||||
services:
|
||||
analyzer:
|
||||
enabled: true
|
||||
cycle_timer_seconds: {{ .Values.workerConfig.cycleTimerSeconds }}
|
||||
max_threads: {{ .Values.workerConfig.concurrentTasksPerWorker }}
|
||||
analyzer_driver: {{ .Values.workerConfig.analyzerMode }}
|
||||
ssl_cert: {{ .Values.workerConfig.ssl.certDir -}}/{{- .Values.workerConfig.ssl.certSecretCertName }}
|
||||
ssl_key: {{ .Values.workerConfig.ssl.certDir -}}/{{ .Values.workerConfig.ssl.certSecretKeyName }}
|
||||
ssl_enable: {{ .Values.globalConfig.internalServicesSslEnabled }}
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
apiVersion: apps/v1beta1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: "{{ template "worker.fullname" . }}"
|
||||
labels:
|
||||
app: "{{ template "worker.fullname" . }}"
|
||||
chart: "{{ .Chart.Name }}-{{ .Chart.Version }}"
|
||||
release: "{{ .Release.Name }}"
|
||||
heritage: "{{ .Release.Service }}"
|
||||
component: worker
|
||||
spec:
|
||||
replicas: {{ .Values.workerConfig.replicaCount }}
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
app: "{{ template "worker.fullname" . }}"
|
||||
component: worker
|
||||
spec:
|
||||
containers:
|
||||
- name: {{ .Chart.Name }}-worker
|
||||
image: {{ .Values.image.tag }}
|
||||
{{- if eq .Values.workerConfig.analyzerMode "localanchore" }}
|
||||
securityContext:
|
||||
privileged: true
|
||||
{{- end }}
|
||||
env:
|
||||
- name: ANCHORE_ENGINE_SERVICES
|
||||
value: anchore-worker
|
||||
- name: ANCHORE_DB
|
||||
value: {{ .Values.postgresql.postgresDatabase }}
|
||||
- name: ANCHORE_DB_HOST
|
||||
value: {{ template "postgres.fullname" . }}
|
||||
- name: ANCHORE_DB_USER
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: {{ template "fullname" . }}
|
||||
key: dbUser
|
||||
- name: ANCHORE_DB_PASSWORD
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: {{ template "fullname" . }}
|
||||
key: dbPassword
|
||||
- name: ANCHORE_ADMIN_PASSWORD
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: {{ template "fullname" . }}
|
||||
key: adminPassword
|
||||
volumeMounts:
|
||||
- name: config-volume
|
||||
mountPath: /config
|
||||
{{- if eq .Values.workerConfig.analyzerMode "localanchore" -}}
|
||||
- name: docker-sock
|
||||
mountPath: /var/run/docker.sock
|
||||
{{- end -}}
|
||||
{{- if .Values.globalConfig.internalServicesSslEnabled }}
|
||||
- name: certs
|
||||
mountPath: {{ default "/certs" .Values.workerConfig.ssl.CertDir }}
|
||||
readOnly: true
|
||||
{{- end }}
|
||||
- name: analysis-scratch
|
||||
mountPath: {{ .Values.workerConfig.analysisScratchVolume.mountPath }}
|
||||
livenessProbe:
|
||||
exec:
|
||||
command:
|
||||
- pgrep
|
||||
- twistd
|
||||
initialDelaySeconds: 60
|
||||
periodSeconds: 60
|
||||
failureThreshold: 5
|
||||
resources:
|
||||
{{ toYaml .Values.workerConfig.resources | indent 10 }}
|
||||
volumes:
|
||||
- name: config-volume
|
||||
configMap:
|
||||
name: {{ template "worker.fullname" .}}
|
||||
{{- if eq .Values.workerConfig.analyzerMode "localanchore" }}
|
||||
- name: docker-sock
|
||||
hostPath:
|
||||
path: /var/run/docker.sock
|
||||
{{- end }}
|
||||
{{- if .Values.globalConfig.internalServicesSslEnabled }}
|
||||
- name: certs
|
||||
secret:
|
||||
secretName: {{ .Values.workerConfig.ssl.certSecret }}
|
||||
{{- end }}
|
||||
- name: analysis-scratch
|
||||
{{ toYaml .Values.workerConfig.analysisScratchVolume.details -}}
|
||||
@@ -0,0 +1,183 @@
|
||||
# Default values for anchore_engine chart.
|
||||
|
||||
# The configuration for the API service, which must be reachable inside the cluster by other workers and users
|
||||
service:
|
||||
type: ClusterIP
|
||||
ports:
|
||||
api: 8228
|
||||
queue: 8083
|
||||
catalog: 8082
|
||||
policy: 8087
|
||||
k8sImagePolicyWebhook: 8338
|
||||
|
||||
image:
|
||||
# Specific version tags are also available, e.g. v0.1.5, v0.1.6,...
|
||||
tag: docker.io/anchore/anchore-engine:latest
|
||||
# pullPolicy: IfNotPresent
|
||||
|
||||
# Used to create Ingress record (should used with service.type: ClusterIP or NodePort depending on platform)
|
||||
ingress:
|
||||
enabled: false
|
||||
annotations:
|
||||
# kubernetes.io/ingress.allow-http: False
|
||||
# kubernetes.io/ingress.class: nginx
|
||||
# kubernetes.io/tls-acme: true
|
||||
|
||||
# Secrets must be manually created in the namespace.
|
||||
tls:
|
||||
# - secretName: tlstestsecret
|
||||
|
||||
# Dependency on Postgresql, configure here
|
||||
postgresql:
|
||||
enabled: true
|
||||
postgresUser: anchoreengine
|
||||
postgresPassword: anchore-postgres,123
|
||||
postgresDatabase: anchore
|
||||
|
||||
|
||||
# Use this config if you set enabled=False and want to specify an external (already existing) postres deployment for use.
|
||||
# Set this to the host and port. eg. mypostgres.myserver.io:5432
|
||||
externalEndpoint: Null
|
||||
|
||||
|
||||
# Global configuration shared by both core and worker
|
||||
globalConfig:
|
||||
dbConfig:
|
||||
timeout: 120
|
||||
# Use ssl, but the default postgresql config in helm's stable repo does not support ssl on server side, so this should be set for external dbs only for the time being
|
||||
ssl: false
|
||||
connectionPoolSize: 30
|
||||
connectionPoolMaxOverflow: 100
|
||||
|
||||
# Cleanup local images used during analysis, defaults to True. If set to false, images will remain on workers after analysis.
|
||||
cleanupImages: true
|
||||
|
||||
# If True, if a user adds an ECR registry with username = awsauto then the system will look for an instance profile to use for auth against the registry
|
||||
allowECRUseIAMRole: false
|
||||
|
||||
# User configuration. Add more users here if needed.
|
||||
users:
|
||||
admin:
|
||||
password: foobar
|
||||
email: admin@myemail.com
|
||||
policyBundleSyncEnabled: false
|
||||
|
||||
# Credentials for https://anchore.io Cloud service if you have them. Can be used to automatically sync policy bundles.
|
||||
anchoreIOCredentials:
|
||||
# If use_anonymous = False, the specific credentials are used for the feed sync and bundle sync features otherwise disregarded.
|
||||
useAnonymous: true
|
||||
user: someuser
|
||||
password: somepassword
|
||||
|
||||
internalServicesSslEnabled: false
|
||||
internalServicesSslVerifyCerts: false
|
||||
|
||||
# Intervals to run specific events on (seconds)
|
||||
cycleTimers:
|
||||
# Interval to check for an update to a tag
|
||||
image_watcher: 3600
|
||||
# Interval to re-run a policy eval on a tag
|
||||
policy_eval: 3600
|
||||
# Interval to run a feed sync to get latest cve data
|
||||
feed_sync: 14400
|
||||
# Interval workers check the queue
|
||||
analyzer_queue: 1
|
||||
# Interval notifications will be processed for state changes
|
||||
notifications: 30
|
||||
# Intervals service state updates are polled
|
||||
service_watcher: 15
|
||||
# Interval for policy bundle sync from anchore.io if enabled
|
||||
policy_bundle_sync: 300
|
||||
|
||||
|
||||
# Configuration for the core engine service that serves the API
|
||||
# The core service handles the user facing APIs and coordination of workers as well as storage interfaces for data
|
||||
coreConfig:
|
||||
# For the moment, the replica count should stay at 1. That restriction should change soon.
|
||||
replicaCount: 1
|
||||
hostId: "anchore-engine-core-host"
|
||||
logLevel: INFO
|
||||
policyBundleSyncEnabled: false
|
||||
|
||||
ssl:
|
||||
# To use certs for TLS directly from the services, create a secret with keys that match the values fo certSecretKey and certSecretCert
|
||||
certSecret: null
|
||||
certSecretKeyName: "tls.key"
|
||||
certSecretCertName: "tls.crt"
|
||||
certDir: "/certs"
|
||||
|
||||
|
||||
# Configure webhook outputs here. The service provides these webhooks for notifying external systems of updates
|
||||
webhooks:
|
||||
enabled: "True"
|
||||
config:
|
||||
# User and password to be set (using HTTP basic auth) on all webhook calls if necessary
|
||||
user: null
|
||||
password: null
|
||||
ssl_verify: true
|
||||
|
||||
# Endpoint for general notification delivery. These events are image/tag updates etc. This is globally configured
|
||||
# and updates for all users are sent to the same host but with a different path for each user.
|
||||
general: {}
|
||||
# url: "http://somehost:9090/<notification_type>/<userId>"
|
||||
# Endpoint and credentials for policy evaluation delivery
|
||||
policy_eval: {}
|
||||
# url: "http://somehost:9090/policy_eval/<userId>"
|
||||
# user: null
|
||||
# password: null
|
||||
# Endpoint for fatal system errors to be delivery
|
||||
error_event: {}
|
||||
# url: 'http://somehost:9090/error_event/'
|
||||
|
||||
# resources:
|
||||
# limits:
|
||||
# cpu: 100m
|
||||
# memory: 6Gi
|
||||
# requests:
|
||||
# cpu: 100m
|
||||
# memory: 4Gi
|
||||
|
||||
# Configuration for the worker pods that perform image analysis
|
||||
# There may be many of these workers but best practice is to not have more than one per node since analysis
|
||||
# is very IO intensive. Use of affinity/anti-affinity rules for scheduling the workers is future work.
|
||||
workerConfig:
|
||||
replicaCount: 1
|
||||
logLevel: INFO
|
||||
|
||||
# Analyzer driver determines how the worker performs download and extraction of images
|
||||
#
|
||||
# "nodocker" does not require docker and pulls content directly from the registry and assembles it directly. This has the side-effect
|
||||
# of not handling images with V1 manifests as cleanly due to missing metadata in those manifests.
|
||||
#
|
||||
# "localanchore" requires the docker socket mounted into the worker container and uses docker itself to pull and extract the image into the container.
|
||||
# this is the legacy mode.
|
||||
analyzerMode: nodocker
|
||||
|
||||
# The cycle timer is the interval between checks to the work queue for new jobs
|
||||
cycleTimerSeconds: 1
|
||||
|
||||
# Controls the concurrency of the worker itself. Can be configured to process more than one task at a time, but it IO bound, so may not
|
||||
# necessarily be faster depending on hardware. Should test and balance this value vs. number of workers for your deployment cluster performance.
|
||||
concurrentTasksPerWorker: 1
|
||||
|
||||
# The analysisVolume controls the mounting of an external volume for scratch space for image analysis. Generally speaking
|
||||
# you need to provision 3x the size of the largest image (uncompressed) that you want to analyze for this space.
|
||||
analysisScratchVolume:
|
||||
mountPath: /tmp
|
||||
details:
|
||||
emptyDir: {}
|
||||
|
||||
# Configuration for ssl used for internal node communications between components
|
||||
ssl:
|
||||
certDir: "/certs"
|
||||
certSecret: null
|
||||
certSecretKeyName: "tls.key"
|
||||
certSecretCertName: "tls.crt"
|
||||
|
||||
# resources:
|
||||
# limits:
|
||||
# cpu: 100m
|
||||
# memory: 3Gi
|
||||
# requests:
|
||||
# cpu: 100m
|
||||
# memory: 2Gi
|
||||
Reference in New Issue
Block a user