【发布时间】:2017-03-29 02:37:48
【问题描述】:
在F# best way to set up a SQLCommand with parameters
为构造 SQLCommand 输入参数提供了一些非常简洁的解决方案。现在我需要做一些输出参数来调用一个返回两个输出参数的存储过程。
到目前为止我有:
let cmd = (createSqlCommand query conn)
let pec = (new SqlParameter("@errorCode", SqlDbType.Int))
pec.Direction <- ParameterDirection.Output
ignore (cmd.Parameters.Add(pec))
let pet = new SqlParameter("@errorMessage", SqlDbType.VarChar, 2000)
pet.Direction <- ParameterDirection.Output
ignore (cmd.Parameters.Add(pet))
let rc = cmd.ExecuteNonQuery()
let errorCode = cmd.Parameters.Item("@errorCode").Value.ToString()
let errorText = cmd.Parameters.Item("@errorMessage").Value.ToString()
这行得通,但我觉得它丑陋且过于迫切。如何扩展前面示例中的解决方案(尤其是我现在正在使用的 Tomas)来处理输出参数?所以输入和输出在同一个命令中发出。
所以我尝试了这个:
type Command =
{ Query : string
Timeout : int
Parameters : (string * Parameter) list
OutParameters : Option<(string * OutParameter)> list}
接下来是:
let createSqlCommand cmd connection =
let sql = new SqlCommand(cmd.Query, connection)
sql.CommandTimeout <- cmd.Timeout
for name, par in cmd.Parameters do
let sqlTyp, value =
match par with
| Int n -> SqlDbType.Int, box n
| VarChar s -> SqlDbType.VarChar, box s
| Text s -> SqlDbType.Text, box s
| DateTime dt -> SqlDbType.DateTime, box dt
sql.Parameters.Add(name, sqlTyp).Value <- value
match cmd.OutParameters with
| Some <string * OutParameter> list ->
for name, par in list do
let sqlParameter =
match par with
| OutInt -> new SqlParameter(name, SqlDbType.Int)
| OutVarChar len -> new SqlParameter(name, SqlDbType.VarChar, len)
sqlParameter.Direction <- ParameterDirection.Output
sql.Parameters.Add sqlParameter |> ignore
| _ -> ()
但我无法计算出接近尾声的匹配语法。我试过了:
一些列表 -> 得到了
错误 52 此表达式应具有类型 选项列表,但这里有类型 '一个选项
然后我尝试了:
| Some Option<string * OutParameter> list ->
遇到同样的错误,所以我尝试了:
| Some <string * OutParameter> list ->
得到一个不同的错误:
错误 53 模式中有意外的标识符。预期的中缀运算符, 引用符号或其他标记。
然后尝试:
| Some <(string * OutParameter)> list ->
得到错误:
错误 53 模式中出现意外符号 '('。预期中缀运算符, 引用符号或其他标记。
终于试过了:
| Some (string * OutParameter) list ->
又遇到了第一个错误。
然后,我放弃了。
这里需要什么语法?
想了一个新的:
| Some list : (string * OutParameter) ->
for name, par in list do
但是“for”上的错误
错误 53 类型中存在意外的关键字“for”
新尝试:
我想也许我可以定义一个函数来构建一个期望输出参数的 sql 命令,并且仍然使用第一个 createSqlCommand 函数。我试过这个:
type OutCommand =
{ Query : string
Timeout : int
Parameters : (string * Parameter) list
OutParameters : (string * OutParameter) list
}
let createSqlCommandOut (cmd : OutCommand) connection =
let sql = createSqlCommand {cmd.Query; cmd.Timeout; cmd.Parameters} connection
for name, par in cmd.OutParameters do
let sqlParameter =
match par with
| OutInt -> new SqlParameter(name, SqlDbType.Int)
| OutVarChar len -> new SqlParameter(name, SqlDbType.VarChar, len)
sqlParameter.Direction <- ParameterDirection.Output
sql.Parameters.Add sqlParameter |> ignore
sql
这个想法是抓取传入的参数并将它们发送给原始函数来完成工作。你可能猜到这不起作用。我得到了错误;
错误 53 无效的对象、序列或记录表达式
在新函数中调用 createSqlCommand。这种事情可能吗?我可以使用 OutCommand 记录的成员制作命令记录吗?如果是这样,我该如何进行铸造? (似乎也不是一个上头下垂的人)
【问题讨论】:
标签: f# sqlcommand