存储过程参数名称和实体框架
Posted
技术标签:
【中文标题】存储过程参数名称和实体框架【英文标题】:Stored procedure parameter names and Entity Framework 【发布时间】:2011-04-29 14:10:07 【问题描述】:我已从 SQL Server 2005 数据库生成实体框架模型并开始导入存储过程。到目前为止一切顺利,但是当我尝试运行其中一个存储过程时会引发异常:
过程或函数“csp_getCoworker”需要参数“@@firstname”,但未提供。
这是存储过程的签名:
ALTER PROCEDURE [dbo].[csp_getCoworker](
@@firstname nvarchar(32),
@@lastname nvarchar(32),
@@businessarea nvarchar(512),
@@location nvarchar(512)
)
这里是实体框架生成的代码
ObjectParameter p_firstnameParameter;
if (p_firstname != null)
p_firstnameParameter = new ObjectParameter("p_firstname", p_firstname);
else
p_firstnameParameter = new ObjectParameter("p_firstname", typeof(global::System.String));
[...]
return base.ExecuteFunction<csp_getCoworker_Result2>("csp_getCoworker", p_firstnameParameter, p_lastnameParameter, p_businessareaParameter, p_locationParameter);
是不是参数名称中的双 @ 字符搞砸了?
【问题讨论】:
【参考方案1】:我刚刚对此进行了测试,因为这是非常罕见的情况。
存储过程遵循非常奇怪的命名约定,因为不应使用@@。默认情况下,某些 SQL Server 系统变量使用它,不应将其用于其他任何东西。使用@x
作为存储过程的参数定义了一个参数x
,但使用@@x
将定义参数@x
- @ 是参数名称的一部分!
这在 C# 中是一个非常大的问题,因为 @ 是用于定义与保留关键字相同的变量名称的转义字符。例如:
string @string = "abc";
定义名为string
的变量。变量名不能以@开头。
实体框架通过将所有@
替换为_
并在SSDL 中直接在参数名称前加上p
来处理此问题。原因是从 SSDL 映射存储过程创建的函数导入必须具有与过程同名的参数,但同时不允许使用 @ 开头字符。如果您尝试手动修改 EDMX,它将无法通过自己的 XSD 验证,因为 @ 不允许作为 CSDL 中定义的标识符的起始字符。
即使这也可能被视为一个错误,它更多的是关于缺少更改 CSDL 中参数名称的可能性。目前这是设计使然,唯一的方法是更正 SQL 存储过程中的参数名称。
【讨论】:
这是一个很好的答案!它让我朝着正确的方向前进,我通过编写包装程序来解决这个问题,其中包含正确命名的变量,这些变量只是将它们传递给适当的 SP。 @Bartek:你应该做的是找到认为在参数名称中使用双@-标记是个好主意的人,打他们的脸,然后然后让他们修复它。 @Matti:我试过了,但他们早就离开了组织。 >:(以上是关于存储过程参数名称和实体框架的主要内容,如果未能解决你的问题,请参考以下文章
更新存储过程实体框架抛出“验证FunctionImport名称是唯一的”错误
如何在 c# 实体框架核心中使用 FromSqlRaw() 将 OUTPUT 参数发送到 MySql 存储过程