gpt4 book ai didi

c# - C# Npgsql 传递的复合类型数组作为存储过程输入

转载 作者:行者123 更新时间:2023-11-29 12:24:57 24 4
gpt4 key购买 nike

我已经阅读了几个与该问题相关的问题和主题,但它们都没有真正帮助我解决我的问题,而且它们实际上都与 C# 无关。这是实际问题:

我有一个 Postgre 复合类型:

CREATE TYPE law_relation_update_model AS (
from_celex character varying,
from_article character varying,
to_celex character varying,
to_article character varying,
link_ids integer[],
to_doc_par_id integer
);

我有一个存储过程,用于接受以下类型的数组:

CREATE OR REPLACE FUNCTION insert_law_relations(_items law_relation_update_model[])
RETURNS VOID
AS
$$
BEGIN

END;
$$
LANGUAGE PLPGSQL;

我删除了主体代码,因为它不相关,因为在从 C# 调用过程时抛出以下错误:

malformed array literal

还有一条内在信息:

array value must start with “{” or dimension information

即将传递的 C# 模型(它的一个数组):

public class LawRelationUpdateModel
{
public string FromCelex { get; set; }

public string FromArticle { get; set; }

public string ToCelex { get; set; }

public string ToArticle { get; set; }

public IEnumerable<int> LinkIds { get; set; } = new List<int>();

public int ToDocParId { get; set; }
}

以及使用 Npgsql 连接器进行调用的方法:

public static void InsertLawRelations(LawRelationUpdateModel[] updateModel)
{
using (NpgsqlConnection conn = new NpgsqlConnection(connPG))
{
conn.Open();
NpgsqlCommand comm = new NpgsqlCommand("insert_law_relations", conn);
comm.CommandType = CommandType.StoredProcedure;
var testParam = new NpgsqlParameter();
testParam.DbType = DbType.Object;
testParam.Value = updateModel;
testParam.ParameterName = "_items";
comm.Parameters.Add(testParam);

comm.ExecuteNonQuery();
}
}

会不会是连接器中的错误,在传递时以某种方式无法正确转换某些单引号/双引号或括号?

或者与我将 DBType 指定为对象这一事实有关的事情?如果我不这样做,则会收到以下错误:

Can't cast LawRelationUpdateModel[] into any valid DbType.

非常感谢有关此问题或其他解决方法的任何帮助!

最佳答案

映射您的 CLR 类型

仍然有可能,并且在某些情况下有必要,为您的 CLR 类型设置显式映射。这样做具有以下优势:

您知道不再需要在参数上指定 DataTypeName 属性。 Npgsql 将从您提供的 CLR 类型推断数据类型。

NpgsqlDataReader.GetValue() 等非类型化读取方法将返回您的 CLR 类型,而不是动态对象(见下文)。一般来说,您应该使用类型化的 NpgsqlDataReader.GetFieldValue(),所以这应该不重要。

您可以在每种类型的基础上自定义名称映射(见下文)。要为所有连接设置全局映射,请在第一次打开之前放置此代码:

 NpgsqlConnection.GlobalTypeMapper.MapEnum<SomeEnum>("some_enum");
NpgsqlConnection.GlobalTypeMapper.MapComposite<SomeType>("some_composite");

This sets up a mapping between your CLR types SomeEnum and SomeType to the PostgreSQL types some_enum and some_composite.

如果您不想为所有连接设置一个映射,您可以只设置一个连接:

var conn = new NpgsqlConnection(...);
conn.TypeMapper.MapEnum<SomeEnum>("some_enum");
conn.TypeMapper.MapComposite<SomeType>("some_composite");

http://www.npgsql.org/doc/types/enums_and_composites.html

关于c# - C# Npgsql 传递的复合类型数组作为存储过程输入,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45329077/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com