Go項目中beego的orm使用和gorm的使用

  按照beego官方文檔練習ORM的使用,model建立完始終沒找到辦法建立表,因而使用gorm翻譯文檔官方文檔進行了練習,使用起來仍是比較簡單。html

  安裝:

  方法一:Terminal打開,go get -u github.com/jinzhu/gormmysql

  方法二:複製地址https://github.com/jinzhu/gorm,到GoLand直接會提示是否將gorm添加到GOPATH,確認添加會自動下載git

  建model,models.go內容以下:

package models

import (
	"github.com/jinzhu/gorm"
)

type User struct {
	gorm.Model
	Name    string
	Profile Profile `gorm:"ForeignKey:UserRefer"` // 一個User包含一個Profile
	Post    []Post                                // 一個User包含多個Post UserID爲外鍵
}

type Profile struct {
	gorm.Model
	Age       int16
	UserRefer uint
}

type Post struct {
	gorm.Model
	Title  string
	UserID uint
	Tag    []*Tag `gorm:"many2many:post_tag;"`
}

type Tag struct {
	gorm.Model
	Name  string
	Posts []*Post `gorm:"many2many:post_tag;"`
}

  鏈接數據庫,main.go部份內容:

package main

import (
	"fmt"
	"github.com/jinzhu/gorm"
	_ "github.com/jinzhu/gorm/dialects/mysql"
	"myproject/models"
	_ "myproject/routers"
)

var db *gorm.DB

func main() {
	// 鏈接數據庫
	var err error
	db, err = gorm.Open("mysql", "root:nola123456@/default?charset=utf8&parseTime=True&loc=Local")
	if err != nil {
		panic(err)
	}
	defer db.Close()
        ...      
}

  建立表,main.go部份內容:

  gorm文檔給出自動遷移模式,警告:自動遷移僅僅會建立表,缺乏列和索引,而且不會改變現有列的類型或刪除未使用的列以保護數據。github

db.AutoMigrate(&models.User{}, &models.Profile{}, &models.Post{}, &models.Tag{})

  使用以下方式建立表(代碼有點繁瑣,還在探索中):sql

func main() {
        ...
	// 建立表User
	if !db.HasTable(&models.User{}) {
		if err := db.Set("gorm:table_options", "ENGINE=InnoDB").CreateTable(&models.User{}).Error; err != nil {
			panic(err)
		}
	}

	// 建立表Profile
	if !db.HasTable(&models.Profile{}) {
		if err := db.Set("gorm:table_options", "ENGINE=InnoDB").CreateTable(&models.Profile{}).Error; err != nil {
			panic(err)
		}
	}

	// 建立表Post
	if !db.HasTable(&models.Post{}) {
		if err := db.Set("gorm:table_options", "ENGINE=InnoDB").CreateTable(&models.Post{}).Error; err != nil {
			panic(err)
		}
	}

	// 建立表Tag
	if !db.HasTable(&models.Tag{}) {
		if err := db.Set("gorm:table_options", "ENGINE=InnoDB").CreateTable(&models.Tag{}).Error; err != nil {
			panic(err)
		}
	}
        ...
}

  運行main.go,數據庫表建立完畢:

    

  CRUD,main.go插入部分:

func main() {
        ...
	// 插入
	profile := models.Profile{Age: 30}
	profile1 := models.Profile{Age: 25}
	db.Create(&profile)
	db.Create(&profile1)
	fmt.Println(profile)
	fmt.Println(profile1)
	db.Create(&models.User{Profile: profile, Name: "silence"})
	db.Create(&models.User{Profile: profile1, Name: "silence 2"})
	db.Create(&models.User{Profile: profile, Name: "nola"})
	db.Create(&models.User{Profile: profile1, Name: "alice"})
        ...
}

  CRUD,main.go查詢部分:

func main() {
       ...
	//查詢
	var count int
	db.First(&models.User{})                                  // 第一條記錄
	db.Last(&models.User{})                                 // 最後一條記錄
	db.Find(&models.User{})                                 // 全部記錄
	db.First(&models.User{}, 1)                             // 使用主鍵獲取記錄
	db.Where("name = ?", "nola").First(&models.User{})      // where條件查詢第一個匹配記錄
	db.Where("name = ?", "nola").Find(&models.User{})        // where條件查詢全部匹配記錄
	db.Where("name <> ?", "nola").Find(&models.User{})        // where條件查詢name不爲nola的全部user
	db.Where("name in (?)", []string{"silence", "silence 2"}) // in
	db.Where("name LIKE ?", "%sil%").Find(&models.User{})    // LIKE
	db.Select([]string{"user_refer", "age"}).Find(&models.Profile{}) // 指定檢索字段
	db.Select("name").Find(&models.User{})                          // 指定檢索字段
	db.Order("name desc").Find(&models.User{})                      // 排序
	db.Limit(3).Find(&models.User{})                                 // limit
	counts := db.Where("name = ?", "rose").Find(&models.User{}).Count(&count)  // count
	fmt.Println(counts)
        ...
}

  CRUD,main.go更新部分:

func main() {
        ...
	// 更新
	db.Table("users").Where("id in (?)", []int{30, 34}).Update(map[string]interface{}{"name":"hello"})  // 批量更新
	affected_nums := db.Model(&models.User{}).Where("name = ?", "jack").Update(models.User{Name:"jim"}).RowsAffected  // 返回影響行數
	fmt.Println(affected_nums)
        ...
}

  CRUD,main.go刪除部分:

func main() {
        ...
	// 刪除
	db.Where("name LIKE ?", "%len%").Delete(models.User{})
	db.Delete(models.Profile{}, "age = ?", "30")  // model存在deleted_at字段爲軟刪除 記錄刪除時間
	fmt.Println(db.Where("age = ?", "30").Find(&models.Profile{}).Value)  // 軟刪除的記錄查詢被忽略
	fmt.Println(db.Unscoped().Where("age = ?", "30").Find(&models.Profile{}).Value)  // 查詢軟刪除的記錄
	db.Unscoped().Delete(models.Profile{}, "age = ?", "30")  // 永久刪除記錄
}

  

  習慣Django那種建好model進行遷移,也有一些人習慣利用sql語句去生成models.go文件,我的感受很彆扭。gorm使用起來很舒服,它還有不少高級用法,值得慢慢研究。。。數據庫


 

 

  着實不甘心,beego的orm連註冊model都有,怎能沒有建立同步表呢?參考csdn上一篇文章,再試一下:post

  建立項目:cd src工做間 - bee new useBeegoORM建立項目ui

  useBeegoORM/models/models.go內容以下:

package models

type User struct {
	Id      int
	Name    string
	Profile *Profile `orm:"rel(one)"`     // 一對一關係
	Post    []*Post  `orm:"reverse(many)"` // 設置一對多反向關係
}

type Profile struct {
	Id   int
	Age  int16
	User *User `orm:"reverse(one)"` // 設置一對一反向關係(可選)
}

type Post struct {
	Id    int
	Title string
	User  *User  `orm:"rel(fk)"`  // 設置一對多關係
	Tags  []*Tag `orm:"rel(m2m)"` // 設置多對多關係
}

type Tag struct {
	Id    int
	Name  string
	Posts []*Post `orm:"reverse(many)"`
}

  useBeegoORM/main.go內容以下:

package main

import (
	_ "github.com/Go-SQL-Driver/MySQL" // 引入driver
	"github.com/astaxie/beego"
	"github.com/astaxie/beego/orm"

	"useBeegoORM/models"  // 引入model
	_ "useBeegoORM/routers"
)

func init() {
	// 註冊driver
	orm.RegisterDriver("mysql", orm.DRMySQL)

	// 須要在init中註冊定義的model
	orm.RegisterModel(new(models.User), new(models.Profile), new(models.Post), new(models.Tag))

	// 註冊數據庫 ORM必須註冊一個別名爲default的數據庫做爲默認使用
	orm.RegisterDataBase("default", "mysql", "root:nola123456@/orm_test?charset=utf8")

	// 自動建立表 參數二開啓建立表 參數三開啓更新表【此句重點】
	orm.RunSyncdb("default", true, true)
}

func main() {
	beego.Run()
}

  運行會自動建立表,同步到數據庫,效果以下:

 

  建立的表終於同步到數據庫了~。~spa

  接着看看CRUD的使用:

  

package main

import (
	_ "github.com/Go-SQL-Driver/MySQL" // 引入driver
	//"github.com/astaxie/beego"
	"github.com/astaxie/beego/orm"

	"fmt"
	"useBeegoORM/models" // 引入model
	_ "useBeegoORM/routers"
)

func init() {
	// 註冊driver
	orm.RegisterDriver("mysql", orm.DRMySQL)

	// 須要在init中註冊定義的model
	orm.RegisterModel(new(models.User), new(models.Profile), new(models.Post), new(models.Tag))

	// 註冊數據庫 ORM必須註冊一個別名爲default的數據庫做爲默認使用
	orm.RegisterDataBase("default", "mysql", "root:nola123456@/orm_test?charset=utf8")

	// 自動建立表 參數二開啓建立表 參數三開啓更新表【此句重點】
	//orm.RunSyncdb("default", true, true)
}

func main() {
	// 對象的CRUD
	o := orm.NewOrm() // 建立一個Ormer
	user := new(models.User)
	profile := new(models.Profile)
	profile.Age = 30
	user.Name = "silence"
	user.Profile = profile
	fmt.Println(o.Insert(user)) // Insert
	fmt.Println(o.Insert(profile))

	user.Name = "Your"
	fmt.Println(o.Update(user)) // Update
	fmt.Println(o.Read(user))   // Read
	fmt.Println(o.Delete(user)) // Delete
	//beego.Run()
}

  查看數據:

  可增減數據,第2步submit,相應的會打印console。.net

  ORM的操做還需慢慢研究。有關GoLand配置數據庫以及配置遠程host,用過jetbrains公司的產品如PyCharm等,配置風格都相似。

  明天有時間寫個詳細步驟留存,供你們參考~

相關文章
相關標籤/搜索