Как создать объединение двух представлений?

Я пытаюсь получить объединение узлов пользователя и комментариев, отсортированных по дате публикации. Это сообщение ссылки на проекты песочницы для D6, но для 7 нет ничего.

Это post имеет пример использования hook_views_pre_execute () и SQL UNION в D6. Это не работает для D7 с представлениями 3.

Я встретил merlinofchaos комментарий

  

Поскольку мы используем новый генератор запросов Drupal, запрос является объектом SelectQuery, который вам нужно будет изменить или заменить. Посмотрите новый слой базы данных Drupal 7 для получения дополнительной информации.

Есть ли у кого-нибудь пример того, как это сделать или какое-либо другое решение для объединения двух представлений?

36 голосов | спросил MotoTribe 22 Mayam12 2012, 01:33:21

9 ответов


15

Вот пример работы и тестирования:

/**
 * Реализует hook_views_pre_execute ().
 * /
function mymodule_views_pre_execute (view & $ view) {
  if ($ view-> имя == 'my_view') {
    $ query1 = & $ view-> build_info ['query'];

    //Базовая настройка второго запроса.
    $ query2 = db_select ('another_table', 'at')
      -> условие ('some_field', 0, '>')
      -> условие ('some_other_field', 12345);

    //Количество полей (и их псевдонимов) должно соответствовать запросу1.
    //Получить информацию с помощью:
    //dpm ($ query1-> getFields ());
    $ query2-> addField ('at', 'some_field', 'alias1');
    $ query2-> addField ('at', 'some_other_field', 'alias2');
    $ query2-> addField ('at', 'some_other_field2', 'alias3');
    $ query2-> addField ('at', 'some_other_field3', 'alias4');

    //Убедитесь, что запросы очень похожи.
    //dpq ($ query1);
    //dpq ($ query2);

    //Супружество.
    $ query1 = $ query2-> union ($ query1, 'UNION ALL');

    //Ручной тест.
    //dpm ($ query1-> execute () -> fetchAll ());

  }
}

Это работает для большинства просмотров. Однако некоторые плагины стиля могут придумывать материал, который не будет работать с этой техникой (модуль Calendar, на который я смотрю).

ответил Dalin 30 +04002013-10-30T19:47:51+04:00312013bEurope/MoscowWed, 30 Oct 2013 19:47:51 +0400 2013, 19:47:51
3

Вы можете использовать модуль дополнительных обработчиков Views для генерации запросов SQL UNION из двух разных представлений /отображений.

Подробное руководство по drupal.org здесь

https://www.drupal.org/project/views_extra_handlers снимок экрана с изменениями

ответил TechNikh 12 FriEurope/Moscow2014-12-12T22:50:42+03:00Europe/Moscow12bEurope/MoscowFri, 12 Dec 2014 22:50:42 +0300 2014, 22:50:42
2

В итоге я использовал db_query () для создания SQL UNION, а затем превратил его в макет таблицы, включая пейджеры, используя функцию theme ().

Пользователю это выглядит как представления по умолчанию. Другое преимущество заключалось в том, что я мог оптимизировать запрос. Я показываю «действия моего друга», и если вы будете использовать представления для этого, он создаст список ваших друзей и будет использовать его в разделе «IN» SQL, которое очень медленное, если у вас более 50 или 100 записей.

Я мог сузить этот список друзей только тем, кто зашел за сайт за последние x дней.

Это пример кода:

//Требуются два запроса (дружба может быть представлена ​​двумя способами в
  //та же таблица). Нет смысла делать два вызова db, хотя это СОЮЗ.

  //Создаем первый запрос.
  $ query = db_select ('flag_friend', 'f')
    -> условие ('f.uid', $ account-> uid)
    -> условие ('u.login', $ timestamp, '>');
  $ query-> addExpression ('f.friend_uid', 'uid');
  $ query-> innerJoin ('users', 'u', 'u.uid = f.friend_uid');

  //Создаем второй запрос.
  $ query2 = db_select ('flag_friend', 'f')
    -> условие ('f.friend_uid', $ account-> uid)
    -> условие ('u.login', $ timestamp, '>');
  $ query2-> addExpression ('f.uid', 'uid');
  $ query2-> innerJoin ('users', 'u', 'u.uid = f.uid');

  //Возвращаем результаты запросов UNIONed.
  return $ query-> union ($ query2) -> execute () -> fetchCol ();
ответил MotoTribe 11 J000000Wednesday12 2012, 20:44:50
1

В дальнейшем для справки я объединил два представления, основываясь на одной и той же таблице. Те же принципы должны также применяться к представлениям на основе разных таблиц с одинаковым количеством полей.

В нижеприведенном случае выбирается только id, поскольку формат установлен на визуализированный объект. Но если вы собираетесь с полями, вы всегда можете добавить дополнительные фиктивные поля в запрос, у которого меньше полей, так как я добавил отметку времени ниже.

/**
 * Реализует hook_views_pre_execute ().
 * /
функция MY_MODULE_views_pre_execute (& $ view) {
  if ($ view-> имя == 'VIEW_1' & & $ view-> current_display == 'DISPLAY_OF_VIEW_1') {

    $ view2 = views_get_view ('VIEW_2');
    $ View2- > построить ( 'DISPLAY_OF_VIEW_2');

    $ View- > build_info [ 'запрос']
    -> fields ('table_alias', array ('timestamp'))
    - > объединение (
        $ View2- > build_info [ 'запрос']
        - > диапазон ()
        -> fields ('table_alias', array ('timestamp'))
        -> orderBy ('timestamp', 'DESC')
    );

    $ View- > build_info [ ''] count_query
    - > объединение (
        $ View2- > build_info [ ''] count_query
        - > диапазон ()
    );
  };
}
ответил MotoTribe 11 J000000Wednesday12 2012, 20:44:50
0

Я представляю себе что-то в этом роде:

/**
* Реализует hook_views_pre_execute ().
* /
function mymodule_views_pre_execute (& $ view) {
  if ($ view-> имя == 'myview') {
    $ query = $ view-> запрос;
    $ other_view = views_get_view ('otherview');
    $ other_query = $ other_view-> запрос;
    $ query = $ query-> union ($ other_query);
    $ view-> query = $ query;
  }
}

Хотя я его не тестировал.

Некоторые ссылки, которые могут помочь:

http: //api.drupal.org/api/drupal/includes!database!select.inc/function/SelectQueryInterface%3A%3Aunion/7

http://drupal.org/node/557318#comment-1991910

ответил cam8001 29 Maypm12 2012, 20:47:53
0

Я наткнулся на модуль под названием Вид поля обзора , который позволяет встраивать представление в виде поля в другом представлении. Я еще не пробовал это еще, но это может быть полезно для вас.

ответил Marijke Luttekes 4 J0000006Europe/Moscow 2012, 15:43:47
0

EntityFieldQuery Views Backend поддерживает одновременное запрос нескольких типов сущностей. Поэтому он должен использоваться для запросов как для узлов, так и для комментариев. Оба типа сущностей используют свойство uid для ссылки на их автора, поэтому на уровне API EntityFieldQuery :: propertyCondition () должен использоваться для выбора узлов и комментариев от одного пользователя. Я предполагаю, что бэкэнд представлений обеспечивает ту же самую функцию.

ответил Pierre Buyle 4 J0000006Europe/Moscow 2012, 23:44:44
0

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

ответил Sam Wilson 20 +04002014-10-20T14:05:52+04:00312014bEurope/MoscowMon, 20 Oct 2014 14:05:52 +0400 2014, 14:05:52
-1

Используется Глобальные: PHP поля? Вы можете использовать их для склеивания ленты вместе с представлением, которое объединяет два.

Создайте представление содержимого с контентом: заголовок и контент: поля комментариев (исключены из отображения).

Добавьте поле PHP, которое вычисляет более позднюю дату, дату последнего обновления или дату последнего комментария пользователя и задает значение поля этой даты. Добавьте это поле как условие сортировки.

Добавьте аналогичное поле, которое выводит либо ссылку на комментарий, либо узел.

Это звучит хорошо для меня!

ответил Johnathan Elmore 22 Mayam12 2012, 02:02:16

Похожие вопросы

Популярные теги

security × 330linux × 316macos × 2827 × 268performance × 244command-line × 241sql-server × 235joomla-3.x × 222java × 189c++ × 186windows × 180cisco × 168bash × 158c# × 142gmail × 139arduino-uno × 139javascript × 134ssh × 133seo × 132mysql × 132