371 lines
10 KiB
Go
371 lines
10 KiB
Go
package controllers
|
|
|
|
import (
|
|
"58team_blog/internal/application/commands"
|
|
"58team_blog/internal/application/queries"
|
|
"58team_blog/internal/application/services"
|
|
"58team_blog/internal/interfaces/api/mapper"
|
|
"58team_blog/internal/interfaces/api/requests"
|
|
"58team_blog/internal/interfaces/api/responses"
|
|
"58team_blog/internal/utils"
|
|
"log"
|
|
"net/http"
|
|
"strings"
|
|
|
|
"github.com/gin-contrib/sessions"
|
|
"github.com/gin-gonic/gin"
|
|
"github.com/google/uuid"
|
|
)
|
|
|
|
type UserController struct {
|
|
adminName string
|
|
adminPass string
|
|
service *services.UserService
|
|
}
|
|
|
|
func CreateUserController(service *services.UserService, adminName string, adminPass string) UserController {
|
|
return UserController{
|
|
service: service,
|
|
adminName: adminName,
|
|
adminPass: adminPass,
|
|
}
|
|
}
|
|
|
|
// @Summary Login
|
|
// @Description Login user into system
|
|
// @Tags user
|
|
// @Accept json
|
|
// @Produce json
|
|
// @Param request body requests.LoginUserRequest true "User login data"
|
|
// @Success 200
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 401 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /login [post]
|
|
func (r *UserController) Login(c *gin.Context) {
|
|
session := sessions.Default(c)
|
|
|
|
var request requests.LoginUserRequest
|
|
if err := c.BindJSON(&request); err != nil {
|
|
log.Println("User invalid request: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusBadRequest, err.Error())
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
// Check admin login
|
|
if request.Username == r.adminName && request.Password == r.adminPass {
|
|
session.Set("user", uuid.NewString())
|
|
if err := session.Save(); err != nil {
|
|
log.Println("User save session error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusInternalServerError, "Internal server error")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
c.Status(http.StatusOK)
|
|
return
|
|
}
|
|
|
|
user, err := r.service.FindByName(queries.UserFindByNameQuery{Name: request.Username})
|
|
if err != nil {
|
|
resp := utils.HandleError(err)
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
pass, err := utils.EncryptPassword(request.Password)
|
|
if err != nil {
|
|
log.Println("User encrypt password error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusInternalServerError, "Internal server error")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
if utils.CheckPassword(user.Result.Password, pass) {
|
|
log.Println("Pass ", user.Result.Password, " != ", pass)
|
|
resp := responses.CreateErrorResponse(http.StatusUnauthorized, "Authentication error")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
session.Set("user", user.Result.Id.String())
|
|
if err := session.Save(); err != nil {
|
|
log.Println("User save session error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusInternalServerError, "Internal server error")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
c.Status(http.StatusOK)
|
|
}
|
|
|
|
// @Summary Create new user
|
|
// @Description Creates new user in system
|
|
// @Tags user
|
|
// @Produce json
|
|
// @Success 200
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /logout [get]
|
|
// @Security BasicAuth
|
|
func (r *UserController) Logout(c *gin.Context) {
|
|
session := sessions.Default(c)
|
|
user := session.Get("user")
|
|
if user == nil {
|
|
c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid session token"})
|
|
return
|
|
}
|
|
session.Delete("user")
|
|
if err := session.Save(); err != nil {
|
|
c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to save session"})
|
|
return
|
|
}
|
|
c.Status(http.StatusOK)
|
|
}
|
|
|
|
// @Summary Create new user
|
|
// @Description Creates new user in system
|
|
// @Tags user
|
|
// @Accept json
|
|
// @Produce json
|
|
// @Param request body requests.CreateUserRequest true "User data"
|
|
// @Success 201 {object} responses.UserResponse
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 409 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /team/ [post]
|
|
// @Security BasicAuth
|
|
func (r *UserController) Post(c *gin.Context) {
|
|
var request requests.CreateUserRequest
|
|
if err := c.BindJSON(&request); err != nil {
|
|
log.Println("User invalid request: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusBadRequest, err.Error())
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
encrypted_password, err := utils.EncryptPassword(request.Password)
|
|
if err != nil {
|
|
log.Println("User encrypt password error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusInternalServerError, "Internal server error")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
cmd := commands.CreateUserCommand{
|
|
Username: request.Username,
|
|
Password: encrypted_password,
|
|
Role: request.Role,
|
|
Name: request.Name,
|
|
Speciality: request.Speciality,
|
|
Description: request.Description,
|
|
Skills: strings.Join(request.Skills, ";"),
|
|
Avatar: request.Avatar,
|
|
JoinDate: request.JoinDate,
|
|
Projects: strings.Join(request.Projects, ";"),
|
|
Motto: request.Motto,
|
|
}
|
|
|
|
user, err := r.service.Create(cmd)
|
|
if err != nil {
|
|
resp := utils.HandleError(err)
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
response := mapper.ResponseFromUserResult(user)
|
|
|
|
c.JSON(http.StatusCreated, response)
|
|
}
|
|
|
|
// @Summary Find user by id
|
|
// @Description Find user by id
|
|
// @Tags user
|
|
// @Accept json
|
|
// @Produce json
|
|
// @Param id path string true "user id"
|
|
// @Success 200 {object} responses.UserResponse
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 404 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /team/{id} [get]
|
|
func (r *UserController) FindById(c *gin.Context) {
|
|
id_path := c.Param("id")
|
|
|
|
id, err := uuid.Parse(id_path)
|
|
if err != nil {
|
|
log.Println("User id error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusBadRequest, "Invalid user id")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
query := queries.UserFindByIdQuery{
|
|
Id: id,
|
|
}
|
|
|
|
user, err := r.service.FindById(query)
|
|
if err != nil {
|
|
resp := utils.HandleError(err)
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
response := mapper.ResponseFromUserFindByIdResult(user)
|
|
c.JSON(http.StatusOK, response)
|
|
}
|
|
|
|
// @Summary Find user by username
|
|
// @Description Find user by username
|
|
// @Tags user
|
|
// @Accept json
|
|
// @Produce json
|
|
// @Param name path string true "User name"
|
|
// @Success 200 {object} responses.UserResponse
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 404 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /team/name/{name} [get]
|
|
func (r *UserController) FindByName(c *gin.Context) {
|
|
name := c.Param("name")
|
|
|
|
query := queries.UserFindByNameQuery{
|
|
Name: name,
|
|
}
|
|
|
|
user, err := r.service.FindByName(query)
|
|
if err != nil {
|
|
resp := utils.HandleError(err)
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
response := mapper.ResponseFromUserFindByNameResult(user)
|
|
|
|
c.JSON(http.StatusOK, response)
|
|
}
|
|
|
|
// @Summary Get all users
|
|
// @Description Return all registered users
|
|
// @Tags user
|
|
// @Produce json
|
|
// @Success 200 {object} responses.UserResponseList
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /members/ [get]
|
|
func (r *UserController) GetAll(c *gin.Context) {
|
|
users, err := r.service.GetAll()
|
|
if err != nil {
|
|
resp := utils.HandleError(err)
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
resp := mapper.ResponseFromUserGetAllResult(users)
|
|
|
|
c.JSON(http.StatusOK, resp)
|
|
}
|
|
|
|
// @Summary Change user
|
|
// @Description Change the user's name and password
|
|
// @Tags user
|
|
// @Accept json
|
|
// @Produce json
|
|
// @Param id path string true "User id"
|
|
// @Param request body requests.PutUserRequest true "User data"
|
|
// @Success 200 {object} responses.UserResponse
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 404 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /team/{id} [put]
|
|
// @Security BasicAuth
|
|
func (r *UserController) Put(c *gin.Context) {
|
|
var request requests.PutUserRequest
|
|
id_path := c.Param("id")
|
|
|
|
id, err := uuid.Parse(id_path)
|
|
if err != nil {
|
|
log.Println("User id error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusBadRequest, "Invalid user ID")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
if err := c.BindJSON(&request); err != nil {
|
|
log.Println("User request error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusBadRequest, err.Error())
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
password, err := utils.EncryptPassword(request.Password)
|
|
if err != nil {
|
|
log.Println("User password encrypt error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusInternalServerError, "Internal server error")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
skills := strings.Join(request.Skills, ";")
|
|
projects := strings.Join(request.Projects, ";")
|
|
|
|
cmd := commands.UpdateUserCommand{
|
|
Id: id,
|
|
Username: request.Username,
|
|
Name: request.Name,
|
|
Password: password,
|
|
Role: request.Role,
|
|
Speciality: request.Speciality,
|
|
Description: request.Description,
|
|
Skills: skills,
|
|
Avatar: request.Avatar,
|
|
Projects: projects,
|
|
Motto: request.Motto,
|
|
}
|
|
|
|
user, err := r.service.Update(cmd)
|
|
if err != nil {
|
|
resp := utils.HandleError(err)
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
response := mapper.ResponseFromUserResult(user)
|
|
c.JSON(http.StatusOK, response)
|
|
}
|
|
|
|
// @Summary Delete user
|
|
// @Description Delete user
|
|
// @Tags user
|
|
// @Produce json
|
|
// @Param id path string true "User id"
|
|
// @Success 200
|
|
// @Failure 400 {object} responses.ErrorResponse
|
|
// @Failure 404 {object} responses.ErrorResponse
|
|
// @Failure 500 {object} responses.ErrorResponse
|
|
// @Router /team/{id} [delete]
|
|
// @Security BasicAuth
|
|
func (r *UserController) Delete(c *gin.Context) {
|
|
id_path := c.Param("id")
|
|
|
|
id, err := uuid.Parse(id_path)
|
|
if err != nil {
|
|
log.Println("User id error: ", err)
|
|
resp := responses.CreateErrorResponse(http.StatusBadRequest, "Invalid user id")
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
cmd := commands.DeleteUserCommand{
|
|
Id: id,
|
|
}
|
|
|
|
if err := r.service.Delete(cmd); err != nil {
|
|
resp := utils.HandleError(err)
|
|
c.JSON(resp.ErrorCode, resp)
|
|
return
|
|
}
|
|
|
|
c.Status(http.StatusOK)
|
|
}
|