У меня есть несколько столбцов JSONB в моих первых объектах кода EF в проекте EFCore. Я хотел бы настроить некоторые индексы GIN для свойств внутри этих строго типизированных объектов, которые хранятся как свойство/столбец JSONB.
Это возможно? (в настоящее время используется postgres: последнее изображение)
Спасибо.





Не существует специального способа настройки индексов GIN через поставщика Npgsql EF6. Однако вы можете использовать необработанный SQL в своих миграциях, чтобы настроить его вручную.
Однако, как написал @hellokitty5685 в другом ответе, это возможно в EF Core.
Я не уверен, что именно вы имеете в виду - вам придется самостоятельно создать миграцию и вручную написать SQL для добавления индекса. Кстати, обратите внимание, что поставщик EF Core поддерживает указание индексов GIN: npgsql.org/efcore/моделирование/indexes.html.
Смотрел на страницу, на которую вы ссылались (снова). Мне интересно, нельзя ли один раз написать собственный оператор в БД, а затем использовать ForNpgsqlHasOperators для покрытия любого количества полей JSONB с нормальными индексами в EF. В этом примере подход к индексу GiST записывается с оператором Create... Возможно, я рассмотрю возможность сделать это с вариантом GIN: postgresql.org/docs/9.3/sql-createopclass.html. Еще раз спасибо.
Я не думаю, что вы сможете создать индекс GIN без CREATE INDEX ... USING gin... Но я не большой эксперт в этом.
ну на самом деле можно так
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Artist>()
.HasIndex(a => new { a.Album })
.ForNpgsqlHasMethod("gin");
base.OnModelCreating(modelBuilder);
}
и когда вы запустите ef add migration, сгенерированный запрос sql будет выглядеть так:
СОЗДАЙТЕ ИНДЕКС ix_artist_album ДЛЯ исполнителя, ИСПОЛЬЗУЮЩЕГО gin ("альбом");
Документация в Npgsql: http://www.npgsql.org/efcore/modeling/indexes.html
По какой-то причине я подумал, что видел в исходном посте Entity Framework 6, а не Entity Framework Core...
Поскольку .ForNpgsqlHasMethod("gin") устарел, с EF Core 3.1 вы можете использовать это:
metaBuilder
.HasIndex(x => x.DocumentNumber)
.HasMethod("gin")
.HasOperators("gin_trgm_ops");
и ваша миграция будет выглядеть так:
migrationBuilder.CreateIndex(
name: "IX_DocumentContentMeta_DocumentNumber",
table: "DocumentContentMeta",
column: "DocumentNumber")
.Annotation("Npgsql:IndexMethod", "gin")
.Annotation("Npgsql:IndexOperators", new[] { "gin_trgm_ops" });
Есть ли что-нибудь еще, что вам нужно сделать с базой данных postgres, чтобы включить поддержку? Я получаю исключение: '42704: operator class "gin_trgm_ops" does not exist for access method "gin". Требуется ли для работы определенная версия Postgresql?
@nikib3ro да, попробуйте выполнить CREATE EXTENSION pg_trgm; в своей базе данных
TL&DR: Вам необходимо ВКЛЮЧИТЬ функцию триграммы в вашей базе данных, после чего вы сможете включить функцию триграммы. Важно отметить, что если вы НЕ включите функцию триграммы в своей базе данных, вы НЕ сможете использовать эту функцию.
Шаг 1: Создайте индекс
modelBuilder.Entity<MyAwesomeModel>()
.HasIndex(f => f.stringToTriGram)
.HasMethod("gin")
.HasOperators("gin_trgm_ops");
Шаг 2: Включите TrigramExtension
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.HasPostgresExtension("pg_trgm");
}
Спасибо, боялся. В таком случае я немедленно думаю о создании пользовательского атрибута, содержащего информацию об индексе GIN для свойства, к которому он будет применяться. Знаете ли вы, существует ли шаблон для управления изменениями схемы вручную из проекта службы?