Микрофронтенд
Теперь, когда микросервис DDG создан, давайте подключим два более практичных микрофронтенда, которые часто встречаются в системах, работающих с HTML-вводом:
-
Наш пользователь пишет markdown, ему нужен HTML.
-
Наш пользователь пишет HTML, ему нужен markdown.
Мы можем вытащить пакеты из npm в браузер для поддержки этого. Это сделает Алекса Рассела 😿, но мы удовлетворим ваши требования. Почему он должен 😢? Ну, возможно, если бы у нас под рукой (и в кошельках) была потрясающая архитектура микрофронтенда, но мы все равно решили бы отправлять большие пакеты JS по проводам.
Если кратко изложить суть проблемы, то мы собираемся:
-
загрузить большой пакет NPM только для того, чтобы удовлетворить требование функции, которая не имеет возможности повторного использования
-
разворот — 7,8 КБ
-
markdown-it — 30KB.
Это 37.8KB для функциональности, которую пользователь может выбрать в лучшем случае, в худшем — вы уже принимаете такие решения, как будто они отбрасываются, так что это 37.8KB в океане мегабайтов.
Мы могли бы лениво загружать (и мы делаем это со всякой всячиной, чтобы обмануть KB метрики в наших собственных материалах), однако, лучшая полезная нагрузка JS — это полезная нагрузка, не отправленная вообще. Так что давайте воспользуемся полезностью быстрого решения сложной проблемы с помощью пакетов NPM, но применим это к нашему подходу микрофронтенда.
Пример общего пользовательского ввода
-
Демо
-
Код в демо
-
Микрокод из MD в HTML
-
Микрокод из HTML в MD
Я уже успешно использовал оба этих кода в проектах node, поэтому решил попробовать и здесь. Код хорошо читается для каждого из них, используя подходы, изученные в примере DDG, и поэтому процесс взятия вещей и превращения их в микрокод пролетает незаметно:
-
есть идея функциональности, которую, кажется, можно решить одним пакетом NPM
-
гуглим, ищем достойные отзывы / примеры
-
создание файла nameOfTheFunctionToPerform[.]js
-
скопировать и обновить вызов
MicroFrontendRegistry.add()
-
вставьте шаблон, подключите экзамен из пакета npm
-
обновить package.json
-
yarn install && yarn start
и в новом терминалеvercel dev
-
await MicroFrontendRegistry.call("@whatever/newFunction")
htmlToMd
import { stdPostBody, stdResponse, invalidRequest } from "../../../../utilities/requestHelpers.js";
import fetch from "node-fetch";
import * as df from 'turndown';
const TurndownService = df.default;
var turndownService = new TurndownService();
export default async function handler(req, res) {
const body = stdPostBody(req);
if (body === null) {
res = invalidRequest(res, 'missing body');
}
else if (!body.html) {
res = invalidRequest(res, 'missing `html` param');
}
else {
var html = body.html;
// md is actually a link reference so fetch it 1st
if (body.type === 'link' && html) {
html = await fetch(html.trim()).then((d) => d.ok ? d.text(): '');
}
stdResponse(res, await turndownService.turndown(html), {cache: 180 });
}
}
mdToHtml
import { stdPostBody, stdResponse, invalidRequest } from "../../../../utilities/requestHelpers.js";
import fetch from "node-fetch";
import * as df from 'markdown-it';
const MarkdownIt = df.default;
const mdClass = new MarkdownIt();
export default async function handler(req, res) {
const body = stdPostBody(req);
if (body === null) {
res = invalidRequest(res, 'missing body');
}
else if (!body.md) {
res = invalidRequest(res, 'missing `md` param');
}
else {
var md = body.md;
// md is actually a link reference so fetch it 1st
if (body.type === 'link' && md) {
md = await fetch(md.trim()).then((d) => d.ok ? d.text(): '');
}
stdResponse(res, await mdClass.render(md), {cache: 180 });
}
}
Как вы можете видеть, обе эти функции очень похожи на пример DDG и еще больше похожи друг на друга, поскольку одна является копией и модификацией другой.
Оба принимают строку содержимого html или md и оба имеют дополнительный флаг link
. Опция link
позволяет удаленно загружать HTML или MD через fetch()
. Хотя fetch
теперь является частью Node v18+, наши микросистемы Vercel работают под управлением V16, поэтому мы все еще включаем пакет node-fetch.
Фактическая реализация в HAX
Итак, хотя демонстрация выше иллюстрирует возможности, это явно не реализация в производственном стиле. А вот это — да. Вот как мы реализовали обе конечные точки в HAX, нашем веб-редакторе на основе компонентов для богатых медиа и устойчивого самовыражения.
В следующей версии HAX мы поддерживаем загрузку текущей страницы в формате markdown. Таким образом, HAX получает страницу, конвертирует ее в HTML, отправляет в конечную точку, а конечная точка отправляет обратно MD.
Мы также теперь поддерживаем импорт уценки в тело контента в HAX. Поскольку HAX основан на веб-компонентах, он ориентирован на HTML. Поэтому, чтобы использовать MD из источника, нам нужно преобразовать его в соответствующий HTML. Теперь все достаточно просто: просто прочитайте файл, возьмите его содержимое и отправьте его в конечную точку в виде MD, получите обратно HTML, импортируйте его в содержимое страницы.
Видео, показывающее все это вместе
Теперь та часть, где я смеюсь над своими очками и рассказываю, как все части собираются вместе.
Часть первая
Определение требований и демонстрация их в контексте, а также в отдельной демонстрации
Часть вторая
Глубокое погружение в код и демонстрация того, как он подключен к HAX для рассматриваемых требований.