• go 学习之gorm


    gorm是一个饱受好评的orm框架,此处数据库我们以mysql为例

    import (
        "github.com/jinzhu/gorm"
        _ "github.com/jinzhu/gorm/dialects/mysql"
    )
    
    var db *gorm.DB
    func init() {
        var err error
        db, err = gorm.Open("mysql", "<user>:<password>/<database>?charset=utf8&parseTime=True&loc=Local")#非常简便就创建了一个数据库连接
        if err != nil {
            panic(err)
        }
    }

    光创建连接还不够,我们还需要model

    type User struct {
        gorm.Model
        Name         string
        Age          sql.NullInt64   #  import "dataase/sql"
        Birthday     *time.Time   # import time
        Email        string  `gorm:"type:varchar(100);unique_index"`
        Role         string  `gorm:"size:255"` // 设置字段大小为255
        MemberNumber *string `gorm:"unique;not null"` // 设置会员号(member number)唯一并且不为空
        Num          int     `gorm:"AUTO_INCREMENT"` // 设置 num 为自增类型
        Address      string  `gorm:"index:addr"` // 给address字段创建名为addr的索引
        IgnoreMe     int     `gorm:"-"` // 忽略本字段
        }
    #这个结构体就对应我们的数据库表

    下一步我们就开始迁移数据库

    方法一 手动创建表:
    if !db.HasTable(&User{}) {
            db.Set("gorm:table_options", "ENGINE=InnoDB DEFAULT CHARSET=utf8").CreateTable(&User{})
            }
    
    方法二 自动迁移命令:
    db.AutoMigrate(&User{})
    //注意:自动迁移 只会 创建表、缺失的列、缺失的索引, 不会 更改现有列的类型或删除未使用的列,以此来保护您的数据。
    //也就是说我们修改user结构体 注销age属性,添加一个sex属性,自动迁移后,表结构还是存在age字段,添加sex字段

    然后我们来简单说说增删改查

    #
    user := User{Name: "Jinzhu",Sex:"1", Age: 18}
    db.Create(&user)
    #查询
    var user [] User
    // 获取第一条记录,按主键排序
    db.First(&user)  
    //// SELECT * FROM users ORDER BY id LIMIT 1;
    
    // 获取最后一条记录,按主键排序
    db.Last(&user)
    //// SELECT * FROM users ORDER BY id DESC LIMIT 1;
    
    // 获取所有记录
    db.Find(&users)
    //// SELECT * FROM users;
    
    // 使用主键获取记录
    db.First(&user, 10)
    //// SELECT * FROM users WHERE id = 10;
    Where查询条件 (简单SQL)
    // 获取第一个匹配记录
    db.Where("name = ?", "jinzhu").First(&user)
    //// SELECT * FROM users WHERE name = 'jinzhu' limit 1;
    
    // 获取所有匹配记录
    db.Where("name = ?", "jinzhu").Find(&users)
    //// SELECT * FROM users WHERE name = 'jinzhu';
    
    db.Where("name <> ?", "jinzhu").Find(&users)
    
    // IN
    db.Where("name in (?)", []string{"jinzhu", "jinzhu 2"}).Find(&users)
    
    // LIKE
    db.Where("name LIKE ?", "%jin%").Find(&users)
    
    // AND
    db.Where("name = ? AND age >= ?", "jinzhu", "22").Find(&users)
    
    // Time
    db.Where("updated_at > ?", lastWeek).Find(&users)
    
    db.Where("created_at BETWEEN ? AND ?", lastWeek, today).Find(&users)
    Where查询条件 (Struct & Map)
    注意:当使用struct查询时,GORM将只查询那些具有值的字段
    
    // Struct
    db.Where(&User{Name: "jinzhu", Age: 20}).First(&user)
    //// SELECT * FROM users WHERE name = "jinzhu" AND age = 20 LIMIT 1;
    
    // Map
    db.Where(map[string]interface{}{"name": "jinzhu", "age": 20}).Find(&users)
    //// SELECT * FROM users WHERE name = "jinzhu" AND age = 20;
    
    // 主键的Slice
    db.Where([]int64{20, 21, 22}).Find(&users)
    //// SELECT * FROM users WHERE id IN (20, 21, 22);
    1.2.3. Not条件查询
    db.Not("name", "jinzhu").First(&user)
    //// SELECT * FROM users WHERE name <> "jinzhu" LIMIT 1;
    
    // Not In
    db.Not("name", []string{"jinzhu", "jinzhu 2"}).Find(&users)
    //// SELECT * FROM users WHERE name NOT IN ("jinzhu", "jinzhu 2");
    
    // Not In slice of primary keys
    db.Not([]int64{1,2,3}).First(&user)
    //// SELECT * FROM users WHERE id NOT IN (1,2,3);
    
    db.Not([]int64{}).First(&user)
    //// SELECT * FROM users;
    
    // Plain SQL
    db.Not("name = ?", "jinzhu").First(&user)
    //// SELECT * FROM users WHERE NOT(name = "jinzhu");
    
    // Struct
    db.Not(User{Name: "jinzhu"}).First(&user)
    //// SELECT * FROM users WHERE name <> "jinzhu";
    
    #user为查询的结果数组
    
    删除操作
    // 删除存在的记录
    db.Delete(&email)
    //// DELETE from emails where id=10;
    
    // 为Delete语句添加额外的SQL选项
    db.Set("gorm:delete_option", "OPTION (OPTIMIZE FOR UNKNOWN)").Delete(&email)
    //// DELETE from emails where id=10 OPTION (OPTIMIZE FOR UNKNOWN);
    批量删除
    删除所有匹配记录
    
    db.Where("email LIKE ?", "%jinzhu%").Delete(Email{})
    //// DELETE from emails where email LIKE "%jinhu%";
    
    db.Delete(Email{}, "email LIKE ?", "%jinzhu%")
    //// DELETE from emails where email LIKE "%jinhu%";
    软删除
    如果模型有DeletedAt字段,它将自动获得软删除功能! 那么在调用Delete时不会从数据库中永久删除,而是只将字段DeletedAt的值设置为当前时间。
    
    db.Delete(&user)
    //// UPDATE users SET deleted_at="2013-10-29 10:23" WHERE id = 111;
    
    // 批量删除
    db.Where("age = ?", 20).Delete(&User{})
    //// UPDATE users SET deleted_at="2013-10-29 10:23" WHERE age = 20;
    
    // 软删除的记录将在查询时被忽略
    db.Where("age = 20").Find(&user)
    //// SELECT * FROM users WHERE age = 20 AND deleted_at IS NULL;
    
    // 使用Unscoped查找软删除的记录
    db.Unscoped().Where("age = 20").Find(&users)
    //// SELECT * FROM users WHERE age = 20;
    
    // 使用Unscoped永久删除记录
    db.Unscoped().Delete(&order)
    //// DELETE FROM orders WHERE id=10;
    
    更新操作
    更新全部字段
    Save将包括执行更新SQL时的所有字段,即使它没有更改
    
    db.First(&user)
    
    user.Name = "jinzhu 2"
    user.Age = 100
    db.Save(&user)
    
    //// UPDATE users SET name='jinzhu 2', age=100, birthday='2016-01-01', updated_at = '2013-11-17 21:34:10' WHERE id=111;
    更新更改字段
    如果只想更新更改的字段,可以使用Update, Updates
    
    更新单个属性(如果更改)
    db.Model(&user).Update("name", "hello")
    //// UPDATE users SET name='hello', updated_at='2013-11-17 21:34:10' WHERE id=111;
    
    // 使用组合条件更新单个属性
    db.Model(&user).Where("active = ?", true).Update("name", "hello")
    //// UPDATE users SET name='hello', updated_at='2013-11-17 21:34:10' WHERE id=111 AND active=true;
    
    // 使用`map`更新多个属性,只会更新这些更改的字段
    db.Model(&user).Updates(map[string]interface{}{"name": "hello", "age": 18, "actived": false})
    //// UPDATE users SET name='hello', age=18, actived=false, updated_at='2013-11-17 21:34:10' WHERE id=111;
    
    // 使用`struct`更新多个属性,只会更新这些更改的和非空白字段
    db.Model(&user).Updates(User{Name: "hello", Age: 18})
    //// UPDATE users SET name='hello', age=18, updated_at = '2013-11-17 21:34:10' WHERE id = 111;
    
    // 警告:当使用struct更新时,FORM将仅更新具有非空值的字段
    // 对于下面的更新,什么都不会更新为"",0,false是其类型的空白值
    db.Model(&user).Updates(User{Name: "", Age: 0, Actived: false})
    更新选择的字段
    如果您只想在更新时更新或忽略某些字段,可以使用Select, Omit
    
    db.Model(&user).Select("name").Updates(map[string]interface{}{"name": "hello", "age": 18, "actived": false})
    //// UPDATE users SET name='hello', updated_at='2013-11-17 21:34:10' WHERE id=111;
    
    db.Model(&user).Omit("name").Updates(map[string]interface{}{"name": "hello", "age": 18, "actived": false})
    //// UPDATE users SET age=18, actived=false, updated_at='2013-11-17 21:34:10' WHERE id=111;
    更新更改字段但不进行Callbacks
    以上更新操作将执行模型的BeforeUpdate, AfterUpdate方法,更新其UpdatedAt时间戳,在更新时保存它的Associations,如果不想调用它们,可以使用UpdateColumn, UpdateColumns
    
    // 更新单个属性,类似于`Update`
    db.Model(&user).UpdateColumn("name", "hello")
    //// UPDATE users SET name='hello' WHERE id = 111;
    
    // 更新多个属性,与“更新”类似
    db.Model(&user).UpdateColumns(User{Name: "hello", Age: 18})
    //// UPDATE users SET name='hello', age=18 WHERE id = 111;
    Batch Updates 批量更新
    Callbacks在批量更新时不会运行
    
    db.Table("users").Where("id IN (?)", []int{10, 11}).Updates(map[string]interface{}{"name": "hello", "age": 18})
    //// UPDATE users SET name='hello', age=18 WHERE id IN (10, 11);
    
    // 使用struct更新仅适用于非零值,或使用map[string]interface{}
    db.Model(User{}).Updates(User{Name: "hello", Age: 18})
    //// UPDATE users SET name='hello', age=18;
    
    // 使用`RowsAffected`获取更新记录计数
    db.Model(User{}).Updates(User{Name: "hello", Age: 18}).RowsAffected
  • 相关阅读:
    论语学习系列(一)
    如何编译生成 dll
    Lua学习系列(二)
    Lua学习系列(一)
    Promise对象
    ... 扩展运算符
    class类
    proxy [ˈprɒksi] 代理
    HBuilder 打包流程
    Generator [ˈdʒenəreɪtə(r)] 函数结构
  • 原文地址:https://www.cnblogs.com/tigerzhouv587/p/11454509.html
Copyright © 2020-2023  润新知