我试图了解以下我必须更新的Coldfusion / MySQL查询中发生的情况(而且我正在CF / MySQL的第一个月中)。
我在搜索之前运行了一个查询,该查询将变量pl(pricelists)设置如下:
<cfif variables.module IS "yes">
<cfquery datasource="ds" name="qp">
<!--- selects pricelist and seller --->
</cfquery>
<cfset variables.pl = "LEFT JOIN pricelist p ON ">
<cfoutput query="qp" >
<cfif qp.preislist IS ''>
<cfset variables.pl= variables.pl & '(p.iln = a.iln AND p.preislist = "AAA" AND p.ean = a.ean AND p.iln = "#qp.seller#") OR '>
<cfelse>
<cfset variables.pl= variables.pl & '(p.iln = a.iln AND p.preisliste = "#qp.preislist#" AND p.ean = a.ean AND p.iln = "#qp.seller#") OR '>
</cfif>
</cfoutput>
<cfset variables.pl = variables.preislisten & "(1=0)">
</cfif>
然后将其“移植”到搜索查询中,使我感到困惑,如下所示:
<cfquery datasource="ds" name="getArt">
SELECT a.* <cfif variables.module IS "yes">, p.ek, p.vk, p.waehrung, p.onlinepreis</cfif>
FROM artdata a
<cfif variables.module IS "yes">
<cfqueryparam cfsqltype="cfsql_varchar" value="#variables.pl#">
</cfif>
....
很多问题:
-不需要cfparam查询字段,例如qp.seller,还是存在?
-我不应该总是像在artdata AS中那样总是使用ALIAS而不是仅在artdata AS中使用ALIAS吗?
-我可以选择p.ek,p.vk等吗,尽管以后只会通过变量variable.pl声明价格表(即LEFT JOIN价格表p ON ...)
-(1 = 0)怎么了?目的是什么? (3 = 2),(1 = 2)的Dito。
感谢您的启发!
最佳答案
不需要cfparam查询字段(例如qp.seller),还是存在?
它不是cfparam,而是cfqueryparam-这是两个执行不同任务的不同标签。
使用cfqueryparam的主要原因有两个:
1)为了安全-如果输入最初可能来自任何第三方,或者如果您不能保证输入是已知值,请使用cfqueryparam来确保不会发生SQL代码注入(有意或无意)。
2)为了提高性能-查询参数会生成一个执行计划,该计划可以缓存并应用于多个查询(即参数不同的地方),因此通常可以提高性能。
如果qp.seller是可以保证安全的数字外键,则您不需要它的安全性,但是从性能方面来说,它仍然可能会带来有益的影响。
通常,如有疑问,请使用它。
(偶尔会有人声称这样做会导致执行计划不佳,从而导致性能下降,但是我对这些主张持谨慎态度,在任何情况下都必须根据具体情况进行处理-安全性很重要)
我是否应该始终像在artdata AS中那样始终使用ALIAS,而不是仅在artdata AS中使用ALIAS?
如果您想输入更多。 :)
表名称与AS关键字没有区别/好处。
我可以选择p.ek,p.vk等吗
是的,那可以。
可能希望将它们放在多行上,以使其更具可读性。
尽管价目表仅稍后会通过变量> variables.pl声明(即LEFT JOIN价格表p ON ...)
这是一个错误的假设。
特别是使用cfqueryparam可以防止注入SQL代码,这就是您要在此处进行的操作。
而不是创建variables.pl,应该将生成的SQL直接输出到将要使用它的cfquery标记中。
(如果您不确定我的意思,我可以为此举一个例子吗?)
(1 = 0)怎么了?它的目的是什么? (3 = 2),(1 = 2)的Dito。
正如Romain的评论所解释的那样,这是一种错误的常见说法,当您进行动态查询时会用到。括号是可选的。
但是,更常见的是将其放在开头-即WHERE 1=0
或JOIN 1=0
-然后让动态语句从OR ...
开始。