Skip to content

Commit 04f67b6

Browse files
developer-guyalexellis
authored andcommitted
Bring GitOps to your OpenFaaS functions with ArgoCD
Review by Alex Ellis Signed-off-by: Batuhan Apaydın <[email protected]> Signed-off-by: Alex Ellis (OpenFaaS Ltd) <[email protected]>
1 parent 90d6767 commit 04f67b6

File tree

2 files changed

+386
-0
lines changed

2 files changed

+386
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,386 @@
1+
---
2+
title: "Bring GitOps to your OpenFaaS functions with ArgoCD"
3+
description: "In this post you'll learn how to manage OpenFaaS functions based on GitOps principles by using ArgoCD"
4+
date: 2021-04-15
5+
image: /images/2021-04-08-bring-gitops-to-your-openfaas-functions-with-argocd/argo-horizontal.jpg
6+
categories:
7+
- arkade
8+
- kubectl
9+
- argocd
10+
- gitops
11+
- openfaas-operator
12+
- helm
13+
author_staff_member: developer-guy
14+
dark_background: true
15+
16+
---
17+
18+
In this post you'll learn how to manage OpenFaaS functions based on GitOps principles by using ArgoCD
19+
20+
## What is GitOps?
21+
22+
[Alexis Richardson](https://twitter.com/monadic) coined the term _GitOps_ in 2017. Since then it's gained significant interest in the enterprise companies because it allows for easier auditing of deployments.
23+
24+
With a GitOps approach, build artifacts from your Continuous Integration (CI) pipeline are deployed to your cluster. The desired state is set in a number of configuration files in a Git repository, and a second agent component runs inside the cluster to compare the delta. The differences are known as drift, and the agent's role is to detect and correct it.
25+
26+
![Separation of CI and CD](https://images.contentstack.io/v3/assets/blt300387d93dabf50e/blt31fc28ca69fa30a8/5a5e940703361d7a0b2936a5/gitops_cd_pipeline.png)
27+
28+
> From [Weaveworks.com](https://www.weave.works/technologies/gitops/)
29+
30+
> In the diagram above, we can see that GitOps separates our code repository, where our teams push and test code, from the repo containing deployment information, aka "config repo". When new images or artifacts are created, the tags and versions in the config repo can be updated automatically or via a separate commit from a team member.
31+
32+
Two of the most popular open-source projects for GitOps are [Flux](https://fluxcd.io/), which was created at Weaveworks. Intuit, an American payroll company created [ArgoCD](https://argoproj.github.io/argo-cd/). Both projects were donated to the Cloud Computing Foundation (CNCF) to encourage broader use and contributions.
33+
34+
We have [previously looked at FluxCD with OpenFaaS](https://www.openfaas.com/blog/openfaas-flux/), but in this post we'll show how to use ArgoCD with the OpenFaaS Function CRD to continuously deploy your functions.
35+
36+
You can read more about ArgoCD on the [project homepage](https://argoproj.github.io/argo-cd/).
37+
38+
## Introducing the OpenFaaS Operator
39+
40+
The normal installation of OpenFaaS uses its REST API to create functions using the CLI, REST API or UI. It also has a mode called "operator mode" where a Custom Resource can be used with `kubectl` to apply and deploy functions.
41+
42+
```yaml
43+
apiVersion: openfaas.com/v1
44+
kind: Function
45+
metadata:
46+
name: nodeinfo
47+
namespace: openfaas-fn
48+
spec:
49+
name: nodeinfo
50+
image: functions/nodeinfo:latest
51+
```
52+
53+
The `faas-cli generate` command can be used to convert the OpenFaaS stack.yml file into the Function CustomResource for use with `kubectl`.
54+
55+
The _OpenFaaS Operator_ comes with an extension to the Kubernetes API that allows you to manage OpenFaaS functions in a
56+
declarative manner. The operator implements a control loop that tries to match the desired state of your OpenFaaS
57+
functions, defined as a collection of custom resources, with the actual state of your cluster.
58+
59+
To get more detail please refer to this [link](https://blog.alexellis.io/introducing-the-openfaas-operator/).
60+
61+
## Tutorial
62+
63+
In this section, we are going to create two application for ArgoCD, first one is OpenFaaS Operator, the second one is the repository that holds OpenFaaS functions manifest files.
64+
65+
ArgoCD can work against Kubernetes manifests in a various ways:
66+
67+
* kustomize applications
68+
* helm charts
69+
* ksonnet applications
70+
* jsonnet files
71+
* Plain directory of YAML/json manifests
72+
* Any custom config management tool configured as a config management plugin
73+
74+
So, we are going to use the OpenFaaS [Helm Chart](https://github.com/openfaas/faas-netes) to deploy OpenFaaS and ist Operator. Once OpenFaaS Operator is deployed, we can use the _Custom Resource_ called _"Function"_ in order to define our OpenFaaS functions like any other Kubernetes resources such as Deployment, Pod etc.
75+
76+
In the second part, we'll to use plain manifests to deploy OpenFaaS functions. A dedicated chart can also be created for deploying functions.
77+
78+
### Prerequisites
79+
80+
Once we have arkade, we can create a cluster and install ArgoCD. If you prefer, you can also manually download all the tools required, and find the instructions for ArgoCD's helm chart.
81+
82+
* [arkade](https://get-arkade.dev) (v0.7.10) Kubernetes marketplace
83+
84+
```bash
85+
# Run with or without sudo
86+
$ curl -sLS https://dl.get-arkade.dev | sudo sh
87+
```
88+
89+
* KinD (Kubernetes in Docker) v0.10.0
90+
91+
Kubernetes is our recommendation for teams running at scale, but in this demo we will be
92+
using [KinD](https://kind.sigs.k8s.io/docs/user/quick-start/) for the sake of simplicity.
93+
94+
```bash
95+
$ arkade get kind --version=v0.10.0
96+
```
97+
98+
* kubectl v1.21.0
99+
100+
You can control your cluster using [kubectl](https://github.com/kubernetes/kubectl) CLI.
101+
102+
```bash
103+
$ arkade get kubectl --version=v1.21.0
104+
```
105+
106+
* ArgoCD CLI v2.0.0
107+
108+
ArgoCD CLI controls an Argo CD server. More detailed installation instructions can be found via
109+
the [CLI installation documentation](https://argoproj.github.io/argo-cd/cli_installation/). Fortunately, we can
110+
install it via arkade too.
111+
112+
```bash
113+
$ arkade get argocd --version=v2.0.0
114+
```
115+
116+
### Setup
117+
118+
### 1. Provision a local Kubernetes Cluster with KinD
119+
120+
You can start a Kubernetes cluster with KinD if you don't have one already.
121+
122+
```bash
123+
$ kind create cluster
124+
```
125+
126+
Verify if your cluster working properly before moving onto the next step.
127+
128+
```bash
129+
$ kubectl cluster-info
130+
Kubernetes control plane is running at https://127.0.0.1:49809
131+
KubeDNS is running at https://127.0.0.1:49809/api/v1/namespaces/kube-system/services/kube-dns:dns/proxy
132+
133+
To further debug and diagnose cluster problems, use 'kubectl cluster-info dump'.
134+
```
135+
136+
### 2. Deploy ArgoCD
137+
138+
There are various ways to install ArgoCD, one of them is _ArgoCD Operator_, and the other one is just with plain YAML
139+
manifest. We are going to deploy ArgoCD with plain YAML manifest in this section.
140+
141+
arkade is not only for the CLI tooling, it also helps you to get started to install applications using helm under the hood,
142+
hopefully arkade also supports installing ArgoCD.
143+
144+
```bash
145+
$ kubectl create namespace argocd
146+
$ arkade install argocd
147+
```
148+
149+
Verify if everything is working properly in _argocd_ namespace before moving onto the next step.
150+
151+
```bash
152+
$ kubectl get pods --namespace argocd
153+
NAME READY STATUS RESTARTS AGE
154+
argocd-application-controller-0 1/1 Running 0 86s
155+
argocd-dex-server-5dd657bd9-zkhb8 1/1 Running 0 86s
156+
argocd-redis-759b6bc7f4-92l4b 1/1 Running 0 86s
157+
argocd-repo-server-6c495f858f-rx8hh 1/1 Running 0 86s
158+
argocd-server-859b4b5578-sczvk 1/1 Running 0 86s
159+
```
160+
161+
### 3. Deploy OpenFaaS Operator and OpenFaaS functions through ArgoCD
162+
163+
There are two ways of defining applications to ArgoCD, one of them is by using CLI, the other one is by using CRDs. We
164+
are going to demonstrate both of them in here.
165+
166+
#### Option 1: by using CLI
167+
168+
First, we need to authenticate to ArgoCD server.Argo CD v1.9. Later the initial password for the admin account is
169+
auto-generated and stored as clear text in the field password in a secret named argocd-initial-admin-secret in your Argo
170+
CD installation namespace.
171+
172+
You can simply retrieve this password using kubectl:
173+
174+
```bash
175+
$ kubectl -n argocd get secret argocd-initial-admin-secret -o jsonpath="{.data.password}" | base64 -d && echo
176+
SyudUgAtDobmgSjM
177+
```
178+
179+
Because ArgoCD Server is running on a Kubernetes, we should do port-forwarding first in order to access the server, it
180+
can be achieved by the following command easily:
181+
182+
```bash
183+
$ kubectl port-forward svc/argocd-server -n argocd 8080:443
184+
Forwarding from 127.0.0.1:8080 -> 8080
185+
Forwarding from [::1]:8080 -> 8080
186+
```
187+
188+
After that, by using the username _admin_ and the password from above, lets log into ArgoCD:
189+
190+
```bash
191+
$ argocd login --name local localhost:8080
192+
WARNING: server certificate had error: x509: certificate signed by unknown authority. Proceed insecurely (y/n)? y
193+
Username: admin
194+
Password:
195+
'admin:login' logged in successfully
196+
Context 'local' updated
197+
```
198+
199+
To get more detail about login process, please refer to
200+
this [link](https://argoproj.github.io/argo-cd/getting_started/#4-login-using-the-cli).
201+
202+
Verify if you log into ArgoCD properly before moving on the next step.
203+
204+
```bash
205+
$ argocd account list
206+
NAME ENABLED CAPABILITIES
207+
admin true login
208+
209+
$ argocd app list
210+
NAME CLUSTER NAMESPACE PROJECT STATUS HEALTH SYNCPOLICY CONDITIONS REPO PATH TARGET
211+
212+
```
213+
214+
After you logged into ArgoCD, lets create our applications.
215+
216+
```bash
217+
$ kubectl create namespace openfaas
218+
namespace/openfaas created
219+
220+
$ kubectl create namespace openfaas-fn
221+
namespace/openfaas-fn created
222+
223+
$ argocd app create openfaas-operator \
224+
--repo https://github.com/openfaas/faas-netes.git \
225+
--dest-namespace openfaas \
226+
--dest-server https://kubernetes.default.svc \
227+
--path chart/openfaas \
228+
--helm-set operator.create=true \
229+
--helm-set generateBasicAuth=true \
230+
--helm-set functionNamespace=openfaas-fn \
231+
--self-heal \
232+
--sync-policy automatic
233+
application 'openfaas-operator' created
234+
```
235+
236+
> When deploying internally (to the same cluster that Argo CD is running in), https://kubernetes.default.svc should be used as the application's K8s API server address. To get more detail about registering another cluster to deploy apps to, please refer to this [link](https://argoproj.github.io/argo-cd/getting_started/#5-register-a-cluster-to-deploy-apps-to-optional).
237+
238+
Verify if everything is working before moving onto the next step.
239+
240+
First, check the application status:
241+
242+
```bash
243+
$ argocd app list -o wide
244+
NAME CLUSTER NAMESPACE PROJECT STATUS HEALTH SYNCPOLICY CONDITIONS REPO PATH TARGET
245+
openfaas-operator https://kubernetes.default.svc openfaas default Synced Healthy Auto <none> https://github.com/openfaas/faas-netes.git chart/openfaas
246+
```
247+
248+
Then, check the _openfaas_ namespace for the installation:
249+
250+
```bash
251+
$ kubectl get pods --namespace openfaas
252+
NAME READY STATUS RESTARTS AGE
253+
alertmanager-84d7b88f74-kt7jg 1/1 Running 0 4m6s
254+
basic-auth-plugin-85d885557c-cgz4j 1/1 Running 0 4m6s
255+
gateway-764b7b4865-p4rk8 2/2 Running 1 4m6s
256+
nats-5fdf6476f-pmftg 1/1 Running 0 4m6s
257+
prometheus-844fffb-5rkc7 1/1 Running 0 4m6s
258+
queue-worker-7cbc9f8688-qfww6 1/1 Running 0 4m6s
259+
```
260+
261+
Before deploying OpenFaaS functions as custom resources, check the available CRDs on the Kubernetes, you should see the
262+
list like the following:
263+
264+
```bash
265+
$ kubectl get customresourcedefinitions.apiextensions.k8s.io
266+
NAME CREATED AT
267+
applications.argoproj.io 2021-04-09T09:33:59Z
268+
appprojects.argoproj.io 2021-04-09T09:33:59Z
269+
functions.openfaas.com 2021-04-09T10:43:03Z
270+
profiles.openfaas.com 2021-04-09T10:43:03Z
271+
```
272+
273+
If you see the same output above, it means you are now ready to deploy OpenFaaS functions.
274+
275+
I prepared a repository that holds the function definitions, so, before running the following code, don't forget to fork
276+
your own copy of this repository and give it to _"--repo"_ flag.
277+
278+
```bash
279+
$ argocd app create openfaas-functions \
280+
--repo https://github.com/developer-guy/bring-gitops-to-your-openfaas-functions-with-argocd.git \
281+
--dest-server https://kubernetes.default.svc \
282+
--path functions \
283+
--self-heal \
284+
--sync-policy automatic
285+
application 'openfaas-functions' created
286+
```
287+
288+
Verify if everything is working before moving onto the next step.
289+
290+
First, check the application status, now, you should see two applications:
291+
292+
```bash
293+
$ argocd app list -o wide
294+
NAME CLUSTER NAMESPACE PROJECT STATUS HEALTH SYNCPOLICY CONDITIONS REPO PATH TARGET
295+
openfaas-functions https://kubernetes.default.svc default Synced Healthy Auto <none> https://github.com/developer-guy/bring-gitops-to-your-openfaas-functions-with-argocd.git functions
296+
openfaas-operator https://kubernetes.default.svc openfaas default Synced Healthy Auto <none> https://github.com/openfaas/faas-netes.git
297+
```
298+
299+
Then, check the _openfaas-fn_ namespace for the installation:
300+
301+
```bash
302+
$ kubectl get functions --namespace openfaas-fn
303+
NAME AGE
304+
nodeinfo 35s
305+
```
306+
307+
Verify if it is working.
308+
309+
```
310+
$ kubectl get pods --namespace openfaas-fn
311+
NAME READY STATUS RESTARTS AGE
312+
nodeinfo-6d5434f4744-l6kfd 1/1 Running 0 2m6s
313+
```
314+
315+
#### Option 2: by using CRDs
316+
317+
We are going to apply _**apps-of-apps**_ pattern in here, which means we can create an app that creates other apps,
318+
which in turn can create other apps. This allows you to declaratively manage a group of app that can be deployed and
319+
configured in concert. In order to do that, we create an _apps-of-apps.yaml_ in the repository and within this manifest
320+
we refer to the exact path which holds the actual application manifests.
321+
322+
To get more detail about _**apps-of-apps**_ pattern, please refer to
323+
this [link](https://argoproj.github.io/argo-cd/operator-manual/declarative-setup/#app-of-apps).
324+
325+
Lets deploy the applications.
326+
327+
```bash
328+
$ kubectl create namespace openfaas
329+
namespace/openfaas created
330+
331+
$ kubectl create namespace openfaas-fn
332+
namespace/openfaas-fn created
333+
334+
$ argocd app create apps-of-apps \
335+
--repo https://github.com/developer-guy/bring-gitops-to-your-openfaas-functions-with-argocd.git \
336+
--dest-server https://kubernetes.default.svc \
337+
--path . \
338+
--self-heal \
339+
--sync-policy automatic
340+
application 'apps-of-apps' created
341+
```
342+
343+
We just created one application called _apps-of-apps_ in here, but if you look at the output of the _list_ command, you
344+
should see three application:
345+
346+
```bash
347+
$ argocd app list
348+
NAME CLUSTER NAMESPACE PROJECT STATUS HEALTH SYNCPOLICY CONDITIONS REPO PATH TARGET
349+
apps-of-apps https://kubernetes.default.svc default OutOfSync Healthy Auto <none> https://github.com/developer-guy/bring-gitops-to-your-openfaas-functions-with-argocd.git applications
350+
openfaas-functions https://kubernetes.default.svc default Synced Healthy Auto <none> https://github.com/developer-guy/bring-gitops-to-your-openfaas-functions-with-argocd.git functions
351+
openfaas-operator https://kubernetes.default.svc openfaas default OutOfSync Missing Auto <none> https://github.com/openfaas/faas-netes.git chart/openfaas
352+
```
353+
354+
Verify if everything is working.
355+
356+
```bash
357+
$ kubectl get functions --namespace openfaas-fn
358+
NAME AGE
359+
nodeinfo 35s
360+
361+
$ kubectl get pods --namespace openfaas-fn
362+
NAME READY STATUS RESTARTS AGE
363+
nodeinfo-7c564f4744-l6kfd 1/1 Running 0 101s
364+
```
365+
366+
### Taking it further
367+
368+
### Join the community
369+
370+
Have you got questions, comments, or suggestions? Join the community on [Slack](https://slack.openfaas.io).
371+
372+
Would you like help to set up your OpenFaaS installation, or someone to call when things don't quite go to
373+
plan? [Our OpenFaaS PRO Subscription plan](https://www.openfaas.com/support/) gives you a say in the project roadmap, a
374+
support contact, and access to Enterprise-grade authentication with OIDC.
375+
376+
### Acknowledgements
377+
378+
* Special Thanks to [Alex Ellis](https://twitter.com/alexellisuk) for all guidance and for merging changes into OpenFaaS to better support this workflow.
379+
* Special Thanks to [Furkan Türkal](https://twitter.com/furkanturkaI) for all the support.
380+
381+
### References
382+
383+
* [Argo CD - Declarative GitOps CD for Kubernetes](https://argoproj.github.io/argo-cd/getting_started)
384+
* [Getting Started with the OpenFaaS Kubernetes Operator](https://dzone.com/articles/getting-started-with-the-openfaas-kubernetes-opera)
385+
* [Weaveworks' Guide To GitOps](https://www.weave.works/technologies/gitops/)
386+
* [GitOps](https://www.gitops.tech)
Loading

0 commit comments

Comments
 (0)