Merge pull request #109 from RafayLabs/prompt-support

changes to expose system and user grpc clients for prompt
This commit is contained in:
Nirav Parikh
2022-04-15 15:08:31 +05:30
committed by GitHub
5 changed files with 221 additions and 14 deletions

View File

@@ -9,7 +9,7 @@ import (
"github.com/uptrace/bun"
)
func GetProjectOrganization(ctx context.Context, db bun.IDB, id uuid.UUID) (string, string, error) {
func GetProjectOrganization(ctx context.Context, db bun.IDB, name string) (string, string, error) {
type projectOrg struct {
Project string
Organization string
@@ -19,7 +19,7 @@ func GetProjectOrganization(ctx context.Context, db bun.IDB, id uuid.UUID) (stri
ColumnExpr("authsrv_project.name as project").
ColumnExpr("authsrv_organization.name as organization").
Join(`JOIN authsrv_organization ON authsrv_project.organization_id=authsrv_organization.id`).
Where("authsrv_project.id = ?", id).
Where("authsrv_project.name = ?", name).
Where("authsrv_project.trash = ?", false).
Where("authsrv_organization.trash = ?", false).
Scan(ctx, &r)

View File

@@ -9,7 +9,6 @@ import (
"github.com/RafayLabs/rcloud-base/internal/dao"
"github.com/RafayLabs/rcloud-base/pkg/common"
commonpbv3 "github.com/RafayLabs/rcloud-base/proto/types/commonpb/v3"
"github.com/google/uuid"
"github.com/uptrace/bun"
"github.com/urfave/negroni"
"go.uber.org/zap"
@@ -48,24 +47,17 @@ func (am *authMiddleware) ServeHTTP(rw http.ResponseWriter, r *http.Request, nex
var org string
if strings.HasPrefix(r.URL.String(), "/v2/debug/prompt/project/") {
// /v2/debug/prompt/project/:project_id/cluster/:cluster_name
// /v2/debug/prompt/project/:project/cluster/:cluster_name
splits := strings.Split(r.URL.String(), "/")
if len(splits) > 5 {
projid, err := uuid.Parse(splits[5])
if err != nil {
_log.Errorf("Failed to authenticate: unable to parse project uuid")
http.Error(rw, http.StatusText(http.StatusForbidden), http.StatusForbidden)
return
}
// What gets sent for project is the id unlike most other
// api routes, so we have to fetch the name as well as the
// org info for casbin
proj, org, err = dao.GetProjectOrganization(r.Context(), am.db, projid)
// we have to fetch the org info for casbin
proj, org, err := dao.GetProjectOrganization(r.Context(), am.db, splits[5])
if err != nil {
_log.Errorf("Failed to authenticate: unable to find project")
http.Error(rw, http.StatusText(http.StatusForbidden), http.StatusForbidden)
return
}
_log.Info("found project with organization %s %s", proj, org)
}
} else {
// The middleware to only used with routes which does not have

View File

@@ -200,6 +200,7 @@ func (s *projectService) GetByName(ctx context.Context, name string) (*systemv3.
project.Metadata = &v3.Metadata{
Name: proj.Name,
Description: proj.Description,
Id: proj.ID.String(),
Organization: org.Name,
Partner: partner.Name,
ModifiedAt: timestamppb.New(proj.ModifiedAt),

View File

@@ -0,0 +1,110 @@
package rpcv3
import (
"context"
"github.com/RafayLabs/rcloud-base/pkg/pool"
grpcpool "github.com/processout/grpc-go-pool"
)
// SystemClient is the interface for accessing all the RPCs
// exposed by Rafay Base
type SystemClient interface {
Unhealthy()
Close() error
ProjectClient
OrganizationClient
PartnerClient
}
type systemClient struct {
*grpcpool.ClientConn
*projectClient
*organizationClient
*partnerClient
}
var _ SystemClient = (*systemClient)(nil)
// SystemPool maintains pool of grpc connections to system base services
type SystemPool interface {
Close()
NewClient(ctx context.Context) (SystemClient, error)
}
// NewSystemPool new system pool
func NewSystemPool(addr string, maxConn int) SystemPool {
return &systemPool{
GRPCPool: pool.NewGRPCPool(addr, maxConn, nil),
}
}
type systemPool struct {
*pool.GRPCPool
}
func (p *systemPool) Close() {
if p.GRPCPool != nil {
p.GRPCPool.Close()
}
}
func (p *systemPool) NewClient(ctx context.Context) (SystemClient, error) {
cc, err := p.GetConnection(ctx)
if err != nil {
return nil, err
}
return &systemClient{
cc,
&projectClient{cc.ClientConn},
&organizationClient{cc.ClientConn},
&partnerClient{cc.ClientConn},
}, nil
}
type options struct {
addr string
maxConn int
cert []byte
key []byte
caCert []byte
}
// Option is the functional argument for Pool options
type Option func(*options)
// WithAddr sets address of the pool
func WithAddr(addr string) Option {
return func(o *options) {
o.addr = addr
}
}
// WithMaxConn sets maximum number of connections of the pool
// if not set defaults to 10
func WithMaxConn(maxConn int) Option {
return func(o *options) {
o.maxConn = maxConn
}
}
// WithClientCertPEM sets PEM encoded client cert for pool
func WithClientCertPEM(cert []byte) Option {
return func(o *options) {
o.cert = cert
}
}
// WithClientKeyPEM sets PEM encoded client key for pool
func WithClientKeyPEM(key []byte) Option {
return func(o *options) {
o.key = key
}
}
// WithCaCertPEM sets PEM encoded CA cert for pool
func WithCaCertPEM(caCert []byte) Option {
return func(o *options) {
o.caCert = caCert
}
}

104
proto/rpc/user/internal.go Normal file
View File

@@ -0,0 +1,104 @@
package rpcv3
import (
"context"
"github.com/RafayLabs/rcloud-base/pkg/pool"
grpcpool "github.com/processout/grpc-go-pool"
)
// UserClient is the interface for accessing all User & Group RPCs
// exposed by Rafay Base
type UGClient interface {
Unhealthy()
Close() error
UserClient
}
type ugClient struct {
*grpcpool.ClientConn
*userClient
}
var _ UGClient = (*ugClient)(nil)
// UGPool maintains pool of grpc connections to system base services
type UGPool interface {
Close()
NewClient(ctx context.Context) (UGClient, error)
}
// NewUGPool new user group pool
func NewUGPool(addr string, maxConn int) UGPool {
return &ugPool{
GRPCPool: pool.NewGRPCPool(addr, maxConn, nil),
}
}
type ugPool struct {
*pool.GRPCPool
}
func (p *ugPool) Close() {
if p.GRPCPool != nil {
p.GRPCPool.Close()
}
}
func (p *ugPool) NewClient(ctx context.Context) (UGClient, error) {
cc, err := p.GetConnection(ctx)
if err != nil {
return nil, err
}
return &ugClient{
cc,
&userClient{cc.ClientConn},
}, nil
}
type options struct {
addr string
maxConn int
cert []byte
key []byte
caCert []byte
}
// Option is the functional argument for Pool options
type Option func(*options)
// WithAddr sets address of the pool
func WithAddr(addr string) Option {
return func(o *options) {
o.addr = addr
}
}
// WithMaxConn sets maximum number of connections of the pool
// if not set defaults to 10
func WithMaxConn(maxConn int) Option {
return func(o *options) {
o.maxConn = maxConn
}
}
// WithClientCertPEM sets PEM encoded client cert for pool
func WithClientCertPEM(cert []byte) Option {
return func(o *options) {
o.cert = cert
}
}
// WithClientKeyPEM sets PEM encoded client key for pool
func WithClientKeyPEM(key []byte) Option {
return func(o *options) {
o.key = key
}
}
// WithCaCertPEM sets PEM encoded CA cert for pool
func WithCaCertPEM(caCert []byte) Option {
return func(o *options) {
o.caCert = caCert
}
}