Как получить компоненты Vue.js для повторного использования / сохранения между изменениями маршрутизатора? - PullRequest
0 голосов
/ 30 мая 2018

Я использую Vue.js 2.5.x и Nuxt 1.4.Я считаю, что это вопрос, связанный с vue-router.

У меня есть один и тот же компонент на двух разных страницах Nuxt, которые я хочу сохранить в макете (не только в памяти) при навигации между страницами.

Чтобы обозначить это с точки зрения событий жизненного цикла, некоторые компоненты добавляются и удаляются из макета и запускают весь жизненный цикл создания, подключения, демонтажа и уничтожения.Я понимаю, как keep-alive работает, чтобы избежать создаваемых / уничтожаемых накладных расходов этого процесса для компонентов, которые мы ожидаем перемонтировать в компоновке, и здесь вопрос не в этом.

Напротив, простые компонентыпохоже, что при изменении маршрута не отключается вообще, как будто Vue каким-то образом понимает, что эти компоненты будут выглядеть одинаково в двух разных макетах, поэтому он не только не уничтожает / не создает их ... он оставляет их в макете и не 'я даже не могу их размонтировать.

Я пытаюсь лучше понять условия, которые позволяют компонентам текущей страницы оставаться подключенными при навигации между маршрутами.Многие из обсуждений, которые я обнаружил, носят характер «Почему мой компонент не обновляется?», Когда происходит изменение маршрута, но у меня фактически есть противоположная проблема: я хочу сохранить компонент и его состояние, но компонентразрушается.Я поиграл с тем, чтобы явно задать ключ для определенного общего значения (обычно дается противоположный совет по страхованию компонентов, которые размонтируются), но, похоже, что-то более глубокое, чем это.

Опять же, для ясности, яне относится к "keep-alive", пытающемуся повиснуть над компонентами в памяти, которые временно удалены из макета.То, что я наблюдаю и пытаюсь понять здесь, кажется другим поведением, когда некоторая часть Vue распознает компоненты как идентичные между двумя макетами, и это оптимизирует удаление и (повторное) создание таких компонентов.Это огромная оптимизация, но такая, поведение которой, кажется, нигде не обсуждается и не документируется.

У меня есть макет Nuxt, концептуально подобный этому ...

default.vue:

<template>
  <div>
    <my-marvelous-header-component />
    <nuxt/>
    <my-also-marvelous-footer-component />
  </div>
</template>

… и у меня есть пара страниц Nuxt, которые выглядят следующим образом…

page-a.vue:

<template>
  <section id=mainContent>
    <wonderful-component id="wonder1" :key=321 />
    <complex-component-with-children :key=123 />
  </section>
</template>

page-b.vue:

<template>
  <section id=mainContent>
    <wonderful-component id="wonder1" :key=321 />
    <complex-component-with-children :key=123 />
  </section>
</template>

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

Когда я перемещаюсь между этими страницами с помощью этого. $ router.push (), мои компоненты верхнего и нижнего колонтитула переживают маршрутнавигация не поддерживается (я проверил это, поместив некоторые выходные данные консоли в хуки жизненного цикла), однако и замечательные, и сложные компоненты уничтожаются, а затем воссоздаются.

Оба компонента, которые я пытаюсь перезапустить, имеют ряд динамическисоздал чКомпоненты внутри, поэтому состояние vdom будет значительно отличаться от исходных условий исходной страницы.Такие компоненты, как чудесные или сложные, не имеют никаких свойств или каких-либо других данных, передаваемых из шаблона ... Они в точности соответствуют приведенному выше макету.Я экспериментировал с предоставлением им уникального идентификатора или значения ключа, которое разделяется между шаблонами (а также вообще ничего), но независимо от того, что я пробовал, нажатие маршрутизатора вызывает разрушение и повторную визуализацию этих компонентов.

Тривиальные компоненты, такие как мой верхний и нижний колонтитулы, нормально перерабатываются, я просто хочу, чтобы мои более сложные компоненты работали так же.

Так что мой вопрос центрЕдинственное, что позволяет или предотвращает переработку компонентов?Что проверяется, чтобы определить, можно ли переработать компонент?Есть ли способ сигнализировать о том, что компонент должен быть сохранен / переработан между изменениями маршрута?Если нет, то что я должен держать вне компонента, чтобы он выглядел в качестве кандидата для слипания между переходами?

Я думал, что свойство «ключа» было магией, но это не так.Кажется, что это не работает, и, к сожалению, просмотр источника Vue.js для этого слова показывает, что он довольно широко используется для именования параметров и локальных переменных… Я считаю, что в Vue есть функция «patch ()», которая занимается обновлением хотя бы vdomв соответствии со старыми и новыми компонентами, но, честно говоря, логика там превышает мои нынешние знания Vue.Если бы кто-то, обладающий некоторыми лучшими знаниями о внутренностях Vue, имел представление о том, какие части кода могли бы помочь прояснить мое мышление, я бы хотел снова погрузиться в это.

Мне кажется, что я преследовал своюхвост на этом несколько дней.Любые мысли или идеи очень ценятся.

1 Ответ

0 голосов
/ 31 мая 2018

(Не уверен, что этих объяснений будет достаточно для вас, но я все равно попытаюсь ответить на него)

Вместо переработка , общий термин, используемый в Vueназывается keep-alive .Это термин, который вы хотели бы использовать, когда будете исследовать это.

Для Nuxt keep-alive пока еще не выглядит надежным .Я бы посоветовал вам хранить все данные в Vuex и отображать элементы на основе данных в Vuex.

, что позволяет или предотвращает переработку компонентов?Что проверяется, чтобы определить, может ли компонент быть переработан?

Здесь полезно подумать с точки зрения монтажа и демонтажа.По умолчанию компонент всегда уничтожается при размонтировании.(Если не используется keep-alive.)

В этом примере

<my-marvelous-header-component />
<nuxt/>
<my-also-marvelous-footer-component />

<nuxt/> - это место, где расположен <router-view></router-view> маршрутизатора Vue. При изменении маршрута только компоненты внутриrouter-view будет установлен / отключен.Следовательно, при изменении маршрута <my-marvelous-header-component /> и <my-also-marvelous-footer-component /> остаются неизменными и не будут монтироваться / демонтироваться.

Есть ли способ указать, что компонент должен быть сохранен / переработан между изменениями маршрута?

В типичном (не Nuxt) проекте Vue он управляется путем применения <keep-alive> к <router-view>.

Это довольно хороший пример: https://jsfiddle.net/Linusborg/L613xva0/4/

<div id="app">
  ...
  <keep-alive include="foo">
    <router-view></router-view>
  </keep-alive>
</div>

Но в Nuxt автоматически генерируется <router-view>, и вы не сможете применить <keep-alive> к нему какв обычном проекте Vue.

(Опять) Для Nuxt keep-alive пока еще не выглядит надежным .Я бы посоветовал вам сохранить все данные в Vuex и визуализировать ваши элементы на основе данных в Vuex.

...