Эта статья является частью 2 серии статей Как создать веб-приложение File Manager Storage. В Части 1 мы завершили настройку фреймворка Django rest и Vue.js и подключили их с помощью загрузчика веб-пакетов Django. Во второй части мы углубимся в vue и создадим наше приложение для загрузки, перечисления и удаления любых файлов с привлекательным пользовательским интерфейсом. 💎

Я расскажу вам шаг за шагом, чтобы создать веб-приложение для хранения файлового менеджера. у нас будет технический стек, такой как Django с DRF, vue.js с webpack и vuex, а также библиотеки, такие как ag-grid, bootstrap, axios и т. д. 🎬

Во второй части этого урока мы собираемся:

Приступим к кодированию! ☕️

Настройте DRF для загрузки и удаления файлов

В Части 1 мы создали конечную точку API с помощью Django rest framework. Мы обновим только viewsets.py, созданный в файловом менеджере. Это будет единственное обновление, которое нам нужно сделать на стороне сервера.

обновите viewsets.py, как указано в последнем коде ниже.

Мы предоставляем набор запросов для всех объектов в нашей базе данных. Этот набор запросов передается автоматически, когда мы вызываем наш класс DataViewSet. Мы уже зарегистрировали расширение URL-адреса файлов в routers.py, которое мы создали в djvuetut. Этот набор запросов будет использоваться здесь для вывода списка всех файлов, которые есть в нашей базе данных.

Кроме того, мы должны обрабатывать сообщения и удалять запросы на стороне сервера и соответствующим образом обновлять нашу базу данных. Мы делаем это с помощью методов post и destroy соответственно.

Настройте main.js и установите библиотеки vue, которые будут использоваться

мы собираемся использовать следующие библиотеки vue:

Vuex → шаблон управления состоянием + библиотека для приложений Vue.js. Мы углубимся в это при создании запросов к API.

Axios → HTTP-клиент node.js для создания API-запросов.

Bootstrap-vue → Компоненты Bootstrap V4 и сеточная система доступны для Vue.js

Ag-Grid → библиотека javascript сетки данных. Он поддерживает Vue через компонент-оболочку.

Fortawesome → набор шрифтов и иконок на основе CSS и LESS.

Moment.js → библиотека Javascript для анализа и отображения даты и времени.

Установите все эти библиотеки с помощью npm:

npm i --save vuex axios bootstrap bootstrap-vue moment
npm i --save ag-grid-community ag-grid-vue vue-property-decorator 
npm i --save @fortawesome/fontawesome-svg-core 
npm i --save @fortawesome/free-solid-svg-icons 
npm i --save @fortawesome/vue-fontawesome

После установки наших зависимостей мы готовы настроить наш main.js, фактическую отправную точку приложения vue. Нам нужно будет сообщить vue, какие библиотеки мы собираемся использовать в нашем приложении.

Убедитесь, что окончательный вид main.js такой же, как показано ниже:

Создание компонентов Vue и настройка параметров Ag-Grid

Мы собираемся создать два компонента: один для заголовка и один для основного текста. Создайте папку с именем components в папке src. Внутри создайте Header.vue и Home.vue, как показано.

Обновите App.vue, как показано ниже. Это отправная точка внешнего интерфейса нашего приложения.

Затем продолжим, обновив Header.vue: на самом деле это просто базовая панель навигации. Хорошо то, что теперь у нас установлен бутстрап для vue. Bootstrap - это библиотека интерфейсных компонентов и набор инструментов для разработки с использованием HTML, CSS и JS. С помощью бутстрапа гораздо проще создать красивый и профессиональный интерфейс.

Добавьте следующий код внутри Header.vue:

Теперь наш компонент заголовка готов. Давайте продолжим работу с нашим основным компонентом Home.vue, но я должен остановиться на этом и подумать, как продолжить, потому что Home.vue содержит много кода. Я просто напишу здесь полный код, а затем пошагово объясню, как я его построил. Я добавил комментарии к разделу html и разделил его практически так:

  • Часть-1 → Список файлов
  • Часть-2 → Загрузить файл
  • Часть-3 → Удалить файл (ы)

Добавьте следующий код внутрь Home.vue

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

Часть 1 → Список файлов: мы добавили компонент ag-grid-vue. Здесь мы определили конфигурацию нашей сетки и необходимый нам источник данных. OnGridReady() - это метод, который вызывается при загрузке DOM. Мы определили заголовки столбцов и несколько других настроек для ag-grid в beforeMount(). Чтобы лучше понять крючки жизненного цикла vue, прочтите статью ниже:



мы также создали методы onRowClicked() и onRowSelected(), в которых мы реализуем наши действия. onRowSelected(), мы вычисляем размер выбранных файлов и добавляем итоговое значение к selectedDataTotal, которое будет отображаться при выборе одной или нескольких строк. onRowClicked(), мы отправляем выбранное имя файла в хранилище vuex для подготовки к загрузке. Подробнее об этом позже в разделе vuex.

Откуда берутся наши данные? rowData - это источник нашего списка файлов, который асинхронно извлекается с использованием Axios для запросов API с использованием Vuex в качестве центрального хранилища данных.

Как вы могли заметить, мы импортируем несколько вспомогательных методов из файлов js, которые мы должны создать в папке / src: filetypeCellRenderer.js и utils.js

Мы хотели бы отображать типы загружаемых файлов. Таким образом, мы можем отображать соответствующий значок для каждого типа файла в столбце filetype вместо того, чтобы показывать один и тот же значок для всех. Мы используем его как компонент каркаса сетки Ag в параметре cellRenderer определения столбца filetype.

Давайте создадим filetypeCellRenderer.js и добавим приведенный ниже код:

Теперь все готово! мы хотели бы отображать в нашем списке размеры файлов в красивом формате, например 85,5 КБ, 3 МБ или 2 ГБ и т. д. Итак, нам нужно будет его отформатировать. В определении столбца size мы вызываем метод sizeFormatter как параметр valueFormatter, предоставляемый Ag-grid. Это будет ожидать отформатированного значения, которое мы предоставим. Точно так же я хотел бы отформатировать дату и время для загрузки. Мы собираемся использовать красивую библиотеку парсера даты и времени moment.js, которую мы уже установили. С его помощью настолько просто разобрать объект date или datetime, что вы можете найти более подробную информацию на их веб-сайте.

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

Создайте utils.js в / src и добавьте код ниже:

Настройте параметры vuex для CRUD с помощью Axios

Я продолжу Часть 1 → Список файлов под этим заголовком, поскольку мы собираемся использовать Vuex и Axios в чтобы получать файлы из нашего бэкэнда, поскольку мы доставляли их информацию в формате JSON из нашего API.

Vuex - это шаблон управления состоянием + библиотека для приложений Vue.js. В качестве действий vuex нам потребуются следующие методы:

  • loadFiles → получить данные из базы данных
  • postFile → загрузить файл в базу данных
  • deleteFile → удалить файл из базы данных по заданному идентификатору.
  • downloadFile → разрешить загрузку файла из нашей папки мультимедиа по заданному имени файла.

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

Давайте создадим store.js файл в / src и добавим следующий код:

теперь вернемся к Home.vue и обратите внимание, что у нас есть вычисляемое свойство, которое мы называем mapState, внутри которого мы импортировали из vuex.

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

mapState позволяет нам легко получить доступ к участникам магазина. Мы определили пустой массив rowData в разделе state в нашем store.js и извлекаем этот rowData для использования в нашем списке ag-grid. Свойство Computed будет вызывать этот массив всякий раз, когда он изменяется. Таким образом, у нас всегда будет актуальный список файлов из нашей базы данных без обновления страницы. Замечательно!

Итак, вопрос теперь в том, как заполняется этот массив rowData? давайте еще раз проверим наш Home.vue и заметим, что мы отправляем метод loadFiles в нашем смонтированном методе, как показано ниже:

this.$store.dispatch(‘loadFiles’)

Затем мы выполняем фиксацию метода SET_FILES при мутации. Мы получаем список файлов с помощью метода Axios get и передаем эти данные.

Часть 2 → Загрузить файл: мы использовали компонент bootstrap-vue b-form-file, который также поддерживает функцию перетаскивания при открытии окна обозревателя файлов. Для нашего действия @click установлен метод submitFile(), который в первую очередь проверяет макс. размер файла, а затем вызовите vuex, как показано ниже:

this.$store.dispatch(‘postfile’, fd)

путем передачи выбранного файла в виде данных формы. postFile() Метод действия vuex выполняет почтовый запрос axios с переданными данными, которые должны быть получены DRF. В почтовом запросе важно определить Content-Type данных, которые мы отправляем. post() метод, который мы добавили в viewsets.py, предоставляемый DRF, может обрабатывать почтовый запрос для объекта типа файла с определением. Мы определили его как «multipart / form-data», потому что мы разработали наше приложение для получения файла в любое время. Затем мы выполняем фиксацию метода POST_FILE при мутациях, добавляя новый добавленный файл в массив rowData и, наконец, отправляем loadFiles() для обновления в нашем списке.

Часть 3 → Удалить файл (ы): аналогичным образом для нашего действия @click установлено значение deleteFile() method. Ag-grid позволяет нам добавить флажок для каждой строки и получить их свойства для выбранных строк простым this.gridApi.getSelectedNodes() методом. Мы можем получить массив уникальных идентификаторов всех выбранных файлов и передать этот массив в vuex после подтверждения запроса на удаление в модальном окне. Это запускается методом handleOk() и выполняется вызов vuex, как показано ниже:

this.$store.dispatch('deleteFile', this.result_id)

deleteFile() Метод действия vuex выполняет запрос на удаление axios с предоставленным массивом result_id. destroy() в DRF viewsets.py обрабатывают этот запрос и удаляют файл (ы) с заданными идентификаторами.

И последнее, но не менее важное

Ag-grid также позволяет нам выполнять действие при щелчке по определенной строке. Для этого у нас есть предопределенный onRowClicked() метод. В этом методе мы вызываем vuex для загрузки файла при щелчке, как показано ниже:

this.$store.dispatch('downloadFile', filename)

downloadFile() Метод действия vuex выполняет запрос на получение прямого URL-адреса файла с именем файла, сохраненным в папке «media», и использует тип ответа «blob» для подготовки файла к загрузке. Все файлы, которые мы загрузили, также могут быть просмотрены / доступны через абсолютный URL-путь с именем следующего файла:

http://localhost:8000/media/{filename}

Заключение

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

npm run build

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

Спасибо за прочтение! Пожалуйста, дайте мне знать, что вы думаете в твиттере @ ozguryarikkas Вот ссылка на Часть 1, если вы еще не читали ее.