{"record":{"id":"d400a6f5bfb69e82","repo":"vitessio/vitess","slug":"recovery-isrecoverydisabled-v","errorCode":null,"errorMessage":"recovery.IsRecoveryDisabled(): %v","messagePattern":"recovery\\.IsRecoveryDisabled\\(\\): (.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"go/vt/vtorc/logic/disable_recovery.go","lineNumber":58,"sourceCode":"\n// IsRecoveryDisabled returns true if Recoveries are disabled globally\nfunc IsRecoveryDisabled() (disabled bool, err error) {\n\tquery := `SELECT\n\t\tCOUNT(*) AS mycount\n\tFROM\n\t\tglobal_recovery_disable\n\tWHERE\n\t\tdisable_recovery = ?\n\t`\n\terr = db.QueryVTOrc(query, sqlutils.Args(1), func(m sqlutils.RowMap) error {\n\t\tmycount := m.GetInt(\"mycount\")\n\t\tdisabled = (mycount > 0)\n\t\treturn nil\n\t})\n\tif err != nil {\n\t\terrMsg := fmt.Sprintf(\"recovery.IsRecoveryDisabled(): %v\", err)\n\t\tlog.Error(errMsg)\n\t\terr = errors.New(errMsg)\n\t}\n\treturn disabled, err\n}\n\n// DisableRecovery ensures recoveries are disabled globally\nfunc DisableRecovery() error {\n\t_, err := db.ExecVTOrc(`INSERT OR IGNORE\n\t\tINTO global_recovery_disable (\n\t\t\tdisable_recovery\n\t\t) VALUES (1)`)\n\treturn err\n}\n\n// EnableRecovery ensures recoveries are enabled globally\nfunc EnableRecovery() error {\n\t// The \"WHERE\" clause is just to avoid full-scan reports by monitoring tools\n\t_, err := db.ExecVTOrc(`DELETE\n\t\tFROM global_recovery_disable","sourceCodeStart":40,"sourceCodeEnd":76,"githubUrl":"https://github.com/vitessio/vitess/blob/01a25a7d176f94613b8d59d799f438380a8760e4/go/vt/vtorc/logic/disable_recovery.go#L40-L76","documentation":"IsRecoveryDisabled wraps any error from its internal count query (checking the disable-recovery flag in the vtorc database) into this prefixed message. It indicates the check itself failed, not that recovery is disabled — the disabled result is unreliable in this case.","triggerScenarios":"The SELECT counting disable-recovery entries fails: vtorc's backend database is unreachable, the config table is missing/corrupted, or a DB timeout occurred.","commonSituations":"vtorc backend MySQL restarted or network blip during the check; schema mismatch after upgrade (missing vtorc internal tables); wrong backend DB credentials.","solutions":["Check vtorc's backend database connectivity and credentials in the vtorc config.","Verify the vtorc internal schema tables exist (run any vtorc schema-init/migration step).","Inspect the wrapped error (%v payload) for the root MySQL error and address it.","Retry after transient DB failures; executeCheckAndRecoverFunction will re-run checks on the next tick."],"exampleFix":null,"handlingStrategy":"retry","validationCode":"if err := backendDBPing(); err != nil {\n    return fmt.Errorf(\"backend DB unavailable before recovery-disable check: %w\", err)\n}","typeGuard":null,"tryCatchPattern":"disabled, err := logic.IsRecoveryDisabled(ctx)\nif err != nil {\n    log.Error(\"could not determine recovery-disabled state; skipping this tick\", slog.Any(\"error\", err))\n    return nil // retry on next check tick\n}","preventionTips":["Monitor vtorc backend database health and connectivity.","Ensure vtorc internal schema tables exist after upgrades.","Treat check failures as 'unknown', never assume recovery is enabled or disabled."],"tags":["vtorc","database","recovery-disabled","mysql"],"backgroundTag":"database-unavailable","analyzedSha":"01a25a7d176f94613b8d59d799f438380a8760e4","analyzedAt":"2026-09-01T17:28:30.605Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}