mirror of
https://github.com/juanfont/headscale.git
synced 2026-11-04 04:34:07 +09:00
db, types: add a nodes column for the ephemeral flag
The migration fills it from the key each node references.
This commit is contained in:
1 parent
95efb8cef1
commit
5827e4b73c
6 files changed
+53
-2
No files matched your search
@@ -294,6 +294,43 @@ WHERE tags IS NOT NULL AND tags != '[]' AND tags != '' AND tags != 'null'
|
||||
},
|
||||
Rollback: func(db *gorm.DB) error { return nil },
|
||||
},
|
||||
{
|
||||
// Store a node's ephemeral flag on the node, taken from the
|
||||
// key it references, so a login with another key keeps it.
|
||||
ID: "202610211300-node-ephemeral",
|
||||
Migrate: func(tx *gorm.DB) error {
|
||||
// The column and backfill commit together, before gormigrate
|
||||
// records the migration; a stop in between leaves both done.
|
||||
if tx.Migrator().HasColumn(&types.Node{}, "ephemeral") {
|
||||
return nil
|
||||
}
|
||||
|
||||
return tx.Transaction(func(tx *gorm.DB) error {
|
||||
colType := "numeric"
|
||||
if tx.Name() != sqlite.DriverName {
|
||||
colType = "boolean"
|
||||
}
|
||||
|
||||
err := tx.Exec(`ALTER TABLE nodes ADD COLUMN ephemeral ` + colType + ` DEFAULT false`).Error
|
||||
if err != nil {
|
||||
return fmt.Errorf("adding ephemeral to nodes: %w", err)
|
||||
}
|
||||
|
||||
err = tx.Exec(`
|
||||
UPDATE nodes SET ephemeral = true
|
||||
WHERE auth_key_id IN (
|
||||
SELECT id FROM credentials WHERE kind = ? AND ephemeral = true
|
||||
);
|
||||
`, types.CredentialPreAuthKey).Error
|
||||
if err != nil {
|
||||
return fmt.Errorf("backfilling ephemeral on nodes: %w", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
})
|
||||
},
|
||||
Rollback: func(db *gorm.DB) error { return nil },
|
||||
},
|
||||
},
|
||||
)
|
||||
|
||||
|
||||
@@ -86,6 +86,7 @@ CREATE TABLE nodes(
|
||||
register_method text,
|
||||
tags text,
|
||||
auth_key_id integer,
|
||||
ephemeral numeric DEFAULT false,
|
||||
last_seen datetime,
|
||||
expiry datetime,
|
||||
approved_routes text,
|
||||
|
||||
@@ -1965,7 +1965,8 @@ var nodeFieldImpact = map[string]string{
|
||||
"MachineKey": "payload", "NodeKey": "payload", "DiscoKey": "payload",
|
||||
"Endpoints": "payload", "Hostname": "payload", "GivenName": "payload",
|
||||
"RegisterMethod": "payload", "AuthKeyID": "payload", "AuthKey": "payload",
|
||||
"Expiry": "election", "LastSeen": "payload", "CreatedAt": "payload",
|
||||
"Ephemeral": "payload",
|
||||
"Expiry": "election", "LastSeen": "payload", "CreatedAt": "payload",
|
||||
"UpdatedAt": "payload", "DeletedAt": "payload",
|
||||
"ActiveSessions": "payload", "SessionEpoch": "payload", "SessionStart": "election",
|
||||
}
|
||||
|
||||
@@ -173,6 +173,11 @@ type Node struct {
|
||||
AuthKeyID *uint64 `sql:"DEFAULT:NULL"`
|
||||
AuthKey *Credential
|
||||
|
||||
// Ephemeral is taken from the key the node was created with. Logging in
|
||||
// again with another key keeps it, as Tailscale does; a user claiming a
|
||||
// tagged node clears it.
|
||||
Ephemeral bool `gorm:"default:false"`
|
||||
|
||||
Expiry *time.Time
|
||||
|
||||
// LastSeen is when the node was last in contact with
|
||||
|
||||
@@ -99,6 +99,7 @@ var _NodeCloneNeedsRegeneration = Node(struct {
|
||||
Tags Strings
|
||||
AuthKeyID *uint64
|
||||
AuthKey *Credential
|
||||
Ephemeral bool
|
||||
Expiry *time.Time
|
||||
LastSeen *time.Time
|
||||
ApprovedRoutes Prefixes
|
||||
|
||||
@@ -236,7 +236,12 @@ func (v NodeView) Tags() views.Slice[string] { return views.SliceOf(v.ж.Tags) }
|
||||
// authkey), which is what auth_key_id references.
|
||||
func (v NodeView) AuthKeyID() views.ValuePointer[uint64] { return views.ValuePointerOf(v.ж.AuthKeyID) }
|
||||
|
||||
func (v NodeView) AuthKey() CredentialView { return v.ж.AuthKey.View() }
|
||||
func (v NodeView) AuthKey() CredentialView { return v.ж.AuthKey.View() }
|
||||
|
||||
// Ephemeral is taken from the key the node was created with. Logging in
|
||||
// again with another key keeps it, as Tailscale does; a user claiming a
|
||||
// tagged node clears it.
|
||||
func (v NodeView) Ephemeral() bool { return v.ж.Ephemeral }
|
||||
func (v NodeView) Expiry() views.ValuePointer[time.Time] { return views.ValuePointerOf(v.ж.Expiry) }
|
||||
|
||||
// LastSeen is when the node was last in contact with
|
||||
@@ -314,6 +319,7 @@ var _NodeViewNeedsRegeneration = Node(struct {
|
||||
Tags Strings
|
||||
AuthKeyID *uint64
|
||||
AuthKey *Credential
|
||||
Ephemeral bool
|
||||
Expiry *time.Time
|
||||
LastSeen *time.Time
|
||||
ApprovedRoutes Prefixes
|
||||
|
||||
Reference in new issue
Block a user