AWS Elasticsearch 使用 ES 客户端返回 403 禁止错误

Har*_*hit 5 go elasticsearch aws-elasticsearch

我正在尝试通过用 Go 编写的索引作业创建索引。我可以使用我的访问密钥和密钥来访问 AWS 上的 ES 集群。

我可以使用 Kibana 轻松创建索引,但是当我尝试使用 Go 客户端时,它不起作用并返回 403 禁止错误。

AWS Elasticsearch 政策:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "AWS": "*"
      },
      "Action": "es:*",
      "Resource": "arn:aws:es:<region>:111111111111:domain/prod-elasticsearch/*"
    }
  ]
}
Run Code Online (Sandbox Code Playgroud)

索引.go

package main

import (
    "flag"
    "fmt"
    "log"

    "github.com/aws/aws-sdk-go/aws/credentials"
    "github.com/olivere/elastic/v7"
    "github.com/spf13/viper"

    aws "github.com/olivere/elastic/v7/aws/v4"
)

func main() {
    var (
        accessKey = viper.GetString("aws.access_key")
        secretKey = viper.GetString("aws.secret_key")
        url       = viper.GetString("elasticsearch.host")
        sniff     = flag.Bool("sniff", false, "Enable or disable sniffing")
        region    = flag.String("region", "ap-southeast-1", "AWS Region name")
    )

    if url == "" {
        log.Fatal("please specify a URL with -url")
    }
    if accessKey == "" {
        log.Fatal("missing -access-key or AWS_ACCESS_KEY environment variable")
    }
    if secretKey == "" {
        log.Fatal("missing -secret-key or AWS_SECRET_KEY environment variable")
    }
    if *region == "" {
        log.Fatal("please specify an AWS region with -region")
    }

    creds := credentials.NewStaticCredentials(accessKey, secretKey, "")
    _, err := creds.Get()

    if err != nil {
        log.Fatal("Wrong credentials: ", err)
    }

    signingClient := aws.NewV4SigningClient(creds, *region)

    // Create an Elasticsearch client
    client, err := elastic.NewClient(
        elastic.SetURL(url),
        elastic.SetSniff(*sniff),
        elastic.SetHealthcheck(*sniff),
        elastic.SetHttpClient(signingClient),
    )

    if err != nil {
        log.Fatal(err)
    }

    // This part gives 403 forbidden error
    indices, err := client.IndexNames()

    if err != nil {
        log.Fatal(err)
    }

    // Just a status message
    fmt.Println("Connection succeeded")
}
Run Code Online (Sandbox Code Playgroud)

配置文件

[elasticsearch]
host = "https://vpc-prod-elasticsearch-111111.ap-southeast-1.es.amazonaws.com"

[aws]
access_key = <ACCESS_KEY>
secret_key = <SECRET_KEY>
Run Code Online (Sandbox Code Playgroud)

Har*_*hit 0

Go 代码看起来不错。由于 AWS 密钥中的一些问题,出现了 403 错误禁止。

要调试此类问题:

  1. 检查 AWS Elasticsearch 集群运行的 VPC 子网是否已删除。如果VPC子网已被删除,那么它总是会抛出403错误。
  2. 如果子网配置正常,那么很可能是 AWS 密钥的问题。您可以为 AWS Elasticsearch 创建新的 AWS 应用程序用户并重试。这应该可以正常工作。

我按照上述2点解决了上述问题。