k3s-io/k3s · error
does not exist, please pass --token to complete the restora
Error message
does not exist, please pass --token to complete the restoration
What it means
When restoring a cluster from a snapshot (--cluster-reset --cluster-reset-restore-path), k3s needs the original cluster token to seed the new cluster. If --token/K3S_TOKEN is empty it falls back to reading <data-dir>/server/token; when that file is also absent the restoration aborts before touching the datastore.
Source
Thrown at pkg/cli/server/server.go:505
}
dataDir, err := datadir.LocalHome(cfg.DataDir, false)
if err != nil {
return err
}
// delete local loadbalancers state for apiserver and supervisor servers
loadbalancer.ResetLoadBalancer(filepath.Join(dataDir, "agent"), loadbalancer.SupervisorServiceName)
loadbalancer.ResetLoadBalancer(filepath.Join(dataDir, "agent"), loadbalancer.APIServerServiceName)
if cfg.ClusterResetRestorePath != "" {
// at this point we're doing a restore. Check to see if we've
// passed in a token and if not, check if the token file exists.
// If it doesn't, return an error indicating the token is necessary.
if cfg.Token == "" {
tokenFile := filepath.Join(dataDir, "server", "token")
if _, err := os.Stat(tokenFile); err != nil {
if os.IsNotExist(err) {
return errors.New(tokenFile + " does not exist, please pass --token to complete the restoration")
}
}
}
}
}
logrus.Info("Starting " + version.Program + " " + app.App.Version)
notifySocket := os.Getenv("NOTIFY_SOCKET")
os.Unsetenv("NOTIFY_SOCKET")
// try setting advertise-ip from agent VPN
if vpnInfo, _ := vpn.GetInfoFromExecutor(); vpnInfo != nil {
// If we are in ipv6-only mode, we should pass the ipv6 address. Otherwise, ipv4
if utilsnet.IsIPv6(nodeIPs[0]) {
if vpnInfo.IPv6Address != nil {
logrus.Infof("Changed advertise-address to %v due to VPN", vpnInfo.IPv6Address)
if serverConfig.ControlConfig.AdvertiseIP != "" {View on GitHub (pinned to 6ba341e396)
Solutions
- Pass the original cluster token: `--token <value>` or `K3S_TOKEN=<value>` (it must match the token used when the snapshot was taken for nodes to rejoin)
- Restore <data-dir>/server/token from a backup copy if the original token value is unknown
- Keep the cluster token in a secret manager at cluster creation time so restores are always possible
Example fix
# before k3s server --cluster-reset --cluster-reset-restore-path=/backups/etcd-snapshot.zip # after K3S_TOKEN=<original-cluster-token> k3s server --cluster-reset --cluster-reset-restore-path=/backups/etcd-snapshot.zip
Defensive patterns
Strategy: validation
Validate before calling
# guard before restore if [ -n "$RESTORE_PATH" ] && [ -z "$K3S_TOKEN" ] && [ ! -s /var/lib/rancher/k3s/server/token ]; then echo 'token required for cluster-reset restore'; exit 1 fi
Prevention
- Store the cluster token in a password manager/secret at cluster creation
- DR runbooks should verify token availability (env or <data-dir>/server/token) before invoking restore
- Backup <data-dir>/server/token alongside etcd snapshots
When it happens
Trigger: `k3s server --cluster-reset --cluster-reset-restore-path=<snap>` with no --token and no <data-dir>/server/token file — typical when restoring onto a wiped or brand-new node.
Common situations: Disaster recovery onto new hardware where the data-dir was freshly created; cleanup scripts that deleted the token file; operators assuming the token is embedded in the snapshot.
Related errors
- invalid flag use; --cluster-reset required with --cluster-re
- cannot perform cluster-reset while server URL is set - remov
- Managed etcd cluster membership has been reset, restart with
- etcd: snapshot path does not exist: %s
- etcd: snapshot path must be a file, not a directory: %s
AI-assisted analysis of k3s-io/k3s@6ba341e396 (2026-08-15).
Data as JSON: /api/errors/2c66303220b92f4f.
Report an issue: GitHub.