Implement yookassa client

This commit is contained in:
2026-03-19 00:09:25 +03:00
parent 075a53f6ef
commit dd2c360cf6
15 changed files with 411 additions and 114 deletions

View File

@@ -2,8 +2,6 @@ package user
import (
"encoding/json"
"errors"
"log/slog"
"net/http"
"time"
@@ -12,6 +10,7 @@ import (
"go.uber.org/fx"
"golang.org/x/crypto/bcrypt"
"payouts/internal/api/common"
"payouts/internal/config"
"payouts/internal/models"
"payouts/internal/service/cache"
@@ -52,28 +51,21 @@ func NewUserHandler(p Params) (Handler, error) {
func (u *userHandler) UserRegister(w http.ResponseWriter, r *http.Request) {
defer r.Body.Close()
errResponse := func(message string, err error, status int) {
http.Error(w, errors.Join(errors.New(message), err).Error(), status)
}
user := models.UserRegister{}
err := json.NewDecoder(r.Body).Decode(&user)
if err != nil {
slog.Error("Failed to get password hash", slog.String("error", err.Error()))
errResponse("failed to decode request body", err, http.StatusBadRequest)
common.ErrorResponse(w, "failed to decode request body", err, http.StatusBadRequest)
return
}
if user.Passwd != user.PasswdCfm || len(user.Passwd) == 0 || len(user.Phone) == 0 || len(user.TIN) == 0 {
slog.Error("No required parameters passed")
errResponse("invalid parameters", nil, http.StatusBadRequest)
common.ErrorResponse(w, "invalid parameters", nil, http.StatusBadRequest)
return
}
hashedPassword, err := bcrypt.GenerateFromPassword([]byte(user.Passwd), bcrypt.DefaultCost)
if err != nil {
slog.Error("Failed to get password hash", slog.String("error", err.Error()))
errResponse("internal error", nil, http.StatusInternalServerError)
common.ErrorResponse(w, "internal error", nil, http.StatusInternalServerError, common.Reason("failed to get password hash: %v", err))
return
}
user.PasswdHash = string(hashedPassword)
@@ -84,8 +76,7 @@ func (u *userHandler) UserRegister(w http.ResponseWriter, r *http.Request) {
// todo: add data validation
err = u.dbService.CreateUser(&ormUser, database.WithContext(r.Context()))
if err != nil {
slog.Error("Failed to create user", slog.String("error", err.Error()))
errResponse("failed to create user", err, http.StatusBadRequest)
common.ErrorResponse(w, "failed to create user", err, http.StatusBadRequest)
return
}
@@ -96,33 +87,27 @@ func (u *userHandler) UserRegister(w http.ResponseWriter, r *http.Request) {
func (u *userHandler) UserLogin(w http.ResponseWriter, r *http.Request) {
defer r.Body.Close()
errResponse := func(message string, err error, status int) {
w.Header().Set("Content-Type", "text/plain")
http.Error(w, errors.Join(errors.New(message), err).Error(), status)
}
user := models.UserLoginReq{}
err := json.NewDecoder(r.Body).Decode(&user)
if err != nil {
errResponse("failed to decode request body", err, http.StatusBadRequest)
common.ErrorResponse(w, "failed to decode request body", err, http.StatusBadRequest)
return
}
if len(user.Phone) == 0 || len(user.Passwd) == 0 {
slog.Error("No required parameters passed")
errResponse("invalid parameters", nil, http.StatusBadRequest)
common.ErrorResponse(w, "invalid parameters", nil, http.StatusBadRequest, common.Reason("no user or password passed"))
return
}
ormUser, err := u.dbService.GetUser(&orm.User{Phone: user.Phone}, database.WithContext(r.Context()))
if err != nil {
errResponse("invalid credentials", nil, http.StatusUnauthorized)
common.ErrorResponse(w, "invalid credentials", nil, http.StatusUnauthorized, common.Reason("no user found by number %s", user.Phone))
return
}
err = bcrypt.CompareHashAndPassword([]byte(ormUser.PasswdHash), []byte(user.Passwd))
if err != nil {
errResponse("invalid credentials", nil, http.StatusUnauthorized)
common.ErrorResponse(w, "invalid credentials", nil, http.StatusUnauthorized, common.Reason("password does not match"))
return
}
@@ -138,7 +123,7 @@ func (u *userHandler) UserLogin(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Content-Type", "application/json")
err = json.NewEncoder(w).Encode(resp)
if err != nil {
errResponse("failed to encode response", err, http.StatusInternalServerError)
common.ErrorResponse(w, "failed to encode response", err, http.StatusInternalServerError)
return
}
}