{"record":{"id":"e8167b8e69e9033e","repo":"crowdsecurity/crowdsec","slug":"listing-machines-w-w","errorCode":null,"errorMessage":"listing machines: %w: %w","messagePattern":"listing machines: %w: %w","errorType":"exception","errorClass":"QueryFail","httpStatus":null,"severity":"error","filePath":"pkg/database/machines.go","lineNumber":133,"sourceCode":"}\n\nfunc (c *Client) QueryMachineByID(ctx context.Context, machineID string) (*ent.Machine, error) {\n\tmachine, err := c.Ent.Machine.\n\t\tQuery().\n\t\tWhere(machine.MachineIdEQ(machineID)).\n\t\tOnly(ctx)\n\tif err != nil {\n\t\tc.Log.Warningf(\"QueryMachineByID : %s\", err)\n\t\treturn &ent.Machine{}, fmt.Errorf(\"user '%s': %w\", machineID, UserNotExists)\n\t}\n\n\treturn machine, nil\n}\n\nfunc (c *Client) ListMachines(ctx context.Context) ([]*ent.Machine, error) {\n\tmachines, err := c.Ent.Machine.Query().All(ctx)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"listing machines: %w: %w\", err, QueryFail)\n\t}\n\n\treturn machines, nil\n}\n\nfunc (c *Client) ValidateMachine(ctx context.Context, machineID string) error {\n\trets, err := c.Ent.Machine.Update().Where(machine.MachineIdEQ(machineID)).SetIsValidated(true).Save(ctx)\n\tif err != nil {\n\t\treturn fmt.Errorf(\"validating machine: %w: %w\", err, UpdateFail)\n\t}\n\n\tif rets == 0 {\n\t\treturn errors.New(\"machine not found\")\n\t}\n\n\treturn nil\n}\n","sourceCodeStart":115,"sourceCodeEnd":151,"githubUrl":"https://github.com/crowdsecurity/crowdsec/blob/909b5157986a2b2c2163300fdaef5ed01289f7d2/pkg/database/machines.go#L115-L151","documentation":"ListMachines wraps the generic QueryFail sentinel plus the underlying error when `c.Ent.Machine.Query().All(ctx)` fails. This is a read of the whole machines table, so the failure is at the database layer, not a per-record issue. The wrapped err carries the ent/SQL detail.","triggerScenarios":"Any call to ListMachines (LAPI /machines list controller, validMachineID checks, metrics collection, prune) while the DB is unreachable, the schema is out of sync, or the SQLite file is locked/corrupt.","commonSituations":"Postgres/MySQL container down in docker-compose; SQLite DB file permissions changed after running as different user; DB migrated by a newer crowdsec then downgraded; network cut to a remote DB.","solutions":["Read the wrapped %w error for the root cause (connection refused / table missing / etc.)","Confirm DB is up and reachable: `cscli machines list` will fail the same way","Run pending migrations so the schema matches the binary: `cscli migration`","Restore file permissions/ownership on the SQLite data dir (/var/lib/crowdsec/data)","Check db_config settings in /etc/crowdsec/config.yaml (host, port, user, type)"],"exampleFix":null,"handlingStrategy":"retry","validationCode":"// probe DB reachability before listing\nif err := db.Ent.Machine.Query().Limit(1).FirstErr(ctx) == nil {} // use as a health probe pattern","typeGuard":null,"tryCatchPattern":"machines, err := db.ListMachines(ctx)\nif err != nil {\n    // wrapped: cause := err; log with errors.Unwrap / %v, retry with backoff\n    return fmt.Errorf(\"listing machines: %v\", err)\n}","preventionTips":["Health-check the DB before starting LAPI (depends_on/healthcheck)","Pin crowdsec version to the schema version; run migrations on upgrade, never downgrade blindly","Watch SQLite file permissions when switching run users","Alert on DB connectivity from the LAPI host"],"tags":["database","query-failed","crowdsec","sqlite"],"backgroundTag":"database-query-failed","analyzedSha":"909b5157986a2b2c2163300fdaef5ed01289f7d2","analyzedAt":"2026-09-06T12:27:26.012Z","contentChangedAt":"2026-09-06T12:27:26.012Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}