mgo 와 mongo-go-driver 사용 소감 비교 mgo 와 mongo-go-driver 사용 소감 비교
9999 단어 데이터베이스+NoSql
>>자원 다운로드: https://72k.us/file/14896800-396374653
mgo 와 mongo-go-driver 비교
라 이브 러 리 소개
용법 소개
데이터베이스 연결
import (
"gopkg.in/mgo.v2"
"gopkg.in/mgo.v2/bson"
)
session, err := mgo.Dial("127.0.0.1:27017")
import (
"go.mongodb.org/mongo-driver/mongo"
"go.mongodb.org/mongo-driver/mongo/options"
)
client, err := mongo.NewClient(options.Client().ApplyURI("mongodb://localhost:27017"))
두 가 지 는 데이터베이스 연결 에 있어 매우 간단 하 다.후 자 는 options 를 사용 하여 연결 수,연결 시간,socket 시간,시간 초과 등 을 설정 할 수 있다.
인덱스
func createUniqueIndex(collection string, keys ...string) {
ms, c := Connect(setting.DatabaseSetting.DBName, collection)
defer ms.Close()
//
index := mgo.Index{
Key: keys, //
Unique: true, //
DropDups: true, // ,
Background: true, //
}
//
err := c.EnsureIndex(index)
if err != nil {
Logger.Error("EnsureIndex error", zap.String("error", err.Error()))
}
}
func createUniqueIndex(collection string, keys ...string) {
db := DB.Mongo.Database(setting.DatabaseSetting.DBName).Collection(collection)
opts := options.CreateIndexes().SetMaxTime(10 * time.Second)
indexView := db.Indexes()
keysDoc := bsonx.Doc{}
//
for _, key := range keys {
if strings.HasPrefix(key, "-") {
keysDoc = keysDoc.Append(strings.TrimLeft(key, "-"), bsonx.Int32(-1))
} else {
keysDoc = keysDoc.Append(key, bsonx.Int32(1))
}
}
//
result, err := indexView.CreateOne(
context.Background(),
mongo.IndexModel{
Keys: keysDoc,
Options: options.Index().SetUnique(true),
},
opts,
)
if result == "" || err != nil {
Logger.Error("EnsureIndex error", zap.String("error", err.Error()))
}
}
mgo 는 복합 색인 을 직접 구축 할 수 있 습 니 다.순서대로 여러 개의 매개 변 수 를 입력 하면 됩 니 다
createIndex(addrTrxC, "address_id", "asset_id")
.그러나 mongo-go-driver 는 스스로 처리 해 야 합 니 다.조회 하 다.
func FindProNode() ([]DBNode, error) {
var nodes []DBNode
ms, c := Connect(setting.DatabaseSetting.DBName, superNodeC)
defer ms.Close()
err := c.Find(M{}).Sort("-vote_count").Limit(10).All(&nodes)
if err != nil {
return nil, err
}
return nodes, nil
}
func FindNodes() ([]DBNode, error) {
var nodes []DBNode
c := Connect(setting.DatabaseSetting.DBName, superNodeC)
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()
opts := options.Find().SetSort(bsonx.Doc{{"vote_count", bsonx.Int32(-1)}})
cursor, err := c.Find(ctx, M{}, opts)
if err != nil {
return nil, err
}
for cursor.Next(context.Background()) {
var node DBNode
if err = cursor.Decode(&node); err != nil {
return nil, err
} else {
nodes = append(nodes, node)
}
}
return nodes, nil
}
하나의 요 소 를 조회 할 때 두 개의 구동 이 모두 편리 하지만 여러 요 소 를 조회 할 때 mongo-go-driver 는 배열 을 직접 분석 할 수 없습니다.cursor 라 는 유형 을 통 해 모든 데 이 터 를 옮 겨 다 니 며 분석 해 야 합 니 다(번 거 로 우 므 로 스스로 포장 해 야 합 니 다).
끼어들다
//
func Insert(db, collection string, docs ...interface{}) error {
ms, c := Connect(db, collection)
defer ms.Close()
return c.Insert(docs...)
}
//
func InsertNode(node DBNode) error {
err := Insert(setting.DatabaseSetting.DBName, superNodeC, node)
return err
}
func Insert(db, collection string, docs ...interface{}) (*mongo.InsertManyResult, error) {
c := Connect(db, collection)
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()
return c.InsertMany(ctx, docs)
}
func InsertNode(node DBNode) error {
_, err := Insert(setting.DatabaseSetting.DBName, superNodeC, node)
return err
}
삽입 의 차이 도 크 지 않 아 요.
수정 하 다.
func UpsertNode(node DBNode) (*mgo.ChangeInfo, error) {
findM := M{"pub_key": node.PubKey}
ms, c := Connect(setting.DatabaseSetting.DBName, superNodeC)
defer ms.Close()
updateM := bson.M{"$inc": M{"vote_count": node.VoteCount},
"$set": M{
"name": node.Name,
"address": node.Address,
"first_timestamp": node.FirstTimestamp}}
return c.Upsert(findM, updateM)
}
func Update(db, collection string, query, update interface{}) (*mongo.UpdateResult, error) {
c := Connect(db, collection)
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()
opts := options.Update().SetUpsert(true)
return c.UpdateOne(ctx, query, update,opts)
}
둘 다 mgo(update)mongo-go-driver(updateOne)를 업데이트 하고 여러 mgo(updateAll)mongo-go-driver(updateMany)를 업데이트 할 수 있 습 니 다.하지만 upsert 에 서 는 mgo 가 upsert 를 직접 사용 하면 됩 니 다.mongo-go-driver 는 설정 해 야 합 니 다
opts := options.Update().SetUpsert(true)
삭제func Remove(db, collection string, query interface{}) error {
ms, c := Connect(db, collection)
defer ms.Close()
return c.Remove(query)
}
func RemoveNode(pubKey string) error {
findM := M{"pub_key": pubKey}
err := Remove(setting.DatabaseSetting.DBName, superNodeC, findM)
return err
}
func Remove(db, collection string, query interface{}) (*mongo.DeleteResult, error) {
c := Connect(db, collection)
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()
return c.DeleteOne(ctx, query)
}
func RemoveNode(pubKey string) error {
findM := M{"pub_key": pubKey}
_, err := Remove(setting.DatabaseSetting.DBName, superNodeC, findM)
return err
}
삭제 도 간단 하고 대체로 같다.
사무.
, ;
Exec operator
type DBTransaction struct {
Commit func(mongo.SessionContext) error
Run func(mongo.SessionContext, func(mongo.SessionContext, DBTransaction) error) error
Logger *logging.Logger
}
func NewDBTransaction(logger *logging.Logger) *DBTransaction {
var dbTransaction = &DBTransaction{}
dbTransaction.SetLogger(logger)
dbTransaction.SetRun()
dbTransaction.SetCommit()
return dbTransaction
}
func (d *DBTransaction) SetCommit() {
d.Commit = func(sctx mongo.SessionContext) error {
err := sctx.CommitTransaction(sctx)
switch e := err.(type) {
case nil:
d.Logger.Info("Transaction committed.")
return nil
default:
d.Logger.Error("Error during commit...")
return e
}
}
}
func (d *DBTransaction) SetRun() {
d.Run = func(sctx mongo.SessionContext, txnFn func(mongo.SessionContext, DBTransaction) error) error {
err := txnFn(sctx, *d) // Performs transaction.
if err == nil {
return nil
}
d.Logger.Error("Transaction aborted. Caught exception during transaction.",
zap.String("error", err.Error()))
return err
}
}
func (d *DBTransaction) SetLogger(logger *logging.Logger) {
d.Logger = logger
}
func (d *DBTransaction) Exec(mongoClient *mongo.Client, operator func(mongo.SessionContext, DBTransaction) error) error {
ctx, cancel := context.WithTimeout(context.Background(), 20*time.Minute)
defer cancel()
return mongoClient.UseSessionWithOptions(
ctx, options.Session().SetDefaultReadPreference(readpref.Primary()),
func(sctx mongo.SessionContext) error {
return d.Run(sctx, operator)
},
)
}
//
func SyncBlockData(node models.DBNode) error {
dbTransaction := db_session_service.NewDBTransaction(Logger)
// Updates two collections in a transaction.
updateEmployeeInfo := func(sctx mongo.SessionContext, d db_session_service.DBTransaction) error {
err := sctx.StartTransaction(options.Transaction().
SetReadConcern(readconcern.Snapshot()).
SetWriteConcern(writeconcern.New(writeconcern.WMajority())),
)
if err != nil {
return err
}
err = models.InsertNodeWithSession(sctx, node)
if err != nil {
_ = sctx.AbortTransaction(sctx)
d.Logger.Info("caught exception during transaction, aborting.")
return err
}
return d.Commit(sctx)
}
return dbTransaction.Exec(models.DB.Mongo, updateEmployeeInfo)
}
총결산