{"record":{"id":"daba77f5717bcee8","repo":"crowdsecurity/crowdsec","slug":"listing-bouncers-w-w","errorCode":null,"errorMessage":"listing bouncers: %w: %w","messagePattern":"listing bouncers: %w: %w","errorType":"exception","errorClass":"QueryFail","httpStatus":null,"severity":"error","filePath":"pkg/database/bouncers.go","lineNumber":75,"sourceCode":"\t\treturn nil, err\n\t}\n\n\treturn result, nil\n}\n\nfunc (c *Client) SelectBouncerByName(ctx context.Context, bouncerName string) (*ent.Bouncer, error) {\n\tresult, err := c.Ent.Bouncer.Query().Where(bouncer.NameEQ(bouncerName)).First(ctx)\n\tif err != nil {\n\t\treturn nil, err\n\t}\n\n\treturn result, nil\n}\n\nfunc (c *Client) ListBouncers(ctx context.Context) ([]*ent.Bouncer, error) {\n\tresult, err := c.Ent.Bouncer.Query().All(ctx)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"listing bouncers: %w: %w\", err, QueryFail)\n\t}\n\n\treturn result, nil\n}\n\nfunc (c *Client) CreateBouncer(ctx context.Context, name string, ipAddr string, apiKey string, authType string, autoCreated bool) (*ent.Bouncer, error) {\n\tbouncer, err := c.Ent.Bouncer.\n\t\tCreate().\n\t\tSetName(name).\n\t\tSetAPIKey(apiKey).\n\t\tSetRevoked(false).\n\t\tSetAuthType(authType).\n\t\tSetIPAddress(ipAddr).\n\t\tSetAutoCreated(autoCreated).\n\t\tSave(ctx)\n\tif err != nil {\n\t\tif ent.IsConstraintError(err) {\n\t\t\treturn nil, fmt.Errorf(\"bouncer %s already exists\", name)","sourceCodeStart":57,"sourceCodeEnd":93,"githubUrl":"https://github.com/crowdsecurity/crowdsec/blob/909b5157986a2b2c2163300fdaef5ed01289f7d2/pkg/database/bouncers.go#L57-L93","documentation":"ListBouncers runs a plain ent query for all bouncers. On failure it wraps the error together with the shared QueryFail sentinel, producing the double-%w format 'listing bouncers: <err>: <QueryFail text>'. It means the bouncer table could not be read.","triggerScenarios":"Any of validBouncerID, cscli 'bouncers list' (delete/List), pushUsageMetrics, or GetMetrics when the ent Bouncer.Query().All fails: SQLite locked, file missing/corrupt, schema version mismatch.","commonSituations":"Running 'cscli bouncers list' while the daemon bulk-inserts metrics; pointing cscli at a different/absent DB file than the daemon uses.","solutions":["Confirm cscli and the daemon point to the same DB (check db_config in crowdsec.yaml)","Read the wrapped error; 'no such table: bouncers' means run the DB migration/upgrade flow","Resolve SQLite lock contention or restore a corrupted DB from backup"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"bouncers, err := c.ListBouncers(ctx)\nif err != nil {\n    if errors.Is(err, QueryFail) || strings.Contains(err.Error(), \"locked\") {\n        return retryAfterBackoff(ctx, func() error { b, e := c.ListBouncers(ctx); bouncers = b; return e })\n    }\n    return fmt.Errorf(\"cannot list bouncers, check DB availability: %w\", err)\n}","preventionTips":["Ensure cscli and the daemon point at the same DB file","Run migrations after every binary upgrade","Back up the SQLite file before administrative operations"],"tags":["database","bouncer","query","cscli"],"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"}