github.com/inklabsfoundation/inkchain@v0.17.1-0.20181025012015-c3cef8062f19/core/peer/config.go (about)

     1  /*
     2  Copyright IBM Corp. 2016 All Rights Reserved.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8  		 http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  // The 'viper' package for configuration handling is very flexible, but has
    18  // been found to have extremely poor performance when configuration values are
    19  // accessed repeatedly. The function CacheConfiguration() defined here caches
    20  // all configuration values that are accessed frequently.  These parameters
    21  // are now presented as function calls that access local configuration
    22  // variables.  This seems to be the most robust way to represent these
    23  // parameters in the face of the numerous ways that configuration files are
    24  // loaded and used (e.g, normal usage vs. test cases).
    25  
    26  // The CacheConfiguration() function is allowed to be called globally to
    27  // ensure that the correct values are always cached; See for example how
    28  // certain parameters are forced in 'ChaincodeDevMode' in main.go.
    29  
    30  package peer
    31  
    32  import (
    33  	"fmt"
    34  	"io/ioutil"
    35  	"math/big"
    36  	"net"
    37  
    38  	"github.com/inklabsfoundation/inkchain/core/wallet"
    39  	inkFeeImpl "github.com/inklabsfoundation/inkchain/core/wallet/ink/impl"
    40  	"github.com/spf13/viper"
    41  
    42  	"github.com/inklabsfoundation/inkchain/core/comm"
    43  	"github.com/inklabsfoundation/inkchain/core/config"
    44  	pb "github.com/inklabsfoundation/inkchain/protos/peer"
    45  	"os"
    46  )
    47  
    48  // Is the configuration cached?
    49  var configurationCached = false
    50  
    51  // Cached values and error values of the computed constants getLocalAddress(),
    52  // getValidatorStreamAddress(), and getPeerEndpoint()
    53  var localAddress string
    54  var localAddressError error
    55  var peerEndpoint *pb.PeerEndpoint
    56  var peerEndpointError error
    57  
    58  // Cached values of commonly used configuration constants.
    59  
    60  // CacheConfiguration computes and caches commonly-used constants and
    61  // computed constants as package variables. Routines which were previously
    62  // global have been embedded here to preserve the original abstraction.
    63  func CacheConfiguration() (err error) {
    64  
    65  	// getLocalAddress returns the address:port the local peer is operating on.  Affected by env:peer.addressAutoDetect
    66  	getLocalAddress := func() (peerAddress string, err error) {
    67  		if viper.GetBool("peer.addressAutoDetect") {
    68  			// Need to get the port from the peer.address setting, and append to the determined host IP
    69  			_, port, err := net.SplitHostPort(viper.GetString("peer.address"))
    70  			if err != nil {
    71  				err = fmt.Errorf("Error auto detecting Peer's address: %s", err)
    72  				return "", err
    73  			}
    74  			peerAddress = net.JoinHostPort(GetLocalIP(), port)
    75  			peerLogger.Infof("Auto detected peer address: %s", peerAddress)
    76  		} else {
    77  			peerAddress = viper.GetString("peer.address")
    78  		}
    79  		return
    80  	}
    81  
    82  	// getPeerEndpoint returns the PeerEndpoint for this Peer instance.  Affected by env:peer.addressAutoDetect
    83  	getPeerEndpoint := func() (*pb.PeerEndpoint, error) {
    84  		var peerAddress string
    85  		peerAddress, err := getLocalAddress()
    86  		if err != nil {
    87  			return nil, err
    88  		}
    89  		return &pb.PeerEndpoint{Id: &pb.PeerID{Name: viper.GetString("peer.id")}, Address: peerAddress}, nil
    90  	}
    91  
    92  	localAddress, localAddressError = getLocalAddress()
    93  	peerEndpoint, _ = getPeerEndpoint()
    94  
    95  	wallet.InkMinimumFee = big.NewInt(0)
    96  	inkFeeImpl.InkFeeK = 1
    97  	inkFeeImpl.InkFeeX0 = 0
    98  	inkFeeImpl.InkFeeB = 0
    99  	wallet.InkMinimumFee.SetString(viper.GetString("peer.minimumFee"), 10)
   100  	inkFeeImpl.InkFeeK = float32(viper.GetFloat64("peer.simpleFeeK"))
   101  	inkFeeImpl.InkFeeX0 = float32(viper.GetFloat64("peer.simpleFeeX0"))
   102  	inkFeeImpl.InkFeeB = float32(viper.GetFloat64("peer.simpleFeeB"))
   103  	wallet.SignPrivateKey = ""
   104  	keyPath := config.GetPath("peer.signPrivateFile")
   105  	if fileIsExist(keyPath){
   106  		key, err := ioutil.ReadFile(keyPath)
   107  		if err == nil {
   108  			wallet.SignPrivateKey = string(key)
   109  		}
   110  	}
   111  
   112  	configurationCached = true
   113  
   114  	if localAddressError != nil {
   115  		return localAddressError
   116  	}
   117  	return
   118  }
   119  
   120  // cacheConfiguration logs an error if error checks have failed.
   121  func cacheConfiguration() {
   122  	if err := CacheConfiguration(); err != nil {
   123  		peerLogger.Errorf("Execution continues after CacheConfiguration() failure : %s", err)
   124  	}
   125  }
   126  
   127  //Functional forms
   128  
   129  // GetLocalAddress returns the peer.address property
   130  func GetLocalAddress() (string, error) {
   131  	if !configurationCached {
   132  		cacheConfiguration()
   133  	}
   134  	return localAddress, localAddressError
   135  }
   136  
   137  // GetPeerEndpoint returns peerEndpoint from cached configuration
   138  func GetPeerEndpoint() (*pb.PeerEndpoint, error) {
   139  	if !configurationCached {
   140  		cacheConfiguration()
   141  	}
   142  	return peerEndpoint, peerEndpointError
   143  }
   144  
   145  // GetSecureConfig returns the secure server configuration for the peer
   146  func GetSecureConfig() (comm.SecureServerConfig, error) {
   147  	secureConfig := comm.SecureServerConfig{
   148  		UseTLS: viper.GetBool("peer.tls.enabled"),
   149  	}
   150  	if secureConfig.UseTLS {
   151  		// get the certs from the file system
   152  		serverKey, err := ioutil.ReadFile(config.GetPath("peer.tls.key.file"))
   153  		serverCert, err := ioutil.ReadFile(config.GetPath("peer.tls.cert.file"))
   154  		// must have both key and cert file
   155  		if err != nil {
   156  			return secureConfig, fmt.Errorf("Error loading TLS key and/or certificate (%s)", err)
   157  		}
   158  		secureConfig.ServerCertificate = serverCert
   159  		secureConfig.ServerKey = serverKey
   160  		// check for root cert
   161  		if config.GetPath("peer.tls.rootcert.file") != "" {
   162  			rootCert, err := ioutil.ReadFile(config.GetPath("peer.tls.rootcert.file"))
   163  			if err != nil {
   164  				return secureConfig, fmt.Errorf("Error loading TLS root certificate (%s)", err)
   165  			}
   166  			secureConfig.ServerRootCAs = [][]byte{rootCert}
   167  		}
   168  		return secureConfig, nil
   169  	}
   170  	return secureConfig, nil
   171  }
   172  
   173  //check the file exists by path
   174  func fileIsExist(path string) bool {
   175  	_, err := os.Stat(path)
   176  	return err == nil || os.IsExist(err)
   177  }