Path: blob/master/src/packages/frontend/editors/slate/element-to-markdown.ts
1691 views
/*1* This file is part of CoCalc: Copyright © 2020 Sagemath, Inc.2* License: MS-RSL – see LICENSE.md for details3*/45import { Element } from "slate";6import { Info, serialize } from "./slate-to-markdown";7import { getChildInfoHook, getSlateToMarkdown } from "./elements";8import stringify from "json-stable-stringify";910export interface ChildInfo extends Info {11// Child info is like info, but we all any other property -- see12// https://stackoverflow.com/questions/33836671/typescript-interface-that-allows-other-properties13// We want this since the getChildInfoHook conveys info to children14// by setting arbitrary fields of this Info object.15[field: string]: any;16}1718export function serializeElement(node: Element, info: Info): string {19if (!Element.isElement(node)) {20// make typescript happier.21throw Error("BUG -- serializeElement takes an element as input");22}2324if (25info.noCache === undefined ||26info.topLevel === undefined ||27!info.noCache.has(info.topLevel)28) {29const cachedMarkdown = info.cache?.[stringify(node)!];30if (cachedMarkdown != null) {31return cachedMarkdown;32}33}3435const childInfo = {36...info,37...{ parent: node },38} as ChildInfo;3940const childInfoHook = getChildInfoHook(node["type"]);41if (childInfoHook != null) {42childInfoHook({ node, childInfo });43}44const v: string[] = [];45for (let index = 0; index < node.children.length; index++) {46v.push(47serialize(node.children[index], {48...childInfo,49...{ index, lastChild: index == node.children.length - 1 },50})51);52}5354let children = v.join("");55const slateToMarkdown = getSlateToMarkdown(node["type"]);56const md = slateToMarkdown({ node, children, info, childInfo });57const hook = info.hook?.(node);58if (hook !== undefined) {59return hook(md);60}61return md;62}636465