RecordNotFound returns false when there are no rows

Viewed 7345

I am having a problem with this library because this function returns false even when the given input is not in the database, when in fact it should return true.

type User struct {
    ID          uint      `gorm:"primary_key"`
    Username    string    `json:",omitempty"`
    Password    string    `json:",omitempty"`
    CreatedAt   time.Time `json:",omitempty"`
}

b, err := db.Con()
if err != nil {
    log.Panic(err)
}

defer db.Close()

// We want an empty struct
// Otherwise it will trigger the unique key constraint
user := []User{}

// Check if the username is taken
// BUX, MUST FIX: This always returns false for some reason
if db.Where(&User{Username: "MyUsername"}).Find(&user).RecordNotFound() == false {
    fmt.Println("Username found")
}

Why is it always returning false, even when the string is empty?

2 Answers

Looks like .RecordNotFound() is removed from the SDK for some reason.

Now use this for handling record not found errors

dbRresult := userHandler.db.Where("email = ?", email).First(&user)
if errors.Is(dbRresult.Error, gorm.ErrRecordNotFound) {
    // handle record not found
}

The following code should work as you expect it:

// We want an empty struct
user := User{} // We expect to have one (or no) user returned.

// Check if the username is taken
// Notice the use of First() instead of Find()
if !db.Where("username = ?", "MyUsername").First(&user).RecordNotFound() {
    fmt.Println("Username found, here's the user:", user)
} else {
    fmt.Println("Username not found")
}

As mkopriva already mentioned the ErrRecordNotFound will not trigger when you're working with slices.

Since you don't need slices (your username should be unique) we can:

  1. Reference not a slice of Users but a single User User{} instead of []User{}.

  2. Use gorms First() method instead of Find().

Related