使用带有 Dapper 的 TableValuedParameter 将字符串转换为 smalldatetime 失败

Using TableValuedParameter with Dapper Conversion Fails for string to smalldatetime

使用 dapper 将数据表转换为 TableValuedParameter 时出现此错误。我在转换为数据表时是否遗漏了某些内容,DBNull.Value 是否适用于可为空的日期时间?是否存在我在我的代码中没有看到的错误映射 属性?

System.Private.CoreLib: Exception while executing function: MyProject. Core .Net SqlClient Data Provider: Conversion failed when converting character string to smalldatetime data type.

我创建数据列表到数据表

List<PersonData> personDatas = maps.Select( mappedData =>
    new PersonData
    {
        PersonId = mappedData.PersonId,
        StartDate = mappedData.StartDate,
        EndDate = mappedData.EndDate,
        CurrentDate = DateTime.Now,
        SomeString = mapped.SomeStringData
    })
    .ToList()
    .ToDataTable();

Method for ToDataTable can be found here

PersonData 定义为

public class PersonData
{
    public int PersonId { get; set; }
    public DateTime? StartDate { get; set; }
    public DateTime? EndDate { get; set; }
    public string SomeString { get; set; }    
    public DateTime? CurrentDate { get; set; }
}

然后我像这样用 Dapper 执行查询

using (var cn = new SqlConnection(connectionString))
{
    cn.Open();
    //This is where the exception happens
    cn.Execute(RepositorySql.MergeSql(), new
    {
        UserDefinedTable = dataTable.AsTableValuedParameter("[dbo].[PersonData]")       
    });
    cn.Close();
}

Sql 是

MERGE dbo.tblPersonData AS target
USING @UserDefinedTable AS source
ON target.PersonID = source.PersonID
    WHEN MATCHED
    THEN UPDATE SET 
                    StartDate = source.StartDate, 
                    EndDate = source.EndDate,
                    --UpdatedDate instead of InsertedDate
                    UpdatedDate = source.CurrentDate,
                    SomeString = source.SomeString
    WHEN NOT MATCHED BY TARGET
    THEN
        --Inserted date instead of UpdatedDate
        INSERT(PersonID, StartDate, EndDate, InsertedDate, SomeString)
        VALUES
            (source.PersonId, source.StartDate, source.EndDate, source.CurrentDate, source.SomeString)

用户定义 Table 是

CREATE TYPE [dbo].[PersonData] AS TABLE(    
   PersonId int NOT NULL
   ,SomeString varchar(50) null
   ,StartDate smalldatetime null
   ,EndDate smalldatetime null
   ,CurrentDate smalldatetime null)

问题是因为对象的序列化使列的顺序不同于用户定义的顺序Table,所以他们试图将日期保存到字符串列中。我将对象更改为此并且错误已解决,请注意属性的顺序已更改:

public class PersonData
{
    public int PersonId { get; set; }
    public string SomeString { get; set; } 
    public DateTime? StartDate { get; set; }
    public DateTime? EndDate { get; set; }   
    public DateTime? CurrentDate { get; set; }
}