Was this page helpful?
Session::query_unpaged
, Session::query_single_page
, Session::execute_unpaged
and Session::execute_single_page
return a QueryResult
with rows represented as Option<Vec<Row>>
.
Note
Using unpaged queries for SELECTs is discouraged in general. Query results may be so big that it is not preferable to fetch them all at once. Even with small results, if there are a lot of tombstones, then there can be similar bad consequences. However,query_unpaged
will return all results in one, possibly giant, piece (unless a timeout occurs due to high load incurred by the cluster). This:
increases latency,
has large memory footprint,
puts high load on the cluster,
is more likely to time out (because big work takes more time than little work, and returning one large piece of data is more work than returning one chunk of data).
To sum up, for SELECTs (especially those that may return a lot of data) prefer paged queries, e.g. with
Session::query_iter()
(see Paged queries).
By calling QueryResult::into_rows_result
,
one can obtain QueryRowsResult
.
QueryRowsResult
provides convenience methods for parsing rows.
Here are a few of them:
rows::<RowT>()
- returns the rows parsed as the given type
maybe_first_row::<RowT>()
- returns the first received row or None
if there are no rows
first_row::<RowT>()
- returns the first received row; fails if there are no rows
single_row::<RowT>()
- same as first_row
, but fails when there is more than one row
Additionally, QueryResult
has a method result_not_rows()
, which ensures that query response was not rows
and thus helps avoid bugs.
// Parse row as a single column containing an int value
let result = session
.query_unpaged("SELECT a from ks.tab", &[])
.await?
.into_rows_result()?;
for row in result.rows::<(i32,)>()? {
let (int_value,): (i32,) = row?;
}
// first_row gets the first row and parses it as the given type
let first_int_val: (i32,) = session
.query_unpaged("SELECT a from ks.tab", &[])
.await?
.into_rows_result()?
.first_row::<(i32,)>()?;
// result_not_rows fails when the response is rows
session.query_unpaged("INSERT INTO ks.tab (a) VALUES (0)", &[]).await?.result_not_rows()?;
For more see QueryResult
and QueryRowsResult
NULL
values¶NULL
values will return an error when parsed as a Rust type.
To properly handle NULL
values parse column as an Option<>
:
use scylla::IntoTypedRows;
// Parse row as two columns containing an int and text which might be null
let rows_result = session
.query_unpaged("SELECT a, b from ks.tab", &[])
.await?
.into_rows_result()?;
for row in rows_result.rows::<(i32, Option<&str>)>()? {
let (int_value, str_or_null): (i32, Option<&str>) = row?;
}
It is possible to receive row as a struct with fields matching the columns.
The struct must:
have the same number of fields as the number of queried columns
have field types matching the columns being received
derive DeserializeRow
Field names don’t need to match column names.
use scylla::IntoTypedRows;
use scylla::macros::DeserializeRow;
use scylla::deserialize::DeserializeRow;
#[derive(DeserializeRow)]
struct MyRow {
age: i32,
name: Option<String>,
}
// Parse row as two columns containing an int and text which might be null
let result_rows = session
.query_unpaged("SELECT a, b from ks.tab", &[])
.await?
.into_rows_result()?;
for row in result_rows.rows::<MyRow>()? {
let my_row: MyRow = row?;
}
For parsing other data types see Data Types
Was this page helpful?