Как передать данные в другие компоненты пользовательского интерфейса DataProvider


9

У меня есть компонент пользовательского интерфейса сетки, который находится внутри набора полей какой-то отредактированной формы. Мне нужно передать entity_idиз формы редактирования в сетку, где я могу отфильтровать коллекцию некоторых элементов по некоторому значению, и сетка покажет соответствующий результат. Я создал компонент сетки, используя компонент insertListing.

<insertListing name="slide_grid">
        <argument name="data" xsi:type="array">
            <item name="config" xsi:type="array">
                <item name="autoRender" xsi:type="boolean">true</item>
                <item name="source" xsi:type="string">slide</item>
                <item name="loading" xsi:type="boolean">true</item>
                <item name="dataScope" xsi:type="string">some_slider_slide_listing</item>
                <item name="externalProvider" xsi:type="string">${ $.ns }.some_slider_slide_listing_data_source</item>
                <item name="ns" xsi:type="string">some_slider_slide_listing</item>
                <item name="externalData" xsi:type="string">id</item>
                <item name="imports" xsi:type="array">
                    <item name="slider_id" xsi:type="string">${ $.provider }:data.entity_id</item>
                </item>
                <item name="exports" xsi:type="array">
                    <item name="slider_id" xsi:type="string">${ $.externalProvider }:params.slider_id</item>
                </item>
            </item>
        </argument>
    </insertListing>

Для передачи данных на внешний dataProvider я использую

<item name="exports" xsi:type="array">
                <item name="slider_id" xsi:type="string">${ $.externalProvider }:params.slider_id</item>
            </item>

Внутри моего внешнего поставщика данных я пытаюсь получить данные через запрос.

$this->request->getParam('slider_id');

Но ничего. Во внешнем интерфейсе я обнаружил, что Magento отправляет запрос ajax с моим параметром, но я не могу перехватить это в своем DataProvider и отфильтровать коллекцию.


Подход, который я получил от кода ядра Magento 2 (например, в продуктах CustomOptions формы Modifier). Но по некоторым причинам это не работает для меня.
Мистери

Вы получили какое-либо решение проблемы ... Я сталкиваюсь с той же проблемой, пожалуйста, помогите, если вы решили ...
Ашиш Радж

Я сделал такой же тег insertListing, как и вы, но в запросе ajax не было моего параметра в теге export .... Нашли решение?
thanhdv2811

Ответы:


2

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

Здесь externalProviderтэг для добавления поставщика источника списка, который мы вставляем.

Здесь importsтэг используется для импорта параметров текущего источника данных формы

Здесь exportsтег используется для экспорта текущих параметров данных формы в листинг, который будет вставлен.

<insertListing name="slide_grid">
    <argument name="data" xsi:type="array">
        <item name="config" xsi:type="array">
            <item name="autoRender" xsi:type="boolean">true</item>
            <item name="ns" xsi:type="string">slide_grid</item><-- data source of the inserted listing -->
            <item name="externalProvider" xsi:type="string">colors_one_listing.colors_one_listing_data_source</item><!-- your insert listing data provider source -->
            <item name="imports" xsi:type="array">
                <item name="spd_id" xsi:type="string">${ $.provider }:data.slider_id</item>
            </item>
            <item name="exports" xsi:type="array">
                <item name="slider_id" xsi:type="string">${ $.externalProvider }:params.slider_id</item>
            </item>
        </item>
    </argument>
</insertListing>

Добавьте объединение с соответствующим столбцом в текущую коллекцию, чтобы использовать его двумя способами:

  1. Фильтровать по сетке dataSource> имя аргумента> «dataProvider»> имя аргумента> «data»> имя элемента «config»> имя элемента = «filter_url_params» => имя элемента> «slider_id» .

Для более подробной информации проверьте код ниже:

<dataSource name="..._listing_data_source">
    <argument name="dataProvider" xsi:type="configurableObject">
        <argument name="class" xsi:type="string">...\...\Ui\DataProvider\...\Grid\...DataProvider</argument>
        <argument name="name" xsi:type="string">..._listing_data_source</argument>
        <argument name="primaryFieldName" xsi:type="string">id</argument>
        <argument name="requestFieldName" xsi:type="string">slider_id</argument>
        <argument name="data" xsi:type="array">
            <item name="config" xsi:type="array">
                <item name="component" xsi:type="string">Magento_Ui/js/grid/provider</item>
                <item name="update_url" xsi:type="url" path="mui/index/render"/>
                <item name="filter_url_params" xsi:type="array">
                    <item name="slider_id" xsi:type="string">*</item>
                </item>
                <item name="storageConfig" xsi:type="array">
                    <item name="indexField" xsi:type="string">id</item>
                </item>
            </item>
        </argument>
    </argument>
    <argument name="data" xsi:type="array">
        <item name="js_config" xsi:type="array">
            <item name="component" xsi:type="string">Magento_Ui/js/grid/provider</item>
        </item>
    </argument>
</dataSource>
  1. Фильтруйте поставщика данных вставленного списка.

В поставщике данных добавьте фильтр для этого параметра:

$collection->addFieldToFilter('slider_id', $this->request->getParam('slider_id'));

Мне нравится следовать варианту 1.


dataProvider не имеет параметров filter_url_params в определении. Пожалуйста, обновите ваш ответ.
Микеланджело

1

После прочтения и отладки основных файлов Magento 2 я нашел простое и понятное решение этой проблемы. Передача данных из пользовательской формы в пользовательскую сетку с использованием UIComponent insertListing действительно трудна и совсем не документирована.

введите описание изображения здесь

У объекта InsertListing есть два параметра под тегом: экспорт и импорт, которые я использовал в своем листинге:

<fieldset name="relatedto" >
    <settings>
        <label>Related to</label>
        <componentType>fieldset</componentType>
    </settings>

    <insertListing name="threadrelated_listing">
        <settings>
            <dataLinks>
                <exports>false</exports>
                <imports>true</imports>
            </dataLinks>
            <externalProvider>mycompany_helpdesk_threadrelated_listing.mycompany_helpdesk_threadrelated_listing_data_source</externalProvider>
            <selectionsProvider>mycompany_helpdesk_threadrelated_listing.mycompany_helpdesk_threadrelated_listing.mycompany_helpdesk_threadrelated_columns.ids</selectionsProvider>
            <autoRender>true</autoRender>
            <dataScope>mycompany_helpdesk_threadrelated_listing</dataScope>
            <ns>mycompany_helpdesk_threadrelated_listing</ns>
            <exports>
                <link name="ticket_id">${ $.externalProvider }:params.ticket_id</link>
            </exports>
            <imports>
                <link name="ticket_id">${ $.provider }:data.ticket_id</link>
            </imports>
        </settings>
    </insertListing>
</fieldset>

и после нескольких часов, чтобы понять и найти решение в Интернете, я не нашел никакой подсказки!

Итак, я прочитал файл Magento Core и обнаружил, что Magento использует способ создания вложенных сеток списков в проекте. Иногда он использует старый метод вставки блока и несколько раз новый метод листинга UIComponent.

Я нашел сетку списка адресов клиентов в customer_address_listing.xml (/vendor/magento/module-customer/view/adminhtml/ui_component/customer_address_listing.xml), и он получает переменную parent_id, определенную в customer_form.xml (/ vendor / magento) /module-customer/view/base/ui_component/customer_form.xml) но вопрос таков:

Как Magento передает данные из формы в сетку вложенных списков?

Magento передает данные с помощью QUERYSTRING PARAMETER!

Если вы прочитаете файл DataProvider.php, вы будете удивлены, потому что он получает переменную parent_id (customer) с помощью QUERYSTRING! Посмотрите на /vendor/magento/module-customer/Ui/Component/Listing/Address/DataProvider.php строка 58:

/**
 * Add country key for default billing/shipping blocks on customer addresses tab
 *
 * @return array
 */
public function getData(): array
{
    $collection = $this->getCollection();
    $data['items'] = [];
    if ($this->request->getParam('parent_id')) {
        $collection->addFieldToFilter('parent_id', $this->request->getParam('parent_id'));
        $data = $collection->toArray();
    }
    foreach ($data['items'] as $key => $item) {
        if (isset($item['country_id']) && !isset($item['country'])) {
            $data['items'][$key]['country'] = $this->countryDirectory->loadByCode($item['country_id'])->getName();
        }
    }

    return $data;
}

но как мне установить параметр в листинге URL? Я нашел параметр filterUrlParams, но здесь есть странная проблема! Давайте посмотрим на этот фрагмент кода dataSource:

<dataSource name="mycompany_helpdesk_threadrelated_listing_data_source" component="Magento_Ui/js/grid/provider">
    <settings>
        <filterUrlParams>
            <param name="ticket_id">*</param>
        </filterUrlParams>
        <storageConfig>
            <param name="indexField" xsi:type="string">threadrelated_id</param>
        </storageConfig>
        <updateUrl path="mui/index/render"/>
    </settings>
    <dataProvider class="mycompany\Helpdesk\Ui\DataProvider\Threadrelated\ThreadRelatedDataProvider" name="mycompany_helpdesk_threadrelated_listing_data_source">
        <settings>
            <requestFieldName>id</requestFieldName>
            <primaryFieldName>threadrelated_id</primaryFieldName>
        </settings>
    </dataProvider>
</dataSource>

Я установил ticket_id с подстановочным знаком (*), что означает: получить все билеты! но если вы не устанавливаете какой-либо идентификатор в filterUrlParams, URL-адрес insertListing НЕ имеет НИКАКОГО УСТАНОВКИ ticket_id! Так почему ?!

Решение, предложенное @ hashish-raj, не работает для меня.

Это все сообщения, которые я прочитал об этой проблеме:

В конце я нашел временный обходной путь с использованием основного сеанса и сохранил параметр ticket_id в сеансе. Затем в пользовательском провайдере данных я проверил его и применил к коллекции:

/***
 * @return array
 */
public function getData()
{

    $collection = $this->getSearchResult();

    /** see: check Mycompany\Helpdesk\Controller\Adminhtml\Ticket\Edit **/
    if($this->coreSession->getTicketId()){
        $collection->addFieldToFilter('ticket_id', ['eq' => $this->coreSession->getTicketId()]);
    }

    return $this->searchResultToOutput($collection);

}

Если у вас есть обходной путь или вы поняли, как Magento справляется с этими отношениями между UIComponent , пожалуйста, поделитесь своими знаниями!

Я открыл «Баунти» здесь: https://magento.stackexchange.com/a/306537/2004

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.