github.com/ahlemtn/fabric@v2.1.1+incompatible/msp/mgmt/mgmt.go (about)

     1  /*
     2  Copyright IBM Corp. All Rights Reserved.
     3  
     4  SPDX-License-Identifier: Apache-2.0
     5  */
     6  
     7  package mgmt
     8  
     9  import (
    10  	"reflect"
    11  	"sync"
    12  
    13  	"github.com/hyperledger/fabric/bccsp"
    14  	"github.com/hyperledger/fabric/bccsp/factory"
    15  	"github.com/hyperledger/fabric/common/flogging"
    16  	"github.com/hyperledger/fabric/msp"
    17  	"github.com/hyperledger/fabric/msp/cache"
    18  	"github.com/pkg/errors"
    19  	"github.com/spf13/viper"
    20  )
    21  
    22  // LoadLocalMspWithType loads the local MSP with the specified type from the specified directory
    23  func LoadLocalMspWithType(dir string, bccspConfig *factory.FactoryOpts, mspID, mspType string) error {
    24  	if mspID == "" {
    25  		return errors.New("the local MSP must have an ID")
    26  	}
    27  
    28  	conf, err := msp.GetLocalMspConfigWithType(dir, bccspConfig, mspID, mspType)
    29  	if err != nil {
    30  		return err
    31  	}
    32  
    33  	return GetLocalMSP(factory.GetDefault()).Setup(conf)
    34  }
    35  
    36  // LoadLocalMsp loads the local MSP from the specified directory
    37  func LoadLocalMsp(dir string, bccspConfig *factory.FactoryOpts, mspID string) error {
    38  	if mspID == "" {
    39  		return errors.New("the local MSP must have an ID")
    40  	}
    41  
    42  	conf, err := msp.GetLocalMspConfig(dir, bccspConfig, mspID)
    43  	if err != nil {
    44  		return err
    45  	}
    46  
    47  	return GetLocalMSP(factory.GetDefault()).Setup(conf)
    48  }
    49  
    50  // FIXME: AS SOON AS THE CHAIN MANAGEMENT CODE IS COMPLETE,
    51  // THESE MAPS AND HELPER FUNCTIONS SHOULD DISAPPEAR BECAUSE
    52  // OWNERSHIP OF PER-CHAIN MSP MANAGERS WILL BE HANDLED BY IT;
    53  // HOWEVER IN THE INTERIM, THESE HELPER FUNCTIONS ARE REQUIRED
    54  
    55  var m sync.Mutex
    56  var localMsp msp.MSP
    57  var mspMap map[string]msp.MSPManager = make(map[string]msp.MSPManager)
    58  var mspLogger = flogging.MustGetLogger("msp")
    59  
    60  // TODO - this is a temporary solution to allow the peer to track whether the
    61  // MSPManager has been setup for a channel, which indicates whether the channel
    62  // exists or not
    63  type mspMgmtMgr struct {
    64  	msp.MSPManager
    65  	// track whether this MSPManager has been setup successfully
    66  	up bool
    67  }
    68  
    69  func (mgr *mspMgmtMgr) DeserializeIdentity(serializedIdentity []byte) (msp.Identity, error) {
    70  	if !mgr.up {
    71  		return nil, errors.New("channel doesn't exist")
    72  	}
    73  	return mgr.MSPManager.DeserializeIdentity(serializedIdentity)
    74  }
    75  
    76  func (mgr *mspMgmtMgr) Setup(msps []msp.MSP) error {
    77  	err := mgr.MSPManager.Setup(msps)
    78  	if err == nil {
    79  		mgr.up = true
    80  	}
    81  	return err
    82  }
    83  
    84  // GetManagerForChain returns the msp manager for the supplied
    85  // chain; if no such manager exists, one is created
    86  func GetManagerForChain(chainID string) msp.MSPManager {
    87  	m.Lock()
    88  	defer m.Unlock()
    89  
    90  	mspMgr, ok := mspMap[chainID]
    91  	if !ok {
    92  		mspLogger.Debugf("Created new msp manager for channel `%s`", chainID)
    93  		mspMgmtMgr := &mspMgmtMgr{msp.NewMSPManager(), false}
    94  		mspMap[chainID] = mspMgmtMgr
    95  		mspMgr = mspMgmtMgr
    96  	} else {
    97  		// check for internal mspManagerImpl and mspMgmtMgr types. if a different
    98  		// type is found, it's because a developer has added a new type that
    99  		// implements the MSPManager interface and should add a case to the logic
   100  		// above to handle it.
   101  		if !(reflect.TypeOf(mspMgr).Elem().Name() == "mspManagerImpl" || reflect.TypeOf(mspMgr).Elem().Name() == "mspMgmtMgr") {
   102  			panic("Found unexpected MSPManager type.")
   103  		}
   104  		mspLogger.Debugf("Returning existing manager for channel '%s'", chainID)
   105  	}
   106  	return mspMgr
   107  }
   108  
   109  // GetManagers returns all the managers registered
   110  func GetDeserializers() map[string]msp.IdentityDeserializer {
   111  	m.Lock()
   112  	defer m.Unlock()
   113  
   114  	clone := make(map[string]msp.IdentityDeserializer)
   115  
   116  	for key, mspManager := range mspMap {
   117  		clone[key] = mspManager
   118  	}
   119  
   120  	return clone
   121  }
   122  
   123  // XXXSetMSPManager is a stopgap solution to transition from the custom MSP config block
   124  // parsing to the channelconfig.Resources interface, while preserving the problematic singleton
   125  // nature of the MSP manager
   126  func XXXSetMSPManager(chainID string, manager msp.MSPManager) {
   127  	m.Lock()
   128  	defer m.Unlock()
   129  
   130  	mspMap[chainID] = &mspMgmtMgr{manager, true}
   131  }
   132  
   133  // GetLocalMSP returns the local msp (and creates it if it doesn't exist)
   134  func GetLocalMSP(cryptoProvider bccsp.BCCSP) msp.MSP {
   135  	m.Lock()
   136  	defer m.Unlock()
   137  
   138  	if localMsp != nil {
   139  		return localMsp
   140  	}
   141  
   142  	localMsp = loadLocaMSP(cryptoProvider)
   143  
   144  	return localMsp
   145  }
   146  
   147  func loadLocaMSP(bccsp bccsp.BCCSP) msp.MSP {
   148  	// determine the type of MSP (by default, we'll use bccspMSP)
   149  	mspType := viper.GetString("peer.localMspType")
   150  	if mspType == "" {
   151  		mspType = msp.ProviderTypeToString(msp.FABRIC)
   152  	}
   153  
   154  	newOpts, found := msp.Options[mspType]
   155  	if !found {
   156  		mspLogger.Panicf("msp type " + mspType + " unknown")
   157  	}
   158  
   159  	mspInst, err := msp.New(newOpts, bccsp)
   160  	if err != nil {
   161  		mspLogger.Fatalf("Failed to initialize local MSP, received err %+v", err)
   162  	}
   163  	switch mspType {
   164  	case msp.ProviderTypeToString(msp.FABRIC):
   165  		mspInst, err = cache.New(mspInst)
   166  		if err != nil {
   167  			mspLogger.Fatalf("Failed to initialize local MSP, received err %+v", err)
   168  		}
   169  	case msp.ProviderTypeToString(msp.IDEMIX):
   170  		// Do nothing
   171  	default:
   172  		panic("msp type " + mspType + " unknown")
   173  	}
   174  
   175  	mspLogger.Debugf("Created new local MSP")
   176  
   177  	return mspInst
   178  }
   179  
   180  // GetIdentityDeserializer returns the IdentityDeserializer for the given chain
   181  func GetIdentityDeserializer(chainID string, cryptoProvider bccsp.BCCSP) msp.IdentityDeserializer {
   182  	if chainID == "" {
   183  		return GetLocalMSP(cryptoProvider)
   184  	}
   185  
   186  	return GetManagerForChain(chainID)
   187  }
   188  
   189  // GetLocalSigningIdentityOrPanic returns the local signing identity or panic in case
   190  // or error
   191  func GetLocalSigningIdentityOrPanic(cryptoProvider bccsp.BCCSP) msp.SigningIdentity {
   192  	id, err := GetLocalMSP(cryptoProvider).GetDefaultSigningIdentity()
   193  	if err != nil {
   194  		mspLogger.Panicf("Failed getting local signing identity [%+v]", err)
   195  	}
   196  	return id
   197  }