diff --git a/go/cmd/zerotier/cli/roots.go b/go/cmd/zerotier/cli/roots.go index c20b2fa0b..5f5c7bc21 100644 --- a/go/cmd/zerotier/cli/roots.go +++ b/go/cmd/zerotier/cli/roots.go @@ -13,6 +13,51 @@ package cli +import ( + "fmt" + "os" + + "zerotier/pkg/zerotier" +) + // Roots CLI command -func Roots(basePath, authToken string, args []string) { +func Roots(basePath, authToken string, args []string, jsonOutput bool) { + var roots []zerotier.Root + apiGet(basePath, authToken, "/root", &roots) + + if jsonOutput { + fmt.Println(jsonDump(roots)) + } else { + fmt.Printf("%32s \n", "") + for _, r := range roots { + rn := r.Name + if len(rn) > 32 { + rn = rn[len(rn)-32:] + } + if r.Locator != nil { + if len(r.Locator.Physical) == 0 && len(r.Locator.Virtual) == 0 { + fmt.Printf("%32s %.10x -\n", rn, uint64(r.Locator.Identity.Address())) + } else { + fmt.Printf("%32s %.10x ", rn, uint64(r.Locator.Identity.Address())) + for i, a := range r.Locator.Physical { + if i > 0 { + fmt.Print(',') + } + fmt.Print(a.String()) + } + for i, a := range r.Locator.Virtual { + if i > 0 || len(r.Locator.Physical) > 0 { + fmt.Print(',') + } + fmt.Print(a.String()) + } + fmt.Printf("\n") + } + } else { + fmt.Printf("%32s - -\n", rn) + } + } + } + + os.Exit(0) } diff --git a/go/cmd/zerotier/zerotier.go b/go/cmd/zerotier/zerotier.go index c9d653f78..60e82a408 100644 --- a/go/cmd/zerotier/zerotier.go +++ b/go/cmd/zerotier/zerotier.go @@ -115,7 +115,7 @@ func main() { cli.Peers(basePath, authToken, cmdArgs, *jflag) case "roots", "listroots", "listmoons": authTokenRequired(authToken) - cli.Roots(basePath, authToken, cmdArgs) + cli.Roots(basePath, authToken, cmdArgs, *jflag) case "addroot": authTokenRequired(authToken) cli.AddRoot(basePath, authToken, cmdArgs) diff --git a/go/pkg/zerotier/identity.go b/go/pkg/zerotier/identity.go index 281efb550..89afec263 100644 --- a/go/pkg/zerotier/identity.go +++ b/go/pkg/zerotier/identity.go @@ -118,6 +118,9 @@ func NewIdentityFromString(s string) (*Identity, error) { return &id, nil } +// Address returns this identity's address +func (id *Identity) Address() Address { return id.address } + // HasPrivate returns true if this identity has its own private portion. func (id *Identity) HasPrivate() bool { return len(id.privateKey) > 0 }