From 2f60ab92dd8c22452c0edc264f174795146dce9f Mon Sep 17 00:00:00 2001 From: Brad Fitzpatrick Date: Thu, 1 Apr 2021 14:03:34 -0700 Subject: [PATCH] tailcfg: add Node.Capabilities, remove old stuff Signed-off-by: Brad Fitzpatrick --- tailcfg/tailcfg.go | 65 +++++------------------ tailcfg/tailcfg_clone.go | 108 ++++----------------------------------- tailcfg/tailcfg_test.go | 1 + 3 files changed, 25 insertions(+), 149 deletions(-) diff --git a/tailcfg/tailcfg.go b/tailcfg/tailcfg.go index 4ffe633bb..0c8f1f83d 100644 --- a/tailcfg/tailcfg.go +++ b/tailcfg/tailcfg.go @@ -4,7 +4,7 @@ package tailcfg -//go:generate go run tailscale.com/cmd/cloner --type=User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse --clonefunc=true --output=tailcfg_clone.go +//go:generate go run tailscale.com/cmd/cloner --type=User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse --clonefunc=true --output=tailcfg_clone.go import ( "bytes" @@ -66,20 +66,6 @@ func (u StableNodeID) IsZero() bool { return u == "" } -type GroupID ID - -func (u GroupID) IsZero() bool { - return u == 0 -} - -type RoleID ID - -func (u RoleID) IsZero() bool { - return u == 0 -} - -type CapabilityID ID - // MachineKey is the curve25519 public key for a machine. type MachineKey [32]byte @@ -90,31 +76,6 @@ type NodeKey [32]byte // It's never written to disk or reused between network start-ups. type DiscoKey [32]byte -type Group struct { - ID GroupID - Name string - Members []ID -} - -type Role struct { - ID RoleID - Name string - Capabilities []CapabilityID -} - -type CapType string - -const ( - CapRead = CapType("read") - CapWrite = CapType("write") -) - -type Capability struct { - ID CapabilityID - Type CapType - Val ID -} - // User is an IPN user. // // A user can have multiple logins associated with it (e.g. gmail and github oauth). @@ -133,7 +94,6 @@ type User struct { ProfilePicURL string // if non-empty overrides Login field Domain string Logins []LoginID - Roles []RoleID Created time.Time } @@ -200,6 +160,13 @@ type Node struct { MachineAuthorized bool `json:",omitempty"` // TODO(crawshaw): replace with MachineStatus + // Capabilities are capabilities that the node has. + // They're free-form strings, but should be in the form of URLs/URIs + // such as: + // "https://tailscale.com/cap/is-admin" + // "https://tailscale.com/cap/recv-file" + Capabilities []string `json:",omitempty"` + // The following three computed fields hold the various names that can // be used for this node in UIs. They are populated from controlclient // (not from control) by calling node.InitDisplayNames. These can be @@ -904,10 +871,6 @@ type MapResponse struct { PacketFilter []FilterRule UserProfiles []UserProfile // as of 1.1.541 (mapver 5): may be new or updated user profiles only - Roles []Role // deprecated; clients should not rely on Roles - - // TODO: Groups []Group - // TODO: Capabilities []Capability // Debug is normally nil, except for when the control server // is setting debug settings on a node. @@ -994,13 +957,10 @@ func (k DiscoKey) ShortString() string { return fmt.Sprintf("d:%x", // IsZero reports whether k is the zero value. func (k DiscoKey) IsZero() bool { return k == DiscoKey{} } -func (id ID) String() string { return fmt.Sprintf("id:%x", int64(id)) } -func (id UserID) String() string { return fmt.Sprintf("userid:%x", int64(id)) } -func (id LoginID) String() string { return fmt.Sprintf("loginid:%x", int64(id)) } -func (id NodeID) String() string { return fmt.Sprintf("nodeid:%x", int64(id)) } -func (id GroupID) String() string { return fmt.Sprintf("groupid:%x", int64(id)) } -func (id RoleID) String() string { return fmt.Sprintf("roleid:%x", int64(id)) } -func (id CapabilityID) String() string { return fmt.Sprintf("capid:%x", int64(id)) } +func (id ID) String() string { return fmt.Sprintf("id:%x", int64(id)) } +func (id UserID) String() string { return fmt.Sprintf("userid:%x", int64(id)) } +func (id LoginID) String() string { return fmt.Sprintf("loginid:%x", int64(id)) } +func (id NodeID) String() string { return fmt.Sprintf("nodeid:%x", int64(id)) } // Equal reports whether n and n2 are equal. func (n *Node) Equal(n2 *Node) bool { @@ -1025,6 +985,7 @@ func (n *Node) Equal(n2 *Node) bool { n.Created.Equal(n2.Created) && eqTimePtr(n.LastSeen, n2.LastSeen) && n.MachineAuthorized == n2.MachineAuthorized && + eqStrings(n.Capabilities, n2.Capabilities) && n.ComputedName == n2.ComputedName && n.computedHostIfDifferent == n2.computedHostIfDifferent && n.ComputedNameWithHost == n2.ComputedNameWithHost diff --git a/tailcfg/tailcfg_clone.go b/tailcfg/tailcfg_clone.go index 89633c5c8..b24036dee 100644 --- a/tailcfg/tailcfg_clone.go +++ b/tailcfg/tailcfg_clone.go @@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -// Code generated by tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse; DO NOT EDIT. +// Code generated by tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse; DO NOT EDIT. package tailcfg @@ -22,12 +22,11 @@ func (src *User) Clone() *User { dst := new(User) *dst = *src dst.Logins = append(src.Logins[:0:0], src.Logins...) - dst.Roles = append(src.Roles[:0:0], src.Roles...) return dst } // A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse +// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse var _UserNeedsRegeneration = User(struct { ID UserID LoginName string @@ -35,7 +34,6 @@ var _UserNeedsRegeneration = User(struct { ProfilePicURL string Domain string Logins []LoginID - Roles []RoleID Created time.Time }{}) @@ -55,11 +53,12 @@ func (src *Node) Clone() *Node { dst.LastSeen = new(time.Time) *dst.LastSeen = *src.LastSeen } + dst.Capabilities = append(src.Capabilities[:0:0], src.Capabilities...) return dst } // A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse +// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse var _NodeNeedsRegeneration = Node(struct { ID NodeID StableID StableNodeID @@ -79,6 +78,7 @@ var _NodeNeedsRegeneration = Node(struct { LastSeen *time.Time KeepAlive bool MachineAuthorized bool + Capabilities []string ComputedName string computedHostIfDifferent string ComputedNameWithHost string @@ -100,7 +100,7 @@ func (src *Hostinfo) Clone() *Hostinfo { } // A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse +// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse var _HostinfoNeedsRegeneration = Hostinfo(struct { IPNVersion string FrontendLogID string @@ -137,7 +137,7 @@ func (src *NetInfo) Clone() *NetInfo { } // A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse +// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse var _NetInfoNeedsRegeneration = NetInfo(struct { MappingVariesByDestIP opt.Bool HairPinning opt.Bool @@ -152,65 +152,6 @@ var _NetInfoNeedsRegeneration = NetInfo(struct { DERPLatency map[string]float64 }{}) -// Clone makes a deep copy of Group. -// The result aliases no memory with the original. -func (src *Group) Clone() *Group { - if src == nil { - return nil - } - dst := new(Group) - *dst = *src - dst.Members = append(src.Members[:0:0], src.Members...) - return dst -} - -// A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse -var _GroupNeedsRegeneration = Group(struct { - ID GroupID - Name string - Members []ID -}{}) - -// Clone makes a deep copy of Role. -// The result aliases no memory with the original. -func (src *Role) Clone() *Role { - if src == nil { - return nil - } - dst := new(Role) - *dst = *src - dst.Capabilities = append(src.Capabilities[:0:0], src.Capabilities...) - return dst -} - -// A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse -var _RoleNeedsRegeneration = Role(struct { - ID RoleID - Name string - Capabilities []CapabilityID -}{}) - -// Clone makes a deep copy of Capability. -// The result aliases no memory with the original. -func (src *Capability) Clone() *Capability { - if src == nil { - return nil - } - dst := new(Capability) - *dst = *src - return dst -} - -// A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse -var _CapabilityNeedsRegeneration = Capability(struct { - ID CapabilityID - Type CapType - Val ID -}{}) - // Clone makes a deep copy of Login. // The result aliases no memory with the original. func (src *Login) Clone() *Login { @@ -223,7 +164,7 @@ func (src *Login) Clone() *Login { } // A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse +// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse var _LoginNeedsRegeneration = Login(struct { _ structs.Incomparable ID LoginID @@ -248,7 +189,7 @@ func (src *DNSConfig) Clone() *DNSConfig { } // A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse +// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse var _DNSConfigNeedsRegeneration = DNSConfig(struct { Nameservers []netaddr.IP Domains []string @@ -269,7 +210,7 @@ func (src *RegisterResponse) Clone() *RegisterResponse { } // A compilation failure here means this code must be regenerated, with command: -// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse +// tailscale.com/cmd/cloner -type User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse var _RegisterResponseNeedsRegeneration = RegisterResponse(struct { User User Login Login @@ -280,7 +221,7 @@ var _RegisterResponseNeedsRegeneration = RegisterResponse(struct { // Clone duplicates src into dst and reports whether it succeeded. // To succeed, must be of types <*T, *T> or <*T, **T>, -// where T is one of User,Node,Hostinfo,NetInfo,Group,Role,Capability,Login,DNSConfig,RegisterResponse. +// where T is one of User,Node,Hostinfo,NetInfo,Login,DNSConfig,RegisterResponse. func Clone(dst, src interface{}) bool { switch src := src.(type) { case *User: @@ -319,33 +260,6 @@ func Clone(dst, src interface{}) bool { *dst = src.Clone() return true } - case *Group: - switch dst := dst.(type) { - case *Group: - *dst = *src.Clone() - return true - case **Group: - *dst = src.Clone() - return true - } - case *Role: - switch dst := dst.(type) { - case *Role: - *dst = *src.Clone() - return true - case **Role: - *dst = src.Clone() - return true - } - case *Capability: - switch dst := dst.(type) { - case *Capability: - *dst = *src.Clone() - return true - case **Capability: - *dst = src.Clone() - return true - } case *Login: switch dst := dst.(type) { case *Login: diff --git a/tailcfg/tailcfg_test.go b/tailcfg/tailcfg_test.go index bc1c2d023..140374c92 100644 --- a/tailcfg/tailcfg_test.go +++ b/tailcfg/tailcfg_test.go @@ -194,6 +194,7 @@ func TestNodeEqual(t *testing.T) { "Key", "KeyExpiry", "Machine", "DiscoKey", "Addresses", "AllowedIPs", "Endpoints", "DERP", "Hostinfo", "Created", "LastSeen", "KeepAlive", "MachineAuthorized", + "Capabilities", "ComputedName", "computedHostIfDifferent", "ComputedNameWithHost", } if have := fieldsOf(reflect.TypeOf(Node{})); !reflect.DeepEqual(have, nodeHandles) {