Обзор Vue.js 2.6

Автор: admin от 27-01-2019, 15:40, посмотрело: 170

Привет, Хабр!



Совсем скоро должна выйти новая версия Vue.js — 2.6. Под катом вы найдете обзор новых фич следующей версии, включая новый синтаксис слотов, Vue.observable() и много чего еще!



Обзор Vue.js 2.6



Подробное описание
  • Обсуждение




  • Сокращение для v-slot






  • 2. Динамический аргумент директивы



    Если вы хотите динамический аргумент для v-bind или v-on, то во Vue@2.5.22 у вас есть только один вариант:

    <div v-bind="{ [key]: value }"></div>
    <div v-on="{ [event]: handler }"></div>
    




    Но у него есть пара недостатков:




    • Не все знают о возможности использования v-bind/v-on на объектах и о динамических названиях переменных

    • vue-template-compier генерирует неэффективный код

    • v-slot не имеет похожего синтаксиса для объектов





    Чтобы избавиться от них, Vue@2.6.0 представляет новый синтаксис:

    <div v-bind:[key]="value"></div>
    <div v-on:[event]="handler"></div>
     




    Примеры использования:



    <template>
      <div>
        <!-- v-bind с динамическим ключом -
        <div v-bind:[key]="value"></div>
    
        <!-- сокращение v-bind с динамическим ключом  -
        <div :[key]="value"></div>
    
        <!-- v-on с динамическим событием -
        <div v-on:[event]="handler"></div>
    
        <!-- сокращение v-on с динамическим событием -
        <div @[event]="handler"></div>
    
        <!-- v-slot с динамическим именем -
        <TestComponent>
          <template v-slot:[name]>
            Hello
          </template>
        </TestComponent>
    
        <!-- сокращение v-slot с динамическим именем -
        <TestComponent>
          <template #[name]>
            Cool slot
          </template>
        </TestComponent>
      </div>
    </template>
    




    Ссылки:







    3. Создание реактивных объектов с помощью Vue.observable()



    Раньше, чтобы создать реактивный объект, нужно было засунуть его внутрь инстанса vue-компонента. Теперь у нас есть отдельный метод, который делает объект реактивным — Vue.observable().



    Реактивный объект можно спокойно использовать в render- и computed-функциях.



    Пример использования:



    import Vue from vue;
    
    const state = Vue.observable({
      counter: 0,
    });
    
    export default {
      render() {
        return (
          <div>
            {state.counter}
    
            <button v-on:click={() => { state.counter++; }}>
              Increment counter
            </button>
          </div>
        );
      },
    };
    




    4. Загрузка данных на сервере



    В новом обновлении vue-server-renderer изменил стратегию загрузки данных для SSR.



    Раньше нам советовали вызывать методы asyncData() у компонентов, полученных через router.getMatchedComponents().



    В новой версии появился специальный метод у компонентов — serverPrefetch(). vue-server-renderer вызовет его у каждого компонента и дождется решения возвращенных промисов:

    <template>
      <div v-if="item">
        {{ item.name }}
      </div>
    </template>
    
    <script>
    export default {
      // Вызовется на сервере
      async serverPrefetch() {
        await this.fetchItem();
      },
    
      computed: {
        item() {
          return this.$store.state.item;
        },
      },
    
      // Вызовется на клиенте
      mounted() {
        if (!this.item) {
          this.fetchItem();
        }
      },
    
      methods: {
        async fetchItem() {
          await this.$store.dispatch('fetchItem');
        },
      },
    };
    </script>
    




    Чтобы узнать, когда завершилось ожидание всех serverPrefetch() и приложение завершило свой рендеринг, в контексте функции серверного рендера появилась возможность добавить хук rendered():



    /* Упрощенный entry-server.js */
    
    import { createApp } from './app';
    
    export default context => new Promise((resolve, reject) => {
      const { app, router, store } = createApp();
      const { url } = context;
    
      router.push(url);
    
      router.onReady(() => {
        context.rendered = () => {
          // Передаем состояние хранилища после завершения всех serverPrefetch()
          context.state = store.state;
        };
    
        resolve(app);
      }, reject);
    });
    




    5. Улучшенный вывод ошибок компилятора



    При компиляции html в render-функцию vue-template-compiler может выдать ошибки. Раньше Vue выводил описание ошибки без ее местоположения, теперь новая версия будет показывать, где она находится.



    Пример:



    <template>
      <div>
        <template key="test-key">
          {{ message }}
        </template>
      </div>
    </template>
    




    Ошибка vue-template-compiler@2.5.22:

      Error compiling template:
    
      <div>
        <template key="test-key">
          {{ message }}
        </template>
      </div>
    
      - <template> cannot be keyed. Place the key on real elements instead.
    




    Новый вывод ошибки vue-template-compiler@2.6.0:

      Errors compiling template:
    
      <template> cannot be keyed. Place the key on real elements instead.
    
      1  |
      2  |  <div>
      3  |    <template key="test-key">
         |              ^^^^^^^^^^^^^^
      4  |      {{ message }}
      5  |    </template>
    




    6. Отлов асинхронных ошибок



    Теперь Vue может ловить даже асинхронные ошибки в хуках жизненного цикла и обработчиках событий.



    Пример:



    /* TestComponent.vue */
    
    <template>
      <div @click="doSomething()">
        Some message
      </div>
    </template>
    
    <script>
    export default {
      methods: {
        async doSomething() {
          await this.$nextTick();
    
          throw new Error('Another Error');
        },
      },
    
      async mounted() {
        await this.$nextTick();
    
        throw new Error('Some Error');
      },
    };
    </script>
    




    Ошибка после маунта:

    [Vue warn]: Error in mounted hook (Promise/async): "Error: Some Error"
    


    Ошибка после клика:

    [Vue warn]: Error in v-on handler (Promise/async): "Error: Another Error"
    




    7. Новая сборка для ESM браузеров



    В новой версии добавилась еще одна сборка Vue — vue.esm.browser.js. Она предназначена для браузеров, поддерживающих ES6 Modules.



    Ее особенности:




    • Содержит компилятор HTML в render-функцию

    • Использует синтаксис ES6 Modules

    • Содержит нетранспилированный код





    Пример использования:



    <html lang="en">
      <head>
        <title>Document</title>
      </head>
      <body>
        <div id="app">
          {{ message }}
        </div>
    
        <script type="module">
          // Раньше приходилось использовать vue.esm.js, 
          // который содержал транспилированный код,
          // весил чуть больше и работал чуть медленнее
          import Vue from 'path/to/vue.esm.browser.js';
    
          new Vue({
            el: '#app',
    
            data() {
              return {
                message: 'Hello World!',
              };
            },
          });
        </script>
      </body>
    </html>
    




    Если честно, мне бы хотелось видеть еще одну сборку — такую же, как vue.esm.browser.js, но без компилятора HTML. Тогда я бы смог подвозить браузерам с ES6 Modules более свежий код, когда компилирую шаблоны при сборке.



    8. Сокращение для v-bind.prop



    У директивы v-bind есть специальный модификатор — .prop. Посмотреть, что он делает, можно вот тут в документации. Сам я ни разу его не использовал и не представляю себе случай, когда его стоит применить.



    Для него теперь есть специальное сокращение: вместо записи v-bind:someProperty.prop=«foo» можно писать .someProperty=«foo».



    Пример:



    Как было во Vue@2.5.22:

    <template>
      <div>
        <div v-bind:textContent.prop="'Important text content'" />
    
        <!-- Или сокращенный вариант -
        <div :textContent.prop="'Important text content'" />
      </div>
    </template>
    




    Как можно во Vue@2.6.0:

    <template>
      <div .textContent="'Important text content'" />
    </template>
    




    9. Поддержка кастомного toString()



    Тут все просто: если вы переопределите метод toString() у объекта, то Vue при отображении станет использовать его вместо JSON.stringify().



    Пример:



    /* TestComponent.vue */
    
    <template>
      <div>
        {{ message }}
      </div>
    </template>
    
    <script>
    export default {
      data() {
        return {
          message: {
            value: 'qwerty',
    
            toString() {
              return 'Hello Habr!';
            },
          },
        };
      },
    };
    </script>
    




    В версии Vue@2.5.22 мы увидим на экране:

    { "value": "qwerty" }
    


    В версии Vue@2.6.0:

    Hello Habr!
    




    10. Работа v-for с итерируемыми объектами



    В новой версии v-for может работать с любыми объектами, которые реализуют iterable protocol, например Map или Set. Правда, для Map и Set в версии 2.X не будет поддерживаться реактивность.



    Пример:



    /* TestComponent.vue */
    
    <template>
      <div>
        <div 
          v-for="item in items"
          :key="item"
        >
          {{ item }}
        </div>
      </div>
    </template>
    
    <script>
    export default {
      data() {
        return {
          items: new Set([4, 2, 6]),
        };
      },
    };
    </script>
    




    Посмотреть все новые фишки в деле можно прямо сейчас, установив бета-версию Vue:

    npm i vue@2.6.0-beta.2
    




    Спасибо, что дочитали до конца!

    Источник: Хабр / Интересные публикации

    Категория: Программирование

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

    Добавление комментария

    Имя:*
    E-Mail:
    Комментарий:
    Полужирный Наклонный текст Подчеркнутый текст Зачеркнутый текст | Выравнивание по левому краю По центру Выравнивание по правому краю | Вставка смайликов Выбор цвета | Скрытый текст Вставка цитаты Преобразовать выбранный текст из транслитерации в кириллицу Вставка спойлера
    Введите два слова, показанных на изображении: *