使用golang、gin和gorm进行验证,类似于在数据库中验证电子邮件是否已存在。

huangapple go评论80阅读模式
英文:

Validation using golang, gin and gorm with postgres like email already exist in database

问题

我有类似这样的代码,并且我想检查电子邮件是否已经存在于数据库中:

func RegisterUser(c *gin.Context) {
    var user models.User
    if err := c.ShouldBindJSON(&user); err != nil {
        c.JSON(http.StatusBadRequest, gin.H{
            "message": err.Error(),
            "data":    "",
        })
        return
    }
    
    var existingUser models.User
    err := database.DB.Where("email = ?", user.Email).First(&existingUser).Error
    if err == nil {
        c.JSON(401, gin.H{"message": "Email already exists"})
        return
    }
    
    if !strings.Contains(user.Email, "@") {
        c.JSON(400, gin.H{"message": utils.ErrEmailWrong})
        return
    }

    if len(user.Password) < 4 {
        c.JSON(400, gin.H{"message": utils.ErrPasswordLength})
        return
    }

    database.DB.Create(&user)
    c.JSON(200, gin.H{
        "message": "CREATED",
    })
}

在这段代码中,每次都告诉我:Email already exists,只有第一次有效。

英文:

使用golang、gin和gorm进行验证,类似于在数据库中验证电子邮件是否已存在。I have something like this and I would like to check if email already exist in DB:

func RegisterUser(c *gin) {
var user models.User
if err := c.ShouldBindJSON(&amp;user); err != nil {
	c.JSON(http.StatusBadRequest, gin.H{
		&quot;messAge&quot;: err.Error(),
		&quot;data&quot;:    &quot;&quot;,
	})
	return
}
// **I TRIED SOEMTHING LIKE THIS**
err := database.DB.Find(&amp;user.Email).Error
if err != nil {
    c.JSON(401, gin.H{&quot;MESSAGE&quot;: &quot;Email ALREADY exist&quot;,
    return
}
// **but is not working, because ANY mail it give me error**


if !strings.Contains(user.Email, &quot;@&quot;) {
	c.JSON(400, gin.H{&quot;MESSAGE&quot;: utils.ErrEmailWrong})
	return
}

if len(user.Password) &lt; 4 {
	c.JSON(400, gin.H{&quot;MESSAGE&quot;: utils.ErrPasswordLength})
	return
}

database.DB.Create(&amp;user)
c.JSON(200, gin.H{
	&quot;MESSAGE&quot;: &quot;CREATED&quot;,
})
}

With this code, every time is telling me that : Email already exist, only works for the first time.

答案1

得分: 2

请阅读文档:
https://gorm.io/docs/query.html

var userFind models.User
database.DB.Where("email = ?", user.Email).First(&userFind)
英文:

plase read the document:
https://gorm.io/docs/query.html

var userFind models.User
database.DB.Where(&quot;email = ?&quot;, user.Email).First(&amp;userFind)

答案2

得分: 2

由于您的结构对象不是切片,您应该使用ErrRecordNotFound

注意:ErrRecordNotFound仅适用于FirstLastTake这些预期返回一些结果的方法。在V2中,RecordNotFound已被移除。

if err != nil {
    if errors.Is(err, gorm.ErrRecordNotFound) {
        c.JSON(401, gin.H{"MESSAGE": "Email Not Found"})
        return
    }
    c.JSON(401, gin.H{"MESSAGE": "Your Message"})
    return
}

或者

如果您想避免ErrRecordNotFound错误,可以使用Find方法,例如db.Limit(1).Find(&user)Find方法接受结构体和切片数据。然后可以像这样检查:

result.RowsAffected // 返回找到的记录数

为了更好地理解,请参考以下链接:https://gorm.io/docs/v2_release_note.html#ErrRecordNotFoundhttps://gorm.io/docs/query.html

如果您想要在数据库中添加记录,即使电子邮件已存在,您应该删除唯一约束,并在创建记录时检查错误。如果记录成功创建,则返回成功响应,否则返回适当的错误消息。

英文:

Since, your struct object is not a slice. You should use ErrRecordNotFound.

Note : ErrRecordNotFound only works with First, Last, Take which is expected to return some result. And RecordNotFound is removed in V2.

if err != nil {
     if errors.Is(err, gorm.ErrRecordNotFound){
           c.JSON(401, gin.H{&quot;MESSAGE&quot;: &quot;Email Not Found&quot;,
           return

     }
    c.JSON(401, gin.H{&quot;MESSAGE&quot;: &quot;Your Message&quot;,
    return
}

OR

If you want to avoid the ErrRecordNotFound error, you could use Find like db.Limit(1).Find(&amp;user), the Find method accepts both struct and slice data. And check like this :

result.RowsAffected // returns count of records found

For better understanding refer the link here : https://gorm.io/docs/v2_release_note.html#ErrRecordNotFound and https://gorm.io/docs/query.html

And, If you want to add record in DB though email exist then you should remove unique constraint and also check the error while creating the record. If record successfully created then return success response else return the appropriate error message.

答案3

得分: 2

  1. 在绑定数据之后、进行数据库查询之前,应该验证输入。
  2. 将你的电子邮件列更改为唯一列。
  3. 尝试将经过验证的数据插入数据库。
    • 如果成功 => 返回200(表示没有相似的电子邮件)
    • 如果出错 => 检查错误代码

例如:

func IsUniqueContraintViolation(err error) bool {
    if pgError, ok := err.(*pgconn.PgError); ok && errors.Is(err, pgError) {
        if pgError.Code == "23505" {
            return true
        }
    }
    
    return false
}

要获取更多信息,你可以查看GoDoc pg lib可能的错误代码,然后返回适当的错误代码。

顺便说一下,希望你不要将明文密码保存到数据库中 使用golang、gin和gorm进行验证,类似于在数据库中验证电子邮件是否已存在。

英文:
  1. you should validate the input after binding and before db queries
  2. alter your email column to be unique
  3. try to insert the validated data to db
    • if success => 200 (there was no similar email)
    • if err => check err code

for example:

func IsUniqueContraintViolation(err error) bool {
		if pgError, ok := err.(*pgconn.PgError); ok &amp;&amp; errors.Is(err, pgError) {
			if pgError.Code == &quot;23505&quot; {
				return true
			}
		}
	
		return false
	}

For more Information, you should look GoDoc pg lib and Possible Error Codes
and then, then you can return a suitable error code

btw. hopefully you don't save clear passwords to db 使用golang、gin和gorm进行验证,类似于在数据库中验证电子邮件是否已存在。

答案4

得分: 2

终于成功了!感谢所有回答问题的人!

使用golang、gin和gorm进行验证,类似于在数据库中验证电子邮件是否已存在。

英文:

ITS FINALLY WORKING ! Thanks for everyone thats answered !

使用golang、gin和gorm进行验证,类似于在数据库中验证电子邮件是否已存在。

huangapple
  • 本文由 发表于 2022年1月7日 10:16:55
  • 转载请务必保留本文链接:https://go.coder-hub.com/70615863.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定