从 Dapper QueryAsync 接收空值返回游标
Receiving null values from Dapper QueryAsync returned cursor
我的一个小巧的调用 return 将游标与所有列数据设为 null
。
时遇到问题
我们有几个看起来与这个相同的调用,return 提供的模型列表。我仍在熟悉 C#、.Net 和 Dapper,因此可能缺少一些简单的东西。
我们的 SQL 存储过程需要:
Procedure ListItemGrid(pUserId in number,
pListType in varchar2,
pSearchTerm in varchar2,
pId in varchar2,
pOut out sys_refcursor
)
Dapper 电话:
public async Task<List<ListItem>> ListItemGrid(string id, string listType = null, string searchTerm = null)
{
using (var conn = this.GetConnection())
{
var p = new OracleDynamicParameters();
p.Add("pUserId", value: this.userResolverService.UserId, dbType: OracleDbType.Double, direction: ParameterDirection.Input);
p.Add("pListType", value: listType, dbType: OracleDbType.Varchar2, size: 4000, direction: ParameterDirection.Input);
p.Add("pSearchTerm", value: searchTerm, dbType: OracleDbType.Varchar2, size: 4000, direction: ParameterDirection.Input);
p.Add("pId", value: id, dbType: OracleDbType.Varchar2, size: 4000, direction: ParameterDirection.Input);
p.AddCursor("pOut");
var itemList = await conn.QueryAsync<ListItem>("SQL_PKG.ListItemGrid", param: p, commandType: CommandType.StoredProcedure);
return itemList.AsList();
}
}
其中 SQL_PKG.ListItemGrid
return 是与 ListItem
模型相同形状的光标:
using System;
using Proj.Name.Infrastructure.DataAccess;
namespace Proj.Name.Models
{
public class ListItem
{
[Column("name")]
public string name { get; set; }
[Column("other_column")]
public string other { get; set; }
[Column("third_column")]
public string third { get; set; }
...
}
}
预期: ListItem
的列表,其中包含我们数据库中的值。
[
{
key: "string value",
keyTwo: "other string value",
...
},
{ ... },
{ ... }
]
实际: ListItem
的列表,长度正确,键来自 ListItem
但每个值 null
。
[
{
key: null,
keyTwo: null,
...
},
{ ... },
{ ... }
]
为什么我得到的所有值都是 null
?
经过反复试验,改变:
using System;
using Proj.Name.Infrastructure.DataAccess;
namespace Proj.Name.Models
{
public class ListItem
{
[Column("name")]
public string name { get; set; }
[Column("other_column")]
public string other { get; set; }
[Column("third_column")]
public string third { get; set; }
...
}
}
到大写:
using System;
using Proj.Name.Infrastructure.DataAccess;
namespace Proj.Name.Models
{
public class ListItem
{
[Column("NAME")]
public string name { get; set; }
[Column("OTHER_COLUMN")]
public string other { get; set; }
[Column("THIRD_COLUMN")]
public string third { get; set; }
...
}
}
解决了我的问题。
这仍然令人困惑,因为我们的其他 models/dapper 调用正在运行并且是小写的。 如果有人知道为什么这是不一致的,请告诉我。
更新: 我没有意识到 Column
是由我们编写的函数提供的,并且是以不区分大小写的方式编写的。
让我从引用 this 文章开始:
The SQL:2008 and SQL-99 standards define databases to be case
insensitive for identifiers unless they are quoted. Lower case
characters may be used in identifiers and keywords, but are considered
to be their upper case counterparts.
我看到您正在使用 Oracle 数据库。 Oracle 符合上述标准。我看不到您的存储过程定义,但是如果您的存储过程是在字段名称周围用双引号定义的,那么它们将被视为 case-sensitive/uppercase。很可能是这样。
因此,您自己将列名称大写的解决方案确实有意义。
我的一个小巧的调用 return 将游标与所有列数据设为 null
。
我们有几个看起来与这个相同的调用,return 提供的模型列表。我仍在熟悉 C#、.Net 和 Dapper,因此可能缺少一些简单的东西。
我们的 SQL 存储过程需要:
Procedure ListItemGrid(pUserId in number,
pListType in varchar2,
pSearchTerm in varchar2,
pId in varchar2,
pOut out sys_refcursor
)
Dapper 电话:
public async Task<List<ListItem>> ListItemGrid(string id, string listType = null, string searchTerm = null)
{
using (var conn = this.GetConnection())
{
var p = new OracleDynamicParameters();
p.Add("pUserId", value: this.userResolverService.UserId, dbType: OracleDbType.Double, direction: ParameterDirection.Input);
p.Add("pListType", value: listType, dbType: OracleDbType.Varchar2, size: 4000, direction: ParameterDirection.Input);
p.Add("pSearchTerm", value: searchTerm, dbType: OracleDbType.Varchar2, size: 4000, direction: ParameterDirection.Input);
p.Add("pId", value: id, dbType: OracleDbType.Varchar2, size: 4000, direction: ParameterDirection.Input);
p.AddCursor("pOut");
var itemList = await conn.QueryAsync<ListItem>("SQL_PKG.ListItemGrid", param: p, commandType: CommandType.StoredProcedure);
return itemList.AsList();
}
}
其中 SQL_PKG.ListItemGrid
return 是与 ListItem
模型相同形状的光标:
using System;
using Proj.Name.Infrastructure.DataAccess;
namespace Proj.Name.Models
{
public class ListItem
{
[Column("name")]
public string name { get; set; }
[Column("other_column")]
public string other { get; set; }
[Column("third_column")]
public string third { get; set; }
...
}
}
预期: ListItem
的列表,其中包含我们数据库中的值。
[
{
key: "string value",
keyTwo: "other string value",
...
},
{ ... },
{ ... }
]
实际: ListItem
的列表,长度正确,键来自 ListItem
但每个值 null
。
[
{
key: null,
keyTwo: null,
...
},
{ ... },
{ ... }
]
为什么我得到的所有值都是 null
?
经过反复试验,改变:
using System;
using Proj.Name.Infrastructure.DataAccess;
namespace Proj.Name.Models
{
public class ListItem
{
[Column("name")]
public string name { get; set; }
[Column("other_column")]
public string other { get; set; }
[Column("third_column")]
public string third { get; set; }
...
}
}
到大写:
using System;
using Proj.Name.Infrastructure.DataAccess;
namespace Proj.Name.Models
{
public class ListItem
{
[Column("NAME")]
public string name { get; set; }
[Column("OTHER_COLUMN")]
public string other { get; set; }
[Column("THIRD_COLUMN")]
public string third { get; set; }
...
}
}
解决了我的问题。
这仍然令人困惑,因为我们的其他 models/dapper 调用正在运行并且是小写的。 如果有人知道为什么这是不一致的,请告诉我。
更新: 我没有意识到 Column
是由我们编写的函数提供的,并且是以不区分大小写的方式编写的。
让我从引用 this 文章开始:
The SQL:2008 and SQL-99 standards define databases to be case insensitive for identifiers unless they are quoted. Lower case characters may be used in identifiers and keywords, but are considered to be their upper case counterparts.
我看到您正在使用 Oracle 数据库。 Oracle 符合上述标准。我看不到您的存储过程定义,但是如果您的存储过程是在字段名称周围用双引号定义的,那么它们将被视为 case-sensitive/uppercase。很可能是这样。
因此,您自己将列名称大写的解决方案确实有意义。