我有一些数据存储在txt文件中,格式如下:
aaaa----bbbb
cccc----dddd
...
但是,该文件可能包含一些无效格式的冗余数据,如下所示:
eeee----ffff----
hhhh
...
现在我想将数据导入到PostgreSQL表中,该表有两个文本列,同时忽略无效行。所以我在下面模仿the answer here写了一个函数。
1 create or replace function import_data(in filepath text, out my_count integer) returns integer as
2 $BODY$
3 declare
4 content text;
5 oid integer;
6 it text;
7 begin
8 oid := lo_import(filepath);
9 content := encode(lo_get(oid, 0, 300000000), 'escape');
10
11 content := replace(content, ',', '\,');
12 content := replace(content, '----', ',');
13 content := trim(content, E'\n');
14
15 --begin
16 -- insert into public.mytable select (E'(\'' || regexp_split_to_table(content, E'\n') || E'\')')::public.mytable;
17 --exception when others then
18 --end;
19
20 for it in select('(' || regexp_split_to_table(content, E'\n') || ')')::public.mytable loop
21 begin
22 insert into public.mytable select (it);
23 exception when others then
24 raise notice 'error occurred when importing file: %s', filepath;
25 end;
26 end loop;
27
28 perform lo_unlink(oid);
29
30 get diagnostics my_count = ROW_COUNT;
31 end;
32 $BODY$
33 LANGUAGE plpgsql VOLATILE;
如果我使用从第15行到第18行注释的代码,似乎PostgreSQL可以正确捕获too_many_columns
异常。但是,如果我使用第20行到第26行的代码,PostgreSQL在too_many_columns
发生时无法捕获异常:
=> select import_data('/run/media/test.rec');
ERROR: malformed record literal: "(eeee,ffff,)"
DETAIL: Too many columns.
CONTEXT: PL/pgSQL function import_data(text) line 20 at FOR over SELECT rows
我使用第20行到第26行的代码的原因是我希望在保留在数据库中之前插入记录,但不按说明here回滚:
当EXCEPTION子句捕获到错误时,PL / pgSQL函数的局部变量保持与发生错误时相同,但会回滚块中持久数据库状态的所有更改。
第一个问题是如何正确忽略异常?
第二个问题是为什么PostgreSQL中存在too_many_columns
错误,但是没有too_few_columns
错误?