From 67d320960d940b3164d94cfd57717cb5afbdf236 Mon Sep 17 00:00:00 2001 From: Jussi Saurio Date: Sat, 27 Sep 2025 09:37:15 +0300 Subject: [PATCH] ALTER TABLE: prevent dropping/renaming column referenced in VIEW --- core/vdbe/execute.rs | 45 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/core/vdbe/execute.rs b/core/vdbe/execute.rs index 4cc61a4f6..de826ebd1 100644 --- a/core/vdbe/execute.rs +++ b/core/vdbe/execute.rs @@ -7929,6 +7929,16 @@ pub fn op_drop_column( } } + for (view_name, view) in schema.views.iter() { + let view_select_sql = format!("SELECT * FROM {view_name}"); + conn.prepare(view_select_sql.as_str()).map_err(|e| { + LimboError::ParseError(format!( + "cannot drop column \"{}\": referenced in VIEW {view_name}: {}", + column_name, view.sql, + )) + })?; + } + state.pc += 1; Ok(InsnFunctionStepResult::Step) } @@ -7984,6 +7994,20 @@ pub fn op_alter_column( let conn = program.connection.clone(); let normalized_table_name = normalize_ident(table_name.as_str()); + let old_column_name = { + let schema = conn.schema.read(); + let table = schema + .tables + .get(table_name) + .expect("table being ALTERed should be in schema"); + table + .get_column_at(*column_index) + .expect("column being ALTERed should be in schema") + .name + .as_ref() + .expect("column being ALTERed should be named") + .clone() + }; let new_column = crate::schema::Column::from(definition); conn.with_schema_mut(|schema| { @@ -8025,6 +8049,27 @@ pub fn op_alter_column( } }); + let schema = conn.schema.read(); + if *rename { + let table = schema + .tables + .get(&normalized_table_name) + .expect("table being ALTERed should be in schema"); + let column = table + .get_column_at(*column_index) + .expect("column being ALTERed should be in schema"); + for (view_name, view) in schema.views.iter() { + let view_select_sql = format!("SELECT * FROM {view_name}"); + // FIXME: this should rewrite the view to reference the new column name + conn.prepare(view_select_sql.as_str()).map_err(|e| { + LimboError::ParseError(format!( + "cannot rename column \"{}\": referenced in VIEW {view_name}: {}", + old_column_name, view.sql, + )) + })?; + } + } + state.pc += 1; Ok(InsnFunctionStepResult::Step) }