소스 검색

CustomerCreate

- implement
Alexey Kim 2 년 전
부모
커밋
583b6858a5
1개의 변경된 파일112개의 추가작업 그리고 2개의 파일을 삭제
  1. 112 2
      graphql/mutationCustomerCreate.go

+ 112 - 2
graphql/mutationCustomerCreate.go

@@ -2,9 +2,119 @@ package graphql
 
 import (
 	"context"
+	"fmt"
+	"github.com/Nerzal/gocloak/v12"
+	"github.com/gshopify/service-wrapper/scalar"
+	"github.com/gshopify/service-wrapper/server/middleware"
 	"gshopper.com/gshopify/customer/graphql/generated"
+	m "gshopper.com/gshopify/customer/model"
+	"time"
 )
 
-func (r *mutationResolver) CustomerCreate(ctx context.Context, input generated.CustomerCreateInput) (*generated.CustomerCreatePayload, error) {
-	panic("not implemented")
+var minPasswordEntropy = 42.0
+
+func (r *mutationResolver) CustomerCreate(
+	ctx context.Context, input generated.CustomerCreateInput) (*generated.CustomerCreatePayload, error) {
+
+	var (
+		response = &generated.CustomerCreatePayload{}
+		user     = gocloak.User{
+			Enabled: gocloak.BoolP(true),
+		}
+		err error
+	)
+
+	if e := input.ValidateEmail(); e != nil {
+		response.CustomerUserErrors = append(response.CustomerUserErrors, e)
+		return response, nil
+	}
+
+	if e := input.ValidatePassword(minPasswordEntropy); e != nil {
+		response.CustomerUserErrors = append(response.CustomerUserErrors, e)
+		return response, nil
+	}
+
+	admin, err := r.conf.Admin.Token(r.client, ctx)
+	if err != nil {
+		response.CustomerUserErrors = append(response.CustomerUserErrors,
+			CustomerError(generated.CustomerErrorCodeTokenInvalid, err, "adminAccessToken"))
+		return response, err
+	}
+
+	if ls, err := r.client.GetUsers(ctx, admin.AccessToken, r.conf.Cli.Realm, gocloak.GetUsersParams{
+		Email: gocloak.StringP(input.Email),
+	}); err != nil {
+		response.CustomerUserErrors = append(response.CustomerUserErrors,
+			CustomerError(generated.CustomerErrorCodeBlank, err))
+	} else if len(ls) > 0 {
+		response.CustomerUserErrors = append(response.CustomerUserErrors,
+			CustomerError(generated.CustomerErrorCodeTaken, fmt.Errorf("email has been already registered"), "email"))
+	}
+
+	if len(response.CustomerUserErrors) > 0 {
+		return response, nil
+	}
+
+	now := scalar.Now()
+	user.Email = gocloak.StringP(input.Email)
+	user.LastName = input.LastName
+	user.FirstName = input.FirstName
+	user.CreatedTimestamp = gocloak.Int64P(time.Now().In(time.UTC).Unix())
+	user.Attributes = &map[string][]string{
+		"updated_at": {fmt.Sprintf("%d", now)},
+		"created_at": {fmt.Sprintf("%d", now)},
+	}
+
+	if input.AcceptsMarketing != nil {
+		(*user.Attributes)["accepts_marketing"] = []string{fmt.Sprintf("%v", input.AcceptsMarketing)}
+	}
+
+	if input.Phone != nil {
+		inContext, err := middleware.InContext(ctx)
+		if err != nil {
+			response.CustomerUserErrors = append(response.CustomerUserErrors,
+				CustomerError(generated.CustomerErrorCodeInvalid, err, "inContext"))
+			return response, nil
+		}
+
+		number, err := m.NewPhoneNumber(*input.Phone, inContext.Country.String(), true)
+		if err != nil {
+			response.CustomerUserErrors = append(response.CustomerUserErrors,
+				CustomerError(generated.CustomerErrorCodeInvalid, err, "phone"))
+			return response, nil
+		}
+
+		(*user.Attributes)["phone_number"] = []string{number.String()}
+		(*user.Attributes)["phone_region"] = []string{number.PhoneRegion}
+		(*user.Attributes)["phone_verified"] = []string{"false"}
+	}
+
+	// Create new user
+	uid, err := r.client.CreateUser(ctx, admin.AccessToken, r.conf.Cli.Realm, user)
+	if err != nil {
+		response.CustomerUserErrors = append(response.CustomerUserErrors,
+			CustomerError(generated.CustomerErrorCodeBlank, err))
+		return response, nil
+	}
+
+	// Set user password
+	if err = r.setPassword(ctx, uid, input.Password, false); err != nil {
+		response.CustomerUserErrors = append(response.CustomerUserErrors,
+			CustomerError(generated.CustomerErrorCodeBlank, err))
+		return response, nil
+	}
+
+	// Email verification
+	if err = r.client.SendVerifyEmail(ctx, admin.AccessToken, uid, r.conf.Cli.Realm, gocloak.SendVerificationMailParams{
+		ClientID:    gocloak.StringP(r.conf.Cli.ClientId),
+		RedirectURI: nil,
+	}); err != nil {
+		response.CustomerUserErrors = append(response.CustomerUserErrors,
+			CustomerError(generated.CustomerErrorCodeBlank, err))
+		return response, nil
+	}
+
+	user.ID = &uid
+	response.Customer = User2Customer(&user)
+	return response, nil
 }