前提
我最近遇到了代码中select
语句中的错误。在我意识到发生了什么之后修复它是相当微不足道的,但我有兴趣找到一种方法来确保类似的错误不再发生。
以下是违规查询的示例:
select
the,
quick,
brown
fox,
jumped,
over,
the,
lazy,
dog
from table_name;
我的意图是:
select
the,
quick,
brown,
fox,
jumped,
over,
the,
lazy,
dog
from table_name;
对于那些看不到它的人,前者brown
后会丢失一个逗号。这会导致列具有别名,因为as
关键字不是必需的。那么,你得到的结果是:
the,
quick,
fox,
jumped,
over,
the,
lazy,
dog
...在名为brown
的列中包含fox
的所有值。对于像上面这样的简短查询,这很容易被注意到(特别是当每个列具有非常不同的值时),但它出现在一个相当复杂的查询中,其中大部分是整数列,如下所示:
select
foo,
bar,
baz,
another_table.quux,
a1,
a2,
a3,
a4,
a5,
a6,
a7,
a8,
a9,
a10,
a11,
a12,
a13,
a14,
a15,
a16,
b1,
b2,
b3,
b7,
b8,
b9,
b10,
b11,
b12,
b13,
b14,
b18,
b19,
b20,
b21,
c1,
c2,
c3,
c4,
c5,
c6,
c7,
c8
from table_name
join another_table on table_name.foo_id = another_table.id
where
blah = 'blargh'
-- many other things here
;
即使列名更好,值也非常相似。如果我在b11
之后错过了一个逗号(例如),然后所有b11
值都被称为b12
,那么当我们通过我们的处理管道运行数据时,这是非常不幸的取决于结果中的这些列名称。通常情况下,我会做select * from table_name
,但我们需要的是要比我们更具选择性。
问题
我正在寻找的是一种阻止这种情况再次发生的策略。
在别名列时是否有办法要求as
?或者写东西以使其产生错误的伎俩? (例如,在类C语言中,我开始编写1 == foo
而不是foo == 1
,以便在我意外遗漏等号时导致编译错误,使其成为无效1 = foo
而不是foo = 1
。)
我正常使用vim
,因此我可以使用hlsearch
突出显示逗号,以便我可以对其进行观察。但是,我必须经常在其他环境中编写查询,包括一个专有的界面,我不能轻易地做这样的事情。
感谢您的帮助!
答案 0 :(得分:6)
我之前做过的一件事就是将逗号移到行尾。这可以带来一些好处。首先,您可以立即查看是否有任何逗号丢失。其次,您可以在最后添加新列,而无需修改之前的最后一行。
缺失:
select
the
, quick
, brown
fox
, jumped
, over
, the
, lazy
, dog
from table_name;
不缺:
select
the
, quick
, brown
, fox
, jumped
, over
, the
, lazy
, dog
from table_name;
答案 1 :(得分:1)
您可以将SQL调用包装在以下函数中:
或
答案 2 :(得分:1)
我遇到了同样的问题。我已经使用make和perl脚本做了一个“lint”,比如检查我的代码很长一段时间。它有助于防止这样的一些错误。 在makefile中我有:
lint_code:
perl lint_code.pl <file_1.php
perl文件是:
$st = 0;
$line_no = 0;
while (<>)
{
$line_no++;
$st = 1 if ( /start-sql/ );
$st = 0 if ( /end-sql/ );
$st = 2 if ( $st == 1 && /select/ );
$st = 3 if ( $st == 2 && /from/ );
if ( $st == 2 && /^[ \t]+[a-zA-Z][a-zA-Z0-9]*[ \t*]$/ )
{
if ( ! /select/ )
{
printf ( "Possible Error: Line: $line_no\n" );
}
}
}
我用select // start-sql和// end-sql包含我的select语句。我希望这有帮助。 我已经更改了正则表达式,以反映您如何格式化SQL 使用不同的格式(前面有逗号)。
作为构建/测试过程的一部分,我对代码进行了一系列检查。这是一个不到 完美的解决方案,但它帮助了我。
(我在使用stackoverflow富文本编辑器改变我的代码时遇到了一些困难。 希望我能学会如何正确使用它。)
答案 3 :(得分:0)
在名称
之前写一个逗号first
,short
,medium
,longlonglong
,...
VS
first,
short,
medium,
longlonglong,
...
也可以很容易地看到sql select参数列表
适用于任何IDE:)
答案 4 :(得分:-1)
如果您的列名相似,只能用后缀编号区分,那么您已经输了。你的数据库设计很糟糕。
现在大多数现代开发人员都使用SQL生成器或ORM,而不是编写这种“汇编语言”SQL。