From 82af1e1b27cb7f4fa0fd302c3460ecf2bcf14eb1 Mon Sep 17 00:00:00 2001
From: _Kerman <kermanx@qq.com>
Date: Sat, 13 Jul 2024 18:09:58 +0800
Subject: [PATCH] feat: allow Mermaid setup function to be async (#1741)

---
 packages/client/modules/mermaid.ts |  2 +-
 packages/client/setup/mermaid.ts   | 10 +++++-----
 packages/types/src/setups.ts       |  6 ++----
 3 files changed, 8 insertions(+), 10 deletions(-)

diff --git a/packages/client/modules/mermaid.ts b/packages/client/modules/mermaid.ts
index 33a6bee790..a59dafa249 100644
--- a/packages/client/modules/mermaid.ts
+++ b/packages/client/modules/mermaid.ts
@@ -19,7 +19,7 @@ export async function renderMermaid(lzEncoded: string, options: any) {
 
   mermaid.initialize({
     startOnLoad: false,
-    ...clearUndefined(setupMermaid() || {}),
+    ...clearUndefined(await setupMermaid() || {}),
     ...clearUndefined(options),
   })
   const code = lz.decompressFromBase64(lzEncoded)
diff --git a/packages/client/setup/mermaid.ts b/packages/client/setup/mermaid.ts
index 01e914894a..48d22fc22d 100644
--- a/packages/client/setup/mermaid.ts
+++ b/packages/client/setup/mermaid.ts
@@ -1,14 +1,14 @@
-import type { MermaidOptions } from '@slidev/types'
-import { defineMermaidSetup } from '@slidev/types'
+import type { MermaidConfig } from 'mermaid'
+import { createSingletonPromise } from '@antfu/utils'
 import setups from '#slidev/setups/mermaid'
 
-export default defineMermaidSetup(() => {
-  const setupReturn: MermaidOptions = {
+export default createSingletonPromise(async () => {
+  const setupReturn: MermaidConfig = {
     theme: 'default',
   }
 
   for (const setup of setups)
-    Object.assign(setupReturn, setup())
+    Object.assign(setupReturn, await setup())
 
   return setupReturn
 })
diff --git a/packages/types/src/setups.ts b/packages/types/src/setups.ts
index 64a8ffc0b5..6e46dd5d45 100644
--- a/packages/types/src/setups.ts
+++ b/packages/types/src/setups.ts
@@ -2,10 +2,10 @@ import type { Awaitable } from '@antfu/utils'
 import type * as monaco from 'monaco-editor'
 import type { App, ComputedRef, Ref } from 'vue'
 import type { RouteRecordRaw, Router } from 'vue-router'
-import type mermaid from 'mermaid'
 import type { KatexOptions } from 'katex'
 import type { BuiltinLanguage, BuiltinTheme, CodeOptionsMeta, CodeOptionsThemes, CodeToHastOptionsCommon, Highlighter, LanguageInput } from 'shiki'
 import type { VitePluginConfig as UnoCssConfig } from 'unocss/vite'
+import type { MermaidConfig } from 'mermaid'
 import type { SlidevPreparserExtension } from './types'
 import type { CodeRunnerProviders } from './code-runner'
 import type { ContextMenuItem } from './context-menu'
@@ -19,8 +19,6 @@ export interface MonacoSetupReturn {
   editorOptions?: monaco.editor.IEditorOptions
 }
 
-export type MermaidOptions = (typeof mermaid.initialize) extends (a: infer A) => any ? A : never
-
 export interface NavOperations {
   next: () => void
   prev: () => Promise<void>
@@ -78,7 +76,7 @@ export type MonacoSetup = (m: typeof monaco) => Awaitable<MonacoSetupReturn | vo
 export type AppSetup = (context: AppContext) => Awaitable<void>
 export type RootSetup = () => Awaitable<void>
 export type RoutesSetup = (routes: RouteRecordRaw[]) => RouteRecordRaw[]
-export type MermaidSetup = () => Partial<MermaidOptions> | void
+export type MermaidSetup = () => Awaitable<Partial<MermaidConfig> | void>
 export type ShortcutsSetup = (nav: NavOperations, defaultShortcuts: ShortcutOptions[]) => Array<ShortcutOptions>
 export type CodeRunnersSetup = (runners: CodeRunnerProviders) => Awaitable<CodeRunnerProviders | void>
 export type ContextMenuSetup = (items: ComputedRef<ContextMenuItem[]>) => ComputedRef<ContextMenuItem[]>