Open CallumDowling opened 4 years ago
use mysql::*;
use mysql::prelude::*;
use std::fmt;
#[derive(Debug)]
struct RowData(Vec<Option<String>>);
impl fmt::Display for RowData {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
for value in &self.0 {
match value {
Some(val) => write!(f, "{}\t", val)?,
None => write!(f, "N/A\t")?,
}
}
writeln!(f)
}
}
fn main() -> Result<()> {
let url = "mysql://username:password@localhost:3306/database";
let pool = Pool::new(url)?;
let mut conn = pool.get_conn()?;
let querystring = "SELECT * FROM your_table";
// Execute the query
let result: Vec<Row> = conn.query(querystring)?;
// Fetch the column names
let column_names: Vec<String> = conn.query(format!("DESCRIBE your_table"))?
.into_iter()
.map(|row| row.get::<String, _>(0).unwrap())
.collect();
// Process the rows
let mut rows_data: Vec<RowData> = Vec::new();
for row in result {
let mut row_data = Vec::new();
for (i, col) in row.columns_ref().iter().enumerate() {
if let Some(value) = row.get_opt::<String, usize>(i) {
row_data.push(value);
} else {
row_data.push(None);
}
}
rows_data.push(RowData(row_data));
}
// Print headers
println!("{}", column_names.join("\t"));
// Print rows
for row_data in rows_data {
println!("{}", row_data);
}
Ok(())
}
Hi all, my use case is using the query! macro to extract both the column names and the row information such that when a column name or alias changes, I don't need to worry about change anywhere except for the query. The data is being used in a html table. At the moment I have to write the column names separately for my frontend, but if the query gets changed, and I don't update the column names the wrong data might be shown to the user.
I know I can use describe on a query to get a vector of header names, but this leaves me with the same problem because when i use map on the record, I may forget to add a column, or put it in the right order.
What I am looking to do is something like
pseudocode using mysql executor, excuse the dodgy code
Has anyone found an elegant way to do this?