Multi tenant groups (#77)

* multitenant groups

* switch users service to use new wrapper

* fix tests

* skip pkg dir

* Check for auth
This commit is contained in:
Dominic Wong
2021-03-25 15:53:14 +00:00
committed by GitHub
parent b37cc09835
commit c42aeaa0a9
17 changed files with 592 additions and 125 deletions

View File

@@ -44,7 +44,7 @@ func (u *Users) Create(ctx context.Context, req *pb.CreateRequest, rsp *pb.Creat
logger.Errorf("Error hashing and salting password: %v", err)
return errors.InternalServerError("HASHING_ERROR", "Error hashing password")
}
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -20,7 +20,7 @@ func (u *Users) Delete(ctx context.Context, req *pb.DeleteRequest, rsp *pb.Delet
if len(req.Id) == 0 {
return ErrMissingID
}
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -1,21 +1,13 @@
package handler
import (
"context"
"database/sql"
"fmt"
"regexp"
"strings"
"sync"
"time"
"github.com/micro/micro/v3/service/auth"
"github.com/micro/micro/v3/service/errors"
gorm2 "github.com/micro/services/pkg/gorm"
pb "github.com/micro/services/users/proto"
"golang.org/x/crypto/bcrypt"
"gorm.io/driver/postgres"
"gorm.io/gorm"
"gorm.io/gorm/schema"
)
var (
@@ -66,52 +58,12 @@ type Token struct {
}
type Users struct {
sync.RWMutex
Time func() time.Time
dbConn *sql.DB
gormConns map[string]*gorm.DB
gorm2.Helper
Time func() time.Time
}
func NewHandler(t func() time.Time, dbConn *sql.DB) *Users {
return &Users{Time: t, dbConn: dbConn, gormConns: map[string]*gorm.DB{}}
}
func (u *Users) getDBConn(ctx context.Context) (*gorm.DB, error) {
acc, ok := auth.AccountFromContext(ctx)
if !ok {
return nil, fmt.Errorf("missing account from context")
}
u.RLock()
if conn, ok := u.gormConns[acc.Issuer]; ok {
u.RUnlock()
return conn, nil
}
u.RUnlock()
u.Lock()
// double check
if conn, ok := u.gormConns[acc.Issuer]; ok {
u.Unlock()
return conn, nil
}
defer u.Unlock()
db, err := gorm.Open(
postgres.New(postgres.Config{
Conn: u.dbConn,
}),
&gorm.Config{
NamingStrategy: schema.NamingStrategy{
TablePrefix: fmt.Sprintf("%s_", strings.ReplaceAll(acc.Issuer, "-", "")),
},
})
if err != nil {
return nil, err
}
if err := db.AutoMigrate(&User{}, &Token{}); err != nil {
return nil, err
}
// record success
u.gormConns[acc.Issuer] = db
return db, nil
func NewHandler(t func() time.Time) *Users {
return &Users{Time: t}
}
// isEmailValid checks if the email provided passes the required structure and length.

View File

@@ -31,7 +31,9 @@ func testHandler(t *testing.T) *handler.Users {
t.Fatalf("Error cleaning database: %v", err)
}
return handler.NewHandler(time.Now, sqlDB)
h := handler.NewHandler(time.Now)
h.DBConn(sqlDB).Migrations(&handler.User{}, &handler.Token{})
return h
}
func assertUsersMatch(t *testing.T, exp, act *pb.User) {

View File

@@ -16,7 +16,7 @@ func (u *Users) List(ctx context.Context, req *pb.ListRequest, rsp *pb.ListRespo
errors.Unauthorized("UNAUTHORIZED", "Unauthorized")
}
// query the database
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -25,7 +25,7 @@ func (u *Users) Login(ctx context.Context, req *pb.LoginRequest, rsp *pb.LoginRe
return ErrInvalidPassword
}
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -21,7 +21,7 @@ func (u *Users) Logout(ctx context.Context, req *pb.LogoutRequest, rsp *pb.Logou
return ErrMissingID
}
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -21,7 +21,7 @@ func (u *Users) Read(ctx context.Context, req *pb.ReadRequest, rsp *pb.ReadRespo
}
// query the database
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -26,7 +26,7 @@ func (u *Users) ReadByEmail(ctx context.Context, req *pb.ReadByEmailRequest, rsp
}
// query the database
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -40,7 +40,7 @@ func (u *Users) Update(ctx context.Context, req *pb.UpdateRequest, rsp *pb.Updat
// lookup the user
var user User
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")

View File

@@ -21,7 +21,7 @@ func (u *Users) Validate(ctx context.Context, req *pb.ValidateRequest, rsp *pb.V
return ErrMissingToken
}
db, err := u.getDBConn(ctx)
db, err := u.GetDBConn(ctx)
if err != nil {
logger.Errorf("Error connecting to DB: %v", err)
return errors.InternalServerError("DB_ERROR", "Error connecting to DB")