We use analytics and cookies to understand site traffic. Information about your use of our site is shared with Google for that purpose.You can read our privacy policies and terms of use etc by clicking here.
VCS GitOps
This page provides a detailed overview of how to set up the GitOps functionality for Seldon Deploy. Setting up GitOps is highly recommended.
Note
Before starting the installation procedure, please download installation resources as explained here and make sure that all pre-requisites are satisfied.
This page also assumes that main Seldon components are installed.
Installation of ArgoCD
We start with installing ArgoCD in your cluster. Official documentation can be found here.
Following set of commands will install argocd in the argocd
namespace.
ARGOCD_VERSION=v1.6.2
kubectl create namespace argocd || echo "namespace exist"
kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/${ARGOCD_VERSION}/manifests/install.yaml
kubectl rollout status deployment/argocd-application-controller -n argocd
kubectl rollout status deployment/argocd-repo-server -n argocd
kubectl rollout status deployment/argocd-server -n argocd
kubectl rollout status deployment/argocd-redis -n argocd
kubectl rollout status deployment/argocd-dex-server -n argocd
We will also need the argocd
command line tool that can be obtained directly from GitHub
ARGOCD_VERSION=v1.6.2
wget -q -O argocd "https://github.com/argoproj/argo-cd/releases/download/${ARGOCD_VERSION}/argocd-linux-amd64"
chmod +x ./argocd
Password and ingress configuration
We can set ArgoCD password by patching a corresponding kubernetes secret
:
ARGOCDINITIALPASS=12341234
kubectl patch secret \
-n argocd argocd-secret \
-p '{"stringData": { "admin.password": "'$(htpasswd -bnBC 10 "" ${ARGOCDINITIALPASS} | tr -d ':\n')'"}}'
If the SSL termination happens at the earlier stage we need to inform ArgoCD that it is suppose to run in the insecure
mode
kubectl patch deploy argocd-server \
-n argocd \
-p '[{"op": "add", "path": "/spec/template/spec/containers/0/command/-", "value": "--insecure"}]' \
--type json
Assuming that base path will be /argocd
we need to patch argocd-server
accordingly
kubectl patch deploy argocd-server \
-n argocd \
-p '[{"op": "add", "path": "/spec/template/spec/containers/0/command/-", "value": "--rootpath"}, {"op": "add", "path": "/spec/template/spec/containers/0/command/-", "value": "/argocd"}]' \
--type json
Finally, we create VirtualService named argocd-vs.yaml
, pointing at the Istio Gateway created for Seldon (see the Istio page):
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: argocd-server
namespace: argocd
spec:
gateways:
- istio-system/seldon-gateway
hosts:
- '*'
http:
- match:
- uri:
prefix: /argocd/
route:
- destination:
host: argocd-server
port:
number: 80
and apply it with
kubectl apply -f argocd-vs.yaml
Accessing ArgoCD UI and API endpoints
If you created virtual service in the previous step the ArgoCD UI should be accessible under following URL:
ISTIO_INGRESS=$(kubectl get svc -n istio-system istio-ingressgateway -o jsonpath='{.status.loadBalancer.ingress[0].ip}')
ISTIO_INGRESS+=$(kubectl get svc -n istio-system istio-ingressgateway -o jsonpath='{.status.loadBalancer.ingress[0].hostname}')
echo "ArgoCD UI URL: http://${ISTIO_INGRESS}/argocd/"
It is also possible to access the UI at localhost:8080
using port-forward
method:
kubectl port-forward -n argocd svc/argocd-server 8080:80
To log ArgoCD API using Istio ingress:
./argocd login ${ISTIO_INGRESS}:80 --username admin --password ${ARGOCDINITIALPASS} --insecure --grpc-web-root-path /argocd
Create ArgoCD project and application
In this section we assume that following environmental variables are set
GIT_USER=... # git user
GIT_TOKEN=... # git token or password
GIT_REPO_NAME=... # repository name, e.g. seldon-gitops-repo
GIT_REPO_URL=... # repository URL, e.g. github.com/${GIT_USER}/${GIT_REPO_NAME}
Note that $GIT_REPO_URL
should not contain http or http protocol. In addition we will use $namespace
to refer to the name of namespace for which we are enabling the GitOps functionality.
The only requirements for the git repository are that it is non-empty (empty README file suffice) and cloneable from within the cluster. The latter can be verified with the following one-liner command
kubectl run --quiet=true -it --rm git-clone --image=radial/busyboxplus:git --restart=Never -- git clone https://$GIT_USER:$GIT_TOKEN@$GIT_REPO_URL
ArgoCD projects and applications can be created via the ArgoCD UI, argocd
CLI tool and through CRDs. As declarative approach guarantees best reproducibility this is the approach that we recommend.
We create ArgoCD project by creating the following AppProject
resources named argocd-project.yaml
cat << EOF > ./argocd-project.yaml
apiVersion: argoproj.io/v1alpha1
kind: AppProject
metadata:
name: seldon
namespace: argocd
spec:
description: Seldon Deploy Project
sourceRepos:
- https://${GIT_REPO_URL}
destinations:
- namespace: ${namespace}
server: https://kubernetes.default.svc
clusterResourceWhitelist:
- group: '*'
kind: '*'
roles:
- name: seldon-admin
policies:
- p, proj:seldon:seldon-admin, applications, get, seldon/*, allow
- p, proj:seldon:seldon-admin, applications, create, seldon/*, allow
- p, proj:seldon:seldon-admin, applications, update, seldon/*, allow
- p, proj:seldon:seldon-admin, applications, delete, seldon/*, allow
- p, proj:seldon:seldon-admin, applications, sync, seldon/*, allow
EOF
kubectl apply -f argocd-project.yaml
Similarly we create the ArgoCD Application
resource:
ARGO_APP_NAME=seldon-gitops-"${namespace}"
cat << EOF > ./argocd-application.yaml
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
name: ${ARGO_APP_NAME}
namespace: argocd
spec:
project: seldon
destination:
namespace: ${namespace}
server: https://kubernetes.default.svc
source:
directory:
recurse: true
path: ${namespace}
repoURL: https://${GIT_REPO_URL}
syncPolicy:
automated: {}
EOF
kubectl apply -f argocd-application.yaml
Seldon namespace configuration
For a namespace to be used with GitOps a following label and annotation are required
kubectl create ns $namespace || echo "namespace $namespace already exists"
kubectl label namespace $namespace seldon.gitops=enabled --overwrite=true
kubectl annotate namespace $namespace git-repo="https://${GIT_REPO_URL}" --overwrite=true
Note
If your ArgoCD application does not follow seldon-gitops-${namespace}
naming convention you can label the namespace accordingly
kubectl label namespace $namespace argocdapp=${ARGO_APP_NAME} --overwrite=true
If you intend to use Batch jobs on the namespace then you’ll need additional config. See the Argo section.
Git credentials configuration
The last required step is to create Git credentials. We configure ArgoCD’s access to the repository with:
./argocd repo add "https://${GIT_REPO_URL}" \
--username ${GIT_USER} \
--password ${GIT_TOKEN} \
--upsert
Seldon Deploy also requires access to the repository. To achieve this we create a secret:
kubectl create secret generic git-creds -n seldon-system \
--from-literal=username="${GIT_USER}" \
--from-literal=token="${GIT_TOKEN}" \
--from-literal=email="${GIT_EMAIL}" \
--dry-run=client -o yaml | kubectl apply -f -
and enable GitOps in the deploy-values.yaml
values file:
gitops:
git:
secret: git-creds
argocd:
enabled: true
It is also possible to configure ssh key based access by including id_rsa
and known_hosts
in the secret:
kubectl create secret generic git-creds -n seldon-system \
--from-file ~/.ssh/id_rsa --from-file ~/.ssh/known_hosts \
--from-literal=passphrase="${GIT_SSHKEY_PASSPHRASE}" \
--from-literal=username="${GIT_USER}" \
--from-literal=token="${GIT_TOKEN}" \
--from-literal=email="${GIT_EMAIL}" \
--dry-run=client -o yaml | kubectl apply -f -
Note
If you do not want to create a secret (not adviced!) and provide username
and token
in the deploy-values.yaml
directly you need to to set secret: ""
gitops:
git:
user: ${GIT_USER}
email: ${GIT_EMAIL}
token: ${GIT_TOKEN}
secret: ""
argocd:
enabled: true
Configure Webhooks (optional)
Here we show how it’s possible to programmatically set up the webhooks programmatically, however you can also set them up manually from the repo.
Note: In case webhooks are not arriving at its destination it is helpful to enable webhook’s history.
It may be necessary to also select Skip certificate verification
option.
Github
First we need to configure the webhook that will be sending updates to the Seldon Deploy endpoint:
whIp=$(kubectl get service seldon-deploy-webhook -o jsonpath='{.status.loadBalancer.ingress[*].ip}')
curl -u ${GIT_USER}:${GIT_TOKEN} -v -H "Content-Type: application/json" -X POST -d "{\"name\": \"web\", \"active\": true, \"events\": [\"*\"], \"config\": {\"url\": \"http://${whIp}/api/git-webhook\", \"content_type\": \"json\" }}" https://${GIT_API}/repos/${GIT_USER}/${REPONAME}/hooks
Then we set up the webhook that will be sending the updates to ArgoCD.
curl -u ${GIT_USER}:${GIT_TOKEN} -v -H "Content-Type: application/json" -X POST -d "{\"name\": \"web\", \"active\": true, \"events\": [\"*\"], \"config\": {\"url\": \"https://${ARGOCDURL}/api/webhook\", \"content_type\": \"json\", \"secret\": \"${ARGOCDINITIALPASS}\", \"insecure_ssl\": \"1\" }}" https://${GIT_API}/repos/${GIT_USER}/${REPONAME}/hooks
Bitbucket
First we need to configure the webhook that will be sending updates to the Seldon Deploy endpoint:
whIp=$(kubectl get service seldon-deploy-webhook -o jsonpath='{.status.loadBalancer.ingress[*].ip}')
curl -v -u ${GIT_USER}:${GIT_TOKEN} -v -H "Content-Type: application/json" -d '
{
"description": "web",
"events": ["repo:push"],
"url": "'"http://${whIp}/api/git-webhook"'",
"active": true
}' https://${GIT_API}/2.0/repositories/${GIT_USER}/${REPONAME}/hooks
Then we set up the webhook that will be sending the updates to ArgoCD.
curl -v -u ${GIT_USER}:${GIT_TOKEN} -v -H "Content-Type: application/json" -d '
{
"description": "web",
"events": ["repo:push"],
"url": "'"https://${ARGOCDURL}/api/webhook"'",
"active": true
}' https://${GIT_API}/2.0/repositories/${GIT_USER}/${REPONAME}/hooks