henrygd/beszel · error
failed to delete from %s: %v
Error message
failed to delete from %s: %v
What it means
deleteOldSystemStats builds a raw DELETE query per stats collection with OR-joined time conditions and executes it against the PocketBase DB. If execution fails, the collection name is embedded in this error so the failing table is identified.
Source
Thrown at internal/records/records_deletion.go:96
now := time.Now().UTC()
for _, collection := range collections {
// Build the WHERE clause
var conditionParts []string
var params dbx.Params = make(map[string]any)
for i := range recordData {
rd := recordData[i]
// Create parameterized condition for this record type
dateParam := fmt.Sprintf("date%d", i)
conditionParts = append(conditionParts, fmt.Sprintf("(type = '%s' AND created < {:%s})", rd.recordType, dateParam))
params[dateParam] = now.Add(-rd.retention)
}
// Combine conditions with OR
conditionStr := strings.Join(conditionParts, " OR ")
// Construct and execute the full raw query
rawQuery := fmt.Sprintf("DELETE FROM %s WHERE %s", collection, conditionStr)
if _, err := app.DB().NewQuery(rawQuery).Bind(params).Execute(); err != nil {
return fmt.Errorf("failed to delete from %s: %v", collection, err)
}
}
return nil
}
// Deletes systemd service records that haven't been updated in the last 20 minutes
func deleteOldSystemdServiceRecords(app core.App) error {
now := time.Now().UTC()
twentyMinutesAgo := now.Add(-20 * time.Minute)
// Delete systemd service records where updated < twentyMinutesAgo
_, err := app.DB().NewQuery("DELETE FROM systemd_services WHERE updated < {:updated}").Bind(dbx.Params{"updated": twentyMinutesAgo.UnixMilli()}).Execute()
if err != nil {
return fmt.Errorf("failed to delete old systemd service records: %v", err)
}
return nil
}View on GitHub (pinned to b38fb7dafa)
Solutions
- Check the wrapped error (%v) for the SQLite/dxdb root cause (locked, disk full, no such table)
- Verify the stats collections still exist with the expected names in the PocketBase schema
- Check disk space and that no backup/other process holds an exclusive lock on the DB during cleanup
Example fix
// before
rawQuery := fmt.Sprintf("DELETE FROM %s WHERE %s", collection, conditionStr)
// after
// ensure collection exists and log the underlying error
if _, err := app.DB().NewQuery(rawQuery).Bind(params).Execute(); err != nil {
return fmt.Errorf("failed to delete from %s: %w", collection, err)
} Defensive patterns
Strategy: try-catch
Validate before calling
if !collectionExists(app, collection) {
return fmt.Errorf("stats collection %s missing from schema", collection)
}
if diskAlmostFull() { return errors.New("insufficient disk space for retention cleanup") } Try / catch
if err := records.DeleteOldSystemStats(app); err != nil {
log.Error().Err(err).Msg("system stats retention cleanup failed")
// alert/check DB lock and disk space; retry next cycle
} Prevention
- Monitor disk space on the hub host
- Avoid exclusive DB locks (backups) during cleanup windows
- Verify stats collection names after schema migrations
- Alert on retention-cleanup failures
When it happens
Trigger: DB-level failure executing the raw DELETE on a system_stats collection: locked database, disk full, permission issues, or a collection name that no longer exists in the schema.
Common situations: SQLite file locked by another process/backup job; disk quota exceeded on the host; schema migrations renaming/dropping a stats collection while retention cleanup still references it.
Related errors
- failed to delete old systemd service records: %v
- failed to delete old container records: %v
- failed to find systems collection: %v
- failed to create new system: %v
AI-assisted analysis of henrygd/beszel@b38fb7dafa (2026-08-31).
Data as JSON: /api/errors/4144a1e0e1c8054f.
Report an issue: GitHub.