github.com/argoproj/argo-cd/v2@v2.10.9/docs/operator-manual/ingress.md (about) 1 # Ingress Configuration 2 3 Argo CD API server runs both a gRPC server (used by the CLI), as well as a HTTP/HTTPS server (used by the UI). 4 Both protocols are exposed by the argocd-server service object on the following ports: 5 6 * 443 - gRPC/HTTPS 7 * 80 - HTTP (redirects to HTTPS) 8 9 There are several ways how Ingress can be configured. 10 11 ## [Ambassador](https://www.getambassador.io/) 12 13 The Ambassador Edge Stack can be used as a Kubernetes ingress controller with [automatic TLS termination](https://www.getambassador.io/docs/latest/topics/running/tls/#host) and routing capabilities for both the CLI and the UI. 14 15 The API server should be run with TLS disabled. Edit the `argocd-server` deployment to add the `--insecure` flag to the argocd-server command, or simply set `server.insecure: "true"` in the `argocd-cmd-params-cm` ConfigMap [as described here](server-commands/additional-configuration-method.md). Given the `argocd` CLI includes the port number in the request `host` header, 2 Mappings are required. 16 17 ### Option 1: Mapping CRD for Host-based Routing 18 ```yaml 19 apiVersion: getambassador.io/v2 20 kind: Mapping 21 metadata: 22 name: argocd-server-ui 23 namespace: argocd 24 spec: 25 host: argocd.example.com 26 prefix: / 27 service: argocd-server:443 28 --- 29 apiVersion: getambassador.io/v2 30 kind: Mapping 31 metadata: 32 name: argocd-server-cli 33 namespace: argocd 34 spec: 35 # NOTE: the port must be ignored if you have strip_matching_host_port enabled on envoy 36 host: argocd.example.com:443 37 prefix: / 38 service: argocd-server:80 39 regex_headers: 40 Content-Type: "^application/grpc.*$" 41 grpc: true 42 ``` 43 44 Login with the `argocd` CLI: 45 46 ```shell 47 argocd login <host> 48 ``` 49 50 ### Option 2: Mapping CRD for Path-based Routing 51 52 The API server must be configured to be available under a non-root path (e.g. `/argo-cd`). Edit the `argocd-server` deployment to add the `--rootpath=/argo-cd` flag to the argocd-server command. 53 54 ```yaml 55 apiVersion: getambassador.io/v2 56 kind: Mapping 57 metadata: 58 name: argocd-server 59 namespace: argocd 60 spec: 61 prefix: /argo-cd 62 rewrite: /argo-cd 63 service: argocd-server:443 64 ``` 65 66 Login with the `argocd` CLI using the extra `--grpc-web-root-path` flag for non-root paths. 67 68 ```shell 69 argocd login <host>:<port> --grpc-web-root-path /argo-cd 70 ``` 71 72 ## [Contour](https://projectcontour.io/) 73 The Contour ingress controller can terminate TLS ingress traffic at the edge. 74 75 The Argo CD API server should be run with TLS disabled. Edit the `argocd-server` Deployment to add the `--insecure` flag to the argocd-server container command, or simply set `server.insecure: "true"` in the `argocd-cmd-params-cm` ConfigMap [as described here](server-commands/additional-configuration-method.md). 76 77 It is also possible to provide an internal-only ingress path and an external-only ingress path by deploying two instances of Contour: one behind a private-subnet LoadBalancer service and one behind a public-subnet LoadBalancer service. The private Contour deployment will pick up Ingresses annotated with `kubernetes.io/ingress.class: contour-internal` and the public Contour deployment will pick up Ingresses annotated with `kubernetes.io/ingress.class: contour-external`. 78 79 This provides the opportunity to deploy the Argo CD UI privately but still allow for SSO callbacks to succeed. 80 81 ### Private Argo CD UI with Multiple Ingress Objects and BYO Certificate 82 Since Contour Ingress supports only a single protocol per Ingress object, define three Ingress objects. One for private HTTP/HTTPS, one for private gRPC, and one for public HTTPS SSO callbacks. 83 84 Internal HTTP/HTTPS Ingress: 85 ```yaml 86 apiVersion: networking.k8s.io/v1 87 kind: Ingress 88 metadata: 89 name: argocd-server-http 90 annotations: 91 kubernetes.io/ingress.class: contour-internal 92 ingress.kubernetes.io/force-ssl-redirect: "true" 93 spec: 94 rules: 95 - host: internal.path.to.argocd.io 96 http: 97 paths: 98 - path: / 99 pathType: Prefix 100 backend: 101 service: 102 name: argocd-server 103 port: 104 name: http 105 tls: 106 - hosts: 107 - internal.path.to.argocd.io 108 secretName: your-certificate-name 109 ``` 110 111 Internal gRPC Ingress: 112 ```yaml 113 apiVersion: networking.k8s.io/v1 114 kind: Ingress 115 metadata: 116 name: argocd-server-grpc 117 annotations: 118 kubernetes.io/ingress.class: contour-internal 119 spec: 120 rules: 121 - host: grpc-internal.path.to.argocd.io 122 http: 123 paths: 124 - path: / 125 pathType: Prefix 126 backend: 127 service: 128 name: argocd-server 129 port: 130 name: https 131 tls: 132 - hosts: 133 - grpc-internal.path.to.argocd.io 134 secretName: your-certificate-name 135 ``` 136 137 External HTTPS SSO Callback Ingress: 138 ```yaml 139 apiVersion: networking.k8s.io/v1 140 kind: Ingress 141 metadata: 142 name: argocd-server-external-callback-http 143 annotations: 144 kubernetes.io/ingress.class: contour-external 145 ingress.kubernetes.io/force-ssl-redirect: "true" 146 spec: 147 rules: 148 - host: external.path.to.argocd.io 149 http: 150 paths: 151 - path: /api/dex/callback 152 pathType: Prefix 153 backend: 154 service: 155 name: argocd-server 156 port: 157 name: http 158 tls: 159 - hosts: 160 - external.path.to.argocd.io 161 secretName: your-certificate-name 162 ``` 163 164 The argocd-server Service needs to be annotated with `projectcontour.io/upstream-protocol.h2c: "https,443"` to wire up the gRPC protocol proxying. 165 166 The API server should then be run with TLS disabled. Edit the `argocd-server` deployment to add the 167 `--insecure` flag to the argocd-server command, or simply set `server.insecure: "true"` in the `argocd-cmd-params-cm` ConfigMap [as described here](server-commands/additional-configuration-method.md). 168 169 ## [kubernetes/ingress-nginx](https://github.com/kubernetes/ingress-nginx) 170 171 ### Option 1: SSL-Passthrough 172 173 Argo CD serves multiple protocols (gRPC/HTTPS) on the same port (443), this provides a 174 challenge when attempting to define a single nginx ingress object and rule for the argocd-service, 175 since the `nginx.ingress.kubernetes.io/backend-protocol` [annotation](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#backend-protocol) 176 accepts only a single value for the backend protocol (e.g. HTTP, HTTPS, GRPC, GRPCS). 177 178 In order to expose the Argo CD API server with a single ingress rule and hostname, the 179 `nginx.ingress.kubernetes.io/ssl-passthrough` [annotation](https://kubernetes.github.io/ingress-nginx/user-guide/nginx-configuration/annotations/#ssl-passthrough) 180 must be used to passthrough TLS connections and terminate TLS at the Argo CD API server. 181 182 ```yaml 183 apiVersion: networking.k8s.io/v1 184 kind: Ingress 185 metadata: 186 name: argocd-server-ingress 187 namespace: argocd 188 annotations: 189 nginx.ingress.kubernetes.io/force-ssl-redirect: "true" 190 nginx.ingress.kubernetes.io/ssl-passthrough: "true" 191 spec: 192 ingressClassName: nginx 193 rules: 194 - host: argocd.example.com 195 http: 196 paths: 197 - path: / 198 pathType: Prefix 199 backend: 200 service: 201 name: argocd-server 202 port: 203 name: https 204 ``` 205 206 The above rule terminates TLS at the Argo CD API server, which detects the protocol being used, 207 and responds appropriately. Note that the `nginx.ingress.kubernetes.io/ssl-passthrough` annotation 208 requires that the `--enable-ssl-passthrough` flag be added to the command line arguments to 209 `nginx-ingress-controller`. 210 211 #### SSL-Passthrough with cert-manager and Let's Encrypt 212 213 ```yaml 214 apiVersion: networking.k8s.io/v1 215 kind: Ingress 216 metadata: 217 name: argocd-server-ingress 218 namespace: argocd 219 annotations: 220 cert-manager.io/cluster-issuer: letsencrypt-prod 221 nginx.ingress.kubernetes.io/ssl-passthrough: "true" 222 # If you encounter a redirect loop or are getting a 307 response code 223 # then you need to force the nginx ingress to connect to the backend using HTTPS. 224 # 225 nginx.ingress.kubernetes.io/backend-protocol: "HTTPS" 226 spec: 227 ingressClassName: nginx 228 rules: 229 - host: argocd.example.com 230 http: 231 paths: 232 - path: / 233 pathType: Prefix 234 backend: 235 service: 236 name: argocd-server 237 port: 238 name: https 239 tls: 240 - hosts: 241 - argocd.example.com 242 secretName: argocd-server-tls # as expected by argocd-server 243 ``` 244 245 ### Option 2: SSL Termination at Ingress Controller 246 247 An alternative approach is to perform the SSL termination at the Ingress. Since an `ingress-nginx` Ingress supports only a single protocol per Ingress object, two Ingress objects need to be defined using the `nginx.ingress.kubernetes.io/backend-protocol` annotation, one for HTTP/HTTPS and the other for gRPC. 248 249 Each ingress will be for a different domain (`argocd.example.com` and `grpc.argocd.example.com`). This requires that the Ingress resources use different TLS `secretName`s to avoid unexpected behavior. 250 251 HTTP/HTTPS Ingress: 252 ```yaml 253 apiVersion: networking.k8s.io/v1 254 kind: Ingress 255 metadata: 256 name: argocd-server-http-ingress 257 namespace: argocd 258 annotations: 259 nginx.ingress.kubernetes.io/force-ssl-redirect: "true" 260 nginx.ingress.kubernetes.io/backend-protocol: "HTTP" 261 spec: 262 ingressClassName: nginx 263 rules: 264 - http: 265 paths: 266 - path: / 267 pathType: Prefix 268 backend: 269 service: 270 name: argocd-server 271 port: 272 name: http 273 host: argocd.example.com 274 tls: 275 - hosts: 276 - argocd.example.com 277 secretName: argocd-ingress-http 278 ``` 279 280 gRPC Ingress: 281 ```yaml 282 apiVersion: networking.k8s.io/v1 283 kind: Ingress 284 metadata: 285 name: argocd-server-grpc-ingress 286 namespace: argocd 287 annotations: 288 nginx.ingress.kubernetes.io/backend-protocol: "GRPC" 289 spec: 290 ingressClassName: nginx 291 rules: 292 - http: 293 paths: 294 - path: / 295 pathType: Prefix 296 backend: 297 service: 298 name: argocd-server 299 port: 300 name: https 301 host: grpc.argocd.example.com 302 tls: 303 - hosts: 304 - grpc.argocd.example.com 305 secretName: argocd-ingress-grpc 306 ``` 307 308 The API server should then be run with TLS disabled. Edit the `argocd-server` deployment to add the 309 `--insecure` flag to the argocd-server command, or simply set `server.insecure: "true"` in the `argocd-cmd-params-cm` ConfigMap [as described here](server-commands/additional-configuration-method.md). 310 311 The obvious disadvantage to this approach is that this technique requires two separate hostnames for 312 the API server -- one for gRPC and the other for HTTP/HTTPS. However it allows TLS termination to 313 happen at the ingress controller. 314 315 316 ## [Traefik (v2.2)](https://docs.traefik.io/) 317 318 Traefik can be used as an edge router and provide [TLS](https://docs.traefik.io/user-guides/grpc/) termination within the same deployment. 319 320 It currently has an advantage over NGINX in that it can terminate both TCP and HTTP connections _on the same port_ meaning you do not require multiple hosts or paths. 321 322 The API server should be run with TLS disabled. Edit the `argocd-server` deployment to add the `--insecure` flag to the argocd-server command or set `server.insecure: "true"` in the `argocd-cmd-params-cm` ConfigMap [as described here](server-commands/additional-configuration-method.md). 323 324 ### IngressRoute CRD 325 ```yaml 326 apiVersion: traefik.containo.us/v1alpha1 327 kind: IngressRoute 328 metadata: 329 name: argocd-server 330 namespace: argocd 331 spec: 332 entryPoints: 333 - websecure 334 routes: 335 - kind: Rule 336 match: Host(`argocd.example.com`) 337 priority: 10 338 services: 339 - name: argocd-server 340 port: 80 341 - kind: Rule 342 match: Host(`argocd.example.com`) && Headers(`Content-Type`, `application/grpc`) 343 priority: 11 344 services: 345 - name: argocd-server 346 port: 80 347 scheme: h2c 348 tls: 349 certResolver: default 350 ``` 351 352 ## AWS Application Load Balancers (ALBs) And Classic ELB (HTTP Mode) 353 AWS ALBs can be used as an L7 Load Balancer for both UI and gRPC traffic, whereas Classic ELBs and NLBs can be used as L4 Load Balancers for both. 354 355 When using an ALB, you'll want to create a second service for argocd-server. This is necessary because we need to tell the ALB to send the GRPC traffic to a different target group then the UI traffic, since the backend protocol is HTTP2 instead of HTTP1. 356 357 ```yaml 358 apiVersion: v1 359 kind: Service 360 metadata: 361 annotations: 362 alb.ingress.kubernetes.io/backend-protocol-version: HTTP2 #This tells AWS to send traffic from the ALB using HTTP2. Can use GRPC as well if you want to leverage GRPC specific features 363 labels: 364 app: argogrpc 365 name: argogrpc 366 namespace: argocd 367 spec: 368 ports: 369 - name: "443" 370 port: 443 371 protocol: TCP 372 targetPort: 8080 373 selector: 374 app.kubernetes.io/name: argocd-server 375 sessionAffinity: None 376 type: NodePort 377 ``` 378 379 Once we create this service, we can configure the Ingress to conditionally route all `application/grpc` traffic to the new HTTP2 backend, using the `alb.ingress.kubernetes.io/conditions` annotation, as seen below. Note: The value after the . in the condition annotation _must_ be the same name as the service that you want traffic to route to - and will be applied on any path with a matching serviceName. 380 381 ```yaml 382 apiVersion: networking.k8s.io/v1 383 kind: Ingress 384 metadata: 385 annotations: 386 alb.ingress.kubernetes.io/backend-protocol: HTTPS 387 # Use this annotation (which must match a service name) to route traffic to HTTP2 backends. 388 alb.ingress.kubernetes.io/conditions.argogrpc: | 389 [{"field":"http-header","httpHeaderConfig":{"httpHeaderName": "Content-Type", "values":["application/grpc"]}}] 390 alb.ingress.kubernetes.io/listen-ports: '[{"HTTPS":443}]' 391 name: argocd 392 namespace: argocd 393 spec: 394 rules: 395 - host: argocd.argoproj.io 396 http: 397 paths: 398 - path: / 399 backend: 400 service: 401 name: argogrpc 402 port: 403 number: 443 404 pathType: Prefix 405 - path: / 406 backend: 407 service: 408 name: argocd-server 409 port: 410 number: 443 411 pathType: Prefix 412 tls: 413 - hosts: 414 - argocd.argoproj.io 415 ``` 416 417 ## [Istio](https://www.istio.io) 418 You can put Argo CD behind Istio using following configurations. Here we will achive both serving Argo CD behind istio and using subpath on Istio 419 420 First we need to make sure that we can run Argo CD with subpath (ie /argocd). For this we have used install.yaml from argocd project as is 421 422 ```bash 423 curl -kLs -o install.yaml https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml 424 ``` 425 426 save following file as kustomization.yml 427 428 ```yaml 429 apiVersion: kustomize.config.k8s.io/v1beta1 430 kind: Kustomization 431 resources: 432 - ./install.yaml 433 434 patches: 435 - path: ./patch.yml 436 ``` 437 438 And following lines as patch.yml 439 440 ```yaml 441 # Use --insecure so Ingress can send traffic with HTTP 442 # --bashref /argocd is the subpath like https://IP/argocd 443 # env was added because of https://github.com/argoproj/argo-cd/issues/3572 error 444 --- 445 apiVersion: apps/v1 446 kind: Deployment 447 metadata: 448 name: argocd-server 449 spec: 450 template: 451 spec: 452 containers: 453 - args: 454 - /usr/local/bin/argocd-server 455 - --staticassets 456 - /shared/app 457 - --redis 458 - argocd-redis-ha-haproxy:6379 459 - --insecure 460 - --basehref 461 - /argocd 462 - --rootpath 463 - /argocd 464 name: argocd-server 465 env: 466 - name: ARGOCD_MAX_CONCURRENT_LOGIN_REQUESTS_COUNT 467 value: "0" 468 ``` 469 470 After that install Argo CD (there should be only 3 yml file defined above in current directory ) 471 472 ```bash 473 kubectl apply -k ./ -n argocd --wait=true 474 ``` 475 476 Be sure you create secret for Isito ( in our case secretname is argocd-server-tls on argocd Namespace). After that we create Istio Resources 477 478 ```yaml 479 apiVersion: networking.istio.io/v1alpha3 480 kind: Gateway 481 metadata: 482 name: argocd-gateway 483 namespace: argocd 484 spec: 485 selector: 486 istio: ingressgateway 487 servers: 488 - port: 489 number: 80 490 name: http 491 protocol: HTTP 492 hosts: 493 - "*" 494 tls: 495 httpsRedirect: true 496 - port: 497 number: 443 498 name: https 499 protocol: HTTPS 500 hosts: 501 - "*" 502 tls: 503 credentialName: argocd-server-tls 504 maxProtocolVersion: TLSV1_3 505 minProtocolVersion: TLSV1_2 506 mode: SIMPLE 507 cipherSuites: 508 - ECDHE-ECDSA-AES128-GCM-SHA256 509 - ECDHE-RSA-AES128-GCM-SHA256 510 - ECDHE-ECDSA-AES128-SHA 511 - AES128-GCM-SHA256 512 - AES128-SHA 513 - ECDHE-ECDSA-AES256-GCM-SHA384 514 - ECDHE-RSA-AES256-GCM-SHA384 515 - ECDHE-ECDSA-AES256-SHA 516 - AES256-GCM-SHA384 517 - AES256-SHA 518 --- 519 apiVersion: networking.istio.io/v1alpha3 520 kind: VirtualService 521 metadata: 522 name: argocd-virtualservice 523 namespace: argocd 524 spec: 525 hosts: 526 - "*" 527 gateways: 528 - argocd-gateway 529 http: 530 - match: 531 - uri: 532 prefix: /argocd 533 route: 534 - destination: 535 host: argocd-server 536 port: 537 number: 80 538 ``` 539 540 And now we can browse http://{{ IP }}/argocd (it will be rewritten to https://{{ IP }}/argocd 541 542 543 ## Google Cloud load balancers with Kubernetes Ingress 544 545 You can make use of the integration of GKE with Google Cloud to deploy Load Balancers using just Kubernetes objects. 546 547 For this we will need these five objects: 548 - A Service 549 - A BackendConfig 550 - A FrontendConfig 551 - A secret with your SSL certificate 552 - An Ingress for GKE 553 554 If you need detail for all the options available for these Google integrations, you can check the [Google docs on configuring Ingress features](https://cloud.google.com/kubernetes-engine/docs/how-to/ingress-features) 555 556 ### Disable internal TLS 557 558 First, to avoid internal redirection loops from HTTP to HTTPS, the API server should be run with TLS disabled. 559 560 Edit the `--insecure` flag in the `argocd-server` command of the argocd-server deployment, or simply set `server.insecure: "true"` in the `argocd-cmd-params-cm` ConfigMap [as described here](server-commands/additional-configuration-method.md). 561 562 ### Creating a service 563 564 Now you need an externally accessible service. This is practically the same as the internal service Argo CD has, but with Google Cloud annotations. Note that this service is annotated to use a [Network Endpoint Group](https://cloud.google.com/load-balancing/docs/negs) (NEG) to allow your load balancer to send traffic directly to your pods without using kube-proxy, so remove the `neg` annotation it that's not what you want. 565 566 The service: 567 568 ```yaml 569 apiVersion: v1 570 kind: Service 571 metadata: 572 name: argocd-server 573 namespace: argocd 574 annotations: 575 cloud.google.com/neg: '{"ingress": true}' 576 cloud.google.com/backend-config: '{"ports": {"http":"argocd-backend-config"}}' 577 spec: 578 type: ClusterIP 579 ports: 580 - name: http 581 port: 80 582 protocol: TCP 583 targetPort: 8080 584 selector: 585 app.kubernetes.io/name: argocd-server 586 ``` 587 588 ### Creating a BackendConfig 589 590 See that previous service referencing a backend config called `argocd-backend-config`? So lets deploy it using this yaml: 591 592 ```yaml 593 apiVersion: cloud.google.com/v1 594 kind: BackendConfig 595 metadata: 596 name: argocd-backend-config 597 namespace: argocd 598 spec: 599 healthCheck: 600 checkIntervalSec: 30 601 timeoutSec: 5 602 healthyThreshold: 1 603 unhealthyThreshold: 2 604 type: HTTP 605 requestPath: /healthz 606 port: 8080 607 ``` 608 609 It uses the same health check as the pods. 610 611 ### Creating a FrontendConfig 612 613 Now we can deploy a frontend config with an HTTP to HTTPS redirect: 614 615 ```yaml 616 apiVersion: networking.gke.io/v1beta1 617 kind: FrontendConfig 618 metadata: 619 name: argocd-frontend-config 620 namespace: argocd 621 spec: 622 redirectToHttps: 623 enabled: true 624 ``` 625 626 --- 627 !!! note 628 629 The next two steps (the certificate secret and the Ingress) are described supposing that you manage the certificate yourself, and you have the certificate and key files for it. In the case that your certificate is Google-managed, fix the next two steps using the [guide to use a Google-managed SSL certificate](https://cloud.google.com/kubernetes-engine/docs/how-to/managed-certs#creating_an_ingress_with_a_google-managed_certificate). 630 631 --- 632 633 ### Creating a certificate secret 634 635 We need now to create a secret with the SSL certificate we want in our load balancer. It's as easy as executing this command on the path you have your certificate keys stored: 636 637 ``` 638 kubectl -n argocd create secret tls secret-yourdomain-com \ 639 --cert cert-file.crt --key key-file.key 640 ``` 641 642 ### Creating an Ingress 643 644 And finally, to top it all, our Ingress. Note the reference to our frontend config, the service, and to the certificate secret. 645 646 --- 647 !!! note 648 649 GKE clusters running versions earlier than `1.21.3-gke.1600`, [the only supported value for the pathType field](https://cloud.google.com/kubernetes-engine/docs/how-to/load-balance-ingress#creating_an_ingress) is `ImplementationSpecific`. So you must check your GKE cluster's version. You need to use different YAML depending on the version. 650 651 --- 652 653 If you use the version earlier than `1.21.3-gke.1600`, you should use the following Ingress resource: 654 ```yaml 655 apiVersion: networking.k8s.io/v1 656 kind: Ingress 657 metadata: 658 name: argocd 659 namespace: argocd 660 annotations: 661 networking.gke.io/v1beta1.FrontendConfig: argocd-frontend-config 662 spec: 663 tls: 664 - secretName: secret-example-com 665 rules: 666 - host: argocd.example.com 667 http: 668 paths: 669 - pathType: ImplementationSpecific 670 path: "/*" # "*" is needed. Without this, the UI Javascript and CSS will not load properly 671 backend: 672 service: 673 name: argocd-server 674 port: 675 number: 80 676 ``` 677 678 If you use the version `1.21.3-gke.1600` or later, you should use the following Ingress resource: 679 ```yaml 680 apiVersion: networking.k8s.io/v1 681 kind: Ingress 682 metadata: 683 name: argocd 684 namespace: argocd 685 annotations: 686 networking.gke.io/v1beta1.FrontendConfig: argocd-frontend-config 687 spec: 688 tls: 689 - secretName: secret-example-com 690 rules: 691 - host: argocd.example.com 692 http: 693 paths: 694 - pathType: Prefix 695 path: "/" 696 backend: 697 service: 698 name: argocd-server 699 port: 700 number: 80 701 ``` 702 703 As you may know already, it can take some minutes to deploy the load balancer and become ready to accept connections. Once it's ready, get the public IP address for your Load Balancer, go to your DNS server (Google or third party) and point your domain or subdomain (i.e. argocd.example.com) to that IP address. 704 705 You can get that IP address describing the Ingress object like this: 706 707 ``` 708 kubectl -n argocd describe ingresses argocd | grep Address 709 ``` 710 711 Once the DNS change is propagated, you're ready to use Argo with your Google Cloud Load Balancer 712 713 ## Authenticating through multiple layers of authenticating reverse proxies 714 715 Argo CD endpoints may be protected by one or more reverse proxies layers, in that case, you can provide additional headers through the `argocd` CLI `--header` parameter to authenticate through those layers. 716 717 ```shell 718 $ argocd login <host>:<port> --header 'x-token1:foo' --header 'x-token2:bar' # can be repeated multiple times 719 $ argocd login <host>:<port> --header 'x-token1:foo,x-token2:bar' # headers can also be comma separated 720 ``` 721 ## ArgoCD Server and UI Root Path (v1.5.3) 722 723 Argo CD server and UI can be configured to be available under a non-root path (e.g. `/argo-cd`). 724 To do this, add the `--rootpath` flag into the `argocd-server` deployment command: 725 726 ```yaml 727 spec: 728 template: 729 spec: 730 name: argocd-server 731 containers: 732 - command: 733 - /argocd-server 734 - --repo-server 735 - argocd-repo-server:8081 736 - --rootpath 737 - /argo-cd 738 ``` 739 NOTE: The flag `--rootpath` changes both API Server and UI base URL. 740 Example nginx.conf: 741 742 ``` 743 worker_processes 1; 744 745 events { worker_connections 1024; } 746 747 http { 748 749 sendfile on; 750 751 server { 752 listen 443; 753 754 location /argo-cd/ { 755 proxy_pass https://localhost:8080/argo-cd/; 756 proxy_redirect off; 757 proxy_set_header Host $host; 758 proxy_set_header X-Real-IP $remote_addr; 759 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 760 proxy_set_header X-Forwarded-Host $server_name; 761 # buffering should be disabled for api/v1/stream/applications to support chunked response 762 proxy_buffering off; 763 } 764 } 765 } 766 ``` 767 Flag ```--grpc-web-root-path ``` is used to provide a non-root path (e.g. /argo-cd) 768 769 ```shell 770 $ argocd login <host>:<port> --grpc-web-root-path /argo-cd 771 ``` 772 773 ## UI Base Path 774 775 If the Argo CD UI is available under a non-root path (e.g. `/argo-cd` instead of `/`) then the UI path should be configured in the API server. 776 To configure the UI path add the `--basehref` flag into the `argocd-server` deployment command: 777 778 ```yaml 779 spec: 780 template: 781 spec: 782 name: argocd-server 783 containers: 784 - command: 785 - /argocd-server 786 - --repo-server 787 - argocd-repo-server:8081 788 - --basehref 789 - /argo-cd 790 ``` 791 792 NOTE: The flag `--basehref` only changes the UI base URL. The API server will keep using the `/` path so you need to add a URL rewrite rule to the proxy config. 793 Example nginx.conf with URL rewrite: 794 795 ``` 796 worker_processes 1; 797 798 events { worker_connections 1024; } 799 800 http { 801 802 sendfile on; 803 804 server { 805 listen 443; 806 807 location /argo-cd { 808 rewrite /argo-cd/(.*) /$1 break; 809 proxy_pass https://localhost:8080; 810 proxy_redirect off; 811 proxy_set_header Host $host; 812 proxy_set_header X-Real-IP $remote_addr; 813 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 814 proxy_set_header X-Forwarded-Host $server_name; 815 # buffering should be disabled for api/v1/stream/applications to support chunked response 816 proxy_buffering off; 817 } 818 } 819 } 820 ```