Npgsql поддерживает разбор System.Net.NetworkInformation.PhysicalAddress
и System.Net.IPAddress
из результата запроса наборов типа MacAddr и инет соответственно. Например, следующий класс может быть заполнен с использованием Npgsql с Dapper:Щеголеватый IPAddress/PhysicalAddress/ENUM Параметр Поддержка над Npgsql v3
-- Postgres CREATE TABLE command
CREATE TABLE foo (
ipaddress inet,
macaddress macaddr
);
// C# class for type "foo"
public class foo
{
public IPAddress ipaddress { get; set; }
public PhysicalAddress macaddress { get; set; }
}
// Code that loads all data from table "foo"
IDbConnection connection = new NpgsqlConnection(connectionString);
var foos = connection.Query<foo>("SELECT * FROM foo");
Поскольку Npgsql v3.0.1 посылает данные в двоичной форме, я полагаю, это означает, что есть некоторое бинарное представление для типов инет и macaddr. Тем не менее, когда я запускаю следующий код, используя одни и те же объявления выше ...
// Code that tries to load a specific row from "foo"
var query = "SELECT * FROM foo WHERE macaddress = :macAddress";
var queryParams = new DynamicParameters();
queryParams.Add("macAddress", PhysicalAddress.Parse("FF-FF-FF-FF-FF-FF"));
IDbConnection connection = new NpgsqlConnection(connectionString);
var foos = connection.Query<foo>(query, queryParams);
я получаю исключение:
Проблема с запросом: SELECT * FROM обув WHERE MacAddress =: MACADDRESS
системы .NotSupportedException: член MACADDRESS типа System.Net.NetworkInformation.PhysicalAddress не может быть использован в качестве значения параметра
Как это, что Чудной/Npgsql знает, как разобрать IPAddress
и PhysicalAddress
из столбца типа inet и macaddr, соответственно, я не могу использовать эти типы в качестве параметров? В предыдущих версиях Npgsql, я просто послал ToString()
результат в качестве значения параметра, но в Npgsql v3.0.1 следующий код ...
// Code that tries to load a specific row from "foo"
// The only change from above is the "ToString()" method called on PhysicalAddress
var query = "SELECT * FROM foo WHERE macaddress = :macAddress";
var queryParams = new DynamicParameters();
queryParams.Add("macAddress", PhysicalAddress.Parse("FF-FF-FF-FF-FF-FF").ToString());
IDbConnection connection = new NpgsqlConnection(connectionString);
var foos = connection.Query<foo>(query, queryParams);
Генерирует исключение:
Проблема с запросом: SELECT * FROM обув WHERE MacAddress =: MACADDRESS
Npgsql.NpgsqlException: 42883: оператор не существует: MacAddr = текст
Я знаю, что я мог бы изменить запрос, чтобы быть «SELECT * FROM foo WHERE macaddress =: macAddress :: macaddr "вместо этого, но мне интересно, есть ли более чистый способ сделать это? Есть ли какой-нибудь план для поддержки поддержки этих типов в ближайшем будущем?
- НАЧАТЬ EDIT -
Я просто понял, что та же самая проблема преследующих перечисленных типов. Если у меня есть параметр перечисления, я могу проанализировать его из результата запроса, но я не могу передать перечисление в Postgres.Например:
CREATE TYPE bar AS ENUM (
val1,
val2
);
CREATE TABLE log (
mybar bar
);
public enum bar
{
val1,
val2
}
public class log
{
public bar mybar { get; set; }
}
// Code that loads all data from table "log"
NpgsqlConnection.RegisterEnumGlobally<bar>();
IDbConnection connection = new NpgsqlConnection(connectionString);
var logs = connection.Query<log>("SELECT * FROM log");
// Code that attempts to get rows from log with a specific enum
var query = "SELECT * FROM log WHERE mybar = :barParam";
var queryParams = new DynamicParameters();
queryParams.Add("barParam", bar.val1);
// The following throws an exception
logs = connection.Query<log>(query, queryParams);
В выше, все работает до последней строки, которая бросает следующее исключение:
42883: оператор не существует: бар = целое число
Если вместо этого я схожу на запрос:
SELECT * FROM log WHERE mybar = :barParam::bar
Тогда я получаю исключение:
42846: не может бросить тип целое запретить
Единственный способ, которым я могу получить перечисленные значения, передаваемые в качестве параметров, чтобы передать их в качестве текст и отливать параметр в запросе, следующим образом:
// Code that successfully performs the query
var query = "SELECT * FROM log WHERE mybar = :barParam::bar";
var queryParams = new DynamicParameters();
queryParams.Add("barParam", bar.val1.ToString());
logs = connection.Query<log>(query, queryParams);
Конечно есть лучший способ пойти об этом. Может ли кто-нибудь пролить свет на то, что это?
можете ли вы пометить вопрос как ответ? –
Я отметил это как ответил вчера. Разве это не появляется как таковое? –
Все хорошо, спасибо! –