decred.org/dcrdex@v1.0.5/server/asset/dcr/config.go (about)

     1  // This code is available on the terms of the project LICENSE.md file,
     2  // also available online at https://blueoakcouncil.org/license/1.0.0.
     3  
     4  package dcr
     5  
     6  import (
     7  	"fmt"
     8  	"os"
     9  	"path/filepath"
    10  
    11  	"decred.org/dcrdex/dex"
    12  	"github.com/decred/dcrd/chaincfg/v3"
    13  	"github.com/decred/dcrd/dcrutil/v4"
    14  	flags "github.com/jessevdk/go-flags"
    15  )
    16  
    17  const (
    18  	defaultMainnet  = "localhost:9109"
    19  	defaultTestnet3 = "localhost:19109"
    20  	defaultSimnet   = "localhost:19556"
    21  )
    22  
    23  var (
    24  	// A global *chaincfg.Params will be set if loadConfig completes without
    25  	// error.
    26  	chainParams       *chaincfg.Params
    27  	dcrdHomeDir       = dcrutil.AppDataDir("dcrd", false)
    28  	defaultRPCCert    = filepath.Join(dcrdHomeDir, "rpc.cert")
    29  	defaultConfigPath = filepath.Join(dcrdHomeDir, "dcrd.conf")
    30  )
    31  
    32  type config struct {
    33  	Network dex.Network
    34  	// RPCUser is the RPC username provided to dcrd configuration as the rpcuser
    35  	// parameter.
    36  	RPCUser string `long:"rpcuser" description:"Username for RPC connections"`
    37  	// RPCPass is the RPC password provided to dcrd configuration as the rpcpass
    38  	// parameter.
    39  	RPCPass string `long:"rpcpass" description:"Password for RPC connections"`
    40  	// RPCListen is the RPC network address provided to dcrd configuration as the
    41  	// rpclisten parameter. If the value is an empty string, it will be set
    42  	// to a default value for the network.
    43  	RPCListen string `long:"rpclisten" description:"dcrd interface/port for RPC connections (default port: 9109, testnet: 19109)"`
    44  	// RPCCert is the filepath to the dcrd TLS certificate. If it is not
    45  	// provided, the default dcrd location will be assumed.
    46  	RPCCert string `long:"rpccert" description:"File containing the certificate file"`
    47  }
    48  
    49  // loadConfig loads the config from file. If no values are found for
    50  // RPCListen or RPCCert in the specified file, default values will be used. If
    51  // configPath is an empty string, loadConfig will attempt to read settings
    52  // directly from the default dcrd.conf file path. If there is no error, the
    53  // module-level chainParams variable will be set appropriately for the network.
    54  func loadConfig(configPath string, network dex.Network) (*config, error) {
    55  	cfg := &config{
    56  		Network: network,
    57  	}
    58  
    59  	// Since we are not reading command-line arguments, and the config fields
    60  	// share names with the dcrd configuration options, passing just
    61  	// IgnoreUnknown allows us to have the option to read directly from the
    62  	// dcrd.conf file.
    63  	parser := flags.NewParser(cfg, flags.IgnoreUnknown)
    64  
    65  	// If no path provided, use default dcrd path.
    66  	if configPath == "" {
    67  		configPath = defaultConfigPath
    68  	}
    69  
    70  	if _, err := os.Stat(configPath); os.IsNotExist(err) {
    71  		return nil, fmt.Errorf("no %q config file found at %s", assetName, configPath)
    72  	}
    73  
    74  	// The config file exists, so attempt to parse it.
    75  	err := flags.NewIniParser(parser).ParseFile(configPath)
    76  	if err != nil {
    77  		return nil, fmt.Errorf("error parsing %q ini file: %w", assetName, err)
    78  	}
    79  
    80  	// Check for missing credentials. The user and password must be set.
    81  	missing := ""
    82  	if cfg.RPCUser == "" {
    83  		missing += " username"
    84  	}
    85  	if cfg.RPCPass == "" {
    86  		missing += " password"
    87  	}
    88  	if missing != "" {
    89  		return nil, fmt.Errorf("missing dcrd credentials: %s", missing)
    90  	}
    91  
    92  	// Get network settings. Configuration defaults to mainnet, but unknown
    93  	// non-empty cfg.Net is an error.
    94  	var defaultServer string
    95  	switch network {
    96  	case dex.Simnet:
    97  		chainParams = chaincfg.SimNetParams()
    98  		defaultServer = defaultSimnet
    99  	case dex.Testnet:
   100  		chainParams = chaincfg.TestNet3Params()
   101  		defaultServer = defaultTestnet3
   102  	case dex.Mainnet:
   103  		chainParams = chaincfg.MainNetParams()
   104  		defaultServer = defaultMainnet
   105  	default:
   106  		return nil, fmt.Errorf("unknown network ID: %d", uint8(network))
   107  	}
   108  	if cfg.RPCListen == "" {
   109  		cfg.RPCListen = defaultServer
   110  	}
   111  	if cfg.RPCCert == "" {
   112  		cfg.RPCCert = defaultRPCCert
   113  	}
   114  
   115  	return cfg, nil
   116  }