vitessio/vitess · critical
tablet record was taken over by another process: my address
Error message
tablet record was taken over by another process: my address is %v:%v, but record is owned by %v:%v
What it means
CheckOwnership verifies that the current process still owns its tablet record in the topo store by comparing hostname and vt port of the locally loaded tablet against the re-fetched record. If either differs, another process has overwritten the record (taken it over, e.g. after a previous instance failed to clean up or a stale process restarted), and this error reports both addresses.
Source
Thrown at go/vt/topotools/tablet.go:140
tablet.Type = newType
tablet.PrimaryTermStartTime = PrimaryTermStartTime
return nil
})
if err != nil {
return nil, err
}
return result, nil
}
// CheckOwnership returns nil iff the Hostname and port match on oldTablet and
// newTablet, which implies that no other tablet process has taken over the
// record.
func CheckOwnership(oldTablet, newTablet *topodatapb.Tablet) error {
if oldTablet == nil || newTablet == nil {
return errors.New("unable to verify ownership of tablet record")
}
if oldTablet.Hostname != newTablet.Hostname || oldTablet.PortMap["vt"] != newTablet.PortMap["vt"] {
return fmt.Errorf(
"tablet record was taken over by another process: "+
"my address is %v:%v, but record is owned by %v:%v",
oldTablet.Hostname, oldTablet.PortMap["vt"], newTablet.Hostname, newTablet.PortMap["vt"])
}
return nil
}
// DoCellsHaveRdonlyTablets returns true if any of the cells has at least one
// tablet with type RDONLY. If the slice of cells to search over is empty, it
// checks all cells in the topo.
func DoCellsHaveRdonlyTablets(ctx context.Context, ts *topo.Server, cells []string) (bool, error) {
areAnyRdonly := func(tablets []*topo.TabletInfo) bool {
for _, tablet := range tablets {
if tablet.Type == topodatapb.TabletType_RDONLY {
return true
}
}
View on GitHub (pinned to 01a25a7d17)
Solutions
- Verify no duplicate vttablet process is running with the same tablet alias (ps / container listing); kill the stale one, then re-register.
- If the record legitimately changed (hostname/IP moved), restart your vttablet so it reloads the current record or re-initializes with --init_keyspace etc. using the correct topology.
- Use vtctldclient to inspect the tablet record and, if it's orphaned, delete or fix it before retrying.
Example fix
// before: assuming ownership
err := topotools.CheckOwnership(oldTablet, newTablet)
// after: detect takeover and bail out loudly
if err := topotools.CheckOwnership(oldTablet, newTablet); err != nil {
log.Errorf("tablet %s record taken over, not proceeding", alias)
return err
} Defensive patterns
Strategy: type-guard
Validate before calling
cur, err := ts.GetTablet(ctx, tablet.Alias)
if err != nil {
return fmt.Errorf("cannot read current record: %w", err)
}
if cur.Hostname != myHostname || cur.PortMap["vt"] != myPort {
return fmt.Errorf("record owned by %v:%v; refusing to act", cur.Hostname, cur.PortMap["vt"])
} Type guard
func recordTakenOver(oldTablet, newTablet *topodatapb.Tablet) bool {
if oldTablet == nil || newTablet == nil {
return false
}
return oldTablet.Hostname != newTablet.Hostname || oldTablet.PortMap["vt"] != newTablet.PortMap["vt"]
} Try / catch
if err := topotools.CheckOwnership(oldTablet, newTablet); err != nil {
if strings.Contains(err.Error(), "taken over by another process") {
log.Error("duplicate vttablet suspected; shutting down this instance")
return err // do NOT proceed with actions on a contested record
}
return err
} Prevention
- Never start two vttablet processes with the same tablet alias/uid
- In containerized environments, ensure a fresh IP/hostname does not silently re-register an existing alias — re-init deliberately
- Use fencing/health checks to confirm the old process is dead before re-registering a tablet alias
When it happens
Trigger: Calling CheckOwnership (from tablet initialization/actions) when the tablet record in the topo has a different Hostname or PortMap["vt"] than the oldTablet passed in — i.e. another vttablet process re-registered the same tablet alias with its own address.
Common situations: Starting a second vttablet with the same tablet alias/uid while the first is still running; a container restarted with a new IP/hostname and re-registered the record; stale topo record overwritten by an orphaned process after a crash.
Related errors
- there are no cells in the topo
- SrvVSchema has no entry for keyspace %v
- shard %v/%v has no primary
- can't get primary tablet record %v: %v
- cells alias %v is not valid: %v
AI-assisted analysis of vitessio/vitess@01a25a7d17 (2026-09-01).
Data as JSON: /api/errors/4547259483ccaafd.
Report an issue: GitHub.