Asp.net 将varchar转换为int:SQL数据类型时,转换失败
我正在asp.net mvc中创建一个web应用程序。我有一个如下所示的查询Asp.net 将varchar转换为int:SQL数据类型时,转换失败,asp.net,sql-server,dapper,dynamicparameters,Asp.net,Sql Server,Dapper,Dynamicparameters,我正在asp.net mvc中创建一个web应用程序。我有一个如下所示的查询 using (SqlConnection conn = new SqlConnection(_connStr)) { conn.Open(); var p = new DynamicParameters(); p.Add("@SP_RoleId", "7,8,9", dbType: DbType.String, direction: ParameterDirection.Input);
using (SqlConnection conn = new SqlConnection(_connStr))
{
conn.Open();
var p = new DynamicParameters();
p.Add("@SP_RoleId", "7,8,9", dbType: DbType.String, direction: ParameterDirection.Input);
p.Add("@SP_UserId", userId, dbType: DbType.Int32, direction: ParameterDirection.Input);
var obj = conn.Query<PendingKmsRequest>(sql: "SELECT [f].[id] AS [FileId],[fvr].[Id] AS [RequestId], [au].[Name]"
+ ", [fvr].[RequestByUserId], [fvr].[FromDate], [fvr].[ToDate],[f].[Title], [fvr].[Status], [fvr].[StatusRemarks]"
+ "FROM [dbo].[File] AS[f]"
+ "INNER JOIN [dbo].[FileViewRequest] AS [fvr] ON [f].[CurrentFileVersionId] = [fvr].[FileVersionId]"
+ "INNER JOIN [Access].[User] AS [au] ON [fvr].[RequestByUserId] = [au].[Id]"
+ "WHERE ([fvr].[Status] = 'P' OR ([fvr].[Status] = 'A' AND [fvr].[StatusByUserId] = @SP_UserId AND GETDATE() BETWEEN [fvr].[FromDate] AND [fvr].[ToDate]))"
+ "AND (SELECT 1 FROM [Access].[UserRoleMap] WHERE UserId=@SP_UserId AND RoleId IN(@SP_RoleId)) = 1", param: p, commandType: CommandType.Text);
if (obj != null && obj.Count() > 0)
return obj.ToList();
else
return new List<PendingKmsRequest>();
}
这就是错误:
将nvarchar值“7,9,10”转换为数据类型int时,转换失败
如何防止此错误?问题代码中的以下行:
p.Add("@SP_RoleId", "7,8,9", dbType: DbType.String, direction: ParameterDirection.Input);
值“7,8,9”
是字符串,参数类型DbType.string
也是字符串
但是,您说过这是数据库中的int
。这是不匹配的
此外,您的查询:
WHERE UserId = @SP_UserId AND RoleId IN (@SP_RoleId))
查询正在使用子句中的
如果传入一个IEnumerable
,Dapper可以转换子句中的值
更改代码行,如下所示:
p.Add("@SP_RoleId", new[] {7,8,9}, dbType: DbType.Int32, direction: ParameterDirection.Input);
无需在数组中使用convert string
或任何字符串split()
函数
如果您有逗号字符串,那么您可以按照以下步骤进行检查
如果您有@SP_RoleId=“7,8,9”
您可以按如下方式转换此字符串
@SP_RoleId=“,7,8,9,”
(”,“+ltrim(rtrim)(@SP_RoleId))+”,“
)
现在使用像
一样检查,UserId,
更新代码如下所示
using (SqlConnection conn = new SqlConnection(_connStr))
{
conn.Open();
var p = new DynamicParameters();
p.Add("@SP_RoleId", "7,8,9", dbType: DbType.String, direction: ParameterDirection.Input);
p.Add("@SP_UserId", userId, dbType: DbType.Int32, direction: ParameterDirection.Input);
var obj = conn.Query<PendingKmsRequest>(sql: "SELECT [f].[id] AS [FileId],[fvr].[Id] AS [RequestId], [au].[Name]"
+ ", [fvr].[RequestByUserId], [fvr].[FromDate], [fvr].[ToDate],[f].[Title], [fvr].[Status], [fvr].[StatusRemarks]"
+ "FROM [dbo].[File] AS[f]"
+ "INNER JOIN [dbo].[FileViewRequest] AS [fvr] ON [f].[CurrentFileVersionId] = [fvr].[FileVersionId]"
+ "INNER JOIN [Access].[User] AS [au] ON [fvr].[RequestByUserId] = [au].[Id]"
+ "WHERE ([fvr].[Status] = 'P' OR ([fvr].[Status] = 'A' AND [fvr].[StatusByUserId] = @SP_UserId AND GETDATE() BETWEEN [fvr].[FromDate] AND [fvr].[ToDate]))"
+ "AND (SELECT 1 FROM [Access].[UserRoleMap] WHERE ',' + lTrim(rTrim(@SP_RoleId)) + ',' like '%,' + lTrim(rTrim(UserId) + ',%' " // Updated line
+ "AND RoleId IN(@SP_RoleId)) = 1", param: p, commandType: CommandType.Text);
if (obj != null && obj.Count() > 0)
return obj.ToList();
else
return new List<PendingKmsRequest>();
}
使用(SqlConnection-conn=newsqlconnection(_-connStr))
{
conn.Open();
var p=新的动态参数();
p、 添加(“@SP_RoleId”,“7,8,9”,dbType:dbType.String,direction:ParameterDirection.Input);
p、 添加(“@SP_UserId”,UserId,dbType:dbType.Int32,direction:ParameterDirection.Input);
var obj=conn.Query(sql:“选择[f].[id]作为[FileId],[fvr].[id]作为[RequestId],[au].[Name]”
+“,[fvr].[RequestByUserId],[fvr].[FromDate],[fvr].[ToDate],[f].[Title],[fvr].[Status],[fvr].[Status备注]”
+“从[dbo].[File]作为[f]”
+“将[dbo].[FileViewRequest]作为[f].[CurrentFileVersionId]=[fvr].[FileVersionId]上的[fvr]进行内部联接”
+“在[fvr].[RequestByUserId]=[au].[Id]上以[au]身份将[Access].[User]作为内部联接”
+“其中([fvr].[Status]='P'或([fvr].[Status]='A'和[fvr].[StatusByUserId]=@SP_UserId和GETDATE(),介于[fvr].[FromDate]和[fvr].[ToDate])”
+“和(从[Access].[UserRoleMap]中选择1,其中','+lTrim(rTrim(@SP_RoleId))+','类似','+lTrim(rTrim(UserId)+',%'”//更新行
+“AND RoleId IN(@SP_RoleId))=1”,参数:p,commandType:commandType.Text);
如果(obj!=null&&obj.Count()>0)
返回obj.ToList();
其他的
返回新列表();
}
列中的RoleID是一个int,但是当您的条件包含逗号“,”时,您的条件是一个字符串,而不是int。请查看解决方案,您使用的是哪个版本的SQL server?SQL server 2008,如果您有“7,8,9”,则我不能使用字符串分割
在@SP_RoleId
中作为字符串,因此无需在数组中转换它。您可以在字符串的开头和结尾添加逗号,并使用像一样检查、用户ID、
ltrim()
和rtrim()
来删除额外的字符串spaces@IbrahimShaikh,答案更新为描述
using (SqlConnection conn = new SqlConnection(_connStr))
{
conn.Open();
var p = new DynamicParameters();
p.Add("@SP_RoleId", "7,8,9", dbType: DbType.String, direction: ParameterDirection.Input);
p.Add("@SP_UserId", userId, dbType: DbType.Int32, direction: ParameterDirection.Input);
var obj = conn.Query<PendingKmsRequest>(sql: "SELECT [f].[id] AS [FileId],[fvr].[Id] AS [RequestId], [au].[Name]"
+ ", [fvr].[RequestByUserId], [fvr].[FromDate], [fvr].[ToDate],[f].[Title], [fvr].[Status], [fvr].[StatusRemarks]"
+ "FROM [dbo].[File] AS[f]"
+ "INNER JOIN [dbo].[FileViewRequest] AS [fvr] ON [f].[CurrentFileVersionId] = [fvr].[FileVersionId]"
+ "INNER JOIN [Access].[User] AS [au] ON [fvr].[RequestByUserId] = [au].[Id]"
+ "WHERE ([fvr].[Status] = 'P' OR ([fvr].[Status] = 'A' AND [fvr].[StatusByUserId] = @SP_UserId AND GETDATE() BETWEEN [fvr].[FromDate] AND [fvr].[ToDate]))"
+ "AND (SELECT 1 FROM [Access].[UserRoleMap] WHERE ',' + lTrim(rTrim(@SP_RoleId)) + ',' like '%,' + lTrim(rTrim(UserId) + ',%' " // Updated line
+ "AND RoleId IN(@SP_RoleId)) = 1", param: p, commandType: CommandType.Text);
if (obj != null && obj.Count() > 0)
return obj.ToList();
else
return new List<PendingKmsRequest>();
}