Golang & mgo: How to create a generic entity with common fields like _id, creation time, and last update

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

Golang & mgo: How to create a generic entity with common fields like _id, creation time, and last update

问题

给定以下struct

package models

import (
    "time"
    "gopkg.in/mgo.v2/bson"
)

type User struct {
    Id         bson.ObjectId `json:"id" bson:"_id"`
    Name       string        `json:"name" bson:"name"`
    BirthDate  time.Time     `json:"birth_date" bson:"birth_date"`
    InsertedAt time.Time     `json:"inserted_at" bson:"inserted_at"`
    LastUpdate time.Time     `json:"last_update" bson:"last_update"`
}

这是我如何将新用户插入Mongo集合的方法:

user := &models.User{
    bson.NewObjectId(),
    "John Belushi",
    time.Date(1949, 01, 24),
    time.Now().UTC(),
    time.Now().UTC(),
}

dao.session.DB("test").C("users").Insert(user)

是否可以有一个通用的Entity,让其他实体继承它?我尝试过这样做:

type Entity struct {
    Id         bson.ObjectId `json:"id" bson:"_id"`
    InsertedAt time.Time     `json:"inserted_at" bson:"inserted_at"`
    LastUpdate time.Time     `json:"last_update" bson:"last_update"`
}

type User struct {
    Entity
    Name       string        `json:"name" bson:"name"`
    BirthDate  time.Time     `json:"birth_date" bson:"birth_date"`
}

...但这会导致最终结果如下:

{
    "Entity": {
        "_id": "...",
        "inserted_at": "...",
        "last_update": "..."
    },
    "name": "John Belushi",
    "birth_date": "1949-01-24..."
}

如何在每个struct中不重复地包含公共字段,以获得以下结果?

{
    "_id": "...",
    "inserted_at": "...",
    "last_update": "...",
    "name": "John Belushi",
    "birth_date": "1949-01-24..."
}
英文:

Given the following struct:

package models

import (
    "time"
    "gopkg.in/mgo.v2/bson"
)

type User struct {
    Id         bson.ObjectId `json:"id" bson:"_id"`
    Name       string        `json:"name" bson:"name"`
    BirthDate  time.Time     `json:"birth_date" bson:"birth_date"`
    InsertedAt time.Time     `json:"inserted_at" bson:"inserted_at"`
    LastUpdate time.Time     `json:"last_update" bson:"last_update"`
}

... here is how I insert a new user into a Mongo collection:

user := &models.User{
    bson.NewObjectId(),
    "John Belushi",
    time.Date(1949, 01, 24),
    time.now().UTC(),
    time.now().UTC(),
}

dao.session.DB("test").C("users").Insert(user)

Is it possible to have a generic Entity all other entities inherit from? I've tried this...

type Entity struct {
    Id         bson.ObjectId `json:"id" bson:"_id"`
    InsertedAt time.Time     `json:"inserted_at" bson:"inserted_at"`
    LastUpdate time.Time     `json:"last_update" bson:"last_update"`
}

type User struct {
    Entity
    Name       string        `json:"name" bson:"name"`
    BirthDate  time.Time     `json:"birth_date" bson:"birth_date"`
}

... but this implies a final result like this:

{
    "Entity": {
        "_id": "...",
        "inserted_at": "...",
        "last_update": "..."
    },
    "name": "John Belushi",
    "birth_date": "1949-01-24..."
}

How do I get the following result without repeating common fields in each struct?

{
    "_id": "...",
    "inserted_at": "...",
    "last_update": "...",
    "name": "John Belushi",
    "birth_date": "1949-01-24..."
}

答案1

得分: 3

这个问题已经在https://stackoverflow.com/questions/20849591/storing-nested-structs-with-mgo中得到了回答,但是非常简单,你只需要在匿名内部结构体上添加bson:",inline",然后像正常初始化一样即可。

以下是一个快速示例:

package main

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

type Entity struct {
	Id         bson.ObjectId `json:"id" bson:"_id"`
	InsertedAt time.Time     `json:"inserted_at" bson:"inserted_at"`
	LastUpdate time.Time     `json:"last_update" bson:"last_update"`
}

type User struct {
	Entity    `bson:",inline"`
	Name      string    `json:"name" bson:"name"`
	BirthDate time.Time `json:"birth_date" bson:"birth_date"`
}

func main() {
	info := &mgo.DialInfo{
		Addrs:    []string{"localhost:27017"},
		Timeout:  60 * time.Second,
		Database: "test",
	}

	session, err := mgo.DialWithInfo(info)
	if err != nil {
		panic(err)
	}
	defer session.Close()
	session.SetMode(mgo.Monotonic, true)

	user := User{
		Entity:    Entity{"123456789098", time.Now().UTC(), time.Now().UTC()},
		Name:      "John Belushi",
		BirthDate: time.Date(1959, time.February, 28, 0, 0, 0, 0, time.UTC),
	}

	session.DB("test").C("users").Insert(user)
}

希望对你有帮助!

英文:

This was already answered in https://stackoverflow.com/questions/20849591/storing-nested-structs-with-mgo, but it is very easy all you need to do is add bson:",inline" on the anonymous inner struct and initialize as normal...

Here a quick example:

package main

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

type Entity struct {
	Id         bson.ObjectId `json:"id" bson:"_id"`
	InsertedAt time.Time     `json:"inserted_at" bson:"inserted_at"`
	LastUpdate time.Time     `json:"last_update" bson:"last_update"`
}

type User struct {
	Entity    `bson:",inline"`
	Name      string    `json:"name" bson:"name"`
	BirthDate time.Time `json:"birth_date" bson:"birth_date"`
}

func main() {
	info := &mgo.DialInfo{
		Addrs:    []string{"localhost:27017"},
		Timeout:  60 * time.Second,
		Database: "test",
	}

	session, err := mgo.DialWithInfo(info)
	if err != nil {
		panic(err)
	}
	defer session.Close()
	session.SetMode(mgo.Monotonic, true)
	//	c := session.DB("test").C("users")

	user := User{
		Entity:    Entity{"123456789098", time.Now().UTC(), time.Now().UTC()},
		Name:      "John Belushi",
		BirthDate: time.Date(1959, time.February, 28, 0, 0, 0, 0, time.UTC),
	}

	session.DB("test").C("users").Insert(user)
}

huangapple
  • 本文由 发表于 2016年4月3日 05:09:19
  • 转载请务必保留本文链接:https://go.coder-hub.com/36378725.html
匿名

发表评论

匿名网友

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

确定