Implement robust type handling in row_to_map: Enhanced the row_to_map function to provide a more reliable string representation of database values based on their actual types, improving error handling and data integrity.
This commit is contained in:
@@ -1,4 +1,5 @@
|
|||||||
use postgres::{Client, NoTls};
|
use postgres::{Client, NoTls};
|
||||||
|
use postgres::types::Type;
|
||||||
use postgres::Error as PgError;
|
use postgres::Error as PgError;
|
||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
@@ -84,11 +85,53 @@ impl Database {
|
|||||||
|
|
||||||
fn row_to_map(row: postgres::Row) -> Row {
|
fn row_to_map(row: postgres::Row) -> Row {
|
||||||
let mut map = HashMap::with_capacity(row.len());
|
let mut map = HashMap::with_capacity(row.len());
|
||||||
|
|
||||||
for (idx, col) in row.columns().iter().enumerate() {
|
for (idx, col) in row.columns().iter().enumerate() {
|
||||||
let name = col.name().to_string();
|
let name = col.name().to_string();
|
||||||
let value: Option<String> = row.get(idx);
|
let ty = col.type_();
|
||||||
map.insert(name, value.unwrap_or_default());
|
|
||||||
|
// Versuche je nach tatsächlichem DB-Typ eine sinnvolle
|
||||||
|
// String-Repräsentation zu erzeugen. Ziel ist maximale
|
||||||
|
// Robustheit: statt zu panic!en geben wir im Zweifel einen
|
||||||
|
// Debug-String zurück.
|
||||||
|
let value = match *ty {
|
||||||
|
// Ganzzahlen
|
||||||
|
Type::INT2 => row.try_get::<_, i16>(idx).map(|v| v.to_string()),
|
||||||
|
Type::INT4 => row.try_get::<_, i32>(idx).map(|v| v.to_string()),
|
||||||
|
Type::INT8 => row.try_get::<_, i64>(idx).map(|v| v.to_string()),
|
||||||
|
|
||||||
|
// Gleitkommazahlen / Numerics
|
||||||
|
Type::FLOAT4 => row.try_get::<_, f32>(idx).map(|v| v.to_string()),
|
||||||
|
Type::FLOAT8 | Type::NUMERIC => {
|
||||||
|
row.try_get::<_, f64>(idx).map(|v| v.to_string())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Textuelle Typen
|
||||||
|
Type::TEXT | Type::VARCHAR | Type::BPCHAR | Type::NAME => {
|
||||||
|
row.try_get::<_, String>(idx)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Booleans
|
||||||
|
Type::BOOL => row.try_get::<_, bool>(idx).map(|v| v.to_string()),
|
||||||
|
|
||||||
|
// Für Zeit-/Datums-Typen und alle anderen seltener
|
||||||
|
// verwendeten Typen nutzen wir eine generische Fallback-
|
||||||
|
// Strategie weiter unten.
|
||||||
|
|
||||||
|
// Fallback: Versuche direkt String, ansonsten Debug-Ausgabe.
|
||||||
|
_ => row
|
||||||
|
.try_get::<_, String>(idx)
|
||||||
|
.or_else(|_| {
|
||||||
|
// Letzter Rettungsanker: hole den Wert als `postgres::types::Type`
|
||||||
|
// existiert nicht direkt, daher nur ein Platzhalter-String.
|
||||||
|
Ok(format!("<unsupported type {:?}>", ty))
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
.unwrap_or_default();
|
||||||
|
|
||||||
|
map.insert(name, value);
|
||||||
|
}
|
||||||
|
|
||||||
map
|
map
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user