Skip to content

Commit

Permalink
[FAB-10568] Identity Config refactoring
Browse files Browse the repository at this point in the history
- decoupled endpoint config from identity config
- identity config should unmarshal its own entities, no need to rely on endpoint config
dictionary based search
- preloading CA configs
- return (entity, bool) for search functions
- return entity only for preloaded entitities

TODO: Client & CertificateAuthorities to be removed from NetworkConfig

Change-Id: Ia53ea227a2bfcdbbf9dec241e7038e3b31f14fca
Signed-off-by: Sudesh Shetty <sudesh.shetty@securekey.com>
  • Loading branch information
sudeshrshetty committed Jun 6, 2018
1 parent ec9053c commit 9cbdc1b
Show file tree
Hide file tree
Showing 26 changed files with 448 additions and 479 deletions.
6 changes: 1 addition & 5 deletions pkg/client/msp/client.go
Expand Up @@ -80,11 +80,7 @@ func New(clientProvider context.ClientProvider, opts ...ClientOption) (*Client,
}

if msp.orgName == "" {
clientConfig, err := ctx.IdentityConfig().Client()
if err != nil {
return nil, errors.WithMessage(err, "failed to create Client")
}
msp.orgName = clientConfig.Organization
msp.orgName = ctx.IdentityConfig().Client().Organization
}
if msp.orgName == "" {
return nil, errors.New("organization is not provided")
Expand Down
18 changes: 10 additions & 8 deletions pkg/common/providers/fab/network.go
Expand Up @@ -14,14 +14,16 @@ import (

// NetworkConfig provides a static definition of a Hyperledger Fabric network
type NetworkConfig struct {
Name string
Description string
Version string
Client msp.ClientConfig
Channels map[string]ChannelNetworkConfig
Organizations map[string]OrganizationConfig
Orderers map[string]OrdererConfig
Peers map[string]PeerConfig
Name string
Description string
Version string
//TODO to be removed, no apparent reason to expose it in network config
Client msp.ClientConfig
Channels map[string]ChannelNetworkConfig
Organizations map[string]OrganizationConfig
Orderers map[string]OrdererConfig
Peers map[string]PeerConfig
//TODO to be removed, no apparent reason to expose it in network config
CertificateAuthorities map[string]msp.CAConfig
}

Expand Down
10 changes: 5 additions & 5 deletions pkg/common/providers/msp/provider.go
Expand Up @@ -25,11 +25,11 @@ type IdentityManagerProvider interface {

//IdentityConfig contains identity configurations
type IdentityConfig interface {
Client() (*ClientConfig, error)
CAConfig(org string) (*CAConfig, error)
CAServerCerts(org string) ([][]byte, error)
CAClientKey(org string) ([]byte, error)
CAClientCert(org string) ([]byte, error)
Client() *ClientConfig
CAConfig(org string) (*CAConfig, bool)
CAServerCerts(org string) ([][]byte, bool)
CAClientKey(org string) ([]byte, bool)
CAClientCert(org string) ([]byte, bool)
CAKeyStorePath() string
CredentialStorePath() string
}
Expand Down
21 changes: 10 additions & 11 deletions pkg/common/providers/test/mockmsp/mockmsp.gen.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions pkg/fab/endpointconfig.go
Expand Up @@ -435,6 +435,7 @@ func (c *EndpointConfig) loadNetworkConfiguration() error {
networkConfig.Description = c.backend.GetString("description")
networkConfig.Version = c.backend.GetString("version")

//TODO: to be removed from NetworkConfig, to be used only in identity Config
err := c.backend.UnmarshalKey("client", &networkConfig.Client)
logger.Debugf("Client is: %+v", networkConfig.Client)
if err != nil {
Expand Down Expand Up @@ -465,6 +466,7 @@ func (c *EndpointConfig) loadNetworkConfiguration() error {
return errors.WithMessage(err, "failed to parse 'peers' config item to networkConfig.Peers type")
}

//TODO: to be removed from NetworkConfig, to be used only in identity Config
err = c.backend.UnmarshalKey("certificateAuthorities", &networkConfig.CertificateAuthorities)
logger.Debugf("certificateAuthorities are: %+v", networkConfig.CertificateAuthorities)
if err != nil {
Expand Down
32 changes: 32 additions & 0 deletions pkg/fab/endpointconfig_test.go
Expand Up @@ -1249,6 +1249,38 @@ func TestEndpointConfigWithMultipleBackends(t *testing.T) {

}

func TestCAConfig(t *testing.T) {
//Test config
backend, err := config.FromFile(configTestFilePath)()
if err != nil {
t.Fatal("Failed to get config backend")
}

endpointConfig, err := ConfigFromBackend(backend...)
if err != nil {
t.Fatal("Failed to get identity config")
}

//Test Crypto config path

val, ok := backend[0].Lookup("client.cryptoconfig.path")
if !ok || val == nil {
t.Fatal("expected valid value")
}

assert.True(t, pathvar.Subst(val.(string)) == endpointConfig.CryptoConfigPath(), "Incorrect crypto config path", t)

//Testing MSPID
mspID, ok := comm.MSPID(endpointConfig, org1)
assert.True(t, ok, "Get MSP ID failed")
assert.True(t, mspID == "Org1MSP", "Get MSP ID failed")

// testing empty OrgMSP
_, ok = comm.MSPID(endpointConfig, "dummyorg1")
assert.False(t, ok, "Get MSP ID did not fail for dummyorg1")

}

func TestNetworkPeers(t *testing.T) {

endpointConfig, err := ConfigFromBackend(configBackend)
Expand Down
20 changes: 10 additions & 10 deletions pkg/fab/mocks/mockconfig.go
Expand Up @@ -62,7 +62,7 @@ func NewMockIdentityConfigCustomized(tlsEnabled, mutualTLSEnabled, errorCase boo
}

// Client ...
func (c *MockConfig) Client() (*msp.ClientConfig, error) {
func (c *MockConfig) Client() *msp.ClientConfig {
clientConfig := msp.ClientConfig{}

clientConfig.CredentialStore = msp.CredentialStoreType{
Expand All @@ -86,31 +86,31 @@ func (c *MockConfig) Client() (*msp.ClientConfig, error) {
clientConfig.TLSCerts = mutualTLSCerts
}

return &clientConfig, nil
return &clientConfig
}

// CAConfig not implemented
func (c *MockConfig) CAConfig(org string) (*msp.CAConfig, error) {
func (c *MockConfig) CAConfig(org string) (*msp.CAConfig, bool) {
caConfig := msp.CAConfig{
CAName: "org1",
}

return &caConfig, nil
return &caConfig, true
}

//CAServerCerts Read configuration option for the server certificates for given org
func (c *MockConfig) CAServerCerts(org string) ([][]byte, error) {
return nil, nil
func (c *MockConfig) CAServerCerts(org string) ([][]byte, bool) {
return nil, false
}

//CAClientKey Read configuration option for the fabric CA client key for given org
func (c *MockConfig) CAClientKey(org string) ([]byte, error) {
return nil, nil
func (c *MockConfig) CAClientKey(org string) ([]byte, bool) {
return nil, false
}

//CAClientCert Read configuration option for the fabric CA client cert for given org
func (c *MockConfig) CAClientCert(org string) ([]byte, error) {
return nil, nil
func (c *MockConfig) CAClientCert(org string) ([]byte, bool) {
return nil, false
}

//Timeout not implemented
Expand Down
9 changes: 2 additions & 7 deletions pkg/fabsdk/context.go
Expand Up @@ -48,14 +48,9 @@ func WithOrg(org string) ContextOption {
// don't include neither username nor identity
var ErrAnonymousIdentity = errors.New("missing credentials")

func (sdk *FabricSDK) newIdentity(options ...ContextOption) (msp.SigningIdentity, error) { //nolint
clientConfig, err := sdk.provider.IdentityConfig().Client()
if err != nil {
return nil, errors.WithMessage(err, "retrieving client configuration failed")
}

func (sdk *FabricSDK) newIdentity(options ...ContextOption) (msp.SigningIdentity, error) {
opts := identityOptions{
orgName: clientConfig.Organization,
orgName: sdk.provider.IdentityConfig().Client().Organization,
}

for _, option := range options {
Expand Down
6 changes: 3 additions & 3 deletions pkg/fabsdk/fabsdk.go
Expand Up @@ -392,7 +392,7 @@ func (sdk *FabricSDK) loadConfigs(configProvider core.ConfigProvider) (*configs,
}

// load identity config
c.identityConfig, err = sdk.loadIdentityConfig(c.endpointConfig, configBackend...)
c.identityConfig, err = sdk.loadIdentityConfig(configBackend...)
if err != nil {
return nil, errors.WithMessage(err, "unalbe to load identity config")
}
Expand Down Expand Up @@ -448,11 +448,11 @@ func (sdk *FabricSDK) loadCryptoConfig(configBackend ...core.ConfigBackend) (cor
return cryptoConfigOpt, nil
}

func (sdk *FabricSDK) loadIdentityConfig(endpointConfig fab.EndpointConfig, configBackend ...core.ConfigBackend) (msp.IdentityConfig, error) {
func (sdk *FabricSDK) loadIdentityConfig(configBackend ...core.ConfigBackend) (msp.IdentityConfig, error) {
identityConfigOpt, ok := sdk.opts.IdentityConfig.(*mspImpl.IdentityConfigOptions)

if sdk.opts.IdentityConfig == nil || (ok && !mspImpl.IsIdentityConfigFullyOverridden(identityConfigOpt)) {
defIdentityConfig, err := mspImpl.ConfigFromEndpointConfig(endpointConfig, configBackend...)
defIdentityConfig, err := mspImpl.ConfigFromBackend(configBackend...)
if err != nil {
return nil, errors.WithMessage(err, "failed to initialize identity config from config backend")
}
Expand Down
5 changes: 1 addition & 4 deletions pkg/fabsdk/fabsdk_chconfig_test.go
Expand Up @@ -138,10 +138,7 @@ func checkClientOrg(configBackend core.ConfigBackend, t *testing.T, orgName stri
if err != nil {
t.Fatalf("Error getting identity config : %s", err)
}
client, err := identityConfig.Client()
if err != nil {
t.Fatalf("Error getting client from config: %s", err)
}
client := identityConfig.Client()
if client.Organization != orgName {
t.Fatalf("Unexpected org in config: %s", client.Organization)
}
Expand Down
6 changes: 1 addition & 5 deletions pkg/fabsdk/fabsdk_test.go
Expand Up @@ -254,11 +254,7 @@ func TestWithConfigSuccess(t *testing.T) {
t.Fatalf("Error getting identity config: %s", err)
}

client1, err := identityConfig.Client()
if err != nil {
t.Fatalf("Error getting client from config: %s", err)
}

client1 := identityConfig.Client()
if client1.Organization != sdkValidClientOrg1 {
t.Fatalf("Unexpected org in config: %s", client1.Organization)
}
Expand Down
6 changes: 1 addition & 5 deletions pkg/fabsdk/factory/defmsp/mspfactory.go
Expand Up @@ -29,11 +29,7 @@ func NewProviderFactory() *ProviderFactory {
// CreateUserStore creates a UserStore using the SDK's default implementation
func (f *ProviderFactory) CreateUserStore(config msp.IdentityConfig) (msp.UserStore, error) {

clientCofig, err := config.Client()
if err != nil {
return nil, errors.WithMessage(err, "Unable to retrieve client config")
}
stateStorePath := clientCofig.CredentialStore.Path
stateStorePath := config.Client().CredentialStore.Path

stateStore, err := kvs.New(&kvs.FileKeyValueStoreOptions{Path: stateStorePath})
if err != nil {
Expand Down
13 changes: 8 additions & 5 deletions pkg/fabsdk/factory/defmsp/mspfactory_test.go
Expand Up @@ -7,9 +7,10 @@ SPDX-License-Identifier: Apache-2.0
package defmsp

import (
"errors"
"testing"

"strings"

"github.com/golang/mock/gomock"
"github.com/hyperledger/fabric-sdk-go/pkg/common/providers/msp"
"github.com/hyperledger/fabric-sdk-go/pkg/common/providers/test/mockmsp"
Expand Down Expand Up @@ -49,14 +50,15 @@ func newMockUserStore(t *testing.T) msp.UserStore {
Path: "/tmp/fabsdkgo_test/store",
},
}
mockConfig.EXPECT().Client().Return(&mockClientConfig, nil)
mockConfig.EXPECT().Client().Return(&mockClientConfig)

userStore, err := factory.CreateUserStore(mockConfig)
if err != nil {
t.Fatalf("Unexpected error creating user store %s", err)
}
return userStore
}

func TestCreateUserStoreByConfig(t *testing.T) {
userStore := newMockUserStore(t)

Expand All @@ -74,7 +76,7 @@ func TestCreateUserStoreEmptyConfig(t *testing.T) {
mockConfig := mockmsp.NewMockIdentityConfig(mockCtrl)

mockClientConfig := msp.ClientConfig{}
mockConfig.EXPECT().Client().Return(&mockClientConfig, nil)
mockConfig.EXPECT().Client().Return(&mockClientConfig)

_, err := factory.CreateUserStore(mockConfig)
if err == nil {
Expand All @@ -89,10 +91,11 @@ func TestCreateUserStoreFailConfig(t *testing.T) {
defer mockCtrl.Finish()
mockConfig := mockmsp.NewMockIdentityConfig(mockCtrl)

mockConfig.EXPECT().Client().Return(nil, errors.New("error"))
mockClientConfig := msp.ClientConfig{}
mockConfig.EXPECT().Client().Return(&mockClientConfig)

_, err := factory.CreateUserStore(mockConfig)
if err == nil {
if err == nil || !strings.Contains(err.Error(), "FileKeyValueStore path is empty") {
t.Fatal("Expected error creating user store")
}
}
Expand Down
13 changes: 5 additions & 8 deletions pkg/msp/caclient.go
Expand Up @@ -36,11 +36,7 @@ type CAClientImpl struct {
func NewCAClient(orgName string, ctx contextApi.Client) (*CAClientImpl, error) {

if orgName == "" {
clientConfig, err1 := ctx.IdentityConfig().Client()
if err1 != nil {
return nil, errors.Wrap(err1, "client config retrieval failed")
}
orgName = clientConfig.Organization
orgName = ctx.IdentityConfig().Client().Organization
}

if orgName == "" {
Expand All @@ -59,19 +55,20 @@ func NewCAClient(orgName string, ctx contextApi.Client) (*CAClientImpl, error) {

var adapter *fabricCAAdapter
var registrar msp.EnrollCredentials
var err error

// Currently, an organization can be associated with only one CA
caName := orgConfig.CertificateAuthorities[0]
caConfig, err := ctx.IdentityConfig().CAConfig(orgName)
if err == nil {
caConfig, ok := ctx.IdentityConfig().CAConfig(orgName)
if ok {
adapter, err = newFabricCAAdapter(orgName, ctx.CryptoSuite(), ctx.IdentityConfig())
if err == nil {
registrar = caConfig.Registrar
} else {
return nil, errors.Wrapf(err, "error initializing CA [%s]", caName)
}
} else {
return nil, errors.Wrapf(err, "error initializing CA [%s]", caName)
return nil, errors.Errorf("error initializing CA [%s]", caName)
}

identityManager, ok := ctx.IdentityManager(orgName)
Expand Down

0 comments on commit 9cbdc1b

Please sign in to comment.