如何解决PHP odbc_执行参数需要单引号进行日期时间转换的问题?
为了安全起见,我尝试转换一些代码,使用PHP的odbc_prepare和odbc_execute,使用参数将数据插入SQL Server表中,但由于PHP处理参数中单引号的方式以及SQL Server需要将文本转换为datetime的单引号,我无法克服错误 我有一个web表单,它接受来自用户的日期时间和其他数据。如何解决PHP odbc_执行参数需要单引号进行日期时间转换的问题?,php,sql-server,Php,Sql Server,为了安全起见,我尝试转换一些代码,使用PHP的odbc_prepare和odbc_execute,使用参数将数据插入SQL Server表中,但由于PHP处理参数中单引号的方式以及SQL Server需要将文本转换为datetime的单引号,我无法克服错误 我有一个web表单,它接受来自用户的日期时间和其他数据。 日期时间输入框(下面的missdt)的输出格式为YY-MM-DDTHH:MM:SS(例如2019-10-09T10:14:00) 这是我的代码(这篇文章的简称,是的,我用我的真实代码清
日期时间输入框(下面的missdt)的输出格式为YY-MM-DDTHH:MM:SS(例如2019-10-09T10:14:00) 这是我的代码(这篇文章的简称,是的,我用我的真实代码清理帖子数据): 问题是$missdt参数导致SQL错误“cast规范的字符值无效” 我在$params数组中尝试了$missdt的以下变体,并收到了指示的错误: “'”$密斯特。“'”,/(添加引号)PHP错误无法打开文件 “'”$密斯特。“'”,/(添加了引号和空格)PHP错误无法打开文件 “'”$密斯特。“'”,//(空格后)SQL错误转换规范的无效字符值 “.$missdt.”,//(双引号与set quoted_identifier off一起使用)导致“无效参数号”和“odbc_execute()期望参数1为资源” sql查询的这种变体工作正常,但可能被滥用: $sql=“在my_表(分支、已提交、未命中日期、名称)中插入值(?,getdate(),“$missdt',?)” 根据PHP文档,在参数前后使用单引号会导致参数被视为文件名,解决方法是在参数的开头或结尾添加空格。你可以从我在上面尝试过的变体中看出,在这种情况下不起作用。我认为这是因为SQLServer需要引号才能将字符数据转换为datetime 有什么办法可以解决这个问题吗
我在Windows 2012上使用PHP7.1、SQLServer2014和Apache,所以结果证明问题不是由单引号引起的。它是日期时间输入中的“T”。如果我使用str_replace并用空格替换T,那么使用不带引号的参数的sql将正常工作 例如: $missdt=str_replace('T','',$_POST[“missdt”]) 然后 $sql=“插入我的表格(分支机构、已提交、未命中日期、名称) 值(?,getdate(),?,?)”
效果很好。因此,问题不是由单引号引起的。它是日期时间输入中的“T”。如果我使用str_replace并用空格替换T,那么使用不带引号的参数的sql将正常工作 例如: $missdt=str_replace('T','',$_POST[“missdt”]) 然后 $sql=“插入我的表格(分支机构、已提交、未命中日期、名称) 值(?,getdate(),?,?)”
工作正常。我已经有一段时间没有在php下使用SQL server或ODBC了。IIRC,只要数据格式正确,就不需要任何引号,但这是FreeTDS驱动程序提供的。显然,MS驱动程序有一些选项,如
returndatesassstrings
,您可能需要查看这些选项。我已经有一段时间没有在php下使用SQL server或ODBC了。IIRC,只要数据格式正确,就不需要任何引号,但这是FreeTDS驱动程序提供的。显然,MS驱动程序有一些选项,如returndatesassstrings
,您可能需要查看这些选项。
$missdt = $_POST["missdt"]; // results in 2019-10-09T10:14:00 stored as datetime in SQL Server
$branch = intval($_POST["branch"]); // stored as integer in SQL Server
$name = $_POST["name"]; // stored as varchar in SQL Server
$params = array($branch,
$missdt, // results in SQL error “Invalid character value for cast specification”
$name, );
$sql = "insert into my_table (branch, submitted, miss_date, name)
values (?, getdate(), ?, ?) ";
$res = odbc_prepare($conn, $sql);
$stmt = odbc_execute($res, $params);