PRQL/prql · error · Error
expected a table or query, found an empty tuple
Error message
expected a table or query, found an empty tuple `{}` What it means
Same validation as the empty-array case: when a relation argument is a bare empty tuple `{}` it has no lineage and cannot act as a table, so the resolver throws this specific error instead of bug #4317 (which is reserved for other lineage-less arguments).
Solutions
- Replace the empty tuple with a real relation (`from table` or `from_text ...`)
- Check the upstream expression producing the tuple — it is likely losing its columns
- Remove the empty tuple argument if it was accidental
Example fix
// before
from {}
// after
from employees Defensive patterns
Strategy: validation
Validate before calling
function validateRelationArg(arg) {
if (arg && typeof arg === "object" && !Array.isArray(arg) && Object.keys(arg).length === 0) {
throw new Error("empty tuple {} is not a table; use from_text or a real table");
}
} Type guard
function isEmptyTupleLiteral(expr) {
return expr && expr.kind === "tuple" && expr.items.length === 0;
} Try / catch
try {
compile(query);
} catch (e) {
if (e.message.includes("an empty tuple")) {
console.error("Tuple literals are not relations; source from a table or from_text.");
} else { throw e; }
} Prevention
- Never pass {} as a pipeline source
- Trace intermediate variables that may collapse to empty tuples
- Use from/join only with tables, views, or from_text output
When it happens
Trigger: `from {}` or passing an empty tuple literal `{}` to a function/transform expecting a table or query.
Common situations: Misusing tuple literals as data sources, or an intermediate variable that ended up an empty tuple being fed to `from`/`join`.
Understand the failure class
Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.
Related errors
- expected , found
- expected a type, found
- expected a value, found a type
- expected a table or query, found an empty array `[]`
- tuple: expected to have at least one entry when initial…
AI-assisted analysis of PRQL/prql@e164e249b9 (2026-09-09).
Data as JSON: /api/errors/84611507daaaccc7.
Report an issue: GitHub.
Appendix: source
Thrown at prqlc/prqlc/src/semantic/resolver/functions.rs:280
log::debug!("resolved arg to {}", arg.kind.as_ref());
resolved_relations.push((index, arg, is_last));
}
// Then, add relation frames into scope
for (index, arg, is_last) in resolved_relations {
if partial_application_position.is_none() {
let frame = arg.lineage.as_ref().ok_or_else(|| {
// Provide helpful error for empty arrays/tuples used directly
// (not from functions like std.from_text which set lineage properly)
match &arg.kind {
ExprKind::Array(v) if v.is_empty() => Error::new(Reason::Expected {
who: None,
expected: "a table or query".to_string(),
found: "an empty array `[]`".to_string(),
})
.with_span(arg.span),
ExprKind::Tuple(v) if v.is_empty() => Error::new(Reason::Expected {
who: None,
expected: "a table or query".to_string(),
found: "an empty tuple `{}`".to_string(),
})
.with_span(arg.span),
_ => Error::new_bug(4317).with_span(closure.body.span),
}
})?;
if is_last {
self.root_mod.module.insert_frame(frame, NS_THIS);
} else {
self.root_mod.module.insert_frame(frame, NS_THAT);
}
}
closure.args[index] = arg;
}
}View on GitHub (pinned to e164e249b9)