3

I'm trying to "pretty-print" the result of a query. I don't know the query beforehand, so I can't manually convert. My idea was to iterate over the column information for the PgRow, and then for each column get the value.

This is the code I have currently:

fn row_to_json(row: PgRow) -> HashMap<String, String> {
    let mut result = HashMap::new();
    for col in row.columns() {
        let name = col.name();
        result.insert(name.to_string(), row.get(name));
    }

    result
}

However, this panics because row.get() doesn't know how to convert just any type into a string (even an integer). I also tried serde_json::Value but that didn't work.

How should I go about doing this? Is there a way to represent any SQL type in rust that can be converted to a string, or is there a better way to format a row?

CircuitSacul
  • 1,594
  • 12
  • 32

1 Answers1

3

After some digging (and help from the discord server), I solved this. The problem is that sqlx::query returns the data encoded in binary, which apparently isn't easy to just convert to a readable string.

If you call the .fetch_* method directly on an Executor (e.g. your pool) it will return the result as text. Combining this with the fixed code, I'm able to get a reasonable output.

fn row_to_json(row: PgRow) -> HashMap<String, String> {
    let mut result = HashMap::new();
    for col in row.columns() {
        let value = row.try_get_raw(col.ordinal()).unwrap();
        let value = match value.is_null() {
            true => "NULL".to_string(),
            false => value.as_str().unwrap().to_string(),
        };
        result.insert(
            col.name().to_string(),
            value,
        );
    }

    result
}
CircuitSacul
  • 1,594
  • 12
  • 32
  • For me it's saying` values.as_str()` is a private method. – Ayan Banerjee Jul 10 '22 at 16:44
  • @AyanBanerjee maybe you're using an older version of sqlx – CircuitSacul Jul 11 '22 at 03:06
  • 1
    If anyone is still having errors while trying this solution, the reason is because in order to trigger the result to be returned as text it's necessary to pass a `&str` to the `pool.fetch()` method instead of the `Query` object returned by the `sqlx::query()`. This is explained on this [changelog](https://github.com/launchbadge/sqlx/blob/76ae2865005cc79d56972d68d3be30805581103d/CHANGELOG.md#changed-7) and only works for Postgres and MySQL. – Eduardo macedo Oct 14 '22 at 15:39