sorm

package module
v1.0.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 4, 2024 License: Apache-2.0 Imports: 7 Imported by: 0

README

sorm-logo

Security Status

SORM 操作框架,是一款适配国产化数据库操作的golang orm 框架,内部适配分库分表策略,提供类似于GORM的操作形式。内部包含所有数据库驱动,直接使用原生的驱动构建而成,提供一站式数据托管的数据操作能力。 欢迎对数据库感兴趣的小伙伴一起来改进这个库,毕竟以我自己一个人的力量还是微小,很多不足之处,欢迎给我留言。 [TOC]

目前支持的数据库驱动如下:

  • dm 达梦
  • gobase
  • kingbase
  • mysql
  • opengauss
  • oracle
  • postgres
  • shentong
  • sqlite
  • yxres 优炫
  • odbc 驱动

后期改进

  1. 神通和达梦的数据库 大小写还是很反人类,设置大小写敏感,使用小写自动转成大写了,如果想使用小写需要使用"" 括起来处理,但是sql 又比较灵活,还有很多聚合和统计的函数不能一一实现,索性就让这两个数据库都使用大写的表名和字段去处理
  2. 关于数据库的自增,目前只支持字段自增,不能使用sequence,因为要同时兼容很多数据库,需要适配,这是也是一个坑。
  3. 还有一些数据库方言类的数据格式需要适配,可能需要一些细微的调整

数据库分库分表功能:

表指定数据库
// 单独给一个表存放一个数据库:
// cofnig 是数据库的配置文件
engine.AddDB("user", &conf)
分表策略
// TableName:表名
// TableShardType 分表策略
// TableSegName 表中分表的字段
engine.AddSpliter( spliter.Split{TableName: tableName, TableShardType: shardType, TableSegName: segName})
取模
%5:按照取模来分表,user_0、user_1,user_2、user_3,user_4
按照分表字段的对应的值 取模上面的数字,例如表名,user,分表的字段是age,按照分表策略%2,生成的表名就是user_0、user_1
时间:
m:按照月来分表 对应的表名为user_202001,user_202002,user_202003...
d:按照天来分表 对应的表名为,user_20200101,user_20200102,user_20200103...      
w:按照周来分表 对应的表名为user_202028,user_202029,user_202030,...
h:按照小时来分表 对应的表为user_2020010101 
y:按照年来分表 对应的表名为user_2020,user_2021,user_2022,user_2023,...

数据库操作

初始化数据库引擎
conf := server.Config{ // 初始化一个engine
		Type:     "dm",
		Host:     "192.168.81.36",
		Port:     5236,
		Username: "test",
		Password: "123456",
		Database: "test",
	}

	engine, err := NewEngineWithConfig(&conf)
	if err != nil {
		t.Fatal("failed to connect", err)
	}
定义数据表结构
type User struct {
	Name       string    `column:"name" sorm:"PRIMARY KEY"`
	Age        int       `json:"age" form:"age" column:"age"`
	CreateTime time.Time `json:"create_time" form:"create_time"  column:"create_time"`
	Num        *int      `json:"num"  form:"num"  column:"num"`
}

func (u *User) GetTableName() string {
	return "user"
}

上述代码定义了一个名为 User 的结构体,它对应数据库中的 user 表。结构体字段使用 column 标签指定了对应的数据库列名。
目前仅支持自增主键,使用 sorm:"PRIMARY KEY" 来表示,还未启用各个数据库的sequence,这个功能还没想好怎么加。
事务
事务框架会自动代理所有的数据库,提供整体的事务处理    
使用数据库引擎的 Transaction 方法可以进行数据库事务操作。示例如下:
engine.Transaction(func(s *session.Session) (result interface{}, err error) {
	s.Where("name =?", "John").First(&User{}) // find a user with name "John"") 
	
}

创建数据:

使用数据库引擎的 Create 方法可以向数据库中插入数据。示例如下:

func create(t *testing.T) {
	engine := OpenDB(t)
	defer engine.Close()

	u1 := User{Name: "Tom", CreateTime: time.Now()}
	us := []User{
		{Name: "Tom", Age: 18, CreateTime: t1, Num: n1},
		{Name: "liu", Age: 19, CreateTime: t1, Num: n1},
		{Name: "lao", Age: 20, CreateTime: time.Now()},
		{Name: "ban", Age: 21, CreateTime: time.Now()},
	}

	s := engine.NewSession()

	_, err := s.Create(&us)
	if err != nil {
		log.Infof("err:%+v\n", err)
		return
	}

	_, err = s.Create(&u1)
	if err != nil {
		log.Infof("err:%+v\n", err)
		return
	}

	_, err = s.Select("name", "age").Create(&u1)
	if err != nil {
		log.Infof("err:%+v\n", err)
		return
	}

	_, err = s.Select("name", "age").Create(&us)
	if err != nil {
		log.Infof("err:%+v\n", err)
		return
	}
}

上述代码通过调用 engine.NewSession 创建一个数据库会话,然后使用会话的 Create 方法插入数据。可以一次插入多个数据,传入的参数为对应的结构体和切片。
查询数据

查询数据可选的方法就就比较多了

Select("name", "age")  // 选择指定的字段
Omit("name") // 选择不显示指定的字段
Join(LEFT, "a", "a.id=b.id") // join 类型/表/连接条件
Limit(10)
Offset(10)
OrderBy("name desc") // order by
GroupBy("name") // group by
Having  


var ps []Point

err := s.Model(&Point{}).Select("t19").Find(&ps)
if err != nil {
    panic(err)
}

fmt.Println("ps:", ps)

更新数据
func UpdatePoint(t *testing.T) {
	engine := OpenDB(t)
	defer engine.Close()
	//engine.AddUserSplitter()
	s := engine.NewSession()

	_, err := s.Model(&Point{}).Where("num = ?", 1).Update("t19 = ?", time.Now())
	if err != nil {
		panic(err)
	}

}

删除数据

func deletePointTran(t *testing.T) {

	engine := OpenDB(t)
	defer engine.Close()
	engine.AddUserSplitter()

	engine.Transaction(func(s *session.Session) (interface{}, error) {
		_, err := s.Model(&Point{}).Where("num = ? and name = ?", 4, "liu").Delete()

		if err != nil {
			panic(err)
		}
		return nil, nil
	})

}

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Engine

type Engine struct {
	// contains filtered or unexported fields
}

Engine is the main struct of sorm, manages all db sessions and transactions.

func NewEngine

func NewEngine(driver, source string) (e *Engine, err error)

NewEngine create a instance of Engine connect database and ping it to test whether it's alive

func NewEngineWithConfig

func NewEngineWithConfig(config *server.Config) (e *Engine, err error)

通过config 初始化一个engine

func (*Engine) AddDB

func (e *Engine) AddDB(tableName string, config *server.Config)

func (*Engine) AddDBWithShard

func (e *Engine) AddDBWithShard(tableName, shardType, segName string, config *server.Config)

给engine 中 通过tableName 和config 增加dbs 用于分库 tableName 分表的原来表名 shardType 分表的类型 例如 %2 对应的表名为 user_0/user_1 m 对应的表名为 user_202001 d 对应的表名为 user_20200101 w 对应的表名为 user_20200101 h 对应的表名为 user_2020010101 y 对应的表名为 user_2020 segName 分表的字段

func (*Engine) AddSpliter

func (engine *Engine) AddSpliter(split spliter.Split)

给engine 新增一个spliter

func (*Engine) AddSpliterMap

func (engine *Engine) AddSpliterMap(splitMap map[string]spliter.Split)

给engine 新增多个spliter

func (*Engine) AddUserSplitter

func (engine *Engine) AddUserSplitter()

生成一个 模拟user 按照%4 的拆分表规则的spliter

func (*Engine) Close

func (engine *Engine) Close()

Close database connection

func (*Engine) NewSession

func (engine *Engine) NewSession() *session.Session

NewSession creates a new session for next operations

func (*Engine) Transaction

func (engine *Engine) Transaction(f TxFunc) (result interface{}, err error)

Transaction executes sql wrapped in a transaction, then automatically commit if no error occurs

type TxFunc

type TxFunc func(*session.Session) (interface{}, error)

TxFunc will be called between tx.Begin() and tx.Commit() https://stackoverflow.com/questions/16184238/database-sql-tx-detecting-commit-or-rollback

Directories

Path Synopsis
Package decimal implements an arbitrary precision fixed-point decimal.
Package decimal implements an arbitrary precision fixed-point decimal.
driver/kingbase/v8r3/kingbase.com/gokb
Package kb is a pure Go Kingbase driver for the database/sql package.
Package kb is a pure Go Kingbase driver for the database/sql package.
driver/kingbase/v8r3/kingbase.com/gokb/oid
Package oid contains OID constants as defined by the Kingbase server.
Package oid contains OID constants as defined by the Kingbase server.
driver/kingbase/v8r3/kingbase.com/gokb/scram
Package scram implements a SCRAM-{SHA-1,etc} client per RFC5802.
Package scram implements a SCRAM-{SHA-1,etc} client per RFC5802.
driver/kingbase/v8r6/kingbase.com/gokb
Package kb is a pure Go Kingbase driver for the database/sql package.
Package kb is a pure Go Kingbase driver for the database/sql package.
driver/kingbase/v8r6/kingbase.com/gokb/oid
Package oid contains OID constants as defined by the Kingbase server.
Package oid contains OID constants as defined by the Kingbase server.
driver/kingbase/v8r6/kingbase.com/gokb/scram
Package scram implements a SCRAM-{SHA-1,etc} client per RFC5802.
Package scram implements a SCRAM-{SHA-1,etc} client per RFC5802.
driver/odbc
Package odbc implements database/sql driver to access data via odbc interface.
Package odbc implements database/sql driver to access data via odbc interface.
driver/yxres/uxgo/oid
Package oid contains OID constants as defined by the UXres server.
Package oid contains OID constants as defined by the UXres server.
driver/yxres/uxgo/scram
Package scram implements a SCRAM-{SHA-1,etc} client per RFC5802.
Package scram implements a SCRAM-{SHA-1,etc} client per RFC5802.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL