Как выбрать только определенные столбцы при использовании предварительной выборки в DBIx-Class?

Я борюсь с довольно фундаментальным использованием предварительной выборки DBIx-Class. Я хочу ограничить количество столбцов, возвращаемых из объединенных таблиц при использовании предварительной выборки.

Этот:

my $rs = $schema->resultset('CD')->search(
  {}, # No searching restrictions through WHERE clause
  {
    prefetch => [qw/ artist /],
    columns  => [qw/ title artist.name /],
  }
);

Генерирует этот SQL:

SELECT cd.title, artist.*
FROM cd
JOIN artist ON cd.artist = artist.id

Но я не хочу вытаскивать все столбцы исполнителя, только столбцы cd.title и artist.name (в этом примере мой реальный вариант использования более сложен). Функция столбцов работает только с основной таблицей, а не с объединенными таблицами.

Я хотел бы этот SQL:

SELECT cd.title, artist.name
FROM cd
JOIN artist ON cd.artist = artist.id

Я только осваиваю Catalyst/DBIX-Class, так что, вероятно, я упускаю из виду что-то ослепительно очевидное!


person Sparky    schedule 05.11.2013    source источник


Ответы (3)


Да, ты прав. Вы можете выбирать только столбцы в основной таблице и не можете получать определенные столбцы в объединенных таблицах. Что вам нужно, так это присоединиться. используйте свойство join и '+select','+as', вы можете выбрать специальные столбцы из двух таблиц.

Предварительная выборка также используется для выбора всех столбцов из таблиц предварительной выборки. Более эффективно использовать предварительную выборку, когда вам действительно нужны эти столбцы, например. так что вы можете сделать $cd->artist->name без необходимости выполнять дополнительный запрос. Но если вам не нужны эти столбцы, у вас будет ненужный удар по производительности для загрузки этих данных.

person JackXu    schedule 05.11.2013
comment
Спасибо, Джек. Моя ситуация такова, что без предварительной выборки я генерирую около 100 отдельных операторов SELECT. С предварительной выборкой я генерирую один запрос, но он возвращает гораздо больше данных, чем мне нужно, когда я перебираю строки. Каков правильный (DBIx) способ ограничения выбранных столбцов (в нескольких таблицах), которые извлекаются оператором SELECT, сгенерированным набором результатов? - person Sparky; 05.11.2013

Версия 0.08250 пакета DBIx::Class поддерживает предварительную выборку подмножества столбцы. Теперь вы можете написать запрос с join, columns и новым collapse, который работает как prefetch:

my $rs = $schema->resultset('CD')->search(
  {},
  {
    join     => [qw/ artist /],
    columns  => [qw/ title artist.name /],
    collapse => 1,
  }
);
person nwellnhof    schedule 14.11.2013

Дополнительный. Если вы хотите указать столбцы для вложенных соединений (2 уровня в глубину или более), вам нужно указать столбцы с использованием хеш-формата, чтобы DBIx мог разрешить отношения для применения к столбцу.

Пример:

    my $rs = $schema->resultset('CD')->search(
      {},
      {
        join     => { 'artist' => { 'agent' => 'publisher' } },
        columns  => [qw/ title artist.name artist.agent.publisher_id /, 
                        { 'artist.agent.publisher.publisher_name' => 'publisher.publisher_name' } ],
        collapse => 1,
      }
    );
person tprocter    schedule 15.01.2015