Table of Contents

Class ResultReader

Namespace
YndigoBlue.Velocity.Engine
Assembly
YndigoBlue.Velocity.dll

Provides forward-only, read-once iteration over query results with minimal memory overhead.

public class ResultReader : IEnumerable<Result>, IEnumerable, IAsyncEnumerable<Result>, IDisposable, IAsyncDisposable
Inheritance
ResultReader
Implements

Remarks

ResultReader is a connected, streaming result processor that wraps a database reader for efficient memory usage when processing large result sets. Unlike ResultSet which loads all results into memory, ResultReader processes rows one at a time as they're retrieved from the database.

Key Characteristics:

  • Forward-only iteration - cannot go backwards or re-read results
  • Minimal memory footprint - only one row in memory at a time
  • Requires active database connection during iteration
  • Must be disposed to release database resources
  • Ideal for processing large datasets or streaming operations

When to Use:

  • Processing large result sets where memory is a concern
  • Streaming data transformations or exports
  • Sequential processing where random access isn't needed
  • Real-time data processing or ETL operations

Use ResultSet instead when:

  • Need random access to results (indexing)
  • Need to iterate multiple times
  • Need to filter or sort results in memory
  • Result set is small enough to fit in memory

Examples

var conn = new PostgreSqlDatasourceConnection
{
    Hostname = "localhost",
    Database = "mydatabase",
    Username = "user",
    Password = "password"
};

using (var manager = new Manager(conn))
{
    var schema = manager.LoadSchema("public");
    var usersTable = schema["users"];

    var query = new Query()
        .Select([usersTable["id"], usersTable["name"], usersTable["email"]])
        .From(usersTable)
        .Where(new Criterion<bool>(usersTable["active"], ConditionalType.Equals, true));

    // Use ResultReader for large datasets
    using (ResultReader reader = manager.ExecuteReader(query))
    {
        foreach (Result row in reader)
        {
            int id = row.GetFieldInteger("id");
            string name = row.GetFieldVarChar("name");
            string email = row.GetFieldVarChar("email");

            Console.WriteLine($"{id}: {name} ({email})");
        }
    } // Reader and connection are disposed here
}

Methods

BindColumnAsync<T>(int, CancellationToken)

Asynchronous counterpart to BindColumn<T>(int). Binds a single column from query results to a typed async sequence by column index.

BindColumnAsync<T>(string, CancellationToken)

Asynchronous counterpart to BindColumn<T>(string). Binds a single column from query results to a typed async sequence by column name.

BindColumnAsync<T>(CancellationToken)

Asynchronous counterpart to BindColumn<T>(). Binds the first column from query results to a typed async sequence.

BindColumn<T>()

Binds the first column from query results to a typed enumerable collection.

BindColumn<T>(int)

Binds a single column from query results to a typed enumerable collection by column index.

BindColumn<T>(string)

Binds a single column from query results to a typed enumerable collection by column name.

BindResultsAsync<T>(BindingType, CancellationToken)

Asynchronous counterpart to BindResults<T>(BindingType). Binds query results to a typed async sequence using the specified binding strategy, streaming rows from the live database reader one at a time using await foreach.

BindResults<T>(BindingType)

Binds query results to a typed enumerable collection using the specified binding strategy.

Dispose()

Releases the underlying DbDataReader and DbCommand, closing the server-side cursor and freeing the associated connection resources.

DisposeAsync()

Asynchronous counterpart to Dispose(). Releases the underlying DbDataReader and DbCommand without blocking a thread while the provider performs any async cleanup.

GetAsyncEnumerator(CancellationToken)

Returns an async enumerator that reads and yields one untyped Result per row from the underlying database reader, enabling await foreach (Result row in reader).

GetEnumerator()

Returns an enumerator that reads and yields one untyped Result per row from the underlying database reader, enabling foreach (Result row in reader).

GetGeoJSON(Stream, string, string)

Converts query results containing geospatial data to GeoJSON format, writing each feature to stream as it's read rather than materializing the entire result set in memory first.

GetGeoJSON(string, string)

Converts query results containing geospatial data to GeoJSON format.

GetGeoJSONAsync(Stream, string, string, CancellationToken)

Asynchronously converts query results containing geospatial data to GeoJSON format, writing each feature to stream as it's read via non-blocking I/O, rather than materializing the entire result set in memory first.

GetGeoJSONAsync(string, string, CancellationToken)

Asynchronously converts the results to GeoJSON format.