Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

release/38851105: Validation server side and docker-compose #2

Open
wants to merge 2 commits into
base: develop
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions .github/pull_request_template.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# [Задача №00000000](https://bigbosop215.kaiten.ru/space/439413/card/00000000)

### Что было не так:
<описание проблемы/причины заведения новой фичи>
### Что было сделано:
* слой repository;
* добавлена валидация на уникальность email;
* ручка на получение подборок фильмов;
* написаны тесты и моки.
### Чек лист до ревью :
- [ ] PR разбит на логические коммиты (если нет, то нужно разбить);
- [ ] PR не содержит секретов (пароли, токены, ключи);
- [ ] PR не содержит лишних файлов (например, `.env`);
- [ ] PR не содержит коммитов, которые не относятся к задаче;

**Перед тем, как отдать на ревью нужно убедиться, что все пункты выполнены**

### как вливать ветку
Если это обычная задача, то просто `squash merge` в `develop`
Если это хотфикс, то обычный `merge` в `master` и `develop` (должно быть два `pull request`). При этом в ветке должен быть один коммит
Если это релиз, то обычный `merge` и в `master` и в `develop`. Там будет несколько коммитов
44 changes: 44 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
version: '3'
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

deprecated


volumes:
postgres_volume:
redis:

services:
validation_ms:
build:
context: ./validation-service/
dockerfile: Dockerfile
restart: always
ports:
- 5050:5050
networks:
- netflix
redis:
image: 'redis:latest'
command: redis-server
ports:
- '6379:6379'
Starlexxx marked this conversation as resolved.
Show resolved Hide resolved
volumes:
- redis:/data
networks:
- netflix
db:
image: postgres:latest
environment:
- "POSTGRES_DB=netflix"
- "POSTGRES_USER=test"
- "POSTGRES_PASSWORD=test"
ports:
- "5432:5432"
volumes:
- "postgres_volume:/var/lib/postgresql/data"
networks:
- netflix


networks:
netflix:
default:
external:
name: netflix
4 changes: 2 additions & 2 deletions validation-service/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,9 @@ RUN go mod download
RUN go mod tidy
RUN go build cmd/main.go

EXPOSE 8081
EXPOSE 5050

CMD [ "main" ]
CMD [ "./main" ]

# /app/
# /api
Expand Down
10 changes: 4 additions & 6 deletions validation-service/api/validation/validation.proto
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,14 @@ package validation;

option go_package = ".";

import "google/protobuf/timestamp.proto";

message ValidateRegistrationRequest {
string email = 1;
string password = 2;
string password_confirm = 3;
}

message ValidateAuthorizationRequest {
string email = 1;
string password = 2;
string sex = 4;
google.protobuf.Timestamp bitrhdate = 5;
}

message ErrorMessage {
Expand All @@ -27,5 +26,4 @@ message ValidationResponse {

service Validation {
rpc ValidateRegistration(ValidateRegistrationRequest) returns (ValidationResponse);
rpc ValidateAuthorization(ValidateAuthorizationRequest) returns (ValidationResponse);
}
18 changes: 17 additions & 1 deletion validation-service/cmd/main.go
Original file line number Diff line number Diff line change
@@ -1,5 +1,21 @@
package main

import (
"context"
"log"

"github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/app"
)

const serverPort = 5050
Starlexxx marked this conversation as resolved.
Show resolved Hide resolved

func main() {

ctx := context.Background()
a, err := app.New(ctx, serverPort)

if err != nil {
log.Fatal(err)
}

a.Run()
}
12 changes: 10 additions & 2 deletions validation-service/go.mod
Original file line number Diff line number Diff line change
@@ -1,8 +1,16 @@
module github.com/go-park-mail-ru/2024_2_GOATS
module github.com/go-park-mail-ru/2024_2_GOATS/validation-service

go 1.22.2

require (
google.golang.org/grpc v1.65.0
google.golang.org/protobuf v1.34.2
)

require (
golang.org/x/net v0.26.0 // indirect
golang.org/x/sys v0.21.0 // indirect
golang.org/x/text v0.16.0 // indirect
google.golang.org/genproto/googleapis/rpc v0.0.0-20240604185151-ef581f913117 // indirect
google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.5.1 // indirect
google.golang.org/protobuf v1.34.2 // indirect
)
12 changes: 12 additions & 0 deletions validation-service/go.sum
Original file line number Diff line number Diff line change
@@ -1,3 +1,15 @@
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
golang.org/x/net v0.26.0 h1:soB7SVo0PWrY4vPW/+ay0jKDNScG2X9wFeYlXIvJsOQ=
golang.org/x/net v0.26.0/go.mod h1:5YKkiSynbBIh3p6iOc/vibscux0x38BZDkn8sCUPxHE=
golang.org/x/sys v0.21.0 h1:rF+pYz3DAGSQAxAu1CbC7catZg4ebC4UIeIhKxBZvws=
golang.org/x/sys v0.21.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/text v0.16.0 h1:a94ExnEXNtEwYLGJSIUxnWoxoRz/ZcCsV63ROupILh4=
golang.org/x/text v0.16.0/go.mod h1:GhwF1Be+LQoKShO3cGOHzqOgRrGaYc9AvblQOmPVHnI=
google.golang.org/genproto/googleapis/rpc v0.0.0-20240604185151-ef581f913117 h1:1GBuWVLM/KMVUv1t1En5Gs+gFZCNd360GGb4sSxtrhU=
google.golang.org/genproto/googleapis/rpc v0.0.0-20240604185151-ef581f913117/go.mod h1:EfXuqaE1J41VCDicxHzUDm+8rk+7ZdXzHV0IhO/I6s0=
google.golang.org/grpc v1.65.0 h1:bs/cUb4lp1G5iImFFd3u5ixQzweKizoZJAwBNLR42lc=
google.golang.org/grpc v1.65.0/go.mod h1:WgYC2ypjlB0EiQi6wdKixMqukr6lBc0Vo+oOgjrM5ZQ=
google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.5.1 h1:F29+wU6Ee6qgu9TddPgooOdaqsxTMunOoj8KA5yuS5A=
google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.5.1/go.mod h1:5KF+wpkbTSbGcR9zteSqZV6fqFOWBl4Yde8En8MryZA=
google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6hg=
Expand Down
26 changes: 26 additions & 0 deletions validation-service/internal/app/api/converter/converter.go
Original file line number Diff line number Diff line change
@@ -1 +1,27 @@
package converter

import (
"github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/app/model"
desc "github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/pb/validation"
"google.golang.org/protobuf/types/known/timestamppb"
)

func ToUserRegisterDataFromDesc(data *desc.ValidateRegistrationRequest) *model.UserRegisterData {
birthday := data.GetBitrhdate().AsTime()
ts := timestamppb.New(birthday)

return &model.UserRegisterData{
Email: data.GetEmail(),
Password: data.GetPassword(),
PasswordConfirm: data.GetPasswordConfirm(),
Sex: data.GetSex(),
Birthday: int(ts.Seconds),
}
}

func ToErrorsFromServ(data *model.ErrorResponse) *desc.ErrorMessage {
return &desc.ErrorMessage{
Code: data.Code,
Error: data.Error,
}
}
24 changes: 23 additions & 1 deletion validation-service/internal/app/api/validation/handler.go
Original file line number Diff line number Diff line change
@@ -1 +1,23 @@
package handler
package validation

import (
"context"

"github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/app/model"
desc "github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/pb/validation"
)

type ValidationService interface {
ValidateRegistration(ctx context.Context, userData *model.UserRegisterData) *model.ValidationResponse
}

type Implementation struct {
desc.UnimplementedValidationServer
validationService ValidationService
}

func NewImplementation(validationService ValidationService) *Implementation {
return &Implementation{
validationService: validationService,
}
}
21 changes: 21 additions & 0 deletions validation-service/internal/app/api/validation/validation.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package validation

import (
"context"

"github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/app/api/converter"
desc "github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/pb/validation"
)

func (i *Implementation) ValidateRegistration(ctx context.Context, req *desc.ValidateRegistrationRequest) (*desc.ValidationResponse, error) {
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Вот пока не знаю, как избавиться от контекста в аргументах функции. Типо это же из pb файла такой интерфейс
И вообще надо ли избавляться?

validData := i.validationService.ValidateRegistration(ctx, converter.ToUserRegisterDataFromDesc(req))
descErrors := make([]*desc.ErrorMessage, 0)
for _, errData := range validData.Errors {
descErrors = append(descErrors, converter.ToErrorsFromServ(&errData))
}

return &desc.ValidationResponse{
Success: validData.Success,
Errors: descErrors,
}, nil
}
47 changes: 46 additions & 1 deletion validation-service/internal/app/app.go
Original file line number Diff line number Diff line change
@@ -1,3 +1,48 @@
package main
package app

import (
"context"
"fmt"
"log"
"net"

"google.golang.org/grpc"
"google.golang.org/grpc/reflection"

validationAPI "github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/app/api/validation"
validationService "github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/app/service/validation"
desc "github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/pb/validation"
)

type App struct {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

хочу видеть сущность конфиг, где будет listener, он из ямлика будет читать адрес и порт. Рут контекст будет обогощаться этим конфигом, потом вы из него сможете достать конфиг где угодно

Copy link
Collaborator Author

@UnicoYal UnicoYal Sep 20, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Что-то типо?

type Config struct {
	listenerAddress string `yaml:"listener_address"`
	listenerPort    int    `yaml:"listener_port"`
}

type App struct {
	serverPort        int
	validationService validationAPI.ValidationService
	config            Config
}

В конструкторе App читаю конфиг из ямла и добавляю в контекст
Пока у меня контекст не прокидывается вниз, надо ли его передавать в конструкторы слоев?

serverPort int
validationService validationAPI.ValidationService
}

func New(ctx context.Context, serverPort int) (*App, error) {
validationService := validationService.NewService()

return &App{
serverPort: serverPort,
validationService: validationService,
}, nil
}

func (a *App) Run() {
lis, err := net.Listen("tcp", fmt.Sprintf(":%d", a.serverPort))
if err != nil {
log.Fatal("Failed to listen: %v", err)
}

validationSrv := validationService.NewService()
s := grpc.NewServer()
reflection.Register(s)

desc.RegisterValidationServer(s, validationAPI.NewImplementation(validationSrv))

log.Printf("Server listening at %v", lis.Addr())

if err = s.Serve(lis); err != nil {
log.Fatalf("failed to serve: %v", err)
}
}
12 changes: 12 additions & 0 deletions validation-service/internal/app/errors/errors.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package errors

var (
ErrInvalidEmailCode = "invalid_email"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

А почему не сделать обычные ошибки через errors.New

ErrInvalidEmailText = "email is incorrect"
ErrInvalidPasswordCode = "invalid_password"
ErrInvalidPasswordText = "password is too short. The minimal len is 8"
ErrInvalidSexCode = "invalid_sex"
ErrInvalidSexText = "only male or female allowed"
ErrInvalidBirthdateCode = "invalid_birthdate"
ErrInvalidBirthdateText = "bithdate should be before current time"
)
18 changes: 18 additions & 0 deletions validation-service/internal/app/model/validation.go
Original file line number Diff line number Diff line change
@@ -1 +1,19 @@
package model

type UserRegisterData struct {
Email string
Password string
PasswordConfirm string
Sex string
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Даже если вы собираетесь поддерживать 50+ гендеров, как нетфликс, string это расточительство

Birthday int
Starlexxx marked this conversation as resolved.
Show resolved Hide resolved
}

type ErrorResponse struct {
Code string
Error string
}

type ValidationResponse struct {
Success bool
Errors []ErrorResponse
}

This file was deleted.

1 change: 0 additions & 1 deletion validation-service/internal/app/repository/repository.go

This file was deleted.

This file was deleted.

This file was deleted.

1 change: 0 additions & 1 deletion validation-service/internal/app/service/service.go

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
package helpers

import (
"fmt"
"log"
"regexp"
"slices"
"time"

errVals "github.com/go-park-mail-ru/2024_2_GOATS/validation-service/internal/app/errors"
"google.golang.org/protobuf/types/known/timestamppb"
)

var (
emailRegex = regexp.MustCompile("^[a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$")
passwordLength = 8
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

кажется, это константа должна быть

sexVals = []string{"male", "female"}
)

func ValidatePassword(pass, passConf string) error {
if passConf == "" {
log.Println("password confirm is missing, but now its OK")
}

if len(pass) < passwordLength {
log.Println(errVals.ErrInvalidPasswordText)
return fmt.Errorf(errVals.ErrInvalidPasswordText)
}

return nil
}

func ValidateEmail(email string) error {
if !emailRegex.MatchString(email) {
log.Println(errVals.ErrInvalidEmailText)
return fmt.Errorf(errVals.ErrInvalidEmailText)
}

return nil
}

func ValidateBirthdate(birthdate int) error {
ts := timestamppb.New(time.Now())
if int(ts.Seconds) < birthdate {
log.Println(errVals.ErrInvalidBirthdateCode)
return fmt.Errorf(errVals.ErrInvalidBirthdateText)
}

return nil
}

func ValidateSex(sex string) error {
if !slices.Contains(sexVals, sex) {
log.Println(errVals.ErrInvalidSexCode)
return fmt.Errorf(errVals.ErrInvalidSexText)
}

return nil
}

This file was deleted.

Loading