将其编组为 bson.Raw。

huangapple go评论88阅读模式
英文:

Marshal into a bson.Raw

问题

使用gopkg.in/mgo.v2/bson,我想知道如何将interface{}类型的值编组为bson.Raw类型的值。

bson.Raw文档中提到:

> 使用此类型可以部分地解组或编组值。

但是我找不到返回bson.RawMarshal函数。

我漏掉了什么?

我尝试的示例:

package main

import (
	"fmt"

	"gopkg.in/mgo.v2/bson"
)

func main() {
	// 如何避免使用MarshalRaw辅助函数?
	raw, err := MarshalRaw("Hello world")
	if err != nil {
		panic(err)
	}

	fmt.Printf("%+v\n", raw)
}

func MarshalRaw(v interface{}) (*bson.Raw, error) {
	bin, err := bson.Marshal(struct{ Raw interface{} }{v})
	if err != nil {
		return nil, err
	}

	var raw struct{ Raw bson.Raw }
	err = bson.Unmarshal(bin, &raw)
	if err != nil {
		return nil, err
	}

	return &raw.Raw, nil
}

输出:

> &{Kind:2 Data:[12 0 0 0 72 101 108 108 111 32 119 111 114 108 100 0]}

英文:

Using gopkg.in/mgo.v2/bson, I wonder how to marshal an interface{} value into a value of type bson.Raw.

The documentation for bson.Raw states:

> Using this type it is possible to unmarshal or marshal values partially.

But I can't find a Marshal function that would return bson.Raw.

What am I missing?

Example of what I try to do:

package main

import (
	"fmt"

	"gopkg.in/mgo.v2/bson"
)

func main() {
	// How to avoid a MarshalRaw help function?
	raw, err := MarshalRaw("Hello world")
	if err != nil {
		panic(err)
	}

	fmt.Printf("%+v\n", raw)
}

func MarshalRaw(v interface{}) (*bson.Raw, error) {
	bin, err := bson.Marshal(struct{ Raw interface{} }{v})
	if err != nil {
		return nil, err
	}

	var raw struct{ Raw bson.Raw }
	err = bson.Unmarshal(bin, &raw)
	if err != nil {
		return nil, err
	}

	return &raw.Raw, nil
}

Output:

> &{Kind:2 Data:[12 0 0 0 72 101 108 108 111 32 119 111 114 108 100 0]}

答案1

得分: 3

bson.Raw在编组和解组时都用作值。

要将interface{}转换为bson.Raw,首先要做的是对其进行编组,以获取表示正在编组的内容的纯文档数据:

var value interface{} = bson.M{"some": "value"}
data, err := bson.Marshal(value)
if err != nil {
    log.Fatal(err)
}

然后,它可能会将一个或多个字段解组为bson.Raw值:

var doc struct{ Some bson.Raw }
err = bson.Unmarshal(data, &doc)
if err != nil {
    log.Fatal(err)
}

甚至可以解组整个文档:

var doc bson.Raw
err = bson.Unmarshal(data, &doc)
if err != nil {
    log.Fatal(err)
}

如果您想获取整个文档而不仅仅是一个字段,还可以使用以下快捷方式:

doc := bson.Raw{3, data}

常量3表示bson规范中的文档,当然必须与提供的数据匹配。由于BSON仅支持顶级文档,我们知道这一点必须是正确的。

英文:

bson.Raw is used as a value both when marshaling and unmarshaling.

To transform an interface{} into a bson.Raw, the first thing to do is to marshal it so that you get the plain document data that represents whatever is being marshaled:

    var value interface{} = bson.M{"some": "value"}
    data, err := bson.Marshal(value)
    if err != nil {
            log.Fatal(err)
    }

and then it may have one or more fields unmarshaled into bson.Raw values:

    var doc struct{ Some bson.Raw }
    err = bson.Unmarshal(data, &doc)
    if err != nil {
            log.Fatal(err)
    }

or even the entire document:

    var doc bson.Raw
    err = bson.Unmarshal(data, &doc)
    if err != nil {
            log.Fatal(err)
    }

If you want the entire document rather than just a field, you can also use this shortcut:

    doc := bson.Raw{3, data}

The 3 constant represents a document in the bson specification, and it must of course match the provided data. Since BSON only supports documents at the top level, we know this must be correct.

答案2

得分: 2

我相信bson.Raw是用作变量类型的。

例如:(在play中)

type Bar struct {
   AnInt int
   AString bson.Raw
}

你的链接提到的"AString"字段将保持为bson.Raw结构。

如果你想要部分解码嵌套结构的顶层,以确定其实际类型,以便将其余部分解析为正确的数据类型,这非常有用。

请注意,上述代码未经测试,我目前没有可以运行Go的机器。这是基于它与标准的encoding/json包的工作方式类似的假设。

英文:

I believe that bson.Raw is intended to be used as a type for a variable.

for example: (in play)

type Bar struct {
   AnInt int
   AString bson.Raw
}

The "AString" field will be kept as the bson.Raw struct your link mentions.

This is super-useful if you want to partially decode the top level of a nested structure to figure out its actualy type so you can parse the rest in to the proper datatype.

Note, the above is untested, not in front of a machine I can actually run go on at the moment. This is based on the assumption that it works like the standard encoding/json package.

答案3

得分: 1

我现在是你的中文翻译助手,以下是你要翻译的内容:

我正在寻找的解决方案

m := bson.M{"ns": bson.M{"coll": "test1", "db": "testdb"}}
data, _ := bson.Marshal(m)
r := bson.Raw(data)
coll := r.Lookup("ns", "coll").StringValue()
println(coll)

Playground

英文:

Solution I was looking for

m := bson.M{"ns": bson.M{"coll": "test1", "db": "testdb"}}
data, _ := bson.Marshal(m)
r := bson.Raw(data)
coll := r.Lookup("ns", "coll").StringValue()
println(coll)

Playground

huangapple
  • 本文由 发表于 2014年8月13日 09:54:56
  • 转载请务必保留本文链接:https://go.coder-hub.com/25276884.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定