69 lines
2.4 KiB
Go
69 lines
2.4 KiB
Go
package models
|
||
|
||
// userapp 是工程名称
|
||
// models 是 userapp 下的一个包,包含了用户相关的结构体和函数
|
||
// common 是 models 下的一个包,包含了 Base 结构体
|
||
import (
|
||
"fmt"
|
||
"userapp/models/common"
|
||
|
||
"golang.org/x/crypto/bcrypt"
|
||
)
|
||
|
||
// password 字段是私有的,外部无法直接访问,可以通过 NewUser 函数来创建用户对象,并设置密码
|
||
func NewUser(name, email string, age int, pwd string) *User {
|
||
return &User{
|
||
Name: name,
|
||
Email: email,
|
||
Age: age,
|
||
password: pwd, // 内部使用私有函数
|
||
}
|
||
}
|
||
|
||
type User struct {
|
||
// 嵌套 common.Base 结构体,包含 ID、CreatedAt 和 UpdatedAt 字段
|
||
common.Base
|
||
|
||
Name string
|
||
Email string
|
||
Age int
|
||
|
||
// 私有字段(包外不可访问)
|
||
password string
|
||
}
|
||
|
||
// GetPasswordHash 公开方法:获取密码哈希(受控访问)
|
||
// 通过这个方法,外部代码可以获取密码的哈希值,但无法直接获取明文密码
|
||
// 这种设计可以保护密码字段的安全性,同时提供必要的访问接口
|
||
// 核心是我们可以直接控制密码访问的逻辑
|
||
func (u *User) GetPasswordHash() string {
|
||
fmt.Println("获取密码")
|
||
|
||
// 使用 bcrypt 库对密码进行加密
|
||
// 当前我们引入我新的库的时候,go mod tidy 会自动下载并更新 go.mod 和 go.sum 文件
|
||
bcryptPwd, _ := bcrypt.GenerateFromPassword([]byte(u.password), bcrypt.DefaultCost)
|
||
return string(bcryptPwd)
|
||
}
|
||
|
||
// SetPasswordHash 公开方法:设置密码(受控访问)
|
||
func (u *User) SetPasswordHash(password string) {
|
||
fmt.Println("设置密码")
|
||
u.password = password
|
||
}
|
||
|
||
// CheckPasswordHash 公开方法:检查密码哈希是否匹配
|
||
// 真实的场景,数据库里面不会存储用户的明文密码,而是存储密码的哈希值。
|
||
// 我们判断一个用户的密码是否正确,是通过比对 hash
|
||
// plan_password 是用户输入的明文密码 -- hash -> u.GetPasswordHash() 来模拟数据库存储的密码哈希值
|
||
// bcrypt.CompareHashAndPassword() 函数会将用户输入的明文密码进行哈希计算,并与存储的哈希值进行比较,如果匹配则返回 nil,否则返回错误
|
||
func (u *User) CheckPasswordHash(password string) bool {
|
||
fmt.Println("检查密码")
|
||
err := bcrypt.CompareHashAndPassword([]byte(u.GetPasswordHash()), []byte(password))
|
||
return err == nil
|
||
}
|
||
|
||
func init() {
|
||
// newUserWithDB()
|
||
fmt.Println("models 包的 init 函数被调用")
|
||
}
|