use crate::{
DataFilter, PolarsViewError, PolarsViewResult, add_row_index_column, drop_columns_by_regex,
normalize_float_strings_by_regex, remove_null_columns, replace_values_with_null,
};
use polars::{prelude::*, sql::SQLContext};
pub trait DataFrameTransform: Send + Sync {
fn apply(&self, df: DataFrame, filter: &DataFilter) -> PolarsViewResult<DataFrame>;
}
pub struct DropColumnsTransform;
impl DataFrameTransform for DropColumnsTransform {
fn apply(&self, df: DataFrame, filter: &DataFilter) -> PolarsViewResult<DataFrame> {
tracing::debug!(
"Applying DropColumnsTransform (regex: '{}')",
filter.drop_regex
);
drop_columns_by_regex(df, &filter.drop_regex)
}
}
pub struct NormalizeTransform;
impl DataFrameTransform for NormalizeTransform {
fn apply(&self, df: DataFrame, filter: &DataFilter) -> PolarsViewResult<DataFrame> {
tracing::debug!(
"Applying NormalizeTransform (regex: '{}')",
filter.normalize_regex
);
normalize_float_strings_by_regex(df, &filter.normalize_regex)
}
}
pub struct ReplaceNullsTransform;
impl DataFrameTransform for ReplaceNullsTransform {
fn apply(&self, df: DataFrame, filter: &DataFilter) -> PolarsViewResult<DataFrame> {
let null_value_list: Vec<&str> = filter.parse_null_values();
if null_value_list.is_empty() {
tracing::trace!("ReplaceNullsTransform skipped: no null values configured.");
return Ok(df);
}
tracing::debug!(
"Applying ReplaceNullsTransform with values: {:?}",
null_value_list
);
replace_values_with_null(df, &null_value_list, false).map_err(crate::PolarsViewError::from)
}
}
pub struct SqlTransform;
impl DataFrameTransform for SqlTransform {
fn apply(&self, df: DataFrame, filter: &DataFilter) -> PolarsViewResult<DataFrame> {
tracing::debug!("Applying SqlTransform...");
let mut ctx = SQLContext::new();
ctx.register(&filter.table_name, df.lazy());
ctx.execute(&filter.query)?
.collect()
.map_err(crate::PolarsViewError::from)
}
}
pub struct RemoveNullColumnsTransform;
impl DataFrameTransform for RemoveNullColumnsTransform {
fn apply(&self, df: DataFrame, filter: &DataFilter) -> PolarsViewResult<DataFrame> {
let _ = filter;
let initial_width = df.width();
let result_df = remove_null_columns(df)?;
tracing::debug!(
"RemoveNullColumnsTransform applied. Width {} -> {}",
initial_width,
result_df.width()
);
Ok(result_df)
}
}
pub struct AddRowIndexTransform;
impl DataFrameTransform for AddRowIndexTransform {
fn apply(&self, df: DataFrame, filter: &DataFilter) -> PolarsViewResult<DataFrame> {
tracing::debug!("Applying AddRowIndexTransform...");
let row_index = filter.get_row_index(df.schema())?;
add_row_index_column(df, row_index).map_err(PolarsViewError::from)
}
}