go-gorm / sharding

High performance table sharding plugin for Gorm.
MIT License
276 stars 60 forks source link

i test example with Mysql, i use Model to use CURD Interface, it return error #47

Closed VagrantPi closed 2 years ago

VagrantPi commented 2 years ago

Your Question

I try to modify the example code to test MySQL sharding

But when I use model interface to access, there will be an error

I change it to Table, is OK

I think this issue like #14 ?

my env:

examples/order.go

package main

import (
    "fmt"

    "gorm.io/driver/mysql"
    "gorm.io/gorm"
    "gorm.io/gorm/logger"
    "gorm.io/gorm/schema"
    "gorm.io/sharding"
)

type Order struct {
    ID        int64 `gorm:"primarykey"`
    UserID    int64
    ProductID int64
}

func main() {
    connection := fmt.Sprintf("test:test@tcp(127.0.0.1:3306)/?parseTime=true")
    db, err := gorm.Open(mysql.New(mysql.Config{
        DSN: connection,
    }), &gorm.Config{
        NamingStrategy: schema.NamingStrategy{
            SingularTable: true,
        },
        Logger: logger.Default.LogMode(logger.Silent),
    })
    if err != nil {
        fmt.Println("err", err)
    }

    db.Exec("USE " + "MyTable")

    for i := 0; i < 4; i += 1 {
        table := fmt.Sprintf("orders_%d", i)
        db.Exec(`DROP TABLE IF EXISTS ` + table)
        db.Table(table).AutoMigrate(&Order{})
    }
    // db.AutoMigrate(&Order{})

    middleware := sharding.Register(sharding.Config{
        ShardingKey:         "user_id",
        NumberOfShards:      4,
        PrimaryKeyGenerator: sharding.PKSnowflake,
    }, "orders")
    db.Use(middleware)

    // this record will insert to orders_02
        // !!!!!!!!!!!!!!!!!!  it returm err: Error 1146: Table 'MyTable.order' doesn't exist
    // err = db.Create(&Order{UserID: 2}).Error
    err = db.Table("orders").Create(&Order{UserID: 2}).Error
    if err != nil {
        fmt.Println("err1", err)
    }

    // this record will insert to orders_03
    err = db.Exec("INSERT INTO orders(user_id) VALUES(?)", int64(3)).Error
    if err != nil {
        fmt.Println("err2", err)
    }

    // this will throw ErrMissingShardingKey error
    err = db.Exec("INSERT INTO orders(product_id) VALUES(1)").Error
    fmt.Println("err3", err)

    // this will redirect query to orders_02
    var orders []Order
        // !!!!!!!!!!!!!!!!!!  it returm err: Error 1146: Table 'MyTable.order' doesn't exist
    // err = db.Model(&Order{}).Where("user_id", int64(3)).Find(&orders).Error
    err = db.Table("orders").Where("user_id", int64(2)).Find(&orders).Error
    if err != nil {
        fmt.Println("err4", err)
    }
    fmt.Printf("%#v\n", orders)

    // Raw SQL also supported
    db.Raw("SELECT * FROM orders WHERE user_id = ?", int64(3)).Scan(&orders)
    fmt.Printf("%#v\n", orders)

    // this will throw ErrMissingShardingKey error
        // !!!!!!!!!!!!!!!!!!  it returm err: Error 1146: Table 'MyTable.order' doesn't exist
    // err = db.Model(&Order{}).Where("product_id", "1").Find(&orders).Error
    err = db.Table("orders").Where("product_id", "1").Find(&orders).Error
    fmt.Println("err5", err)

    // Update and Delete are similar to create and query
    err = db.Exec("UPDATE orders SET product_id = ? WHERE user_id = ?", 2, int64(3)).Error
    fmt.Println("err6", err) // nil
    err = db.Exec("DELETE FROM orders WHERE product_id = 3").Error
    fmt.Println("err7", err) // ErrMissingShardingKey
}

see // !!!!!!!!!!!!!!!!!! it returm err: Error 1146: Table 'MyTable.order' doesn't exist

The document you expected this should be explained

Expected answer

i want use Model to access, not Table

huacnlee commented 2 years ago

Remove SingularTable: true

VagrantPi commented 2 years ago

thanks