stay Gin framework building Golang interface project template -- controller layer In this chapter, we briefly introduce how to use gin to create a simple api interface, but in the actual development, it is not a complete project if there is only interface definition and no database interaction. In this project, gorm is used as a framework of persistence layer. The official document address is: gorm , MySQL is selected as the database. The following describes in detail how to use gorm to complete database interaction.
Step 1: introduce gorm dependency and MySQL driver
It is easy to introduce gorm dependency and MySQL driver. Execute the following command:
// Introducing gorm dependency go get -u gorm.io/gorm
// Introducing MySQL driver go get -u gorm.io/driver/mysql
Step 2: complete the initialization of the database
In an enterprise project, the data source information will not be written directly into the code. There will be a configuration file to maintain the project configuration information uniformly. Here, yml format is used as the configuration file. Let's mention here that some projects may use the tom file as the project configuration file. Although the official says it has many advantages, I personally prefer yml, according to my personal choice. The configuration information is as follows:
- configuration file
server: port: 8848 # Data source configuration datasource: driverName: mysql host: 127.0.0.1 port: "3306" dbname: gin_temp username: root password: root123 charset: utf8 sslmode: disable loc: Asia/Shanghai
Viper is used to read the configuration file. The dependency command of viper is introduced: go get -u # GitHub com/spf13/viper . Next, you need to add the initialization of the configuration file in the project entry file (main.go), and the configuration code is in main Go file creates a new function processing, as follows:
func InitConfig() { var envPara = "/src/config" workDir, _ := os.Getwd() viper.SetConfigName("base") viper.SetConfigType("yml") viper.AddConfigPath(workDir + envPara) fmt.Println(workDir) err := viper.ReadInConfig() if err != nil { panic(err) } }
- database initialized
The initialization code for creating a database under the database package is as follows:
var DB *gorm.DB func InitDB() *gorm.DB { host := viper.GetString("datasource.host") port := viper.Get("datasource.port") database := viper.GetString("datasource.dbname") username := viper.GetString("datasource.username") password := viper.GetString("datasource.password") charset := viper.GetString("datasource.charset") loc := viper.GetString("datasource.loc") dns := fmt.Sprintf("%s:%s@tcp(%s:%s)/%s?charset=%s&parseTime=true&loc=%s", username, password, host, port, database, charset, url.QueryEscape(loc)) db, err := gorm.Open(mysql.Open(dns), &gorm.Config{}) if err != nil { panic("failed to connect database, err: " + err.Error()) } DB = db return db }
- Initialize profile and database connections
Add configuration file initialization and database connection in the entry of the project (main.go), as follows:
func main() { InitConfig() database.InitDB() r := gin.New() r = route.PathRoute(r) r.Run() }
Step 3: create a data table script
It's very simple here. Post the script directly:
CREATE TABLE `t_user` ( `user_id` bigint(20) NOT NULL COMMENT 'Primary key', `user_name` varchar(128) COLLATE utf8mb4_bin DEFAULT NULL COMMENT 'full name', `age` int(11) DEFAULT NULL COMMENT 'Age', `gender` int(1) DEFAULT NULL COMMENT 'Gender (1: male, 2: female)', `create_time` timestamp NULL DEFAULT NULL ON UPDATE CURRENT_TIMESTAMP COMMENT 'Creation time', PRIMARY KEY (`user_id`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin;
Step 4: create a table mapping
Create a mapping entity of the data table in the project. The code is as follows:
type User struct { database.CommonTableData UserId int64 `gorm:"primaryKey; not null" json:"userId" description:"user id"` UserName string `gorm:"varchar(128); not null" json:"userName" description:"user name"` Age int8 `gorm:"varchar(128); not null" json:"age" description:"Age"` Gender int8 `gorm:"varchar(256); not null" json:"gender" description:"Gender"` } func (User) TableName() string { return "t_user" }
gorm's tag is used here. You can check it directly in the official documents.
Step 5: definition and implementation of persistence layer interface
Here are the basic knowledge of go language, so I won't introduce it more, as follows:
type IUserRepository interface { FindUser(*int64) (*entity.User, error) } type UserManagerRepository struct { } func NewUserManagerRepository() IUserRepository { return &UserManagerRepository{} } func (u UserManagerRepository) FindUser(userId *int64) (*entity.User, error) { var user entity.User database.DB.Where("user_id = ?", &userId).First(&user) return &user, nil }
Step 6: write service logic
After the persistence layer obtains the data, the code related to business logic will be added to the service layer. Here is a relatively simple data query, as follows:
type IUserService interface { FindUserInfo(*gin.Context, *int64) } type UserService struct { userRepository repository.IUserRepository } func NewUserService(repository repository.IUserRepository) IUserService { return &UserService{repository} } func (us UserService) FindUserInfo(ctx *gin.Context, userId *int64) { user, _ := us.userRepository.FindUser(userId) if user == nil { response.Success(ctx, constant.DataIsNilCode, constant.DataIsNilMsg, nil) } else { userVo := &vo.UserVO{ UserId: user.UserId, UserName: user.UserName, Age: user.Age, Gender: user.Gender, } response.Success(ctx, constant.SelectSuccessCode, constant.SelectSuccessMsg, userVo) } }
Step 7: adjust the controller code
Adjust the code of the control layer in the previous chapter as follows:
type UserController struct { userService service.IUserService } func UserRegister(userGrp *gin.RouterGroup) { userRepository := repository.NewUserManagerRepository() userService := service.NewUserService(userRepository) userController := &UserController{userService: userService} userGrp.Use().POST("/findUser", userController.findUser) } func (uc UserController) findUser(ctx *gin.Context) { var userQuery query.FindUserQuery _ = ctx.Bind(&userQuery) uc.userService.FindUserInfo(ctx, &userQuery.UserId) }
Step 8: run the project
Start the project request interface as follows:
So far, the project integration gorm framework has completed the interaction of the database, and the relevant codes of the project have been submitted to github, address: https://github.com/WXCTX007/golang.git