登录
首页 >  Golang >  Go问答

在 Go 中如何访问和操作 Elasticsearch 文档的字段值?

来源:stackoverflow

时间:2024-02-18 11:00:24 500浏览 收藏

一分耕耘,一分收获!既然打开了这篇文章《在 Go 中如何访问和操作 Elasticsearch 文档的字段值?》,就坚持看下去吧!文中内容包含等等知识点...希望你能在阅读本文后,能真真实实学到知识或者帮你解决心中的疑惑,也欢迎大佬或者新人朋友们多留言评论,多给建议!谢谢!

问题内容

我正在尝试用 go 重写我们系统的部分内容。它们目前是用 python 编写的。我想要提供的一些数据存在于 elasticsearch 中。

在我们的用户中,我们有一些标准字段,但也允许人们创建许多特定于其环境的自定义字段。例如,我们有一个产品对象,它具有一些常见字段,如 nameprice,但我们让某人创建一个字段,如 discount_pricerequires_freight 来同意他们的用例。

在 python 中,这很容易实现。读入 json,我们选择的 json 解析器会进行一些合理的类型推断,然后我们可以在处理后返回数据。

在 go 中,我们想要处理来自 elasticsearch json 响应的任何数据都必须映射到类型。或者至少这是我的理解。例如:

import (
    "encoding/json"
)

...

type product struct {
    name              string   `json:"name"`
    price             string   `json:"price"`
}

以下是数据的简化示例。我已将要传递的非标准字段的名称添加为 custom 前缀:

{
    "id": "ABC123",
    "name": "Great Product",
    "price": 10.99,
    "custom_alternate_names": ["Great Product"],
    "custom_sellers": [{
        "id": "ABC123",
        "name": "Great Product LLC",
        "emails": ["[email protected]"]
    }]
}

对于路由实际需要处理或操作自定义字段的地方来说,特殊情况是可以的。但在大多数情况下,不加修改地传递 json 数据就可以了,因此,为了安全起见,我们没有强加任何类型映射,这一事实并没有添加任何内容。

有没有办法设置 struct 的接口(?)可以充当任何未映射字段的直通?或者在返回数据之前获取未解析的 json 数据并将其与映射对象重新组合的方法?


解决方案


你可以做这样的事情

package main

import (
    "encoding/json"
    "log"
)

type Product struct {
    //embed product to be able to pull the properties without
    //requiring a nested object in the json
    KnownFields
    OtherStuff json.RawMessage
}

//Custom unmarshaller
func (p *Product) UnmarshalJSON(b []byte) error {
    var k KnownFields
    //unmarshal the known fields
   err := json.Unmarshal(b, &k)
    if err != nil {
        return err
    }
    p.KnownFields = k
    //You can use json.RawMessage or map[string]interface
    p.OtherStuff = json.RawMessage(b)
    return nil
}

type KnownFields struct {
    Name  string      `json:"name"`
    Price json.Number `json:"price"`
}

const JSON = `
{
    "id": "ABC123",
    "name": "Great Product",
    "price": 10.99,
    "custom_alternate_names": ["Great Product"],
    "custom_sellers": [{
        "id": "ABC123",
        "name": "Great Product LLC",
        "emails": ["[email protected]"]
    }]
}`

func main() {
    var p Product
    err := json.Unmarshal([]byte(JSON), &p)
    if err != nil {
        log.Panic(err)
    }
    log.Printf("%v", p)
}

如果您要对 product 进行变异和编组,则必须实现自定义编组器,并且还需要使用 map[string]interface{} 作为 otherstuff 以避免已知字段出现重复条目​​ p>

本篇关于《在 Go 中如何访问和操作 Elasticsearch 文档的字段值?》的介绍就到此结束啦,但是学无止境,想要了解学习更多关于Golang的相关知识,请关注golang学习网公众号!

声明:本文转载于:stackoverflow 如有侵犯,请联系study_golang@163.com删除
相关阅读
更多>
最新阅读
更多>
课程推荐
更多>