Редактирование word с помощью js
Для решений многих повседневных задач используются продукты Microsoft Office, такие, как Word, Excel, PowerPoint и т.д. Но не все знают, что в этих приложениях можно использовать надстройки (Add-ins), доступные из Microsoft AppSource. Эти надстройки позволяют расширить стандартный функционал Office, например, осуществлять перевод текста, искать изображения в интернете или даже планировать встречи в Starbucks. Стоит отметить, что многие современные надстройки работают с Office для iPad, Office Online и Office для Mac, а не только с традиционными настольными версиями Office для Windows.
Мне необходимо было интегрировать виджет для работы с уже существующим веб-сайтом, написанным ранее. Основные задачи надстройки можно выделить в следующие пункты:
- получение данных из открытого документа Microsoft Office в контекст виджета;
- анализ полученных данных из текущего документа, выделение ключевых слов с помощью простого NLP алгоритма (подсчет наиболее используемых слов, не считая предлогов и союзов), а также поиск по этим словам и отображение соответствующего контента (карточки с различными типами содержания: текст, изображения, видео, опросники и т.д.), посредством API уже написанного сервера;
- возможность быстрой вставки контента из результатов поиска в рабочую область документа.
Для реализации собственной надстройки Office, нам нужно подготовить два основных компонента — файл манифеста и веб-приложение.
Манифест представляет собой XML-файл, который определяет следующие параметры и возможности надстройки:
- Отображаемое имя, описание, идентификатор, версию и языковой стандарт надстройки по умолчанию.
- Способ интеграции надстройки с Office.
- Уровень разрешений и требования для доступа к данным для надстройки.
Веб-приложение — это HTML-страница, которая отображается в приложении Office. Для создания кода, который взаимодействует с документами Office, а также позволяет пользователю взаимодействовать с веб-ресурсами из приложения Office, можно применять любые технологии, как клиентские, так и серверные. В свою очередь, Microsoft предоставляет интерфейсы API JavaScript Office.js для взаимодействия с документами. Выглядит это следующим образом:
Перед началом разработки, Microsoft Office предлагает ознакомиться, и соответственно придерживаться следующих принципов оформления надстроек:
- Разрабатывайте специально для Office.
- Сосредоточьтесь на нескольких ключевых задачах.
- Содержимое важнее, чем хром (внешний вид).
- Сделайте работу с надстройкой приятной и разрешите пользователям самим выбирать, что делать.
- Поддержка всех платформ и способов ввода.
Так же Microsoft разработал Office UI Fabric — официальный front-end framework для создания интерфейсов в Office. И конечно же, рекомендует его использовать при разработке.
Написание файла манифеста
Для начала подготовим файл манифеста. На следующей схеме показана иерархия элементов, используемых для задания команд надстройки.
Весь файл манифеста разбиваем на 3 части:
- Общая информация о надстройке — тут отображается название, версия, описание надстройки и т.д, а также поддерживаемые типы платформ в нашей надстройке (доступны: Word, Excel, PowerPoint, Outlook, Project и SharePoint).
- Далее идет информационный блок для каждого типа платформы, которые мы объявили. Тут содержится информация для конкретного типа. Пример для Word:
- В последней части, мы описываем информационный блок ресурсов:
Детальную информацию по созданию файла манифеста можно прочитать в официальной документации.
Написание веб-приложения
Для разработки веб-приложения нам понадобится API JavaScript для Office. Библиотека API JavaScript для Office состоит из файла Office.js и связанных JS-файлов. Простейший способ сослаться на API — использовать сеть доставки содержимого (CDN), добавив следующий код в тег страницы:
Начать работу с библиотекой необходимо с инициализации библиотеки Office, для этого предусмотрен метод Office.onReady() — это асинхронный метод, который возвращает объект Promise во время проверки загрузки библиотеки Office.js. Когда библиотека будет загружена, объект Promise сопоставляется в качестве объекта, определяющего приложение Office, с числовым значением Office.HostType (Excel, Word и т. д.), а платформа — с числовым значением Office.PlatformType (PC, Mac, OfficeOnline и т. д.). Объект Promise сопоставляется незамедлительно, если библиотека уже загружена, когда вызывается Office.onReady() .
Надстройки взаимодействует с объектами в Office с помощью двух типов объектных моделей JavaScript:
Общий API JavaScript для Office используется, если вам нужно:
- создать надстройки для Word 2013;
- выполнить начальные действия для приложения;
- проверить поддерживаемый набор требований;
- получить доступ к метаданным документа, его параметрам и сведениям о среде;
- создать привязку к разделам документа и записать события;
- использовать пользовательские XML-части;
- открыть диалоговое окно.
API JavaScript для Excel, Word, PowerPoint предоставляют строго типизированные объекты, с помощью которых можно получать доступ к различным объектам рабочей области документов.
Например, для получения контента из рабочей области документа можно воспользоваться методом getSelectedDataAsync :
А для вставки контента в рабочую область, можем воспользоваться методом setSelectedDataAsync :
Также хотелось бы выделить использование Dialog API в надстройках Office. В настоящее время оно поддерживается для Word, Excel, PowerPoint и Outlook. Dialog API позволяет реализовать:
- Отобразить страницу входа, которую невозможно открыть непосредственно в области задач.
- Предоставить больше места на экране (или даже весь экран) для некоторых задач в надстройке.
- Разместить видео, которое будет слишком маленьким в области задач.
Важно отметить, что страница веб-приложения и ресурсы диалоговых окон должны иметь одинаковые полные доменные имена.
В целом, для создания веб-приложения можно использовать любые веб-технологии и фреймворки. Так как я разрабатывал надстройку для уже готового веб-сайта, то в качестве клиентского фреймворка я выбрал React, как и в основном сайте, также использовал API уже готового бэкенда написанного на Ruby. В итоге у меня получилась вот такая надстройка, которую можно найти в общем доступе, правда она вам пригодится, если вы являетесь пользователем платформы ProjectX.
На данный момент AppSource содержит около 6,5 тысяч готовых приложений разделенные на определенные категории и отрасли. Майкрософт продолжает развивать и поддерживать данное направление, облегчая процесс создания надстроек и расширяя возможности интерфейсов API JavaScript Office.js. На сайте Майкрософта можно найти много полезных ресурсов для разработки. В конечном счете, перед тем как надстройка окажется в общем доступе, она должна пройти этап тестирования, а также должна соответствовать всем требованиям для запуска надстроек Office от Microsoft.
Думаю, что большинство из нас очень часто использует отличный сервис Google Docs. Однажды меня озарила мысль попробовать написать что-нибудь подобное, только не сервис, а библиотеку, которая решит задачу работы с документами наиболее популярных форматов непосредственно в браузере и offline! И конечно же для разработки только JavaScript и ничего более :) Так на свет родилась библиотека jDoc, которая еще находится на ранней стадии своего развития, под версией 0.1.0.
Что мы умеем
- .docx
- .txt
- .fb2
- .odt
- .csv
- .tsv
Как использовать
Подключаем в проект библиотеку:
Или её минифицированную версию:
И читаем необходимый файл:
- result.html() — вернет documentFragment с преобразованной структурой file в html, удобно использовать для моментального отображения документа пользователю
- result.data() — вернет прочитанную структуру документа как обычный JavaScript-объект
Используемые технологии
Конечно же вы догадались, что для чтения файлов с помощью JavaScript в браузере используются наиболее новые технологии, которые все включают в единое понятие HTML5, такие как: Blob, FileAPI, JavaScript typed arrays
Сборка исходников в один единственных файл осуществляется с помощью Grunt.
Особенности
Для меня сущим кошмаром стала работа с форматом Office Open XML, который включает в себя файлы .docx. По сравнению с тем же OpenDocument (.odt-файлы), структура Open XML выглядит невероятно монструозной.
Не обошлось и без забавных казусов. В манифесте к файлу .docx есть тэг который регламентирует количество страниц документа для отображения. Но если взять и открыть этот же документ в MS Word, то количество страниц будет равняться 2 :) Для почти десятка остальных тестируемых документов такой ситуации не возникало.
Пришлось помучиться и с WebWorkers, т.к. и в Chrome, и в FireFox одновременное создания более 20 воркеров закончивалось ничем или крашило браузер. Для примера, один файл .docx «разбирается» в 20-25 файлов, не учитывая изображения и другие сторонние ресурсы.
Поддержка браузерами
К сожалению, была возмость проверить работу библиотеки только в последних версиях Google Chrome и Mozilla FireFox.
Планы
- Кастомизация — сделать отдельную страницу для сборки библиотеки под определенные форматы документом, что-то наподобие сборки jQuery UI
- Все же использовать WebWorkers, т.к. технология очень удобная и мощная, хотя, возможно, использовать не для всех форматов файлов
- Возможность редактирования, создания новых файлов с возможностью указания конкретного формата для сохранения файла
- Расширение списка поддерживаемых форматов файлов
P.S. Хотя библиотека еще достаточно сыровата, ее можно уже использовать для весьма тривиальных задач, например, чтения, предпросмотра документов на клиенте перед отправкой на сервер.
Это мой первый пост, так что не пинайте сильно. Буду рад конструктивным предложениям и пожеланиям в комментариях.
P.P.S. Спасибо большое хабраюзеру aleks_raiden за размещение демки
После выбора файла следует немного подождать, т.к. визуализировать процесс обработки просто не успел :)
Надстройка Word взаимодействует с объектами в Word с помощью API JavaScript для Office, включающего две указанных ниже объектных модели JavaScript.
API JavaScript для Word — это API конкретных приложений для Word. Впервые представленный в Office 2016, API JavaScript для Word предоставляет строго типизированные объекты, которые можно использовать для доступа к объектам и метаданным в документе Word.
Общие API. Появившиеся в Office 2013 общие API можно использовать для доступа к таким компонентам, как пользовательский интерфейс, диалоговые окна и параметры клиентов, общие для нескольких типов приложений Office.
В этом разделе документации основное внимание уделяется интерфейсу API JavaScript для Word, который используется для разработки большинства функций надстройки, ориентированных на Word в Интернете или Word 2016 и более поздние версии. Сведения об общем API см. в статье об общей объектной модели API JavaScript.
Сведения о понятиях, связанных с программированием
Сведения о важных понятиях программирования см. в статье Объектная модель JavaScript для Word в надстройках Office.
Сведения о возможностях API
Используйте другие статьи в этом разделе, чтобы узнать, как получить весь документ из надстройки, воспользоваться параметрами поиска, чтобы найти текст в надстройке Word, и т. д. Полный список доступных статей см. в оглавлении.
Чтобы получить практический опыт доступа к объектам в Word с помощью API JavaScript для Word, выполните инструкции из руководства по надстройкам Word.
Дополнительные сведения об объектной модели API JavaScript для Word см. в справочной документации по API JavaScript для Word.
Опробуйте примеры кода в Script Lab
Используйте Script Lab, чтобы быстро начать работу с коллекцией встроенных примеров, демонстрирующих выполнение задач с помощью API. Вы можете выполнять примеры в Script Lab, чтобы сразу увидеть результат в области задач или документе, изучать примеры, чтобы понять принципы действия API, и даже использовать примеры для создания собственных надстроек.
В этой статье описаны основные концепции использования API JavaScript для Word с целью создания надстроек.
Сведения об асинхронном типе API-интерфейсов Word и принципах их работы с документами см. в статье Использование модели API, зависящей от приложения.
API-интерфейсы Office.js для Word
Надстройка Word взаимодействует с объектами в Word с помощью API JavaScript для Office. Сюда относятся две объектные модели JavaScript:
API JavaScript для Word. API-интерфейс JavaScript для Word предоставляет строго типизированные объекты, подходящие для документов, диапазонов, таблиц, списков, форматирования и т. д.
Общие API-интерфейсы. Общий API предоставляет доступ к таким компонентам, как пользовательский интерфейс, диалоговые окна и параметры клиентов, общие для разных приложений Office.
Скорее всего, вы будете разрабатывать большую часть функций надстроек для Word с помощью API JavaScript для Word, но вам также потребуются объекты из общего API. Например:
-
. Объект Context представляет среду выполнения надстройки и предоставляет доступ к ключевым объектам API. Он состоит из данных о конфигурации, например contentLanguage и officeTheme , а также предоставляет сведения о среде выполнения надстройки, например host и platform . Кроме того, он предоставляет метод requirements.isSetSupported() , с помощью которого можно проверить, поддерживается ли указанный набор обязательных элементов приложением Word, в котором запускается надстройка. . Объект Office.Document предоставляет метод getFileAsync() , позволяющий загрузить файл Word, в котором работает надстройка. Это выполняется отдельно от объекта Word.Document.
Объектная модель для Word
Чтобы понять API-интерфейсы Word, нужно понимать, как компоненты документа связаны друг с другом.
В этой статье мы создадим приложение, которое позволит пользователям вводить свой данные в текстовом редакторе и генерировать из него документ Word. Мы будем использовать Express для внутреннего интерфейса и React для внешнего интерфейса.
Мы начнем с серверной части. Для начала мы создадим папку проекта с папкой backend внутри. Затем в папке backend запустите, npx express-generator чтобы создать приложение Express. Затем запустите npm i для установки пакетов. Далее мы устанавливаем наши собственные пакеты. Нам нужен Babel для запуска приложения с последней версией JavaScript, CORS для междоменных запросов, HTML-DOCX-JS для преобразования строк HTML в документы Word, Multer для загрузки файлов, Sequelize для ORM и SQLite3 для нашей базы данных.
Мы устанавливаем все это, выполнив:
После этого мы изменим package.json чтобы добавить команды start и babel-node :
Таким образом мы запускаем наше приложение с Babel вместо обычной среды выполнения Node.
Затем создайте файл .babelrc в папке backend и добавьте:
чтобы указать, что мы запускаем наше приложение с последней версией JavaScript.
Далее мы добавляем код нашей базы данных. Запустите npx sequelize-cli init в папке backend , чтобы создать код Sequelize.
В config.js добавьте:
Затем создайте нашу модель и выполните миграцию, запустив:
создать модель Document и таблицу Documents .
Затем мы запускаем:
Далее мы создаем наши маршруты. Создайте файл document.js в папке routes и добавьте:
Мы выполняем стандартные операции CRUD для таблицы Documents в первых 4 маршрутах. У нас есть GET для получения всех Documents , POST для создания Document , PUT для обновления Document по ID, DELETE для удаления Document путем поиска по ID. У нас есть HTML в поле document для создания документа Word позже.
Маршрут generate для создания документа Word. Мы получаем идентификатор из URL, а затем используем пакет HTML-DOCX-JS для создания документа Word. Мы генерируем документ Word путем преобразования документа HTML в объект файлового потока с помощью пакета HTML-DOCX-JS, а затем записываем поток в файл и сохраняем путь к файлу в Document с идентификатором в параметре URL.
У нас также есть маршрут uploadImage , позволяющий пользователю загружать изображения с помощью CKEditor с помощью плагина CKFinder. Плагин ожидает uploaded и url в ответе, поэтому мы возвращаем их.
Затем нам нужно добавить папку files в backend .
Далее в app.js мы заменим существующий код на:
Мы открываем папку с файлом:
и устанавливаем маршрут document с помощью:
Теперь наше API готово, мы можем перейти к работе с интерфейсом. Создайте приложение React с помощью команды «Create React App». Запускаем npx create-react-app frontend в корневой папке проекта.
Установите все пакеты, запустив:
После установки пакетов мы можем заменить существующий код в App.js на:
добавить наш верхний бар и маршрут к домашней странице.
В App.css , мы заменим существующий код на:
Далее мы создаем форму для добавления и редактирования документов. Создайте файл DocumentForm.js в src и добавьте:
Мы обертываем нашу React Bootstrap Form в компоненту Formik , чтобы получить функцию обработки формы от Formik, которую мы используем непосредственно в полях формы React Bootstrap. Мы не можем сделать то же самое с CKEditor, поэтому мы пишем свои собственные обработчики форм для редактора форматированного текста. Мы устанавливаем data в, CKEditor чтобы установить значение ввода редактора форматированного текста. Эта функция onInit используется, когда пользователи пытаются редактировать существующий документ, поскольку мы должны установить параметр data с помощью редактора, который инициализируется при запуске setContent(doc.document); . Метод onChange является функция обработчика для установки content всякий раз, когда он обновляется, так что параметр data будет иметь последнее значение, которое мы будем представлять, когда пользователь нажимает кнопку Сохранить.
Мы используем плагин CKFinder для загрузки изображений. Чтобы это работало, мы устанавливаем URL загрузки изображения на URL маршрута загрузки в нашем бэкэнде.
Схема проверки формы предоставляется объектом Yup schema , который мы создаем в верхней части кода. Мы проверяем, заполнено ли поле name .
Функция handleSubmit предназначена для обработки представления данных в заднюю часть. Мы проверяем оба объекта content и evt , чтобы проверить оба поля, поскольку мы не можем включить обработчики форм Formik непосредственно в CKEditor компонент.
Если все верно, то мы добавляем новый документ или обновляем его в зависимости от того, является ли реквизит верным или нет.
Затем, когда сохранение getAllDocuments прошло успешно, мы вызываем, чтобы заполнить последние документы в нашем хранилище MobX, запустив documentStore.setDocuments(response.data); .
Далее мы делаем нашу домашнюю страницу, создав HomePage.js в папке src и добавив:
У нас есть таблица React Bootstrap для перечисления документов с кнопками для редактирования, удаления документов и создания документа Word. Кроме того, в каждой строке есть ссылка Open для открытия документа Word. У нас есть кнопка создания в верхней части таблицы.
Когда страница загружается, мы вызываем getAllDocuments и заполняем их в хранилище MobX.
Далее создайте request.js в папке src и добавьте:
Добавив функции для отправки запросов к нашим маршрутам в серверной части.
Затем мы создаем наше хранилище MobX. Создайте store.js в папке src и добавьте:
Мы имеем функцию, setDocuments чтобы поместить данные в хранилище, который мы использовали в HomePage и DocumentForm и мы инстанцировали его перед экспортом , так что мы должны сделать это только в одном месте.
обозначает массив documents в DocumentStore в качестве объекта, который может отслеживаться компонентами на предмет изменений. setDocuments обозначается как функция , которая может быть использована для установки массива documents в хранилище.
Затем мы создаем верхнюю панель, создав файл TopBar.js в папке src и добавив:
Это содержит Reac Bootstrap Navbar чтобы показать верхнюю панель со ссылкой на главную страницу и имя приложения. Мы показываем ее только если существует token . Также мы проверяем pathname чтобы выделить правильные ссылки, установив параметр active .
Далее в index.html мы заменим существующий код на:
После написания всего этого кода мы можем запустить наше приложение. Прежде чем что-либо запускать, установите nodemon , запустив, npm i -g nodemon чтобы нам не приходилось перезагружать сервер при изменении файлов.
Затем запустите back end, запустив команду npm start в папке backend и npm start в папке frontend , затем выберите «yes», если вас попросят запустить его с другого порта.
Читайте также: