Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
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
7 changes: 6 additions & 1 deletion gnmi_server/clientCertAuth.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (
"crypto/x509"
"io"
"net/http"
"strings"
"time"
"github.com/sonic-net/sonic-gnmi/common_utils"
"github.com/sonic-net/sonic-gnmi/swsscommon"
Expand Down Expand Up @@ -260,7 +261,11 @@ func PopulateAuthStructByCommonName(certCommonName string, auth *common_utils.Au

var fieldValuePairs = configDbConnector.Get_entry(serviceConfigTableName, certCommonName)
if fieldValuePairs.Size() > 0 {
if fieldValuePairs.Has_key("role") {
if fieldValuePairs.Has_key("role@") {
var role = fieldValuePairs.Get("role@")
auth.Roles = strings.Split(role, ",")
} else if fieldValuePairs.Has_key("role") {
// Backward compatibility for single role DB schema
var role = fieldValuePairs.Get("role")
auth.Roles = []string{role}
}
Expand Down
65 changes: 65 additions & 0 deletions gnmi_server/server_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5036,6 +5036,71 @@ func TestClientCertAuthenAndAuthor(t *testing.T) {
swsscommon.DeleteDBConnector(configDb)
}

func TestClientCertAuthenAndAuthorMultiRole(t *testing.T) {
if !swsscommon.SonicDBConfigIsInit() {
swsscommon.SonicDBConfigInitialize()
}

var configDb = swsscommon.NewDBConnector("CONFIG_DB", uint(0), true)
var gnmiTable = swsscommon.NewTable(configDb, "GNMI_CLIENT_CERT")
configDb.Flushdb()

// initialize err variable
err := status.Error(codes.Unauthenticated, "")

// when config table is empty, will authorize with PopulateAuthStruct
mockpopulate := gomonkey.ApplyFunc(PopulateAuthStruct, func(username string, auth *common_utils.AuthInfo, r []string) error {
return nil
})
defer mockpopulate.Reset()

// check auth with nil cert name
ctx, cancel := CreateAuthorizationCtx()
ctx, err = ClientCertAuthenAndAuthor(ctx, "", false)
if err != nil {
t.Errorf("CommonNameMatch with empty config table should success: %v", err)
}

cancel()

// check get 1 cert name
ctx, cancel = CreateAuthorizationCtx()
configDb.Flushdb()
gnmiTable.Hset("certname1", "role@", "readwrite")
ctx, err = ClientCertAuthenAndAuthor(ctx, "GNMI_CLIENT_CERT", false)
if err != nil {
t.Errorf("CommonNameMatch with correct cert name should success: %v", err)
}

cancel()

// check get multiple cert names
ctx, cancel = CreateAuthorizationCtx()
configDb.Flushdb()
gnmiTable.Hset("certname1", "role@", "readwrite")
gnmiTable.Hset("certname2", "role@", "readonly")
ctx, err = ClientCertAuthenAndAuthor(ctx, "GNMI_CLIENT_CERT", false)
if err != nil {
t.Errorf("CommonNameMatch with correct cert name should success: %v", err)
}

cancel()

// check a invalid cert cname
ctx, cancel = CreateAuthorizationCtx()
configDb.Flushdb()
gnmiTable.Hset("certname2", "role@", "readonly")
ctx, err = ClientCertAuthenAndAuthor(ctx, "GNMI_CLIENT_CERT", false)
if err == nil {
t.Errorf("CommonNameMatch with invalid cert name should fail: %v", err)
}

cancel()

swsscommon.DeleteTable(gnmiTable)
swsscommon.DeleteDBConnector(configDb)
}

type MockServerStream struct {
grpc.ServerStream
}
Expand Down