项目搭建 | 青训营笔记

129 阅读3分钟

这是我参与「第三届青训营 -后端场」笔记创作活动的的第3篇笔记。

1. 项目搭建

(1)技术栈

后端采用golang框架gin

前端采用vue

数据库使用MySQL,拟定后期加入redis作为缓存数据库

使用gorm操作数据库

gin-jwt进行登录及鉴权操作

(2)初始化项目

下载gin

 go get -u github.com/gin-gonic/gin

目录结构

目录结构.png

配置文件

2. 数据库设计

(1)MySQL

user表

-- auto-generated definition
create table user
(
    id        int auto_increment
        primary key,
    username  varchar(50)  default ''                null comment '账号',
    password  varchar(255) default ''                null comment '密码',
    nickname  varchar(50)  default ''                null comment '用户名',
    avatar    varchar(255) default ''                null comment '头像地址',
    status    int          default 1                 not null comment '权限状态',
    major     varchar(50)  default ''                null comment '专业',
    class     varchar(50)  default ''                null comment '班级',
    create_at datetime     default CURRENT_TIMESTAMP null comment '创建时间',
    update_at datetime     default CURRENT_TIMESTAMP null comment '修改时间',
    constraint user_username_uindex
        unique (username)
);

(2)models

Model

package models

import "time"

// Model 定义基础模型类,实现复用
type Model struct {
	ID       uint      `gorm:"primaryKey" json:"id"` // id
	CreateAt time.Time `json:"createAt"`             // 创建时间
	UpdateAt time.Time `json:"updateAt"`             // 更新时间
}

User

package models

// Login jwt登录使用
type Login struct {
	Username string `form:"username" json:"username" binding:"required"`
	Password string `form:"password" json:"password" binding:"required"`
}
type User struct {
	Model
	Username string `json:"username"` // 账号
	Password string `json:"password"` // 密码
	Nickname string `json:"nickname"` // 昵称
	Avatar   string `json:"avatar"`   // 头像
	Status   int    `json:"status"`   // 权限状态
	Major    string `json:"major"`    // 专业
	Class    string `json:"class"`    // 班级
}

// TableName 设置User的表名为user
func (User) TableName() string {
	return "user"
}

func (u User) ToMap() map[string]interface{} {
	return map[string]interface{}{
		"id":       u.ID,
		"username": u.Username,
		"nickname": u.Nickname,
		"avatar":   u.Avatar,
		"status":   u.Status,
		"major":    u.Major,
		"class":    u.Class,
		"createAt": u.CreateAt,
		"updateAt": u.UpdateAt,
	}
}

3. dao数据库操作

go get	gorm.io/driver/mysql  // 安装mysql驱动
go get	gorm.io/gorm  

(1)初始化,连接数据库

package dao

import (
	"fmt"
	"gorm.io/driver/mysql"
	"gorm.io/gorm"
	"k8s_deploy_gin/pkg/setting"
	"log"
)

var db *gorm.DB

func init() {
	var (
		err                          error
		dbName, user, password, host string
	)
	sec, err := setting.Cfg.GetSection("database")
	if err != nil {
		log.Fatal(2, "Fail to get section 'database': %v", err)
	}

	dbName = sec.Key("NAME").String()
	user = sec.Key("USER").String()
	password = sec.Key("PASSWORD").String()
	host = sec.Key("HOST").String()

	dsn := fmt.Sprintf("%s:%s@tcp(%s)/%s?charset=utf8&parseTime=True&loc=Local",
		user, password, host, dbName)

	db, err = gorm.Open(mysql.Open(dsn), &gorm.Config{})
	if err != nil {
		log.Println(err)
	}
	sqlDb, err := db.DB()
	if err != nil {
		log.Fatal(err)
	}
	sqlDb.SetMaxIdleConns(10)
	sqlDb.SetMaxOpenConns(100)
	//defer func() {
	//	sqlDb.Close()
	//}()
}

(2) 通过gorm操作user

package dao

import (
	"golang.org/x/crypto/bcrypt"
	"k8s_deploy_gin/models"
	"time"
)

var users []models.User

// GetUserList 分页返回用户列表(page第几页,pageSize每页几条数据)
func GetUserList(page int, pageSize int) (int, []interface{}) {
	// 分页用户列表数据
	userList := make([]interface{}, 0, len(users))
	// 计算偏移量 Offset指定开始返回记录前要跳过的记录数。
	offset := (page - 1) * pageSize
	// 查看所有的user,并获取user总数
	var total int64
	result := db.Order("status DESC").Offset(offset).Limit(pageSize).Where("status > ?", "0").Find(&users).Count(&total)
	// 如果返回的数据为0条
	if result.RowsAffected == 0 {
		return 0, userList
	}
	// 返回的user总数,用count更好
	//total := count

	// 查询数据
	result.Offset(offset).Limit(pageSize).Find(&users)
	for _, userSingle := range users {
		userItemMap := userSingle.ToMap()
		userList = append(userList, userItemMap)
	}
	return int(total), userList
}

// GetUserById 通过id获取user
func GetUserById(id int) *models.User {
	user := models.User{}
	db.First(&user, id)
	return &user
}

// GetUserByName 通过name获取user
func GetUserByName(name string) *models.User {
	user := models.User{}
	result := db.Where("username = ?", name).First(&user)
	if result.RowsAffected == 0 {
		return nil
	}
	return &user
}

// CreateUser 新增user
func CreateUser(data map[string]interface{}) bool {
	result := db.Create(&models.User{
		Model: models.Model{
			CreateAt: time.Now(),
			UpdateAt: time.Now(),
		},
		Username: data["username"].(string),
		Password: data["password"].(string),
		Nickname: data["nickname"].(string),
		Status:   1,
	})

	if result.RowsAffected == 0 {
		return false
	}
	return true
}

// UpdateUser 更新user
func UpdateUser(u *models.User) bool {
	u.UpdateAt = time.Now()
	result := db.Save(&u)
	if result.RowsAffected == 0 {
		return false
	}
	return true
}

// CheckUser 检查密码是否正确
func CheckUser(username string, password string) bool {
	user := GetUserByName(username)
	if user == nil {
		return false
	}
	err := bcrypt.CompareHashAndPassword([]byte(user.Password), []byte(password))
	if err != nil {
		return false
	}
	return true
}