sql - 从多个表中删除清理脚本 SQL
问题描述
答案在底部,最终发现。感谢所有的贡献。
我必须制作一个脚本,将其制作成一个存储过程,然后每隔几个月运行一次。它需要进入一些特定的表并删除旧记录。我认为这会很简单,但我一直遇到同样的问题。
如果我尝试运行我得到的代码和无效标识符错误,这似乎是日期字段的问题,其中 oracle 默认使用几个月的字母,我尝试了各种日期格式,但我似乎没有工作。
我声明要删除的日期,然后将一个执行立即语句串在一起,该语句将循环遍历包含表名的 tabletoclean 表,以及我将对其进行清理的表的日期字段名称。
错误代码是 ORA-00904:“APR”无效指示符我猜是因为它尝试使用 APR - APRIL 而不是 04。但我不知道。据我所见,没有一个 dtl_fields 使用月份名称日期格式。
Declare
dtldate date := to_date(add_months( to_date(sysdate), -24 ), 'dd-mm-yy');
Begin
for tbl IN (Select * from tbltoclean)
loop
execute immediate 'Delete from '||tbl.tbl_name || ' where ' || tbl.dtl_field ||' < ' || dtldate;
DBMS_OUTPUT.PUT_LINE ('Deleted from '|| to_char(tbl.tbl_name));
end loop;
end;
如果我在 dbms.output 中运行执行立即字符串,我会返回字符串 Select * from mytable where datefield < 30-APR-16
确认问题出在日期格式上。
编辑/回答问题出在 dtldate 变量上。它将日期发布到立即执行,如下所示。
从 mytable 中选择 *,其中 datefield < 30-APR-16
这没有用,但是
从 mytable 中选择 *,其中 datefield < '30-APR-16'
会工作,所以我编辑了以下代码工作的字符串。
Declare
dtldate date := add_months( to_date(sysdate), -24 );
Begin
for tbl IN (Select * from tbltoclean)
loop
execute immediate 'Select null from '||tbl.tbl_name || ' where ' || tbl.dtl_field ||' < ' || 'to_date('''||dtldate||''')'; --dtldate have escaped ''
DBMS_OUTPUT.PUT_LINE ('Deleted from '|| to_char(tbl.tbl_name));
end loop;
end;
解决方案
SYSDATE
是一个返回DATE
数据类型的函数;TO_DATE
再次将其转换为日期(使用 )是没有用的。
所以,这可能会做你想要的:
declare
dtldate date := add_months(trunc(sysdate), -24);
begin
for tbl in (select * from tbltoclean)
loop
execute immediate 'Delete from '||tbl.tbl_name ||
' where ' || tbl.dtl_field ||' < DATE ''' || to_char(dtldate, 'YYYY-MM-DD') || '''';
dbms_output.put_line ('Deleted from '|| to_char(tbl.tbl_name));
end loop;
end;
推荐阅读
- android - 了解如何访问嵌入式安全元素
- javascript - 具有合并真实覆盖对象的firestore集
- go - 在生产者速度慢、消费者速度快的情况下,如何处理通道关闭同步?
- android - Unity Gradle 构建失败。DexException: 多个 dex 文件定义
- c - C 中的 std::array 等效项
- java - 可以转换 ArrayList
到数组列表 ? - c# - 具有 2 种不同类型的 TaskCompleteSource?
- mongodb - 如何在mongodb的所有文档中向子文档数组中添加一个字段?
- c - C:如何从标准输入读取许多字符串
- python - 需要 Python 帮助。将电子表格中的数据收集到可以保存字符串和数字的数组中的最佳方法是什么