Flow reference: Storage & Databases
Find Many Records
List records that match filters, sorted and paged: order lists, stock left, leaderboards (Bottly storage or your PostgreSQL).
List records that match filters, sorted and paged: order lists, stock left, leaderboards (Bottly storage or your PostgreSQL).
When and how to use it
Connect the input from the preceding step on the path that should perform this operation.
Fill the fields with data available in the trigger's context.
Connect the needed outputs; an unconnected path cannot run later blocks.
Configuration fields
Database — database
Bottly storage keeps records on Bottly (plan row limits, Storage page with import/export). Your PostgreSQL writes to your own database instead: the table and column names are used exactly as written, and values are sent as text parameters.
Input: Fixed choice.
Editor guidance: Bottly storage is built in (plan row limits apply). Your PostgreSQL uses your own database: tables and columns are used by name, values are sent as text parameters.
Available choices (preserve the exact value):
`` — Bottly storage
postgres — Your PostgreSQLConnection string (Your PostgreSQL) — connection
A postgres://user:password@host:5432/database URL, kept in a bot env secret such as {env.DATABASE_URL} rather than typed into the block. The host must be reachable on the public internet; TLS is used unless the URL ends with ?sslmode=disable (?sslmode=verify-full also checks the certificate).
Input: Text with variable suggestions.
Editor guidance: Only used with Your PostgreSQL. Empty uses {env.DATABASE_URL}. Keep it in an env secret, never typed here. The host must be public; TLS is used unless the URL says sslmode=disable.
Format example, not a ready value for your server:
{env.DATABASE_URL}.Table — table
Name the bot-owned record collection consistently, such as tickets. A typo addresses a different table, not an alias of the old one.
Input: Text.
Format example, not a ready value for your server:
orders.Default:
orders.Filters (one per line) — filters
One condition per line: field = value, or != > < >= <= and contains (case-insensitive). Every line must match; leave it empty for all records. Values that are both numbers compare as numbers (10 > 9), anything else as text, and a missing field counts as empty, so sold != yes also matches records that were never marked. Values may use variables such as {user.id}.
Input: Multiline text.
Editor guidance: field = value per line; also != > < >= <= and contains. Numbers compare as numbers. Every line must match. Empty = all records.
Format example, not a ready value for your server: `status = paid
price >= 5
name contains vip`.
Default:
user = {user.id}.Sort by field (empty = when saved) — sortField
Field to sort by: numbers by value first, then text, then records without the field. Leave it empty to sort by when the record was saved.
Input: Text.
Format example, not a ready value for your server:
price.Default: ``.
Order — sortOrder
desc puts the newest or highest first, asc the oldest or lowest. Find Many Records defaults to desc, Take One Item to asc (first in, first out).
Input: Fixed choice.
Default:
desc.Available choices (preserve the exact value):
desc — Newest / highest firstasc — Oldest / lowest firstLimit (1-100) — limit
Maximum count returned or allowed by this operation. For a guard, combine it with the time window; for a list, keep output readable.
Input: Number.
Default:
25.Skip (offset) — offset
How many matching records to skip before the list starts (0-10000), for pages: with a limit of 10, offset 10 shows the second page. Can be a variable.
Input: Text with variable suggestions.
Format example, not a ready value for your server:
0.Default: ``.
Line template (optional) — lineTemplate
How each record is written in {records.list}, for example • {name} — {price}. {field} is the record's own field (other variables still work); empty writes field: value pairs.
Input: Text.
Editor guidance: How each record looks in {records.list}. {field} is the record's field; empty shows field: value pairs.
Format example, not a ready value for your server:
{name} — {price}.Default: ``.
Store as — storeAs
Choose a short result prefix such as result. Later blocks must use this same prefix and run after this block. It is not a Discord channel or a persistent table.
Input: Text.
Editor guidance: {records.count}, {records.list} (one line each; For Each with separator \n), {records.json}, {records.0.field}…
Default:
records.Outputs and next steps
found: A matching record exists.empty: Nothing matched (or the storage could not be read; {prefix.error} says why); answer, for example, "Out of stock".Read the result after this block, using its configured prefix and the fields supported by the selected operation. Do not assume every response has a text or id field.
Test and troubleshoot
Test a missing record, then save and read the same lookup value. Use a narrow filter for Update/Delete. Renaming a table or field changes where the lookup runs.
Save, validate and publish. Perform one real test and read the first relevant log error. [Testing](/docs/flow-testing) · [Variables](/docs/flow-variables) · [Permissions](/docs/flow-permissions).
Save, validate and publish. Perform one real test and read the first relevant log error. [Testing](/docs/flow-testing) · [Variables](/docs/flow-variables) · [Permissions](/docs/flow-permissions).