数据结构
go-ethereum/node/node.go
type Node struct {
accman *accounts.Manager
serviceFuncs []ServiceConstructor // Service constructors (in dependency 依赖 order)
}
1.1. go-ethereum/cmd/geth/consolecmd.go
var (
consoleCommand = cli.Command{
Action: utils.MigrateFlags(localConsole),
Name: "console", //console命令对应的方法是localConsole
Usage: "Start an interactive JavaScript environment",
Flags: append(append(append(nodeFlags, rpcFlags...), consoleFlags...), whisperFlags...),
Category: "CONSOLE COMMANDS",
Description: `
The Geth console is an interactive shell for the
JavaScript runtime environment which exposes a node
admin interface as well as the Ðapp JavaScript API.
See https://github.com/ethereum/go-ethereum/wiki/JavaScript-Console.`,
}
)
1.2. go-ethereum/cmd/geth/consolecmd.go
makeFullNode
func localConsole(ctx *cli.Context) error {
node := makeFullNode(ctx)
startNode(ctx, node)
}
1.3.go-ethereum/cmd/geth/config.go
func makeFullNode(ctx *cli.Context) *node.Node {
stack, cfg := makeConfigNode(ctx)
utils.RegisterEthService(stack, &cfg.Eth) //2.1
}
1.4.go-ethereum/cmd/geth/config.go
func makeConfigNode(ctx *cli.Context) (*node.Node, gethConfig) {
// Load defaults.
cfg := gethConfig{
Eth: eth.DefaultConfig,
Shh: whisper.DefaultConfig,
Node: defaultNodeConfig(), //node.Config
Dashboard: dashboard.DefaultConfig,
}
// Apply flags.
utils.SetNodeConfig(ctx, &cfg.Node)
stack, err := node.New(&cfg.Node) //创建node.Node
return stack
}
1.5.go-ethereum/node/node.go
func New(conf *Config) (*Node, error) {
am, ephemeralKeystore, err := makeAccountManager(conf) //创建accounts.Manager
return &Node{
accman: am, //Node持有accounts.Manager
ephemeralKeystore: ephemeralKeystore,
config: conf,
serviceFuncs: []ServiceConstructor{},
ipcEndpoint: conf.IPCEndpoint(),
httpEndpoint: conf.HTTPEndpoint(),
wsEndpoint: conf.WSEndpoint(),
eventmux: new(event.TypeMux),
log: conf.Logger,
}, nil
}
1.6. go-ethereum/node/config.go
func makeAccountManager(conf *Config) (*accounts.Manager, string, error) {
return accounts.NewManager(backends...), ephemeral, nil
}
1.7. go-ethereum/accounts/manager.go
func NewManager(backends ...Backend) *Manager {
am := &Manager{
backends: make(map[reflect.Type][]Backend),
updaters: subs,
updates: updates,
wallets: wallets,
quit: make(chan chan error),
}
for _, backend := range backends {
kind := reflect.TypeOf(backend)
am.backends[kind] = append(am.backends[kind], backend)
}
go am.update()
return am
}
2.1. go-ethereum/cmd/utils/flags.go
func RegisterEthService(stack *node.Node, cfg *eth.Config) {
var err error
if cfg.SyncMode == downloader.LightSync {
err = stack.Register(func(ctx *node.ServiceContext) (node.Service, error) {
return les.New(ctx, cfg)
})
} else {
//方法添加至serviceFuncs
err = stack.Register(func(ctx *node.ServiceContext) (node.Service, error) {
fullNode, err := eth.New(ctx, cfg)
if fullNode != nil && cfg.LightServ > 0 {
ls, _ := les.NewLesServer(fullNode, cfg)
fullNode.AddLesServer(ls)
}
return fullNode, err
})
}
if err != nil {
Fatalf("Failed to register the Ethereum service: %v", err)
}
}
2.2. go-ethereum/node/node.go
func (n *Node) Register(constructor ServiceConstructor) error {
n.lock.Lock()
defer n.lock.Unlock()
fmt.Println("test node/node.go Register")
debugcommon.PrintStack()
if n.server != nil {
return ErrNodeRunning
}
n.serviceFuncs = append(n.serviceFuncs, constructor)
return nil
}