Используйте стороннюю библиотеку Javascript в компоненте Vue

Я использую Webpack и VueJs 2. Я хочу использовать в своем компоненте стороннюю библиотеку javascript, например такую:

<script async defer src = "https://apis.google.com/js/api.js" ... ></script>

Я нашел статью здесь о том, как это сделать для пакетов npm, но у меня это не работает, поскольку эта библиотека недоступна как пакет npm.

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

Я нашел одно возможное решение здесь, но это в основном взлом (измените dom, чтобы добавить элемент script после загрузки документа)

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

Обновлять: Если я помещу сценарий в теги заголовка в моем индексном файле, он будет загружен для всех компонентов. По соображениям производительности я бы хотел, чтобы он загружался только для определенного компонента.

Почему бы вам просто не включить скрипт, как показано в вашем примере, и создать его экземпляр, если он должен быть .. внутри хуков created / method?

samayo 19.03.2018 16:02

Почему бы вам не поместить тег сценария в <head> файла index.html?

Loïc Monard 19.03.2018 16:03

@ LoïcMonard см. Обновление

Caner 19.03.2018 16:06

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

samayo 19.03.2018 16:13

@samayo, можешь ли ты привести пример, как это сделать?

Caner 19.03.2018 16:15

Это настолько хорошо, насколько это возможно: stackoverflow.com/a/49331651/1850609 - Различия, о которых вы говорите («Я бы хотел, чтобы он загружался только для определенного компонента».), технически невозможны. Эти внешние скрипты обычно модифицируют (добавляют переменные) объект window. Вы не можете изменить его с помощью ООН, не зная внутренней части скрипта (так что общего решения этой проблемы нет). Если бы была достаточно хорошая идея, даже если бы загрузчика не было, я бы реализовал ее сам (ваш запрос очень распространен!), Но, к сожалению, нет хорошего универсального решения .

acdcjunior 19.03.2018 16:28
Поиск всех неиспользуемых файлов в проекте
Поиск всех неиспользуемых файлов в проекте
Количество файлов в проекте растет по мере его развития. И если быть по-настоящему честным, их продвижение происходит в геометрической прогрессии...
Настройка шаблона Metronic с помощью Webpack и Gulp
Настройка шаблона Metronic с помощью Webpack и Gulp
Я пишу эту статью, чтобы поделиться тем, как настроить макет Metronic с помощью Sass, поскольку Metronic предоставляет так много документации, и они...
4
6
5 613
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Насколько я знаю, вы не можете использовать что-то лучше, чем динамическое добавление тега script в заголовок вашей страницы. Однако вы можете создать небольшой плагин, который справится с этим за вас и запускает загрузку скрипта только в тех компонентах, которые вам нужны, и только один раз.

Начнем с самого плагина:

import Vue from 'vue'

const scriptLoader = {
    loaded: [],
    load (src) {
        if (this.loaded.indexOf(src) !== -1) {
            return
        }

        this.loaded.push(src)

        if (document) {
            const script = document.createElement('script')
            script.setAttribute('src', src)
            document.head.appendChild(script)
        }
    }
}

Vue.use({
    install () {
        Vue.prototype.$scriptLoader = scriptLoader
    }
})

Как видите, вы создаете объект scriptLoader, который содержит какой-то объект кэша loaded, который будет помнить, какой сценарий вы уже загрузили в какой-то момент своего приложения. Он также содержит метод load(), который будет обрабатывать добавление сценария в вашу голову.

Условие if (document) здесь, в случае, если вы будете отображать свое приложение на стороне сервера, document не будет существовать.

Затем вы можете загрузить свой скрипт в любой из ваших компонентов при создании с помощью ловушки created:

export default {
    ...
    created () {
        this.$scriptLoader.load('https://apis.google.com/js/api.js')
    }
}

Это самый чистый способ обработки такого сценария ... Надеюсь, это поможет ...

Ответ принят как подходящий

Хорошо, нашел решение, удовлетворяющее всем требованиям.

  • Скрипт загружается из Интернета, пакет npm не требуется
  • Скрипт загружается только наверняка компоненты при необходимости
  • Никаких уродливых манипуляций с домом

Добавьте скрипт в index.html с директивой v-if

<script v-if = "loadGoogleAPI" async defer src = "https://apis.google.com/js/api.js" ... ></script>

Внутри файла компонента (.vue), если вы хотите, чтобы скрипт загружался, установите флаг true:

<script>
export default {
  ...
  loadGoogleAPI: true,
  data() {
  ...
  }
};
</script>

Если script с v-if находится вне экземпляра Vue, v-if вообще не действует.

acdcjunior 19.03.2018 17:09

Даже если v-if действительно работал, удаление script тоже не повлияет на уже загруженный код. Удаление <script>не выгружает свой код.

acdcjunior 19.03.2018 17:19

@acdcjunior Это хороший момент, но, к счастью, мне не нужно выгружать скрипт. Если бы мне понадобился один обходной путь, я бы сделал многостраничное приложение vue

Caner 19.03.2018 17:54

Тогда другой вопрос / ответ, который я указал, делают то же самое.

acdcjunior 19.03.2018 17:55

Другие вопросы по теме