在 GKE 上設定 Elastic Stack


本教學課程說明如何使用 Elastic Cloud on Kubernetes (ECK) 運算子,在 GKE 上執行 Elastic Stack

Elastic Stack 是熱門的開放原始碼解決方案,可用於記錄、監控及即時分析資料。在 GKE 上使用 Elastic Stack,即可享有 GKE Autopilot 提供的擴充性和可靠性,以及強大的 Elastic Stack 功能。

本教學課程適用於 Kubernetes 管理員或網站可靠性工程師。

目標

  • 建立 GKE 叢集。
  • 部署 ECK 運算子。
  • 使用 ECK 運算子設定 Elasticsearch 叢集和 Kibana。
  • 使用 ECK 運算子部署完整的 Elastic Stack。
  • 自動調度 Elasticsearch 叢集資源,並升級 Elastic Stack 部署作業。
  • 使用 Elastic Stack 監控 Kubernetes 環境。

費用

在本文件中,您會使用 Google Cloud的下列計費元件:

如要根據預測用量估算費用,請使用 Pricing Calculator

初次使用 Google Cloud 的使用者可能符合免費試用資格。

完成本文所述工作後,您可以刪除已建立的資源,避免繼續計費。詳情請參閱清除所用資源一節。

事前準備

  1. Sign in to your Google Cloud account. If you're new to Google Cloud, create an account to evaluate how our products perform in real-world scenarios. New customers also get $300 in free credits to run, test, and deploy workloads.
  2. Install the Google Cloud CLI.

  3. If you're using an external identity provider (IdP), you must first sign in to the gcloud CLI with your federated identity.

  4. To initialize the gcloud CLI, run the following command:

    gcloud init
  5. Create or select a Google Cloud project.

    • Create a Google Cloud project:

      gcloud projects create PROJECT_ID

      Replace PROJECT_ID with a name for the Google Cloud project you are creating.

    • Select the Google Cloud project that you created:

      gcloud config set project PROJECT_ID

      Replace PROJECT_ID with your Google Cloud project name.

  6. Make sure that billing is enabled for your Google Cloud project.

  7. Enable the GKE API:

    gcloud services enable container.googleapis.com
  8. Install the Google Cloud CLI.

  9. If you're using an external identity provider (IdP), you must first sign in to the gcloud CLI with your federated identity.

  10. To initialize the gcloud CLI, run the following command:

    gcloud init
  11. Create or select a Google Cloud project.

    • Create a Google Cloud project:

      gcloud projects create PROJECT_ID

      Replace PROJECT_ID with a name for the Google Cloud project you are creating.

    • Select the Google Cloud project that you created:

      gcloud config set project PROJECT_ID

      Replace PROJECT_ID with your Google Cloud project name.

  12. Make sure that billing is enabled for your Google Cloud project.

  13. Enable the GKE API:

    gcloud services enable container.googleapis.com
  14. Grant roles to your user account. Run the following command once for each of the following IAM roles: roles/container.clusterAdmin

    gcloud projects add-iam-policy-binding PROJECT_ID --member="user:USER_IDENTIFIER" --role=ROLE
    • Replace PROJECT_ID with your project ID.
    • Replace USER_IDENTIFIER with the identifier for your user account. For example, user:myemail@example.com.

    • Replace ROLE with each individual role.
    • 您必須擁有網域名稱,網域名稱的長度不得超過 63 個字元。您可以使用 Cloud Domains 或其他註冊商。

準備環境

在本教學課程中,您將使用 Cloud Shell 管理託管在 Google Cloud上的資源。Cloud Shell 已預先安裝本教學課程所需的軟體,包括 kubectlHelmgcloud CLI

如要使用 Cloud Shell 設定環境,請按照下列步驟操作:

  1. 在 Google Cloud 控制台中,按一下Cloud Shell 啟用圖示Google Cloud 控制台中的「啟用 Cloud Shell」,即可啟動 Cloud Shell 工作階段。系統會在 Google Cloud 控制台的底部窗格啟動工作階段。

  2. 新增並更新 Helm 資訊套件存放區:

    helm repo add elastic https://helm.elastic.co
    helm repo update
    
  3. 複製 GitHub 存放區:

    git clone https://github.com/GoogleCloudPlatform/kubernetes-engine-samples.git
    
  4. 變更為工作目錄:

    cd kubernetes-engine-samples/observability/elastic-stack-tutorial
    

建立 GKE 叢集

建立 GKE 叢集,並啟用控制層指標收集功能:

gcloud container clusters create-auto elk-stack \
    --location="us-central1" \
    --monitoring="SYSTEM,WORKLOAD,API_SERVER,SCHEDULER,CONTROLLER_MANAGER"

部署 ECK 運算子

Elastic Cloud on Kubernetes (ECK) 平台可在 Kubernetes 叢集上部署及管理 Elastic Stack。

ECK 可自動部署及管理 Elastic Stack 叢集,簡化在 Kubernetes 上設定及維護 Elastic Stack 的程序。這項服務提供一組 Kubernetes 自訂資源,可用於在 Kubernetes 中建立及設定 Elasticsearch、Kibana、應用程式效能管理伺服器和其他 Elastic Stack 元件。開發人員和 DevOps 團隊可藉此大規模設定及管理 Elastic Stack 叢集。

ECK 支援多個 Elasticsearch 節點、自動應用程式容錯移轉、無縫升級和 SSL 加密。ECK 也提供相關功能,可監控及排解 Elasticsearch 效能問題。

  1. 安裝 ECK Helm 資訊套件:

    helm upgrade --install "elastic-operator" "elastic/eck-operator" \
        --version="2.8.0" \
        --create-namespace \
        --namespace="elastic-system" \
        --set="resources.limits.cpu=250m" \
        --set="resources.limits.memory=512Mi" \
        --set="resources.limits.ephemeral-storage=1Gi" \
        --set="resources.requests.cpu=250m" \
        --set="resources.requests.memory=512Mi" \
        --set="resources.requests.ephemeral-storage=1Gi"
    
  2. 等待運算子準備就緒:

    watch kubectl get pods -n elastic-system
    

    輸出結果會與下列內容相似:

    NAME                 READY   STATUS    RESTARTS   AGE
    elastic-operator-0   1/1     Running   0          31s    
    

    如果運算子為 STATUS,請按 Ctrl+C 返回指令列。Running

使用 ECK 設定 Elastic Stack

使用 Elastic Stack (包含 Elasticsearch、Kibana 和以 Fleet 模式運作的 Elastic Agent),即可設定功能強大、可擴充且全代管的解決方案,透過 Kibana 管理及視覺化資料。

Kibana 是一項開放原始碼的資料分析和視覺化工具,可讓您在 Elasticsearch 中搜尋、分析及以視覺化方式呈現資料。

Elastic Agent 是一種輕量型資料傳送程式,可從記錄或指標等不同來源收集資料,並自動傳送至 Elasticsearch。

彈性車隊是一種作業模式,其中彈性代理程式會向中央車隊伺服器回報,由該伺服器處理代理程式的設定和管理作業。機群伺服器可簡化 Elastic 代理程式的部署、設定和資源調度作業,方便您管理大型複雜的部署作業。

Elasticsearch 自動調度資源是一項自我監控功能,可根據運算子定義的政策,在需要額外資源時回報。舉例來說,政策可能會指定某個層級應根據可用磁碟空間進行調整。Elasticsearch 可以監控磁碟空間,並在預測空間不足時建議擴充,但仍須由運算子新增必要資源。如要進一步瞭解 Elasticsearch 自動調度資源,請參閱 Elasticsearch 說明文件的「自動調度資源」一節。

設定 Elasticsearch 叢集

Elasticsearch 提供分散式 RESTful 搜尋和分析引擎,可快速有效率地儲存及搜尋大量資料。

在 Kubernetes 上部署 Elastic Stack 時,您應管理 VM 設定,特別是 Elasticsearch 要求的 vm.max_map_count settingvm.max_map_count 指定程序可分配給檔案的記憶體區域數量。Elasticsearch 必須將此值設為至少 262144,才能以最佳狀態執行。詳情請參閱 ECK 說明文件中的「虛擬記憶體」。

  1. 請查看下列資訊清單:

    apiVersion: scheduling.k8s.io/v1
    kind: PriorityClass
    metadata:
      name: user-daemonset-priority
    value: 999999999
    preemptionPolicy: PreemptLowerPriority
    globalDefault: false
    description: "User DaemonSet priority"

    這個資訊清單說明的 DaemonSet 會直接在主機上設定核心設定。DaemonSet 是 Kubernetes 控制器,可確保 Pod 副本在叢集的每個節點上執行。

    上述資訊清單位於允許清單中,可在 Autopilot 上執行。請勿修改這份資訊清單,包括容器圖片。

  2. 將這個資訊清單套用至叢集:

    kubectl apply -f max-map-count-setter-ds.yaml
    
  3. 請查看下列資訊清單:

    apiVersion: elasticsearch.k8s.elastic.co/v1
    kind: Elasticsearch
    metadata:
      name: elasticsearch
      namespace: elastic-system
    spec:
      version: "8.9.0"
      volumeClaimDeletePolicy: DeleteOnScaledownOnly
      podDisruptionBudget:
        spec:
          minAvailable: 2
          selector:
            matchLabels:
              elasticsearch.k8s.elastic.co/cluster-name: elasticsearch
      nodeSets:
        - name: default
          config:
            node.roles: ["master", "data", "ingest", "ml", "remote_cluster_client"]
          podTemplate:
            metadata:
              labels:
                app.kubernetes.io/name: elasticsearch
                app.kubernetes.io/version: "8.9.0"
                app.kubernetes.io/component: "elasticsearch"
                app.kubernetes.io/part-of: "elk"
            spec:
              nodeSelector:
                cloud.google.com/compute-class: "Balanced"
              initContainers:
                - name: max-map-count-check
                  command:
                    - sh
                    - -c
                    - while true; do mmc=$(cat /proc/sys/vm/max_map_count); if test ${mmc} -eq 262144; then exit 0; fi; sleep 1; done
                  resources:
                    requests:
                      cpu: 10m
                      memory: 16Mi
                      ephemeral-storage: 16Mi
                    limits:
                      cpu: 10m
                      memory: 16Mi
                      ephemeral-storage: 16Mi
              containers:
                - name: elasticsearch
                  resources:
                    requests:
                      cpu: 990m
                      memory: 4080Mi
                      ephemeral-storage: 1008Mi
                    limits:
                      cpu: 1000m
                      memory: 4080Mi
                      ephemeral-storage: 1008Mi
                  env:
                    - name: ES_JAVA_OPTS
                      value: "-Xms2g -Xmx2g"
          count: 3
          volumeClaimTemplates:
            - metadata:
                name: elasticsearch-data # Do not change this name unless you set up a volume mount for the data path.
              spec:
                accessModes:
                  - ReadWriteOnce
                resources:
                  requests:
                    storage: 2Gi
                storageClassName: standard-rwo

    這個資訊清單會定義 Elasticsearch 叢集,並包含下列欄位:

    • initContainers:等待虛擬記憶體主機的 Kernel 設定變更。
    • podDisruptionBudget:指定叢集不會在 Pod 重整程序期間遭到毀損。
    • config.node.roles:Elasticsearch 節點角色設定。如要進一步瞭解節點角色,請參閱 Elasticsearch 說明文件中的「節點」。
  4. 將這個資訊清單套用至叢集:

    kubectl apply -f elasticsearch.yaml
    
  5. 等待 Elasticsearch 叢集準備就緒:

    watch kubectl --namespace elastic-system get elasticsearches.elasticsearch.k8s.elastic.co
    

    輸出結果會與下列內容相似:

    NAME            HEALTH   NODES   VERSION   PHASE   AGE
    elasticsearch   green    3       8.8.0     Ready   5m3s
    

    當 Elasticsearch 叢集 HEALTHgreenPHASEReady 時,請按下 Ctrl+C 返回指令列。

設定 Kibana

  1. 請查看下列資訊清單:

    apiVersion: kibana.k8s.elastic.co/v1
    kind: Kibana
    metadata:
      name: kibana
      namespace: elastic-system
    spec:
      version: "8.9.0"
      count: 1
      elasticsearchRef:
        name: elasticsearch
        namespace: elastic-system
      http:
        tls:
          selfSignedCertificate:
            disabled: true
      config:
        server.publicBaseUrl: https://elk.BASE_DOMAIN
        xpack.reporting.kibanaServer.port: 5601
        xpack.reporting.kibanaServer.protocol: http
        xpack.reporting.kibanaServer.hostname: kibana-kb-http.elastic-system.svc
        xpack.fleet.agents.elasticsearch.hosts: ["https://elasticsearch-es-http.elastic-system.svc:9200"]
        xpack.fleet.agents.fleet_server.hosts: ["https://fleet-server-agent-http.elastic-system.svc:8220"]
        xpack.fleet.packages:
        - name: system
          version: latest
        - name: elastic_agent
          version: latest
        - name: fleet_server
          version: latest
        - name: kubernetes
          version: latest
        xpack.fleet.agentPolicies:
        - name: Fleet Server on ECK policy
          id: eck-fleet-server
          namespace: default
          monitoring_enabled:
          - logs
          - metrics
          unenroll_timeout: 900
          package_policies:
          - name: fleet_server-1
            id: fleet_server-1
            package:
              name: fleet_server
        - name: Elastic Agent on ECK policy
          id: eck-agent
          namespace: default
          monitoring_enabled:
          - logs
          - metrics
          unenroll_timeout: 900
          package_policies:
          - package:
              name: system
            name: system-1
          - package:
              name: kubernetes
            name: kubernetes-1
      podTemplate:
        metadata:
          labels:
            app.kubernetes.io/name: kibana
            app.kubernetes.io/version: "8.9.0"
            app.kubernetes.io/component: "ui"
            app.kubernetes.io/part-of: "elk"
        spec:
          containers:
          - name: kibana
            resources:
              requests:
                memory: 1Gi
                cpu: 500m
                ephemeral-storage: 1Gi
              limits:
                memory: 1Gi
                cpu: 500m
                ephemeral-storage: 1Gi

    這個資訊清單說明 Kibana 自訂資源,可為 Fleet 伺服器和代理程式設定代理程式政策。

  2. 將這個資訊清單套用至叢集:

    kubectl apply -f kibana.yaml
    
  3. 等待 Pod 準備就緒:

    watch kubectl --namespace elastic-system get kibanas.kibana.k8s.elastic.co
    

    輸出結果會與下列內容相似:

    NAME     HEALTH   NODES   VERSION   AGE
    kibana   green    1       8.8.0     6m47s
    

    當 Pods HEALTHgreen 時,請按下 Ctrl+C 返回指令列。

設定負載平衡器以存取 Kibana

如要存取 Kibana,請建立 Kubernetes Ingress 物件、Google 管理的憑證、全域 IP 位址和 DNS 區域。

  1. 建立全域外部 IP 位址:

    gcloud compute addresses create "elastic-stack" --global
    
  2. 在 Cloud DNS 中建立代管區域和記錄集:

    gcloud dns managed-zones create "elk" \
        --description="DNS Zone for Airflow" \
        --dns-name="elk.BASE_DOMAIN" \
        --visibility="public"
    
    gcloud dns record-sets create "elk.BASE_DOMAIN" \
        --rrdatas="$(gcloud compute addresses describe "elastic-stack" --global --format="value(address)")" \
        --ttl="300" \
        --type="A" \
        --zone="elk"
    
  3. 建立含有名稱伺服器清單的 NS 記錄集,將 DNS 區域委派為基礎網域的子網域。您可以使用下列指令取得名稱伺服器清單:

    gcloud dns record-sets describe elk.BASE_DOMAIN \
        --type="NS" \
        --zone="elk" \
        --format="value(DATA)"
    
  4. 請查看下列資訊清單:

    apiVersion: networking.gke.io/v1
    kind: ManagedCertificate
    metadata:
      name: elastic-stack
      namespace: elastic-system
    spec:
      domains:
        - elk.BASE_DOMAIN

    這個資訊清單說明 ManagedCertificate,該憑證會佈建 SSL 憑證來建立 TLS 連線。

  5. 將資訊清單套用至叢集:

    kubectl apply -f ingress.yaml
    

設定 Elastic Agent

  1. 請查看下列資訊清單:

    apiVersion: agent.k8s.elastic.co/v1alpha1
    kind: Agent
    metadata:
      name: fleet-server
      namespace: elastic-system
    spec:
      version: 8.9.0
      kibanaRef:
        name: kibana
        namespace: elastic-system
      elasticsearchRefs:
        - name: elasticsearch
          namespace: elastic-system
      mode: fleet
      fleetServerEnabled: true
      policyID: eck-fleet-server
      deployment:
        replicas: 1
        podTemplate:
          metadata:
            labels:
              app.kubernetes.io/name: fleet-server
              app.kubernetes.io/version: "8.9.0"
              app.kubernetes.io/component: "agent"
              app.kubernetes.io/part-of: "elk"
          spec:
            containers:
              - name: agent
                resources:
                  requests:
                    memory: 512Mi
                    cpu: 250m
                    ephemeral-storage: 10Gi
                  limits:
                    memory: 512Mi
                    cpu: 250m
                    ephemeral-storage: 10Gi
            volumes:
              - name: "agent-data"
                ephemeral:
                  volumeClaimTemplate:
                    spec:
                      accessModes: ["ReadWriteOnce"]
                      storageClassName: "standard-rwo"
                      resources:
                        requests:
                          storage: 10Gi
            serviceAccountName: fleet-server
            automountServiceAccountToken: true
            securityContext:
              runAsUser: 0

    這個資訊清單說明 Elastic Agent,可使用 ECK 設定叢集伺服器。

  2. 將這個資訊清單套用至叢集:

    kubectl apply -f fleet-server-and-agents.yaml
    
  3. 等待 Pod 準備就緒:

    watch kubectl --namespace elastic-system get agents.agent.k8s.elastic.co
    

    輸出結果會與下列內容相似:

    NAME            HEALTH   AVAILABLE   EXPECTED   VERSION   AGE
    elastic-agent   green    5           5          8.8.0     14m
    fleet-server    green    1           1          8.8.0     16m
    

    當 Pod HEALTHgreen 時,請按下 Ctrl+C 返回指令列。

設定記錄和監控功能

Elastic Stack 可以使用 kube-state-metrics 匯出工具收集叢集層級指標。

  1. 安裝 kube-state-metrics:

    helm repo add prometheus-community https://prometheus-community.github.io/helm-charts
    helm repo update
    helm install kube-state-metrics prometheus-community/kube-state-metrics --namespace elastic-system
    
  2. 取得預設的 Kibana elastic 使用者憑證:

    kubectl get secret elasticsearch-es-elastic-user -o yaml -n elastic-system -o jsonpath='{.data.elastic}' | base64 -d
    
  3. 在瀏覽器中開啟 https://elk.BASE_DOMAIN,然後使用憑證登入 Kibana。

  4. 在選單中依序選取「數據分析」和「資訊主頁」

  5. 在搜尋文字欄位中輸入「Kubernetes overview」(Kubernetes 總覽),然後選取「Overview dashboard」(總覽資訊主頁),即可查看基本指標。

    部分資訊主頁面板可能不會顯示任何資料或錯誤訊息,因為 GKE 會限制存取 Kibana 用來取得叢集指標的部分控制層端點。

清除所用資源

如要避免系統向您的 Google Cloud 帳戶收取本教學課程中所用資源的相關費用,請刪除含有該項資源的專案,或者保留專案但刪除個別資源。

刪除專案

    Delete a Google Cloud project:

    gcloud projects delete PROJECT_ID

刪除個別資源

如果您使用現有專案,但不想刪除專案,請刪除個別資源。

  1. 刪除 Elastic Stack 元件、ECK 運算子和 kube-state-metrics:

    kubectl --namespace elastic-system delete ingresses.networking.k8s.io elastic-stack
    kubectl --namespace elastic-system delete managedcertificates.networking.gke.io elastic-stack
    kubectl --namespace elastic-system delete frontendconfigs.networking.gke.io elastic-stack
    kubectl --namespace elastic-system delete agents.agent.k8s.elastic.co elastic-agent
    kubectl --namespace elastic-system delete agents.agent.k8s.elastic.co fleet-server
    kubectl --namespace elastic-system delete kibanas.kibana.k8s.elastic.co kibana
    kubectl --namespace elastic-system delete elasticsearches.elasticsearch.k8s.elastic.co elasticsearch
    kubectl --namespace elastic-system delete daemonsets.apps max-map-count-setter
    kubectl --namespace elastic-system delete pvc --selector='elasticsearch.k8s.elastic.co/cluster-name=elasticsearch'
    helm --namespace elastic-system uninstall kube-state-metrics
    helm --namespace elastic-system uninstall elastic-operator
    
  2. 刪除 DNS 記錄集、IP 位址、DNS 代管可用區和 GKE 叢集:

    gcloud dns record-sets delete "elk.BASE_DOMAIN" \
        --type="A" \
        --zone="elk" \
        --quiet
    
    gcloud compute addresses delete "elastic-stack" \
        --global \
        --quiet
    
    gcloud dns managed-zones delete "elk" --quiet
    
    gcloud container clusters delete "elk-stack" \
        --location="us-central1" \
        --quiet
    

後續步驟

  • 探索 Google Cloud 的參考架構、圖表和最佳做法。 歡迎瀏覽我們的雲端架構中心