diff --git a/core-service/internal/models/models.go b/core-service/internal/models/models.go index 1547c87..32f4cba 100644 --- a/core-service/internal/models/models.go +++ b/core-service/internal/models/models.go @@ -74,11 +74,25 @@ type RegisterRequest struct { OrganizationType string `json:"organization_type"` } +// UserResponse ответ с информацией о пользователе +type UserResponse struct { + ID uuid.UUID `json:"id"` + Email string `json:"email"` + Role string `json:"role"` +} + +// OrganizationResponse ответ с информацией об организации +type OrganizationResponse struct { + ID uuid.UUID `json:"id"` + Name string `json:"name"` + Type string `json:"type"` +} + // LoginResponse ответ на аутентификацию type LoginResponse struct { - Token string `json:"token"` - User User `json:"user"` - ExpiresAt time.Time `json:"expires_at"` + Token string `json:"token"` + User UserResponse `json:"user"` + Organization OrganizationResponse `json:"organization"` } // CreateLocationRequest запрос на создание места хранения diff --git a/core-service/internal/repository/organizations.go b/core-service/internal/repository/organizations.go index 46192f3..73191f6 100644 --- a/core-service/internal/repository/organizations.go +++ b/core-service/internal/repository/organizations.go @@ -3,6 +3,7 @@ package repository import ( "context" "database/sql" + "encoding/json" "fmt" "erp-mvp/core-service/internal/models" @@ -29,7 +30,13 @@ func (r *organizationRepository) Create(ctx context.Context, org *models.Organiz VALUES ($1, $2, $3, $4, $5) ` - _, err := r.db.ExecContext(ctx, query, org.ID, org.Name, org.Type, org.Settings, org.CreatedAt) + // Конвертируем JSON в строку + settingsJSON, err := json.Marshal(org.Settings) + if err != nil { + return fmt.Errorf("failed to marshal settings: %w", err) + } + + _, err = r.db.ExecContext(ctx, query, org.ID, org.Name, org.Type, string(settingsJSON), org.CreatedAt) if err != nil { return fmt.Errorf("failed to create organization: %w", err) } @@ -44,12 +51,13 @@ func (r *organizationRepository) GetByID(ctx context.Context, id uuid.UUID) (*mo WHERE id = $1 ` + var settingsJSON []byte org := &models.Organization{} err := r.db.QueryRowContext(ctx, query, id).Scan( &org.ID, &org.Name, &org.Type, - &org.Settings, + &settingsJSON, &org.CreatedAt, ) @@ -60,6 +68,16 @@ func (r *organizationRepository) GetByID(ctx context.Context, id uuid.UUID) (*mo return nil, fmt.Errorf("failed to get organization: %w", err) } + // Конвертируем JSON строку в map + if len(settingsJSON) > 0 { + err = json.Unmarshal(settingsJSON, &org.Settings) + if err != nil { + return nil, fmt.Errorf("failed to unmarshal settings: %w", err) + } + } else { + org.Settings = make(models.JSON) + } + return org, nil } @@ -70,7 +88,13 @@ func (r *organizationRepository) Update(ctx context.Context, org *models.Organiz WHERE id = $1 ` - result, err := r.db.ExecContext(ctx, query, org.ID, org.Name, org.Type, org.Settings) + // Конвертируем JSON в строку + settingsJSON, err := json.Marshal(org.Settings) + if err != nil { + return fmt.Errorf("failed to marshal settings: %w", err) + } + + result, err := r.db.ExecContext(ctx, query, org.ID, org.Name, org.Type, string(settingsJSON)) if err != nil { return fmt.Errorf("failed to update organization: %w", err) } diff --git a/core-service/internal/service/auth_service.go b/core-service/internal/service/auth_service.go index a41b968..97d30b8 100644 --- a/core-service/internal/service/auth_service.go +++ b/core-service/internal/service/auth_service.go @@ -7,7 +7,9 @@ import ( "erp-mvp/core-service/internal/auth" "erp-mvp/core-service/internal/models" "erp-mvp/core-service/internal/repository" + "github.com/google/uuid" + "github.com/sirupsen/logrus" ) type AuthService interface { @@ -19,6 +21,7 @@ type authService struct { orgRepo repository.OrganizationRepository userRepo repository.UserRepository jwtService *auth.JWTService + logger *logrus.Logger } func NewAuthService(orgRepo repository.OrganizationRepository, userRepo repository.UserRepository, jwtService *auth.JWTService) AuthService { @@ -26,37 +29,46 @@ func NewAuthService(orgRepo repository.OrganizationRepository, userRepo reposito orgRepo: orgRepo, userRepo: userRepo, jwtService: jwtService, + logger: logrus.New(), } } func (s *authService) Register(ctx context.Context, req *models.RegisterRequest) (*models.LoginResponse, error) { + s.logger.Info("Starting registration process") + // Проверяем, что пользователь с таким email не существует existingUser, err := s.userRepo.GetByEmail(ctx, req.UserEmail) if err == nil && existingUser != nil { + s.logger.Error("User with this email already exists") return nil, &ValidationError{Message: "User with this email already exists"} } - // Создаём организацию + // Создаем организацию orgID := uuid.New() org := &models.Organization{ ID: orgID, Name: req.OrganizationName, Type: req.OrganizationType, - Settings: models.JSON{}, + Settings: models.JSON{"created_at": time.Now().Unix()}, CreatedAt: time.Now(), } + s.logger.Info("Creating organization with ID: ", orgID) if err := s.orgRepo.Create(ctx, org); err != nil { + s.logger.Error("Failed to create organization: ", err) return nil, err } + s.logger.Info("Organization created successfully") // Хешируем пароль passwordHash, err := auth.HashPassword(req.UserPassword) if err != nil { + s.logger.Error("Failed to hash password: ", err) return nil, err } + s.logger.Info("Password hashed successfully") - // Создаём пользователя + // Создаем пользователя userID := uuid.New() user := &models.User{ ID: userID, @@ -66,20 +78,33 @@ func (s *authService) Register(ctx context.Context, req *models.RegisterRequest) CreatedAt: time.Now(), } + s.logger.Info("Creating user with ID: ", userID) if err := s.userRepo.Create(ctx, user, passwordHash); err != nil { + s.logger.Error("Failed to create user: ", err) return nil, err } + s.logger.Info("User created successfully") // Генерируем JWT токен token, err := s.jwtService.GenerateToken(user.ID, org.ID, user.Email, user.Role) if err != nil { + s.logger.Error("Failed to generate token: ", err) return nil, err } + s.logger.Info("JWT token generated successfully") return &models.LoginResponse{ - Token: token, - User: *user, - ExpiresAt: time.Now().Add(24 * time.Hour), // TTL из конфигурации + Token: token, + User: models.UserResponse{ + ID: user.ID, + Email: user.Email, + Role: user.Role, + }, + Organization: models.OrganizationResponse{ + ID: org.ID, + Name: org.Name, + Type: org.Type, + }, }, nil } @@ -101,10 +126,24 @@ func (s *authService) Login(ctx context.Context, req *models.LoginRequest) (*mod return nil, err } + // Получаем организацию для ответа + org, err := s.orgRepo.GetByID(ctx, user.OrganizationID) + if err != nil { + return nil, err + } + return &models.LoginResponse{ - Token: token, - User: *user, - ExpiresAt: time.Now().Add(24 * time.Hour), // TTL из конфигурации + Token: token, + User: models.UserResponse{ + ID: user.ID, + Email: user.Email, + Role: user.Role, + }, + Organization: models.OrganizationResponse{ + ID: org.ID, + Name: org.Name, + Type: org.Type, + }, }, nil }