有关更新数据库的 ColdFusion 10 文档有一节介绍 ColdFusion 10 中与数据库相关的增强功能。该页面提到现在支持
CF_SQL_NVARCHAR
等,但没有有关它们的详细信息。此外,cfqueryparam 文档尚未更新以包含它们的存在。
cfqueryparam的 ColdFusion 9 文档提到
CF_SQL_VARCHAR
映射到 MSSQL 中的 varchar
。除非 ColdFusion 管理员数据源设置启用了 String Format
设置,否则情况就是如此。在这种情况下,CF_SQL_VARCHAR
映射到nvarchar
。这个记录不足的功能是一种黑客行为,可能会在 ColdFusion 中导致性能问题。
所以很高兴他们推出了
CF_SQL_NVARCHAR
,但最好了解它是如何工作的。它只是 CF_SQL_VARCHAR
的别名,毫无意义?它总是以 nvarchar
的形式发送字符串吗?如果是这样,CF_SQL_VARCHAR
是否总是发送varchar
?
我希望为了向后兼容,它是这样实现的:
如果启用
String Format
,CF_SQL_VARCHAR
和 CF_SQL_NVARCHAR
都会映射到 nvarchar
。
如果禁用
String Format
,则 CF_SQL_VARCHAR
映射到 varchar
,CF_SQL_NVARCHAR
映射到 nvarchar
。
这意味着任何 CF10 之前的站点都可以迁移到 CF10 并工作,并且具有与 CF10 之前相同的性能考虑因素。
新站点或重写所有查询以匹配
CF_SQL_VARCHAR
和 CF_SQL_NVARCHAR
与数据库设计的站点将不会受到 CF10 之前不可避免的性能损失。
任何人都可以确认是否是这种情况吗?如果有官方的东西就更好了?
当您等待更正式的消息时,我将投入 0.02 美元......
我做了一些挖掘,根据我的观察(使用 MS SQL 数据源),我相信:
CF_SQL_NVARCHAR
不仅仅是 CF_SQL_VARCHAR
的别名。它映射到较新的 NVARCHAR jdbc 类型,它使您可以更精细地处理 unicode 值。CF_SQL_NVARCHAR
值始终被视为 nvarchar
CF_SQL_VARCHAR
的处理取决于String Format
设置,与之前的版本相同。 CF_SQL_NVARCHAR 测试/结果:
如果启用数据源日志记录,您可以看到每当使用 setNString
时驱动程序都会调用特殊的
CF_SQL_NVARCHAR
方法。因此最终该值会以 nvarchar
的形式发送到数据库。 (您可以使用 SQL Profiler 确认这一点)
// Query
SELECT ID
FROM Test
WHERE NVarcharColumn = <cfqueryparam value="#form.value#" cfsqltype="cf_sql_nvarchar">
// Log
spy(...)>> PreparedStatement[9].setNString(int parameterIndex, String value)
// Profiler
exec sp_prepexec @p1 output,N'@P1 nvarchar(4000)',N'SELECT ID
FROM Test
WHERE NVarcharColumn = @P1 ',N'Стоял он, дум великих полн'
CF_SQL_VARCHAR 测试/结果:
对于
CF_SQL_VARCHAR
,技术上它被标记为 varchar
。但是,String Format
设置最终控制数据库如何处理它。启用该设置后,将按 nvarchar
处理。当它被禁用时,它被视为 varchar
。同样,您可以使用 SQL Profiler 来验证这一点。
底线,到目前为止我所看到的一切都表明您的实施目标是正确的。
// Query
SELECT ID
FROM Test
WHERE PlainVarcharColumn = <cfqueryparam value="#form.value#" cfsqltype="cf_sql_varchar">
// Log
spy(..)>> PreparedStatement[8].setObject(int parameterIndex, Object x, int targetSqlType)
spy(..)>> parameterIndex = 1
spy(..)>> x = ????? ??, ??? ??????? ????
spy(..)>> targetSqlType = 12 (ie CF_SQL_VARCHAR)
// Profiler (Setting ENABLED)
exec sp_prepexec @p1 output,N'@P1 nvarchar(4000)',N'SELECT ID
FROM Test
WHERE PlainVarcharColumn = @P1 ',N'Стоял он, дум великих полн'
// Profiler (Setting DIS-abled)
exec sp_prepexec @p1 output,N'@P1 varchar(8000)',N'SELECT ID
FROM Test
WHERE PlainVarcharColumn = @P1 ','????? ??, ??? ??????? ????'
遇到此问题的任何人,请尝试将
sendStringParametersAsUnicode=false
添加到 cf 管理员中的数据库连接字符串。