1. ArgoCD自动同步策略
自动同步策略允许ArgoCD在检测到GitRepo与实际状态之间存在差异时,自动启动同步操作.
Prune Resource(自动修剪):在集群上某个资源在GitRepo中找不到对应的配置时,自动删除集群上的该资源
Self Heal(自愈): 因各种原因(如手动修改)集群上资源的实时状态而导致与GitRepo不匹配时,自动将实际状态与GitRepo的期望状态同步.
- 自动同步仅发生在应用处于OutOfSync状态时,ArgoCD并不会对处于Synced或Error状态的Applicationzhix自动同步
- 对于GitRepo上的一次提交,自动同步仅会执行一次,除非同时启用Self-Heal机制.
- 启用了自动同步的Application不支持RollBack.
2. ArgoCD Sync Options
用于禁用或启用同步过程中的某些特性
- ApplyOutOfSyncOnly.仅对于那些OutOfSync状态的资源执行同步操作,可以加速同步过程
- PrunePropagationPolicy,资源修剪传播策略,默认使用foreground策略,还能选择background和orphan
- PruneLast,在同步操作的最后再执行修剪操作,即使它资源已经部署且转为健康状态后再进行Prue
- Replace,对资源的修改,以replace方式进行,而非默认的apply.先删除后创建,apply以补丁方式覆盖更新
- FailOnSharedResource,默认的同步操作不会考虑GitRepo中定义的资源是否已经被其他Application所使用.将该选项设置为true,意味着在发现资源已经被其他Application所使用时,则将同步状态设置为fail.当删除或修剪碰到共享资源时,将状态改为false,即不进行修改
- RespectIgnoreDifferences,在同步阶段忽略期望状态的字段
- CreateNamespace,创建缺失的名称空间
- Validation,是否执行资源规范格式的校验,相当于"kubectl apply --validate={true|false}" ,默认为true.
3. 通过Cli修改同步方式
将guestbook的同步方式设置为自动
# argocd app get guestbook
Name: argocd/guestbook
Project: default
Server: https://kubernetes.default.svc
Namespace: default
URL: https://argocd.intra.com/applications/guestbook
Repo: http://192.168.31.199/root/argocd-example-apps.git
Target:
Path: guestbook
SyncWindow: Sync Allowed
Sync Policy: <none> # 此处sync是none状态
Sync Status: Synced to (58982ea)
Health Status: Healthy
GROUP KIND NAMESPACE NAME STATUS HEALTH HOOK MESSAGE
Service default guestbook-ui Synced Healthy service/guestbook-ui created
apps Deployment default guestbook-ui Synced Healthy deployment.apps/guestbook-ui created
# argocd app set guestbook --sync-policy aut
通过命令行可以看到此时guestbook的同步方式已经变更为了自动
# argocd app get guestbook
Name: argocd/guestbook
Project: default
Server: https://kubernetes.default.svc
Namespace: default
URL: https://argocd.intra.com/applications/guestbook
Repo: http://192.168.31.199/root/argocd-example-apps.git
Target:
Path: guestbook
SyncWindow: Sync Allowed
Sync Policy: Automated
Sync Status: Synced to (58982ea)
Health Status: Healthy
GROUP KIND NAMESPACE NAME STATUS HEALTH HOOK MESSAGE
Service default guestbook-ui Synced Healthy service/guestbook-ui created
apps Deployment default guestbook-ui Synced Healthy deployment.apps/guestbook-ui created
自动修剪
argocd app set guestbook --auto-prune
自动修复
argocd app set guestbook --self-heal
禁止修剪特定的资源
metadata:
annotations:
argocd.argoproj.io/sync-options:Prunc=false
禁用kubectl验证
metadata:
annotations:
argocd.argoproj.io/sync-options:Validate=false
有选择的同步
argocd app set guestbook --sync-option ApplyOutOfSyncOnly=true
资源修剪传播策略
argocd app set guestbook --sync-option PrunePropagationPolicy={foreground|background|orphan}
是否同步完成后再进行修剪
argocd app set guestbook --sync-option PruneLast=true
是否replace资源而非执行apply
argocd app set guestbook --sync-option Replace={true|false}
若存在共享资源,是否将同步置为Fail
argocd app set guestbook --sync-option FailOnSharedResource={true|false}
是否忽略差异
argocd app set guestbook --sync-option RespectIgnoreDifferences={true|false}
是否自动创建命名空间
argocd app set guestbook --sync-option CreateNamespace={true|false}
4. ArgoCD CLI回滚
查看项目的历史版本
# argocd app history argocd/spring-boot-helloworld
ID DATE REVISION
0 2022-11-18 16:22:17 +0800 CST HEAD (d3f19ac)
1 2022-11-18 16:35:43 +0800 CST HEAD (bbf73a3)
2 2022-11-18 16:45:39 +0800 CST HEAD (b82bb4a)
回滚前需要先将sync-policy的自动关闭
# argocd app set argocd/spring-boot-helloworld --sync-policy none
# argocd app rollback argocd/spring-boot-helloworld --prune 1
TIMESTAMP GROUP KIND NAMESPACE NAME STATUS HEALTH HOOK MESSAGE
2022-11-21T12:20:49+08:00 Namespace helloworld Synced
2022-11-21T12:20:49+08:00 Service helloworld spring-boot-helloworld Synced Healthy
2022-11-21T12:20:49+08:00 apps Deployment helloworld spring-boot-helloworld Synced Healthy
2022-11-21T12:20:51+08:00 Namespace helloworld Synced namespace/helloworld unchanged
2022-11-21T12:20:51+08:00 Service helloworld spring-boot-helloworld Synced Healthy service/spring-boot-helloworld unchanged
2022-11-21T12:20:51+08:00 apps Deployment helloworld spring-boot-helloworld Synced Healthy deployment.apps/spring-boot-helloworld configured
2022-11-21T12:20:51+08:00 apps Deployment helloworld spring-boot-helloworld OutOfSync Progressing deployment.apps/spring-boot-helloworld configured
Name: argocd/spring-boot-helloworld
Project: default
Server: https://kubernetes.default.svc
Namespace:
URL: https://argocd.intra.com/applications/argocd/spring-boot-helloworld
Repo: http://192.168.31.199/root/spring-boot-helloworld-deployment.git
Target: HEAD
Path: kubernetes
SyncWindow: Sync Allowed
Sync Policy: <none>
Sync Status: OutOfSync from HEAD (b82bb4a)
Health Status: Progressing
Operation: Sync
Sync Revision: bbf73a31cb13c11dc9d82717119bc03df7aac040
Phase: Succeeded
Start: 2022-11-21 12:20:48 +0800 CST
Finished: 2022-11-21 12:20:51 +0800 CST
Duration: 3s
Message: successfully synced (all tasks run)
GROUP KIND NAMESPACE NAME STATUS HEALTH HOOK MESSAGE
Namespace helloworld Synced namespace/helloworld unchanged
Service helloworld spring-boot-helloworld Synced Healthy service/spring-boot-helloworld unchanged
apps Deployment helloworld spring-boot-helloworld OutOfSync Progressing deployment.apps/spring-boot-helloworld configured
此时同步状态就会显示OutOfSync
再将自动同步打开,此时又会被同步到最新状态
# argocd app set argocd/spring-boot-helloworld --sync-policy auto
5. ArgoCD上添加Application
argocd app create guestbook --repo http://192.168.31.199/root/spring-boot-helloWorld.git --path guestbook --dest-server https://kubernetes.default.svc --dest-namespace default
参数含义
参数 | 含义 |
---|---|
–repo | Git仓库Url |
–path | Git Repository中含有配置文件的子目录路径 |
–directory-recurse | 对目录进行递归 |
–revision string | 要使用revision通常是指源码branch,tag,commit和Helm chart版本 |
-f,–file string | 部署Application用到的配置文件路径或URL |
–release-name string | 配置为Helm Charts时,为其指定release的名称 |
–project string | 隶属于Project,默认为default |
–dest-server string | 目标K8s集群的API Server URL |
–dest-namespace | 目标名称空间 |
6. 将Repository添加到ArgoCD
一般私有仓库需要进行添加,公有仓库一般不需要添加
命令行添加
argocd repo add --password
管理GitRepo常用参数
参数 | 含义 |
---|---|
–name | 当前Repo的名称 |
–ssh-private-key-path | 用于访问GitRepo的SSH私钥文件路径 |
–insecure-ignore-host-key | 不校验host key |
–insecure-skip-server-verification | 不校验host key和server cerificate |
–username string | 用户名 |
–password string | 密码 |
–project string | Repo所属的Project |
–type string | Repo的类型 |
管理Cluster
argocd cluster add context-intra --kubeconfig=.kube/config
参数 | 含义 |
---|---|
–name | Cluster的名称 |
–in-cluster | ArgoCD自身运行在Kubernetes集群,访问地址为https://kubernetes.default.svc |
–kubeconfig string | 使用指定的kubeconfig文件 |
–namespace string | Array |
–project string | 所属的Project |
–service-account string | 使用的ServiceAccount |
7. 创建一个application
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
name: spring-boot-helloworld
namespace: argocd
spec:
project: default
source:
repoURL: http://192.168.31.199/root/spring-boot-helloworld-deployment.git
targetRevision: HEAD
path: kubernetes
destination:
server: https://kubernetes.default.svc
namespace: helloworld
syncPolicy:
automated:
prune: true # 是否修剪
selfHeal: true #是否自愈
allowEmpty: false # 是否允许空资源
syncOptions:
- Validate=false # 是否校验
- CreateNamespace=true # 是否自动创建命名空间
- PrunePropagationPolicy=foreground
- PruneLast=true # 增改后是否做Prun操作
retry: # 重试策略
limit: 5
backoff:
duration: 5s
factor: 2
maxDuration: 3m
删除原有app,然后新增spring-boot-helloworld app
# argocd app list
NAME CLUSTER NAMESPACE PROJECT STATUS HEALTH SYNCPOLICY CONDITIONS REPO PATH TARGET
argocd/guestbook https://kubernetes.default.svc default default Synced Healthy Auto <none> http://192.168.31.199/root/argocd-example-apps.git guestbook
argocd/spring-boot-helloworld https://kubernetes.default.svc default Synced Healthy Auto <none> http://192.168.31.199/root/spring-boot-helloworld-deployment.git kubernetes HEAD
# argocd app delete argocd/spring-boot-helloworld
Are you sure you want to delete 'argocd/spring-boot-helloworld' and all its resources? [y/n] y
application 'argocd/spring-boot-helloworld' deleted
# argocd app list
NAME CLUSTER NAMESPACE PROJECT STATUS HEALTH SYNCPOLICY CONDITIONS REPO PATH TARGET
argocd/guestbook https://kubernetes.default.svc default default Synced Healthy Auto <none> http://192.168.31.199/root/argocd-example-apps.git guestbook
# kubectl apply -f 01-application-helloworld.yaml
application.argoproj.io/spring-boot-helloworld created
8. 基于Project CRD创建项目
Project负责为Application提供逻辑分组.主要功能如下:
- 限制可以部署的内容(指定受信任的Git Source仓库)通过黑,白名单实现.
- 限制Application可以部署到的目标位置(指定目标Cluster和Namespace)
- 限制能够及不能够部署的对象类型
- 定义Project Role,从而为Application提供RBAC机制,以绑定到OIDC组成JWT Token
ArgoCD的默认项目
default Project由ArgoCD自动部署,它允许用户按需修改,但不能被删除
白名单方式
apiVersion: argoproj.io/v1alpha1
kind: AppProject
metadata:
name: default
namespace: argocd
spec:
clusterResourceWhitelist:
- group: "*"
kind: "*"
destinations:
- namespace: "*"
server: "*"
sourceRepos:
- "*"
黑名单
spec:
clusterResourceBlacklist:
9. ApplicationSet
ApplicationSet CRD用于定义可自动生成Application的模板,从而能够在monorepo(单个Repo中定义了多个ArgoCD Application)或多个Repo,以及跨大量Cluster的场景中自动化管理ArgoCD Application
ApplicationSet CRD需要同其专用的ApplicationSet控制器支撑实现
ApplicationSet可以提供
- 目标Cluster的模板化,从而能够在单个资源配置文件中适配部署到多个kubernetes集群
- 源Git配置仓库的模板化
- 较好地支持monorepo
ApplicationSet控制器负责生成Application,ApplicationSet控制器生成或更新Application资源
生成或更新Application资源是有Application控制器确保期望状态和实际状态的一致
ApplicationSet控制器仅负责确保ApplicationSet资源的期望状态与实际状态的一致
AS CRD资源定义–>AS控制器–>Apps CRD —> Application Controller -->目标集群上创建
9.2 ApplicationSet CRD资源规范
在ApplicationSet CRD的spec下可以定义以下三个字段
- generators
定义负责生成参数的生成器,这些参数会被用于template字段中定义的模板
生成器的关键作用在于,他们是模板参数的数据源
ApplicationSet支持多种不同类型的generator
- syncPolicy
资源同步策略,仅支持一个布尔类型字段preserverResourcesOnDeletion
- template
Application资源模板,配置格式与Application规范相同,但它包含有一些参数化的配置
通过将这些参数替换为generators生成的值,完成模板的实例化
9.3 ApplicationSet多环境适配
apiVersion: argoproj.io/v1alpha1
kind: ApplicationSet
metadata:
name: helloworld
namespace: argocd
spec:
generators:
- list:
elements:
- environment: dev
- environment: staging
- environment: prod
template:
metadata:
name: '{{environment}}-guestbook'
spec:
project: default
source:
repoURL: http://192.168.31.199/root/spring-boot-helloworld-deployment.git
targetRevision: HEAD
path: helloworld/{{environment}}
destination:
server: https://kubernetes.default.svc
namespace: '{{environment}}'
syncPolicy:
automated:
prune: true
selfHeal: true
allowEmpty: false
syncOptions:
- Validate=false
- CreateNamespace=true
- PrunePropagationPolicy=foreground
- PruneLast=true
retry:
limit: 5
backoff:
duration: 5s
factor: 2
maxDuration: 3m
syncPolicy:
preserveResourcesOnDeletion: false # 是否在资源删除是保留
部署
# kubectl apply -f 02-applicationset-demo.yaml
applicationset.argoproj.io/helloworld created
此时分别在3个命名空间完成创建
# kubectl get pods -n dev
NAME READY STATUS RESTARTS AGE
spring-boot-helloworld-78596987bc-pqtbv 1/1 Running 0 29s
# kubectl get pods -n prod
NAME READY STATUS RESTARTS AGE
spring-boot-helloworld-9fbc44457-5g8tt 1/1 Running 0 34s
spring-boot-helloworld-9fbc44457-jxcm2 1/1 Running 0 34s
spring-boot-helloworld-9fbc44457-s6jpj 1/1 Running 0 34s
# kubectl get pods -n staging
NAME READY STATUS RESTARTS AGE
spring-boot-helloworld-9fbc44457-pp74b 1/1 Running 0 39s
# argocd appset list
NAME NAMESPACE PROJECT SYNCPOLICY CONDITIONS REPO PATH TARGET
helloworld argocd default &ApplicationSetSyncPolicy{PreserveResourcesOnDeletion:false,} [{ParametersGenerated Successfully generated parameters for all Applications 2022-11-22 11:40:34 +0800 CST True ParametersGenerated} {ResourcesUpToDate ApplicationSet up to date 2022-11-22 11:40:34 +0800 CST True ApplicationSetUpToDate}] http://192.168.31.199/root/spring-boot-helloworld-deployment.git helloworld/{{environment}} HEAD
决定不同版本具体区别的是在git仓库helloworld/prod,helloworld/dev,helloworld/staging/下的配置
# cat prod/02-deployment.yaml
kind: Deployment
apiVersion: apps/v1
metadata:
name: spring-boot-helloworld
labels:
app: spring-boot-helloworld
spec:
replicas: 3
selector:
matchLabels:
app: spring-boot-helloworld
template:
metadata:
name: spring-boot-helloworld
labels:
app: spring-boot-helloworld
spec:
containers:
- name: spring-boot-helloworld
image: ikubernetes/spring-boot-helloworld:v0.8.0
ports:
- name: http
containerPort: 80
protocol: TCP
resources:
requests:
cpu: 50m
memory: 32Mi
# cat staging/02-deployment.yaml
kind: Deployment
apiVersion: apps/v1
metadata:
name: spring-boot-helloworld
labels:
app: spring-boot-helloworld
spec:
replicas: 1
selector:
matchLabels:
app: spring-boot-helloworld
template:
metadata:
name: spring-boot-helloworld
labels:
app: spring-boot-helloworld
spec:
containers:
- name: spring-boot-helloworld
image: ikubernetes/spring-boot-helloworld:v0.8.0
ports:
- name: http
containerPort: 80
protocol: TCP
resources:
requests:
cpu: 50m
memory: 32Mi