@tiptap/cli 3.3.7 → 3.3.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +21 -20
- package/dist/index.js.map +1 -1
- package/package.json +4 -4
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/commands/add.ts","../src/inquirer/select.ts","../src/preflights/preflight-add.ts","../src/utils/get-config.ts","../src/utils/resolve-import.ts","../src/utils/get-project-info.ts","../src/utils/frameworks.ts","../src/utils/get-package-info.ts","../src/utils/colors.ts","../src/utils/logger.ts","../src/utils/add-components.ts","../src/utils/handle-error.ts","../src/utils/registry/schema.ts","../src/utils/registry/index.ts","../src/utils/token-storage.ts","../src/utils/bootstrap.ts","../src/utils/spinner.ts","../src/utils/get-package-manager.ts","../src/utils/updaters/update-dependencies.ts","../src/utils/updaters/update-files.ts","../src/utils/transformers/index.ts","../src/utils/transformers/transform-import.ts","../src/utils/transformers/transform-jsx.ts","../src/utils/transformers/transform-rsc.ts","../src/utils/transformers/transform-remove-components.ts","../src/utils/transformers/transform-scss-to-css.ts","../src/utils/updaters/update-dev-dependencies.ts","../src/utils/common.ts","../src/utils/auth.ts","../src/utils/package-manager-config.ts","../src/commands/auth.ts","../src/utils/auth-check.ts","../src/utils/cli-ui.ts","../src/utils/prompt-messages.ts","../src/commands/info.ts","../src/commands/init.ts","../src/preflights/preflight-init.ts","../src/utils/create-project.ts","../src/index.ts","../package.json"],"sourcesContent":["import path from \"path\"\nimport { Command } from \"commander\"\nimport { z } from \"zod\"\nimport select from \"@/src/inquirer/select\"\nimport { Separator, input, confirm, checkbox } from \"@inquirer/prompts\"\nimport { preFlightAdd } from \"@/src/preflights/preflight-add\"\nimport { addComponents } from \"@/src/utils/add-components\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { getRegistryIndex } from \"@/src/utils/registry\"\nimport { colors } from \"@/src/utils/colors\"\nimport type { RegistryItemIndexSchema } from \"@/src/utils/registry/schema\"\nimport { toReadableName } from \"@/src/utils/common\"\nimport { ensureAuthForPaidComponents } from \"../utils/auth-check\"\nimport { type Plan } from \"../utils/registry/schema\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport {\n showNotionTemplateSetupMessage,\n showStylesConfigurationMessage,\n} from \"@/src/utils/prompt-messages\"\nimport {\n createWelcomeBanner,\n logLines,\n createExplanationSection,\n clearTerminal,\n createSpacedDivider,\n} from \"@/src/utils/cli-ui\"\n\nexport const addOptionsSchema = z.object({\n components: z.array(z.string()).optional(),\n cwd: z.string(),\n path: z.string().optional(),\n silent: z.boolean(),\n overwrite: z.boolean(),\n})\n\ntype AddOptions = z.infer<typeof addOptionsSchema>\n\ninterface CategoryMap {\n templates: RegistryItemIndexSchema\n ui: RegistryItemIndexSchema\n primitives: RegistryItemIndexSchema\n uiUtils: RegistryItemIndexSchema\n nodes: RegistryItemIndexSchema\n}\n\nconst PROMPT_PAGE_SIZE = 1_000 // Large size to avoid help tip\n\nconst UI = {\n emptyRegistry: colors.red(\"❌ No components or templates found\"),\n operationCancelled: colors.gray(\"Operation cancelled\"),\n missingDirectory: colors.red(\n \"❌ Directory not found. Use init to initialize a project first.\"\n ),\n}\n\nconst PROMPT_THEME = {\n icon: {\n cursor: colors.cyan(\"▸\"),\n checked: colors.cyan(\"◉\"),\n unchecked: \"○\",\n },\n style: {\n highlight: (text: string) => colors.cyan(text),\n message: (text: string) => text,\n answer: (text: string) => \"\", // Hide inline answer display\n },\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: colors.cyan(\"?\"),\n },\n}\n\n/**\n * Creates a themed confirmation prompt with consistent styling\n */\nconst createThemedConfirm = (message: string, defaultValue: boolean = true) => {\n return confirm({\n message,\n default: defaultValue,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Filters templates to only include free ones based on registry data\n */\nfunction filterFreeTemplates(\n templates: RegistryItemIndexSchema,\n freeComponents: string[] | null\n): RegistryItemIndexSchema {\n if (!freeComponents) {\n return templates\n }\n\n return templates.filter((template) => freeComponents.includes(template.name))\n}\n\n/**\n * Clears specified number of lines from console\n */\nfunction clearPromptLines(lines: number) {\n for (let i = 0; i < lines; i++) {\n process.stdout.write(\"\\x1B[1A\") // Move cursor up\n process.stdout.write(\"\\x1B[2K\") // Clear line\n }\n}\n\n/**\n * Categorizes registry items by type\n */\nconst categorizeRegistryItems = (\n registryIndex: RegistryItemIndexSchema\n): CategoryMap => {\n return {\n templates: registryIndex.filter(\n (entry) => entry.type === \"registry:template\"\n ),\n ui: registryIndex.filter((entry) => entry.type === \"registry:ui\"),\n primitives: registryIndex.filter(\n (entry) => entry.type === \"registry:ui-primitive\"\n ),\n uiUtils: registryIndex.filter(\n (entry) => entry.type === \"registry:ui-utils\"\n ),\n nodes: registryIndex.filter((entry) => entry.type === \"registry:node\"),\n }\n}\n\n/**\n * Prompts user to select between components and templates\n */\nasync function promptForInitialSelection(\n categories: CategoryMap,\n showDivider = true\n): Promise<\"components\" | \"templates\" | null> {\n const message = \"What would you like to integrate?\"\n\n const choices = []\n const isComponentEmpty =\n categories.ui.length === 0 && categories.nodes.length === 0\n const isTemplateEmpty = categories.templates.length === 0\n\n if (!isTemplateEmpty) {\n choices.push({\n name: \"Templates - Full editor applications\",\n value: \"templates\",\n })\n }\n\n if (!isComponentEmpty) {\n choices.push({\n name: \"UI Components - Individual editor building blocks\",\n value: \"components\",\n })\n }\n\n if (choices.length === 0) {\n logger.break()\n console.log(UI.emptyRegistry)\n return null\n }\n\n try {\n if (showDivider) {\n console.log(createSpacedDivider())\n }\n\n const selection = await select({\n message: colors.reset(message),\n pageSize: PROMPT_PAGE_SIZE,\n theme: PROMPT_THEME,\n choices,\n })\n\n if (showDivider) {\n console.log(createSpacedDivider())\n }\n\n return selection as \"templates\" | \"components\"\n } catch (error) {\n clearPromptLines(4)\n console.log(UI.operationCancelled)\n return null\n }\n}\n\n/**\n * Creates choices for component menu with appropriate sections\n */\nasync function createComponentChoices(\n categories: CategoryMap,\n components: string[] | null\n): Promise<Array<{ name: string; value: string } | Separator>> {\n const choices: Array<{ name: string; value: string } | Separator> = []\n\n if (!components) {\n return choices\n }\n\n const addCategorySection = (\n items: RegistryItemIndexSchema,\n title: string\n ) => {\n const filtertedItems = items.filter((item) =>\n components.includes(item.name)\n )\n\n if (filtertedItems.length > 0) {\n choices.push(new Separator(\"\"))\n choices.push(new Separator(colors.gray(` ${title}`)))\n\n filtertedItems.forEach((item) => {\n const planLabel =\n item.plans && item.plans.length\n ? item.plans.includes(\"light\")\n ? \"Open Source\"\n : \"Available from Start plan\"\n : \"Free\"\n\n const name = toReadableName(item.name)\n const paddedName = name.padEnd(35)\n\n choices.push({\n name: `${paddedName} ${colors.gray(planLabel)}`,\n value: item.name,\n })\n })\n\n choices.push(new Separator(\" \"))\n }\n }\n\n addCategorySection(categories.ui, \"UI COMPONENTS\")\n addCategorySection(categories.nodes, \"NODE COMPONENTS\")\n addCategorySection(categories.primitives, \"PRIMITIVES\")\n\n return choices\n}\n\n/**\n * Shows menu for selecting components\n */\nasync function componentMenu(\n categories: CategoryMap,\n components: string[] | null\n): Promise<string[]> {\n const choices = await createComponentChoices(categories, components)\n\n if (choices.length === 0) {\n return []\n }\n\n try {\n logger.log(\"\")\n logger.log(\n colors.gray(\" Use Space to select • A to toggle all • Enter to confirm\")\n )\n\n const selectedComponents = await checkbox({\n message: \"Choose UI components to install:\",\n pageSize: 20,\n choices,\n theme: PROMPT_THEME,\n })\n\n // Display selected components\n if (selectedComponents && selectedComponents.length > 0) {\n logger.log(\"\")\n logger.log(colors.cyan(\"Selected components:\"))\n selectedComponents.forEach((component) => {\n logger.log(` ${colors.cyan(\"•\")} ${toReadableName(component)}`)\n })\n }\n\n logger.log(\"\")\n return selectedComponents || []\n } catch (error) {\n clearPromptLines(25)\n console.log(UI.operationCancelled)\n return []\n }\n}\n\n/**\n * Shows menu for selecting templates\n */\nasync function templateMenu(\n templates: RegistryItemIndexSchema\n): Promise<string[]> {\n try {\n const choices = templates.map((template) => {\n const planLabel =\n template.plans && template.plans.length\n ? template.plans.includes(\"light\")\n ? \"Open Source\"\n : \"Available from Start plan\"\n : \"Free\"\n\n const name = toReadableName(template.name)\n const description = template.description\n ? ` - ${template.description}`\n : \"\"\n const nameWithDesc = `${name}${description}`\n const paddedNameWithDesc = nameWithDesc.padEnd(50)\n\n return {\n name: `${paddedNameWithDesc} ${colors.gray(planLabel)}`,\n value: template.name,\n }\n })\n\n logger.log(\"\")\n\n const selectedTemplate = await select({\n message: \"Choose an editor template to install:\",\n pageSize: 20,\n choices,\n theme: PROMPT_THEME,\n })\n\n // Display selected template\n if (selectedTemplate) {\n logger.log(\"\")\n logger.log(colors.cyan(\"Selected template:\"))\n logger.log(` ${colors.cyan(\"•\")} ${toReadableName(selectedTemplate)}`)\n }\n\n logger.log(\"\")\n return selectedTemplate ? [selectedTemplate] : []\n } catch (error) {\n clearPromptLines(25)\n console.log(UI.operationCancelled)\n return []\n }\n}\n\n/**\n * Main function to prompt for registry components\n */\nexport async function promptForRegistryComponents(\n options: AddOptions,\n showDivider = true\n): Promise<string[]> {\n if (options.components?.length) {\n return options.components\n }\n\n let registryIndex\n try {\n registryIndex = await getRegistryIndex()\n } catch (error) {\n // Check if this is a 401 authentication error\n if (\n error instanceof Error &&\n error.message.includes(\"You are not authorized\")\n ) {\n // Assume the component is paid and trigger authentication flow\n const isAuthenticated = await ensureAuthForPaidComponents(\n [{ name: \"unknown\", plans: [\"start\" as Plan] }], // Assume paid component\n options.cwd\n )\n\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with component selection.\"\n )\n return []\n }\n\n // Retry registry fetch after authentication\n try {\n registryIndex = await getRegistryIndex()\n } catch (retryError) {\n logger.break()\n handleError(\n new Error(\n \"[prompts] - Failed to fetch registry index after authentication.\"\n )\n )\n return []\n }\n } else {\n logger.break()\n handleError(error)\n return []\n }\n }\n\n if (!registryIndex) {\n logger.break()\n handleError(new Error(\"[prompts] - Failed to fetch registry index.\"))\n return []\n }\n\n const categories = categorizeRegistryItems(registryIndex)\n const selection = await promptForInitialSelection(categories, showDivider)\n\n if (!selection) {\n return []\n }\n\n const allComponents = registryIndex\n .filter((item) => {\n const hide = item.hide ?? false\n return !hide\n })\n .map((item) => item.name)\n\n switch (selection) {\n case \"components\":\n return (await componentMenu(categories, allComponents)) || []\n case \"templates\": {\n const filteredTemplates = filterFreeTemplates(\n categories.templates,\n allComponents\n )\n const templateResults = await templateMenu(filteredTemplates)\n return templateResults || []\n }\n default:\n return []\n }\n}\n\nexport const add = new Command()\n .name(\"add\")\n .description(\n \"add Tiptap UI components or templates as source code to your project\"\n )\n .argument(\"[components...]\", \"the components to add\")\n .option(\"-o, --overwrite\", \"overwrite existing files.\", false)\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .option(\"-p, --path <path>\", \"the path to add the component to.\")\n .option(\"-s, --silent\", \"mute output.\", false)\n .action(async (components, opts) => {\n try {\n // Clear terminal for a fresh start\n clearTerminal()\n\n // Show welcome banner\n const welcomeBanner = createWelcomeBanner(\n \"Tiptap UI Components\",\n \"Install UI components or templates as editable source code in your project\"\n )\n logLines(welcomeBanner)\n\n // Explain what Tiptap CLI does\n const explanation = createExplanationSection(\n \"What are Tiptap UI Components?\",\n [\n \"React UI components that help you develop an editor\",\n \"They install as source code (not npm packages) in your src/components/\",\n \"UI components are a foundation for customization rather than a fixed library\",\n ]\n )\n logLines(explanation)\n\n // Wait for user to press Enter\n await input({\n message: colors.reset(\n `Press ${colors.cyan(\"Enter\")} to add components or templates...`\n ),\n theme: {\n prefix: {\n done: \"\",\n idle: \"\",\n },\n },\n })\n\n // Add visual separation\n logger.log(\"\")\n logger.log(\"\")\n logger.log(\"\")\n\n const options = addOptionsSchema.parse({\n components,\n cwd: path.resolve(opts.cwd),\n ...opts,\n })\n\n if (!options.components?.length) {\n options.components = await promptForRegistryComponents(options)\n }\n\n // No components selected\n if (!options.components?.length) {\n return\n }\n\n const registryIndex = await getRegistryIndex()\n if (!registryIndex) {\n throw new Error(\"Failed to fetch registry index.\")\n }\n\n // Get details of selected components\n const selectedComponentDetails = options.components.map(\n (componentName) => {\n const componentInfo = registryIndex.find(\n (item) => item.name === componentName\n )\n return {\n name: componentName,\n plans: componentInfo?.plans || [],\n }\n }\n )\n\n const isAuthenticated = await ensureAuthForPaidComponents(\n selectedComponentDetails,\n options.cwd\n )\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with paid component download.\"\n )\n logger.log(\n \"You can try again with only free components, or authenticate first.\"\n )\n process.exit(1)\n }\n\n const { errors, config } = await preFlightAdd(options)\n\n if (errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT]) {\n logger.warn(`\\n${UI.missingDirectory}`)\n process.exit(0)\n }\n\n if (!config) {\n throw new Error(`Failed to read config at ${colors.cyan(options.cwd)}.`)\n }\n\n const created = await addComponents(options.components, config, options)\n\n // Show success message if components were added\n if (created && created.filesCreated.length > 0) {\n const containsNotion = created.filesCreated.some((path) =>\n path.includes(\"notion\")\n )\n const containsSimpleEditor = created.filesCreated.some(\n (path) => path.includes(\"simple\") && path.includes(\"editor\")\n )\n\n if (containsNotion) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Notion template installed - ${created.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show combined setup message for Notion template\n const projectInfo = await getProjectInfo(options.cwd)\n if (projectInfo) {\n showNotionTemplateSetupMessage(projectInfo.framework, config)\n }\n } else if (containsSimpleEditor) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Simple editor template installed - ${created.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration as required\n const projectInfo = await getProjectInfo(options.cwd)\n if (projectInfo) {\n showStylesConfigurationMessage(projectInfo.framework, config)\n }\n } else {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Components installed - ${created.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration if UI components were added\n const hasUIComponents = created.filesCreated.some(\n (path) =>\n path.includes(\"tiptap-templates\") || path.includes(\"tiptap-ui\")\n )\n\n if (hasUIComponents) {\n const projectInfo = await getProjectInfo(options.cwd)\n if (projectInfo) {\n showStylesConfigurationMessage(projectInfo.framework, config)\n }\n }\n }\n }\n } catch (error) {\n logger.break()\n handleError(error)\n }\n })\n","import {\n createPrompt,\n useState,\n useKeypress,\n usePrefix,\n usePagination,\n useRef,\n useMemo,\n useEffect,\n isBackspaceKey,\n isEnterKey,\n isUpKey,\n isDownKey,\n isNumberKey,\n Separator,\n ValidationError,\n makeTheme,\n type Theme,\n type Status,\n} from \"@inquirer/core\"\nimport type { PartialDeep } from \"@inquirer/type\"\nimport colors from \"yoctocolors-cjs\"\nimport figures from \"@inquirer/figures\"\nimport ansiEscapes from \"ansi-escapes\"\n\ntype SelectTheme = {\n icon: { cursor: string }\n style: {\n disabled: (text: string) => string\n description: (text: string) => string\n }\n indexMode: \"hidden\" | \"number\"\n}\n\nconst selectTheme: SelectTheme = {\n icon: { cursor: figures.pointer },\n style: {\n disabled: (text: string) => colors.dim(`- ${text}`),\n description: (text: string) => colors.cyan(text),\n },\n indexMode: \"hidden\",\n}\n\ntype Choice<Value> = {\n value: Value\n name?: string\n description?: string\n short?: string\n disabled?: boolean | string\n type?: never\n}\n\ntype NormalizedChoice<Value> = {\n value: Value\n name: string\n description?: string\n short: string\n disabled: boolean | string\n}\n\ntype SelectConfig<\n Value,\n ChoicesObject =\n | ReadonlyArray<string | Separator>\n | ReadonlyArray<Choice<Value> | Separator>,\n> = {\n message: string\n choices: ChoicesObject extends ReadonlyArray<string | Separator>\n ? ChoicesObject\n : ReadonlyArray<Choice<Value> | Separator>\n pageSize?: number\n loop?: boolean\n default?: unknown\n instructions?: string | boolean\n theme?: PartialDeep<Theme<SelectTheme>>\n}\n\nfunction isSelectable<Value>(\n item: NormalizedChoice<Value> | Separator\n): item is NormalizedChoice<Value> {\n return !Separator.isSeparator(item) && !item.disabled\n}\n\nfunction normalizeChoices<Value>(\n choices:\n | ReadonlyArray<string | Separator>\n | ReadonlyArray<Choice<Value> | Separator>\n): Array<NormalizedChoice<Value> | Separator> {\n return choices.map((choice) => {\n if (Separator.isSeparator(choice)) return choice\n\n if (typeof choice === \"string\") {\n return {\n value: choice as Value,\n name: choice,\n short: choice,\n disabled: false,\n }\n }\n\n const name = choice.name ?? String(choice.value)\n const normalizedChoice: NormalizedChoice<Value> = {\n value: choice.value,\n name,\n short: choice.short ?? name,\n disabled: choice.disabled ?? false,\n }\n\n if (choice.description) {\n normalizedChoice.description = choice.description\n }\n\n return normalizedChoice\n })\n}\n\nexport default createPrompt(\n <Value>(config: SelectConfig<Value>, done: (value: Value) => void) => {\n const { loop = true, pageSize = 7, instructions } = config\n const firstRender = useRef(true)\n const theme = makeTheme<SelectTheme>(selectTheme, config.theme)\n const [status, setStatus] = useState<Status>(\"idle\")\n const prefix = usePrefix({ status, theme })\n const searchTimeoutRef = useRef<ReturnType<typeof setTimeout>>()\n const [showHelpTip, setShowHelpTip] = useState(true)\n\n const items = useMemo(\n () => normalizeChoices(config.choices),\n [config.choices]\n )\n\n const bounds = useMemo(() => {\n const first = items.findIndex(isSelectable)\n const last = items.findLastIndex(isSelectable)\n\n if (first === -1) {\n throw new ValidationError(\n \"[select prompt] No selectable choices. All choices are disabled.\"\n )\n }\n\n return { first, last }\n }, [items])\n\n const defaultItemIndex = useMemo(() => {\n if (!(\"default\" in config)) return -1\n return items.findIndex(\n (item) => isSelectable(item) && item.value === config.default\n )\n }, [config.default, items])\n\n const [active, setActive] = useState(\n defaultItemIndex === -1 ? bounds.first : defaultItemIndex\n )\n\n // Safe to assume the cursor position always point to a Choice.\n const selectedChoice = items[active] as NormalizedChoice<Value>\n\n useKeypress((key, rl) => {\n clearTimeout(searchTimeoutRef.current)\n setShowHelpTip(false)\n\n if (isEnterKey(key)) {\n setStatus(\"done\")\n done(selectedChoice.value)\n } else if (isUpKey(key) || isDownKey(key)) {\n rl.clearLine(0)\n if (\n loop ||\n (isUpKey(key) && active !== bounds.first) ||\n (isDownKey(key) && active !== bounds.last)\n ) {\n const offset = isUpKey(key) ? -1 : 1\n let next = active\n do {\n next = (next + offset + items.length) % items.length\n } while (!isSelectable(items[next]!))\n setActive(next)\n }\n } else if (isNumberKey(key) && !Number.isNaN(Number(rl.line))) {\n const position = Number(rl.line) - 1\n const item = items[position]\n if (item != null && isSelectable(item)) {\n setActive(position)\n }\n\n searchTimeoutRef.current = setTimeout(() => {\n rl.clearLine(0)\n }, 700)\n } else if (isBackspaceKey(key)) {\n rl.clearLine(0)\n } else {\n // Default to search\n const searchTerm = rl.line.toLowerCase()\n const matchIndex = items.findIndex((item) => {\n if (Separator.isSeparator(item) || !isSelectable(item)) return false\n\n return item.name.toLowerCase().startsWith(searchTerm)\n })\n\n if (matchIndex !== -1) {\n setActive(matchIndex)\n }\n\n searchTimeoutRef.current = setTimeout(() => {\n rl.clearLine(0)\n }, 700)\n }\n })\n\n useEffect(\n () => () => {\n clearTimeout(searchTimeoutRef.current)\n },\n []\n )\n\n const message = theme.style.message(config.message, status)\n\n let helpTipTop = \"\"\n let helpTipBottom = \"\"\n // Help text is now always hidden\n if (typeof instructions === \"string\") {\n helpTipTop = instructions\n }\n\n const page = usePagination({\n items,\n active,\n renderItem({ item, isActive, index }) {\n if (Separator.isSeparator(item)) {\n return ` ${item.separator}`\n }\n\n const indexLabel = theme.indexMode === \"number\" ? `${index + 1}. ` : \"\"\n if (item.disabled) {\n const disabledLabel =\n typeof item.disabled === \"string\" ? item.disabled : \"(disabled)\"\n return theme.style.disabled(\n `${indexLabel}${item.name} ${disabledLabel}`\n )\n }\n\n const color = isActive ? theme.style.highlight : (x: string) => x\n const cursor = isActive ? theme.icon.cursor : ` `\n return color(`${cursor} ${indexLabel}${item.name}`)\n },\n pageSize,\n loop,\n })\n\n if (status === \"done\") {\n return `${prefix} ${message} ${theme.style.answer(selectedChoice.short)}`\n }\n\n const choiceDescription = selectedChoice.description\n ? `\\n${theme.style.description(selectedChoice.description)}`\n : ``\n\n return `${[prefix, message, helpTipTop].filter(Boolean).join(\" \")}\\n${page}${helpTipBottom}${choiceDescription}${ansiEscapes.cursorHide}`\n }\n)\n\nexport { Separator } from \"@inquirer/core\"\n","import path from \"path\"\nimport { addOptionsSchema } from \"@/src/commands/add\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { getConfig } from \"@/src/utils/get-config\"\nimport { logger } from \"@/src/utils/logger\"\nimport fs from \"fs-extra\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport async function preFlightAdd(options: z.infer<typeof addOptionsSchema>) {\n const errors: Record<string, boolean> = {}\n\n if (\n !fs.existsSync(options.cwd) ||\n !fs.existsSync(path.resolve(options.cwd, \"package.json\"))\n ) {\n errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT] = true\n return {\n errors,\n config: null,\n }\n }\n\n try {\n const config = await getConfig(options.cwd)\n\n return {\n errors,\n config: config!,\n }\n } catch (error) {\n console.log(\"[preFlightAdd] - \", error)\n\n logger.break()\n logger.error(\n `Make sure you are in a valid project directory. Run ${colors.cyan(\n \"npx @tiptap/cli init\"\n )} to create a new project.`\n )\n logger.break()\n process.exit(0)\n }\n}\n","import path from \"path\"\nimport { resolveImport } from \"@/src/utils/resolve-import\"\nimport { cosmiconfig } from \"cosmiconfig\"\nimport fg from \"fast-glob\"\nimport { loadConfig } from \"tsconfig-paths\"\nimport { z } from \"zod\"\nimport { getProjectInfo } from \"./get-project-info\"\n\nexport const DEFAULT_COMPONENTS = \"@/components\"\nexport const DEFAULT_CONTEXTS = \"@/contexts\"\nexport const DEFAULT_HOOKS = \"@/hooks\"\nexport const DEFAULT_TIPTAP_ICONS = \"@/components/tiptap-icons\"\nexport const DEFAULT_LIB = \"@/lib\"\nexport const DEFAULT_TIPTAP_EXTENSIONS = \"@/components/tiptap-extension\"\nexport const DEFAULT_TIPTAP_NODES = \"@/components/tiptap-node\"\nexport const DEFAULT_TIPTAP_UI = \"@/components/tiptap-ui\"\nexport const DEFAULT_TIPTAP_UI_PRIMITIVES = \"@/components/tiptap-ui-primitive\"\nexport const DEFAULT_TIPTAP_UI_UTILS = \"@/components/tiptap-ui-utils\"\nexport const DEFAULT_STYLES = \"@/styles\"\n\nconst explorer = cosmiconfig(\"components\", {\n searchPlaces: [\"components.json\"],\n})\n\nexport const rawConfigSchema = z.object({\n rsc: z.coerce.boolean().default(false),\n tsx: z.coerce.boolean().default(true),\n aliases: z.object({\n components: z.string(),\n contexts: z.string().optional(),\n hooks: z.string().optional(),\n tiptapIcons: z.string().optional(),\n lib: z.string().optional(),\n tiptapExtensions: z.string().optional(),\n tiptapNodes: z.string().optional(),\n tiptapUi: z.string().optional(),\n tiptapUiPrimitives: z.string().optional(),\n tiptapUiUtils: z.string().optional(),\n styles: z.string().optional(),\n }),\n})\n\nexport const configSchema = rawConfigSchema.extend({\n resolvedPaths: z.object({\n cwd: z.string(),\n components: z.string(),\n contexts: z.string(),\n hooks: z.string(),\n tiptapIcons: z.string(),\n lib: z.string(),\n tiptapExtensions: z.string(),\n tiptapNodes: z.string(),\n tiptapUi: z.string(),\n tiptapUiPrimitives: z.string(),\n tiptapUiUtils: z.string(),\n styles: z.string(),\n }),\n})\n\nexport const workspaceConfigSchema = z.record(configSchema)\n\nexport type RawConfig = z.infer<typeof rawConfigSchema>\n\nexport type Config = z.infer<typeof configSchema>\n\nexport async function getConfig(cwd: string) {\n const res = await explorer.search(cwd)\n const projectInfo = await getProjectInfo(cwd)\n\n const defaultAliases = {\n components: DEFAULT_COMPONENTS,\n contexts: DEFAULT_CONTEXTS,\n hooks: DEFAULT_HOOKS,\n tiptapIcons: DEFAULT_TIPTAP_ICONS,\n lib: DEFAULT_LIB,\n tiptapExtensions: DEFAULT_TIPTAP_EXTENSIONS,\n tiptapNodes: DEFAULT_TIPTAP_NODES,\n tiptapUi: DEFAULT_TIPTAP_UI,\n tiptapUiPrimitives: DEFAULT_TIPTAP_UI_PRIMITIVES,\n tiptapUiUtils: DEFAULT_TIPTAP_UI_UTILS,\n styles: DEFAULT_STYLES,\n }\n\n const applyAliasPrefix = (aliases: typeof defaultAliases, prefix: string) => {\n return Object.fromEntries(\n Object.entries(aliases).map(([key, value]) => [\n key,\n value.replace(/^@/, prefix),\n ])\n ) as typeof defaultAliases\n }\n\n let config: RawConfig\n\n if (!res) {\n let aliases = defaultAliases\n\n if (projectInfo?.aliasPrefix) {\n aliases = applyAliasPrefix(aliases, projectInfo.aliasPrefix)\n }\n\n config = rawConfigSchema.parse({\n rsc: projectInfo?.isRSC ?? false,\n tsx: projectInfo?.isTsx ?? true,\n aliases,\n })\n } else {\n const resolvedAliases = {\n ...defaultAliases,\n ...res.config.aliases,\n }\n\n if (projectInfo?.aliasPrefix) {\n config = rawConfigSchema.parse({\n ...res.config,\n aliases: applyAliasPrefix(resolvedAliases, projectInfo.aliasPrefix),\n })\n } else {\n config = rawConfigSchema.parse({\n ...res.config,\n aliases: resolvedAliases,\n })\n }\n }\n\n return await resolveConfigPaths(cwd, config)\n}\n\nexport async function resolveConfigPaths(cwd: string, config: RawConfig) {\n // Read tsconfig.json.\n const tsConfig = await loadConfig(cwd)\n\n if (tsConfig.resultType === \"failed\") {\n throw new Error(\n `Failed to load ${config.tsx ? \"tsconfig\" : \"jsconfig\"}.json. ${\n tsConfig.message ?? \"\"\n }`.trim()\n )\n }\n\n const schema = configSchema.parse({\n ...config,\n resolvedPaths: {\n cwd,\n components: await resolveImport(config.aliases.components, tsConfig),\n contexts: config.aliases.contexts\n ? await resolveImport(config.aliases.contexts, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"..\",\n \"contexts\"\n ),\n hooks: config.aliases.hooks\n ? await resolveImport(config.aliases.hooks, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"..\",\n \"hooks\"\n ),\n tiptapIcons: config.aliases.tiptapIcons\n ? await resolveImport(config.aliases.tiptapIcons, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-icons\"\n ),\n lib: config.aliases.lib\n ? await resolveImport(config.aliases.lib, tsConfig)\n : path.resolve(\n (await resolveImport(DEFAULT_LIB, tsConfig)) ?? cwd,\n \"..\"\n ),\n tiptapExtensions: config.aliases.tiptapExtensions\n ? await resolveImport(config.aliases.tiptapExtensions, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-extension\"\n ),\n tiptapNodes: config.aliases.tiptapNodes\n ? await resolveImport(config.aliases.tiptapNodes, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-node\"\n ),\n tiptapUi: config.aliases.tiptapUi\n ? await resolveImport(config.aliases.tiptapUi, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-ui\"\n ),\n tiptapUiPrimitives: config.aliases.tiptapUiPrimitives\n ? await resolveImport(config.aliases.tiptapUiPrimitives, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-ui-primitive\"\n ),\n tiptapUiUtils: config.aliases.tiptapUiUtils\n ? await resolveImport(config.aliases.tiptapUiUtils, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-ui-utils\"\n ),\n styles: config.aliases.styles\n ? await resolveImport(config.aliases.styles, tsConfig)\n : path.resolve(cwd, \"styles\"),\n },\n })\n\n return schema\n}\n\n// Note: we can check for -workspace.yaml or \"workspace\" in package.json.\n// Since cwd is not necessarily the root of the project.\n// We'll instead check if ui aliases resolve to a different root.\nexport async function getWorkspaceConfig(config: Config) {\n const resolvedAliases: Record<string, Config> = {}\n\n for (const key of Object.keys(config.aliases)) {\n if (!isAliasKey(key, config)) {\n continue\n }\n\n const resolvedPath = config.resolvedPaths[key]\n const packageRoot = await findPackageRoot(\n config.resolvedPaths.cwd,\n resolvedPath\n )\n\n if (!packageRoot) {\n resolvedAliases[key] = config\n continue\n }\n\n resolvedAliases[key] = await getConfig(packageRoot)\n }\n\n const result = workspaceConfigSchema.safeParse(resolvedAliases)\n if (!result.success) {\n return null\n }\n\n return result.data\n}\n\nexport async function findPackageRoot(cwd: string, resolvedPath: string) {\n const commonRoot = findCommonRoot(cwd, resolvedPath)\n const relativePath = path.relative(commonRoot, resolvedPath)\n\n const packageRoots = await fg.glob(\"**/package.json\", {\n cwd: commonRoot,\n deep: 3,\n ignore: [\"**/node_modules/**\", \"**/dist/**\", \"**/build/**\", \"**/public/**\"],\n })\n\n const matchingPackageRoot = packageRoots\n .map((pkgPath) => path.dirname(pkgPath))\n .find((pkgDir) => relativePath.startsWith(pkgDir))\n\n return matchingPackageRoot ? path.join(commonRoot, matchingPackageRoot) : null\n}\n\nfunction isAliasKey(\n key: string,\n config: Config\n): key is keyof Config[\"aliases\"] {\n return Object.keys(config.resolvedPaths).includes(key)\n}\n\nexport function findCommonRoot(cwd: string, resolvedPath: string) {\n const parts1 = cwd.split(path.sep)\n const parts2 = resolvedPath.split(path.sep)\n const commonParts = []\n\n for (let i = 0; i < Math.min(parts1.length, parts2.length); i++) {\n if (parts1[i] !== parts2[i]) {\n break\n }\n commonParts.push(parts1[i])\n }\n\n return commonParts.join(path.sep)\n}\n","import { createMatchPath, type ConfigLoaderSuccessResult } from \"tsconfig-paths\"\n\nexport async function resolveImport(\n importPath: string,\n config: Pick<ConfigLoaderSuccessResult, \"absoluteBaseUrl\" | \"paths\">\n) {\n return createMatchPath(config.absoluteBaseUrl, config.paths)(\n importPath,\n undefined,\n () => true,\n [\".ts\", \".tsx\"]\n )\n}\n","import path from \"path\"\nimport { FRAMEWORKS, Framework } from \"@/src/utils/frameworks\"\nimport { getPackageInfo } from \"@/src/utils/get-package-info\"\nimport fg from \"fast-glob\"\nimport fs from \"fs-extra\"\nimport { loadConfig } from \"tsconfig-paths\"\nimport {\n Config,\n RawConfig,\n getConfig,\n resolveConfigPaths,\n} from \"@/src/utils/get-config\"\n\nexport type ProjectInfo = {\n framework: Framework\n isSrcDir: boolean\n isRSC: boolean\n isTsx: boolean\n aliasPrefix: string | null\n}\n\nconst PROJECT_SHARED_IGNORE = [\n \"**/node_modules/**\",\n \".next\",\n \"public\",\n \"dist\",\n \"build\",\n]\n\nexport async function getProjectInfo(cwd: string): Promise<ProjectInfo | null> {\n const [configFiles, isSrcDir, isTsx, aliasPrefix, packageJson] =\n await Promise.all([\n fg.glob(\n \"**/{next,vite,astro,app}.config.*|gatsby-config.*|composer.json|react-router.config.*\",\n {\n cwd,\n deep: 3,\n ignore: PROJECT_SHARED_IGNORE,\n }\n ),\n fs.pathExists(path.resolve(cwd, \"src\")),\n isTypeScriptProject(cwd),\n getTsConfigAliasPrefix(cwd),\n getPackageInfo(cwd, false),\n ])\n\n const isUsingAppDir = await fs.pathExists(\n path.resolve(cwd, `${isSrcDir ? \"src/\" : \"\"}app`)\n )\n\n const type: ProjectInfo = {\n framework: FRAMEWORKS[\"manual\"],\n isSrcDir,\n isRSC: false,\n isTsx,\n aliasPrefix,\n }\n\n // Next.js.\n if (configFiles.find((file) => file.startsWith(\"next.config.\"))?.length) {\n type.framework = isUsingAppDir\n ? FRAMEWORKS[\"next-app\"]\n : FRAMEWORKS[\"next-pages\"]\n type.isRSC = isUsingAppDir\n return type\n }\n\n // Astro.\n if (configFiles.find((file) => file.startsWith(\"astro.config.\"))?.length) {\n type.framework = FRAMEWORKS[\"astro\"]\n return type\n }\n\n // Gatsby.\n // if (configFiles.find((file) => file.startsWith(\"gatsby-config.\"))?.length) {\n // type.framework = FRAMEWORKS[\"gatsby\"]\n // return type\n // }\n\n // Laravel.\n if (configFiles.find((file) => file.startsWith(\"composer.json\"))?.length) {\n type.framework = FRAMEWORKS[\"laravel\"]\n return type\n }\n\n // Remix.\n // if (\n // Object.keys(packageJson?.dependencies ?? {}).find((dep) =>\n // dep.startsWith(\"@remix-run/\")\n // )\n // ) {\n // type.framework = FRAMEWORKS[\"remix\"]\n // return type\n // }\n\n // TanStack Start.\n if (\n configFiles.find((file) => file.startsWith(\"app.config.\"))?.length &&\n [\n ...Object.keys(packageJson?.dependencies ?? {}),\n ...Object.keys(packageJson?.devDependencies ?? {}),\n ].find((dep) => dep.startsWith(\"@tanstack/start\"))\n ) {\n type.framework = FRAMEWORKS[\"tanstack-start\"]\n return type\n }\n\n // React Router.\n if (\n configFiles.find((file) => file.startsWith(\"react-router.config.\"))?.length\n ) {\n type.framework = FRAMEWORKS[\"react-router\"]\n return type\n }\n\n // Vite.\n // Some Remix templates also have a vite.config.* file.\n // We'll assume that it got caught by the Remix check above.\n if (configFiles.find((file) => file.startsWith(\"vite.config.\"))?.length) {\n type.framework = FRAMEWORKS[\"vite\"]\n return type\n }\n\n return type\n}\n\nexport async function getTsConfigAliasPrefix(cwd: string) {\n const tsConfig = await loadConfig(cwd)\n\n if (\n tsConfig?.resultType === \"failed\" ||\n !Object.entries(tsConfig?.paths).length\n ) {\n return null\n }\n\n // This assume that the first alias is the prefix.\n for (const [alias, paths] of Object.entries(tsConfig.paths)) {\n if (\n paths.includes(\"./*\") ||\n paths.includes(\"./src/*\") ||\n paths.includes(\"./app/*\") ||\n paths.includes(\"./resources/js/*\") // Laravel.\n ) {\n return alias.replace(/\\/\\*$/, \"\") ?? null\n }\n }\n\n // Use the first alias as the prefix.\n return Object.keys(tsConfig?.paths)?.[0].replace(/\\/\\*$/, \"\") ?? null\n}\n\nexport async function isTypeScriptProject(cwd: string) {\n const files = await fg.glob(\"tsconfig.*\", {\n cwd,\n deep: 1,\n ignore: PROJECT_SHARED_IGNORE,\n })\n\n return files.length > 0\n}\n\nexport async function getProjectConfig(\n cwd: string,\n defaultProjectInfo: ProjectInfo | null = null\n): Promise<Config | null> {\n const [existingConfig, projectInfo] = await Promise.all([\n getConfig(cwd),\n !defaultProjectInfo\n ? getProjectInfo(cwd)\n : Promise.resolve(defaultProjectInfo),\n ])\n\n if (existingConfig) {\n return existingConfig\n }\n\n if (!projectInfo) {\n return null\n }\n\n const config: RawConfig = {\n rsc: projectInfo.isRSC,\n tsx: projectInfo.isTsx,\n aliases: {\n components: `${projectInfo.aliasPrefix}/components`,\n contexts: `${projectInfo.aliasPrefix}/contexts`,\n hooks: `${projectInfo.aliasPrefix}/hooks`,\n tiptapIcons: `${projectInfo.aliasPrefix}/components/tiptap-icons`,\n lib: `${projectInfo.aliasPrefix}/lib`,\n tiptapExtensions: `${projectInfo.aliasPrefix}/components/tiptap-extensions`,\n tiptapNodes: `${projectInfo.aliasPrefix}/components/tiptap-nodes`,\n tiptapUi: `${projectInfo.aliasPrefix}/components/tiptap-ui`,\n tiptapUiPrimitives: `${projectInfo.aliasPrefix}/components/tiptap-ui-primitives`,\n tiptapUiUtils: `${projectInfo.aliasPrefix}/components/tiptap-ui-utils`,\n styles: `${projectInfo.aliasPrefix}/styles`,\n },\n }\n\n return await resolveConfigPaths(cwd, config)\n}\n","export const FRAMEWORKS = {\n \"next-app\": {\n name: \"next-app\",\n label: \"Next.js\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/next\",\n },\n },\n \"next-pages\": {\n name: \"next-pages\",\n label: \"Next.js\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/next\",\n },\n },\n // remix: {\n // name: \"remix\",\n // label: \"Remix\",\n // links: {\n // installation: \"https://tiptap.dev/docs/ui-components/install/remix\",\n // },\n // },\n \"react-router\": {\n name: \"react-router\",\n label: \"React Router\",\n links: {\n installation:\n \"https://tiptap.dev/docs/ui-components/install/react-router\",\n },\n },\n vite: {\n name: \"vite\",\n label: \"Vite\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/vite\",\n },\n },\n astro: {\n name: \"astro\",\n label: \"Astro\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/astro\",\n },\n },\n laravel: {\n name: \"laravel\",\n label: \"Laravel\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/laravel\",\n },\n },\n \"tanstack-start\": {\n name: \"tanstack-start\",\n label: \"TanStack Start\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/tanstack\",\n },\n },\n // gatsby: {\n // name: \"gatsby\",\n // label: \"Gatsby\",\n // links: {\n // installation: \"https://tiptap.dev/docs/ui-components/install/gatsby\",\n // },\n // },\n manual: {\n name: \"manual\",\n label: \"Manual\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/next\",\n },\n },\n} as const\n\nexport type Framework = (typeof FRAMEWORKS)[keyof typeof FRAMEWORKS]\n","import path from \"path\"\nimport fs from \"fs-extra\"\nimport { type PackageJson } from \"type-fest\"\n\nexport function getPackageInfo(\n cwd: string = \"\",\n shouldThrow: boolean = true\n): PackageJson | null {\n const packageJsonPath = path.join(cwd, \"package.json\")\n\n return fs.readJSONSync(packageJsonPath, {\n throws: shouldThrow,\n }) as PackageJson\n}\n","import chalk from \"chalk\"\n\nexport const colors = {\n cyan: chalk.cyan,\n magenta: chalk.magenta,\n gray: chalk.gray,\n white: chalk.white,\n yellow: chalk.yellow,\n green: chalk.green,\n red: chalk.red,\n blue: chalk.blue,\n reset: chalk.reset,\n}\n","import { colors } from \"@/src/utils/colors\"\n\nexport type Logger = {\n error: (...args: unknown[]) => void\n warn: (...args: unknown[]) => void\n info: (...args: unknown[]) => void\n success: (...args: unknown[]) => void\n log: (...args: unknown[]) => void\n break: () => void\n}\n\nconst join = (args: unknown[]) => args.map(String).join(\" \")\n\nexport const logger: Logger = {\n error(...args: unknown[]) {\n console.log(colors.red(join(args)))\n },\n warn(...args: unknown[]) {\n console.log(colors.yellow(join(args)))\n },\n info(...args: unknown[]) {\n console.log(colors.cyan(join(args)))\n },\n success(...args: unknown[]) {\n console.log(colors.green(join(args)))\n },\n log(...args: unknown[]) {\n console.log(join(args))\n },\n break() {\n console.log(\"\")\n },\n}\n","import path from \"path\"\nimport {\n configSchema,\n findCommonRoot,\n findPackageRoot,\n getWorkspaceConfig,\n workspaceConfigSchema,\n type Config,\n} from \"@/src/utils/get-config\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport {\n fetchRegistry,\n getRegistryParentMap,\n getRegistryTypeAliasMap,\n registryResolveItemsTree,\n resolveRegistryItems,\n} from \"@/src/utils/registry\"\nimport { registryItemSchema } from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { updateDependencies } from \"@/src/utils/updaters/update-dependencies\"\nimport { updateFiles } from \"@/src/utils/updaters/update-files\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\nimport { updateDevDependencies } from \"@/src/utils/updaters/update-dev-dependencies\"\n\nexport async function addComponents(\n components: string[],\n config: Config,\n options: {\n overwrite?: boolean\n silent?: boolean\n isNewProject?: boolean\n }\n) {\n options = {\n overwrite: false,\n silent: false,\n isNewProject: false,\n ...options,\n }\n\n const workspaceConfig = await getWorkspaceConfig(config)\n\n if (\n workspaceConfig &&\n workspaceConfig.tiptapUi &&\n workspaceConfig.tiptapUi.resolvedPaths.cwd !== config.resolvedPaths.cwd\n ) {\n return await addWorkspaceComponents(components, config, workspaceConfig, {\n ...options,\n })\n }\n\n return await addProjectComponents(components, config, options)\n}\n\nasync function addProjectComponents(\n components: string[],\n config: z.infer<typeof configSchema>,\n options: {\n overwrite?: boolean\n silent?: boolean\n isNewProject?: boolean\n }\n) {\n const registrySpinner = spinner(`Checking registry`, {\n silent: options.silent,\n }).start()\n const tree = await registryResolveItemsTree(components, config)\n if (!tree) {\n registrySpinner?.fail()\n return handleError(new Error(\"Failed to fetch components from registry\"))\n }\n\n registrySpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n\n await updateDependencies(tree.dependencies, config, {\n silent: options.silent,\n })\n\n await updateDevDependencies(tree.devDependencies, config, {\n silent: options.silent,\n })\n\n return await updateFiles(tree.files, config, {\n overwrite: options.overwrite,\n silent: options.silent,\n })\n}\n\nasync function addWorkspaceComponents(\n components: string[],\n config: z.infer<typeof configSchema>,\n workspaceConfig: z.infer<typeof workspaceConfigSchema>,\n options: {\n overwrite?: boolean\n silent?: boolean\n isNewProject?: boolean\n }\n) {\n const registrySpinner = spinner(`Checking registry`, {\n silent: options.silent,\n }).start()\n const registryItems = await resolveRegistryItems(components)\n const result = await fetchRegistry(registryItems)\n\n const payload = z.array(registryItemSchema).parse(result)\n if (!payload.length) {\n registrySpinner?.fail()\n return handleError(new Error(\"Failed to fetch components from registry\"))\n }\n registrySpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n\n const registryParentMap = getRegistryParentMap(payload)\n const registryTypeAliasMap = getRegistryTypeAliasMap()\n\n const filesCreated: string[] = []\n const filesUpdated: string[] = []\n const filesSkipped: string[] = []\n\n const rootSpinner = spinner(`Installing components`)?.start()\n\n for (const component of payload) {\n const alias = registryTypeAliasMap.get(component.type)\n const registryParent = registryParentMap.get(component.name)\n\n // We don't support this type of component.\n if (!alias) {\n continue\n }\n\n // A good start is ui for now.\n const targetConfig =\n component.type === \"registry:ui\" || registryParent?.type === \"registry:ui\"\n ? workspaceConfig.tiptapUi || config\n : config\n\n if (!targetConfig.resolvedPaths.tiptapUi) {\n continue\n }\n\n const workspaceRoot = findCommonRoot(\n config.resolvedPaths.cwd,\n targetConfig.resolvedPaths.tiptapUi\n )\n const packageRoot =\n (await findPackageRoot(workspaceRoot, targetConfig.resolvedPaths.cwd)) ??\n targetConfig.resolvedPaths.cwd\n\n // 3. Update dependencies.\n await updateDependencies(component.dependencies || [], targetConfig, {\n silent: true,\n })\n\n await updateDevDependencies(component.devDependencies || [], targetConfig, {\n silent: true,\n })\n\n // 4. Update files.\n const files = await updateFiles(component.files || [], targetConfig, {\n overwrite: options.overwrite,\n silent: true,\n rootSpinner,\n })\n\n if (files.errors && files.errors.length > 0) {\n spinner(`Encountered ${files.errors.length} errors:`, {\n silent: options.silent,\n })?.fail()\n\n for (const { file, error } of files.errors) {\n logger.error(` - ${file}: ${error}`)\n }\n }\n\n filesCreated.push(\n ...files.filesCreated.map((file) =>\n path.relative(workspaceRoot, path.join(packageRoot, file))\n )\n )\n filesUpdated.push(\n ...files.filesUpdated.map((file) =>\n path.relative(workspaceRoot, path.join(packageRoot, file))\n )\n )\n filesSkipped.push(\n ...files.filesSkipped.map((file) =>\n path.relative(workspaceRoot, path.join(packageRoot, file))\n )\n )\n }\n\n rootSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n\n // Sort files.\n filesCreated.sort()\n filesUpdated.sort()\n filesSkipped.sort()\n\n const hasUpdatedFiles = filesCreated.length || filesUpdated.length\n if (!hasUpdatedFiles && !filesSkipped.length) {\n spinner(`No files updated`, {\n silent: options.silent,\n })?.info()\n }\n\n if (filesCreated.length) {\n spinner(\n `Created ${filesCreated.length} ${\n filesCreated.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n for (const file of filesCreated) {\n logger.log(` - ${file}`)\n }\n }\n\n if (filesUpdated.length) {\n spinner(\n `Updated ${filesUpdated.length} ${\n filesUpdated.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.info()\n for (const file of filesUpdated) {\n logger.log(` - ${file}`)\n }\n }\n\n if (filesSkipped.length) {\n spinner(\n `Skipped ${filesSkipped.length} ${\n filesSkipped.length === 1 ? \"file\" : \"files\"\n }: (use --overwrite to overwrite)`,\n {\n silent: options.silent,\n }\n )?.info()\n for (const file of filesSkipped) {\n logger.log(` - ${file}`)\n }\n }\n\n return {\n filesCreated,\n filesUpdated,\n filesSkipped,\n }\n}\n","import { logger } from \"@/src/utils/logger\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport function handleError(error: unknown) {\n logger.error(\n `Something went wrong. Please check the error below for more details.`\n )\n logger.error(`If the problem persists, please open an issue on GitHub.`)\n logger.error(\"\")\n if (typeof error === \"string\") {\n logger.error(error)\n logger.break()\n process.exit(0)\n }\n\n if (error instanceof z.ZodError) {\n logger.error(\"Validation failed:\")\n for (const [key, value] of Object.entries(error.flatten().fieldErrors)) {\n logger.error(`- ${colors.cyan(key)}: ${value}`)\n }\n logger.break()\n process.exit(0)\n }\n\n if (error instanceof Error) {\n logger.error(error.message)\n logger.break()\n process.exit(0)\n }\n\n logger.break()\n process.exit(0)\n}\n","import { z } from \"zod\"\n\nexport const registryItemTypeSchema = z.enum([\n \"registry:context\",\n \"registry:extension\",\n \"registry:hook\",\n \"registry:icon\",\n \"registry:lib\",\n \"registry:node\",\n \"registry:template\",\n \"registry:ui-primitive\",\n \"registry:ui\",\n \"registry:ui-utils\",\n \"registry:page\",\n \"registry:component\",\n \"registry:style\",\n \"registry:asset\",\n])\n\nexport type PaidPlan = \"start\" | \"team\" | \"growth\" | \"enterprise\"\nexport type FreePlan = \"open-source\" | \"light\"\nexport type Plan = PaidPlan | FreePlan\n\nexport const PAID_PLANS = [\n \"start\",\n \"team\",\n \"growth\",\n \"enterprise\",\n] as const satisfies readonly PaidPlan[]\n\nexport const FREE_PLANS = [\n \"open-source\",\n \"light\",\n] as const satisfies readonly FreePlan[]\n\nconst ALL_PLANS = [...PAID_PLANS, ...FREE_PLANS] as const\n\nexport const planSchema = z.array(z.enum(ALL_PLANS)).default([])\n\nexport const registryItemFileSchema = z.object({\n path: z.string(),\n content: z.string().optional(),\n type: registryItemTypeSchema,\n target: z.string().optional(),\n})\n\nexport const registryItemSchema = z.object({\n name: z.string(),\n type: registryItemTypeSchema,\n description: z.string().optional(),\n dependencies: z.array(z.string()).optional(),\n devDependencies: z.array(z.string()).optional(),\n registryDependencies: z.array(z.string()).optional(),\n files: z.array(registryItemFileSchema).optional(),\n meta: z.record(z.string(), z.any()).optional(),\n plans: planSchema.optional(),\n hide: z.boolean().default(false).optional(),\n})\n\nexport const registrySchema = z.array(registryItemSchema)\n\nexport type Registry = z.infer<typeof registrySchema>\n\nexport const registryIndexSchema = z.array(\n registryItemSchema.extend({\n files: z.array(z.union([z.string(), registryItemFileSchema])).optional(),\n })\n)\n\nexport const registryResolvedItemsTreeSchema = registryItemSchema.pick({\n dependencies: true,\n devDependencies: true,\n files: true,\n})\n\nexport type RegistryItem = z.infer<typeof registryItemSchema>\nexport type RegistryItemIndexSchema = z.infer<typeof registryIndexSchema>\n","import { configSchema } from \"@/src/utils/get-config\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport {\n registryIndexSchema,\n RegistryItem,\n registryItemSchema,\n registryResolvedItemsTreeSchema,\n} from \"@/src/utils/registry/schema\"\nimport deepmerge from \"deepmerge\"\nimport { HttpsProxyAgent } from \"https-proxy-agent\"\nimport fetch, { Response } from \"node-fetch\"\nimport { z } from \"zod\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { Framework, FRAMEWORKS } from \"@/src/utils/frameworks\"\nimport { colors } from \"@/src/utils/colors\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\n\nexport const REGISTRY_URL = \"https://template.tiptap.dev\"\n// export const REGISTRY_URL = \"https://template-preview.tiptap.dev\"\n// export const REGISTRY_URL = \"http://localhost:3000\"\n\nconst agent = process.env.https_proxy\n ? new HttpsProxyAgent(process.env.https_proxy)\n : undefined\n\nexport async function getRegistryIndex() {\n try {\n const [result] = await fetchRegistry([\"index.json\"])\n\n return registryIndexSchema.parse(result)\n } catch (error) {\n logger.error(\"\\n\")\n handleError(error)\n }\n}\n\nfunction createRegistryError(response: Response, url?: string): Error {\n const errorMessages: Record<number, string> = {\n 400: \"Bad request\",\n 401: \"Unauthorized\",\n 403: \"Forbidden\",\n 404: \"Not found\",\n 500: \"Internal server error\",\n }\n\n const urlInfo = url ? ` at ${colors.cyan(url)}` : \"\"\n\n switch (response.status) {\n case 401:\n tokenStorage.clear()\n return new Error(\n `You are not authorized to access the component${urlInfo}.\\n` +\n `Please run ${colors.cyan(\"@tiptap/cli login\")} to log in to your Tiptap Cloud account.`\n )\n\n case 404:\n return new Error(\n `The component${urlInfo} was not found.\\n` +\n `It may not exist at the registry. Please make sure it is a valid component.`\n )\n\n case 403:\n return new Error(\n `You do not have access to the component${urlInfo}.\\n` +\n `Your account may not have the required subscription plan for this component.\\n` +\n `Please upgrade your subscription or use a component available in your current plan.`\n )\n\n default:\n const message = errorMessages[response.status] || response.statusText\n return new Error(`Failed to fetch${urlInfo}.\\n${message}`)\n }\n}\n\nasync function fetchComponent(path: string, headers: Record<string, string>) {\n const url = getRegistryUrl(path)\n\n const response = await fetch(url, {\n agent,\n headers,\n })\n\n if (!response.ok) {\n throw createRegistryError(response, url)\n }\n\n return response.json()\n}\n\nasync function fetchRegistryBatch(\n componentNames: string[],\n headers: Record<string, string>\n) {\n const response = await fetch(\n `${REGISTRY_URL}/api/registry/components/batch`,\n {\n method: \"POST\",\n agent,\n headers,\n body: JSON.stringify({ components: componentNames }),\n }\n )\n\n if (!response.ok) {\n throw createRegistryError(response)\n }\n\n const results = (await response.json()) as RegistryItem[]\n\n return results\n}\n\nexport async function fetchRegistry(paths: string[]) {\n try {\n const bearerToken = tokenStorage.getBearerToken()\n const headers: Record<string, string> = {\n \"Content-Type\": \"application/json\",\n }\n\n if (bearerToken) {\n headers[\"Authorization\"] = `Bearer ${bearerToken}`\n }\n\n const componentNames = paths.map((path) => {\n if (path.includes(\"/components/\")) {\n return path.replace(/.*\\/components\\//, \"\").replace(\".json\", \"\")\n }\n return path.replace(\".json\", \"\")\n })\n\n if (componentNames.length > 1) {\n return await fetchRegistryBatch(componentNames, headers)\n }\n\n return Promise.all(paths.map((path) => fetchComponent(path, headers)))\n } catch (error) {\n logger.error(\"\\n\")\n handleError(error)\n return []\n }\n}\n\nexport async function fetchRegistryDependencies(\n components: string[]\n): Promise<string[]> {\n const response = await fetch(`${REGISTRY_URL}/api/registry/dependencies`, {\n method: \"POST\",\n agent,\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({ components }),\n })\n\n if (!response.ok) {\n throw new Error(\n `Failed to fetch registry dependencies: ${response.statusText}`\n )\n }\n\n return (await response.json()) as Promise<string[]>\n}\n\nexport async function registryResolveItemsTree(\n names: z.infer<typeof registryItemSchema>[\"name\"][],\n config: z.infer<typeof configSchema>\n) {\n try {\n const index = await getRegistryIndex()\n if (!index) {\n return null\n }\n\n // If we're resolving the index, we want it to go first.\n if (names.includes(\"index\")) {\n names.unshift(\"index\")\n }\n\n const registryItems = await resolveRegistryItems(names)\n const result = await fetchRegistry(registryItems)\n const payload = z.array(registryItemSchema).parse(result)\n\n if (!payload) {\n return null\n }\n\n const projectInfo = await getProjectInfo(config.resolvedPaths.cwd)\n const framework = projectInfo?.framework.name as Framework[\"name\"]\n\n const allDependencies = deepmerge.all(\n payload.map((item) => item.dependencies ?? [])\n )\n\n const allDevDependencies = deepmerge.all(\n payload.map((item) => item.devDependencies ?? [])\n )\n\n const filteredDevDependencies = filterDevDependenciesByFramework(\n allDevDependencies,\n framework\n )\n\n return registryResolvedItemsTreeSchema.parse({\n dependencies: allDependencies,\n devDependencies: filteredDevDependencies,\n files: deepmerge.all(payload.map((item) => item.files ?? [])),\n })\n } catch (error) {\n handleError(error)\n return null\n }\n}\n\nexport async function resolveRegistryItems(names: string[]) {\n const results = await fetchRegistryDependencies(names)\n const registryDependencies = results.map((name) =>\n getRegistryUrl(`components/${name}.json`)\n )\n\n return registryDependencies\n}\n\nfunction getRegistryUrl(path: string) {\n if (isUrl(path)) {\n const url = new URL(path)\n return url.toString()\n }\n\n if (!REGISTRY_URL) {\n throw new Error(\"No registry URL found\")\n }\n\n // Keep the index.json path as is (public)\n if (path === \"index.json\") {\n return `${REGISTRY_URL}/r/${path}`\n }\n\n // Only redirect component paths to the API\n if (path.startsWith(\"components/\")) {\n const componentName = path.replace(\"components/\", \"\").replace(\".json\", \"\")\n return `${REGISTRY_URL}/api/registry/components/${componentName}`\n }\n\n return `${REGISTRY_URL}/${path}`\n}\n\nfunction isUrl(path: string) {\n try {\n new URL(path)\n return true\n } catch (error) {\n return false\n }\n}\n\nexport function getRegistryTypeAliasMap() {\n return new Map<string, string>([\n [\"registry:ui\", \"tiptapUi\"],\n [\"registry:ui-primitive\", \"tiptapUiPrimitives\"],\n [\"registry:ui-utils\", \"tiptapUiUtils\"],\n [\"registry:extension\", \"tiptapExtensions\"],\n [\"registry:node\", \"tiptapNodes\"],\n [\"registry:context\", \"contexts\"],\n [\"registry:hook\", \"hooks\"],\n [\"registry:lib\", \"lib\"],\n [\"registry:context\", \"components\"],\n [\"registry:template\", \"tiptapTemplates\"],\n [\"registry:component\", \"components\"],\n [\"registry:icon\", \"titpapIcons\"],\n [\"registry:style\", \"styles\"],\n ])\n}\n\n// Track a dependency and its parent.\nexport function getRegistryParentMap(\n registryItems: z.infer<typeof registryItemSchema>[]\n) {\n const map = new Map<string, z.infer<typeof registryItemSchema>>()\n\n registryItems.forEach((item) => {\n if (!item.registryDependencies) {\n return\n }\n\n item.registryDependencies.forEach((dependency) => {\n map.set(dependency, item)\n })\n })\n\n return map\n}\n\n/**\n * Filter development dependencies based on framework requirements\n * @param devDependencies Array of development dependencies\n * @param framework Framework name\n * @returns Filtered array of development dependencies\n */\nfunction filterDevDependenciesByFramework(\n devDependencies: unknown,\n framework: Framework[\"name\"]\n): string[] {\n const depsArray = Array.isArray(devDependencies) ? devDependencies : []\n\n if (!depsArray.length) {\n return []\n }\n\n const stringDeps = depsArray.map((dep) => String(dep))\n\n if (framework) {\n const hasSass = stringDeps.includes(\"sass\")\n const hasSassEmbedded = stringDeps.includes(\"sass-embedded\")\n\n if (hasSass || hasSassEmbedded) {\n let filteredDeps = [...stringDeps]\n\n const prefersEmbedded: Framework[\"name\"][] = [\n FRAMEWORKS.astro.name,\n FRAMEWORKS.laravel.name,\n FRAMEWORKS.vite.name,\n // FRAMEWORKS.remix.name,\n FRAMEWORKS[\"tanstack-start\"].name,\n FRAMEWORKS[\"react-router\"].name,\n ]\n\n const prefersRegular: Framework[\"name\"][] = [\n FRAMEWORKS[\"next-app\"].name,\n FRAMEWORKS[\"next-pages\"].name,\n // FRAMEWORKS.gatsby.name,\n ]\n\n if (prefersEmbedded.includes(framework)) {\n filteredDeps = filteredDeps.filter((dep) => dep !== \"sass\")\n } else if (prefersRegular.includes(framework)) {\n filteredDeps = filteredDeps.filter((dep) => dep !== \"sass-embedded\")\n }\n\n return filteredDeps\n }\n }\n\n return stringDeps\n}\n","import Conf from \"conf\"\nimport type { Logger } from \"./logger\"\n\nexport interface TokenConfig {\n bearerToken?: string\n authToken?: string\n email?: string\n loginDate?: string\n plans?: string[]\n licenseAccepted?: boolean\n licenseAcceptedDate?: string\n}\n\nexport class TokenStorage {\n private config: Conf<TokenConfig>\n private logger: Logger\n\n constructor(logger: Logger) {\n this.logger = logger\n this.config = new Conf<TokenConfig>({\n projectName: \"tiptap-cli\",\n clearInvalidConfig: true, // auto-reset if file is corrupted\n schema: {\n bearerToken: { type: \"string\" },\n authToken: { type: \"string\" },\n email: { type: \"string\" },\n loginDate: { type: \"string\" },\n plans: { type: \"array\", items: { type: \"string\" }, default: [] },\n licenseAccepted: { type: \"boolean\" },\n licenseAcceptedDate: { type: \"string\" },\n },\n })\n }\n\n private safeError(prefix: string, error: unknown) {\n const msg =\n error instanceof Error\n ? `${error.name}: ${error.message}`\n : String(error ?? \"Unknown error\")\n try {\n this.logger.error(`${prefix}: ${msg}`)\n } catch {\n // never throw from logging\n }\n }\n\n setBearerToken(\n token: string,\n userInfo?: { email?: string; plans?: string[] }\n ): void {\n try {\n this.config.set(\"bearerToken\", token)\n this.config.set(\"loginDate\", new Date().toISOString())\n if (userInfo?.email) this.config.set(\"email\", userInfo.email)\n if (userInfo?.plans) this.config.set(\"plans\", userInfo.plans)\n } catch (e) {\n this.safeError(\"Failed to store bearer token\", e)\n }\n }\n\n getBearerToken(): string | null {\n try {\n return this.config.get(\"bearerToken\") ?? null\n } catch (e) {\n this.safeError(\"Failed to retrieve bearer token\", e)\n return null\n }\n }\n\n setAuthToken(\n token: string,\n userInfo?: { email?: string; plans?: string[] }\n ): void {\n try {\n this.config.set(\"authToken\", token)\n this.config.set(\"loginDate\", new Date().toISOString())\n if (userInfo?.email) this.config.set(\"email\", userInfo.email)\n if (userInfo?.plans) this.config.set(\"plans\", userInfo.plans)\n } catch (e) {\n this.safeError(\"Failed to store auth token\", e)\n }\n }\n\n getAuthToken(): string | null {\n try {\n return this.config.get(\"authToken\") ?? null\n } catch (e) {\n this.safeError(\"Failed to retrieve auth token\", e)\n return null\n }\n }\n\n getUserInfo(): { email?: string; plans: string[]; loginDate?: string } {\n return {\n email: this.config.get(\"email\"),\n plans: this.config.get(\"plans\") ?? [],\n loginDate: this.config.get(\"loginDate\"),\n }\n }\n\n getTokenExpiration(): string | null {\n const loginDate = this.config.get(\"loginDate\")\n if (!loginDate) return null\n const expiration = new Date(loginDate)\n expiration.setMonth(expiration.getMonth() + 11)\n\n return expiration.toISOString()\n }\n\n isValidToken(): boolean {\n const bearerToken = this.getBearerToken()\n const authToken = this.getAuthToken()\n\n if (!bearerToken && !authToken) return false\n\n const expirationISO = this.getTokenExpiration()\n if (expirationISO) {\n const expiryDate = new Date(expirationISO)\n if (expiryDate <= new Date()) {\n this.clear()\n return false\n }\n }\n\n return true\n }\n\n clear(): void {\n try {\n this.config.clear()\n } catch (e) {\n this.safeError(\"Failed to clear token storage\", e)\n }\n }\n\n hasPlan(planName: string): boolean {\n const plans = this.config.get(\"plans\") ?? []\n return Array.isArray(plans) && plans.includes(planName)\n }\n\n setLicenseAccepted(): void {\n try {\n this.config.set(\"licenseAccepted\", true)\n this.config.set(\"licenseAcceptedDate\", new Date().toISOString())\n } catch (e) {\n this.safeError(\"Failed to store license acceptance\", e)\n }\n }\n\n hasAcceptedLicense(): boolean {\n try {\n return this.config.get(\"licenseAccepted\") ?? false\n } catch (e) {\n this.safeError(\"Failed to retrieve license acceptance\", e)\n return false\n }\n }\n\n clearLicenseAcceptance(): void {\n try {\n this.config.delete(\"licenseAccepted\")\n this.config.delete(\"licenseAcceptedDate\")\n } catch (e) {\n this.safeError(\"Failed to clear license acceptance\", e)\n }\n }\n}\n","import { logger } from \"./logger\"\nimport { TokenStorage } from \"./token-storage\"\n\nexport const tokenStorage = new TokenStorage(logger)\n","import ora, { type Options } from \"ora\"\nimport { colors } from \"@/src/utils/colors\"\n\n// Custom Tiptap-style spinner frames that resemble a typewriter cursor\nconst tiptapSpinner = {\n frames: [\n `${colors.cyan(\"█\")}`, // Full block (cursor visible)\n `${colors.cyan(\"█\")}`, // Full block (cursor visible)\n `${colors.cyan(\"█\")}`, // Full block (cursor visible)\n ` `, // Space (cursor hidden)\n ` `, // Space (cursor hidden)\n ` `, // Space (cursor hidden)\n ],\n interval: 200, // Typewriter-like blinking speed\n}\n\nexport function spinner(\n text: Options[\"text\"],\n options?: {\n silent?: boolean\n }\n) {\n return ora({\n text: text,\n spinner: tiptapSpinner,\n color: \"cyan\",\n isSilent: options?.silent,\n })\n}\n","import { detect } from \"@antfu/ni\"\nimport fs from \"fs-extra\"\nimport path from \"path\"\n\nexport async function getPackageManager(\n targetDir: string,\n { withFallback }: { withFallback?: boolean } = {\n withFallback: false,\n }\n): Promise<\"yarn\" | \"pnpm\" | \"bun\" | \"npm\"> {\n let packageManager = await detect({ programmatic: true, cwd: targetDir })\n if (packageManager === \"deno\") packageManager = undefined\n\n if (packageManager === \"yarn@berry\") return \"yarn\"\n if (packageManager === \"pnpm@6\") return \"pnpm\"\n if (packageManager === \"bun\") return \"bun\"\n\n if (!withFallback) {\n return packageManager ?? \"npm\"\n }\n\n // Fallback to user agent if not detected.\n const userAgent = process.env.npm_config_user_agent || \"\"\n\n if (userAgent.startsWith(\"yarn\")) {\n return \"yarn\"\n }\n\n if (userAgent.startsWith(\"pnpm\")) {\n return \"pnpm\"\n }\n\n if (userAgent.startsWith(\"bun\")) {\n return \"bun\"\n }\n\n return \"npm\"\n}\n\nexport async function getPackageRunner(cwd: string) {\n const packageManager = await getPackageManager(cwd)\n\n if (packageManager === \"pnpm\") return \"pnpm dlx\"\n\n if (packageManager === \"bun\") return \"bunx\"\n\n return \"npx\"\n}\n\nexport function isBunProject(cwd: string) {\n const hasBunLock = fs.existsSync(path.join(cwd, \"bun.lock\"))\n const hasBunfig = fs.existsSync(path.join(cwd, \"bunfig.toml\"))\n\n if (hasBunLock && hasBunfig) {\n return true\n }\n\n return false\n}\n","import { Config } from \"@/src/utils/get-config\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { RegistryItem } from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { execa } from \"execa\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport async function updateDependencies(\n dependencies: RegistryItem[\"dependencies\"],\n config: Config,\n options: {\n silent?: boolean\n }\n) {\n dependencies = Array.from(new Set(dependencies))\n if (!dependencies?.length) {\n return\n }\n\n options = {\n silent: false,\n ...options,\n }\n\n const dependenciesSpinner = spinner(`Installing dependencies.`, {\n silent: options.silent,\n }).start()\n const packageManager = await getPackageManager(config.resolvedPaths.cwd)\n\n await execa(\n packageManager,\n [\n packageManager === \"npm\" ? \"install\" : \"add\",\n ...(packageManager === \"npm\" ? [\"--save\"] : []),\n ...dependencies,\n ],\n {\n cwd: config.resolvedPaths.cwd,\n }\n )\n\n dependenciesSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n}\n","import { existsSync, promises as fs } from \"fs\"\nimport path, { basename } from \"path\"\nimport { Config } from \"@/src/utils/get-config\"\nimport { getProjectInfo, ProjectInfo } from \"@/src/utils/get-project-info\"\nimport { logger } from \"@/src/utils/logger\"\nimport {\n RegistryItem,\n registryItemFileSchema,\n} from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { transform } from \"@/src/utils/transformers\"\nimport { transformImport } from \"@/src/utils/transformers/transform-import\"\nimport { transformRsc } from \"@/src/utils/transformers/transform-rsc\"\nimport { z } from \"zod\"\nimport { confirm } from \"@inquirer/prompts\"\nimport {\n getPackageManager,\n isBunProject,\n} from \"@/src/utils/get-package-manager\"\nimport { colors } from \"@/src/utils/colors\"\nimport { transformRemoveComponents } from \"@/src/utils/transformers/transform-remove-components\"\n\nexport async function updateFiles(\n files: RegistryItem[\"files\"],\n config: Config,\n options: {\n overwrite?: boolean\n force?: boolean\n silent?: boolean\n rootSpinner?: ReturnType<typeof spinner>\n }\n) {\n const result = {\n filesCreated: [] as string[],\n filesUpdated: [] as string[],\n filesSkipped: [] as string[],\n errors: [] as { file: string; error: string }[],\n }\n\n if (!files?.length) {\n return result\n }\n\n options = {\n overwrite: false,\n force: false,\n silent: false,\n ...options,\n }\n\n const filesCreatedSpinner = spinner(`Updating files.`, {\n silent: options.silent,\n })?.start()\n\n try {\n const [projectInfo, packageManager] = await Promise.all([\n getProjectInfo(config.resolvedPaths.cwd),\n getPackageManager(config.resolvedPaths.cwd),\n ])\n\n for (const file of files) {\n try {\n if (!file.content) {\n continue\n }\n\n let filePath: string | undefined\n try {\n filePath = resolveFilePath(file, config, {\n isSrcDir: projectInfo?.isSrcDir,\n framework: projectInfo?.framework.name,\n commonRoot: findCommonRoot(\n files.map((f) => f.path),\n file.path\n ),\n })\n } catch (error) {\n result.errors.push({\n file: file.path,\n error: `Failed to resolve file path: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n\n if (!filePath) {\n continue\n }\n\n const fileName = basename(file.path)\n const targetDir = path.dirname(filePath)\n\n if (!config.tsx) {\n filePath = filePath.replace(/\\.tsx?$/, (match) =>\n match === \".tsx\" ? \".jsx\" : \".js\"\n )\n }\n\n const isBun = isBunProject(config.resolvedPaths.cwd)\n\n // For Bun projects, convert .scss files to .css\n if (isBun && filePath.endsWith(\".scss\")) {\n filePath = filePath.replace(/\\.scss$/, \".css\")\n }\n\n let existingFile = false\n try {\n existingFile = existsSync(filePath)\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to check if file exists: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n\n let content: string\n try {\n content = await transform(\n {\n filename: file.path,\n raw: file.content,\n config,\n transformJsx: !config.tsx,\n packageManager,\n },\n [transformImport, transformRsc, transformRemoveComponents]\n )\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to transform content: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n\n if (existingFile) {\n try {\n const existingFileContent = await fs.readFile(filePath, \"utf-8\")\n const [normalizedExisting, normalizedNew] = await Promise.all([\n getNormalizedFileContent(existingFileContent),\n getNormalizedFileContent(content),\n ])\n if (normalizedExisting === normalizedNew) {\n result.filesSkipped.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n continue\n }\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to read or normalize existing file: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n }\n\n if (existingFile && !options.overwrite) {\n filesCreatedSpinner?.stop()\n if (options.rootSpinner) {\n options.rootSpinner?.stop()\n }\n\n try {\n const overwrite = await confirm({\n message: colors.reset(\n `The file ${colors.cyan(\n fileName\n )} already exists. Would you like to overwrite?`\n ),\n theme: {\n prefix: colors.cyan(\"?\"),\n style: {\n message: (text: string) => colors.reset(text),\n },\n },\n })\n\n if (!overwrite) {\n result.filesSkipped.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n if (options.rootSpinner) {\n options.rootSpinner.start()\n }\n continue\n }\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to get user confirmation: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n } finally {\n filesCreatedSpinner?.start()\n if (options.rootSpinner) {\n options.rootSpinner.start()\n }\n }\n }\n\n try {\n if (!existsSync(targetDir)) {\n await fs.mkdir(targetDir, { recursive: true })\n }\n\n await fs.writeFile(filePath, content, \"utf-8\")\n\n existingFile\n ? result.filesUpdated.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n : result.filesCreated.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to write file: ${error instanceof Error ? error.message : String(error)}`,\n })\n }\n } catch (error) {\n result.errors.push({\n file: file.path || \"unknown\",\n error: `Unexpected error processing file: ${error instanceof Error ? error.message : String(error)}`,\n })\n }\n }\n } catch (error) {\n logger.error(\n `An error occurred while updating files: ${error instanceof Error ? error.message : String(error)}`\n )\n } finally {\n const hasUpdatedFiles =\n result.filesCreated.length || result.filesUpdated.length\n if (!hasUpdatedFiles && !result.filesSkipped.length) {\n filesCreatedSpinner?.info(\"No files updated.\")\n }\n\n if (result.filesCreated.length) {\n filesCreatedSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: `Created ${result.filesCreated.length} ${\n result.filesCreated.length === 1 ? \"file\" : \"files\"\n }:`,\n })\n if (!options.silent) {\n for (const file of result.filesCreated) {\n logger.log(` - ${file}`)\n }\n }\n } else {\n filesCreatedSpinner?.stop()\n }\n\n if (result.filesUpdated.length) {\n spinner(\n `Updated ${result.filesUpdated.length} ${\n result.filesUpdated.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.info()\n if (!options.silent) {\n for (const file of result.filesUpdated) {\n logger.log(` - ${file}`)\n }\n }\n }\n\n if (result.filesSkipped.length) {\n spinner(\n `Skipped ${result.filesSkipped.length} ${\n result.filesUpdated.length === 1 ? \"file\" : \"files\"\n }: (use --overwrite to overwrite)`,\n {\n silent: options.silent,\n }\n )?.info()\n if (!options.silent) {\n for (const file of result.filesSkipped) {\n logger.log(` - ${file}`)\n }\n }\n }\n\n if (result.errors.length) {\n spinner(\n `Failed to process ${result.errors.length} ${\n result.errors.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.fail()\n if (!options.silent) {\n for (const { file, error } of result.errors) {\n logger.error(` - ${file}: ${error}`)\n }\n }\n }\n\n if (!options.silent) {\n logger.break()\n }\n }\n\n return result\n}\n\nexport function resolveFileTargetDirectory(\n file: z.infer<typeof registryItemFileSchema>,\n config: Config,\n override?: string\n) {\n if (override) {\n return override\n }\n\n if (file.type === \"registry:ui\") {\n return config.resolvedPaths.tiptapUi\n }\n\n if (file.type === \"registry:ui-primitive\") {\n return config.resolvedPaths.tiptapUiPrimitives\n }\n\n if (file.type === \"registry:ui-utils\") {\n return config.resolvedPaths.tiptapUiUtils\n }\n\n if (file.type === \"registry:extension\") {\n return config.resolvedPaths.tiptapExtensions\n }\n\n if (file.type === \"registry:node\") {\n return config.resolvedPaths.tiptapNodes\n }\n\n if (file.type === \"registry:icon\") {\n return config.resolvedPaths.tiptapIcons\n }\n\n if (file.type === \"registry:hook\") {\n return config.resolvedPaths.hooks\n }\n\n if (file.type === \"registry:lib\") {\n return config.resolvedPaths.lib\n }\n\n if (file.type === \"registry:context\") {\n return config.resolvedPaths.contexts\n }\n\n if (file.type === \"registry:template\" || file.type === \"registry:component\") {\n return config.resolvedPaths.components\n }\n\n if (file.type === \"registry:style\") {\n return config.resolvedPaths.styles\n }\n\n return config.resolvedPaths.components\n}\n\nexport function findCommonRoot(paths: string[], needle: string): string {\n // Remove leading slashes for consistent handling\n const normalizedPaths = paths.map((p) => p.replace(/^\\//, \"\"))\n const normalizedNeedle = needle.replace(/^\\//, \"\")\n\n // Get the directory path of the needle by removing the file name\n const needleDir = normalizedNeedle.split(\"/\").slice(0, -1).join(\"/\")\n\n // If needle is at root level, return empty string\n if (!needleDir) {\n return \"\"\n }\n\n // Split the needle directory into segments\n const needleSegments = needleDir.split(\"/\")\n\n // Start from the full path and work backwards\n for (let i = needleSegments.length; i > 0; i--) {\n const testPath = needleSegments.slice(0, i).join(\"/\")\n // Check if this is a common root by verifying if any other paths start with it\n const hasRelatedPaths = normalizedPaths.some(\n (path) => path !== normalizedNeedle && path.startsWith(testPath + \"/\")\n )\n if (hasRelatedPaths) {\n return \"/\" + testPath // Add leading slash back for the result\n }\n }\n\n // If no common root found with other files, return the parent directory of the needle\n return \"/\" + needleDir // Add leading slash back for the result\n}\n\nexport async function getNormalizedFileContent(content: string) {\n return content.replace(/\\r\\n/g, \"\\n\").trim()\n}\n\nexport function resolvePageTarget(\n target: string,\n framework?: ProjectInfo[\"framework\"][\"name\"]\n) {\n if (!framework) {\n return \"\"\n }\n\n if (framework === \"next-app\") {\n return target\n }\n\n if (framework === \"next-pages\") {\n let result = target.replace(/^app\\//, \"pages/\")\n result = result.replace(/\\/page(\\.[jt]sx?)$/, \"$1\")\n\n return result\n }\n\n if (framework === \"react-router\") {\n let result = target.replace(/^app\\//, \"app/routes/\")\n result = result.replace(/\\/page(\\.[jt]sx?)$/, \"$1\")\n\n return result\n }\n\n if (framework === \"laravel\") {\n let result = target.replace(/^app\\//, \"resources/js/pages/\")\n result = result.replace(/\\/page(\\.[jt]sx?)$/, \"$1\")\n\n return result\n }\n\n return \"\"\n}\n\nexport function resolveNestedFilePath(\n filePath: string,\n targetDir: string\n): string {\n // Normalize paths by removing leading/trailing slashes\n const normalizedFilePath = filePath.replace(/^\\/|\\/$/g, \"\")\n const normalizedTargetDir = targetDir.replace(/^\\/|\\/$/g, \"\")\n\n // Split paths into segments\n const fileSegments = normalizedFilePath.split(\"/\")\n const targetSegments = normalizedTargetDir.split(\"/\")\n\n // Find the last matching segment from targetDir in filePath\n const lastTargetSegment = targetSegments[targetSegments.length - 1]\n const commonDirIndex = fileSegments.findIndex(\n (segment) => segment === lastTargetSegment\n )\n\n if (commonDirIndex === -1) {\n // Return just the filename if no common directory is found\n return fileSegments[fileSegments.length - 1]\n }\n\n // Return everything after the common directory\n return fileSegments.slice(commonDirIndex + 1).join(\"/\")\n}\n\nexport function resolveFilePath(\n file: z.infer<typeof registryItemFileSchema>,\n config: Config,\n options: {\n isSrcDir?: boolean\n commonRoot?: string\n framework?: ProjectInfo[\"framework\"][\"name\"]\n }\n) {\n // if (file.type === \"registry:asset\") {\n // if (file.target) {\n // // replace assets/ and public/ with the public directory\n // const targetDir = file.target.replace(/^assets\\//, \"\")\n // const targetDirPublic = targetDir.replace(/^public\\//, \"\")\n // const targetDirPublicPath = path.join(\n // config.resolvedPaths.cwd,\n // \"public\",\n // targetDirPublic\n // )\n\n // return targetDirPublicPath\n // }\n // }\n\n // Special handling for template files without targets\n if (\n !file.target &&\n file.path.includes(\"tiptap-templates/\") &&\n file.type !== \"registry:page\"\n ) {\n const match = file.path.match(/tiptap-templates\\/([^/]+)\\/(.*)/)\n if (match) {\n const [, templateName, relativePath] = match\n\n // If it's a component file in the components directory, adjust the path\n if (relativePath.startsWith(\"components/\")) {\n const finalPath = relativePath.replace(\"components/\", \"\")\n return path.join(\n config.resolvedPaths.components,\n \"tiptap-templates\",\n templateName,\n finalPath\n )\n }\n\n // For data and other files\n return path.join(\n config.resolvedPaths.components,\n \"tiptap-templates\",\n templateName,\n relativePath\n )\n }\n }\n\n // Special handling for data files with targets in templates\n if (\n file.target &&\n file.path.includes(\"tiptap-templates/\") &&\n file.target.includes(\"/data/\")\n ) {\n const templateMatch = file.path.match(/tiptap-templates\\/([^/]+)\\//)\n if (templateMatch) {\n const templateName = templateMatch[1]\n const dataPath = file.target.split(\"/data/\")[1]\n return path.join(\n config.resolvedPaths.components,\n \"tiptap-templates\",\n templateName,\n \"data\",\n dataPath\n )\n }\n }\n\n // Original logic for files with explicit targets\n if (file.target) {\n if (file.target.startsWith(\"~/\")) {\n return path.join(config.resolvedPaths.cwd, file.target.replace(\"~/\", \"\"))\n }\n\n let target = file.target\n\n if (file.type === \"registry:page\") {\n target = resolvePageTarget(target, options.framework)\n if (!target) {\n return \"\"\n }\n }\n\n return options.isSrcDir\n ? path.join(config.resolvedPaths.cwd, \"src\", target.replace(\"src/\", \"\"))\n : path.join(config.resolvedPaths.cwd, target.replace(\"src/\", \"\"))\n }\n\n // Original logic for non-template files\n const targetDir = resolveFileTargetDirectory(file, config)\n const relativePath = resolveNestedFilePath(file.path, targetDir)\n return path.join(targetDir, relativePath)\n}\n","import { promises as fs } from \"fs\"\nimport { tmpdir } from \"os\"\nimport path from \"path\"\nimport { Config } from \"@/src/utils/get-config\"\nimport { transformImport } from \"@/src/utils/transformers/transform-import\"\nimport { transformJsx } from \"@/src/utils/transformers/transform-jsx\"\nimport { transformRsc } from \"@/src/utils/transformers/transform-rsc\"\nimport { transformRemoveComponents } from \"@/src/utils/transformers/transform-remove-components\"\nimport { transformScssToCSS } from \"@/src/utils/transformers/transform-scss-to-css\"\nimport { Project, ScriptKind, type SourceFile } from \"ts-morph\"\nimport { isBunProject } from \"../get-package-manager\"\n\nexport type TransformOpts = {\n filename: string\n raw: string\n config: Config\n transformJsx?: boolean\n packageManager?: \"yarn\" | \"pnpm\" | \"bun\" | \"npm\"\n}\n\nexport type Transformer<Output = SourceFile> = (\n opts: TransformOpts & {\n sourceFile: SourceFile\n }\n) => Promise<Output>\n\nconst project = new Project({\n compilerOptions: {},\n})\n\nasync function createTempSourceFile(filename: string) {\n const dir = await fs.mkdtemp(path.join(tmpdir(), \"tiptap-\"))\n return path.join(dir, filename)\n}\n\nexport async function transform(\n opts: TransformOpts,\n transformers: Transformer[] = [\n transformImport,\n transformRsc,\n transformRemoveComponents,\n ]\n) {\n const isBun = isBunProject(opts.config.resolvedPaths.cwd)\n // For Bun projects, convert SCSS to CSS\n if (opts.filename.endsWith(\".scss\") && isBun) {\n return await transformScssToCSS(opts.raw)\n }\n\n if (\n opts.filename.endsWith(\".scss\") ||\n opts.filename.endsWith(\".css\") ||\n opts.filename.endsWith(\".json\")\n ) {\n return opts.raw\n }\n\n const tempFile = await createTempSourceFile(opts.filename)\n const sourceFile = project.createSourceFile(tempFile, opts.raw, {\n scriptKind: ScriptKind.TSX,\n })\n\n for (const transformer of transformers) {\n await transformer({ sourceFile, ...opts })\n }\n\n if (opts.transformJsx) {\n return await transformJsx({\n sourceFile,\n ...opts,\n })\n }\n\n return sourceFile.getText()\n}\n","import { Config } from \"@/src/utils/get-config\"\nimport { Transformer } from \"@/src/utils/transformers\"\nimport { isBunProject } from \"../get-package-manager\"\n\nexport const transformImport: Transformer = async ({\n sourceFile,\n config,\n packageManager,\n}) => {\n const importDeclarations = sourceFile.getImportDeclarations()\n\n for (const importDeclaration of importDeclarations) {\n let moduleSpecifier = updateImportAliases(\n importDeclaration.getModuleSpecifierValue(),\n config\n )\n\n const isBun = isBunProject(config.resolvedPaths.cwd)\n\n // For Bun projects, convert .scss imports to .css\n if (isBun && moduleSpecifier.endsWith(\".scss\")) {\n moduleSpecifier = moduleSpecifier.replace(/\\.scss$/, \".css\")\n }\n\n if (moduleSpecifier) {\n importDeclaration.setModuleSpecifier(moduleSpecifier)\n }\n }\n\n return sourceFile\n}\n\nfunction updateImportAliases(moduleSpecifier: string, config: Config): string {\n // Remove \"/registry/\" from the module specifier\n if (!moduleSpecifier.startsWith(\"@/registry/\")) {\n // We fix the alias and return.\n const alias = config.aliases.components.split(\"/\")[0]\n return moduleSpecifier.replace(/^@\\//, `${alias}/`)\n }\n\n // Handle template imports specifically to preserve the template structure\n if (\n moduleSpecifier.match(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\/components\\//\n )\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\/components\\//,\n `${config.aliases.components}/tiptap-templates/$1/`\n )\n }\n\n // Handle template imports without the components part\n if (\n moduleSpecifier.match(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\/(?!components\\/)/\n )\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\//,\n `${config.aliases.components}/tiptap-templates/$1/`\n )\n }\n\n if (\n config.aliases.components &&\n moduleSpecifier.match(/@\\/registry\\/components/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/components/,\n config.aliases.components\n )\n }\n\n if (\n config.aliases.contexts &&\n moduleSpecifier.match(/@\\/registry\\/contexts/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/contexts/,\n config.aliases.contexts\n )\n }\n\n if (\n config.aliases.tiptapExtensions &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-extension/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-extension/,\n config.aliases.tiptapExtensions\n )\n }\n\n if (config.aliases.hooks && moduleSpecifier.match(/@\\/registry\\/hooks/)) {\n return moduleSpecifier.replace(/@\\/registry\\/hooks/, config.aliases.hooks)\n }\n\n if (\n config.aliases.tiptapIcons &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-icons/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-icons/,\n config.aliases.tiptapIcons\n )\n }\n\n if (config.aliases.lib && moduleSpecifier.match(/@\\/registry\\/lib/)) {\n return moduleSpecifier.replace(/@\\/registry\\/lib/, config.aliases.lib)\n }\n\n if (\n config.aliases.tiptapNodes &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-node/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-node/,\n config.aliases.tiptapNodes\n )\n }\n\n if (\n config.aliases.tiptapUiPrimitives &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-ui-primitive/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-ui-primitive/,\n config.aliases.tiptapUiPrimitives\n )\n }\n\n if (\n config.aliases.tiptapUiUtils &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-ui-utils/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-ui-utils/,\n config.aliases.tiptapUiUtils\n )\n }\n\n if (\n config.aliases.tiptapUi &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-ui/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-ui/,\n config.aliases.tiptapUi\n )\n }\n\n if (config.aliases.styles && moduleSpecifier.match(/@\\/registry\\/styles/)) {\n return moduleSpecifier.replace(/@\\/registry\\/styles/, config.aliases.styles)\n }\n\n // Default case - preserve all other imports\n return moduleSpecifier.replace(\n /^@\\/registry\\/[^/]+(?:\\/.*\\/)?/,\n config.aliases.components + \"/\"\n )\n}\n","import { type Transformer } from \"@/src/utils/transformers\"\nimport { transformFromAstSync } from \"@babel/core\"\nimport { ParserOptions, parse } from \"@babel/parser\"\n// eslint-disable-next-line @typescript-eslint/ban-ts-comment\n// @ts-expect-error\nimport transformTypescript from \"@babel/plugin-transform-typescript\"\nimport * as recast from \"recast\"\n\n// TODO.\n// I'm using recast for the AST here.\n// Figure out if ts-morph AST is compatible with Babel.\n\n// This is a copy of the babel options from recast/parser.\n// The goal here is to tolerate as much syntax as possible.\n// We want to be able to parse any valid tsx code.\n// See https://github.com/benjamn/recast/blob/master/parsers/_babel_options.ts.\nconst PARSE_OPTIONS: ParserOptions = {\n sourceType: \"module\",\n allowImportExportEverywhere: true,\n allowReturnOutsideFunction: true,\n startLine: 1,\n tokens: true,\n plugins: [\n \"asyncGenerators\",\n \"bigInt\",\n \"classPrivateMethods\",\n \"classPrivateProperties\",\n \"classProperties\",\n \"classStaticBlock\",\n \"decimal\",\n \"decorators-legacy\",\n \"doExpressions\",\n \"dynamicImport\",\n \"exportDefaultFrom\",\n \"exportNamespaceFrom\",\n \"functionBind\",\n \"functionSent\",\n \"importAssertions\",\n \"importMeta\",\n \"nullishCoalescingOperator\",\n \"numericSeparator\",\n \"objectRestSpread\",\n \"optionalCatchBinding\",\n \"optionalChaining\",\n [\n \"pipelineOperator\",\n {\n proposal: \"minimal\",\n },\n ],\n [\n \"recordAndTuple\",\n {\n syntaxType: \"hash\",\n },\n ],\n \"throwExpressions\",\n \"topLevelAwait\",\n \"v8intrinsic\",\n \"typescript\",\n \"jsx\",\n ],\n}\n\nexport const transformJsx: Transformer<string> = async ({\n sourceFile,\n config,\n}) => {\n const output = sourceFile.getFullText()\n\n if (config.tsx) {\n return output\n }\n\n const ast = recast.parse(output, {\n parser: {\n parse: (code: string) => {\n return parse(code, PARSE_OPTIONS)\n },\n },\n })\n\n const result = transformFromAstSync(ast, output, {\n cloneInputAst: false,\n code: false,\n ast: true,\n plugins: [transformTypescript],\n configFile: false,\n })\n\n if (!result || !result.ast) {\n throw new Error(\"Failed to transform JSX\")\n }\n\n return recast.print(result.ast).code\n}\n","import { Transformer } from \"@/src/utils/transformers\"\nimport { SyntaxKind } from \"ts-morph\"\n\nconst directiveRegex = /^[\"']use client[\"']$/g\n\nexport const transformRsc: Transformer = async ({ sourceFile, config }) => {\n if (config.rsc) {\n return sourceFile\n }\n\n // Remove \"use client\" from the top of the file.\n const first = sourceFile.getFirstChildByKind(SyntaxKind.ExpressionStatement)\n if (first && directiveRegex.test(first.getText())) {\n first.remove()\n }\n\n return sourceFile\n}\n","import { Transformer } from \"@/src/utils/transformers\"\nimport {\n BinaryExpression,\n CallExpression,\n Node,\n PropertyAccessExpression,\n PropertyAssignment,\n SourceFile,\n SyntaxKind,\n} from \"ts-morph\"\nimport { Framework, FRAMEWORKS } from \"@/src/utils/frameworks\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { Config } from \"@/src/utils/get-config\"\n\n/**\n * Defines a rule for excluding components based on name matching patterns\n */\nexport interface ComponentExclusionRule {\n name: string // The name or pattern to match against\n matchType: \"exact\" | \"contains\" | \"startsWith\" | \"endsWith\" | \"regex\" // How to match the name\n caseSensitive?: boolean // Whether matching should be case sensitive\n pattern?: string // Regex pattern (used when matchType is \"regex\")\n onlyInFiles?: string[]\n}\n\ninterface NodeToRemove {\n node: any\n newText?: string\n action: \"remove\" | \"replace\"\n}\n\n/**\n * Default set of exclusion rules for common unwanted component patterns\n * These target development, testing, and internal components that shouldn't\n * be included in production builds or public APIs\n */\n/**\n * Default set of exclusion rules for common unwanted component patterns\n * These target development, testing, and internal components that shouldn't\n * be included in production builds or public APIs\n */\nconst DEFAULT_EXCLUSIONS: ComponentExclusionRule[] = [\n {\n name: \"cta\",\n matchType: \"contains\",\n caseSensitive: false,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"initialContent\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"JSONContent\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"onCreate\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"getDocumentId\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n]\n\n/**\n * Determines whether a component should be excluded based on the provided rules\n * @param componentName - The name of the component to check\n * @param rules - Array of exclusion rules to apply\n * @returns true if the component should be excluded, false otherwise\n */\nfunction shouldExcludeComponent(\n componentName: string,\n rules: ComponentExclusionRule[],\n filePath: string\n): boolean {\n return rules.some((rule) => {\n // Check file path restriction\n if (\n rule.onlyInFiles &&\n !rule.onlyInFiles.some((f) => filePath.endsWith(f))\n ) {\n return false\n }\n\n const name = rule.caseSensitive\n ? componentName\n : componentName.toLowerCase()\n const ruleName = rule.caseSensitive ? rule.name : rule.name.toLowerCase()\n\n switch (rule.matchType) {\n case \"exact\":\n return name === ruleName\n case \"contains\":\n return name.includes(ruleName)\n case \"startsWith\":\n return name.startsWith(ruleName)\n case \"endsWith\":\n return name.endsWith(ruleName)\n case \"regex\":\n if (!rule.pattern) return false\n const regex = new RegExp(rule.pattern, rule.caseSensitive ? \"\" : \"i\")\n return regex.test(name)\n default:\n return false\n }\n })\n}\n\nfunction getFrameworkEnvVarName(\n constantName: string,\n framework: Framework\n): string {\n const frameworkName = framework.name\n\n if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n return `NEXT_PUBLIC_${constantName}`\n } else if (frameworkName === FRAMEWORKS.astro.name) {\n return `PUBLIC_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n return `VITE_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.laravel.name ||\n frameworkName === FRAMEWORKS.manual.name\n ) {\n return constantName\n } else {\n return constantName\n }\n}\n\nfunction stripFrameworkPrefix(varName: string): string {\n return varName.replace(/^(NEXT_PUBLIC_|VITE_|PUBLIC_)/, \"\")\n}\n\nasync function transformEnvironmentVariables(\n sourceFile: SourceFile,\n config: Config\n): Promise<void> {\n const projectInfo = await getProjectInfo(config.resolvedPaths.cwd)\n\n if (!projectInfo) {\n return\n }\n\n const nodesToTransform: Array<{\n node: BinaryExpression | PropertyAccessExpression | CallExpression\n newText: string\n }> = []\n\n // 1. Transform environment variable access\n const binaryExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.BinaryExpression\n )\n\n for (const binaryExpr of binaryExpressions) {\n if (binaryExpr.getOperatorToken().getKind() === SyntaxKind.BarBarToken) {\n const left = binaryExpr.getLeft()\n const leftText = left.getText()\n\n if (leftText.match(/^process\\.env\\.[A-Z_]+$/)) {\n const match = leftText.match(/process\\.env\\.([A-Z_]+)/)\n if (match && match[1]) {\n const constantName = stripFrameworkPrefix(match[1])\n const frameworkName = projectInfo.framework.name\n\n let transformedEnvVar: string\n if (frameworkName === FRAMEWORKS.astro.name) {\n transformedEnvVar = `import.meta.env.PUBLIC_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n transformedEnvVar = `import.meta.env.VITE_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n transformedEnvVar = `process.env.NEXT_PUBLIC_${constantName}`\n } else {\n transformedEnvVar = `process.env.${constantName}`\n }\n\n const rightSide = binaryExpr.getRight().getText()\n const newExpression = `${transformedEnvVar} || ${rightSide}`\n\n nodesToTransform.push({\n node: binaryExpr,\n newText: newExpression,\n })\n }\n }\n }\n }\n\n // 2. Transform alert calls that contain environment variable lists\n const callExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.CallExpression\n )\n\n for (const callExpr of callExpressions) {\n const expression = callExpr.getExpression()\n const expressionText = expression.getText()\n\n // Check for alert calls\n if (expressionText.match(/^alert$/)) {\n const args = callExpr.getArguments()\n if (args.length > 0) {\n const firstArg = args[0]\n const argText = firstArg.getText()\n\n // Look for template literals or strings that contain environment variable lists\n if (\n argText.includes(\"TIPTAP_COLLAB_TOKEN\") ||\n argText.includes(\"TIPTAP_COLLAB_DOC_PREFIX\") ||\n argText.includes(\"TIPTAP_AI_TOKEN\")\n ) {\n let newArgText = argText\n\n const envVarsToTransform = [\n \"TIPTAP_COLLAB_DOC_PREFIX\",\n \"TIPTAP_COLLAB_APP_ID\",\n \"TIPTAP_COLLAB_TOKEN\",\n \"TIPTAP_AI_APP_ID\",\n \"TIPTAP_AI_TOKEN\",\n \"USE_JWT_TOKEN_API_ENDPOINT\",\n ]\n\n for (let constantName of envVarsToTransform) {\n const frameworkEnvVarName = getFrameworkEnvVarName(\n constantName,\n projectInfo.framework\n )\n newArgText = newArgText.replace(\n new RegExp(constantName, \"g\"),\n frameworkEnvVarName\n )\n }\n\n if (newArgText !== argText) {\n const newCallExpr = `${expressionText}(${newArgText})`\n nodesToTransform.push({\n node: callExpr,\n newText: newCallExpr,\n })\n }\n }\n }\n }\n }\n\n // 3. Transform standalone process.env\n const propertyAccessExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.PropertyAccessExpression\n )\n\n for (const propAccess of propertyAccessExpressions) {\n const propAccessText = propAccess.getText()\n\n if (propAccessText.match(/^process\\.env\\.[A-Z_]+$/)) {\n const parent = propAccess.getParent()\n if (parent?.getKind() === SyntaxKind.BinaryExpression) {\n continue\n }\n\n const match = propAccessText.match(/process\\.env\\.([A-Z_]+)/)\n if (match && match[1]) {\n const constantName = stripFrameworkPrefix(match[1])\n const frameworkName = projectInfo.framework.name\n\n let transformedEnvVar: string\n if (frameworkName === FRAMEWORKS.astro.name) {\n transformedEnvVar = `import.meta.env.PUBLIC_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n transformedEnvVar = `import.meta.env.VITE_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n transformedEnvVar = `process.env.NEXT_PUBLIC_${constantName}`\n } else {\n transformedEnvVar = `process.env.${constantName}`\n }\n\n nodesToTransform.push({\n node: propAccess,\n newText: transformedEnvVar,\n })\n }\n }\n }\n\n // Apply all transformations\n for (const { node, newText } of nodesToTransform) {\n try {\n node.replaceWithText(newText)\n } catch (error) {\n console.warn(`Skipping transformation of node: ${error}`)\n }\n }\n}\n\n/**\n * Main transformer function that removes excluded components from TypeScript/React source files\n * This transformer processes various AST nodes to remove unwanted components based on exclusion rules\n */\nexport const transformRemoveComponents: Transformer = async ({\n sourceFile,\n config,\n}) => {\n // Use default exclusion rules (could be made configurable in the future)\n const exclusionRules: ComponentExclusionRule[] = DEFAULT_EXCLUSIONS\n const filePath = sourceFile.getFilePath()\n // Collect all nodes to be modified instead of modifying immediately\n const nodesToModify: NodeToRemove[] = []\n\n // STEP 1: Collect excluded component imports\n const importDeclarations = sourceFile.getImportDeclarations()\n\n for (const importDeclaration of importDeclarations) {\n const moduleSpecifier = importDeclaration.getModuleSpecifierValue()\n\n // Check if the entire import module should be removed\n if (\n exclusionRules.some((rule) =>\n shouldExcludeComponent(moduleSpecifier, [rule], filePath)\n )\n ) {\n nodesToModify.push({ node: importDeclaration, action: \"remove\" })\n continue\n }\n\n // Handle default imports (import defaultName from \"...\")\n const defaultImport = importDeclaration.getDefaultImport()\n if (\n defaultImport &&\n shouldExcludeComponent(defaultImport.getText(), exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: importDeclaration, action: \"remove\" })\n continue\n }\n\n // Remove specific named imports that match exclusion rules\n const namedImports = importDeclaration.getNamedImports()\n const excludedImports = namedImports.filter((namedImport) =>\n shouldExcludeComponent(namedImport.getName(), exclusionRules, filePath)\n )\n\n if (excludedImports.length > 0) {\n excludedImports.forEach((excludedImport) =>\n nodesToModify.push({ node: excludedImport, action: \"remove\" })\n )\n\n // Check if this would remove all named imports\n const remainingImports = namedImports.filter(\n (namedImport) => !excludedImports.includes(namedImport)\n )\n\n if (remainingImports.length === 0 && !defaultImport) {\n nodesToModify.push({ node: importDeclaration, action: \"remove\" })\n }\n }\n }\n\n // STEP 2: Collect excluded component exports\n const exportDeclarations = sourceFile.getExportDeclarations()\n\n for (const exportDeclaration of exportDeclarations) {\n const namedExports = exportDeclaration.getNamedExports()\n const excludedExports = namedExports.filter((namedExport) =>\n shouldExcludeComponent(namedExport.getName(), exclusionRules, filePath)\n )\n\n if (excludedExports.length > 0) {\n excludedExports.forEach((excludedExport) =>\n nodesToModify.push({ node: excludedExport, action: \"remove\" })\n )\n\n // Check if this would remove all named exports\n const remainingExports = namedExports.filter(\n (namedExport) => !excludedExports.includes(namedExport)\n )\n\n if (remainingExports.length === 0) {\n nodesToModify.push({ node: exportDeclaration, action: \"remove\" })\n }\n }\n }\n\n // STEP 3: Collect excluded component variable declarations\n const variableStatements = sourceFile.getVariableStatements()\n\n for (const variableStatement of variableStatements) {\n const declarations = variableStatement.getDeclarations()\n const excludedDeclarations = declarations.filter((declaration) =>\n shouldExcludeComponent(declaration.getName(), exclusionRules, filePath)\n )\n\n if (excludedDeclarations.length > 0) {\n if (declarations.length === excludedDeclarations.length) {\n // Remove entire variable statement if all declarations are excluded\n nodesToModify.push({ node: variableStatement, action: \"remove\" })\n } else {\n // Remove only excluded declarations, keep others\n excludedDeclarations.forEach((declaration) =>\n nodesToModify.push({ node: declaration, action: \"remove\" })\n )\n }\n }\n }\n\n // STEP 4: Collect excluded component function declarations\n const functionDeclarations = sourceFile.getFunctions()\n\n for (const functionDeclaration of functionDeclarations) {\n const functionName = functionDeclaration.getName()\n if (\n functionName &&\n shouldExcludeComponent(functionName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: functionDeclaration, action: \"remove\" })\n }\n }\n\n // STEP 5: Collect excluded component interface declarations\n const interfaceDeclarations = sourceFile.getInterfaces()\n\n for (const interfaceDeclaration of interfaceDeclarations) {\n const interfaceName = interfaceDeclaration.getName()\n if (shouldExcludeComponent(interfaceName, exclusionRules, filePath)) {\n nodesToModify.push({ node: interfaceDeclaration, action: \"remove\" })\n }\n }\n\n // STEP 6: Collect excluded component type aliases\n const typeAliases = sourceFile.getTypeAliases()\n\n for (const typeAlias of typeAliases) {\n const typeName = typeAlias.getName()\n if (shouldExcludeComponent(typeName, exclusionRules, filePath)) {\n nodesToModify.push({ node: typeAlias, action: \"remove\" })\n }\n }\n\n // STEP 6.5: Collect excluded interface property signatures\n const propertySignatures = sourceFile.getDescendantsOfKind(\n SyntaxKind.PropertySignature\n )\n\n for (const propertySignature of propertySignatures) {\n const propName = propertySignature.getName()\n if (\n propName &&\n shouldExcludeComponent(propName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: propertySignature, action: \"remove\" })\n }\n }\n\n // STEP 7: Collect excluded JSX elements from React components\n const jsxElements = sourceFile.getDescendantsOfKind(SyntaxKind.JsxElement)\n\n for (const jsxElement of jsxElements) {\n const tagName = jsxElement.getOpeningElement().getTagNameNode().getText()\n if (shouldExcludeComponent(tagName, exclusionRules, filePath)) {\n nodesToModify.push({\n node: jsxElement,\n action: \"replace\",\n newText: \"\",\n })\n }\n }\n\n // STEP 8: Collect excluded self-closing JSX elements\n const jsxSelfClosingElements = sourceFile.getDescendantsOfKind(\n SyntaxKind.JsxSelfClosingElement\n )\n\n for (const jsxSelfClosingElement of jsxSelfClosingElements) {\n const tagName = jsxSelfClosingElement.getTagNameNode().getText()\n if (shouldExcludeComponent(tagName, exclusionRules, filePath)) {\n nodesToModify.push({\n node: jsxSelfClosingElement,\n action: \"replace\",\n newText: \"\",\n })\n }\n }\n\n // STEP 9: Collect excluded component properties from objects\n const propertyAssignments = sourceFile.getDescendantsOfKind(\n SyntaxKind.PropertyAssignment\n )\n\n for (const propertyAssignment of propertyAssignments) {\n const propertyName = propertyAssignment.getName()\n if (\n propertyName &&\n shouldExcludeComponent(propertyName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: propertyAssignment, action: \"remove\" })\n }\n }\n\n // STEP 10: Collect excluded JSX attributes\n const jsxAttributes = sourceFile.getDescendantsOfKind(SyntaxKind.JsxAttribute)\n\n for (const jsxAttribute of jsxAttributes) {\n const attributeName = jsxAttribute.getNameNode().getText()\n if (\n attributeName &&\n shouldExcludeComponent(attributeName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: jsxAttribute, action: \"remove\" })\n }\n }\n\n // STEP 11: Collect excluded parameters from function/method signatures\n const parameters = sourceFile.getDescendantsOfKind(SyntaxKind.Parameter)\n\n for (const parameter of parameters) {\n const parameterName = parameter.getName()\n if (\n parameterName &&\n shouldExcludeComponent(parameterName, exclusionRules, filePath)\n ) {\n const paramList = parameter.getParent()\n\n // Only proceed if the parent is a function-like structure\n if (\n paramList &&\n (Node.isFunctionDeclaration(paramList) ||\n Node.isArrowFunction(paramList) ||\n Node.isFunctionExpression(paramList) ||\n Node.isMethodDeclaration(paramList))\n ) {\n const allParams = paramList.getParameters()\n const index = allParams.indexOf(parameter)\n\n // Handle comma removal for cleaner output\n if (index !== -1) {\n if (index === allParams.length - 1 && index > 0) {\n const prev = parameter.getPreviousSibling()\n if (prev?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: prev, action: \"remove\" })\n }\n } else {\n const next = parameter.getNextSibling()\n if (next?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: next, action: \"remove\" })\n }\n }\n\n nodesToModify.push({ node: parameter, action: \"remove\" })\n }\n }\n }\n }\n\n // STEP 11.1: Handle function arguments in call expressions\n const callExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.CallExpression\n )\n\n for (const callExpr of callExpressions) {\n const args = callExpr.getArguments()\n for (let i = 0; i < args.length; i++) {\n const arg = args[i]\n const argText = arg.getText()\n\n if (shouldExcludeComponent(argText, exclusionRules, filePath)) {\n // Handle comma removal for cleaner output\n if (i === args.length - 1) {\n // Last argument - remove preceding comma if exists\n const prevSibling = arg.getPreviousSibling()\n if (prevSibling && prevSibling.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: prevSibling, action: \"remove\" })\n }\n } else {\n // Not last argument - remove following comma if exists\n const nextSibling = arg.getNextSibling()\n if (nextSibling && nextSibling.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: nextSibling, action: \"remove\" })\n }\n }\n\n nodesToModify.push({ node: arg, action: \"remove\" })\n }\n }\n }\n\n // STEP 11.5: Collect excluded binding elements (destructured parameters)\n const bindingElements = sourceFile.getDescendantsOfKind(\n SyntaxKind.BindingElement\n )\n\n for (const bindingElement of bindingElements) {\n const bindingName = bindingElement.getName()\n if (\n bindingName &&\n shouldExcludeComponent(bindingName, exclusionRules, filePath)\n ) {\n // Handle comma cleanup (already correct in your code)\n const bindingPattern = bindingElement.getParent()\n if (bindingPattern) {\n const allBindings = bindingPattern.getDescendantsOfKind(\n SyntaxKind.BindingElement\n )\n const bindingIndex = allBindings.indexOf(bindingElement)\n\n if (bindingIndex === allBindings.length - 1) {\n const prevSibling = bindingElement.getPreviousSibling()\n if (prevSibling?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: prevSibling, action: \"remove\" })\n }\n } else {\n const nextSibling = bindingElement.getNextSibling()\n if (nextSibling?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: nextSibling, action: \"remove\" })\n }\n }\n }\n\n nodesToModify.push({ node: bindingElement, action: \"remove\" })\n }\n }\n\n // STEP 12: Collect excluded identifiers in function calls and expressions\n const identifiers = sourceFile.getDescendantsOfKind(SyntaxKind.Identifier)\n\n for (const identifier of identifiers) {\n const identifierName = identifier.getText()\n if (shouldExcludeComponent(identifierName, exclusionRules, filePath)) {\n const parent = identifier.getParent()\n\n // Handle different contexts where the identifier appears\n if (parent) {\n const parentKind = parent.getKind()\n\n // Remove entire call expression if it's calling an excluded function\n if (parentKind === SyntaxKind.CallExpression) {\n const callExpr = parent as CallExpression\n if (callExpr.getExpression() === identifier) {\n // This is a function call like getDocumentId()\n nodesToModify.push({ node: callExpr, action: \"remove\" })\n } else {\n // This is an argument in a function call\n const args = callExpr.getArguments()\n const argIndex = args.findIndex((arg) => arg === identifier)\n if (argIndex !== -1) {\n nodesToModify.push({ node: identifier, action: \"remove\" })\n }\n }\n }\n\n // Remove property access expressions with excluded identifiers\n if (parentKind === SyntaxKind.PropertyAccessExpression) {\n const propAccess = parent as PropertyAccessExpression\n if (propAccess.getName() === identifierName) {\n nodesToModify.push({ node: propAccess, action: \"remove\" })\n }\n }\n\n // Remove variable references and expressions\n if (\n parentKind === SyntaxKind.VariableDeclaration ||\n parentKind === SyntaxKind.BinaryExpression ||\n parentKind === SyntaxKind.IfStatement ||\n parentKind === SyntaxKind.ConditionalExpression\n ) {\n nodesToModify.push({ node: identifier, action: \"remove\" })\n }\n\n // Remove from object literal property values\n if (parentKind === SyntaxKind.PropertyAssignment) {\n const propAssignment = parent as PropertyAssignment\n if (propAssignment.getInitializer() === identifier) {\n nodesToModify.push({ node: propAssignment, action: \"remove\" })\n }\n }\n }\n }\n }\n\n // STEP 13: Collect excluded shorthand property assignments (e.g., { initialContent })\n const shorthandPropertyAssignments = sourceFile.getDescendantsOfKind(\n SyntaxKind.ShorthandPropertyAssignment\n )\n\n for (const shorthandProp of shorthandPropertyAssignments) {\n const propName = shorthandProp.getName()\n if (\n propName &&\n shouldExcludeComponent(propName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: shorthandProp, action: \"remove\" })\n }\n }\n\n // Apply environment variable transformations first (before removing nodes)\n await transformEnvironmentVariables(sourceFile, config)\n\n // STEP 16: Apply all collected modifications\n // Sort by position (deepest nodes first) to avoid accessing removed parents\n nodesToModify.sort((a, b) => {\n const aStart = a.node.getStart?.() ?? 0\n const bStart = b.node.getStart?.() ?? 0\n return bStart - aStart // Reverse order - process deepest/rightmost first\n })\n\n // Apply transformations safely\n for (const { node, action, newText } of nodesToModify) {\n try {\n // Check if node still exists and hasn't been removed\n if (node.wasForgotten?.() === true) {\n continue // Skip nodes that were already removed\n }\n\n if (action === \"remove\") {\n if (typeof node.remove === \"function\") {\n node.remove()\n }\n } else if (action === \"replace\" && newText !== undefined) {\n node.replaceWithText(newText)\n }\n } catch (error) {\n // console.warn(`Skipping transformation of node: ${error}`)\n // Continue with other transformations even if one fails\n }\n }\n\n // Return the modified source file with excluded components removed\n return sourceFile\n}\n","import * as sass from \"sass\"\n\n/**\n * Converts SCSS content to CSS\n * @param scssContent The SCSS content to convert\n * @returns The compiled CSS content\n */\nexport async function transformScssToCSS(scssContent: string): Promise<string> {\n try {\n const result = sass.compileString(scssContent, {\n style: \"expanded\",\n })\n return result.css\n } catch (error) {\n throw new Error(\n `Failed to compile SCSS to CSS: ${error instanceof Error ? error.message : String(error)}`\n )\n }\n}\n","import { Config } from \"@/src/utils/get-config\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { RegistryItem } from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { execa } from \"execa\"\nimport { colors } from \"@/src/utils/colors\"\n\n/**\n * Installs development dependencies for a component\n *\n * @param devDependencies List of development dependencies to install\n * @param config Configuration object with project paths\n * @param options Additional options\n */\nexport async function updateDevDependencies(\n devDependencies: RegistryItem[\"devDependencies\"],\n config: Config,\n options: {\n silent?: boolean\n }\n) {\n devDependencies = Array.from(new Set(devDependencies))\n if (!devDependencies?.length) {\n return\n }\n\n options = {\n silent: false,\n ...options,\n }\n\n const devDependenciesSpinner = spinner(\n `Installing development dependencies.`,\n {\n silent: options.silent,\n }\n )?.start()\n const packageManager = await getPackageManager(config.resolvedPaths.cwd)\n\n devDependenciesSpinner?.start()\n\n // Different package managers have different flags for dev dependencies\n const devFlag = packageManager === \"npm\" ? \"--save-dev\" : \"-D\"\n\n await execa(\n packageManager,\n [packageManager === \"npm\" ? \"install\" : \"add\", devFlag, ...devDependencies],\n {\n cwd: config.resolvedPaths.cwd,\n }\n )\n\n devDependenciesSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n}\n","/**\n * Converts kebab-case or snake_case to Title Case\n */\nexport function toReadableName(input: string): string {\n return input\n .split(/[-_]/)\n .map((word) => word.charAt(0).toUpperCase() + word.slice(1))\n .join(\" \")\n}\n","import fetch from \"node-fetch\"\nimport { HttpsProxyAgent } from \"https-proxy-agent\"\nimport { logger } from \"@/src/utils/logger\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { colors } from \"@/src/utils/colors\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\nimport { saveAuthToken, type PackageManager } from \"./package-manager-config\"\nimport { REGISTRY_URL } from \"./registry\"\n\nconst AUTH_API_URL = `${REGISTRY_URL}/api/cli/v1`\n\ntype LoginResponse = {\n token: string\n authToken: string\n}\n\ntype PlanResponse = Array<{\n name: string\n}>\n\ntype AuthTokens = {\n bearerToken: string\n authToken: string\n}\n\nexport type AuthResult = {\n success: boolean\n tokens?: AuthTokens\n error?: string\n}\n\nexport type AuthStatus = {\n authenticated: boolean\n user?: string\n plans?: string[]\n expires?: string | null\n token?: string\n}\n\nconst httpAgent = process.env.https_proxy\n ? new HttpsProxyAgent(process.env.https_proxy)\n : undefined\n\n/**\n * Authenticate a user with the Tiptap registry\n */\nexport async function authenticateUser({\n email,\n password,\n packageManager,\n writeConfig = true,\n cwd,\n}: {\n email?: string\n password?: string\n packageManager: PackageManager\n writeConfig?: boolean\n cwd: string\n}): Promise<AuthResult> {\n const loginSpinner = spinner(\n \"Authenticating with Tiptap registry...\"\n )?.start()\n\n try {\n if (!email || !password) {\n loginSpinner?.fail(\"Authentication failed\")\n return { success: false, error: \"Invalid credentials\" }\n }\n\n const tokens = await requestAuthTokens(email, password)\n\n let userPlans: string[] = []\n const plansResponse = await fetch(`${AUTH_API_URL}/plans`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${tokens.bearerToken}`,\n },\n agent: httpAgent,\n })\n\n if (!plansResponse.ok) {\n loginSpinner?.fail(\"Authentication failed (could not load user plans)\")\n return {\n success: false,\n error: `Failed to fetch user plans: ${plansResponse.status}`,\n }\n }\n\n const plans = (await plansResponse.json()) as PlanResponse\n userPlans = plans.map((plan) => plan.name)\n\n if (!userPlans.length) {\n loginSpinner?.fail(\"Authentication failed (no active plans)\")\n return { success: false, error: \"No active plans found for user\" }\n }\n\n tokenStorage.setBearerToken(tokens.bearerToken, {\n email,\n plans: userPlans,\n })\n tokenStorage.setAuthToken(tokens.authToken)\n\n if (writeConfig) {\n const success = await saveAuthToken(tokens.authToken, packageManager, cwd)\n if (!success) {\n loginSpinner?.fail(\"Failed to save authentication token\")\n return { success: false, error: \"Could not save authentication token\" }\n }\n }\n\n loginSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: \"Authentication successful\",\n })\n return { success: true, tokens }\n } catch (error) {\n loginSpinner?.fail(\"Authentication failed\")\n return {\n success: false,\n error:\n error instanceof Error\n ? error.message\n : \"Unknown error during authentication\",\n }\n }\n}\n\n/**\n * Request an authentication token from the API\n */\nasync function requestAuthTokens(\n email: string,\n password: string\n): Promise<AuthTokens> {\n const response = await fetch(`${AUTH_API_URL}/login`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ email, password }),\n agent: httpAgent,\n })\n\n if (!response.ok) {\n throw new Error(`Error ${response.status}: ${response.statusText}`)\n }\n\n const data = (await response.json()) as LoginResponse\n\n return {\n bearerToken: data.token,\n authToken: data.authToken,\n }\n}\n\n/**\n * Check if user is authenticated with Tiptap registry\n */\nexport async function checkAuthStatus(): Promise<AuthStatus> {\n try {\n const bearerToken = tokenStorage.getBearerToken()\n\n if (!bearerToken) {\n return { authenticated: false }\n }\n\n if (!tokenStorage.isValidToken()) {\n return { authenticated: false }\n }\n\n // Use plans API to verify token is still valid\n let userPlans: string[] = []\n try {\n const plansResponse = await fetch(`${AUTH_API_URL}/plans`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${bearerToken}`,\n },\n agent: httpAgent,\n })\n\n if (!plansResponse.ok) {\n tokenStorage.clear()\n return { authenticated: false }\n }\n\n const plans = (await plansResponse.json()) as PlanResponse\n userPlans = plans.map((plan) => plan.name)\n\n // Update stored plans\n const userInfo = tokenStorage.getUserInfo()\n tokenStorage.setBearerToken(bearerToken, {\n email: userInfo.email,\n plans: userPlans,\n })\n } catch (error) {\n tokenStorage.clear()\n return { authenticated: false }\n }\n\n const userInfo = tokenStorage.getUserInfo()\n const expiration = tokenStorage.getTokenExpiration()\n\n return {\n authenticated: true,\n user: userInfo.email || \"unknown user\",\n plans: userPlans,\n expires: expiration,\n token: bearerToken,\n }\n } catch (error) {\n logger.error(\n `Auth status check error: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n return { authenticated: false }\n }\n}\n\n/**\n * Logout user from Tiptap registry\n */\nexport async function logoutUser(): Promise<{\n success: boolean\n error?: string\n}> {\n try {\n const bearerToken = tokenStorage.getBearerToken()\n\n if (bearerToken) {\n const response = await fetch(`${AUTH_API_URL}/logout`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${bearerToken}`,\n },\n agent: httpAgent,\n })\n\n if (!response.ok) {\n logger.warn(\"Logout API call failed, but clearing local tokens anyway\")\n }\n }\n\n tokenStorage.clear()\n return { success: true }\n } catch (error) {\n tokenStorage.clear()\n return {\n success: false,\n error:\n error instanceof Error ? error.message : \"Unknown error during logout\",\n }\n }\n}\n\n/**\n * Check if user has a specific plan\n */\nexport function userHasPlan(planName: string): boolean {\n return tokenStorage.hasPlan(planName)\n}\n\n/**\n * Check if user has any of the specified plans\n */\nexport function userHasAnyPlan(planNames: string[]): boolean {\n return planNames.some((plan) => tokenStorage.hasPlan(plan))\n}\n\n/**\n * Get user's plans\n */\nexport function getUserPlans(): string[] {\n return tokenStorage.getUserInfo().plans || []\n}\n","import fs from \"fs-extra\"\nimport path from \"path\"\nimport os from \"os\"\nimport { execa } from \"execa\"\nimport { logger } from \"@/src/utils/logger\"\nimport yaml from \"yaml\"\n\nconst TIPTAP_REGISTRY = \"https://registry.tiptap.dev/\"\nconst AUTH_TOKEN_KEY = \"//registry.tiptap.dev/:_authToken\"\nconst TIPTAP_PRO_REGISTRY_KEY = \"@tiptap-pro:registry\"\n\nexport type PackageManager = \"npm\" | \"yarn\" | \"pnpm\" | \"bun\"\n\n/**\n * Add .npmrc to .gitignore if it's not already there\n */\nasync function addNpmrcToGitignore(cwd: string): Promise<void> {\n try {\n const gitignorePath = path.join(cwd, \".gitignore\")\n const npmrcEntry = \".npmrc\"\n let gitignoreContent = \"\"\n\n if (await fs.pathExists(gitignorePath)) {\n gitignoreContent = await fs.readFile(gitignorePath, \"utf8\")\n }\n\n const lines = gitignoreContent.split(\"\\n\")\n const hasNpmrcEntry = lines.some(\n (line) =>\n line.trim() === npmrcEntry ||\n line.trim() === \"/.npmrc\" ||\n line.trim() === \"**/.npmrc\"\n )\n\n if (!hasNpmrcEntry) {\n const newContent = gitignoreContent.trim()\n ? `${gitignoreContent}\\n\\n# Authentication tokens\\n${npmrcEntry}\\n`\n : `# Authentication tokens\\n${npmrcEntry}\\n`\n\n await fs.writeFile(gitignorePath, newContent)\n }\n } catch (error) {\n logger.warn(\n `Could not update .gitignore: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n }\n}\n\n/**\n * Save authentication token to package manager config\n */\nexport async function saveAuthToken(\n token: string,\n packageManager: PackageManager,\n cwd: string\n): Promise<boolean> {\n try {\n let createdNpmrc = false\n\n switch (packageManager) {\n case \"npm\":\n await saveNpmToken(token, cwd)\n createdNpmrc = true\n break\n case \"yarn\":\n await saveYarnToken(token, cwd)\n createdNpmrc = await fs.pathExists(path.join(cwd, \".npmrc\"))\n break\n case \"pnpm\":\n case \"bun\":\n await saveToNpmrc(path.join(cwd, \".npmrc\"), token)\n createdNpmrc = true\n break\n }\n\n if (createdNpmrc) {\n await addNpmrcToGitignore(cwd)\n }\n\n return true\n } catch (error) {\n logger.error(\n `Error saving auth token: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n return false\n }\n}\n\n/**\n * Save token for npm\n */\nasync function saveNpmToken(token: string, cwd: string): Promise<void> {\n await execa(\n \"npm\",\n [\n \"config\",\n \"set\",\n TIPTAP_PRO_REGISTRY_KEY,\n TIPTAP_REGISTRY,\n \"--location=project\",\n ],\n { cwd }\n )\n\n await execa(\n \"npm\",\n [\"config\", \"set\", AUTH_TOKEN_KEY, token, \"--location=project\"],\n { cwd }\n )\n}\n\n/**\n * Save token for yarn (handles v1 and v2+)\n */\nasync function saveYarnToken(token: string, cwd: string): Promise<void> {\n try {\n const { stdout: yarnVersion } = await execa(\"yarn\", [\"--version\"], { cwd })\n const isYarnV1 = yarnVersion.startsWith(\"1.\")\n\n if (isYarnV1) {\n // For Yarn 1.x\n await execa(\n \"yarn\",\n [\n \"config\",\n \"set\",\n TIPTAP_PRO_REGISTRY_KEY,\n TIPTAP_REGISTRY,\n \"--location=project\",\n ],\n { cwd }\n )\n\n await execa(\n \"yarn\",\n [\"config\", \"set\", AUTH_TOKEN_KEY, token, \"--location=project\"],\n { cwd }\n )\n } else {\n // For Yarn 2+ (Berry)\n await saveYarnBerryToken(token, cwd)\n }\n } catch (error) {\n // Fallback to .npmrc for yarn\n await saveToNpmrc(path.join(cwd, \".npmrc\"), token)\n }\n}\n\n/**\n * Save token for Yarn Berry (v2+)\n */\nasync function saveYarnBerryToken(token: string, cwd: string): Promise<void> {\n const yarnrcPath = path.join(cwd, \".yarnrc.yml\")\n let yamlObj: Record<string, unknown> = {}\n\n // Read existing config if it exists\n if (fs.existsSync(yarnrcPath)) {\n const yarnrcContent = await fs.readFile(yarnrcPath, \"utf8\")\n try {\n yamlObj = yaml.parse(yarnrcContent) || {}\n } catch (e) {\n // If parsing fails, start with empty object\n }\n }\n\n // Ensure the structure exists\n if (!yamlObj.npmScopes) {\n yamlObj.npmScopes = {}\n }\n\n // Set or update the tiptap-pro scope\n ;(yamlObj.npmScopes as Record<string, unknown>)[\"tiptap-pro\"] = {\n npmRegistryServer: TIPTAP_REGISTRY,\n npmAuthToken: token,\n }\n\n // Write back to file\n await fs.writeFile(yarnrcPath, yaml.stringify(yamlObj))\n}\n\n/**\n * Update .npmrc file with token\n */\nasync function saveToNpmrc(npmrcPath: string, token: string): Promise<void> {\n let npmrcContent = \"\"\n\n // Read existing file if it exists\n if (fs.existsSync(npmrcPath)) {\n npmrcContent = await fs.readFile(npmrcPath, \"utf8\")\n }\n\n // Parse .npmrc content\n const { lines, processedKeys } = parseNpmrc(npmrcContent, token)\n\n // Add missing keys\n if (!processedKeys.has(TIPTAP_PRO_REGISTRY_KEY)) {\n lines.push(`${TIPTAP_PRO_REGISTRY_KEY}=${TIPTAP_REGISTRY}`)\n }\n\n if (!processedKeys.has(AUTH_TOKEN_KEY)) {\n lines.push(`${AUTH_TOKEN_KEY}=${token}`)\n }\n\n // Ensure file ends with a newline\n if (lines.length > 0 && lines[lines.length - 1] !== \"\") {\n lines.push(\"\")\n }\n\n // Write the updated content back to the file\n await fs.writeFile(npmrcPath, lines.join(\"\\n\"))\n}\n\n/**\n * Parse .npmrc content\n */\nfunction parseNpmrc(\n npmrcContent: string,\n token: string\n): {\n lines: string[]\n processedKeys: Set<string>\n} {\n const lines: string[] = []\n const processedKeys = new Set<string>()\n\n // Split content into lines\n const contentLines = npmrcContent.split(\"\\n\")\n\n // Process each line\n for (const line of contentLines) {\n const trimmedLine = line.trim()\n\n // Skip empty lines or add them as-is\n if (!trimmedLine) {\n lines.push(line)\n continue\n }\n\n // Preserve comments\n if (trimmedLine.startsWith(\"#\")) {\n lines.push(line)\n continue\n }\n\n // Process key-value pairs\n const index = line.indexOf(\"=\")\n if (index !== -1) {\n const key = line.substring(0, index).trim()\n\n // Update specific keys\n if (key === TIPTAP_PRO_REGISTRY_KEY) {\n lines.push(`${TIPTAP_PRO_REGISTRY_KEY}=${TIPTAP_REGISTRY}`)\n processedKeys.add(key)\n } else if (key === AUTH_TOKEN_KEY) {\n lines.push(`${AUTH_TOKEN_KEY}=${token}`)\n processedKeys.add(key)\n } else {\n // Keep other keys unchanged\n lines.push(line)\n }\n } else {\n // Keep lines that aren't key-value pairs\n lines.push(line)\n }\n }\n\n return { lines, processedKeys }\n}\n\n/**\n * Get auth token from package manager config\n */\nexport async function getAuthToken(\n packageManager: PackageManager,\n cwd: string\n): Promise<string | null> {\n try {\n const projectToken = await checkProjectNpmrc(cwd)\n if (projectToken) {\n return projectToken\n }\n\n if (packageManager === \"npm\") {\n const npmAuthToken = await getNpmAuthToken(cwd)\n return npmAuthToken\n }\n\n const globalAuthToken = await checkGlobalNpmrc()\n return globalAuthToken\n } catch (error) {\n return null\n }\n}\n\n/**\n * Check project .npmrc for auth token\n */\nasync function checkProjectNpmrc(cwd: string): Promise<string | null> {\n const projectNpmrcPath = path.join(cwd, \".npmrc\")\n if (fs.existsSync(projectNpmrcPath)) {\n const content = await fs.readFile(projectNpmrcPath, \"utf8\")\n return extractAuthToken(content)\n }\n return null\n}\n\n/**\n * Get npm auth token using npm config command\n */\nasync function getNpmAuthToken(cwd: string): Promise<string | null> {\n const { stdout } = await execa(\"npm\", [\"config\", \"get\", AUTH_TOKEN_KEY], {\n cwd,\n })\n\n return stdout && stdout !== \"undefined\" ? stdout.trim() : null\n}\n\n/**\n * Check global .npmrc file for auth token\n */\nasync function checkGlobalNpmrc(): Promise<string | null> {\n const globalNpmrcPath = path.join(os.homedir(), \".npmrc\")\n\n if (fs.existsSync(globalNpmrcPath)) {\n const content = await fs.readFile(globalNpmrcPath, \"utf8\")\n return extractAuthToken(content)\n }\n\n return null\n}\n\n/**\n * Extract auth token from config string\n */\nexport function extractAuthToken(configString: string): string | null {\n // Split into lines and filter for registry.tiptap.dev\n const lines = configString\n .split(\"\\n\")\n .filter((line) => line.startsWith(\"//registry.tiptap.dev/:_authToken=\"))\n\n if (lines.length === 0) {\n return null\n }\n\n // Extract the token after the \"=\" sign\n const token = lines[0].split(\"=\")[1]?.trim()\n return token || null\n}\n","import { Command } from \"commander\"\nimport { execa } from \"execa\"\nimport { z } from \"zod\"\nimport { confirm, input, password as passwordPrompt } from \"@inquirer/prompts\"\nimport { authenticateUser, checkAuthStatus } from \"@/src/utils/auth\"\nimport { colors } from \"@/src/utils/colors\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { logoutUser } from \"@/src/utils/auth\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { getAuthToken } from \"@/src/utils/package-manager-config\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\n\nexport const authOptionsSchema = z.object({\n cwd: z.string(),\n email: z.string().optional(),\n password: z.string().optional(),\n writeConfig: z.boolean().optional(),\n showMessage: z.boolean().default(true),\n})\n\ntype AuthOptions = z.infer<typeof authOptionsSchema>\ntype PackageManager = \"npm\" | \"yarn\" | \"pnpm\" | \"bun\"\n\n/**\n * Creates a themed input prompt with consistent styling\n */\nconst createThemedInput = (\n message: string,\n options: {\n required?: boolean\n validate?: (value: string) => boolean | string\n } = {}\n) => {\n return input({\n message: colors.reset(message),\n required: options.required ?? true,\n validate:\n options.validate ??\n ((value: string) => (value ? true : \"This field is required\")),\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Creates a themed password prompt with consistent styling\n */\nconst createThemedPassword = (\n message: string,\n options: {\n validate?: (value: string) => boolean | string\n } = {}\n) => {\n return passwordPrompt({\n message: colors.reset(message),\n validate:\n options.validate ??\n ((value: string) => (value ? true : \"This field is required\")),\n mask: \"*\",\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Creates a themed confirmation prompt with consistent styling\n */\nexport const createThemedConfirm = (\n message: string,\n defaultValue: boolean = true\n) => {\n return confirm({\n message: colors.reset(message),\n default: defaultValue,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Get the appropriate configuration file name based on package manager\n */\nfunction getConfigFileName(packageManager: PackageManager): string {\n switch (packageManager) {\n case \"npm\":\n return \".npmrc (via npm config)\"\n case \"yarn\":\n return \".yarnrc.yml or .npmrc (depending on Yarn version)\"\n case \"pnpm\":\n case \"bun\":\n return \".npmrc\"\n default:\n return \"configuration file\"\n }\n}\n\n/**\n * Display appropriate token configuration instructions for each package manager\n */\nasync function displayTokenInstructions(\n packageManager: PackageManager,\n token: string,\n cwd: string\n) {\n logger.log(\n `To use this token, add it to your project's package manager configuration in ${colors.cyan(cwd)}:`\n )\n\n if (packageManager === \"npm\") {\n logger.log(\"Run these commands in your project directory:\")\n logger.log(\n ` npm config set @tiptap-pro:registry https://registry.tiptap.dev/`\n )\n logger.log(` npm config set //registry.tiptap.dev/:_authToken ${token}`)\n logger.log(`\\nOr add to your project's .npmrc file:`)\n logger.log(` @tiptap-pro:registry=https://registry.tiptap.dev/`)\n logger.log(` //registry.tiptap.dev/:_authToken=${token}`)\n } else if (packageManager === \"yarn\") {\n const isYarnV1 = await checkYarnVersion(cwd)\n\n if (isYarnV1) {\n logger.log(\"Run these commands in your project directory:\")\n logger.log(\n ` yarn config set @tiptap-pro:registry https://registry.tiptap.dev/`\n )\n logger.log(` yarn config set //registry.tiptap.dev/:_authToken ${token}`)\n } else {\n logger.log(`Add to your project's .yarnrc.yml file:`)\n logger.log(\n `npmScopes:\\n tiptap-pro:\\n npmRegistryServer: \"https://registry.tiptap.dev/\"\\n npmAuthToken: \"${token}\"`\n )\n }\n } else if (packageManager === \"pnpm\" || packageManager === \"bun\") {\n logger.log(`Add to your project's .npmrc file:`)\n logger.log(\n colors.cyan(\n `@tiptap-pro:registry=https://registry.tiptap.dev/\\n//registry.tiptap.dev/:_authToken=${token}`\n )\n )\n }\n}\n\n/**\n * Check if the project is using Yarn v1\n */\nasync function checkYarnVersion(cwd: string): Promise<boolean> {\n try {\n const yarnVersionOutput = await execa(\"yarn\", [\"--version\"], { cwd })\n return yarnVersionOutput.stdout.startsWith(\"1.\")\n } catch (error) {\n // If yarn command fails, default to false\n return false\n }\n}\n\n/**\n * Handle the login process with interactive prompts if needed\n */\nexport async function handleLogin(options: AuthOptions) {\n let { email, password, writeConfig, showMessage } = options\n const { cwd } = options\n\n // Interactive prompts if necessary values aren't provided\n if (!email) {\n email = await createThemedInput(\"Email:\", {\n validate: (value: string) => (value ? true : \"Please enter your email\"),\n })\n }\n\n if (!password) {\n password = await createThemedPassword(\"Password:\", {\n validate: (value: string) =>\n value ? true : \"Please enter your password\",\n })\n }\n\n // User cancelled the prompt\n if (!email || !password) {\n logger.error(\"Authentication cancelled\")\n process.exit(0)\n }\n\n const packageManager = await getPackageManager(cwd)\n\n // Prompt for writeConfig if not explicitly set via command line\n if (writeConfig === undefined) {\n const configFileName = getConfigFileName(packageManager)\n\n writeConfig = await createThemedConfirm(\n `Would you like to save the auth token to your ${configFileName}?`\n )\n\n // User cancelled the prompt\n if (writeConfig === undefined) {\n logger.error(\"Authentication cancelled\")\n process.exit(0)\n }\n }\n\n const result = await authenticateUser({\n email,\n password,\n packageManager,\n writeConfig: writeConfig ?? false,\n cwd,\n })\n\n if (result.success && result.tokens) {\n if (writeConfig && showMessage) {\n logger.log(\n `\\nRegistry auth token saved to project directory for ${colors.cyan(packageManager)}`\n )\n logger.log(`.npmrc file saved at: ${colors.cyan(cwd)}`)\n logger.log(`Project path: ${colors.cyan(cwd)}`)\n } else if (result.tokens.authToken && showMessage) {\n logger.log(\n `\\nRegistry Auth Token: ${colors.cyan(result.tokens.authToken)}`\n )\n logger.log(\"This token should be added to your project's configuration:\")\n await displayTokenInstructions(\n packageManager,\n result.tokens.authToken,\n cwd\n )\n }\n\n if (showMessage) {\n logger.log(`Bearer token saved globally for CLI authentication`)\n }\n\n return true\n } else {\n logger.error(\"Authentication failed: \" + result.error)\n\n return false\n }\n}\n\n/**\n * Handle checking authentication status\n */\nasync function handleStatusCheck(cwd: string) {\n const packageManager = await getPackageManager(cwd)\n const status = await checkAuthStatus()\n\n if (status.authenticated) {\n logger.success(\n `Authenticated as ${colors.cyan(status.user ?? \"unknown user\")}`\n )\n\n // Display plans\n if (status.plans && status.plans.length > 0) {\n if (status.plans.length === 1) {\n logger.log(`Plan: ${colors.cyan(status.plans[0])}`)\n } else {\n logger.log(`Plans: ${colors.cyan(status.plans.join(\", \"))}`)\n }\n } else {\n logger.log(`Plans: ${colors.cyan(\"No active plans\")}`)\n }\n\n if (status.expires) {\n const expiryDate = new Date(status.expires)\n const now = new Date()\n const daysUntilExpiry = Math.ceil(\n (expiryDate.getTime() - now.getTime()) / (1000 * 60 * 60 * 24)\n )\n\n if (daysUntilExpiry > 30) {\n logger.log(\n `Token expires: ${colors.cyan(expiryDate.toDateString())} (${daysUntilExpiry} days)`\n )\n } else if (daysUntilExpiry > 0) {\n logger.log(\n `Token expires: ${colors.yellow(expiryDate.toDateString())} (${daysUntilExpiry} days)`\n )\n } else {\n logger.log(`Token expires: ${colors.red(\"Expired\")}`)\n }\n }\n\n if (status.token) {\n const tokenPreview = status.token.substring(0, 10) + \"...\"\n logger.log(`Bearer token: ${colors.cyan(tokenPreview)}`)\n }\n\n const registryToken = await getAuthToken(packageManager, cwd)\n if (registryToken) {\n const registryPreview = registryToken.substring(0, 10) + \"...\"\n logger.log(`Registry token: ${colors.cyan(registryPreview)}`)\n } else {\n logger.log(\n `Registry token: ${colors.yellow(\"Not configured for this project\")}`\n )\n logger.log(\n `Run ${colors.cyan(\"@tiptap/cli login --write-config\")} to configure for this project`\n )\n }\n } else {\n logger.log(\"Not authenticated with Tiptap registry\")\n logger.log(`Run ${colors.cyan(`@tiptap/cli login`)} to authenticate`)\n }\n}\n\nexport const login = new Command()\n .command(\"login\")\n .description(\"log in to your Tiptap Cloud account\")\n .option(\"-e, --email <email>\", \"your account email\")\n .option(\"-p, --password <password>\", \"your account password\")\n .option(\n \"--write-config\",\n \"write the auth token to your package manager config\",\n undefined\n )\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .action(async (options) => {\n try {\n const opts = authOptionsSchema.parse(options)\n await handleLogin(opts)\n } catch (error) {\n handleError(error)\n }\n })\n\nexport const status = new Command()\n .command(\"status\")\n .description(\"review your Tiptap Cloud authentication status\")\n .description(\"log out from your Tiptap registry account\")\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .action(async (options) => {\n const opts = authOptionsSchema.parse(options)\n const { cwd } = opts\n try {\n await handleStatusCheck(cwd)\n } catch (error) {\n handleError(error)\n }\n })\n\nexport const logout = new Command()\n .command(\"logout\")\n .description(\"log out from your Tiptap registry account\")\n\n .action(async () => {\n try {\n const logoutSpinner = spinner(\"Logging out...\")?.start()\n\n const result = await logoutUser()\n\n if (result.success) {\n logoutSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: \"Successfully logged out\",\n })\n } else {\n logoutSpinner?.fail(\"Logout failed\")\n logger.error(\"Logout failed: \" + result.error)\n }\n } catch (error) {\n handleError(error)\n }\n })\n\n/**\n * Handle displaying license information\n */\nasync function handleLicenseInfo() {\n logger.log(\"\")\n logger.log(colors.yellow(\"📋 Tiptap Pro License Information\"))\n logger.log(\"\")\n\n // Check license acceptance status\n const hasAccepted = tokenStorage.hasAcceptedLicense()\n const userInfo = tokenStorage.getUserInfo()\n\n if (hasAccepted) {\n logger.log(`${colors.cyan(\"✔\")} Pro License and Terms of Service accepted`)\n if (userInfo.email) {\n logger.log(` Accepted by: ${colors.cyan(userInfo.email)}`)\n }\n logger.log(\"\")\n } else {\n logger.log(\n colors.yellow(\"⚠ Pro License and Terms of Service not yet accepted\")\n )\n logger.log(\" License acceptance is required for using paid components\")\n logger.log(\"\")\n }\n\n logger.log(\"License Details:\")\n logger.log(\n ` • Pro License: ${colors.cyan(\"https://tiptap.dev/pro-license\")}`\n )\n logger.log(\n ` • Terms of Service: ${colors.cyan(\"https://tiptap.dev/terms-of-service\")}`\n )\n logger.log(\"\")\n\n logger.log(\"About Paid Components:\")\n logger.log(\n \" Some paid UI components or templates are limited to specific plans.\"\n )\n logger.log(\n \" The license is valid during your trial period and active subscription.\"\n )\n logger.log(\"\")\n\n // Show hidden command hint only when using license command\n if (hasAccepted) {\n logger.log(colors.gray(\"Available commands:\"))\n logger.log(\n colors.gray(\n ` • ${colors.cyan(\"tiptap license forget me\")} - Reset license acceptance`\n )\n )\n logger.log(\"\")\n }\n}\n\n/**\n * Handle license forget me command\n */\nasync function handleLicenseForgetMe() {\n const hasAccepted = tokenStorage.hasAcceptedLicense()\n\n if (!hasAccepted) {\n logger.log(colors.yellow(\"⚠ License has not been accepted yet\"))\n return\n }\n\n const confirmed = await createThemedConfirm(\n \"Are you sure you want to reset your license acceptance?\",\n false\n )\n\n if (confirmed) {\n tokenStorage.clearLicenseAcceptance()\n logger.log(`${colors.cyan(\"✔\")} License acceptance has been reset`)\n logger.log(\n \" You will need to accept the license again when installing paid components\"\n )\n } else {\n logger.log(\"License acceptance reset cancelled\")\n }\n}\n\nexport const license = new Command()\n .command(\"license\")\n .description(\"display Tiptap Pro license information and acceptance status\")\n .action(async () => {\n try {\n await handleLicenseInfo()\n } catch (error) {\n handleError(error)\n }\n })\n .addCommand(\n new Command()\n .command(\"forget me\")\n .description(\"reset license acceptance status\")\n .action(async () => {\n try {\n await handleLicenseForgetMe()\n } catch (error) {\n handleError(error)\n }\n })\n )\n","import { checkAuthStatus } from \"@/src/utils/auth\"\nimport {\n getAuthToken,\n saveAuthToken,\n type PackageManager,\n} from \"@/src/utils/package-manager-config\"\nimport { logger } from \"@/src/utils/logger\"\nimport { colors } from \"@/src/utils/colors\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { getPackageManager } from \"./get-package-manager\"\nimport { PAID_PLANS, PaidPlan, Plan } from \"./registry/schema\"\nimport { createThemedConfirm, handleLogin } from \"../commands/auth\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\n\n/**\n * Checks if the selected components contain any paid components\n */\nexport function hasPaidComponents(\n components: Array<{ name: string; plans: Plan[] }>\n): boolean {\n return components.some(\n (component) =>\n component.plans &&\n component.plans.some((plan) => PAID_PLANS.includes(plan as PaidPlan))\n )\n}\n\n/**\n * Prompts user to accept Pro license and Terms of Service for paid components\n */\nasync function promptLicenseAcceptance(\n selectedComponents: Array<{ name: string; plans: Plan[] }>\n): Promise<boolean> {\n const paidComponents = selectedComponents.filter(\n (component) =>\n component.plans &&\n component.plans.some((plan) => PAID_PLANS.includes(plan as PaidPlan))\n )\n\n if (paidComponents.length === 0) {\n return true\n }\n\n // Check if license was already accepted\n if (tokenStorage.hasAcceptedLicense()) {\n logger.log(`${colors.cyan(\"✔\")} Pro license accepted`)\n return true\n }\n\n logger.log(\"\")\n logger.log(colors.yellow(\"📋 License Agreement\"))\n logger.log(\"\")\n logger.log(\"Integrating paid components requires accepting:\")\n logger.log(\n ` • Pro License: ${colors.cyan(\"https://tiptap.dev/pro-license\")}`\n )\n logger.log(\n ` • Terms of Service: ${colors.cyan(\"https://tiptap.dev/terms-of-service\")}`\n )\n logger.log(\"\")\n logger.log(colors.gray(\" Valid during trial and active subscription\"))\n logger.log(\"\")\n\n try {\n const accepted = await createThemedConfirm(\n \"Do you accept the Pro license and terms of service?\",\n false\n )\n\n if (!accepted) {\n logger.log(colors.gray(\"License not accepted\"))\n logger.log(colors.gray(\"Tip: You can still install free components\"))\n return false\n }\n\n // Store license acceptance\n tokenStorage.setLicenseAccepted()\n logger.log(`${colors.cyan(\"✔\")} License accepted`)\n return true\n } catch (error) {\n logger.log(colors.gray(\"License acceptance cancelled\"))\n return false\n }\n}\n\n/**\n * Ensures user is authenticated for paid components and has proper .npmrc configuration\n */\nexport async function ensureAuthForPaidComponents(\n selectedComponents: Array<{ name: string; plans: Plan[] }>,\n cwd: string\n): Promise<boolean> {\n try {\n if (!hasPaidComponents(selectedComponents)) {\n return true\n }\n\n const authStatus = await checkAuthStatus()\n\n if (!authStatus.authenticated) {\n logger.log(\"\")\n logger.log(colors.yellow(\"🔐 Authentication Required\"))\n logger.log(\"\")\n logger.log(\"Pro components require authentication.\")\n logger.log(\n `Run ${colors.cyan(\"tiptap login\")} or create an account at ${colors.cyan(\"https://cloud.tiptap.dev\")}`\n )\n logger.log(\"\")\n\n const shouldLoginNow = await createThemedConfirm(\n \"Would you like to login now?\",\n true\n )\n\n if (!shouldLoginNow) {\n logger.log(\"\")\n logger.log(colors.gray(\"Authentication cancelled\"))\n logger.log(colors.gray(\"Tip: You can still install free components\"))\n return false\n }\n\n const loginSuccess = await handleLogin({\n cwd,\n writeConfig: true,\n showMessage: false,\n })\n if (!loginSuccess) {\n return false\n }\n } else {\n const packageManager = await getPackageManager(cwd)\n const hasNpmrcConfig = await checkNpmrcConfiguration(packageManager, cwd)\n\n if (!hasNpmrcConfig) {\n await createNpmrcConfiguration(packageManager, cwd)\n }\n }\n\n // After authentication is complete, prompt for license acceptance\n const licenseAccepted = await promptLicenseAcceptance(selectedComponents)\n if (!licenseAccepted) {\n return false\n }\n\n return true\n } catch (error) {\n logger.error(\n `Authentication check failed: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n return false\n }\n}\n\n/**\n * Checks if .npmrc configuration exists for the project\n */\nasync function checkNpmrcConfiguration(\n packageManager: PackageManager,\n cwd: string\n): Promise<boolean> {\n try {\n const authToken = await getAuthToken(packageManager, cwd)\n return !!authToken\n } catch (error) {\n return false\n }\n}\n\n/**\n * Creates .npmrc configuration for the project\n */\nasync function createNpmrcConfiguration(\n packageManager: PackageManager,\n cwd: string\n) {\n const configSpinner = spinner(\"Creating registry configuration...\")?.start()\n\n try {\n const authStatus = await checkAuthStatus()\n\n if (!authStatus.authenticated) {\n configSpinner?.fail(\n \"Cannot create configuration - user not authenticated\"\n )\n return false\n }\n\n const authToken = tokenStorage.getAuthToken()\n\n if (!authToken) {\n configSpinner?.fail(\"No authentication token found\")\n return false\n }\n\n const success = await saveAuthToken(authToken, packageManager, cwd)\n if (!success) {\n configSpinner?.fail(\"Failed to save authentication token\")\n return false\n }\n\n configSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: \".npmrc created successfully\",\n })\n } catch (error) {\n configSpinner?.fail(\"Failed to create registry configuration\")\n logger.error(\n `Configuration error: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n }\n}\n","import { colors } from \"@/src/utils/colors\"\nimport { logger } from \"@/src/utils/logger\"\nimport process from \"process\"\n\n/**\n * CLI UI utilities for consistent visual styling\n */\n\n/**\n * Get the current terminal width with a fallback\n */\nexport function getTerminalWidth(): number {\n return process.stdout.columns || 80\n}\n\n/**\n * Creates a bordered box with content\n */\nexport function createBox(\n title: string,\n content: string[],\n options?: {\n borderColor?: \"cyan\" | \"yellow\" | \"red\" | \"green\" | \"gray\"\n padding?: boolean\n }\n) {\n const borderColor = options?.borderColor || \"gray\"\n const padding = options?.padding !== false\n\n // Box drawing characters\n const topLeft = \"\"\n const topRight = \"\"\n const bottomLeft = \"\"\n const bottomRight = \"\"\n const horizontal = \"-\"\n const vertical = \"\"\n\n // Use terminal width with max constraint for readability\n const terminalWidth = getTerminalWidth()\n const boxWidth = Math.min(terminalWidth - 4, 80) // Max 80 chars for readability\n\n const colorFn = colors[borderColor]\n const topBorder = colorFn(\n topLeft + horizontal.repeat(boxWidth - 2) + topRight\n )\n const bottomBorder = colorFn(\n bottomLeft + horizontal.repeat(boxWidth - 2) + bottomRight\n )\n const sideBorder = colorFn(vertical)\n\n // Create the box\n const lines = []\n\n if (padding) lines.push(\"\")\n\n lines.push(topBorder)\n\n // Empty line before title\n lines.push(`${sideBorder}${\" \".repeat(boxWidth - 2)}${sideBorder}`)\n\n // Title line\n const titlePadding = Math.floor((boxWidth - 4 - stripAnsi(title).length) / 2)\n const titleLine = title\n .padStart(titlePadding + stripAnsi(title).length)\n .padEnd(boxWidth - 4)\n lines.push(`${sideBorder} ${titleLine} ${sideBorder}`)\n\n // Empty line after title\n lines.push(`${sideBorder}${\" \".repeat(boxWidth - 2)}${sideBorder}`)\n\n // Content lines\n content.forEach((line) => {\n const strippedLength = stripAnsi(line).length\n const padding = boxWidth - 4 - strippedLength\n const paddedLine = line + \" \".repeat(Math.max(0, padding))\n lines.push(`${sideBorder} ${paddedLine} ${sideBorder}`)\n })\n\n // Empty line before bottom border\n if (content.length > 0) {\n lines.push(`${sideBorder}${\" \".repeat(boxWidth - 2)}${sideBorder}`)\n }\n\n lines.push(bottomBorder)\n\n if (padding) lines.push(\"\")\n\n return lines\n}\n\n/**\n * Creates a section with title and content\n */\nexport function createSection(\n title: string,\n content: string[],\n subtitle?: string\n) {\n const lines = []\n\n lines.push(\"\")\n lines.push(title)\n\n if (subtitle) {\n lines.push(colors.gray(subtitle))\n }\n\n lines.push(\"\")\n\n content.forEach((line) => {\n lines.push(line)\n })\n\n return lines\n}\n\n/**\n * Creates a welcome banner\n */\nexport function createWelcomeBanner(title: string, subtitle?: string) {\n const content = subtitle ? [subtitle] : []\n return createBox(`${title}`, content, { borderColor: \"gray\" })\n}\n\n/**\n * Creates an info box\n */\nexport function createInfoBox(title: string, content: string[]) {\n return createBox(`ℹ️ ${title}`, content, { borderColor: \"cyan\" })\n}\n\n/**\n * Creates a warning box\n */\nexport function createWarningBox(title: string, content: string[]) {\n return createBox(`⚠️ ${title}`, content, { borderColor: \"yellow\" })\n}\n\n/**\n * Creates a success box\n */\nexport function createSuccessBox(title: string, content: string[]) {\n return createBox(`✅ ${title}`, content, { borderColor: \"green\" })\n}\n\n/**\n * Logs multiple lines with proper spacing\n */\nexport function logLines(lines: string[]) {\n lines.forEach((line) => logger.log(line))\n}\n\n/**\n * Strips ANSI color codes from a string to get actual length\n */\nfunction stripAnsi(str: string): string {\n // eslint-disable-next-line no-control-regex\n return str.replace(/\\x1b\\[[0-9;]*m/g, \"\")\n}\n\n/**\n * Creates a numbered list with proper spacing\n */\nexport function createNumberedList(\n items: Array<{ label: string; description?: string }>\n) {\n const lines: string[] = []\n\n items.forEach((item, index) => {\n const number = colors.gray(`${index + 1}.`)\n lines.push(` ${number} ${item.label}`)\n\n if (item.description) {\n lines.push(` ${colors.gray(item.description)}`)\n }\n\n // Add spacing between items except the last one\n if (index < items.length - 1) {\n lines.push(\"\")\n }\n })\n\n return lines\n}\n\n/**\n * Creates a preview box with code content\n */\nexport function createPreviewBox(title: string, content: string[]) {\n const lines = []\n\n lines.push(\"\")\n lines.push(title)\n lines.push(\"\")\n\n // Create bordered preview area with terminal width constraint\n const terminalWidth = getTerminalWidth()\n const maxLength = Math.max(...content.map((line) => stripAnsi(line).length))\n const boxWidth = Math.min(Math.max(50, maxLength + 4), terminalWidth - 4)\n\n const topBorder = \"┌\" + \"─\".repeat(boxWidth - 2) + \"┐\"\n const bottomBorder = \"└\" + \"─\".repeat(boxWidth - 2) + \"┘\"\n\n lines.push(topBorder)\n\n content.forEach((line, index) => {\n const lineNumber = colors.gray(`${index + 1}`)\n const paddedLine = line.padEnd(boxWidth - 6)\n lines.push(`│ ${lineNumber} ${paddedLine} │`)\n })\n\n lines.push(bottomBorder)\n lines.push(\"\")\n\n return lines\n}\n\n/**\n * Creates an explanation section with bullet points\n */\nexport function createExplanationSection(title: string, points: string[]) {\n const lines = []\n\n lines.push(\"\")\n lines.push(colors.cyan(title))\n lines.push(\"\")\n\n points.forEach((point) => {\n lines.push(` • ${point}`)\n })\n\n lines.push(\"\")\n\n return lines\n}\n\n/**\n * Clears the terminal screen\n */\nexport function clearTerminal() {\n // Clear screen and move cursor to top-left\n process.stdout.write(\"\\x1B[2J\\x1B[0f\")\n\n // Alternative method that works better on some terminals\n // console.clear()\n\n // For Windows compatibility\n if (process.platform === \"win32\") {\n process.stdout.write(\"\\x1B[2J\\x1B[3J\\x1B[H\")\n }\n}\n\n/**\n * Creates a subtle divider line that spans the terminal width\n */\nexport function createDivider() {\n const width = Math.min(getTerminalWidth() - 4, 80)\n return colors.gray(\"─\".repeat(width))\n}\n\n/**\n * Creates a dash divider for prompts\n */\nexport function createSpacedDivider() {\n const width = Math.min(getTerminalWidth() - 4, 80)\n return colors.gray(\"-\".repeat(width))\n}\n","import { colors } from \"@/src/utils/colors\"\nimport { Framework, FRAMEWORKS } from \"@/src/utils/frameworks\"\nimport { createInfoBox, createWarningBox, logLines } from \"@/src/utils/cli-ui\"\nimport { existsSync } from \"fs\"\nimport path from \"path\"\nimport type { Config } from \"@/src/utils/get-config\"\n\n/**\n * Get the appropriate environment variable prefix for the framework\n */\nfunction getFrameworkEnvPrefix(framework: Framework): string {\n const frameworkName = framework.name\n\n if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n return \"NEXT_PUBLIC_\"\n } else if (frameworkName === FRAMEWORKS.astro.name) {\n return \"PUBLIC_\"\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n return \"VITE_\"\n } else if (\n frameworkName === FRAMEWORKS.laravel.name ||\n frameworkName === FRAMEWORKS.manual.name\n ) {\n return \"\"\n } else {\n return \"\"\n }\n}\n\n/**\n * Detect the actual file extension of style files in the project\n */\nfunction detectStyleFileExtension(config?: Config): string {\n if (!config?.resolvedPaths?.styles) {\n return \"scss\" // Default to scss if no config\n }\n\n const stylesDir = config.resolvedPaths.styles\n const variablesScss = path.join(stylesDir, \"_variables.scss\")\n const variablesCss = path.join(stylesDir, \"_variables.css\")\n\n // Check if CSS version exists (from Bun conversion)\n if (existsSync(variablesCss)) {\n return \"css\"\n }\n\n // Check if SCSS version exists\n if (existsSync(variablesScss)) {\n return \"scss\"\n }\n\n // Default to scss for new installations\n return \"scss\"\n}\n\n/**\n * Calculate the correct import path from main CSS file to styles directory\n */\nfunction calculateStylesImportPath(\n framework?: Framework,\n config?: Config\n): { cssFile: string; importPath: string } {\n const frameworkName = framework?.name || \"unknown\"\n\n // Check if styles are in src directory\n const stylesInSrc = config?.resolvedPaths?.styles?.includes(\"/src/\")\n const hasSrcDir = config?.resolvedPaths?.components?.includes(\"/src/\")\n\n // Determine the main CSS file location based on framework\n let cssFile = \"your main CSS file\"\n let importPath = \"./styles/\"\n\n switch (frameworkName) {\n case FRAMEWORKS[\"next-app\"].name:\n // Next.js App Router\n if (hasSrcDir) {\n // With srcDir: src/app/globals.css -> ../styles/\n cssFile = \"src/app/globals.css\"\n importPath = \"../styles/\"\n } else if (stylesInSrc) {\n // Without srcDir but styles in src: app/globals.css -> ../src/styles/\n cssFile = \"app/globals.css\"\n importPath = \"../src/styles/\"\n } else {\n // Without srcDir and styles at root: app/globals.css -> ../styles/\n cssFile = \"app/globals.css\"\n importPath = \"../styles/\"\n }\n break\n\n case FRAMEWORKS[\"next-pages\"].name:\n // Next.js Pages Router\n if (hasSrcDir) {\n // With srcDir: src/pages/_app.tsx imports from ../styles/globals.css\n cssFile = \"src/styles/globals.css\"\n importPath = \"./\"\n } else if (stylesInSrc) {\n // Without srcDir but styles in src: pages/_app.tsx imports from ../src/styles/\n cssFile = \"src/styles/globals.css\"\n importPath = \"./\"\n } else {\n // Without srcDir: styles/globals.css\n cssFile = \"styles/globals.css\"\n importPath = \"./\"\n }\n break\n\n case FRAMEWORKS.vite.name:\n // Vite - typically src/index.css or src/main.css\n cssFile = \"src/index.css\" // or src/main.css\n importPath = \"./styles/\"\n break\n\n case FRAMEWORKS[\"react-router\"].name:\n // React Router - similar to Vite, uses src structure\n cssFile = \"src/index.css\" // or src/main.css\n importPath = \"./styles/\"\n break\n\n case FRAMEWORKS[\"tanstack-start\"].name:\n // TanStack Start - Vite-based, uses src structure\n cssFile = \"src/index.css\" // or src/main.css\n importPath = \"./styles/\"\n break\n\n case FRAMEWORKS.astro.name:\n // Astro - typically has styles imported in layout files\n if (stylesInSrc) {\n cssFile = \"src/layouts/Layout.astro\" // or src/pages/index.astro\n importPath = \"../styles/\"\n } else {\n cssFile = \"src/layouts/Layout.astro\"\n importPath = \"../../styles/\" // If styles at root\n }\n break\n\n case FRAMEWORKS.laravel.name:\n // Laravel - uses resources/css/app.css\n cssFile = \"resources/css/app.css\"\n // Laravel styles would be in resources/styles/\n importPath = \"../styles/\"\n break\n\n case FRAMEWORKS.manual.name:\n default:\n // Manual/Unknown - make best guess based on config\n if (hasSrcDir || stylesInSrc) {\n cssFile = \"src/index.css\"\n importPath = \"./styles/\"\n } else {\n cssFile = \"your main CSS file\"\n importPath = \"./styles/\"\n }\n break\n }\n\n return { cssFile, importPath }\n}\n\n/**\n * Show styles setup message to remind users to configure styles\n */\nexport function showStylesConfigurationMessage(\n framework?: Framework,\n config?: Config\n) {\n const fileExtension = detectStyleFileExtension(config)\n const { cssFile, importPath } = calculateStylesImportPath(framework, config)\n\n const content = [\n \"The editor requires these style imports:\",\n \"\",\n `Add to ${colors.cyan(cssFile)}:`,\n \"\",\n colors.yellow(` @import '${importPath}_variables.${fileExtension}';`),\n colors.yellow(\n ` @import '${importPath}_keyframe-animations.${fileExtension}';`\n ),\n \"\",\n \"Without these imports, the editor will not display correctly.\",\n \"\",\n `Setup guide: ${colors.cyan(\"https://tiptap.dev/docs/ui-components/getting-started/style\")}`,\n ]\n\n const box = createWarningBox(\"Action Required: Import Styles\", content)\n logLines(box)\n}\n\n/**\n * Show package manager consistency warning\n */\nexport function showPackageManagerWarning(projectPackageManager: string) {\n const content = [\n `Your project uses ${colors.cyan(projectPackageManager)} as its package manager.`,\n \"\",\n \"For consistency, use the same package manager for all operations:\",\n `• Install dependencies: ${colors.yellow(`${projectPackageManager} install`)}`,\n `• Add packages: ${colors.yellow(`${projectPackageManager} add [package]`)}`,\n `• Run scripts: ${colors.yellow(`${projectPackageManager} run [script]`)}`,\n \"\",\n \"Mixing package managers (npm, pnpm, yarn) can cause conflicts.\",\n ]\n\n const box = createInfoBox(\"Package Manager Detected\", content)\n logLines(box)\n}\n\n/**\n * Show combined Notion setup message with environment variables\n */\nexport function showNotionSetupMessage(framework: Framework) {\n const prefix = getFrameworkEnvPrefix(framework)\n\n const content = [\n \"The Notion template requires these environment variables:\",\n \"\",\n colors.yellow(`${prefix}TIPTAP_COLLAB_DOC_PREFIX`) +\n \" - Document prefix (required)\",\n colors.yellow(`${prefix}TIPTAP_COLLAB_APP_ID`) +\n \" - Document Server App ID (required)\",\n colors.yellow(`${prefix}TIPTAP_COLLAB_TOKEN`) +\n \" - JWT token for collaboration (required)\",\n colors.yellow(`${prefix}TIPTAP_AI_APP_ID`) + \" - AI App ID (required)\",\n colors.yellow(`${prefix}TIPTAP_AI_TOKEN`) +\n \" - JWT token for AI (required)\",\n \"\",\n \"Get these credentials from your account at cloud.tiptap.dev\",\n \"\",\n `Setup guide: ${colors.cyan(\"https://tiptap.dev/docs/ui-components/templates/notion-like-editor\")}`,\n ]\n\n const box = createWarningBox(\"Action Required: Environment Setup\", content)\n logLines(box)\n}\n\n/**\n * Show combined Notion template setup message\n */\nexport function showNotionTemplateSetupMessage(\n framework: Framework,\n config?: Config\n) {\n const prefix = getFrameworkEnvPrefix(framework)\n const fileExtension = detectStyleFileExtension(config)\n const { cssFile, importPath } = calculateStylesImportPath(framework, config)\n\n const content = [\n \"The Notion-like template is a complete editor application that requires\",\n \"additional configuration before it can be used:\",\n \"\",\n colors.cyan(\"1. Import Required Styles\"),\n ` Add to ${colors.yellow(cssFile)}:`,\n colors.gray(` @import '${importPath}_variables.${fileExtension}';`),\n colors.gray(\n ` @import '${importPath}_keyframe-animations.${fileExtension}';`\n ),\n \"\",\n colors.cyan(\"2. Add Environment Variables (for collaborative features)\"),\n ` Add to your .env file:`,\n colors.gray(` ${prefix}TIPTAP_COLLAB_DOC_PREFIX - Document prefix`),\n colors.gray(` ${prefix}TIPTAP_COLLAB_APP_ID - Document Server App ID`),\n colors.gray(\n ` ${prefix}TIPTAP_COLLAB_TOKEN - JWT token for collaboration`\n ),\n colors.gray(` ${prefix}TIPTAP_AI_APP_ID - AI App ID`),\n colors.gray(` ${prefix}TIPTAP_AI_TOKEN - JWT token for AI`),\n \"\",\n `Get credentials at ${colors.cyan(\"https://cloud.tiptap.dev\")}`,\n `Setup guide: ${colors.cyan(\"https://tiptap.dev/docs/ui-components/templates/notion-like-editor\")}`,\n ]\n\n const box = createWarningBox(\"Next Steps: Configure your Editor\", content)\n logLines(box)\n}\n","import { getConfig } from \"@/src/utils/get-config\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { logger } from \"@/src/utils/logger\"\nimport { Command } from \"commander\"\n\nexport const info = new Command()\n .name(\"info\")\n .description(\"get information about your project\")\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .action(async (opts) => {\n logger.info(\"> project info\")\n console.log(await getProjectInfo(opts.cwd))\n logger.break()\n\n try {\n const config = await getConfig(opts.cwd)\n logger.info(\"> config\")\n console.log(config)\n } catch {\n logger.info(\"\")\n }\n })\n","import path from \"path\"\nimport { Command } from \"commander\"\nimport { confirm, input } from \"@inquirer/prompts\"\nimport { z } from \"zod\"\n\nimport { preFlightInit } from \"@/src/preflights/preflight-init\"\nimport { promptForRegistryComponents } from \"@/src/commands/add\"\nimport { FRAMEWORKS, createProject } from \"@/src/utils/create-project\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { colors } from \"@/src/utils/colors\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { addComponents } from \"@/src/utils/add-components\"\nimport {\n getProjectConfig,\n getProjectInfo,\n ProjectInfo,\n} from \"@/src/utils/get-project-info\"\nimport {\n DEFAULT_COMPONENTS,\n DEFAULT_CONTEXTS,\n DEFAULT_HOOKS,\n DEFAULT_TIPTAP_ICONS,\n DEFAULT_LIB,\n DEFAULT_STYLES,\n DEFAULT_TIPTAP_EXTENSIONS,\n DEFAULT_TIPTAP_NODES,\n DEFAULT_TIPTAP_UI,\n DEFAULT_TIPTAP_UI_PRIMITIVES,\n DEFAULT_TIPTAP_UI_UTILS,\n getConfig,\n rawConfigSchema,\n resolveConfigPaths,\n type Config,\n} from \"@/src/utils/get-config\"\nimport { getRegistryIndex } from \"../utils/registry\"\nimport { ensureAuthForPaidComponents } from \"../utils/auth-check\"\nimport { type Plan } from \"../utils/registry/schema\"\nimport {\n showNotionTemplateSetupMessage,\n showStylesConfigurationMessage,\n} from \"@/src/utils/prompt-messages\"\nimport { Framework } from \"../utils/frameworks\"\nimport {\n createWelcomeBanner,\n logLines,\n createExplanationSection,\n clearTerminal,\n} from \"@/src/utils/cli-ui\"\n\nexport const initOptionsSchema = z.object({\n cwd: z.string(),\n components: z.array(z.string()).optional(),\n silent: z.boolean(),\n isNewProject: z.boolean(),\n srcDir: z.boolean().optional(),\n reactCompiler: z.boolean().optional(),\n framework: z\n .string()\n .optional()\n .refine((val) => !val || FRAMEWORKS[val as keyof typeof FRAMEWORKS], {\n message: \"Invalid framework. Please use 'next' or 'vite'.\",\n }),\n})\n\ntype InitOptions = z.infer<typeof initOptionsSchema> & {\n skipPreflight?: boolean\n}\n\n/**\n * Creates a themed confirmation prompt with consistent styling\n */\nconst createThemedConfirm = (message: string, defaultValue: boolean = true) => {\n return confirm({\n message: colors.reset(message),\n default: defaultValue,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Initialize the CLI command\n */\nexport const init = new Command()\n .name(\"init\")\n .description(\n \"initialize your project and install Tiptap UI components as source code\"\n )\n .argument(\"[components...]\", \"the components to add\")\n .option(\"-f, --framework <framework>\", \"the framework to use. (next, vite)\")\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .option(\"-s, --silent\", \"mute output.\", false)\n .option(\n \"--src-dir\",\n \"use the src directory when creating a new project (specific to next).\",\n false\n )\n .option(\n \"--react-compiler\",\n \"enable React Compiler when creating a new project (specific to next).\",\n false\n )\n .action(async (components, opts) => {\n try {\n // Clear terminal for a fresh start\n clearTerminal()\n\n // Show welcome banner\n const welcomeBanner = createWelcomeBanner(\n \"Tiptap UI Components\",\n \"Install UI components or templates as editable source code in your project\"\n )\n logLines(welcomeBanner)\n\n // Explain what Tiptap CLI does\n const explanation = createExplanationSection(\n \"What are Tiptap UI Components?\",\n [\n \"React UI components that help you develop an editor\",\n \"They install as source code (not npm packages) in your src/components/\",\n \"UI components are a foundation for customization rather than a fixed library\",\n ]\n )\n logLines(explanation)\n\n // Wait for user to press Enter\n await input({\n message: colors.reset(\n `Press ${colors.cyan(\"Enter\")} to initialize a project...`\n ),\n theme: {\n prefix: {\n done: \"\",\n idle: \"\",\n },\n },\n })\n\n // Add visual separation\n logger.log(\"\")\n\n const options = initOptionsSchema.parse({\n cwd: path.resolve(opts.cwd),\n isNewProject: false,\n components,\n ...opts,\n })\n const result = await runInit(options)\n\n // Show success message\n if (result?.filesCreated && result.filesCreated.length > 0) {\n const containsNotion = result.filesCreated.some((path) =>\n path.includes(\"notion\")\n )\n const containsSimpleEditor = result.filesCreated.some(\n (path) => path.includes(\"simple\") && path.includes(\"editor\")\n )\n\n if (containsNotion) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Notion template installed - ${result.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show combined setup message for Notion template\n const framework = result.framework || result.projectInfo?.framework\n if (framework) {\n showNotionTemplateSetupMessage(\n framework as Framework,\n result.config\n )\n }\n } else if (containsSimpleEditor) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Simple editor template installed - ${result.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration as required\n const framework = result.framework || result.projectInfo?.framework\n if (framework) {\n showStylesConfigurationMessage(\n framework as Framework,\n result.config\n )\n }\n } else {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Components installed - ${result.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration if UI components were added\n const hasUIComponents = result.filesCreated.some(\n (path) =>\n path.includes(\"tiptap-templates\") || path.includes(\"tiptap-ui\")\n )\n\n if (hasUIComponents) {\n showStylesConfigurationMessage(\n result?.projectInfo?.framework,\n result.config\n )\n }\n }\n }\n\n logger.break()\n } catch (error) {\n logger.break()\n handleError(error)\n }\n })\n\n/**\n * Main initialization function\n */\nexport async function runInit(options: InitOptions) {\n const { cwd, skipPreflight, components, silent } = options\n let updatedOptions = { ...options }\n let newProjectFramework: string | undefined\n\n // Standard return structure creator\n const createResult = (\n config: Config,\n projectInfo: ProjectInfo | null,\n selectedComponents: string[] = [],\n addResult?: {\n filesCreated: string[]\n filesUpdated: string[]\n filesSkipped: string[]\n }\n ) => ({\n config,\n projectInfo,\n framework: newProjectFramework,\n selectedComponents,\n filesCreated: addResult?.filesCreated || [],\n filesUpdated: addResult?.filesUpdated || [],\n filesSkipped: addResult?.filesSkipped || [],\n errors: [],\n })\n\n // Handle preflight checks and project creation\n let projectInfo\n if (!skipPreflight) {\n const preflight = await preFlightInit(options)\n const isMissingDirOrEmptyProject =\n preflight.errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT]\n\n if (isMissingDirOrEmptyProject) {\n const { projectPath, framework } = await createProject(options)\n if (!projectPath) process.exit(0)\n\n updatedOptions = {\n ...updatedOptions,\n cwd: projectPath,\n isNewProject: true,\n }\n newProjectFramework = framework\n logger.log(\"\")\n }\n projectInfo = preflight.projectInfo\n } else {\n projectInfo = await getProjectInfo(cwd)\n }\n\n // Handle monorepo special case\n if (newProjectFramework === \"next-monorepo\") {\n const monorepoWebPath = path.resolve(updatedOptions.cwd, \"apps/web\")\n const config = await getConfig(monorepoWebPath)\n return createResult(config, projectInfo)\n }\n\n // Get configuration\n const projectConfig = await getProjectConfig(updatedOptions.cwd, projectInfo)\n const config = projectConfig\n ? await promptForMinimalConfig(projectConfig)\n : await promptForConfig(await getConfig(updatedOptions.cwd))\n\n logger.log(\"\")\n\n // Handle component selection\n let selectedComponents = components || []\n if (!selectedComponents.length) {\n const shouldAddComponents = await createThemedConfirm(\n \"Would you like to add a template or UI components to your project?\"\n )\n\n if (!shouldAddComponents) {\n const fullConfig = await resolveConfigPaths(updatedOptions.cwd, config)\n return createResult(fullConfig, projectInfo)\n }\n\n selectedComponents = await promptForRegistryComponents(\n { ...updatedOptions, overwrite: false },\n true // Show divider\n )\n\n if (!selectedComponents.length) {\n const fullConfig = await resolveConfigPaths(updatedOptions.cwd, config)\n return createResult(fullConfig, projectInfo)\n }\n }\n\n // Handle registry fetching and authentication for selected components\n let registryIndex\n try {\n registryIndex = await getRegistryIndex()\n if (!registryIndex) {\n throw new Error(\"Failed to fetch registry index.\")\n }\n } catch (error) {\n // Handle 401 auth error with retry\n if (\n error instanceof Error &&\n error.message.includes(\"You are not authorized\")\n ) {\n // Trigger auth flow with assumed paid components\n const assumedPaidComponents = selectedComponents.map((name) => ({\n name,\n plans: [\"start\" as Plan],\n }))\n\n const isAuthenticated = await ensureAuthForPaidComponents(\n assumedPaidComponents,\n updatedOptions.cwd\n )\n\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with paid component download.\"\n )\n logger.log(\n \"You can try again with only free components, or authenticate first.\"\n )\n process.exit(1)\n }\n\n // Retry registry fetch after authentication\n registryIndex = await getRegistryIndex()\n if (!registryIndex) {\n throw new Error(\"Failed to fetch registry index after authentication.\")\n }\n } else {\n throw error\n }\n }\n\n // Map components to details and perform final authentication check\n const selectedComponentDetails = selectedComponents.map((componentName) => {\n const componentInfo = registryIndex.find(\n (item) => item.name === componentName\n )\n return {\n name: componentName,\n plans: componentInfo?.plans || [],\n }\n })\n\n const isAuthenticated = await ensureAuthForPaidComponents(\n selectedComponentDetails,\n updatedOptions.cwd\n )\n\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with paid component download.\"\n )\n logger.log(\n \"You can try again with only free components, or authenticate first.\"\n )\n process.exit(1)\n }\n\n // Add components and return result\n const fullConfig = await resolveConfigPaths(updatedOptions.cwd, config)\n const addComponentsResult = await addComponents(\n selectedComponents,\n fullConfig,\n {\n overwrite: false,\n silent,\n isNewProject:\n updatedOptions.isNewProject ||\n projectInfo?.framework.name === \"next-app\",\n }\n )\n\n return createResult(\n fullConfig,\n projectInfo,\n selectedComponents,\n addComponentsResult || {\n filesCreated: [],\n filesUpdated: [],\n filesSkipped: [],\n }\n )\n}\n/**\n * Prompt for full configuration\n */\nasync function promptForConfig(defaultConfig: Config | null = null) {\n logger.log(\"\")\n logger.log(colors.cyan(\"Project Configuration\"))\n logger.log(\"\")\n\n const tsx = await createThemedConfirm(\n `Would you like to use ${colors.cyan(\"TypeScript\")} (recommended)?`,\n defaultConfig?.tsx ?? true\n )\n\n const rsc = await createThemedConfirm(\n `Are you using ${colors.cyan(\"React Server Components\")}?`,\n defaultConfig?.rsc ?? true\n )\n\n return rawConfigSchema.parse({\n rsc,\n tsx,\n aliases: {\n components: DEFAULT_COMPONENTS,\n contexts: DEFAULT_CONTEXTS,\n hooks: DEFAULT_HOOKS,\n tiptapIcons: DEFAULT_TIPTAP_ICONS,\n lib: DEFAULT_LIB,\n tiptapExtensions: DEFAULT_TIPTAP_EXTENSIONS,\n tiptapNodes: DEFAULT_TIPTAP_NODES,\n tiptapUi: DEFAULT_TIPTAP_UI,\n tiptapUiPrimitives: DEFAULT_TIPTAP_UI_PRIMITIVES,\n tiptapUiUtils: DEFAULT_TIPTAP_UI_UTILS,\n styles: DEFAULT_STYLES,\n },\n })\n}\n\n/**\n * Prompt for minimal configuration from existing config\n */\nasync function promptForMinimalConfig(defaultConfig: Config) {\n return rawConfigSchema.parse({\n rsc: defaultConfig?.rsc,\n tsx: defaultConfig?.tsx,\n aliases: defaultConfig?.aliases,\n })\n}\n","import path from \"path\"\nimport { initOptionsSchema } from \"@/src/commands/init\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { logger } from \"@/src/utils/logger\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport fs from \"fs-extra\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport async function preFlightInit(\n options: z.infer<typeof initOptionsSchema>\n) {\n const errors: Record<string, boolean> = {}\n\n // Ensure target directory exists.\n // Check for empty project. We assume if no package.json exists, the project is empty.\n if (\n !fs.existsSync(options.cwd) ||\n !fs.existsSync(path.resolve(options.cwd, \"package.json\"))\n ) {\n errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT] = true\n return {\n errors,\n projectInfo: null,\n }\n }\n\n const frameworkSpinner = spinner(`Verifying framework.`, {\n silent: options.silent,\n }).start()\n const projectInfo = await getProjectInfo(options.cwd)\n if (!projectInfo || projectInfo?.framework.name === \"manual\") {\n errors[ERRORS.UNSUPPORTED_FRAMEWORK] = true\n frameworkSpinner?.fail()\n logger.break()\n if (projectInfo?.framework.links.installation) {\n logger.error(\n `We could not detect a supported framework at ${colors.cyan(\n options.cwd\n )}.\\n` +\n `Visit ${colors.cyan(\n projectInfo?.framework.links.installation\n )} to manually configure your project.\\nOnce configured, you can use the cli to add components.`\n )\n }\n logger.break()\n process.exit(0)\n }\n frameworkSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: `Verifying framework. Found ${colors.cyan(projectInfo.framework.label)}.`,\n })\n\n const tsConfigSpinner = spinner(`Validating import alias.`, {\n silent: options.silent,\n }).start()\n if (!projectInfo?.aliasPrefix) {\n errors[ERRORS.IMPORT_ALIAS_MISSING] = true\n tsConfigSpinner?.fail()\n } else {\n tsConfigSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n }\n\n if (Object.keys(errors).length > 0) {\n if (errors[ERRORS.IMPORT_ALIAS_MISSING]) {\n logger.break()\n logger.error(`No import alias found in your tsconfig.json file.`)\n if (projectInfo?.framework.links.installation) {\n logger.error(\n `Visit ${colors.cyan(\n projectInfo?.framework.links.installation\n )} to learn how to set an import alias.`\n )\n }\n }\n\n logger.break()\n process.exit(0)\n }\n\n return {\n errors,\n projectInfo,\n }\n}\n","import os from \"os\"\nimport path from \"path\"\nimport fs from \"fs-extra\"\nimport { execa } from \"execa\"\nimport { z } from \"zod\"\nimport { parse as parseJsonc } from \"jsonc-parser\"\nimport { input } from \"@inquirer/prompts\"\n\nimport { initOptionsSchema } from \"@/src/commands/init\"\nimport select from \"@/src/inquirer/select\"\nimport { colors } from \"@/src/utils/colors\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { spinner } from \"@/src/utils/spinner\"\n\nconst MONOREPO_FRAMEWORK_URL =\n \"https://codeload.github.com/shadcn-ui/ui/tar.gz/main\"\n\nexport const FRAMEWORKS = {\n next: \"next\",\n vite: \"vite\",\n \"next-monorepo\": \"next-monorepo\",\n} as const\n\ntype Framework = keyof typeof FRAMEWORKS\ntype ProjectOptions = Pick<\n z.infer<typeof initOptionsSchema>,\n \"cwd\" | \"srcDir\" | \"components\" | \"framework\" | \"reactCompiler\"\n>\ntype CreateNextOptions = {\n version: string\n cwd: string\n packageManager: string\n srcDir: boolean\n reactCompiler: boolean\n}\ntype CreateViteOptions = {\n cwd: string\n packageManager: string\n projectName: string\n}\ntype CreateMonorepoOptions = {\n packageManager: string\n}\n\n/**\n * Creates a themed input prompt with consistent styling\n */\nconst createThemedInput = (message: string, defaultValue: string = \"\") => {\n return input({\n message: colors.reset(message),\n default: defaultValue,\n required: true,\n validate: (value: string) =>\n value.length > 128 ? `Name should be less than 128 characters.` : true,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Creates a themed select prompt with consistent styling\n */\nconst createThemedSelect = async (\n message: string,\n choices: Array<{ name: string; value: string }>\n) => {\n const instructions = `\\n${colors.gray(\" Use arrow-keys ▲▼ / [Return] to submit\")}\\n`\n\n return select({\n message: colors.reset(message),\n instructions,\n theme: {\n icon: {\n cursor: colors.cyan(\"❯\"),\n },\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n choices,\n })\n}\n\n/**\n * Creates a new project based on the specified framework\n */\nexport async function createProject(options: ProjectOptions) {\n const normalizedOptions = {\n srcDir: false,\n reactCompiler: false,\n ...options,\n }\n\n let framework: Framework =\n normalizedOptions.framework &&\n FRAMEWORKS[normalizedOptions.framework as Framework]\n ? (normalizedOptions.framework as Framework)\n : \"next\"\n\n let projectName = \"my-app\"\n const nextVersion = \"latest\"\n\n // Only prompt for framework if not already specified\n if (!normalizedOptions.framework) {\n const frameworkPromptMessage = `The path ${colors.cyan(normalizedOptions.cwd)} does not contain a package.json file. Would you like to start a new project?`\n\n const selectedFramework = await createThemedSelect(frameworkPromptMessage, [\n { name: \"Next.js\", value: \"next\" },\n { name: \"Vite + React + TypeScript\", value: \"vite\" },\n // { name: 'Next.js (Monorepo)', value: 'next-monorepo' }\n ])\n\n framework = selectedFramework as Framework\n\n // Add spacing after framework selection\n logger.log(\"\")\n }\n\n // Prompt for project name\n projectName = await createThemedInput(\n \"What is your project named?\",\n projectName\n )\n\n // Get the package manager for the project\n const packageManager = await getPackageManager(normalizedOptions.cwd, {\n withFallback: true,\n })\n\n const projectPath = path.join(normalizedOptions.cwd, projectName)\n\n // Validate path is writable\n await validateProjectPath(normalizedOptions.cwd, projectName)\n\n // Create the project based on framework\n if (framework === FRAMEWORKS.next) {\n await createNextProject(projectPath, {\n version: nextVersion,\n cwd: normalizedOptions.cwd,\n packageManager,\n srcDir: !!normalizedOptions.srcDir,\n reactCompiler: !!normalizedOptions.reactCompiler,\n })\n } else if (framework === FRAMEWORKS.vite) {\n await createViteProject(projectPath, {\n cwd: normalizedOptions.cwd,\n packageManager,\n projectName,\n })\n } else if (framework === FRAMEWORKS[\"next-monorepo\"]) {\n await createMonorepoProject(projectPath, {\n packageManager,\n })\n }\n\n return {\n projectPath,\n projectName,\n framework,\n }\n}\n\n/**\n * Validates that the project path is writable and doesn't already exist\n */\nasync function validateProjectPath(cwd: string, projectName: string) {\n // Check if path is writable\n try {\n await fs.access(cwd, fs.constants.W_OK)\n } catch (error) {\n logger.break()\n logger.error(`The path ${colors.cyan(cwd)} is not writable.`)\n logger.error(\n `It is likely you do not have write permissions for this folder or the path ${colors.cyan(cwd)} does not exist.`\n )\n logger.break()\n process.exit(0)\n }\n\n // Check if project already exists\n if (fs.existsSync(path.resolve(cwd, projectName, \"package.json\"))) {\n logger.break()\n logger.error(\n `A project with the name ${colors.cyan(projectName)} already exists.`\n )\n logger.error(`Please choose a different name and try again.`)\n logger.break()\n process.exit(0)\n }\n}\n\n/**\n * Creates a new Next.js project\n */\nasync function createNextProject(\n projectPath: string,\n options: CreateNextOptions\n) {\n const createSpinner = spinner(\n \"Creating a new Next.js project. This may take a few minutes.\"\n ).start()\n\n // Note: pnpm fails here. Fallback to npx with --use-PACKAGE-MANAGER.\n const args = [\n \"--tailwind\",\n \"--eslint\",\n \"--typescript\",\n \"--app\",\n options.srcDir ? \"--src-dir\" : \"--no-src-dir\",\n \"--no-import-alias\",\n options.reactCompiler ? \"--react-compiler\" : \"--no-react-compiler\",\n `--use-${options.packageManager}`,\n ]\n\n // Add turbopack for Next.js 15+ or canary/latest\n if (\n options.version.startsWith(\"15\") ||\n options.version.startsWith(\"latest\") ||\n options.version.startsWith(\"canary\")\n ) {\n args.push(\"--turbopack\")\n }\n\n try {\n await execa(\n \"npx\",\n [`create-next-app@${options.version}`, projectPath, \"--silent\", ...args],\n { cwd: options.cwd }\n )\n\n await updateReadmeFile(projectPath)\n\n createSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n } catch (error) {\n createSpinner?.fail(\"Something went wrong creating a new Next.js project.\")\n logger.break()\n logger.error(\n `Something went wrong creating a new Next.js project. Please try again.`\n )\n process.exit(0)\n }\n}\n\n/**\n * Creates a new Vite + React + TypeScript project\n */\nasync function createViteProject(\n projectPath: string,\n options: CreateViteOptions\n) {\n const createSpinner = spinner(\n `Creating a new Vite + React + TypeScript project. This may take a few minutes.`\n ).start()\n\n try {\n await execa(\n \"npm\",\n [\n \"create\",\n \"vite@latest\",\n options.projectName,\n \"--\",\n \"--template\",\n \"react-ts\",\n ],\n { cwd: options.cwd }\n )\n\n await execa(options.packageManager, [\"install\"], {\n cwd: projectPath,\n })\n\n await setupViteTsConfig(projectPath, options.packageManager)\n\n await updateReadmeFile(projectPath)\n\n createSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n } catch (error) {\n createSpinner?.fail(\"Something went wrong creating a new Vite project.\")\n handleError(error)\n }\n}\n\n/**\n * Configures TypeScript and path aliases for a Vite project\n */\nasync function setupViteTsConfig(projectPath: string, packageManager: string) {\n try {\n await setupTsConfigPathAliases(projectPath)\n await setupViteConfigPathAliases(projectPath)\n await installTypesNode(projectPath, packageManager)\n } catch (error) {\n logger.warn(\n \"Failed to set up TypeScript path aliases, but project creation succeeded\"\n )\n }\n}\n\n/**\n * Installs @types/node as a development dependency\n */\nasync function installTypesNode(projectPath: string, packageManager: string) {\n try {\n const devFlag = packageManager === \"npm\" ? \"--save-dev\" : \"-D\"\n\n await execa(\n packageManager,\n [packageManager === \"npm\" ? \"install\" : \"add\", devFlag, \"@types/node\"],\n { cwd: projectPath }\n )\n } catch (error) {\n logger.warn(\"Failed to install @types/node, but project creation succeeded\")\n }\n}\n\n/**\n * Sets up TypeScript configuration files with path aliases\n */\nasync function setupTsConfigPathAliases(projectPath: string) {\n const addAliasToTsConfig = async (tsconfigFile: string) => {\n const tsconfigPath = path.join(projectPath, tsconfigFile)\n if (!(await fs.pathExists(tsconfigPath))) return\n\n const jsonContent = await fs.readFile(tsconfigPath, \"utf-8\")\n const jsonObj = parseJsonc(jsonContent)\n\n jsonObj.compilerOptions = {\n ...jsonObj.compilerOptions,\n baseUrl: \".\",\n paths: {\n ...(jsonObj.compilerOptions?.paths || {}),\n \"@/*\": [\"./src/*\"],\n },\n }\n\n const updatedJson = JSON.stringify(jsonObj, null, 2)\n await fs.writeFile(tsconfigPath, updatedJson)\n }\n\n await addAliasToTsConfig(\"tsconfig.json\")\n await addAliasToTsConfig(\"tsconfig.app.json\")\n}\n\n/**\n * Sets up Vite configuration with path aliases\n */\nasync function setupViteConfigPathAliases(projectPath: string) {\n const viteConfigPath = path.join(projectPath, \"vite.config.ts\")\n const viteConfigContent = await fs.readFile(viteConfigPath, \"utf-8\")\n\n const updatedViteConfig = viteConfigContent\n .replace(\n \"import { defineConfig } from 'vite'\",\n \"import { defineConfig } from 'vite'\\nimport path from 'path'\"\n )\n .replace(\n \"plugins: [react()]\",\n `plugins: [react()],\n resolve: {\n alias: {\n '@': path.resolve(__dirname, './src')\n }\n }`\n )\n\n await fs.writeFile(viteConfigPath, updatedViteConfig)\n}\n\n/**\n * Creates a new Next.js monorepo project\n */\nasync function createMonorepoProject(\n projectPath: string,\n options: CreateMonorepoOptions\n) {\n const createSpinner = spinner(\n `Creating a new Next.js monorepo. This may take a few minutes.`\n ).start()\n\n try {\n await downloadAndExtractFramework(projectPath)\n\n // Run install\n await execa(options.packageManager, [\"install\"], {\n cwd: projectPath,\n })\n\n // Initialize git repository\n await initializeGitRepository(projectPath)\n\n createSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: `Created a new Next.js monorepo at ${colors.cyan(projectPath)}`,\n })\n } catch (error) {\n createSpinner?.fail(\"Something went wrong creating a new Next.js monorepo.\")\n handleError(error)\n }\n}\n\n/**\n * Downloads and extracts the monorepo framework\n */\nasync function downloadAndExtractFramework(projectPath: string) {\n // Create temporary directory\n const frameworkPath = path.join(os.tmpdir(), `tiptap-framework-${Date.now()}`)\n await fs.ensureDir(frameworkPath)\n\n // Download framework\n const response = await fetch(MONOREPO_FRAMEWORK_URL)\n if (!response.ok) {\n throw new Error(`Failed to download framework: ${response.statusText}`)\n }\n\n // Write the tar file\n const tarPath = path.resolve(frameworkPath, \"framework.tar.gz\")\n await fs.writeFile(tarPath, Buffer.from(await response.arrayBuffer()))\n\n // Extract framework\n await execa(\"tar\", [\n \"-xzf\",\n tarPath,\n \"-C\",\n frameworkPath,\n \"--strip-components=2\",\n \"ui-main/templates/monorepo-next\",\n ])\n\n // Move to project path and cleanup\n const extractedPath = path.resolve(frameworkPath, \"monorepo-next\")\n await fs.move(extractedPath, projectPath)\n await fs.remove(frameworkPath)\n}\n\n/**\n * Initializes a git repository in the project directory\n */\nasync function initializeGitRepository(projectPath: string) {\n const cwd = process.cwd()\n\n try {\n await execa(\"git\", [\"--version\"], { cwd: projectPath })\n await execa(\"git\", [\"init\"], { cwd: projectPath })\n await execa(\"git\", [\"add\", \"-A\"], { cwd: projectPath })\n await execa(\"git\", [\"commit\", \"-m\", \"Initial commit\"], {\n cwd: projectPath,\n })\n await execa(\"cd\", [cwd])\n } catch (error) {\n logger.warn(\n \"Failed to initialize git repository, but project creation succeeded\"\n )\n }\n}\n\nconst simpleEditorTemplateDocs = `# Simple template\n\nIntegrate the Tiptap open source editor with UI components and open source extensions.\n\nThe Simple Editor Template is a fully working setup for the Tiptap editor. It includes commonly used open source extensions and UI components, all MIT licensed and ready to customize.\n\n**Quick Links:**\n- [View in Full Screen](http://template.tiptap.dev/preview/templates/simple)\n- [GitHub Repository](https://github.com/ueberdosis/tiptap-ui-components/tree/main/apps/web/src/components/tiptap-templates/simple)\n\n## Installation\n\nAdd the Simple Editor Template to your project using the Tiptap CLI:\n\n\\`\\`\\`bash\nnpx @tiptap/cli add simple-editor\n\\`\\`\\`\n\n## Style\n\n> **Missing styles?** If you haven't added the styles yet, make sure to [follow the style setup guide](/ui-components/getting-started/style) to ensure your editor and components render correctly.\n\n## Usage\n\nAfter installation, use the SimpleEditor component in your React or Next.js project:\n\n\\`\\`\\`jsx\nimport { SimpleEditor } from '@/components/tiptap-templates/simple/simple-editor'\n\nexport default function App() {\n return <SimpleEditor />\n}\n\\`\\`\\`\n\n## Features\n\nA fully responsive rich text editor with built-in support for common formatting and layout tools. All components are open source and easy to extend.\n\n- **Responsive design**: Mobile-friendly by default\n- **Dark and light mode**: Supported out-of-the-box\n- **Formatting**: Bold, Italic, Underline\n- **Lists**: Bullet, Ordered, Checkboxes\n- **Text alignment**: Left, Center, Right, Justified\n- **Headings**: Multiple levels via dropdown\n- **Image upload**\n- **Link editing:** UI for adding and editing links\n- **Undo / Redo:** History management\n\n### Used reference components\n\n#### Hooks\n\n- \\`use-mobile\\`\n- \\`use-window-size\\`\n\n#### Icons\n\n- \\`arrow-left-icon\\`\n- \\`highlighter-icon\\`\n- \\`link-icon\\`\n- \\`moon-star-icon\\`\n- \\`sun-icon\\`\n\n#### Extensions\n\n- \\`selection-extension\\`\n- \\`link-extension\\`\n- \\`trailing-node-extension\\`\n\n#### Lib\n\n- \\`tiptap-utils\\`\n\n#### UI Components\n\n- \\`blockquote-button\\`\n- \\`code-block-button\\`\n- \\`color-highlight-button\\`\n- \\`color-highlight-popover\\`\n- \\`heading-button\\`\n- \\`heading-dropdown-menu\\`\n- \\`image-upload-button\\`\n- \\`link-popover\\`\n- \\`list-button\\`\n- \\`list-dropdown-menu\\`\n- \\`mark-button\\`\n- \\`text-align-button\\`\n- \\`undo-redo-button\\`\n\n#### Node Components\n\n- \\`code-block-node\\`\n- \\`image-node\\`\n- \\`image-upload-node\\`\n- \\`list-node\\`\n- \\`paragraph-node\\`\n\n#### Primitives\n\n- \\`button\\`\n- \\`spacer\\`\n- \\`toolbar\\`\n\n## License\n\nThe Simple Editor Template and all included components are MIT licensed. You're free to use, modify, and extend the code as needed.\n\n## Future compatibility\n\nYou can extend this template with additional features as your needs grow.\n\nPaid Tiptap Cloud features will have matching UI components that integrate just as easily! No rework needed.`\n\nconst notionLikeEditorDocs = `# Notion-like Editor\n\nA Notion-style Tiptap editor with collaboration, AI, and rich UI components. Fully customizable and easy to integrate.\n\nThe **Notion-like Editor Template** is a fully featured block-based editor that replicates the familiar Notion experience. It supports collaboration, AI assistance, emoji, drag & drop, advanced formatting—and it's fully customizable.\n\n## Installation\n\nInstall the Notion-like editor with the Tiptap CLI:\n\n\\`\\`\\`bash\nnpx @tiptap/cli add notion-like-editor\n\\`\\`\\`\n\n## Styling\n\n> **Note:** If the editor doesn't look right, make sure you've followed the [style setup guide](/ui-components/getting-started/style).\n\n## Configuration\n\nBefore running the app, configure the required constants inside \\`tiptap-collab-utils.ts\\`. This is necessary to enable features like AI or collaboration.\n\n### Environment Variables\n\nProvide values for the following environment variables:\n\n- \\`TIPTAP_COLLAB_DOC_PREFIX\\` - Prefix for identifying collaborative documents\n- \\`TIPTAP_COLLAB_APP_ID\\` - Your Document Server App ID\n- \\`TIPTAP_COLLAB_TOKEN\\` - JWT token for accessing Collaboration services\n- \\`TIPTAP_AI_APP_ID\\` - Your AI App ID\n- \\`TIPTAP_AI_TOKEN\\` - JWT token for accessing AI services\n\nThe above environment variables should be available in the client-side. Depending on your framework, use the following prefixes to expose them to the client:\n\n- **[Next.js](/ui-components/install/next)**: \\`NEXT_PUBLIC_\\`. For example, \\`NEXT_PUBLIC_TIPTAP_COLLAB_DOC_PREFIX\\`.\n- **[Vite + React](/ui-components/install/vite)**: \\`VITE_\\`. For example, \\`VITE_TIPTAP_COLLAB_DOC_PREFIX\\`.\n- **Other frameworks**: Follow the specific rules of your framework, and define the variables in the \\`tiptap-collab-utils.ts\\` file.\n\n### JWT Authentication\n\nCollaboration and AI features require a valid server-generated JWT token passed to the editor. See the \\`fetchCollabToken\\` function in \\`tiptap-collab-utils.ts\\` for an example.\n\n> See the full guide on JWT authentication at [https://tiptap.dev/docs/guides/authentication](https://tiptap.dev/docs/guides/authentication).\n\n> **Important:** To get started quickly, you can use the example JWT tokens from your Tiptap Cloud account and store them in the \\`TIPTAP_COLLAB_TOKEN\\` and \\`TIPTAP_AI_TOKEN\\` environment variables. However, example JWT tokens are valid for a short time and should not be used in production. In production, implement an API endpoint that generates JWTs on the server side.\n\n### \\`room\\` prop\n\nUse the \\`room\\` prop to distinguish collaborative documents. Each session should use a unique room ID.\n\n## Usage\n\nImport and render the \\`NotionEditor\\` component in your React app:\n\n\\`\\`\\`tsx\nimport { NotionEditor } from '@/components/tiptap-templates/notion/notion-like-editor'\n\nexport default function App() {\n return <NotionEditor room=\"my-document-room\" placeholder=\"Start writing...\" />\n}\n\\`\\`\\`\n\n## Features\n\nThe template includes all the essentials of a modern Notion-style editor:\n\n- **Real-time collaboration**: Live cursors and user presence\n- **AI assistance**: Inline AI tools for writing and editing\n- **Responsive design**: Mobile-ready UI with adaptive toolbars\n- **Dark/light mode**: Fully themed out of the box\n- **Slash commands**: \\`/\\` menu for quick formatting\n- **Floating toolbar**: Context-aware formatting\n- **Drag and drop**: Block-level reordering\n- **Emoji support**: GitHub-style emoji picker\n- **Mentions**: \\`@user\\` autocomplete\n- **Rich formatting**:\n - Bold, italic, underline, strikethrough\n - Highlight and color\n - Superscript / subscript\n - Syntax-highlighted code blocks\n- **Block types**:\n - Headings, lists, blockquotes, dividers, math\n- **Media support**: Drag & drop image upload\n- **Link management**: With inline previews\n- **Text alignment**: Left, center, right, justified\n- **Undo/Redo**: Full editing history\n- **Context menus**: Right-click enhancements\n\n## Component Breakdown\n\n### Hooks\n\n- \\`use-mobile\\`\n- \\`use-window-size\\`\n- \\`use-ui-editor-state\\`\n\n### Icons\n\n- \\`arrow-left-icon\\`\n- \\`chevron-right-icon\\`\n- \\`highlighter-icon\\`\n- \\`link-icon\\`\n- \\`more-vertical-icon\\`\n\n### Tiptap Extensions\n\n- \\`collaboration\\`, \\`collaboration-cursor\\`\n- \\`selection-extension\\`\n- \\`link-extension\\`\n- \\`trailing-node-extension\\`\n- \\`ai-extension\\`\n- \\`emoji-extension\\`\n- \\`mention-extension\\`\n- \\`mathematics-extension\\`\n- \\`unique-id-extension\\`\n\n### Libs\n\n- \\`tiptap-utils\\`\n- \\`tiptap-collab-utils\\`\n\n### UI Components\n\n- \\`ai-menu\\`\n- \\`blockquote-button\\`\n- \\`code-block-button\\`\n- \\`color-highlight-button\\`, \\`color-highlight-popover\\`\n- \\`drag-context-menu\\`\n- \\`emoji-dropdown-menu\\`\n- \\`heading-button\\`, \\`heading-dropdown-menu\\`\n- \\`image-upload-button\\`\n- \\`link-popover\\`\n- \\`list-button\\`, \\`list-dropdown-menu\\`\n- \\`mark-button\\`\n- \\`mention-dropdown-menu\\`\n- \\`slash-dropdown-menu\\`\n- \\`text-align-button\\`\n- \\`turn-into-dropdown\\`\n- \\`undo-redo-button\\`\n\n### Nodes\n\n- \\`code-block-node\\`\n- \\`image-node\\`, \\`image-upload-node\\`\n- \\`list-node\\`\n- \\`paragraph-node\\`\n\n### Notion-specific\n\n- \\`notion-like-editor-header\\`\n- \\`notion-toolbar-floating\\`\n- \\`mobile-toolbar\\`\n- \\`collaboration-users\\`\n- \\`theme-toggle\\`\n\n### Primitives\n\n- \\`button\\`, \\`button-group\\`\n- \\`dropdown-menu\\`\n- \\`separator\\`, \\`spacer\\`, \\`toolbar\\`\n\n### Contexts\n\n- \\`app-context\\`\n- \\`user-context\\`\n- \\`collab-context\\`\n\n## Collaboration\n\nTo use collaboration:\n\n1. Pass a unique \\`room\\` ID to \\`NotionEditor\\`\n2. Enable JWT auth for each user session\n3. User presence and cursors are handled automatically\n4. Operational transformation handles concurrent edits\n5. Sync and save are managed out-of-the-box\n\n\\`\\`\\`tsx\n<NotionEditor room=\"team-notes\" placeholder=\"Share your ideas...\" />\n\\`\\`\\`\n\n## AI Integration\n\nThe built-in AI tools let you:\n\n- **Generate content** from prompts\n- **Improve** existing text\n- **Get smart completions** based on context\n\n> **AI Configuration:** Make sure to configure your AI provider. Check the [AI Generation extension docs](/content-ai/capabilities/generation/overview) for setup steps.\n\n## Extendability\n\nThis template is designed to grow with your needs. New Tiptap Cloud features will be seamlessly compatible with the same UI system—no rewrites required.`\n\nasync function updateReadmeFile(projectPath: string, templateName?: string) {\n const readmePath = path.join(projectPath, \"README.md\")\n\n const templateContent = {\n \"simple-editor\": simpleEditorTemplateDocs,\n \"notion-like-editor\": notionLikeEditorDocs,\n } as const\n\n type TemplateKey = keyof typeof templateContent\n\n const readmeContent =\n templateName && templateName in templateContent\n ? templateContent[templateName as TemplateKey]\n : \"\"\n\n try {\n if (readmeContent.trim()) {\n await fs.writeFile(readmePath, readmeContent, \"utf-8\")\n }\n } catch {\n /* empty */\n }\n}\n","#!/usr/bin/env node\nimport { add } from \"@/src/commands/add\"\nimport { info } from \"@/src/commands/info\"\nimport { init } from \"@/src/commands/init\"\nimport { login, logout, status, license } from \"@/src/commands/auth\"\nimport { Command } from \"commander\"\n\nimport packageJson from \"../package.json\"\n\nprocess.on(\"SIGINT\", () => process.exit(0))\nprocess.on(\"SIGTERM\", () => process.exit(0))\n\nasync function main() {\n const program = new Command()\n .name(\"tiptap\")\n .description(\"add components and dependencies to your project\")\n .version(\n packageJson.version || \"1.0.0\",\n \"-v, --version\",\n \"display the CLI version number\"\n )\n\n program\n .addCommand(init)\n .addCommand(add)\n .addCommand(info)\n .addCommand(login)\n .addCommand(logout)\n .addCommand(status)\n .addCommand(license)\n\n program.parse()\n}\n\nmain()\n","{\n \"name\": \"@tiptap/cli\",\n \"version\": \"3.3.7\",\n \"description\": \"Tiptap CLI\",\n \"publishConfig\": {\n \"access\": \"public\"\n },\n \"author\": {\n \"name\": \"tiptap\",\n \"url\": \"https://github.com/ueberdosis/tiptap\"\n },\n \"files\": [\n \"dist\"\n ],\n \"keywords\": [\n \"cli\",\n \"components\",\n \"nextjs\",\n \"react\",\n \"templates\",\n \"tiptap\",\n \"@tiptap/cli\",\n \"ui\"\n ],\n \"license\": \"SEE LICENSE IN LICENSE.md\",\n \"type\": \"module\",\n \"exports\": {\n \".\": {\n \"types\": \"./dist/index.d.ts\",\n \"default\": \"./dist/index.js\"\n }\n },\n \"bin\": \"./dist/index.js\",\n \"scripts\": {\n \"dev\": \"tsup --watch\",\n \"build\": \"tsup\",\n \"typecheck\": \"tsc --noEmit\",\n \"clean\": \"rm -rf dist\",\n \"start:dev\": \"cross-env REGISTRY_URL=http://localhost:3000 node dist/index.js\",\n \"start:prod\": \"cross-env REGISTRY_URL=https://template.tiptap.dev node dist/index.js\",\n \"start\": \"node dist/index.js\",\n \"pub:beta\": \"pnpm build && pnpm publish --no-git-checks --access public --tag beta\",\n \"pub:release\": \"pnpm build && pnpm publish --access public\"\n },\n \"dependencies\": {\n \"@antfu/ni\": \"^23.3.1\",\n \"@babel/core\": \"^7.28.4\",\n \"@babel/parser\": \"^7.28.4\",\n \"@babel/plugin-transform-typescript\": \"^7.28.0\",\n \"@inquirer/core\": \"^10.3.0\",\n \"@inquirer/figures\": \"^1.0.14\",\n \"@inquirer/prompts\": \"^7.9.0\",\n \"@inquirer/type\": \"^3.0.9\",\n \"ansi-escapes\": \"^7.1.1\",\n \"chalk\": \"^5.6.2\",\n \"commander\": \"^13.1.0\",\n \"conf\": \"^14.0.0\",\n \"cosmiconfig\": \"^9.0.0\",\n \"deepmerge\": \"^4.3.1\",\n \"execa\": \"^9.6.0\",\n \"fast-glob\": \"^3.3.3\",\n \"fs-extra\": \"^11.3.2\",\n \"https-proxy-agent\": \"^7.0.6\",\n \"jsonc-parser\": \"^3.3.1\",\n \"node-fetch\": \"^3.3.2\",\n \"ora\": \"^8.2.0\",\n \"recast\": \"^0.23.11\",\n \"sass\": \"^1.93.2\",\n \"ts-morph\": \"^25.0.1\",\n \"tsconfig-paths\": \"^4.2.0\",\n \"yaml\": \"^2.8.1\",\n \"yoctocolors-cjs\": \"^2.1.3\",\n \"zod\": \"^3.25.76\"\n },\n \"devDependencies\": {\n \"@babel/plugin-transform-typescript\": \"^7.26.5\",\n \"@types/babel__core\": \"^7.20.5\",\n \"@types/conf\": \"^3.0.3\",\n \"@types/fs-extra\": \"^11.0.4\",\n \"@types/prompts\": \"^2.4.9\",\n \"cross-env\": \"^7.0.3\",\n \"tsup\": \"^8.5.0\",\n \"type-fest\": \"^4.41.0\"\n }\n}\n"],"mappings":"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AAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,8GAiH3BC,GAAuB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;A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","names":["path","Command","z","createPrompt","useState","useKeypress","usePrefix","usePagination","useRef","useMemo","useEffect","isBackspaceKey","isEnterKey","isUpKey","isDownKey","isNumberKey","Separator","ValidationError","makeTheme","colors","figures","ansiEscapes","selectTheme","text","isSelectable","item","normalizeChoices","choices","choice","name","normalizedChoice","select_default","config","done","loop","pageSize","instructions","firstRender","theme","status","setStatus","prefix","searchTimeoutRef","showHelpTip","setShowHelpTip","items","bounds","first","last","defaultItemIndex","active","setActive","selectedChoice","key","rl","offset","next","position","searchTerm","matchIndex","message","helpTipTop","helpTipBottom","page","isActive","index","indexLabel","disabledLabel","color","x","cursor","choiceDescription","Separator","input","confirm","checkbox","path","path","createMatchPath","resolveImport","importPath","config","cosmiconfig","fg","loadConfig","z","path","FRAMEWORKS","path","fs","getPackageInfo","cwd","shouldThrow","packageJsonPath","fg","fs","loadConfig","PROJECT_SHARED_IGNORE","getProjectInfo","cwd","configFiles","isSrcDir","isTsx","aliasPrefix","packageJson","fg","fs","path","isTypeScriptProject","getTsConfigAliasPrefix","getPackageInfo","isUsingAppDir","type","FRAMEWORKS","file","dep","tsConfig","loadConfig","alias","paths","getProjectConfig","defaultProjectInfo","existingConfig","projectInfo","getConfig","config","resolveConfigPaths","DEFAULT_COMPONENTS","DEFAULT_CONTEXTS","DEFAULT_HOOKS","DEFAULT_TIPTAP_ICONS","DEFAULT_LIB","DEFAULT_TIPTAP_EXTENSIONS","DEFAULT_TIPTAP_NODES","DEFAULT_TIPTAP_UI","DEFAULT_TIPTAP_UI_PRIMITIVES","DEFAULT_TIPTAP_UI_UTILS","DEFAULT_STYLES","explorer","cosmiconfig","rawConfigSchema","z","configSchema","workspaceConfigSchema","getConfig","cwd","res","projectInfo","getProjectInfo","defaultAliases","applyAliasPrefix","aliases","prefix","key","value","config","resolvedAliases","resolveConfigPaths","tsConfig","loadConfig","resolveImport","path","getWorkspaceConfig","isAliasKey","resolvedPath","packageRoot","findPackageRoot","result","commonRoot","findCommonRoot","relativePath","matchingPackageRoot","fg","pkgPath","pkgDir","parts1","parts2","commonParts","chalk","colors","join","args","logger","colors","fs","preFlightAdd","options","errors","fs","path","config","getConfig","error","logger","colors","path","z","handleError","error","logger","z","key","value","colors","z","registryItemTypeSchema","PAID_PLANS","FREE_PLANS","ALL_PLANS","planSchema","registryItemFileSchema","registryItemSchema","registrySchema","registryIndexSchema","registryResolvedItemsTreeSchema","deepmerge","HttpsProxyAgent","fetch","z","Conf","TokenStorage","logger","prefix","error","msg","token","userInfo","e","loginDate","expiration","bearerToken","authToken","expirationISO","planName","plans","tokenStorage","TokenStorage","logger","REGISTRY_URL","agent","HttpsProxyAgent","getRegistryIndex","result","fetchRegistry","registryIndexSchema","error","logger","handleError","createRegistryError","response","url","errorMessages","urlInfo","colors","tokenStorage","message","fetchComponent","path","headers","getRegistryUrl","fetch","fetchRegistryBatch","componentNames","paths","bearerToken","fetchRegistryDependencies","components","registryResolveItemsTree","names","config","registryItems","resolveRegistryItems","payload","z","registryItemSchema","framework","getProjectInfo","allDependencies","deepmerge","item","allDevDependencies","filteredDevDependencies","filterDevDependenciesByFramework","registryResolvedItemsTreeSchema","name","isUrl","componentName","getRegistryTypeAliasMap","getRegistryParentMap","map","dependency","devDependencies","depsArray","stringDeps","dep","hasSass","hasSassEmbedded","filteredDeps","prefersEmbedded","FRAMEWORKS","prefersRegular","ora","tiptapSpinner","colors","spinner","text","options","ora","detect","fs","path","getPackageManager","targetDir","withFallback","packageManager","userAgent","isBunProject","cwd","hasBunLock","fs","path","hasBunfig","execa","updateDependencies","dependencies","config","options","dependenciesSpinner","spinner","packageManager","getPackageManager","execa","colors","existsSync","fs","path","basename","fs","tmpdir","path","transformImport","sourceFile","config","packageManager","importDeclarations","importDeclaration","moduleSpecifier","updateImportAliases","isBunProject","alias","transformFromAstSync","parse","transformTypescript","recast","PARSE_OPTIONS","transformJsx","sourceFile","config","output","ast","code","result","SyntaxKind","directiveRegex","transformRsc","sourceFile","config","first","Node","SyntaxKind","DEFAULT_EXCLUSIONS","shouldExcludeComponent","componentName","rules","filePath","rule","f","name","ruleName","getFrameworkEnvVarName","constantName","framework","frameworkName","FRAMEWORKS","stripFrameworkPrefix","varName","transformEnvironmentVariables","sourceFile","config","projectInfo","getProjectInfo","nodesToTransform","binaryExpressions","SyntaxKind","binaryExpr","leftText","match","transformedEnvVar","rightSide","newExpression","callExpressions","callExpr","expressionText","args","argText","newArgText","envVarsToTransform","frameworkEnvVarName","newCallExpr","propertyAccessExpressions","propAccess","propAccessText","node","newText","error","transformRemoveComponents","exclusionRules","nodesToModify","importDeclarations","importDeclaration","moduleSpecifier","defaultImport","namedImports","excludedImports","namedImport","excludedImport","exportDeclarations","exportDeclaration","namedExports","excludedExports","namedExport","excludedExport","variableStatements","variableStatement","declarations","excludedDeclarations","declaration","functionDeclarations","functionDeclaration","functionName","interfaceDeclarations","interfaceDeclaration","interfaceName","typeAliases","typeAlias","typeName","propertySignatures","propertySignature","propName","jsxElements","jsxElement","tagName","jsxSelfClosingElements","jsxSelfClosingElement","propertyAssignments","propertyAssignment","propertyName","jsxAttributes","jsxAttribute","attributeName","parameters","parameter","parameterName","paramList","Node","allParams","index","prev","next","i","arg","prevSibling","nextSibling","bindingElements","bindingElement","bindingName","bindingPattern","allBindings","identifiers","identifier","identifierName","parent","parentKind","propAssignment","shorthandPropertyAssignments","shorthandProp","a","b","aStart","action","sass","transformScssToCSS","scssContent","error","Project","ScriptKind","project","Project","createTempSourceFile","filename","dir","fs","path","tmpdir","transform","opts","transformers","transformImport","transformRsc","transformRemoveComponents","isBun","isBunProject","transformScssToCSS","tempFile","sourceFile","ScriptKind","transformer","transformJsx","confirm","updateFiles","files","config","options","result","filesCreatedSpinner","spinner","projectInfo","packageManager","getProjectInfo","getPackageManager","file","filePath","resolveFilePath","findCommonRoot","f","error","fileName","basename","targetDir","path","match","isBunProject","existingFile","existsSync","content","transform","transformImport","transformRsc","transformRemoveComponents","existingFileContent","fs","normalizedExisting","normalizedNew","getNormalizedFileContent","confirm","colors","text","logger","resolveFileTargetDirectory","override","paths","needle","normalizedPaths","p","normalizedNeedle","needleDir","needleSegments","i","testPath","resolvePageTarget","target","framework","resolveNestedFilePath","normalizedFilePath","normalizedTargetDir","fileSegments","targetSegments","lastTargetSegment","commonDirIndex","segment","templateName","relativePath","finalPath","templateMatch","dataPath","z","execa","updateDevDependencies","devDependencies","config","options","devDependenciesSpinner","spinner","packageManager","getPackageManager","execa","colors","addComponents","components","config","options","workspaceConfig","getWorkspaceConfig","addWorkspaceComponents","addProjectComponents","registrySpinner","spinner","tree","registryResolveItemsTree","colors","updateDependencies","updateDevDependencies","updateFiles","handleError","registryItems","resolveRegistryItems","result","fetchRegistry","payload","z","registryItemSchema","registryParentMap","getRegistryParentMap","registryTypeAliasMap","getRegistryTypeAliasMap","filesCreated","filesUpdated","filesSkipped","rootSpinner","component","alias","registryParent","targetConfig","workspaceRoot","findCommonRoot","packageRoot","findPackageRoot","files","file","error","logger","path","toReadableName","input","word","fetch","HttpsProxyAgent","fs","path","os","execa","yaml","TIPTAP_REGISTRY","AUTH_TOKEN_KEY","TIPTAP_PRO_REGISTRY_KEY","addNpmrcToGitignore","cwd","gitignorePath","path","npmrcEntry","gitignoreContent","fs","line","newContent","error","logger","saveAuthToken","token","packageManager","createdNpmrc","saveNpmToken","saveYarnToken","saveToNpmrc","execa","yarnVersion","saveYarnBerryToken","yarnrcPath","yamlObj","yarnrcContent","npmrcPath","npmrcContent","lines","processedKeys","parseNpmrc","contentLines","trimmedLine","index","key","getAuthToken","projectToken","checkProjectNpmrc","getNpmAuthToken","checkGlobalNpmrc","projectNpmrcPath","content","extractAuthToken","stdout","globalNpmrcPath","os","configString","AUTH_API_URL","REGISTRY_URL","httpAgent","HttpsProxyAgent","authenticateUser","email","password","packageManager","writeConfig","cwd","loginSpinner","spinner","tokens","requestAuthTokens","userPlans","plansResponse","fetch","plan","tokenStorage","saveAuthToken","colors","error","response","data","checkAuthStatus","bearerToken","userInfo","expiration","logger","logoutUser","Command","execa","z","confirm","input","passwordPrompt","authOptionsSchema","z","createThemedInput","message","options","input","colors","value","createThemedPassword","passwordPrompt","createThemedConfirm","defaultValue","confirm","getConfigFileName","packageManager","displayTokenInstructions","token","cwd","logger","checkYarnVersion","execa","handleLogin","email","password","writeConfig","showMessage","getPackageManager","configFileName","result","authenticateUser","handleStatusCheck","status","checkAuthStatus","expiryDate","now","daysUntilExpiry","tokenPreview","registryToken","getAuthToken","registryPreview","login","Command","opts","error","handleError","logout","logoutSpinner","spinner","logoutUser","handleLicenseInfo","hasAccepted","tokenStorage","userInfo","handleLicenseForgetMe","license","hasPaidComponents","components","component","plan","PAID_PLANS","promptLicenseAcceptance","selectedComponents","tokenStorage","logger","colors","createThemedConfirm","ensureAuthForPaidComponents","cwd","checkAuthStatus","packageManager","getPackageManager","checkNpmrcConfiguration","createNpmrcConfiguration","handleLogin","error","getAuthToken","configSpinner","spinner","authToken","saveAuthToken","process","getTerminalWidth","createBox","title","content","options","borderColor","padding","topLeft","topRight","bottomLeft","bottomRight","horizontal","vertical","terminalWidth","boxWidth","colorFn","colors","topBorder","bottomBorder","sideBorder","lines","titlePadding","stripAnsi","titleLine","line","strippedLength","paddedLine","createWelcomeBanner","title","subtitle","content","createBox","createWarningBox","title","content","createBox","logLines","lines","line","logger","stripAnsi","str","createExplanationSection","title","points","lines","colors","point","clearTerminal","process","createSpacedDivider","width","getTerminalWidth","colors","existsSync","path","getFrameworkEnvPrefix","framework","frameworkName","FRAMEWORKS","detectStyleFileExtension","config","stylesDir","variablesScss","variablesCss","calculateStylesImportPath","stylesInSrc","hasSrcDir","cssFile","importPath","showStylesConfigurationMessage","fileExtension","content","colors","box","createWarningBox","logLines","showNotionTemplateSetupMessage","framework","config","prefix","getFrameworkEnvPrefix","fileExtension","detectStyleFileExtension","cssFile","importPath","calculateStylesImportPath","content","colors","box","createWarningBox","logLines","addOptionsSchema","z","PROMPT_PAGE_SIZE","UI","colors","PROMPT_THEME","text","filterFreeTemplates","templates","freeComponents","template","clearPromptLines","lines","i","categorizeRegistryItems","registryIndex","entry","promptForInitialSelection","categories","showDivider","message","choices","isComponentEmpty","logger","UI","createSpacedDivider","selection","select_default","colors","PROMPT_PAGE_SIZE","PROMPT_THEME","createComponentChoices","components","addCategorySection","items","title","filtertedItems","item","Separator","planLabel","paddedName","toReadableName","componentMenu","selectedComponents","checkbox","component","templateMenu","name","description","selectedTemplate","promptForRegistryComponents","options","getRegistryIndex","error","ensureAuthForPaidComponents","handleError","allComponents","filteredTemplates","add","Command","opts","clearTerminal","welcomeBanner","createWelcomeBanner","logLines","explanation","createExplanationSection","input","addOptionsSchema","path","selectedComponentDetails","componentName","componentInfo","errors","config","preFlightAdd","created","addComponents","containsNotion","containsSimpleEditor","projectInfo","getProjectInfo","showNotionTemplateSetupMessage","showStylesConfigurationMessage","Command","info","opts","logger","getProjectInfo","config","getConfig","path","Command","confirm","input","z","path","fs","preFlightInit","options","errors","fs","path","frameworkSpinner","spinner","projectInfo","getProjectInfo","logger","colors","tsConfigSpinner","os","path","fs","execa","parseJsonc","input","MONOREPO_FRAMEWORK_URL","FRAMEWORKS","createThemedInput","message","defaultValue","input","colors","value","createThemedSelect","choices","instructions","select_default","createProject","options","normalizedOptions","framework","projectName","nextVersion","frameworkPromptMessage","logger","packageManager","getPackageManager","projectPath","path","validateProjectPath","createNextProject","createViteProject","createMonorepoProject","cwd","fs","createSpinner","spinner","args","execa","updateReadmeFile","setupViteTsConfig","error","handleError","setupTsConfigPathAliases","setupViteConfigPathAliases","installTypesNode","addAliasToTsConfig","tsconfigFile","tsconfigPath","jsonContent","jsonObj","parseJsonc","updatedJson","viteConfigPath","updatedViteConfig","downloadAndExtractFramework","initializeGitRepository","frameworkPath","os","response","tarPath","extractedPath","simpleEditorTemplateDocs","notionLikeEditorDocs","templateName","readmePath","templateContent","readmeContent","initOptionsSchema","z","val","FRAMEWORKS","createThemedConfirm","message","defaultValue","confirm","colors","init","Command","components","opts","clearTerminal","welcomeBanner","createWelcomeBanner","logLines","explanation","createExplanationSection","input","logger","options","path","result","runInit","containsNotion","containsSimpleEditor","framework","showNotionTemplateSetupMessage","showStylesConfigurationMessage","error","handleError","cwd","skipPreflight","silent","updatedOptions","newProjectFramework","createResult","config","projectInfo","selectedComponents","addResult","getProjectInfo","preflight","preFlightInit","projectPath","createProject","monorepoWebPath","getConfig","projectConfig","getProjectConfig","promptForMinimalConfig","promptForConfig","fullConfig","resolveConfigPaths","promptForRegistryComponents","registryIndex","getRegistryIndex","assumedPaidComponents","name","ensureAuthForPaidComponents","selectedComponentDetails","componentName","componentInfo","item","addComponentsResult","addComponents","defaultConfig","tsx","rsc","rawConfigSchema","DEFAULT_COMPONENTS","DEFAULT_CONTEXTS","DEFAULT_HOOKS","DEFAULT_TIPTAP_ICONS","DEFAULT_LIB","DEFAULT_TIPTAP_EXTENSIONS","DEFAULT_TIPTAP_NODES","DEFAULT_TIPTAP_UI","DEFAULT_TIPTAP_UI_PRIMITIVES","DEFAULT_TIPTAP_UI_UTILS","DEFAULT_STYLES","Command","package_default","main","program","Command","package_default","init","add","info","login","logout","status","license"]}
|
|
1
|
+
{"version":3,"sources":["../src/commands/add.ts","../src/inquirer/select.ts","../src/preflights/preflight-add.ts","../src/utils/get-config.ts","../src/utils/resolve-import.ts","../src/utils/get-project-info.ts","../src/utils/frameworks.ts","../src/utils/get-package-info.ts","../src/utils/colors.ts","../src/utils/logger.ts","../src/utils/add-components.ts","../src/utils/handle-error.ts","../src/utils/registry/schema.ts","../src/utils/registry/index.ts","../src/utils/token-storage.ts","../src/utils/bootstrap.ts","../src/utils/spinner.ts","../src/utils/get-package-manager.ts","../src/utils/updaters/update-dependencies.ts","../src/utils/updaters/update-files.ts","../src/utils/transformers/index.ts","../src/utils/transformers/transform-import.ts","../src/utils/transformers/transform-jsx.ts","../src/utils/transformers/transform-rsc.ts","../src/utils/transformers/transform-remove-components.ts","../src/utils/transformers/transform-scss-to-css.ts","../src/utils/updaters/update-dev-dependencies.ts","../src/utils/common.ts","../src/utils/auth.ts","../src/utils/package-manager-config.ts","../src/commands/auth.ts","../src/utils/auth-check.ts","../src/utils/cli-ui.ts","../src/utils/prompt-messages.ts","../src/commands/info.ts","../src/commands/init.ts","../src/preflights/preflight-init.ts","../src/utils/create-project.ts","../src/index.ts","../package.json"],"sourcesContent":["import path from \"path\"\nimport { Command } from \"commander\"\nimport { z } from \"zod\"\nimport select from \"@/src/inquirer/select\"\nimport { Separator, input, confirm, checkbox } from \"@inquirer/prompts\"\nimport { preFlightAdd } from \"@/src/preflights/preflight-add\"\nimport { addComponents } from \"@/src/utils/add-components\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { getRegistryIndex } from \"@/src/utils/registry\"\nimport { colors } from \"@/src/utils/colors\"\nimport type { RegistryItemIndexSchema } from \"@/src/utils/registry/schema\"\nimport { toReadableName } from \"@/src/utils/common\"\nimport { ensureAuthForPaidComponents } from \"../utils/auth-check\"\nimport { type Plan } from \"../utils/registry/schema\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport {\n showNotionTemplateSetupMessage,\n showStylesConfigurationMessage,\n showTableNodeSetupMessage,\n} from \"@/src/utils/prompt-messages\"\nimport {\n createWelcomeBanner,\n logLines,\n createExplanationSection,\n clearTerminal,\n createSpacedDivider,\n} from \"@/src/utils/cli-ui\"\n\nexport const addOptionsSchema = z.object({\n components: z.array(z.string()).optional(),\n cwd: z.string(),\n path: z.string().optional(),\n silent: z.boolean(),\n overwrite: z.boolean(),\n})\n\ntype AddOptions = z.infer<typeof addOptionsSchema>\n\ninterface CategoryMap {\n templates: RegistryItemIndexSchema\n newComponents: RegistryItemIndexSchema\n ui: RegistryItemIndexSchema\n primitives: RegistryItemIndexSchema\n uiUtils: RegistryItemIndexSchema\n nodes: RegistryItemIndexSchema\n}\n\nconst PROMPT_PAGE_SIZE = 1_000 // Large size to avoid help tip\n\nconst UI = {\n emptyRegistry: colors.red(\"❌ No components or templates found\"),\n operationCancelled: colors.gray(\"Operation cancelled\"),\n missingDirectory: colors.red(\n \"❌ Directory not found. Use init to initialize a project first.\"\n ),\n}\n\nconst PROMPT_THEME = {\n icon: {\n cursor: colors.cyan(\"▸\"),\n checked: colors.cyan(\"◉\"),\n unchecked: \"○\",\n },\n style: {\n highlight: (text: string) => colors.cyan(text),\n message: (text: string) => text,\n answer: (text: string) => \"\", // Hide inline answer display\n },\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: colors.cyan(\"?\"),\n },\n}\n\n/**\n * Creates a themed confirmation prompt with consistent styling\n */\nconst createThemedConfirm = (message: string, defaultValue: boolean = true) => {\n return confirm({\n message,\n default: defaultValue,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Filters templates to only include free ones based on registry data\n */\nfunction filterFreeTemplates(\n templates: RegistryItemIndexSchema,\n freeComponents: string[] | null\n): RegistryItemIndexSchema {\n if (!freeComponents) {\n return templates\n }\n\n return templates.filter((template) => freeComponents.includes(template.name))\n}\n\n/**\n * Clears specified number of lines from console\n */\nfunction clearPromptLines(lines: number) {\n for (let i = 0; i < lines; i++) {\n process.stdout.write(\"\\x1B[1A\") // Move cursor up\n process.stdout.write(\"\\x1B[2K\") // Clear line\n }\n}\n\n/**\n * Categorizes registry items by type\n */\nconst categorizeRegistryItems = (\n registryIndex: RegistryItemIndexSchema\n): CategoryMap => {\n return {\n templates: registryIndex.filter(\n (entry) => entry.type === \"registry:template\"\n ),\n newComponents: registryIndex.filter((entry) => entry.isNew === true),\n ui: registryIndex.filter((entry) => entry.type === \"registry:ui\"),\n primitives: registryIndex.filter(\n (entry) => entry.type === \"registry:ui-primitive\"\n ),\n uiUtils: registryIndex.filter(\n (entry) => entry.type === \"registry:ui-utils\"\n ),\n nodes: registryIndex.filter((entry) => entry.type === \"registry:node\"),\n }\n}\n\n/**\n * Prompts user to select between components and templates\n */\nasync function promptForInitialSelection(\n categories: CategoryMap,\n showDivider = true\n): Promise<\"components\" | \"templates\" | null> {\n const message = \"What would you like to integrate?\"\n\n const choices = []\n const isComponentEmpty =\n categories.ui.length === 0 &&\n categories.nodes.length === 0 &&\n categories.newComponents.length === 0\n const isTemplateEmpty = categories.templates.length === 0\n\n if (!isTemplateEmpty) {\n choices.push({\n name: \"Templates - Full editor applications\",\n value: \"templates\",\n })\n }\n\n if (!isComponentEmpty) {\n choices.push({\n name: \"UI Components - Individual editor building blocks\",\n value: \"components\",\n })\n }\n\n if (choices.length === 0) {\n logger.break()\n console.log(UI.emptyRegistry)\n return null\n }\n\n try {\n if (showDivider) {\n console.log(createSpacedDivider())\n }\n\n const selection = await select({\n message: colors.reset(message),\n pageSize: PROMPT_PAGE_SIZE,\n theme: PROMPT_THEME,\n choices,\n })\n\n if (showDivider) {\n console.log(createSpacedDivider())\n }\n\n return selection as \"templates\" | \"components\"\n } catch (error) {\n clearPromptLines(4)\n console.log(UI.operationCancelled)\n return null\n }\n}\n\n/**\n * Creates choices for component menu with appropriate sections\n */\nasync function createComponentChoices(\n categories: CategoryMap,\n components: string[] | null\n): Promise<Array<{ name: string; value: string } | Separator>> {\n const choices: Array<{ name: string; value: string } | Separator> = []\n\n if (!components) {\n return choices\n }\n\n const addCategorySection = (\n items: RegistryItemIndexSchema,\n title: string\n ) => {\n const filtertedItems = items.filter((item) =>\n components.includes(item.name)\n )\n\n if (filtertedItems.length > 0) {\n choices.push(new Separator(\"\"))\n choices.push(new Separator(colors.whiteBold(` ${title}`)))\n\n filtertedItems.forEach((item) => {\n const planLabel =\n item.plans && item.plans.length\n ? item.plans.includes(\"light\")\n ? \"Open source (MIT)\"\n : \"Start plan • Trial\"\n : \"Free\"\n\n const name = toReadableName(item.name)\n const paddedName = name.padEnd(35)\n\n choices.push({\n name: `${paddedName} ${colors.dim(planLabel)}`,\n value: item.name,\n })\n })\n\n choices.push(new Separator(\" \"))\n }\n }\n\n const addNewComponentsSection = (\n items: RegistryItemIndexSchema,\n title: string\n ) => {\n const filtertedItems = items.filter((item) =>\n components.includes(item.name)\n )\n\n if (filtertedItems.length > 0) {\n choices.push(new Separator(\"\"))\n choices.push(new Separator(colors.whiteBold(` ${title}`)))\n\n filtertedItems.forEach((item) => {\n const planLabel =\n item.plans && item.plans.length\n ? item.plans.includes(\"light\")\n ? \"Open source (MIT)\"\n : \"Start plan • Trial\"\n : \"Free\"\n\n const name = toReadableName(item.name)\n const paddedName = name.padEnd(35)\n const description = item.description\n ? `\\n ${colors.dim(item.description)}`\n : \"\"\n\n choices.push({\n name: `${paddedName} ${colors.dim(planLabel)}${description}`,\n value: item.name,\n })\n })\n\n choices.push(new Separator(\" \"))\n }\n }\n\n addNewComponentsSection(categories.newComponents, \"NEW COMPONENTS\")\n addCategorySection(categories.ui, \"UI COMPONENTS\")\n addCategorySection(categories.nodes, \"NODE COMPONENTS\")\n addCategorySection(categories.primitives, \"PRIMITIVES\")\n\n return choices\n}\n\n/**\n * Shows menu for selecting components\n */\nasync function componentMenu(\n categories: CategoryMap,\n components: string[] | null\n): Promise<string[]> {\n const choices = await createComponentChoices(categories, components)\n\n if (choices.length === 0) {\n return []\n }\n\n try {\n logger.log(\"\")\n logger.log(\n colors.cyan(\" Press Space to select • A to toggle all • Enter to confirm\")\n )\n\n const selectedComponents = await checkbox({\n message: \"Choose UI components to install:\",\n pageSize: 20,\n choices,\n theme: PROMPT_THEME,\n validate: (items) => {\n if (items.length === 0) {\n return \"Select at least one component (use Space to select, then Enter to confirm)\"\n }\n return true\n },\n })\n\n // Display selected components\n if (selectedComponents && selectedComponents.length > 0) {\n logger.log(\"\")\n logger.log(colors.cyan(\"Selected components:\"))\n selectedComponents.forEach((component) => {\n logger.log(` ${colors.cyan(\"•\")} ${toReadableName(component)}`)\n })\n }\n\n logger.log(\"\")\n return selectedComponents || []\n } catch (error) {\n clearPromptLines(25)\n console.log(UI.operationCancelled)\n return []\n }\n}\n\n/**\n * Shows menu for selecting templates\n */\nasync function templateMenu(\n templates: RegistryItemIndexSchema\n): Promise<string[]> {\n try {\n const choices = templates.map((template) => {\n const planLabel =\n template.plans && template.plans.length\n ? template.plans.includes(\"light\")\n ? \"Open source (MIT)\"\n : \"Start plan • Trial\"\n : \"Free\"\n\n const name = toReadableName(template.name)\n const description = template.description\n ? ` - ${template.description}`\n : \"\"\n const nameWithDesc = `${name}${description}`\n const paddedNameWithDesc = nameWithDesc.padEnd(50)\n\n return {\n name: `${paddedNameWithDesc} ${colors.dim(planLabel)}`,\n value: template.name,\n }\n })\n\n logger.log(\"\")\n\n const selectedTemplate = await select({\n message: \"Choose an editor template to install:\",\n pageSize: 20,\n choices,\n theme: PROMPT_THEME,\n })\n\n // Display selected template\n if (selectedTemplate) {\n logger.log(\"\")\n logger.log(colors.cyan(\"Selected template:\"))\n logger.log(` ${colors.cyan(\"•\")} ${toReadableName(selectedTemplate)}`)\n }\n\n logger.log(\"\")\n return selectedTemplate ? [selectedTemplate] : []\n } catch (error) {\n clearPromptLines(25)\n console.log(UI.operationCancelled)\n return []\n }\n}\n\n/**\n * Main function to prompt for registry components\n */\nexport async function promptForRegistryComponents(\n options: AddOptions,\n showDivider = true\n): Promise<string[]> {\n if (options.components?.length) {\n return options.components\n }\n\n let registryIndex\n try {\n registryIndex = await getRegistryIndex()\n } catch (error) {\n // Check if this is a 401 authentication error\n if (\n error instanceof Error &&\n error.message.includes(\"You are not authorized\")\n ) {\n // Assume the component is paid and trigger authentication flow\n const isAuthenticated = await ensureAuthForPaidComponents(\n [{ name: \"unknown\", plans: [\"start\" as Plan] }], // Assume paid component\n options.cwd\n )\n\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with component selection.\"\n )\n return []\n }\n\n // Retry registry fetch after authentication\n try {\n registryIndex = await getRegistryIndex()\n } catch (retryError) {\n logger.break()\n handleError(\n new Error(\n \"[prompts] - Failed to fetch registry index after authentication.\"\n )\n )\n return []\n }\n } else {\n logger.break()\n handleError(error)\n return []\n }\n }\n\n if (!registryIndex) {\n logger.break()\n handleError(new Error(\"[prompts] - Failed to fetch registry index.\"))\n return []\n }\n\n const categories = categorizeRegistryItems(registryIndex)\n const selection = await promptForInitialSelection(categories, showDivider)\n\n if (!selection) {\n return []\n }\n\n const allComponents = registryIndex\n .filter((item) => {\n const hide = item.hide ?? false\n return !hide\n })\n .map((item) => item.name)\n\n switch (selection) {\n case \"components\":\n return (await componentMenu(categories, allComponents)) || []\n case \"templates\": {\n const filteredTemplates = filterFreeTemplates(\n categories.templates,\n allComponents\n )\n const templateResults = await templateMenu(filteredTemplates)\n return templateResults || []\n }\n default:\n return []\n }\n}\n\nexport const add = new Command()\n .name(\"add\")\n .description(\n \"add Tiptap UI components or templates as source code to your project\"\n )\n .argument(\"[components...]\", \"the components to add\")\n .option(\"-o, --overwrite\", \"overwrite existing files.\", false)\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .option(\"-p, --path <path>\", \"the path to add the component to.\")\n .option(\"-s, --silent\", \"mute output.\", false)\n .action(async (components, opts) => {\n try {\n // Clear terminal for a fresh start\n clearTerminal()\n\n // Show welcome banner\n const welcomeBanner = createWelcomeBanner(\n \"Tiptap UI Components\",\n \"Install UI components or templates as editable source code in your project\"\n )\n logLines(welcomeBanner)\n\n // Explain what Tiptap CLI does\n const explanation = createExplanationSection(\n \"What are Tiptap UI Components?\",\n [\n \"React UI components that help you develop an editor\",\n \"They install as source code (not npm packages) in your src/components/\",\n \"UI components are a foundation for customization rather than a fixed library\",\n ]\n )\n logLines(explanation)\n\n // Wait for user to press Enter\n await input({\n message: colors.reset(\n `Press ${colors.cyan(\"Enter\")} to add components or templates...`\n ),\n theme: {\n prefix: {\n done: \"\",\n idle: \"\",\n },\n },\n })\n\n // Add visual separation\n logger.log(\"\")\n logger.log(\"\")\n logger.log(\"\")\n\n const options = addOptionsSchema.parse({\n components,\n cwd: path.resolve(opts.cwd),\n ...opts,\n })\n\n if (!options.components?.length) {\n options.components = await promptForRegistryComponents(options)\n }\n\n // No components selected\n if (!options.components?.length) {\n return\n }\n\n const registryIndex = await getRegistryIndex()\n if (!registryIndex) {\n throw new Error(\"Failed to fetch registry index.\")\n }\n\n // Get details of selected components\n const selectedComponentDetails = options.components.map(\n (componentName) => {\n const componentInfo = registryIndex.find(\n (item) => item.name === componentName\n )\n return {\n name: componentName,\n plans: componentInfo?.plans || [],\n }\n }\n )\n\n const isAuthenticated = await ensureAuthForPaidComponents(\n selectedComponentDetails,\n options.cwd\n )\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with paid component download.\"\n )\n logger.log(\n \"You can try again with only free components, or authenticate first.\"\n )\n process.exit(1)\n }\n\n const { errors, config } = await preFlightAdd(options)\n\n if (errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT]) {\n logger.warn(`\\n${UI.missingDirectory}`)\n process.exit(0)\n }\n\n if (!config) {\n throw new Error(`Failed to read config at ${colors.cyan(options.cwd)}.`)\n }\n\n const created = await addComponents(options.components, config, options)\n\n // Show success message if components were added\n if (created && created.filesCreated.length > 0) {\n const containsNotion = created.filesCreated.some((path) =>\n path.includes(\"notion\")\n )\n const containsSimpleEditor = created.filesCreated.some(\n (path) => path.includes(\"simple\") && path.includes(\"editor\")\n )\n\n if (containsNotion) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Notion template installed - ${created.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show combined setup message for Notion template\n const projectInfo = await getProjectInfo(options.cwd)\n if (projectInfo) {\n showNotionTemplateSetupMessage(projectInfo.framework, config)\n }\n } else if (containsSimpleEditor) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Simple editor template installed - ${created.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration as required\n const projectInfo = await getProjectInfo(options.cwd)\n if (projectInfo) {\n showStylesConfigurationMessage(projectInfo.framework, config)\n }\n } else {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Components installed - ${created.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration if UI components were added\n const hasUIComponents = created.filesCreated.some(\n (path) =>\n path.includes(\"tiptap-templates\") || path.includes(\"tiptap-ui\")\n )\n\n if (hasUIComponents) {\n const projectInfo = await getProjectInfo(options.cwd)\n if (projectInfo) {\n showStylesConfigurationMessage(projectInfo.framework, config)\n }\n }\n\n // Show Table Node integration guide if table-node was installed\n const containsTableNode = options.components.includes(\"table-node\")\n if (containsTableNode) {\n showTableNodeSetupMessage()\n }\n }\n }\n } catch (error) {\n logger.break()\n handleError(error)\n }\n })\n","import {\n createPrompt,\n useState,\n useKeypress,\n usePrefix,\n usePagination,\n useRef,\n useMemo,\n useEffect,\n isBackspaceKey,\n isEnterKey,\n isUpKey,\n isDownKey,\n isNumberKey,\n Separator,\n ValidationError,\n makeTheme,\n type Theme,\n type Status,\n} from \"@inquirer/core\"\nimport type { PartialDeep } from \"@inquirer/type\"\nimport colors from \"yoctocolors-cjs\"\nimport figures from \"@inquirer/figures\"\nimport ansiEscapes from \"ansi-escapes\"\n\ntype SelectTheme = {\n icon: { cursor: string }\n style: {\n disabled: (text: string) => string\n description: (text: string) => string\n }\n indexMode: \"hidden\" | \"number\"\n}\n\nconst selectTheme: SelectTheme = {\n icon: { cursor: figures.pointer },\n style: {\n disabled: (text: string) => colors.dim(`- ${text}`),\n description: (text: string) => colors.cyan(text),\n },\n indexMode: \"hidden\",\n}\n\ntype Choice<Value> = {\n value: Value\n name?: string\n description?: string\n short?: string\n disabled?: boolean | string\n type?: never\n}\n\ntype NormalizedChoice<Value> = {\n value: Value\n name: string\n description?: string\n short: string\n disabled: boolean | string\n}\n\ntype SelectConfig<\n Value,\n ChoicesObject =\n | ReadonlyArray<string | Separator>\n | ReadonlyArray<Choice<Value> | Separator>,\n> = {\n message: string\n choices: ChoicesObject extends ReadonlyArray<string | Separator>\n ? ChoicesObject\n : ReadonlyArray<Choice<Value> | Separator>\n pageSize?: number\n loop?: boolean\n default?: unknown\n instructions?: string | boolean\n theme?: PartialDeep<Theme<SelectTheme>>\n}\n\nfunction isSelectable<Value>(\n item: NormalizedChoice<Value> | Separator\n): item is NormalizedChoice<Value> {\n return !Separator.isSeparator(item) && !item.disabled\n}\n\nfunction normalizeChoices<Value>(\n choices:\n | ReadonlyArray<string | Separator>\n | ReadonlyArray<Choice<Value> | Separator>\n): Array<NormalizedChoice<Value> | Separator> {\n return choices.map((choice) => {\n if (Separator.isSeparator(choice)) return choice\n\n if (typeof choice === \"string\") {\n return {\n value: choice as Value,\n name: choice,\n short: choice,\n disabled: false,\n }\n }\n\n const name = choice.name ?? String(choice.value)\n const normalizedChoice: NormalizedChoice<Value> = {\n value: choice.value,\n name,\n short: choice.short ?? name,\n disabled: choice.disabled ?? false,\n }\n\n if (choice.description) {\n normalizedChoice.description = choice.description\n }\n\n return normalizedChoice\n })\n}\n\nexport default createPrompt(\n <Value>(config: SelectConfig<Value>, done: (value: Value) => void) => {\n const { loop = true, pageSize = 7, instructions } = config\n const firstRender = useRef(true)\n const theme = makeTheme<SelectTheme>(selectTheme, config.theme)\n const [status, setStatus] = useState<Status>(\"idle\")\n const prefix = usePrefix({ status, theme })\n const searchTimeoutRef = useRef<ReturnType<typeof setTimeout>>()\n const [showHelpTip, setShowHelpTip] = useState(true)\n\n const items = useMemo(\n () => normalizeChoices(config.choices),\n [config.choices]\n )\n\n const bounds = useMemo(() => {\n const first = items.findIndex(isSelectable)\n const last = items.findLastIndex(isSelectable)\n\n if (first === -1) {\n throw new ValidationError(\n \"[select prompt] No selectable choices. All choices are disabled.\"\n )\n }\n\n return { first, last }\n }, [items])\n\n const defaultItemIndex = useMemo(() => {\n if (!(\"default\" in config)) return -1\n return items.findIndex(\n (item) => isSelectable(item) && item.value === config.default\n )\n }, [config.default, items])\n\n const [active, setActive] = useState(\n defaultItemIndex === -1 ? bounds.first : defaultItemIndex\n )\n\n // Safe to assume the cursor position always point to a Choice.\n const selectedChoice = items[active] as NormalizedChoice<Value>\n\n useKeypress((key, rl) => {\n clearTimeout(searchTimeoutRef.current)\n setShowHelpTip(false)\n\n if (isEnterKey(key)) {\n setStatus(\"done\")\n done(selectedChoice.value)\n } else if (isUpKey(key) || isDownKey(key)) {\n rl.clearLine(0)\n if (\n loop ||\n (isUpKey(key) && active !== bounds.first) ||\n (isDownKey(key) && active !== bounds.last)\n ) {\n const offset = isUpKey(key) ? -1 : 1\n let next = active\n do {\n next = (next + offset + items.length) % items.length\n } while (!isSelectable(items[next]!))\n setActive(next)\n }\n } else if (isNumberKey(key) && !Number.isNaN(Number(rl.line))) {\n const position = Number(rl.line) - 1\n const item = items[position]\n if (item != null && isSelectable(item)) {\n setActive(position)\n }\n\n searchTimeoutRef.current = setTimeout(() => {\n rl.clearLine(0)\n }, 700)\n } else if (isBackspaceKey(key)) {\n rl.clearLine(0)\n } else {\n // Default to search\n const searchTerm = rl.line.toLowerCase()\n const matchIndex = items.findIndex((item) => {\n if (Separator.isSeparator(item) || !isSelectable(item)) return false\n\n return item.name.toLowerCase().startsWith(searchTerm)\n })\n\n if (matchIndex !== -1) {\n setActive(matchIndex)\n }\n\n searchTimeoutRef.current = setTimeout(() => {\n rl.clearLine(0)\n }, 700)\n }\n })\n\n useEffect(\n () => () => {\n clearTimeout(searchTimeoutRef.current)\n },\n []\n )\n\n const message = theme.style.message(config.message, status)\n\n let helpTipTop = \"\"\n let helpTipBottom = \"\"\n // Help text is now always hidden\n if (typeof instructions === \"string\") {\n helpTipTop = instructions\n }\n\n const page = usePagination({\n items,\n active,\n renderItem({ item, isActive, index }) {\n if (Separator.isSeparator(item)) {\n return ` ${item.separator}`\n }\n\n const indexLabel = theme.indexMode === \"number\" ? `${index + 1}. ` : \"\"\n if (item.disabled) {\n const disabledLabel =\n typeof item.disabled === \"string\" ? item.disabled : \"(disabled)\"\n return theme.style.disabled(\n `${indexLabel}${item.name} ${disabledLabel}`\n )\n }\n\n const color = isActive ? theme.style.highlight : (x: string) => x\n const cursor = isActive ? theme.icon.cursor : ` `\n return color(`${cursor} ${indexLabel}${item.name}`)\n },\n pageSize,\n loop,\n })\n\n if (status === \"done\") {\n return `${prefix} ${message} ${theme.style.answer(selectedChoice.short)}`\n }\n\n const choiceDescription = selectedChoice.description\n ? `\\n${theme.style.description(selectedChoice.description)}`\n : ``\n\n return `${[prefix, message, helpTipTop].filter(Boolean).join(\" \")}\\n${page}${helpTipBottom}${choiceDescription}${ansiEscapes.cursorHide}`\n }\n)\n\nexport { Separator } from \"@inquirer/core\"\n","import path from \"path\"\nimport { addOptionsSchema } from \"@/src/commands/add\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { getConfig } from \"@/src/utils/get-config\"\nimport { logger } from \"@/src/utils/logger\"\nimport fs from \"fs-extra\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport async function preFlightAdd(options: z.infer<typeof addOptionsSchema>) {\n const errors: Record<string, boolean> = {}\n\n if (\n !fs.existsSync(options.cwd) ||\n !fs.existsSync(path.resolve(options.cwd, \"package.json\"))\n ) {\n errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT] = true\n return {\n errors,\n config: null,\n }\n }\n\n try {\n const config = await getConfig(options.cwd)\n\n return {\n errors,\n config: config!,\n }\n } catch (error) {\n console.log(\"[preFlightAdd] - \", error)\n\n logger.break()\n logger.error(\n `Make sure you are in a valid project directory. Run ${colors.cyan(\n \"npx @tiptap/cli init\"\n )} to create a new project.`\n )\n logger.break()\n process.exit(0)\n }\n}\n","import path from \"path\"\nimport { resolveImport } from \"@/src/utils/resolve-import\"\nimport { cosmiconfig } from \"cosmiconfig\"\nimport fg from \"fast-glob\"\nimport { loadConfig } from \"tsconfig-paths\"\nimport { z } from \"zod\"\nimport { getProjectInfo } from \"./get-project-info\"\n\nexport const DEFAULT_COMPONENTS = \"@/components\"\nexport const DEFAULT_CONTEXTS = \"@/contexts\"\nexport const DEFAULT_HOOKS = \"@/hooks\"\nexport const DEFAULT_TIPTAP_ICONS = \"@/components/tiptap-icons\"\nexport const DEFAULT_LIB = \"@/lib\"\nexport const DEFAULT_TIPTAP_EXTENSIONS = \"@/components/tiptap-extension\"\nexport const DEFAULT_TIPTAP_NODES = \"@/components/tiptap-node\"\nexport const DEFAULT_TIPTAP_UI = \"@/components/tiptap-ui\"\nexport const DEFAULT_TIPTAP_UI_PRIMITIVES = \"@/components/tiptap-ui-primitive\"\nexport const DEFAULT_TIPTAP_UI_UTILS = \"@/components/tiptap-ui-utils\"\nexport const DEFAULT_STYLES = \"@/styles\"\n\nconst explorer = cosmiconfig(\"components\", {\n searchPlaces: [\"components.json\"],\n})\n\nexport const rawConfigSchema = z.object({\n rsc: z.coerce.boolean().default(false),\n tsx: z.coerce.boolean().default(true),\n aliases: z.object({\n components: z.string(),\n contexts: z.string().optional(),\n hooks: z.string().optional(),\n tiptapIcons: z.string().optional(),\n lib: z.string().optional(),\n tiptapExtensions: z.string().optional(),\n tiptapNodes: z.string().optional(),\n tiptapUi: z.string().optional(),\n tiptapUiPrimitives: z.string().optional(),\n tiptapUiUtils: z.string().optional(),\n styles: z.string().optional(),\n }),\n})\n\nexport const configSchema = rawConfigSchema.extend({\n resolvedPaths: z.object({\n cwd: z.string(),\n components: z.string(),\n contexts: z.string(),\n hooks: z.string(),\n tiptapIcons: z.string(),\n lib: z.string(),\n tiptapExtensions: z.string(),\n tiptapNodes: z.string(),\n tiptapUi: z.string(),\n tiptapUiPrimitives: z.string(),\n tiptapUiUtils: z.string(),\n styles: z.string(),\n }),\n})\n\nexport const workspaceConfigSchema = z.record(configSchema)\n\nexport type RawConfig = z.infer<typeof rawConfigSchema>\n\nexport type Config = z.infer<typeof configSchema>\n\nexport async function getConfig(cwd: string) {\n const res = await explorer.search(cwd)\n const projectInfo = await getProjectInfo(cwd)\n\n const defaultAliases = {\n components: DEFAULT_COMPONENTS,\n contexts: DEFAULT_CONTEXTS,\n hooks: DEFAULT_HOOKS,\n tiptapIcons: DEFAULT_TIPTAP_ICONS,\n lib: DEFAULT_LIB,\n tiptapExtensions: DEFAULT_TIPTAP_EXTENSIONS,\n tiptapNodes: DEFAULT_TIPTAP_NODES,\n tiptapUi: DEFAULT_TIPTAP_UI,\n tiptapUiPrimitives: DEFAULT_TIPTAP_UI_PRIMITIVES,\n tiptapUiUtils: DEFAULT_TIPTAP_UI_UTILS,\n styles: DEFAULT_STYLES,\n }\n\n const applyAliasPrefix = (aliases: typeof defaultAliases, prefix: string) => {\n return Object.fromEntries(\n Object.entries(aliases).map(([key, value]) => [\n key,\n value.replace(/^@/, prefix),\n ])\n ) as typeof defaultAliases\n }\n\n let config: RawConfig\n\n if (!res) {\n let aliases = defaultAliases\n\n if (projectInfo?.aliasPrefix) {\n aliases = applyAliasPrefix(aliases, projectInfo.aliasPrefix)\n }\n\n config = rawConfigSchema.parse({\n rsc: projectInfo?.isRSC ?? false,\n tsx: projectInfo?.isTsx ?? true,\n aliases,\n })\n } else {\n const resolvedAliases = {\n ...defaultAliases,\n ...res.config.aliases,\n }\n\n if (projectInfo?.aliasPrefix) {\n config = rawConfigSchema.parse({\n ...res.config,\n aliases: applyAliasPrefix(resolvedAliases, projectInfo.aliasPrefix),\n })\n } else {\n config = rawConfigSchema.parse({\n ...res.config,\n aliases: resolvedAliases,\n })\n }\n }\n\n return await resolveConfigPaths(cwd, config)\n}\n\nexport async function resolveConfigPaths(cwd: string, config: RawConfig) {\n // Read tsconfig.json.\n const tsConfig = await loadConfig(cwd)\n\n if (tsConfig.resultType === \"failed\") {\n throw new Error(\n `Failed to load ${config.tsx ? \"tsconfig\" : \"jsconfig\"}.json. ${\n tsConfig.message ?? \"\"\n }`.trim()\n )\n }\n\n const schema = configSchema.parse({\n ...config,\n resolvedPaths: {\n cwd,\n components: await resolveImport(config.aliases.components, tsConfig),\n contexts: config.aliases.contexts\n ? await resolveImport(config.aliases.contexts, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"..\",\n \"contexts\"\n ),\n hooks: config.aliases.hooks\n ? await resolveImport(config.aliases.hooks, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"..\",\n \"hooks\"\n ),\n tiptapIcons: config.aliases.tiptapIcons\n ? await resolveImport(config.aliases.tiptapIcons, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-icons\"\n ),\n lib: config.aliases.lib\n ? await resolveImport(config.aliases.lib, tsConfig)\n : path.resolve(\n (await resolveImport(DEFAULT_LIB, tsConfig)) ?? cwd,\n \"..\"\n ),\n tiptapExtensions: config.aliases.tiptapExtensions\n ? await resolveImport(config.aliases.tiptapExtensions, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-extension\"\n ),\n tiptapNodes: config.aliases.tiptapNodes\n ? await resolveImport(config.aliases.tiptapNodes, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-node\"\n ),\n tiptapUi: config.aliases.tiptapUi\n ? await resolveImport(config.aliases.tiptapUi, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-ui\"\n ),\n tiptapUiPrimitives: config.aliases.tiptapUiPrimitives\n ? await resolveImport(config.aliases.tiptapUiPrimitives, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-ui-primitive\"\n ),\n tiptapUiUtils: config.aliases.tiptapUiUtils\n ? await resolveImport(config.aliases.tiptapUiUtils, tsConfig)\n : path.resolve(\n (await resolveImport(config.aliases.components, tsConfig)) ?? cwd,\n \"tiptap-ui-utils\"\n ),\n styles: config.aliases.styles\n ? await resolveImport(config.aliases.styles, tsConfig)\n : path.resolve(cwd, \"styles\"),\n },\n })\n\n return schema\n}\n\n// Note: we can check for -workspace.yaml or \"workspace\" in package.json.\n// Since cwd is not necessarily the root of the project.\n// We'll instead check if ui aliases resolve to a different root.\nexport async function getWorkspaceConfig(config: Config) {\n const resolvedAliases: Record<string, Config> = {}\n\n for (const key of Object.keys(config.aliases)) {\n if (!isAliasKey(key, config)) {\n continue\n }\n\n const resolvedPath = config.resolvedPaths[key]\n const packageRoot = await findPackageRoot(\n config.resolvedPaths.cwd,\n resolvedPath\n )\n\n if (!packageRoot) {\n resolvedAliases[key] = config\n continue\n }\n\n resolvedAliases[key] = await getConfig(packageRoot)\n }\n\n const result = workspaceConfigSchema.safeParse(resolvedAliases)\n if (!result.success) {\n return null\n }\n\n return result.data\n}\n\nexport async function findPackageRoot(cwd: string, resolvedPath: string) {\n const commonRoot = findCommonRoot(cwd, resolvedPath)\n const relativePath = path.relative(commonRoot, resolvedPath)\n\n const packageRoots = await fg.glob(\"**/package.json\", {\n cwd: commonRoot,\n deep: 3,\n ignore: [\"**/node_modules/**\", \"**/dist/**\", \"**/build/**\", \"**/public/**\"],\n })\n\n const matchingPackageRoot = packageRoots\n .map((pkgPath) => path.dirname(pkgPath))\n .find((pkgDir) => relativePath.startsWith(pkgDir))\n\n return matchingPackageRoot ? path.join(commonRoot, matchingPackageRoot) : null\n}\n\nfunction isAliasKey(\n key: string,\n config: Config\n): key is keyof Config[\"aliases\"] {\n return Object.keys(config.resolvedPaths).includes(key)\n}\n\nexport function findCommonRoot(cwd: string, resolvedPath: string) {\n const parts1 = cwd.split(path.sep)\n const parts2 = resolvedPath.split(path.sep)\n const commonParts = []\n\n for (let i = 0; i < Math.min(parts1.length, parts2.length); i++) {\n if (parts1[i] !== parts2[i]) {\n break\n }\n commonParts.push(parts1[i])\n }\n\n return commonParts.join(path.sep)\n}\n","import { createMatchPath, type ConfigLoaderSuccessResult } from \"tsconfig-paths\"\n\nexport async function resolveImport(\n importPath: string,\n config: Pick<ConfigLoaderSuccessResult, \"absoluteBaseUrl\" | \"paths\">\n) {\n return createMatchPath(config.absoluteBaseUrl, config.paths)(\n importPath,\n undefined,\n () => true,\n [\".ts\", \".tsx\"]\n )\n}\n","import path from \"path\"\nimport { FRAMEWORKS, Framework } from \"@/src/utils/frameworks\"\nimport { getPackageInfo } from \"@/src/utils/get-package-info\"\nimport fg from \"fast-glob\"\nimport fs from \"fs-extra\"\nimport { loadConfig } from \"tsconfig-paths\"\nimport {\n Config,\n RawConfig,\n getConfig,\n resolveConfigPaths,\n} from \"@/src/utils/get-config\"\n\nexport type ProjectInfo = {\n framework: Framework\n isSrcDir: boolean\n isRSC: boolean\n isTsx: boolean\n aliasPrefix: string | null\n}\n\nconst PROJECT_SHARED_IGNORE = [\n \"**/node_modules/**\",\n \".next\",\n \"public\",\n \"dist\",\n \"build\",\n]\n\nexport async function getProjectInfo(cwd: string): Promise<ProjectInfo | null> {\n const [configFiles, isSrcDir, isTsx, aliasPrefix, packageJson] =\n await Promise.all([\n fg.glob(\n \"**/{next,vite,astro,app}.config.*|gatsby-config.*|composer.json|react-router.config.*\",\n {\n cwd,\n deep: 3,\n ignore: PROJECT_SHARED_IGNORE,\n }\n ),\n fs.pathExists(path.resolve(cwd, \"src\")),\n isTypeScriptProject(cwd),\n getTsConfigAliasPrefix(cwd),\n getPackageInfo(cwd, false),\n ])\n\n const isUsingAppDir = await fs.pathExists(\n path.resolve(cwd, `${isSrcDir ? \"src/\" : \"\"}app`)\n )\n\n const type: ProjectInfo = {\n framework: FRAMEWORKS[\"manual\"],\n isSrcDir,\n isRSC: false,\n isTsx,\n aliasPrefix,\n }\n\n // Next.js.\n if (configFiles.find((file) => file.startsWith(\"next.config.\"))?.length) {\n type.framework = isUsingAppDir\n ? FRAMEWORKS[\"next-app\"]\n : FRAMEWORKS[\"next-pages\"]\n type.isRSC = isUsingAppDir\n return type\n }\n\n // Astro.\n if (configFiles.find((file) => file.startsWith(\"astro.config.\"))?.length) {\n type.framework = FRAMEWORKS[\"astro\"]\n return type\n }\n\n // Gatsby.\n // if (configFiles.find((file) => file.startsWith(\"gatsby-config.\"))?.length) {\n // type.framework = FRAMEWORKS[\"gatsby\"]\n // return type\n // }\n\n // Laravel.\n if (configFiles.find((file) => file.startsWith(\"composer.json\"))?.length) {\n type.framework = FRAMEWORKS[\"laravel\"]\n return type\n }\n\n // Remix.\n // if (\n // Object.keys(packageJson?.dependencies ?? {}).find((dep) =>\n // dep.startsWith(\"@remix-run/\")\n // )\n // ) {\n // type.framework = FRAMEWORKS[\"remix\"]\n // return type\n // }\n\n // TanStack Start.\n if (\n configFiles.find((file) => file.startsWith(\"app.config.\"))?.length &&\n [\n ...Object.keys(packageJson?.dependencies ?? {}),\n ...Object.keys(packageJson?.devDependencies ?? {}),\n ].find((dep) => dep.startsWith(\"@tanstack/start\"))\n ) {\n type.framework = FRAMEWORKS[\"tanstack-start\"]\n return type\n }\n\n // React Router.\n if (\n configFiles.find((file) => file.startsWith(\"react-router.config.\"))?.length\n ) {\n type.framework = FRAMEWORKS[\"react-router\"]\n return type\n }\n\n // Vite.\n // Some Remix templates also have a vite.config.* file.\n // We'll assume that it got caught by the Remix check above.\n if (configFiles.find((file) => file.startsWith(\"vite.config.\"))?.length) {\n type.framework = FRAMEWORKS[\"vite\"]\n return type\n }\n\n return type\n}\n\nexport async function getTsConfigAliasPrefix(cwd: string) {\n const tsConfig = await loadConfig(cwd)\n\n if (\n tsConfig?.resultType === \"failed\" ||\n !Object.entries(tsConfig?.paths).length\n ) {\n return null\n }\n\n // This assume that the first alias is the prefix.\n for (const [alias, paths] of Object.entries(tsConfig.paths)) {\n if (\n paths.includes(\"./*\") ||\n paths.includes(\"./src/*\") ||\n paths.includes(\"./app/*\") ||\n paths.includes(\"./resources/js/*\") // Laravel.\n ) {\n return alias.replace(/\\/\\*$/, \"\") ?? null\n }\n }\n\n // Use the first alias as the prefix.\n return Object.keys(tsConfig?.paths)?.[0].replace(/\\/\\*$/, \"\") ?? null\n}\n\nexport async function isTypeScriptProject(cwd: string) {\n const files = await fg.glob(\"tsconfig.*\", {\n cwd,\n deep: 1,\n ignore: PROJECT_SHARED_IGNORE,\n })\n\n return files.length > 0\n}\n\nexport async function getProjectConfig(\n cwd: string,\n defaultProjectInfo: ProjectInfo | null = null\n): Promise<Config | null> {\n const [existingConfig, projectInfo] = await Promise.all([\n getConfig(cwd),\n !defaultProjectInfo\n ? getProjectInfo(cwd)\n : Promise.resolve(defaultProjectInfo),\n ])\n\n if (existingConfig) {\n return existingConfig\n }\n\n if (!projectInfo) {\n return null\n }\n\n const config: RawConfig = {\n rsc: projectInfo.isRSC,\n tsx: projectInfo.isTsx,\n aliases: {\n components: `${projectInfo.aliasPrefix}/components`,\n contexts: `${projectInfo.aliasPrefix}/contexts`,\n hooks: `${projectInfo.aliasPrefix}/hooks`,\n tiptapIcons: `${projectInfo.aliasPrefix}/components/tiptap-icons`,\n lib: `${projectInfo.aliasPrefix}/lib`,\n tiptapExtensions: `${projectInfo.aliasPrefix}/components/tiptap-extensions`,\n tiptapNodes: `${projectInfo.aliasPrefix}/components/tiptap-nodes`,\n tiptapUi: `${projectInfo.aliasPrefix}/components/tiptap-ui`,\n tiptapUiPrimitives: `${projectInfo.aliasPrefix}/components/tiptap-ui-primitives`,\n tiptapUiUtils: `${projectInfo.aliasPrefix}/components/tiptap-ui-utils`,\n styles: `${projectInfo.aliasPrefix}/styles`,\n },\n }\n\n return await resolveConfigPaths(cwd, config)\n}\n","export const FRAMEWORKS = {\n \"next-app\": {\n name: \"next-app\",\n label: \"Next.js\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/next\",\n },\n },\n \"next-pages\": {\n name: \"next-pages\",\n label: \"Next.js\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/next\",\n },\n },\n // remix: {\n // name: \"remix\",\n // label: \"Remix\",\n // links: {\n // installation: \"https://tiptap.dev/docs/ui-components/install/remix\",\n // },\n // },\n \"react-router\": {\n name: \"react-router\",\n label: \"React Router\",\n links: {\n installation:\n \"https://tiptap.dev/docs/ui-components/install/react-router\",\n },\n },\n vite: {\n name: \"vite\",\n label: \"Vite\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/vite\",\n },\n },\n astro: {\n name: \"astro\",\n label: \"Astro\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/astro\",\n },\n },\n laravel: {\n name: \"laravel\",\n label: \"Laravel\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/laravel\",\n },\n },\n \"tanstack-start\": {\n name: \"tanstack-start\",\n label: \"TanStack Start\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/tanstack\",\n },\n },\n // gatsby: {\n // name: \"gatsby\",\n // label: \"Gatsby\",\n // links: {\n // installation: \"https://tiptap.dev/docs/ui-components/install/gatsby\",\n // },\n // },\n manual: {\n name: \"manual\",\n label: \"Manual\",\n links: {\n installation: \"https://tiptap.dev/docs/ui-components/install/next\",\n },\n },\n} as const\n\nexport type Framework = (typeof FRAMEWORKS)[keyof typeof FRAMEWORKS]\n","import path from \"path\"\nimport fs from \"fs-extra\"\nimport { type PackageJson } from \"type-fest\"\n\nexport function getPackageInfo(\n cwd: string = \"\",\n shouldThrow: boolean = true\n): PackageJson | null {\n const packageJsonPath = path.join(cwd, \"package.json\")\n\n return fs.readJSONSync(packageJsonPath, {\n throws: shouldThrow,\n }) as PackageJson\n}\n","import chalk from \"chalk\"\n\nexport const colors = {\n cyan: chalk.cyan,\n magenta: chalk.magenta,\n gray: chalk.gray,\n white: chalk.white,\n yellow: chalk.yellow,\n green: chalk.green,\n red: chalk.red,\n blue: chalk.blue,\n reset: chalk.reset,\n dim: chalk.dim,\n bold: chalk.bold,\n whiteBold: chalk.white.bold,\n}\n","import { colors } from \"@/src/utils/colors\"\n\nexport type Logger = {\n error: (...args: unknown[]) => void\n warn: (...args: unknown[]) => void\n info: (...args: unknown[]) => void\n success: (...args: unknown[]) => void\n log: (...args: unknown[]) => void\n break: () => void\n}\n\nconst join = (args: unknown[]) => args.map(String).join(\" \")\n\nexport const logger: Logger = {\n error(...args: unknown[]) {\n console.log(colors.red(join(args)))\n },\n warn(...args: unknown[]) {\n console.log(colors.yellow(join(args)))\n },\n info(...args: unknown[]) {\n console.log(colors.cyan(join(args)))\n },\n success(...args: unknown[]) {\n console.log(colors.green(join(args)))\n },\n log(...args: unknown[]) {\n console.log(join(args))\n },\n break() {\n console.log(\"\")\n },\n}\n","import path from \"path\"\nimport {\n configSchema,\n findCommonRoot,\n findPackageRoot,\n getWorkspaceConfig,\n workspaceConfigSchema,\n type Config,\n} from \"@/src/utils/get-config\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport {\n fetchRegistry,\n getRegistryParentMap,\n getRegistryTypeAliasMap,\n registryResolveItemsTree,\n resolveRegistryItems,\n} from \"@/src/utils/registry\"\nimport { registryItemSchema } from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { updateDependencies } from \"@/src/utils/updaters/update-dependencies\"\nimport { updateFiles } from \"@/src/utils/updaters/update-files\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\nimport { updateDevDependencies } from \"@/src/utils/updaters/update-dev-dependencies\"\n\nexport async function addComponents(\n components: string[],\n config: Config,\n options: {\n overwrite?: boolean\n silent?: boolean\n isNewProject?: boolean\n }\n) {\n options = {\n overwrite: false,\n silent: false,\n isNewProject: false,\n ...options,\n }\n\n const workspaceConfig = await getWorkspaceConfig(config)\n\n if (\n workspaceConfig &&\n workspaceConfig.tiptapUi &&\n workspaceConfig.tiptapUi.resolvedPaths.cwd !== config.resolvedPaths.cwd\n ) {\n return await addWorkspaceComponents(components, config, workspaceConfig, {\n ...options,\n })\n }\n\n return await addProjectComponents(components, config, options)\n}\n\nasync function addProjectComponents(\n components: string[],\n config: z.infer<typeof configSchema>,\n options: {\n overwrite?: boolean\n silent?: boolean\n isNewProject?: boolean\n }\n) {\n const registrySpinner = spinner(`Checking registry`, {\n silent: options.silent,\n }).start()\n const tree = await registryResolveItemsTree(components, config)\n if (!tree) {\n registrySpinner?.fail()\n return handleError(new Error(\"Failed to fetch components from registry\"))\n }\n\n registrySpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n\n await updateDependencies(tree.dependencies, config, {\n silent: options.silent,\n })\n\n await updateDevDependencies(tree.devDependencies, config, {\n silent: options.silent,\n })\n\n return await updateFiles(tree.files, config, {\n overwrite: options.overwrite,\n silent: options.silent,\n })\n}\n\nasync function addWorkspaceComponents(\n components: string[],\n config: z.infer<typeof configSchema>,\n workspaceConfig: z.infer<typeof workspaceConfigSchema>,\n options: {\n overwrite?: boolean\n silent?: boolean\n isNewProject?: boolean\n }\n) {\n const registrySpinner = spinner(`Checking registry`, {\n silent: options.silent,\n }).start()\n const registryItems = await resolveRegistryItems(components)\n const result = await fetchRegistry(registryItems)\n\n const payload = z.array(registryItemSchema).parse(result)\n if (!payload.length) {\n registrySpinner?.fail()\n return handleError(new Error(\"Failed to fetch components from registry\"))\n }\n registrySpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n\n const registryParentMap = getRegistryParentMap(payload)\n const registryTypeAliasMap = getRegistryTypeAliasMap()\n\n const filesCreated: string[] = []\n const filesUpdated: string[] = []\n const filesSkipped: string[] = []\n\n const rootSpinner = spinner(`Installing components`)?.start()\n\n for (const component of payload) {\n const alias = registryTypeAliasMap.get(component.type)\n const registryParent = registryParentMap.get(component.name)\n\n // We don't support this type of component.\n if (!alias) {\n continue\n }\n\n // A good start is ui for now.\n const targetConfig =\n component.type === \"registry:ui\" || registryParent?.type === \"registry:ui\"\n ? workspaceConfig.tiptapUi || config\n : config\n\n if (!targetConfig.resolvedPaths.tiptapUi) {\n continue\n }\n\n const workspaceRoot = findCommonRoot(\n config.resolvedPaths.cwd,\n targetConfig.resolvedPaths.tiptapUi\n )\n const packageRoot =\n (await findPackageRoot(workspaceRoot, targetConfig.resolvedPaths.cwd)) ??\n targetConfig.resolvedPaths.cwd\n\n // 3. Update dependencies.\n await updateDependencies(component.dependencies || [], targetConfig, {\n silent: true,\n })\n\n await updateDevDependencies(component.devDependencies || [], targetConfig, {\n silent: true,\n })\n\n // 4. Update files.\n const files = await updateFiles(component.files || [], targetConfig, {\n overwrite: options.overwrite,\n silent: true,\n rootSpinner,\n })\n\n if (files.errors && files.errors.length > 0) {\n spinner(`Encountered ${files.errors.length} errors:`, {\n silent: options.silent,\n })?.fail()\n\n for (const { file, error } of files.errors) {\n logger.error(` - ${file}: ${error}`)\n }\n }\n\n filesCreated.push(\n ...files.filesCreated.map((file) =>\n path.relative(workspaceRoot, path.join(packageRoot, file))\n )\n )\n filesUpdated.push(\n ...files.filesUpdated.map((file) =>\n path.relative(workspaceRoot, path.join(packageRoot, file))\n )\n )\n filesSkipped.push(\n ...files.filesSkipped.map((file) =>\n path.relative(workspaceRoot, path.join(packageRoot, file))\n )\n )\n }\n\n rootSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n\n // Sort files.\n filesCreated.sort()\n filesUpdated.sort()\n filesSkipped.sort()\n\n const hasUpdatedFiles = filesCreated.length || filesUpdated.length\n if (!hasUpdatedFiles && !filesSkipped.length) {\n spinner(`No files updated`, {\n silent: options.silent,\n })?.info()\n }\n\n if (filesCreated.length) {\n spinner(\n `Created ${filesCreated.length} ${\n filesCreated.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n for (const file of filesCreated) {\n logger.log(` - ${file}`)\n }\n }\n\n if (filesUpdated.length) {\n spinner(\n `Updated ${filesUpdated.length} ${\n filesUpdated.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.info()\n for (const file of filesUpdated) {\n logger.log(` - ${file}`)\n }\n }\n\n if (filesSkipped.length) {\n spinner(\n `Skipped ${filesSkipped.length} ${\n filesSkipped.length === 1 ? \"file\" : \"files\"\n }: (use --overwrite to overwrite)`,\n {\n silent: options.silent,\n }\n )?.info()\n for (const file of filesSkipped) {\n logger.log(` - ${file}`)\n }\n }\n\n return {\n filesCreated,\n filesUpdated,\n filesSkipped,\n }\n}\n","import { logger } from \"@/src/utils/logger\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport function handleError(error: unknown) {\n logger.error(\n `Something went wrong. Please check the error below for more details.`\n )\n logger.error(`If the problem persists, please open an issue on GitHub.`)\n logger.error(\"\")\n if (typeof error === \"string\") {\n logger.error(error)\n logger.break()\n process.exit(0)\n }\n\n if (error instanceof z.ZodError) {\n logger.error(\"Validation failed:\")\n for (const [key, value] of Object.entries(error.flatten().fieldErrors)) {\n logger.error(`- ${colors.cyan(key)}: ${value}`)\n }\n logger.break()\n process.exit(0)\n }\n\n if (error instanceof Error) {\n logger.error(error.message)\n logger.break()\n process.exit(0)\n }\n\n logger.break()\n process.exit(0)\n}\n","import { z } from \"zod\"\n\nexport const registryItemTypeSchema = z.enum([\n \"registry:context\",\n \"registry:extension\",\n \"registry:hook\",\n \"registry:icon\",\n \"registry:lib\",\n \"registry:node\",\n \"registry:template\",\n \"registry:ui-primitive\",\n \"registry:ui\",\n \"registry:ui-utils\",\n \"registry:page\",\n \"registry:component\",\n \"registry:style\",\n \"registry:asset\",\n])\n\nexport type PaidPlan = \"start\" | \"team\" | \"growth\" | \"enterprise\"\nexport type FreePlan = \"open-source\" | \"light\"\nexport type Plan = PaidPlan | FreePlan\n\nexport const PAID_PLANS = [\n \"start\",\n \"team\",\n \"growth\",\n \"enterprise\",\n] as const satisfies readonly PaidPlan[]\n\nexport const FREE_PLANS = [\n \"open-source\",\n \"light\",\n] as const satisfies readonly FreePlan[]\n\nconst ALL_PLANS = [...PAID_PLANS, ...FREE_PLANS] as const\n\nexport const planSchema = z.array(z.enum(ALL_PLANS)).default([])\n\nexport const registryItemFileSchema = z.object({\n path: z.string(),\n content: z.string().optional(),\n type: registryItemTypeSchema,\n target: z.string().optional(),\n})\n\nexport const registryItemSchema = z.object({\n name: z.string(),\n type: registryItemTypeSchema,\n description: z.string().optional(),\n dependencies: z.array(z.string()).optional(),\n devDependencies: z.array(z.string()).optional(),\n registryDependencies: z.array(z.string()).optional(),\n files: z.array(registryItemFileSchema).optional(),\n meta: z.record(z.string(), z.any()).optional(),\n plans: planSchema.optional(),\n hide: z.boolean().default(false).optional(),\n isNew: z.boolean().default(false).optional(),\n})\n\nexport const registrySchema = z.array(registryItemSchema)\n\nexport type Registry = z.infer<typeof registrySchema>\n\nexport const registryIndexSchema = z.array(\n registryItemSchema.extend({\n files: z.array(z.union([z.string(), registryItemFileSchema])).optional(),\n })\n)\n\nexport const registryResolvedItemsTreeSchema = registryItemSchema.pick({\n dependencies: true,\n devDependencies: true,\n files: true,\n})\n\nexport type RegistryItem = z.infer<typeof registryItemSchema>\nexport type RegistryItemIndexSchema = z.infer<typeof registryIndexSchema>\n","import { configSchema } from \"@/src/utils/get-config\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport {\n registryIndexSchema,\n RegistryItem,\n registryItemSchema,\n registryResolvedItemsTreeSchema,\n} from \"@/src/utils/registry/schema\"\nimport deepmerge from \"deepmerge\"\nimport { HttpsProxyAgent } from \"https-proxy-agent\"\nimport fetch, { Response } from \"node-fetch\"\nimport { z } from \"zod\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { Framework, FRAMEWORKS } from \"@/src/utils/frameworks\"\nimport { colors } from \"@/src/utils/colors\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\n\nexport const REGISTRY_URL = \"https://template.tiptap.dev\"\n// export const REGISTRY_URL = \"https://template-preview.tiptap.dev\"\n// export const REGISTRY_URL = \"http://localhost:3000\"\n\nconst agent = process.env.https_proxy\n ? new HttpsProxyAgent(process.env.https_proxy)\n : undefined\n\nexport async function getRegistryIndex() {\n try {\n const [result] = await fetchRegistry([\"index.json\"])\n\n return registryIndexSchema.parse(result)\n } catch (error) {\n logger.error(\"\\n\")\n handleError(error)\n }\n}\n\nfunction createRegistryError(response: Response, url?: string): Error {\n const errorMessages: Record<number, string> = {\n 400: \"Bad request\",\n 401: \"Unauthorized\",\n 403: \"Forbidden\",\n 404: \"Not found\",\n 500: \"Internal server error\",\n }\n\n const urlInfo = url ? ` at ${colors.cyan(url)}` : \"\"\n\n switch (response.status) {\n case 401:\n tokenStorage.clear()\n return new Error(\n `You are not authorized to access the component${urlInfo}.\\n` +\n `Please run ${colors.cyan(\"@tiptap/cli login\")} to log in to your Tiptap Cloud account.`\n )\n\n case 404:\n return new Error(\n `The component${urlInfo} was not found.\\n` +\n `It may not exist at the registry. Please make sure it is a valid component.`\n )\n\n case 403:\n return new Error(\n `You do not have access to the component${urlInfo}.\\n` +\n `Your account may not have the required subscription plan for this component.\\n` +\n `Please upgrade your subscription or use a component available in your current plan.`\n )\n\n default:\n const message = errorMessages[response.status] || response.statusText\n return new Error(`Failed to fetch${urlInfo}.\\n${message}`)\n }\n}\n\nasync function fetchComponent(path: string, headers: Record<string, string>) {\n const url = getRegistryUrl(path)\n\n const response = await fetch(url, {\n agent,\n headers,\n })\n\n if (!response.ok) {\n throw createRegistryError(response, url)\n }\n\n return response.json()\n}\n\nasync function fetchRegistryBatch(\n componentNames: string[],\n headers: Record<string, string>\n) {\n const response = await fetch(\n `${REGISTRY_URL}/api/registry/components/batch`,\n {\n method: \"POST\",\n agent,\n headers,\n body: JSON.stringify({ components: componentNames }),\n }\n )\n\n if (!response.ok) {\n throw createRegistryError(response)\n }\n\n const results = (await response.json()) as RegistryItem[]\n\n return results\n}\n\nexport async function fetchRegistry(paths: string[]) {\n try {\n const bearerToken = tokenStorage.getBearerToken()\n const headers: Record<string, string> = {\n \"Content-Type\": \"application/json\",\n }\n\n if (bearerToken) {\n headers[\"Authorization\"] = `Bearer ${bearerToken}`\n }\n\n const componentNames = paths.map((path) => {\n if (path.includes(\"/components/\")) {\n return path.replace(/.*\\/components\\//, \"\").replace(\".json\", \"\")\n }\n return path.replace(\".json\", \"\")\n })\n\n if (componentNames.length > 1) {\n return await fetchRegistryBatch(componentNames, headers)\n }\n\n return Promise.all(paths.map((path) => fetchComponent(path, headers)))\n } catch (error) {\n logger.error(\"\\n\")\n handleError(error)\n return []\n }\n}\n\nexport async function fetchRegistryDependencies(\n components: string[]\n): Promise<string[]> {\n const response = await fetch(`${REGISTRY_URL}/api/registry/dependencies`, {\n method: \"POST\",\n agent,\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({ components }),\n })\n\n if (!response.ok) {\n throw new Error(\n `Failed to fetch registry dependencies: ${response.statusText}`\n )\n }\n\n return (await response.json()) as Promise<string[]>\n}\n\nexport async function registryResolveItemsTree(\n names: RegistryItem[\"name\"][],\n config: z.infer<typeof configSchema>\n) {\n try {\n const index = await getRegistryIndex()\n if (!index) {\n return null\n }\n\n // If we're resolving the index, we want it to go first.\n if (names.includes(\"index\")) {\n names.unshift(\"index\")\n }\n\n const registryItems = await resolveRegistryItems(names)\n const result = await fetchRegistry(registryItems)\n const payload = z.array(registryItemSchema).parse(result)\n\n if (!payload) {\n return null\n }\n\n const projectInfo = await getProjectInfo(config.resolvedPaths.cwd)\n const framework = projectInfo?.framework.name as Framework[\"name\"]\n\n const allDependencies = deepmerge.all(\n payload.map((item) => item.dependencies ?? [])\n )\n\n const allDevDependencies = deepmerge.all(\n payload.map((item) => item.devDependencies ?? [])\n )\n\n const filteredDevDependencies = filterDevDependenciesByFramework(\n allDevDependencies,\n framework\n )\n\n return registryResolvedItemsTreeSchema.parse({\n dependencies: allDependencies,\n devDependencies: filteredDevDependencies,\n files: deepmerge.all(payload.map((item) => item.files ?? [])),\n })\n } catch (error) {\n handleError(error)\n return null\n }\n}\n\nexport async function resolveRegistryItems(names: string[]) {\n const results = await fetchRegistryDependencies(names)\n const registryDependencies = results.map((name) =>\n getRegistryUrl(`components/${name}.json`)\n )\n\n return registryDependencies\n}\n\nfunction getRegistryUrl(path: string) {\n if (isUrl(path)) {\n const url = new URL(path)\n return url.toString()\n }\n\n if (!REGISTRY_URL) {\n throw new Error(\"No registry URL found\")\n }\n\n // Keep the index.json path as is (public)\n if (path === \"index.json\") {\n return `${REGISTRY_URL}/r/${path}`\n }\n\n // Only redirect component paths to the API\n if (path.startsWith(\"components/\")) {\n const componentName = path.replace(\"components/\", \"\").replace(\".json\", \"\")\n return `${REGISTRY_URL}/api/registry/components/${componentName}`\n }\n\n return `${REGISTRY_URL}/${path}`\n}\n\nfunction isUrl(path: string) {\n try {\n new URL(path)\n return true\n } catch (error) {\n return false\n }\n}\n\nexport function getRegistryTypeAliasMap() {\n return new Map<string, string>([\n [\"registry:ui\", \"tiptapUi\"],\n [\"registry:ui-primitive\", \"tiptapUiPrimitives\"],\n [\"registry:ui-utils\", \"tiptapUiUtils\"],\n [\"registry:extension\", \"tiptapExtensions\"],\n [\"registry:node\", \"tiptapNodes\"],\n [\"registry:context\", \"contexts\"],\n [\"registry:hook\", \"hooks\"],\n [\"registry:lib\", \"lib\"],\n [\"registry:context\", \"components\"],\n [\"registry:template\", \"tiptapTemplates\"],\n [\"registry:component\", \"components\"],\n [\"registry:icon\", \"titpapIcons\"],\n [\"registry:style\", \"styles\"],\n ])\n}\n\n// Track a dependency and its parent.\nexport function getRegistryParentMap(registryItems: RegistryItem[]) {\n const map = new Map<string, RegistryItem>()\n\n registryItems.forEach((item) => {\n if (!item.registryDependencies) {\n return\n }\n\n item.registryDependencies.forEach((dependency) => {\n map.set(dependency, item)\n })\n })\n\n return map\n}\n\n/**\n * Filter development dependencies based on framework requirements\n * @param devDependencies Array of development dependencies\n * @param framework Framework name\n * @returns Filtered array of development dependencies\n */\nfunction filterDevDependenciesByFramework(\n devDependencies: unknown,\n framework: Framework[\"name\"]\n): string[] {\n const depsArray = Array.isArray(devDependencies) ? devDependencies : []\n\n if (!depsArray.length) {\n return []\n }\n\n const stringDeps = depsArray.map((dep) => String(dep))\n\n if (framework) {\n const hasSass = stringDeps.includes(\"sass\")\n const hasSassEmbedded = stringDeps.includes(\"sass-embedded\")\n\n if (hasSass || hasSassEmbedded) {\n let filteredDeps = [...stringDeps]\n\n const prefersEmbedded: Framework[\"name\"][] = [\n FRAMEWORKS.astro.name,\n FRAMEWORKS.laravel.name,\n FRAMEWORKS.vite.name,\n // FRAMEWORKS.remix.name,\n FRAMEWORKS[\"tanstack-start\"].name,\n FRAMEWORKS[\"react-router\"].name,\n ]\n\n const prefersRegular: Framework[\"name\"][] = [\n FRAMEWORKS[\"next-app\"].name,\n FRAMEWORKS[\"next-pages\"].name,\n // FRAMEWORKS.gatsby.name,\n ]\n\n if (prefersEmbedded.includes(framework)) {\n filteredDeps = filteredDeps.filter((dep) => dep !== \"sass\")\n } else if (prefersRegular.includes(framework)) {\n filteredDeps = filteredDeps.filter((dep) => dep !== \"sass-embedded\")\n }\n\n return filteredDeps\n }\n }\n\n return stringDeps\n}\n","import Conf from \"conf\"\nimport type { Logger } from \"./logger\"\n\nexport interface TokenConfig {\n bearerToken?: string\n authToken?: string\n email?: string\n loginDate?: string\n plans?: string[]\n licenseAccepted?: boolean\n licenseAcceptedDate?: string\n}\n\nexport class TokenStorage {\n private config: Conf<TokenConfig>\n private logger: Logger\n\n constructor(logger: Logger) {\n this.logger = logger\n this.config = new Conf<TokenConfig>({\n projectName: \"tiptap-cli\",\n clearInvalidConfig: true, // auto-reset if file is corrupted\n schema: {\n bearerToken: { type: \"string\" },\n authToken: { type: \"string\" },\n email: { type: \"string\" },\n loginDate: { type: \"string\" },\n plans: { type: \"array\", items: { type: \"string\" }, default: [] },\n licenseAccepted: { type: \"boolean\" },\n licenseAcceptedDate: { type: \"string\" },\n },\n })\n }\n\n private safeError(prefix: string, error: unknown) {\n const msg =\n error instanceof Error\n ? `${error.name}: ${error.message}`\n : String(error ?? \"Unknown error\")\n try {\n this.logger.error(`${prefix}: ${msg}`)\n } catch {\n // never throw from logging\n }\n }\n\n setBearerToken(\n token: string,\n userInfo?: { email?: string; plans?: string[] }\n ): void {\n try {\n this.config.set(\"bearerToken\", token)\n this.config.set(\"loginDate\", new Date().toISOString())\n if (userInfo?.email) this.config.set(\"email\", userInfo.email)\n if (userInfo?.plans) this.config.set(\"plans\", userInfo.plans)\n } catch (e) {\n this.safeError(\"Failed to store bearer token\", e)\n }\n }\n\n getBearerToken(): string | null {\n try {\n return this.config.get(\"bearerToken\") ?? null\n } catch (e) {\n this.safeError(\"Failed to retrieve bearer token\", e)\n return null\n }\n }\n\n setAuthToken(\n token: string,\n userInfo?: { email?: string; plans?: string[] }\n ): void {\n try {\n this.config.set(\"authToken\", token)\n this.config.set(\"loginDate\", new Date().toISOString())\n if (userInfo?.email) this.config.set(\"email\", userInfo.email)\n if (userInfo?.plans) this.config.set(\"plans\", userInfo.plans)\n } catch (e) {\n this.safeError(\"Failed to store auth token\", e)\n }\n }\n\n getAuthToken(): string | null {\n try {\n return this.config.get(\"authToken\") ?? null\n } catch (e) {\n this.safeError(\"Failed to retrieve auth token\", e)\n return null\n }\n }\n\n getUserInfo(): { email?: string; plans: string[]; loginDate?: string } {\n return {\n email: this.config.get(\"email\"),\n plans: this.config.get(\"plans\") ?? [],\n loginDate: this.config.get(\"loginDate\"),\n }\n }\n\n getTokenExpiration(): string | null {\n const loginDate = this.config.get(\"loginDate\")\n if (!loginDate) return null\n const expiration = new Date(loginDate)\n expiration.setMonth(expiration.getMonth() + 11)\n\n return expiration.toISOString()\n }\n\n isValidToken(): boolean {\n const bearerToken = this.getBearerToken()\n const authToken = this.getAuthToken()\n\n if (!bearerToken && !authToken) return false\n\n const expirationISO = this.getTokenExpiration()\n if (expirationISO) {\n const expiryDate = new Date(expirationISO)\n if (expiryDate <= new Date()) {\n this.clear()\n return false\n }\n }\n\n return true\n }\n\n clear(): void {\n try {\n this.config.clear()\n } catch (e) {\n this.safeError(\"Failed to clear token storage\", e)\n }\n }\n\n hasPlan(planName: string): boolean {\n const plans = this.config.get(\"plans\") ?? []\n return Array.isArray(plans) && plans.includes(planName)\n }\n\n setLicenseAccepted(): void {\n try {\n this.config.set(\"licenseAccepted\", true)\n this.config.set(\"licenseAcceptedDate\", new Date().toISOString())\n } catch (e) {\n this.safeError(\"Failed to store license acceptance\", e)\n }\n }\n\n hasAcceptedLicense(): boolean {\n try {\n return this.config.get(\"licenseAccepted\") ?? false\n } catch (e) {\n this.safeError(\"Failed to retrieve license acceptance\", e)\n return false\n }\n }\n\n clearLicenseAcceptance(): void {\n try {\n this.config.delete(\"licenseAccepted\")\n this.config.delete(\"licenseAcceptedDate\")\n } catch (e) {\n this.safeError(\"Failed to clear license acceptance\", e)\n }\n }\n}\n","import { logger } from \"./logger\"\nimport { TokenStorage } from \"./token-storage\"\n\nexport const tokenStorage = new TokenStorage(logger)\n","import ora, { type Options } from \"ora\"\nimport { colors } from \"@/src/utils/colors\"\n\n// Custom Tiptap-style spinner frames that resemble a typewriter cursor\nconst tiptapSpinner = {\n frames: [\n `${colors.cyan(\"█\")}`, // Full block (cursor visible)\n `${colors.cyan(\"█\")}`, // Full block (cursor visible)\n `${colors.cyan(\"█\")}`, // Full block (cursor visible)\n ` `, // Space (cursor hidden)\n ` `, // Space (cursor hidden)\n ` `, // Space (cursor hidden)\n ],\n interval: 200, // Typewriter-like blinking speed\n}\n\nexport function spinner(\n text: Options[\"text\"],\n options?: {\n silent?: boolean\n }\n) {\n return ora({\n text: text,\n spinner: tiptapSpinner,\n color: \"cyan\",\n isSilent: options?.silent,\n })\n}\n","import { detect } from \"@antfu/ni\"\nimport fs from \"fs-extra\"\nimport path from \"path\"\n\nexport async function getPackageManager(\n targetDir: string,\n { withFallback }: { withFallback?: boolean } = {\n withFallback: false,\n }\n): Promise<\"yarn\" | \"pnpm\" | \"bun\" | \"npm\"> {\n let packageManager = await detect({ programmatic: true, cwd: targetDir })\n if (packageManager === \"deno\") packageManager = undefined\n\n if (packageManager === \"yarn@berry\") return \"yarn\"\n if (packageManager === \"pnpm@6\") return \"pnpm\"\n if (packageManager === \"bun\") return \"bun\"\n\n if (!withFallback) {\n return packageManager ?? \"npm\"\n }\n\n // Fallback to user agent if not detected.\n const userAgent = process.env.npm_config_user_agent || \"\"\n\n if (userAgent.startsWith(\"yarn\")) {\n return \"yarn\"\n }\n\n if (userAgent.startsWith(\"pnpm\")) {\n return \"pnpm\"\n }\n\n if (userAgent.startsWith(\"bun\")) {\n return \"bun\"\n }\n\n return \"npm\"\n}\n\nexport async function getPackageRunner(cwd: string) {\n const packageManager = await getPackageManager(cwd)\n\n if (packageManager === \"pnpm\") return \"pnpm dlx\"\n\n if (packageManager === \"bun\") return \"bunx\"\n\n return \"npx\"\n}\n\nexport function isBunProject(cwd: string) {\n const hasBunLock = fs.existsSync(path.join(cwd, \"bun.lock\"))\n const hasBunfig = fs.existsSync(path.join(cwd, \"bunfig.toml\"))\n\n if (hasBunLock && hasBunfig) {\n return true\n }\n\n return false\n}\n","import { Config } from \"@/src/utils/get-config\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { RegistryItem } from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { execa } from \"execa\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport async function updateDependencies(\n dependencies: RegistryItem[\"dependencies\"],\n config: Config,\n options: {\n silent?: boolean\n }\n) {\n dependencies = Array.from(new Set(dependencies))\n if (!dependencies?.length) {\n return\n }\n\n options = {\n silent: false,\n ...options,\n }\n\n const dependenciesSpinner = spinner(`Installing dependencies.`, {\n silent: options.silent,\n }).start()\n const packageManager = await getPackageManager(config.resolvedPaths.cwd)\n\n await execa(\n packageManager,\n [\n packageManager === \"npm\" ? \"install\" : \"add\",\n ...(packageManager === \"npm\" ? [\"--save\"] : []),\n ...dependencies,\n ],\n {\n cwd: config.resolvedPaths.cwd,\n }\n )\n\n dependenciesSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n}\n","import { existsSync, promises as fs } from \"fs\"\nimport path, { basename } from \"path\"\nimport { Config } from \"@/src/utils/get-config\"\nimport { getProjectInfo, ProjectInfo } from \"@/src/utils/get-project-info\"\nimport { logger } from \"@/src/utils/logger\"\nimport {\n RegistryItem,\n registryItemFileSchema,\n} from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { transform } from \"@/src/utils/transformers\"\nimport { transformImport } from \"@/src/utils/transformers/transform-import\"\nimport { transformRsc } from \"@/src/utils/transformers/transform-rsc\"\nimport { z } from \"zod\"\nimport { confirm } from \"@inquirer/prompts\"\nimport {\n getPackageManager,\n isBunProject,\n} from \"@/src/utils/get-package-manager\"\nimport { colors } from \"@/src/utils/colors\"\nimport { transformRemoveComponents } from \"@/src/utils/transformers/transform-remove-components\"\n\nexport async function updateFiles(\n files: RegistryItem[\"files\"],\n config: Config,\n options: {\n overwrite?: boolean\n force?: boolean\n silent?: boolean\n rootSpinner?: ReturnType<typeof spinner>\n }\n) {\n const result = {\n filesCreated: [] as string[],\n filesUpdated: [] as string[],\n filesSkipped: [] as string[],\n errors: [] as { file: string; error: string }[],\n }\n\n if (!files?.length) {\n return result\n }\n\n options = {\n overwrite: false,\n force: false,\n silent: false,\n ...options,\n }\n\n const filesCreatedSpinner = spinner(`Updating files.`, {\n silent: options.silent,\n })?.start()\n\n try {\n const [projectInfo, packageManager] = await Promise.all([\n getProjectInfo(config.resolvedPaths.cwd),\n getPackageManager(config.resolvedPaths.cwd),\n ])\n\n for (const file of files) {\n try {\n if (!file.content) {\n continue\n }\n\n let filePath: string | undefined\n try {\n filePath = resolveFilePath(file, config, {\n isSrcDir: projectInfo?.isSrcDir,\n framework: projectInfo?.framework.name,\n commonRoot: findCommonRoot(\n files.map((f) => f.path),\n file.path\n ),\n })\n } catch (error) {\n result.errors.push({\n file: file.path,\n error: `Failed to resolve file path: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n\n if (!filePath) {\n continue\n }\n\n const fileName = basename(file.path)\n const targetDir = path.dirname(filePath)\n\n if (!config.tsx) {\n filePath = filePath.replace(/\\.tsx?$/, (match) =>\n match === \".tsx\" ? \".jsx\" : \".js\"\n )\n }\n\n const isBun = isBunProject(config.resolvedPaths.cwd)\n\n // For Bun projects, convert .scss files to .css\n if (isBun && filePath.endsWith(\".scss\")) {\n filePath = filePath.replace(/\\.scss$/, \".css\")\n }\n\n let existingFile = false\n try {\n existingFile = existsSync(filePath)\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to check if file exists: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n\n let content: string\n try {\n content = await transform(\n {\n filename: file.path,\n raw: file.content,\n config,\n transformJsx: !config.tsx,\n packageManager,\n },\n [transformImport, transformRsc, transformRemoveComponents]\n )\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to transform content: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n\n if (existingFile) {\n try {\n const existingFileContent = await fs.readFile(filePath, \"utf-8\")\n const [normalizedExisting, normalizedNew] = await Promise.all([\n getNormalizedFileContent(existingFileContent),\n getNormalizedFileContent(content),\n ])\n if (normalizedExisting === normalizedNew) {\n result.filesSkipped.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n continue\n }\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to read or normalize existing file: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n }\n }\n\n if (existingFile && !options.overwrite) {\n filesCreatedSpinner?.stop()\n if (options.rootSpinner) {\n options.rootSpinner?.stop()\n }\n\n try {\n const overwrite = await confirm({\n message: colors.reset(\n `The file ${colors.cyan(\n fileName\n )} already exists. Would you like to overwrite?`\n ),\n theme: {\n prefix: colors.cyan(\"?\"),\n style: {\n message: (text: string) => colors.reset(text),\n },\n },\n })\n\n if (!overwrite) {\n result.filesSkipped.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n if (options.rootSpinner) {\n options.rootSpinner.start()\n }\n continue\n }\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to get user confirmation: ${error instanceof Error ? error.message : String(error)}`,\n })\n continue\n } finally {\n filesCreatedSpinner?.start()\n if (options.rootSpinner) {\n options.rootSpinner.start()\n }\n }\n }\n\n try {\n if (!existsSync(targetDir)) {\n await fs.mkdir(targetDir, { recursive: true })\n }\n\n await fs.writeFile(filePath, content, \"utf-8\")\n\n existingFile\n ? result.filesUpdated.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n : result.filesCreated.push(\n path.relative(config.resolvedPaths.cwd, filePath)\n )\n } catch (error) {\n result.errors.push({\n file: filePath,\n error: `Failed to write file: ${error instanceof Error ? error.message : String(error)}`,\n })\n }\n } catch (error) {\n result.errors.push({\n file: file.path || \"unknown\",\n error: `Unexpected error processing file: ${error instanceof Error ? error.message : String(error)}`,\n })\n }\n }\n } catch (error) {\n logger.error(\n `An error occurred while updating files: ${error instanceof Error ? error.message : String(error)}`\n )\n } finally {\n const hasUpdatedFiles =\n result.filesCreated.length || result.filesUpdated.length\n if (!hasUpdatedFiles && !result.filesSkipped.length) {\n filesCreatedSpinner?.info(\"No files updated.\")\n }\n\n if (result.filesCreated.length) {\n filesCreatedSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: `Created ${result.filesCreated.length} ${\n result.filesCreated.length === 1 ? \"file\" : \"files\"\n }:`,\n })\n if (!options.silent) {\n for (const file of result.filesCreated) {\n logger.log(` - ${file}`)\n }\n }\n } else {\n filesCreatedSpinner?.stop()\n }\n\n if (result.filesUpdated.length) {\n spinner(\n `Updated ${result.filesUpdated.length} ${\n result.filesUpdated.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.info()\n if (!options.silent) {\n for (const file of result.filesUpdated) {\n logger.log(` - ${file}`)\n }\n }\n }\n\n if (result.filesSkipped.length) {\n spinner(\n `Skipped ${result.filesSkipped.length} ${\n result.filesUpdated.length === 1 ? \"file\" : \"files\"\n }: (use --overwrite to overwrite)`,\n {\n silent: options.silent,\n }\n )?.info()\n if (!options.silent) {\n for (const file of result.filesSkipped) {\n logger.log(` - ${file}`)\n }\n }\n }\n\n if (result.errors.length) {\n spinner(\n `Failed to process ${result.errors.length} ${\n result.errors.length === 1 ? \"file\" : \"files\"\n }:`,\n {\n silent: options.silent,\n }\n )?.fail()\n if (!options.silent) {\n for (const { file, error } of result.errors) {\n logger.error(` - ${file}: ${error}`)\n }\n }\n }\n\n if (!options.silent) {\n logger.break()\n }\n }\n\n return result\n}\n\nexport function resolveFileTargetDirectory(\n file: z.infer<typeof registryItemFileSchema>,\n config: Config,\n override?: string\n) {\n if (override) {\n return override\n }\n\n if (file.type === \"registry:ui\") {\n return config.resolvedPaths.tiptapUi\n }\n\n if (file.type === \"registry:ui-primitive\") {\n return config.resolvedPaths.tiptapUiPrimitives\n }\n\n if (file.type === \"registry:ui-utils\") {\n return config.resolvedPaths.tiptapUiUtils\n }\n\n if (file.type === \"registry:extension\") {\n return config.resolvedPaths.tiptapExtensions\n }\n\n if (file.type === \"registry:node\") {\n return config.resolvedPaths.tiptapNodes\n }\n\n if (file.type === \"registry:icon\") {\n return config.resolvedPaths.tiptapIcons\n }\n\n if (file.type === \"registry:hook\") {\n return config.resolvedPaths.hooks\n }\n\n if (file.type === \"registry:lib\") {\n return config.resolvedPaths.lib\n }\n\n if (file.type === \"registry:context\") {\n return config.resolvedPaths.contexts\n }\n\n if (file.type === \"registry:template\" || file.type === \"registry:component\") {\n return config.resolvedPaths.components\n }\n\n if (file.type === \"registry:style\") {\n return config.resolvedPaths.styles\n }\n\n return config.resolvedPaths.components\n}\n\nexport function findCommonRoot(paths: string[], needle: string): string {\n // Remove leading slashes for consistent handling\n const normalizedPaths = paths.map((p) => p.replace(/^\\//, \"\"))\n const normalizedNeedle = needle.replace(/^\\//, \"\")\n\n // Get the directory path of the needle by removing the file name\n const needleDir = normalizedNeedle.split(\"/\").slice(0, -1).join(\"/\")\n\n // If needle is at root level, return empty string\n if (!needleDir) {\n return \"\"\n }\n\n // Split the needle directory into segments\n const needleSegments = needleDir.split(\"/\")\n\n // Start from the full path and work backwards\n for (let i = needleSegments.length; i > 0; i--) {\n const testPath = needleSegments.slice(0, i).join(\"/\")\n // Check if this is a common root by verifying if any other paths start with it\n const hasRelatedPaths = normalizedPaths.some(\n (path) => path !== normalizedNeedle && path.startsWith(testPath + \"/\")\n )\n if (hasRelatedPaths) {\n return \"/\" + testPath // Add leading slash back for the result\n }\n }\n\n // If no common root found with other files, return the parent directory of the needle\n return \"/\" + needleDir // Add leading slash back for the result\n}\n\nexport async function getNormalizedFileContent(content: string) {\n return content.replace(/\\r\\n/g, \"\\n\").trim()\n}\n\nexport function resolvePageTarget(\n target: string,\n framework?: ProjectInfo[\"framework\"][\"name\"]\n) {\n if (!framework) {\n return \"\"\n }\n\n if (framework === \"next-app\") {\n return target\n }\n\n if (framework === \"next-pages\") {\n let result = target.replace(/^app\\//, \"pages/\")\n result = result.replace(/\\/page(\\.[jt]sx?)$/, \"$1\")\n\n return result\n }\n\n if (framework === \"react-router\") {\n let result = target.replace(/^app\\//, \"app/routes/\")\n result = result.replace(/\\/page(\\.[jt]sx?)$/, \"$1\")\n\n return result\n }\n\n if (framework === \"laravel\") {\n let result = target.replace(/^app\\//, \"resources/js/pages/\")\n result = result.replace(/\\/page(\\.[jt]sx?)$/, \"$1\")\n\n return result\n }\n\n return \"\"\n}\n\nexport function resolveNestedFilePath(\n filePath: string,\n targetDir: string\n): string {\n // Normalize paths by removing leading/trailing slashes\n const normalizedFilePath = filePath.replace(/^\\/|\\/$/g, \"\")\n const normalizedTargetDir = targetDir.replace(/^\\/|\\/$/g, \"\")\n\n // Split paths into segments\n const fileSegments = normalizedFilePath.split(\"/\")\n const targetSegments = normalizedTargetDir.split(\"/\")\n\n // Find the last matching segment from targetDir in filePath\n const lastTargetSegment = targetSegments[targetSegments.length - 1]\n const commonDirIndex = fileSegments.findIndex(\n (segment) => segment === lastTargetSegment\n )\n\n if (commonDirIndex === -1) {\n // Return just the filename if no common directory is found\n return fileSegments[fileSegments.length - 1]\n }\n\n // Return everything after the common directory\n return fileSegments.slice(commonDirIndex + 1).join(\"/\")\n}\n\nexport function resolveFilePath(\n file: z.infer<typeof registryItemFileSchema>,\n config: Config,\n options: {\n isSrcDir?: boolean\n commonRoot?: string\n framework?: ProjectInfo[\"framework\"][\"name\"]\n }\n) {\n // if (file.type === \"registry:asset\") {\n // if (file.target) {\n // // replace assets/ and public/ with the public directory\n // const targetDir = file.target.replace(/^assets\\//, \"\")\n // const targetDirPublic = targetDir.replace(/^public\\//, \"\")\n // const targetDirPublicPath = path.join(\n // config.resolvedPaths.cwd,\n // \"public\",\n // targetDirPublic\n // )\n\n // return targetDirPublicPath\n // }\n // }\n\n // Special handling for template files without targets\n if (\n !file.target &&\n file.path.includes(\"tiptap-templates/\") &&\n file.type !== \"registry:page\"\n ) {\n const match = file.path.match(/tiptap-templates\\/([^/]+)\\/(.*)/)\n if (match) {\n const [, templateName, relativePath] = match\n\n // If it's a component file in the components directory, adjust the path\n if (relativePath.startsWith(\"components/\")) {\n const finalPath = relativePath.replace(\"components/\", \"\")\n return path.join(\n config.resolvedPaths.components,\n \"tiptap-templates\",\n templateName,\n finalPath\n )\n }\n\n // For data and other files\n return path.join(\n config.resolvedPaths.components,\n \"tiptap-templates\",\n templateName,\n relativePath\n )\n }\n }\n\n // Special handling for data files with targets in templates\n if (\n file.target &&\n file.path.includes(\"tiptap-templates/\") &&\n file.target.includes(\"/data/\")\n ) {\n const templateMatch = file.path.match(/tiptap-templates\\/([^/]+)\\//)\n if (templateMatch) {\n const templateName = templateMatch[1]\n const dataPath = file.target.split(\"/data/\")[1]\n return path.join(\n config.resolvedPaths.components,\n \"tiptap-templates\",\n templateName,\n \"data\",\n dataPath\n )\n }\n }\n\n // Original logic for files with explicit targets\n if (file.target) {\n if (file.target.startsWith(\"~/\")) {\n return path.join(config.resolvedPaths.cwd, file.target.replace(\"~/\", \"\"))\n }\n\n let target = file.target\n\n if (file.type === \"registry:page\") {\n target = resolvePageTarget(target, options.framework)\n if (!target) {\n return \"\"\n }\n }\n\n return options.isSrcDir\n ? path.join(config.resolvedPaths.cwd, \"src\", target.replace(\"src/\", \"\"))\n : path.join(config.resolvedPaths.cwd, target.replace(\"src/\", \"\"))\n }\n\n // Original logic for non-template files\n const targetDir = resolveFileTargetDirectory(file, config)\n const relativePath = resolveNestedFilePath(file.path, targetDir)\n return path.join(targetDir, relativePath)\n}\n","import { promises as fs } from \"fs\"\nimport { tmpdir } from \"os\"\nimport path from \"path\"\nimport { Config } from \"@/src/utils/get-config\"\nimport { transformImport } from \"@/src/utils/transformers/transform-import\"\nimport { transformJsx } from \"@/src/utils/transformers/transform-jsx\"\nimport { transformRsc } from \"@/src/utils/transformers/transform-rsc\"\nimport { transformRemoveComponents } from \"@/src/utils/transformers/transform-remove-components\"\nimport { transformScssToCSS } from \"@/src/utils/transformers/transform-scss-to-css\"\nimport { Project, ScriptKind, type SourceFile } from \"ts-morph\"\nimport { isBunProject } from \"../get-package-manager\"\n\nexport type TransformOpts = {\n filename: string\n raw: string\n config: Config\n transformJsx?: boolean\n packageManager?: \"yarn\" | \"pnpm\" | \"bun\" | \"npm\"\n}\n\nexport type Transformer<Output = SourceFile> = (\n opts: TransformOpts & {\n sourceFile: SourceFile\n }\n) => Promise<Output>\n\nconst project = new Project({\n compilerOptions: {},\n})\n\nasync function createTempSourceFile(filename: string) {\n const dir = await fs.mkdtemp(path.join(tmpdir(), \"tiptap-\"))\n return path.join(dir, filename)\n}\n\nexport async function transform(\n opts: TransformOpts,\n transformers: Transformer[] = [\n transformImport,\n transformRsc,\n transformRemoveComponents,\n ]\n) {\n const isBun = isBunProject(opts.config.resolvedPaths.cwd)\n // For Bun projects, convert SCSS to CSS\n if (opts.filename.endsWith(\".scss\") && isBun) {\n return await transformScssToCSS(opts.raw)\n }\n\n if (\n opts.filename.endsWith(\".scss\") ||\n opts.filename.endsWith(\".css\") ||\n opts.filename.endsWith(\".json\")\n ) {\n return opts.raw\n }\n\n const tempFile = await createTempSourceFile(opts.filename)\n const sourceFile = project.createSourceFile(tempFile, opts.raw, {\n scriptKind: ScriptKind.TSX,\n })\n\n for (const transformer of transformers) {\n await transformer({ sourceFile, ...opts })\n }\n\n if (opts.transformJsx) {\n return await transformJsx({\n sourceFile,\n ...opts,\n })\n }\n\n return sourceFile.getText()\n}\n","import { Config } from \"@/src/utils/get-config\"\nimport { Transformer } from \"@/src/utils/transformers\"\nimport { isBunProject } from \"../get-package-manager\"\n\nexport const transformImport: Transformer = async ({\n sourceFile,\n config,\n packageManager,\n}) => {\n const importDeclarations = sourceFile.getImportDeclarations()\n\n for (const importDeclaration of importDeclarations) {\n let moduleSpecifier = updateImportAliases(\n importDeclaration.getModuleSpecifierValue(),\n config\n )\n\n const isBun = isBunProject(config.resolvedPaths.cwd)\n\n // For Bun projects, convert .scss imports to .css\n if (isBun && moduleSpecifier.endsWith(\".scss\")) {\n moduleSpecifier = moduleSpecifier.replace(/\\.scss$/, \".css\")\n }\n\n if (moduleSpecifier) {\n importDeclaration.setModuleSpecifier(moduleSpecifier)\n }\n }\n\n return sourceFile\n}\n\nfunction updateImportAliases(moduleSpecifier: string, config: Config): string {\n // Remove \"/registry/\" from the module specifier\n if (!moduleSpecifier.startsWith(\"@/registry/\")) {\n // We fix the alias and return.\n const alias = config.aliases.components.split(\"/\")[0]\n return moduleSpecifier.replace(/^@\\//, `${alias}/`)\n }\n\n // Handle template imports specifically to preserve the template structure\n if (\n moduleSpecifier.match(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\/components\\//\n )\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\/components\\//,\n `${config.aliases.components}/tiptap-templates/$1/`\n )\n }\n\n // Handle template imports without the components part\n if (\n moduleSpecifier.match(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\/(?!components\\/)/\n )\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-templates\\/([^/]+)\\//,\n `${config.aliases.components}/tiptap-templates/$1/`\n )\n }\n\n if (\n config.aliases.components &&\n moduleSpecifier.match(/@\\/registry\\/components/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/components/,\n config.aliases.components\n )\n }\n\n if (\n config.aliases.contexts &&\n moduleSpecifier.match(/@\\/registry\\/contexts/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/contexts/,\n config.aliases.contexts\n )\n }\n\n if (\n config.aliases.tiptapExtensions &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-extension/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-extension/,\n config.aliases.tiptapExtensions\n )\n }\n\n if (config.aliases.hooks && moduleSpecifier.match(/@\\/registry\\/hooks/)) {\n return moduleSpecifier.replace(/@\\/registry\\/hooks/, config.aliases.hooks)\n }\n\n if (\n config.aliases.tiptapIcons &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-icons/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-icons/,\n config.aliases.tiptapIcons\n )\n }\n\n if (config.aliases.lib && moduleSpecifier.match(/@\\/registry\\/lib/)) {\n return moduleSpecifier.replace(/@\\/registry\\/lib/, config.aliases.lib)\n }\n\n if (\n config.aliases.tiptapNodes &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-node/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-node/,\n config.aliases.tiptapNodes\n )\n }\n\n if (\n config.aliases.tiptapUiPrimitives &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-ui-primitive/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-ui-primitive/,\n config.aliases.tiptapUiPrimitives\n )\n }\n\n if (\n config.aliases.tiptapUiUtils &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-ui-utils/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-ui-utils/,\n config.aliases.tiptapUiUtils\n )\n }\n\n if (\n config.aliases.tiptapUi &&\n moduleSpecifier.match(/@\\/registry\\/tiptap-ui/)\n ) {\n return moduleSpecifier.replace(\n /@\\/registry\\/tiptap-ui/,\n config.aliases.tiptapUi\n )\n }\n\n if (config.aliases.styles && moduleSpecifier.match(/@\\/registry\\/styles/)) {\n return moduleSpecifier.replace(/@\\/registry\\/styles/, config.aliases.styles)\n }\n\n // Default case - preserve all other imports\n return moduleSpecifier.replace(\n /^@\\/registry\\/[^/]+(?:\\/.*\\/)?/,\n config.aliases.components + \"/\"\n )\n}\n","import { type Transformer } from \"@/src/utils/transformers\"\nimport { transformFromAstSync } from \"@babel/core\"\nimport { ParserOptions, parse } from \"@babel/parser\"\n// eslint-disable-next-line @typescript-eslint/ban-ts-comment\n// @ts-expect-error\nimport transformTypescript from \"@babel/plugin-transform-typescript\"\nimport * as recast from \"recast\"\n\n// TODO.\n// I'm using recast for the AST here.\n// Figure out if ts-morph AST is compatible with Babel.\n\n// This is a copy of the babel options from recast/parser.\n// The goal here is to tolerate as much syntax as possible.\n// We want to be able to parse any valid tsx code.\n// See https://github.com/benjamn/recast/blob/master/parsers/_babel_options.ts.\nconst PARSE_OPTIONS: ParserOptions = {\n sourceType: \"module\",\n allowImportExportEverywhere: true,\n allowReturnOutsideFunction: true,\n startLine: 1,\n tokens: true,\n plugins: [\n \"asyncGenerators\",\n \"bigInt\",\n \"classPrivateMethods\",\n \"classPrivateProperties\",\n \"classProperties\",\n \"classStaticBlock\",\n \"decimal\",\n \"decorators-legacy\",\n \"doExpressions\",\n \"dynamicImport\",\n \"exportDefaultFrom\",\n \"exportNamespaceFrom\",\n \"functionBind\",\n \"functionSent\",\n \"importAssertions\",\n \"importMeta\",\n \"nullishCoalescingOperator\",\n \"numericSeparator\",\n \"objectRestSpread\",\n \"optionalCatchBinding\",\n \"optionalChaining\",\n [\n \"pipelineOperator\",\n {\n proposal: \"minimal\",\n },\n ],\n [\n \"recordAndTuple\",\n {\n syntaxType: \"hash\",\n },\n ],\n \"throwExpressions\",\n \"topLevelAwait\",\n \"v8intrinsic\",\n \"typescript\",\n \"jsx\",\n ],\n}\n\nexport const transformJsx: Transformer<string> = async ({\n sourceFile,\n config,\n}) => {\n const output = sourceFile.getFullText()\n\n if (config.tsx) {\n return output\n }\n\n const ast = recast.parse(output, {\n parser: {\n parse: (code: string) => {\n return parse(code, PARSE_OPTIONS)\n },\n },\n })\n\n const result = transformFromAstSync(ast, output, {\n cloneInputAst: false,\n code: false,\n ast: true,\n plugins: [transformTypescript],\n configFile: false,\n })\n\n if (!result || !result.ast) {\n throw new Error(\"Failed to transform JSX\")\n }\n\n return recast.print(result.ast).code\n}\n","import { Transformer } from \"@/src/utils/transformers\"\nimport { SyntaxKind } from \"ts-morph\"\n\nconst directiveRegex = /^[\"']use client[\"']$/g\n\nexport const transformRsc: Transformer = async ({ sourceFile, config }) => {\n if (config.rsc) {\n return sourceFile\n }\n\n // Remove \"use client\" from the top of the file.\n const first = sourceFile.getFirstChildByKind(SyntaxKind.ExpressionStatement)\n if (first && directiveRegex.test(first.getText())) {\n first.remove()\n }\n\n return sourceFile\n}\n","import { Transformer } from \"@/src/utils/transformers\"\nimport {\n BinaryExpression,\n CallExpression,\n Node,\n PropertyAccessExpression,\n PropertyAssignment,\n SourceFile,\n SyntaxKind,\n} from \"ts-morph\"\nimport { Framework, FRAMEWORKS } from \"@/src/utils/frameworks\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { Config } from \"@/src/utils/get-config\"\n\n/**\n * Defines a rule for excluding components based on name matching patterns\n */\nexport interface ComponentExclusionRule {\n name: string // The name or pattern to match against\n matchType: \"exact\" | \"contains\" | \"startsWith\" | \"endsWith\" | \"regex\" // How to match the name\n caseSensitive?: boolean // Whether matching should be case sensitive\n pattern?: string // Regex pattern (used when matchType is \"regex\")\n onlyInFiles?: string[]\n}\n\ninterface NodeToRemove {\n node: any\n newText?: string\n action: \"remove\" | \"replace\"\n}\n\n/**\n * Default set of exclusion rules for common unwanted component patterns\n * These target development, testing, and internal components that shouldn't\n * be included in production builds or public APIs\n */\n/**\n * Default set of exclusion rules for common unwanted component patterns\n * These target development, testing, and internal components that shouldn't\n * be included in production builds or public APIs\n */\nconst DEFAULT_EXCLUSIONS: ComponentExclusionRule[] = [\n {\n name: \"cta\",\n matchType: \"contains\",\n caseSensitive: false,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"initialContent\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"JSONContent\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"onCreate\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n {\n name: \"getDocumentId\",\n matchType: \"exact\",\n caseSensitive: true,\n onlyInFiles: [\"notion-like-editor.tsx\"],\n },\n]\n\n/**\n * Determines whether a component should be excluded based on the provided rules\n * @param componentName - The name of the component to check\n * @param rules - Array of exclusion rules to apply\n * @returns true if the component should be excluded, false otherwise\n */\nfunction shouldExcludeComponent(\n componentName: string,\n rules: ComponentExclusionRule[],\n filePath: string\n): boolean {\n return rules.some((rule) => {\n // Check file path restriction\n if (\n rule.onlyInFiles &&\n !rule.onlyInFiles.some((f) => filePath.endsWith(f))\n ) {\n return false\n }\n\n const name = rule.caseSensitive\n ? componentName\n : componentName.toLowerCase()\n const ruleName = rule.caseSensitive ? rule.name : rule.name.toLowerCase()\n\n switch (rule.matchType) {\n case \"exact\":\n return name === ruleName\n case \"contains\":\n return name.includes(ruleName)\n case \"startsWith\":\n return name.startsWith(ruleName)\n case \"endsWith\":\n return name.endsWith(ruleName)\n case \"regex\":\n if (!rule.pattern) return false\n const regex = new RegExp(rule.pattern, rule.caseSensitive ? \"\" : \"i\")\n return regex.test(name)\n default:\n return false\n }\n })\n}\n\nfunction getFrameworkEnvVarName(\n constantName: string,\n framework: Framework\n): string {\n const frameworkName = framework.name\n\n if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n return `NEXT_PUBLIC_${constantName}`\n } else if (frameworkName === FRAMEWORKS.astro.name) {\n return `PUBLIC_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n return `VITE_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.laravel.name ||\n frameworkName === FRAMEWORKS.manual.name\n ) {\n return constantName\n } else {\n return constantName\n }\n}\n\nfunction stripFrameworkPrefix(varName: string): string {\n return varName.replace(/^(NEXT_PUBLIC_|VITE_|PUBLIC_)/, \"\")\n}\n\nasync function transformEnvironmentVariables(\n sourceFile: SourceFile,\n config: Config\n): Promise<void> {\n const projectInfo = await getProjectInfo(config.resolvedPaths.cwd)\n\n if (!projectInfo) {\n return\n }\n\n const nodesToTransform: Array<{\n node: BinaryExpression | PropertyAccessExpression | CallExpression\n newText: string\n }> = []\n\n // 1. Transform environment variable access\n const binaryExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.BinaryExpression\n )\n\n for (const binaryExpr of binaryExpressions) {\n if (binaryExpr.getOperatorToken().getKind() === SyntaxKind.BarBarToken) {\n const left = binaryExpr.getLeft()\n const leftText = left.getText()\n\n if (leftText.match(/^process\\.env\\.[A-Z_]+$/)) {\n const match = leftText.match(/process\\.env\\.([A-Z_]+)/)\n if (match && match[1]) {\n const constantName = stripFrameworkPrefix(match[1])\n const frameworkName = projectInfo.framework.name\n\n let transformedEnvVar: string\n if (frameworkName === FRAMEWORKS.astro.name) {\n transformedEnvVar = `import.meta.env.PUBLIC_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n transformedEnvVar = `import.meta.env.VITE_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n transformedEnvVar = `process.env.NEXT_PUBLIC_${constantName}`\n } else {\n transformedEnvVar = `process.env.${constantName}`\n }\n\n const rightSide = binaryExpr.getRight().getText()\n const newExpression = `${transformedEnvVar} || ${rightSide}`\n\n nodesToTransform.push({\n node: binaryExpr,\n newText: newExpression,\n })\n }\n }\n }\n }\n\n // 2. Transform alert calls that contain environment variable lists\n const callExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.CallExpression\n )\n\n for (const callExpr of callExpressions) {\n const expression = callExpr.getExpression()\n const expressionText = expression.getText()\n\n // Check for alert calls\n if (expressionText.match(/^alert$/)) {\n const args = callExpr.getArguments()\n if (args.length > 0) {\n const firstArg = args[0]\n const argText = firstArg.getText()\n\n // Look for template literals or strings that contain environment variable lists\n if (\n argText.includes(\"TIPTAP_COLLAB_TOKEN\") ||\n argText.includes(\"TIPTAP_COLLAB_DOC_PREFIX\") ||\n argText.includes(\"TIPTAP_AI_TOKEN\")\n ) {\n let newArgText = argText\n\n const envVarsToTransform = [\n \"TIPTAP_COLLAB_DOC_PREFIX\",\n \"TIPTAP_COLLAB_APP_ID\",\n \"TIPTAP_COLLAB_TOKEN\",\n \"TIPTAP_AI_APP_ID\",\n \"TIPTAP_AI_TOKEN\",\n \"USE_JWT_TOKEN_API_ENDPOINT\",\n ]\n\n for (let constantName of envVarsToTransform) {\n const frameworkEnvVarName = getFrameworkEnvVarName(\n constantName,\n projectInfo.framework\n )\n newArgText = newArgText.replace(\n new RegExp(constantName, \"g\"),\n frameworkEnvVarName\n )\n }\n\n if (newArgText !== argText) {\n const newCallExpr = `${expressionText}(${newArgText})`\n nodesToTransform.push({\n node: callExpr,\n newText: newCallExpr,\n })\n }\n }\n }\n }\n }\n\n // 3. Transform standalone process.env\n const propertyAccessExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.PropertyAccessExpression\n )\n\n for (const propAccess of propertyAccessExpressions) {\n const propAccessText = propAccess.getText()\n\n if (propAccessText.match(/^process\\.env\\.[A-Z_]+$/)) {\n const parent = propAccess.getParent()\n if (parent?.getKind() === SyntaxKind.BinaryExpression) {\n continue\n }\n\n const match = propAccessText.match(/process\\.env\\.([A-Z_]+)/)\n if (match && match[1]) {\n const constantName = stripFrameworkPrefix(match[1])\n const frameworkName = projectInfo.framework.name\n\n let transformedEnvVar: string\n if (frameworkName === FRAMEWORKS.astro.name) {\n transformedEnvVar = `import.meta.env.PUBLIC_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n transformedEnvVar = `import.meta.env.VITE_${constantName}`\n } else if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n transformedEnvVar = `process.env.NEXT_PUBLIC_${constantName}`\n } else {\n transformedEnvVar = `process.env.${constantName}`\n }\n\n nodesToTransform.push({\n node: propAccess,\n newText: transformedEnvVar,\n })\n }\n }\n }\n\n // Apply all transformations\n for (const { node, newText } of nodesToTransform) {\n try {\n node.replaceWithText(newText)\n } catch (error) {\n console.warn(`Skipping transformation of node: ${error}`)\n }\n }\n}\n\n/**\n * Main transformer function that removes excluded components from TypeScript/React source files\n * This transformer processes various AST nodes to remove unwanted components based on exclusion rules\n */\nexport const transformRemoveComponents: Transformer = async ({\n sourceFile,\n config,\n}) => {\n // Use default exclusion rules (could be made configurable in the future)\n const exclusionRules: ComponentExclusionRule[] = DEFAULT_EXCLUSIONS\n const filePath = sourceFile.getFilePath()\n // Collect all nodes to be modified instead of modifying immediately\n const nodesToModify: NodeToRemove[] = []\n\n // STEP 1: Collect excluded component imports\n const importDeclarations = sourceFile.getImportDeclarations()\n\n for (const importDeclaration of importDeclarations) {\n const moduleSpecifier = importDeclaration.getModuleSpecifierValue()\n\n // Check if the entire import module should be removed\n if (\n exclusionRules.some((rule) =>\n shouldExcludeComponent(moduleSpecifier, [rule], filePath)\n )\n ) {\n nodesToModify.push({ node: importDeclaration, action: \"remove\" })\n continue\n }\n\n // Handle default imports (import defaultName from \"...\")\n const defaultImport = importDeclaration.getDefaultImport()\n if (\n defaultImport &&\n shouldExcludeComponent(defaultImport.getText(), exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: importDeclaration, action: \"remove\" })\n continue\n }\n\n // Remove specific named imports that match exclusion rules\n const namedImports = importDeclaration.getNamedImports()\n const excludedImports = namedImports.filter((namedImport) =>\n shouldExcludeComponent(namedImport.getName(), exclusionRules, filePath)\n )\n\n if (excludedImports.length > 0) {\n excludedImports.forEach((excludedImport) =>\n nodesToModify.push({ node: excludedImport, action: \"remove\" })\n )\n\n // Check if this would remove all named imports\n const remainingImports = namedImports.filter(\n (namedImport) => !excludedImports.includes(namedImport)\n )\n\n if (remainingImports.length === 0 && !defaultImport) {\n nodesToModify.push({ node: importDeclaration, action: \"remove\" })\n }\n }\n }\n\n // STEP 2: Collect excluded component exports\n const exportDeclarations = sourceFile.getExportDeclarations()\n\n for (const exportDeclaration of exportDeclarations) {\n const namedExports = exportDeclaration.getNamedExports()\n const excludedExports = namedExports.filter((namedExport) =>\n shouldExcludeComponent(namedExport.getName(), exclusionRules, filePath)\n )\n\n if (excludedExports.length > 0) {\n excludedExports.forEach((excludedExport) =>\n nodesToModify.push({ node: excludedExport, action: \"remove\" })\n )\n\n // Check if this would remove all named exports\n const remainingExports = namedExports.filter(\n (namedExport) => !excludedExports.includes(namedExport)\n )\n\n if (remainingExports.length === 0) {\n nodesToModify.push({ node: exportDeclaration, action: \"remove\" })\n }\n }\n }\n\n // STEP 3: Collect excluded component variable declarations\n const variableStatements = sourceFile.getVariableStatements()\n\n for (const variableStatement of variableStatements) {\n const declarations = variableStatement.getDeclarations()\n const excludedDeclarations = declarations.filter((declaration) =>\n shouldExcludeComponent(declaration.getName(), exclusionRules, filePath)\n )\n\n if (excludedDeclarations.length > 0) {\n if (declarations.length === excludedDeclarations.length) {\n // Remove entire variable statement if all declarations are excluded\n nodesToModify.push({ node: variableStatement, action: \"remove\" })\n } else {\n // Remove only excluded declarations, keep others\n excludedDeclarations.forEach((declaration) =>\n nodesToModify.push({ node: declaration, action: \"remove\" })\n )\n }\n }\n }\n\n // STEP 4: Collect excluded component function declarations\n const functionDeclarations = sourceFile.getFunctions()\n\n for (const functionDeclaration of functionDeclarations) {\n const functionName = functionDeclaration.getName()\n if (\n functionName &&\n shouldExcludeComponent(functionName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: functionDeclaration, action: \"remove\" })\n }\n }\n\n // STEP 5: Collect excluded component interface declarations\n const interfaceDeclarations = sourceFile.getInterfaces()\n\n for (const interfaceDeclaration of interfaceDeclarations) {\n const interfaceName = interfaceDeclaration.getName()\n if (shouldExcludeComponent(interfaceName, exclusionRules, filePath)) {\n nodesToModify.push({ node: interfaceDeclaration, action: \"remove\" })\n }\n }\n\n // STEP 6: Collect excluded component type aliases\n const typeAliases = sourceFile.getTypeAliases()\n\n for (const typeAlias of typeAliases) {\n const typeName = typeAlias.getName()\n if (shouldExcludeComponent(typeName, exclusionRules, filePath)) {\n nodesToModify.push({ node: typeAlias, action: \"remove\" })\n }\n }\n\n // STEP 6.5: Collect excluded interface property signatures\n const propertySignatures = sourceFile.getDescendantsOfKind(\n SyntaxKind.PropertySignature\n )\n\n for (const propertySignature of propertySignatures) {\n const propName = propertySignature.getName()\n if (\n propName &&\n shouldExcludeComponent(propName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: propertySignature, action: \"remove\" })\n }\n }\n\n // STEP 7: Collect excluded JSX elements from React components\n const jsxElements = sourceFile.getDescendantsOfKind(SyntaxKind.JsxElement)\n\n for (const jsxElement of jsxElements) {\n const tagName = jsxElement.getOpeningElement().getTagNameNode().getText()\n if (shouldExcludeComponent(tagName, exclusionRules, filePath)) {\n nodesToModify.push({\n node: jsxElement,\n action: \"replace\",\n newText: \"\",\n })\n }\n }\n\n // STEP 8: Collect excluded self-closing JSX elements\n const jsxSelfClosingElements = sourceFile.getDescendantsOfKind(\n SyntaxKind.JsxSelfClosingElement\n )\n\n for (const jsxSelfClosingElement of jsxSelfClosingElements) {\n const tagName = jsxSelfClosingElement.getTagNameNode().getText()\n if (shouldExcludeComponent(tagName, exclusionRules, filePath)) {\n nodesToModify.push({\n node: jsxSelfClosingElement,\n action: \"replace\",\n newText: \"\",\n })\n }\n }\n\n // STEP 9: Collect excluded component properties from objects\n const propertyAssignments = sourceFile.getDescendantsOfKind(\n SyntaxKind.PropertyAssignment\n )\n\n for (const propertyAssignment of propertyAssignments) {\n const propertyName = propertyAssignment.getName()\n if (\n propertyName &&\n shouldExcludeComponent(propertyName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: propertyAssignment, action: \"remove\" })\n }\n }\n\n // STEP 10: Collect excluded JSX attributes\n const jsxAttributes = sourceFile.getDescendantsOfKind(SyntaxKind.JsxAttribute)\n\n for (const jsxAttribute of jsxAttributes) {\n const attributeName = jsxAttribute.getNameNode().getText()\n if (\n attributeName &&\n shouldExcludeComponent(attributeName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: jsxAttribute, action: \"remove\" })\n }\n }\n\n // STEP 11: Collect excluded parameters from function/method signatures\n const parameters = sourceFile.getDescendantsOfKind(SyntaxKind.Parameter)\n\n for (const parameter of parameters) {\n const parameterName = parameter.getName()\n if (\n parameterName &&\n shouldExcludeComponent(parameterName, exclusionRules, filePath)\n ) {\n const paramList = parameter.getParent()\n\n // Only proceed if the parent is a function-like structure\n if (\n paramList &&\n (Node.isFunctionDeclaration(paramList) ||\n Node.isArrowFunction(paramList) ||\n Node.isFunctionExpression(paramList) ||\n Node.isMethodDeclaration(paramList))\n ) {\n const allParams = paramList.getParameters()\n const index = allParams.indexOf(parameter)\n\n // Handle comma removal for cleaner output\n if (index !== -1) {\n if (index === allParams.length - 1 && index > 0) {\n const prev = parameter.getPreviousSibling()\n if (prev?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: prev, action: \"remove\" })\n }\n } else {\n const next = parameter.getNextSibling()\n if (next?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: next, action: \"remove\" })\n }\n }\n\n nodesToModify.push({ node: parameter, action: \"remove\" })\n }\n }\n }\n }\n\n // STEP 11.1: Handle function arguments in call expressions\n const callExpressions = sourceFile.getDescendantsOfKind(\n SyntaxKind.CallExpression\n )\n\n for (const callExpr of callExpressions) {\n const args = callExpr.getArguments()\n for (let i = 0; i < args.length; i++) {\n const arg = args[i]\n const argText = arg.getText()\n\n if (shouldExcludeComponent(argText, exclusionRules, filePath)) {\n // Handle comma removal for cleaner output\n if (i === args.length - 1) {\n // Last argument - remove preceding comma if exists\n const prevSibling = arg.getPreviousSibling()\n if (prevSibling && prevSibling.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: prevSibling, action: \"remove\" })\n }\n } else {\n // Not last argument - remove following comma if exists\n const nextSibling = arg.getNextSibling()\n if (nextSibling && nextSibling.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: nextSibling, action: \"remove\" })\n }\n }\n\n nodesToModify.push({ node: arg, action: \"remove\" })\n }\n }\n }\n\n // STEP 11.5: Collect excluded binding elements (destructured parameters)\n const bindingElements = sourceFile.getDescendantsOfKind(\n SyntaxKind.BindingElement\n )\n\n for (const bindingElement of bindingElements) {\n const bindingName = bindingElement.getName()\n if (\n bindingName &&\n shouldExcludeComponent(bindingName, exclusionRules, filePath)\n ) {\n // Handle comma cleanup (already correct in your code)\n const bindingPattern = bindingElement.getParent()\n if (bindingPattern) {\n const allBindings = bindingPattern.getDescendantsOfKind(\n SyntaxKind.BindingElement\n )\n const bindingIndex = allBindings.indexOf(bindingElement)\n\n if (bindingIndex === allBindings.length - 1) {\n const prevSibling = bindingElement.getPreviousSibling()\n if (prevSibling?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: prevSibling, action: \"remove\" })\n }\n } else {\n const nextSibling = bindingElement.getNextSibling()\n if (nextSibling?.getKind() === SyntaxKind.CommaToken) {\n nodesToModify.push({ node: nextSibling, action: \"remove\" })\n }\n }\n }\n\n nodesToModify.push({ node: bindingElement, action: \"remove\" })\n }\n }\n\n // STEP 12: Collect excluded identifiers in function calls and expressions\n const identifiers = sourceFile.getDescendantsOfKind(SyntaxKind.Identifier)\n\n for (const identifier of identifiers) {\n const identifierName = identifier.getText()\n if (shouldExcludeComponent(identifierName, exclusionRules, filePath)) {\n const parent = identifier.getParent()\n\n // Handle different contexts where the identifier appears\n if (parent) {\n const parentKind = parent.getKind()\n\n // Remove entire call expression if it's calling an excluded function\n if (parentKind === SyntaxKind.CallExpression) {\n const callExpr = parent as CallExpression\n if (callExpr.getExpression() === identifier) {\n // This is a function call like getDocumentId()\n nodesToModify.push({ node: callExpr, action: \"remove\" })\n } else {\n // This is an argument in a function call\n const args = callExpr.getArguments()\n const argIndex = args.findIndex((arg) => arg === identifier)\n if (argIndex !== -1) {\n nodesToModify.push({ node: identifier, action: \"remove\" })\n }\n }\n }\n\n // Remove property access expressions with excluded identifiers\n if (parentKind === SyntaxKind.PropertyAccessExpression) {\n const propAccess = parent as PropertyAccessExpression\n if (propAccess.getName() === identifierName) {\n nodesToModify.push({ node: propAccess, action: \"remove\" })\n }\n }\n\n // Remove variable references and expressions\n if (\n parentKind === SyntaxKind.VariableDeclaration ||\n parentKind === SyntaxKind.BinaryExpression ||\n parentKind === SyntaxKind.IfStatement ||\n parentKind === SyntaxKind.ConditionalExpression\n ) {\n nodesToModify.push({ node: identifier, action: \"remove\" })\n }\n\n // Remove from object literal property values\n if (parentKind === SyntaxKind.PropertyAssignment) {\n const propAssignment = parent as PropertyAssignment\n if (propAssignment.getInitializer() === identifier) {\n nodesToModify.push({ node: propAssignment, action: \"remove\" })\n }\n }\n }\n }\n }\n\n // STEP 13: Collect excluded shorthand property assignments (e.g., { initialContent })\n const shorthandPropertyAssignments = sourceFile.getDescendantsOfKind(\n SyntaxKind.ShorthandPropertyAssignment\n )\n\n for (const shorthandProp of shorthandPropertyAssignments) {\n const propName = shorthandProp.getName()\n if (\n propName &&\n shouldExcludeComponent(propName, exclusionRules, filePath)\n ) {\n nodesToModify.push({ node: shorthandProp, action: \"remove\" })\n }\n }\n\n // Apply environment variable transformations first (before removing nodes)\n await transformEnvironmentVariables(sourceFile, config)\n\n // STEP 16: Apply all collected modifications\n // Sort by position (deepest nodes first) to avoid accessing removed parents\n nodesToModify.sort((a, b) => {\n const aStart = a.node.getStart?.() ?? 0\n const bStart = b.node.getStart?.() ?? 0\n return bStart - aStart // Reverse order - process deepest/rightmost first\n })\n\n // Apply transformations safely\n for (const { node, action, newText } of nodesToModify) {\n try {\n // Check if node still exists and hasn't been removed\n if (node.wasForgotten?.() === true) {\n continue // Skip nodes that were already removed\n }\n\n if (action === \"remove\") {\n if (typeof node.remove === \"function\") {\n node.remove()\n }\n } else if (action === \"replace\" && newText !== undefined) {\n node.replaceWithText(newText)\n }\n } catch (error) {\n // console.warn(`Skipping transformation of node: ${error}`)\n // Continue with other transformations even if one fails\n }\n }\n\n // Return the modified source file with excluded components removed\n return sourceFile\n}\n","import * as sass from \"sass\"\n\n/**\n * Converts SCSS content to CSS\n * @param scssContent The SCSS content to convert\n * @returns The compiled CSS content\n */\nexport async function transformScssToCSS(scssContent: string): Promise<string> {\n try {\n const result = sass.compileString(scssContent, {\n style: \"expanded\",\n })\n return result.css\n } catch (error) {\n throw new Error(\n `Failed to compile SCSS to CSS: ${error instanceof Error ? error.message : String(error)}`\n )\n }\n}\n","import { Config } from \"@/src/utils/get-config\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { RegistryItem } from \"@/src/utils/registry/schema\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { execa } from \"execa\"\nimport { colors } from \"@/src/utils/colors\"\n\n/**\n * Installs development dependencies for a component\n *\n * @param devDependencies List of development dependencies to install\n * @param config Configuration object with project paths\n * @param options Additional options\n */\nexport async function updateDevDependencies(\n devDependencies: RegistryItem[\"devDependencies\"],\n config: Config,\n options: {\n silent?: boolean\n }\n) {\n devDependencies = Array.from(new Set(devDependencies))\n if (!devDependencies?.length) {\n return\n }\n\n options = {\n silent: false,\n ...options,\n }\n\n const devDependenciesSpinner = spinner(\n `Installing development dependencies.`,\n {\n silent: options.silent,\n }\n )?.start()\n const packageManager = await getPackageManager(config.resolvedPaths.cwd)\n\n devDependenciesSpinner?.start()\n\n // Different package managers have different flags for dev dependencies\n const devFlag = packageManager === \"npm\" ? \"--save-dev\" : \"-D\"\n\n await execa(\n packageManager,\n [packageManager === \"npm\" ? \"install\" : \"add\", devFlag, ...devDependencies],\n {\n cwd: config.resolvedPaths.cwd,\n }\n )\n\n devDependenciesSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n}\n","/**\n * Converts kebab-case or snake_case to Title Case\n */\nexport function toReadableName(input: string): string {\n return input\n .split(/[-_]/)\n .map((word) => word.charAt(0).toUpperCase() + word.slice(1))\n .join(\" \")\n}\n","import fetch from \"node-fetch\"\nimport { HttpsProxyAgent } from \"https-proxy-agent\"\nimport { logger } from \"@/src/utils/logger\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { colors } from \"@/src/utils/colors\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\nimport { saveAuthToken, type PackageManager } from \"./package-manager-config\"\nimport { REGISTRY_URL } from \"./registry\"\n\nconst AUTH_API_URL = `${REGISTRY_URL}/api/cli/v1`\n\ntype LoginResponse = {\n token: string\n authToken: string\n}\n\ntype PlanResponse = Array<{\n name: string\n}>\n\ntype AuthTokens = {\n bearerToken: string\n authToken: string\n}\n\nexport type AuthResult = {\n success: boolean\n tokens?: AuthTokens\n error?: string\n}\n\nexport type AuthStatus = {\n authenticated: boolean\n user?: string\n plans?: string[]\n expires?: string | null\n token?: string\n}\n\nconst httpAgent = process.env.https_proxy\n ? new HttpsProxyAgent(process.env.https_proxy)\n : undefined\n\n/**\n * Authenticate a user with the Tiptap registry\n */\nexport async function authenticateUser({\n email,\n password,\n packageManager,\n writeConfig = true,\n cwd,\n}: {\n email?: string\n password?: string\n packageManager: PackageManager\n writeConfig?: boolean\n cwd: string\n}): Promise<AuthResult> {\n const loginSpinner = spinner(\n \"Authenticating with Tiptap registry...\"\n )?.start()\n\n try {\n if (!email || !password) {\n loginSpinner?.fail(\"Authentication failed\")\n return { success: false, error: \"Invalid credentials\" }\n }\n\n const tokens = await requestAuthTokens(email, password)\n\n let userPlans: string[] = []\n const plansResponse = await fetch(`${AUTH_API_URL}/plans`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${tokens.bearerToken}`,\n },\n agent: httpAgent,\n })\n\n if (!plansResponse.ok) {\n loginSpinner?.fail(\"Authentication failed (could not load user plans)\")\n return {\n success: false,\n error: `Failed to fetch user plans: ${plansResponse.status}`,\n }\n }\n\n const plans = (await plansResponse.json()) as PlanResponse\n userPlans = plans.map((plan) => plan.name)\n\n if (!userPlans.length) {\n loginSpinner?.fail(\"Authentication failed (no active plans)\")\n return { success: false, error: \"No active plans found for user\" }\n }\n\n tokenStorage.setBearerToken(tokens.bearerToken, {\n email,\n plans: userPlans,\n })\n tokenStorage.setAuthToken(tokens.authToken)\n\n if (writeConfig) {\n const success = await saveAuthToken(tokens.authToken, packageManager, cwd)\n if (!success) {\n loginSpinner?.fail(\"Failed to save authentication token\")\n return { success: false, error: \"Could not save authentication token\" }\n }\n }\n\n loginSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: \"Authentication successful\",\n })\n return { success: true, tokens }\n } catch (error) {\n loginSpinner?.fail(\"Authentication failed\")\n return {\n success: false,\n error:\n error instanceof Error\n ? error.message\n : \"Unknown error during authentication\",\n }\n }\n}\n\n/**\n * Request an authentication token from the API\n */\nasync function requestAuthTokens(\n email: string,\n password: string\n): Promise<AuthTokens> {\n const response = await fetch(`${AUTH_API_URL}/login`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({ email, password }),\n agent: httpAgent,\n })\n\n if (!response.ok) {\n throw new Error(`Error ${response.status}: ${response.statusText}`)\n }\n\n const data = (await response.json()) as LoginResponse\n\n return {\n bearerToken: data.token,\n authToken: data.authToken,\n }\n}\n\n/**\n * Check if user is authenticated with Tiptap registry\n */\nexport async function checkAuthStatus(): Promise<AuthStatus> {\n try {\n const bearerToken = tokenStorage.getBearerToken()\n\n if (!bearerToken) {\n return { authenticated: false }\n }\n\n if (!tokenStorage.isValidToken()) {\n return { authenticated: false }\n }\n\n // Use plans API to verify token is still valid\n let userPlans: string[] = []\n try {\n const plansResponse = await fetch(`${AUTH_API_URL}/plans`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${bearerToken}`,\n },\n agent: httpAgent,\n })\n\n if (!plansResponse.ok) {\n tokenStorage.clear()\n return { authenticated: false }\n }\n\n const plans = (await plansResponse.json()) as PlanResponse\n userPlans = plans.map((plan) => plan.name)\n\n // Update stored plans\n const userInfo = tokenStorage.getUserInfo()\n tokenStorage.setBearerToken(bearerToken, {\n email: userInfo.email,\n plans: userPlans,\n })\n } catch (error) {\n tokenStorage.clear()\n return { authenticated: false }\n }\n\n const userInfo = tokenStorage.getUserInfo()\n const expiration = tokenStorage.getTokenExpiration()\n\n return {\n authenticated: true,\n user: userInfo.email || \"unknown user\",\n plans: userPlans,\n expires: expiration,\n token: bearerToken,\n }\n } catch (error) {\n logger.error(\n `Auth status check error: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n return { authenticated: false }\n }\n}\n\n/**\n * Logout user from Tiptap registry\n */\nexport async function logoutUser(): Promise<{\n success: boolean\n error?: string\n}> {\n try {\n const bearerToken = tokenStorage.getBearerToken()\n\n if (bearerToken) {\n const response = await fetch(`${AUTH_API_URL}/logout`, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${bearerToken}`,\n },\n agent: httpAgent,\n })\n\n if (!response.ok) {\n logger.warn(\"Logout API call failed, but clearing local tokens anyway\")\n }\n }\n\n tokenStorage.clear()\n return { success: true }\n } catch (error) {\n tokenStorage.clear()\n return {\n success: false,\n error:\n error instanceof Error ? error.message : \"Unknown error during logout\",\n }\n }\n}\n\n/**\n * Check if user has a specific plan\n */\nexport function userHasPlan(planName: string): boolean {\n return tokenStorage.hasPlan(planName)\n}\n\n/**\n * Check if user has any of the specified plans\n */\nexport function userHasAnyPlan(planNames: string[]): boolean {\n return planNames.some((plan) => tokenStorage.hasPlan(plan))\n}\n\n/**\n * Get user's plans\n */\nexport function getUserPlans(): string[] {\n return tokenStorage.getUserInfo().plans || []\n}\n","import fs from \"fs-extra\"\nimport path from \"path\"\nimport os from \"os\"\nimport { execa } from \"execa\"\nimport { logger } from \"@/src/utils/logger\"\nimport yaml from \"yaml\"\n\nconst TIPTAP_REGISTRY = \"https://registry.tiptap.dev/\"\nconst AUTH_TOKEN_KEY = \"//registry.tiptap.dev/:_authToken\"\nconst TIPTAP_PRO_REGISTRY_KEY = \"@tiptap-pro:registry\"\n\nexport type PackageManager = \"npm\" | \"yarn\" | \"pnpm\" | \"bun\"\n\n/**\n * Add .npmrc to .gitignore if it's not already there\n */\nasync function addNpmrcToGitignore(cwd: string): Promise<void> {\n try {\n const gitignorePath = path.join(cwd, \".gitignore\")\n const npmrcEntry = \".npmrc\"\n let gitignoreContent = \"\"\n\n if (await fs.pathExists(gitignorePath)) {\n gitignoreContent = await fs.readFile(gitignorePath, \"utf8\")\n }\n\n const lines = gitignoreContent.split(\"\\n\")\n const hasNpmrcEntry = lines.some(\n (line) =>\n line.trim() === npmrcEntry ||\n line.trim() === \"/.npmrc\" ||\n line.trim() === \"**/.npmrc\"\n )\n\n if (!hasNpmrcEntry) {\n const newContent = gitignoreContent.trim()\n ? `${gitignoreContent}\\n\\n# Authentication tokens\\n${npmrcEntry}\\n`\n : `# Authentication tokens\\n${npmrcEntry}\\n`\n\n await fs.writeFile(gitignorePath, newContent)\n }\n } catch (error) {\n logger.warn(\n `Could not update .gitignore: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n }\n}\n\n/**\n * Save authentication token to package manager config\n */\nexport async function saveAuthToken(\n token: string,\n packageManager: PackageManager,\n cwd: string\n): Promise<boolean> {\n try {\n let createdNpmrc = false\n\n switch (packageManager) {\n case \"npm\":\n await saveNpmToken(token, cwd)\n createdNpmrc = true\n break\n case \"yarn\":\n await saveYarnToken(token, cwd)\n createdNpmrc = await fs.pathExists(path.join(cwd, \".npmrc\"))\n break\n case \"pnpm\":\n case \"bun\":\n await saveToNpmrc(path.join(cwd, \".npmrc\"), token)\n createdNpmrc = true\n break\n }\n\n if (createdNpmrc) {\n await addNpmrcToGitignore(cwd)\n }\n\n return true\n } catch (error) {\n logger.error(\n `Error saving auth token: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n return false\n }\n}\n\n/**\n * Save token for npm\n */\nasync function saveNpmToken(token: string, cwd: string): Promise<void> {\n await execa(\n \"npm\",\n [\n \"config\",\n \"set\",\n TIPTAP_PRO_REGISTRY_KEY,\n TIPTAP_REGISTRY,\n \"--location=project\",\n ],\n { cwd }\n )\n\n await execa(\n \"npm\",\n [\"config\", \"set\", AUTH_TOKEN_KEY, token, \"--location=project\"],\n { cwd }\n )\n}\n\n/**\n * Save token for yarn (handles v1 and v2+)\n */\nasync function saveYarnToken(token: string, cwd: string): Promise<void> {\n try {\n const { stdout: yarnVersion } = await execa(\"yarn\", [\"--version\"], { cwd })\n const isYarnV1 = yarnVersion.startsWith(\"1.\")\n\n if (isYarnV1) {\n // For Yarn 1.x\n await execa(\n \"yarn\",\n [\n \"config\",\n \"set\",\n TIPTAP_PRO_REGISTRY_KEY,\n TIPTAP_REGISTRY,\n \"--location=project\",\n ],\n { cwd }\n )\n\n await execa(\n \"yarn\",\n [\"config\", \"set\", AUTH_TOKEN_KEY, token, \"--location=project\"],\n { cwd }\n )\n } else {\n // For Yarn 2+ (Berry)\n await saveYarnBerryToken(token, cwd)\n }\n } catch (error) {\n // Fallback to .npmrc for yarn\n await saveToNpmrc(path.join(cwd, \".npmrc\"), token)\n }\n}\n\n/**\n * Save token for Yarn Berry (v2+)\n */\nasync function saveYarnBerryToken(token: string, cwd: string): Promise<void> {\n const yarnrcPath = path.join(cwd, \".yarnrc.yml\")\n let yamlObj: Record<string, unknown> = {}\n\n // Read existing config if it exists\n if (fs.existsSync(yarnrcPath)) {\n const yarnrcContent = await fs.readFile(yarnrcPath, \"utf8\")\n try {\n yamlObj = yaml.parse(yarnrcContent) || {}\n } catch (e) {\n // If parsing fails, start with empty object\n }\n }\n\n // Ensure the structure exists\n if (!yamlObj.npmScopes) {\n yamlObj.npmScopes = {}\n }\n\n // Set or update the tiptap-pro scope\n ;(yamlObj.npmScopes as Record<string, unknown>)[\"tiptap-pro\"] = {\n npmRegistryServer: TIPTAP_REGISTRY,\n npmAuthToken: token,\n }\n\n // Write back to file\n await fs.writeFile(yarnrcPath, yaml.stringify(yamlObj))\n}\n\n/**\n * Update .npmrc file with token\n */\nasync function saveToNpmrc(npmrcPath: string, token: string): Promise<void> {\n let npmrcContent = \"\"\n\n // Read existing file if it exists\n if (fs.existsSync(npmrcPath)) {\n npmrcContent = await fs.readFile(npmrcPath, \"utf8\")\n }\n\n // Parse .npmrc content\n const { lines, processedKeys } = parseNpmrc(npmrcContent, token)\n\n // Add missing keys\n if (!processedKeys.has(TIPTAP_PRO_REGISTRY_KEY)) {\n lines.push(`${TIPTAP_PRO_REGISTRY_KEY}=${TIPTAP_REGISTRY}`)\n }\n\n if (!processedKeys.has(AUTH_TOKEN_KEY)) {\n lines.push(`${AUTH_TOKEN_KEY}=${token}`)\n }\n\n // Ensure file ends with a newline\n if (lines.length > 0 && lines[lines.length - 1] !== \"\") {\n lines.push(\"\")\n }\n\n // Write the updated content back to the file\n await fs.writeFile(npmrcPath, lines.join(\"\\n\"))\n}\n\n/**\n * Parse .npmrc content\n */\nfunction parseNpmrc(\n npmrcContent: string,\n token: string\n): {\n lines: string[]\n processedKeys: Set<string>\n} {\n const lines: string[] = []\n const processedKeys = new Set<string>()\n\n // Split content into lines\n const contentLines = npmrcContent.split(\"\\n\")\n\n // Process each line\n for (const line of contentLines) {\n const trimmedLine = line.trim()\n\n // Skip empty lines or add them as-is\n if (!trimmedLine) {\n lines.push(line)\n continue\n }\n\n // Preserve comments\n if (trimmedLine.startsWith(\"#\")) {\n lines.push(line)\n continue\n }\n\n // Process key-value pairs\n const index = line.indexOf(\"=\")\n if (index !== -1) {\n const key = line.substring(0, index).trim()\n\n // Update specific keys\n if (key === TIPTAP_PRO_REGISTRY_KEY) {\n lines.push(`${TIPTAP_PRO_REGISTRY_KEY}=${TIPTAP_REGISTRY}`)\n processedKeys.add(key)\n } else if (key === AUTH_TOKEN_KEY) {\n lines.push(`${AUTH_TOKEN_KEY}=${token}`)\n processedKeys.add(key)\n } else {\n // Keep other keys unchanged\n lines.push(line)\n }\n } else {\n // Keep lines that aren't key-value pairs\n lines.push(line)\n }\n }\n\n return { lines, processedKeys }\n}\n\n/**\n * Get auth token from package manager config\n */\nexport async function getAuthToken(\n packageManager: PackageManager,\n cwd: string\n): Promise<string | null> {\n try {\n const projectToken = await checkProjectNpmrc(cwd)\n if (projectToken) {\n return projectToken\n }\n\n if (packageManager === \"npm\") {\n const npmAuthToken = await getNpmAuthToken(cwd)\n return npmAuthToken\n }\n\n const globalAuthToken = await checkGlobalNpmrc()\n return globalAuthToken\n } catch (error) {\n return null\n }\n}\n\n/**\n * Check project .npmrc for auth token\n */\nasync function checkProjectNpmrc(cwd: string): Promise<string | null> {\n const projectNpmrcPath = path.join(cwd, \".npmrc\")\n if (fs.existsSync(projectNpmrcPath)) {\n const content = await fs.readFile(projectNpmrcPath, \"utf8\")\n return extractAuthToken(content)\n }\n return null\n}\n\n/**\n * Get npm auth token using npm config command\n */\nasync function getNpmAuthToken(cwd: string): Promise<string | null> {\n const { stdout } = await execa(\"npm\", [\"config\", \"get\", AUTH_TOKEN_KEY], {\n cwd,\n })\n\n return stdout && stdout !== \"undefined\" ? stdout.trim() : null\n}\n\n/**\n * Check global .npmrc file for auth token\n */\nasync function checkGlobalNpmrc(): Promise<string | null> {\n const globalNpmrcPath = path.join(os.homedir(), \".npmrc\")\n\n if (fs.existsSync(globalNpmrcPath)) {\n const content = await fs.readFile(globalNpmrcPath, \"utf8\")\n return extractAuthToken(content)\n }\n\n return null\n}\n\n/**\n * Extract auth token from config string\n */\nexport function extractAuthToken(configString: string): string | null {\n // Split into lines and filter for registry.tiptap.dev\n const lines = configString\n .split(\"\\n\")\n .filter((line) => line.startsWith(\"//registry.tiptap.dev/:_authToken=\"))\n\n if (lines.length === 0) {\n return null\n }\n\n // Extract the token after the \"=\" sign\n const token = lines[0].split(\"=\")[1]?.trim()\n return token || null\n}\n","import { Command } from \"commander\"\nimport { execa } from \"execa\"\nimport { z } from \"zod\"\nimport { confirm, input, password as passwordPrompt } from \"@inquirer/prompts\"\nimport { authenticateUser, checkAuthStatus } from \"@/src/utils/auth\"\nimport { colors } from \"@/src/utils/colors\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { logoutUser } from \"@/src/utils/auth\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { getAuthToken } from \"@/src/utils/package-manager-config\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\n\nexport const authOptionsSchema = z.object({\n cwd: z.string(),\n email: z.string().optional(),\n password: z.string().optional(),\n writeConfig: z.boolean().optional(),\n showMessage: z.boolean().default(true),\n})\n\ntype AuthOptions = z.infer<typeof authOptionsSchema>\ntype PackageManager = \"npm\" | \"yarn\" | \"pnpm\" | \"bun\"\n\n/**\n * Creates a themed input prompt with consistent styling\n */\nconst createThemedInput = (\n message: string,\n options: {\n required?: boolean\n validate?: (value: string) => boolean | string\n } = {}\n) => {\n return input({\n message: colors.reset(message),\n required: options.required ?? true,\n validate:\n options.validate ??\n ((value: string) => (value ? true : \"This field is required\")),\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Creates a themed password prompt with consistent styling\n */\nconst createThemedPassword = (\n message: string,\n options: {\n validate?: (value: string) => boolean | string\n } = {}\n) => {\n return passwordPrompt({\n message: colors.reset(message),\n validate:\n options.validate ??\n ((value: string) => (value ? true : \"This field is required\")),\n mask: \"*\",\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Creates a themed confirmation prompt with consistent styling\n */\nexport const createThemedConfirm = (\n message: string,\n defaultValue: boolean = true\n) => {\n return confirm({\n message: colors.reset(message),\n default: defaultValue,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Get the appropriate configuration file name based on package manager\n */\nfunction getConfigFileName(packageManager: PackageManager): string {\n switch (packageManager) {\n case \"npm\":\n return \".npmrc (via npm config)\"\n case \"yarn\":\n return \".yarnrc.yml or .npmrc (depending on Yarn version)\"\n case \"pnpm\":\n case \"bun\":\n return \".npmrc\"\n default:\n return \"configuration file\"\n }\n}\n\n/**\n * Display appropriate token configuration instructions for each package manager\n */\nasync function displayTokenInstructions(\n packageManager: PackageManager,\n token: string,\n cwd: string\n) {\n logger.log(\n `To use this token, add it to your project's package manager configuration in ${colors.cyan(cwd)}:`\n )\n\n if (packageManager === \"npm\") {\n logger.log(\"Run these commands in your project directory:\")\n logger.log(\n ` npm config set @tiptap-pro:registry https://registry.tiptap.dev/`\n )\n logger.log(` npm config set //registry.tiptap.dev/:_authToken ${token}`)\n logger.log(`\\nOr add to your project's .npmrc file:`)\n logger.log(` @tiptap-pro:registry=https://registry.tiptap.dev/`)\n logger.log(` //registry.tiptap.dev/:_authToken=${token}`)\n } else if (packageManager === \"yarn\") {\n const isYarnV1 = await checkYarnVersion(cwd)\n\n if (isYarnV1) {\n logger.log(\"Run these commands in your project directory:\")\n logger.log(\n ` yarn config set @tiptap-pro:registry https://registry.tiptap.dev/`\n )\n logger.log(` yarn config set //registry.tiptap.dev/:_authToken ${token}`)\n } else {\n logger.log(`Add to your project's .yarnrc.yml file:`)\n logger.log(\n `npmScopes:\\n tiptap-pro:\\n npmRegistryServer: \"https://registry.tiptap.dev/\"\\n npmAuthToken: \"${token}\"`\n )\n }\n } else if (packageManager === \"pnpm\" || packageManager === \"bun\") {\n logger.log(`Add to your project's .npmrc file:`)\n logger.log(\n colors.cyan(\n `@tiptap-pro:registry=https://registry.tiptap.dev/\\n//registry.tiptap.dev/:_authToken=${token}`\n )\n )\n }\n}\n\n/**\n * Check if the project is using Yarn v1\n */\nasync function checkYarnVersion(cwd: string): Promise<boolean> {\n try {\n const yarnVersionOutput = await execa(\"yarn\", [\"--version\"], { cwd })\n return yarnVersionOutput.stdout.startsWith(\"1.\")\n } catch (error) {\n // If yarn command fails, default to false\n return false\n }\n}\n\n/**\n * Handle the login process with interactive prompts if needed\n */\nexport async function handleLogin(options: AuthOptions) {\n let { email, password, writeConfig, showMessage } = options\n const { cwd } = options\n\n // Interactive prompts if necessary values aren't provided\n if (!email) {\n email = await createThemedInput(\"Email:\", {\n validate: (value: string) => (value ? true : \"Please enter your email\"),\n })\n }\n\n if (!password) {\n password = await createThemedPassword(\"Password:\", {\n validate: (value: string) =>\n value ? true : \"Please enter your password\",\n })\n }\n\n // User cancelled the prompt\n if (!email || !password) {\n logger.error(\"Authentication cancelled\")\n process.exit(0)\n }\n\n const packageManager = await getPackageManager(cwd)\n\n // Prompt for writeConfig if not explicitly set via command line\n if (writeConfig === undefined) {\n const configFileName = getConfigFileName(packageManager)\n\n writeConfig = await createThemedConfirm(\n `Would you like to save the auth token to your ${configFileName}?`\n )\n\n // User cancelled the prompt\n if (writeConfig === undefined) {\n logger.error(\"Authentication cancelled\")\n process.exit(0)\n }\n }\n\n const result = await authenticateUser({\n email,\n password,\n packageManager,\n writeConfig: writeConfig ?? false,\n cwd,\n })\n\n if (result.success && result.tokens) {\n if (writeConfig && showMessage) {\n logger.log(\n `\\nRegistry auth token saved to project directory for ${colors.cyan(packageManager)}`\n )\n logger.log(`.npmrc file saved at: ${colors.cyan(cwd)}`)\n logger.log(`Project path: ${colors.cyan(cwd)}`)\n } else if (result.tokens.authToken && showMessage) {\n logger.log(\n `\\nRegistry Auth Token: ${colors.cyan(result.tokens.authToken)}`\n )\n logger.log(\"This token should be added to your project's configuration:\")\n await displayTokenInstructions(\n packageManager,\n result.tokens.authToken,\n cwd\n )\n }\n\n if (showMessage) {\n logger.log(`Bearer token saved globally for CLI authentication`)\n }\n\n return true\n } else {\n logger.error(\"Authentication failed: \" + result.error)\n\n return false\n }\n}\n\n/**\n * Handle checking authentication status\n */\nasync function handleStatusCheck(cwd: string) {\n const packageManager = await getPackageManager(cwd)\n const status = await checkAuthStatus()\n\n if (status.authenticated) {\n logger.success(\n `Authenticated as ${colors.cyan(status.user ?? \"unknown user\")}`\n )\n\n // Display plans\n if (status.plans && status.plans.length > 0) {\n if (status.plans.length === 1) {\n logger.log(`Plan: ${colors.cyan(status.plans[0])}`)\n } else {\n logger.log(`Plans: ${colors.cyan(status.plans.join(\", \"))}`)\n }\n } else {\n logger.log(`Plans: ${colors.cyan(\"No active plans\")}`)\n }\n\n if (status.expires) {\n const expiryDate = new Date(status.expires)\n const now = new Date()\n const daysUntilExpiry = Math.ceil(\n (expiryDate.getTime() - now.getTime()) / (1000 * 60 * 60 * 24)\n )\n\n if (daysUntilExpiry > 30) {\n logger.log(\n `Token expires: ${colors.cyan(expiryDate.toDateString())} (${daysUntilExpiry} days)`\n )\n } else if (daysUntilExpiry > 0) {\n logger.log(\n `Token expires: ${colors.yellow(expiryDate.toDateString())} (${daysUntilExpiry} days)`\n )\n } else {\n logger.log(`Token expires: ${colors.red(\"Expired\")}`)\n }\n }\n\n if (status.token) {\n const tokenPreview = status.token.substring(0, 10) + \"...\"\n logger.log(`Bearer token: ${colors.cyan(tokenPreview)}`)\n }\n\n const registryToken = await getAuthToken(packageManager, cwd)\n if (registryToken) {\n const registryPreview = registryToken.substring(0, 10) + \"...\"\n logger.log(`Registry token: ${colors.cyan(registryPreview)}`)\n } else {\n logger.log(\n `Registry token: ${colors.yellow(\"Not configured for this project\")}`\n )\n logger.log(\n `Run ${colors.cyan(\"@tiptap/cli login --write-config\")} to configure for this project`\n )\n }\n } else {\n logger.log(\"Not authenticated with Tiptap registry\")\n logger.log(`Run ${colors.cyan(`@tiptap/cli login`)} to authenticate`)\n }\n}\n\nexport const login = new Command()\n .command(\"login\")\n .description(\"log in to your Tiptap Cloud account\")\n .option(\"-e, --email <email>\", \"your account email\")\n .option(\"-p, --password <password>\", \"your account password\")\n .option(\n \"--write-config\",\n \"write the auth token to your package manager config\",\n undefined\n )\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .action(async (options) => {\n try {\n const opts = authOptionsSchema.parse(options)\n await handleLogin(opts)\n } catch (error) {\n handleError(error)\n }\n })\n\nexport const status = new Command()\n .command(\"status\")\n .description(\"review your Tiptap Cloud authentication status\")\n .description(\"log out from your Tiptap registry account\")\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .action(async (options) => {\n const opts = authOptionsSchema.parse(options)\n const { cwd } = opts\n try {\n await handleStatusCheck(cwd)\n } catch (error) {\n handleError(error)\n }\n })\n\nexport const logout = new Command()\n .command(\"logout\")\n .description(\"log out from your Tiptap registry account\")\n\n .action(async () => {\n try {\n const logoutSpinner = spinner(\"Logging out...\")?.start()\n\n const result = await logoutUser()\n\n if (result.success) {\n logoutSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: \"Successfully logged out\",\n })\n } else {\n logoutSpinner?.fail(\"Logout failed\")\n logger.error(\"Logout failed: \" + result.error)\n }\n } catch (error) {\n handleError(error)\n }\n })\n\n/**\n * Handle displaying license information\n */\nasync function handleLicenseInfo() {\n logger.log(\"\")\n logger.log(colors.yellow(\"📋 Tiptap Pro License Information\"))\n logger.log(\"\")\n\n // Check license acceptance status\n const hasAccepted = tokenStorage.hasAcceptedLicense()\n const userInfo = tokenStorage.getUserInfo()\n\n if (hasAccepted) {\n logger.log(`${colors.cyan(\"✔\")} Pro License and Terms of Service accepted`)\n if (userInfo.email) {\n logger.log(` Accepted by: ${colors.cyan(userInfo.email)}`)\n }\n logger.log(\"\")\n } else {\n logger.log(\n colors.yellow(\"⚠ Pro License and Terms of Service not yet accepted\")\n )\n logger.log(\" License acceptance is required for using paid components\")\n logger.log(\"\")\n }\n\n logger.log(\"License Details:\")\n logger.log(\n ` • Pro License: ${colors.cyan(\"https://tiptap.dev/pro-license\")}`\n )\n logger.log(\n ` • Terms of Service: ${colors.cyan(\"https://tiptap.dev/terms-of-service\")}`\n )\n logger.log(\"\")\n\n logger.log(\"About Paid Components:\")\n logger.log(\n \" Some paid UI components or templates are limited to specific plans.\"\n )\n logger.log(\n \" The license is valid during your trial period and active subscription.\"\n )\n logger.log(\"\")\n\n // Show hidden command hint only when using license command\n if (hasAccepted) {\n logger.log(colors.gray(\"Available commands:\"))\n logger.log(\n colors.gray(\n ` • ${colors.cyan(\"tiptap license forget me\")} - Reset license acceptance`\n )\n )\n logger.log(\"\")\n }\n}\n\n/**\n * Handle license forget me command\n */\nasync function handleLicenseForgetMe() {\n const hasAccepted = tokenStorage.hasAcceptedLicense()\n\n if (!hasAccepted) {\n logger.log(colors.yellow(\"⚠ License has not been accepted yet\"))\n return\n }\n\n const confirmed = await createThemedConfirm(\n \"Are you sure you want to reset your license acceptance?\",\n false\n )\n\n if (confirmed) {\n tokenStorage.clearLicenseAcceptance()\n logger.log(`${colors.cyan(\"✔\")} License acceptance has been reset`)\n logger.log(\n \" You will need to accept the license again when installing paid components\"\n )\n } else {\n logger.log(\"License acceptance reset cancelled\")\n }\n}\n\nexport const license = new Command()\n .command(\"license\")\n .description(\"display Tiptap Pro license information and acceptance status\")\n .action(async () => {\n try {\n await handleLicenseInfo()\n } catch (error) {\n handleError(error)\n }\n })\n .addCommand(\n new Command()\n .command(\"forget me\")\n .description(\"reset license acceptance status\")\n .action(async () => {\n try {\n await handleLicenseForgetMe()\n } catch (error) {\n handleError(error)\n }\n })\n )\n","import { checkAuthStatus } from \"@/src/utils/auth\"\nimport {\n getAuthToken,\n saveAuthToken,\n type PackageManager,\n} from \"@/src/utils/package-manager-config\"\nimport { logger } from \"@/src/utils/logger\"\nimport { colors } from \"@/src/utils/colors\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport { getPackageManager } from \"./get-package-manager\"\nimport { PAID_PLANS, PaidPlan, Plan } from \"./registry/schema\"\nimport { createThemedConfirm, handleLogin } from \"../commands/auth\"\nimport { tokenStorage } from \"@/src/utils/bootstrap\"\n\n/**\n * Checks if the selected components contain any paid components\n */\nexport function hasPaidComponents(\n components: Array<{ name: string; plans: Plan[] }>\n): boolean {\n return components.some(\n (component) =>\n component.plans &&\n component.plans.some((plan) => PAID_PLANS.includes(plan as PaidPlan))\n )\n}\n\n/**\n * Prompts user to accept Pro license and Terms of Service for paid components\n */\nasync function promptLicenseAcceptance(\n selectedComponents: Array<{ name: string; plans: Plan[] }>\n): Promise<boolean> {\n const paidComponents = selectedComponents.filter(\n (component) =>\n component.plans &&\n component.plans.some((plan) => PAID_PLANS.includes(plan as PaidPlan))\n )\n\n if (paidComponents.length === 0) {\n return true\n }\n\n // Check if license was already accepted\n if (tokenStorage.hasAcceptedLicense()) {\n logger.log(`${colors.cyan(\"✔\")} Pro license accepted`)\n return true\n }\n\n logger.log(\"\")\n logger.log(colors.yellow(\"📋 License Agreement\"))\n logger.log(\"\")\n logger.log(\"Integrating paid components requires accepting:\")\n logger.log(\n ` • Pro License: ${colors.cyan(\"https://tiptap.dev/pro-license\")}`\n )\n logger.log(\n ` • Terms of Service: ${colors.cyan(\"https://tiptap.dev/terms-of-service\")}`\n )\n logger.log(\"\")\n logger.log(colors.gray(\" Valid during trial and active subscription\"))\n logger.log(\"\")\n\n try {\n const accepted = await createThemedConfirm(\n \"Do you accept the Pro license and terms of service?\",\n false\n )\n\n if (!accepted) {\n logger.log(colors.gray(\"License not accepted\"))\n logger.log(colors.gray(\"Tip: You can still install free components\"))\n return false\n }\n\n // Store license acceptance\n tokenStorage.setLicenseAccepted()\n logger.log(`${colors.cyan(\"✔\")} License accepted`)\n return true\n } catch (error) {\n logger.log(colors.gray(\"License acceptance cancelled\"))\n return false\n }\n}\n\n/**\n * Ensures user is authenticated for paid components and has proper .npmrc configuration\n */\nexport async function ensureAuthForPaidComponents(\n selectedComponents: Array<{ name: string; plans: Plan[] }>,\n cwd: string\n): Promise<boolean> {\n try {\n if (!hasPaidComponents(selectedComponents)) {\n return true\n }\n\n const authStatus = await checkAuthStatus()\n\n if (!authStatus.authenticated) {\n logger.log(\"\")\n logger.log(colors.yellow(\"🔐 Authentication Required\"))\n logger.log(\"\")\n logger.log(\"Pro components require authentication.\")\n logger.log(\n `Run ${colors.cyan(\"tiptap login\")} or create an account at ${colors.cyan(\"https://cloud.tiptap.dev\")}`\n )\n logger.log(\"\")\n\n const shouldLoginNow = await createThemedConfirm(\n \"Would you like to login now?\",\n true\n )\n\n if (!shouldLoginNow) {\n logger.log(\"\")\n logger.log(colors.gray(\"Authentication cancelled\"))\n logger.log(colors.gray(\"Tip: You can still install free components\"))\n return false\n }\n\n const loginSuccess = await handleLogin({\n cwd,\n writeConfig: true,\n showMessage: false,\n })\n if (!loginSuccess) {\n return false\n }\n } else {\n const packageManager = await getPackageManager(cwd)\n const hasNpmrcConfig = await checkNpmrcConfiguration(packageManager, cwd)\n\n if (!hasNpmrcConfig) {\n await createNpmrcConfiguration(packageManager, cwd)\n }\n }\n\n // After authentication is complete, prompt for license acceptance\n const licenseAccepted = await promptLicenseAcceptance(selectedComponents)\n if (!licenseAccepted) {\n return false\n }\n\n return true\n } catch (error) {\n logger.error(\n `Authentication check failed: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n return false\n }\n}\n\n/**\n * Checks if .npmrc configuration exists for the project\n */\nasync function checkNpmrcConfiguration(\n packageManager: PackageManager,\n cwd: string\n): Promise<boolean> {\n try {\n const authToken = await getAuthToken(packageManager, cwd)\n return !!authToken\n } catch (error) {\n return false\n }\n}\n\n/**\n * Creates .npmrc configuration for the project\n */\nasync function createNpmrcConfiguration(\n packageManager: PackageManager,\n cwd: string\n) {\n const configSpinner = spinner(\"Creating registry configuration...\")?.start()\n\n try {\n const authStatus = await checkAuthStatus()\n\n if (!authStatus.authenticated) {\n configSpinner?.fail(\n \"Cannot create configuration - user not authenticated\"\n )\n return false\n }\n\n const authToken = tokenStorage.getAuthToken()\n\n if (!authToken) {\n configSpinner?.fail(\"No authentication token found\")\n return false\n }\n\n const success = await saveAuthToken(authToken, packageManager, cwd)\n if (!success) {\n configSpinner?.fail(\"Failed to save authentication token\")\n return false\n }\n\n configSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: \".npmrc created successfully\",\n })\n } catch (error) {\n configSpinner?.fail(\"Failed to create registry configuration\")\n logger.error(\n `Configuration error: ${error instanceof Error ? error.message : \"Unknown error\"}`\n )\n }\n}\n","import { colors } from \"@/src/utils/colors\"\nimport { logger } from \"@/src/utils/logger\"\nimport process from \"process\"\n\n/**\n * CLI UI utilities for consistent visual styling\n */\n\n/**\n * Get the current terminal width with a fallback\n */\nexport function getTerminalWidth(): number {\n return process.stdout.columns || 80\n}\n\n/**\n * Creates a bordered box with content\n */\nexport function createBox(\n title: string,\n content: string[],\n options?: {\n borderColor?: \"cyan\" | \"yellow\" | \"red\" | \"green\" | \"gray\"\n padding?: boolean\n }\n) {\n const borderColor = options?.borderColor || \"gray\"\n const padding = options?.padding !== false\n\n // Box drawing characters\n const topLeft = \"\"\n const topRight = \"\"\n const bottomLeft = \"\"\n const bottomRight = \"\"\n const horizontal = \"-\"\n const vertical = \"\"\n\n // Use terminal width with max constraint for readability\n const terminalWidth = getTerminalWidth()\n const boxWidth = Math.min(terminalWidth - 4, 80) // Max 80 chars for readability\n\n const colorFn = colors[borderColor]\n const topBorder = colorFn(\n topLeft + horizontal.repeat(boxWidth - 2) + topRight\n )\n const bottomBorder = colorFn(\n bottomLeft + horizontal.repeat(boxWidth - 2) + bottomRight\n )\n const sideBorder = colorFn(vertical)\n\n // Create the box\n const lines = []\n\n if (padding) lines.push(\"\")\n\n lines.push(topBorder)\n\n // Empty line before title\n lines.push(`${sideBorder}${\" \".repeat(boxWidth - 2)}${sideBorder}`)\n\n // Title line\n const titlePadding = Math.floor((boxWidth - 4 - stripAnsi(title).length) / 2)\n const titleLine = title\n .padStart(titlePadding + stripAnsi(title).length)\n .padEnd(boxWidth - 4)\n lines.push(`${sideBorder} ${titleLine} ${sideBorder}`)\n\n // Empty line after title\n lines.push(`${sideBorder}${\" \".repeat(boxWidth - 2)}${sideBorder}`)\n\n // Content lines\n content.forEach((line) => {\n const strippedLength = stripAnsi(line).length\n const padding = boxWidth - 4 - strippedLength\n const paddedLine = line + \" \".repeat(Math.max(0, padding))\n lines.push(`${sideBorder} ${paddedLine} ${sideBorder}`)\n })\n\n // Empty line before bottom border\n if (content.length > 0) {\n lines.push(`${sideBorder}${\" \".repeat(boxWidth - 2)}${sideBorder}`)\n }\n\n lines.push(bottomBorder)\n\n if (padding) lines.push(\"\")\n\n return lines\n}\n\n/**\n * Creates a section with title and content\n */\nexport function createSection(\n title: string,\n content: string[],\n subtitle?: string\n) {\n const lines = []\n\n lines.push(\"\")\n lines.push(title)\n\n if (subtitle) {\n lines.push(colors.gray(subtitle))\n }\n\n lines.push(\"\")\n\n content.forEach((line) => {\n lines.push(line)\n })\n\n return lines\n}\n\n/**\n * Creates a welcome banner\n */\nexport function createWelcomeBanner(title: string, subtitle?: string) {\n const content = subtitle ? [subtitle] : []\n return createBox(`${title}`, content, { borderColor: \"gray\" })\n}\n\n/**\n * Creates an info box\n */\nexport function createInfoBox(title: string, content: string[]) {\n return createBox(`ℹ️ ${title}`, content, { borderColor: \"cyan\" })\n}\n\n/**\n * Creates a warning box\n */\nexport function createWarningBox(title: string, content: string[]) {\n return createBox(`⚠️ ${title}`, content, { borderColor: \"yellow\" })\n}\n\n/**\n * Creates a success box\n */\nexport function createSuccessBox(title: string, content: string[]) {\n return createBox(`✅ ${title}`, content, { borderColor: \"green\" })\n}\n\n/**\n * Logs multiple lines with proper spacing\n */\nexport function logLines(lines: string[]) {\n lines.forEach((line) => logger.log(line))\n}\n\n/**\n * Strips ANSI color codes from a string to get actual length\n */\nfunction stripAnsi(str: string): string {\n // eslint-disable-next-line no-control-regex\n return str.replace(/\\x1b\\[[0-9;]*m/g, \"\")\n}\n\n/**\n * Creates a numbered list with proper spacing\n */\nexport function createNumberedList(\n items: Array<{ label: string; description?: string }>\n) {\n const lines: string[] = []\n\n items.forEach((item, index) => {\n const number = colors.gray(`${index + 1}.`)\n lines.push(` ${number} ${item.label}`)\n\n if (item.description) {\n lines.push(` ${colors.gray(item.description)}`)\n }\n\n // Add spacing between items except the last one\n if (index < items.length - 1) {\n lines.push(\"\")\n }\n })\n\n return lines\n}\n\n/**\n * Creates a preview box with code content\n */\nexport function createPreviewBox(title: string, content: string[]) {\n const lines = []\n\n lines.push(\"\")\n lines.push(title)\n lines.push(\"\")\n\n // Create bordered preview area with terminal width constraint\n const terminalWidth = getTerminalWidth()\n const maxLength = Math.max(...content.map((line) => stripAnsi(line).length))\n const boxWidth = Math.min(Math.max(50, maxLength + 4), terminalWidth - 4)\n\n const topBorder = \"┌\" + \"─\".repeat(boxWidth - 2) + \"┐\"\n const bottomBorder = \"└\" + \"─\".repeat(boxWidth - 2) + \"┘\"\n\n lines.push(topBorder)\n\n content.forEach((line, index) => {\n const lineNumber = colors.gray(`${index + 1}`)\n const paddedLine = line.padEnd(boxWidth - 6)\n lines.push(`│ ${lineNumber} ${paddedLine} │`)\n })\n\n lines.push(bottomBorder)\n lines.push(\"\")\n\n return lines\n}\n\n/**\n * Creates an explanation section with bullet points\n */\nexport function createExplanationSection(title: string, points: string[]) {\n const lines = []\n\n lines.push(\"\")\n lines.push(colors.cyan(title))\n lines.push(\"\")\n\n points.forEach((point) => {\n lines.push(` • ${point}`)\n })\n\n lines.push(\"\")\n\n return lines\n}\n\n/**\n * Clears the terminal screen\n */\nexport function clearTerminal() {\n // Clear screen and move cursor to top-left\n process.stdout.write(\"\\x1B[2J\\x1B[0f\")\n\n // Alternative method that works better on some terminals\n // console.clear()\n\n // For Windows compatibility\n if (process.platform === \"win32\") {\n process.stdout.write(\"\\x1B[2J\\x1B[3J\\x1B[H\")\n }\n}\n\n/**\n * Creates a subtle divider line that spans the terminal width\n */\nexport function createDivider() {\n const width = Math.min(getTerminalWidth() - 4, 80)\n return colors.gray(\"─\".repeat(width))\n}\n\n/**\n * Creates a dash divider for prompts\n */\nexport function createSpacedDivider() {\n const width = Math.min(getTerminalWidth() - 4, 80)\n return colors.gray(\"-\".repeat(width))\n}\n","import { colors } from \"@/src/utils/colors\"\nimport { Framework, FRAMEWORKS } from \"@/src/utils/frameworks\"\nimport { createInfoBox, createWarningBox, logLines } from \"@/src/utils/cli-ui\"\nimport { logger } from \"@/src/utils/logger\"\nimport { existsSync } from \"fs\"\nimport path from \"path\"\nimport type { Config } from \"@/src/utils/get-config\"\n\n/**\n * Get the appropriate environment variable prefix for the framework\n */\nfunction getFrameworkEnvPrefix(framework: Framework): string {\n const frameworkName = framework.name\n\n if (\n frameworkName === FRAMEWORKS[\"next-app\"].name ||\n frameworkName === FRAMEWORKS[\"next-pages\"].name\n ) {\n return \"NEXT_PUBLIC_\"\n } else if (frameworkName === FRAMEWORKS.astro.name) {\n return \"PUBLIC_\"\n } else if (\n frameworkName === FRAMEWORKS.vite.name ||\n frameworkName === FRAMEWORKS[\"tanstack-start\"].name ||\n frameworkName === FRAMEWORKS[\"react-router\"].name\n ) {\n return \"VITE_\"\n } else if (\n frameworkName === FRAMEWORKS.laravel.name ||\n frameworkName === FRAMEWORKS.manual.name\n ) {\n return \"\"\n } else {\n return \"\"\n }\n}\n\n/**\n * Detect the actual file extension of style files in the project\n */\nfunction detectStyleFileExtension(config?: Config): string {\n if (!config?.resolvedPaths?.styles) {\n return \"scss\" // Default to scss if no config\n }\n\n const stylesDir = config.resolvedPaths.styles\n const variablesScss = path.join(stylesDir, \"_variables.scss\")\n const variablesCss = path.join(stylesDir, \"_variables.css\")\n\n // Check if CSS version exists (from Bun conversion)\n if (existsSync(variablesCss)) {\n return \"css\"\n }\n\n // Check if SCSS version exists\n if (existsSync(variablesScss)) {\n return \"scss\"\n }\n\n // Default to scss for new installations\n return \"scss\"\n}\n\n/**\n * Calculate the correct import path from main CSS file to styles directory\n */\nfunction calculateStylesImportPath(\n framework?: Framework,\n config?: Config\n): { cssFile: string; importPath: string } {\n const frameworkName = framework?.name || \"unknown\"\n\n // Check if styles are in src directory\n const stylesInSrc = config?.resolvedPaths?.styles?.includes(\"/src/\")\n const hasSrcDir = config?.resolvedPaths?.components?.includes(\"/src/\")\n\n // Determine the main CSS file location based on framework\n let cssFile = \"your main CSS file\"\n let importPath = \"./styles/\"\n\n switch (frameworkName) {\n case FRAMEWORKS[\"next-app\"].name:\n // Next.js App Router\n if (hasSrcDir) {\n // With srcDir: src/app/globals.css -> ../styles/\n cssFile = \"src/app/globals.css\"\n importPath = \"../styles/\"\n } else if (stylesInSrc) {\n // Without srcDir but styles in src: app/globals.css -> ../src/styles/\n cssFile = \"app/globals.css\"\n importPath = \"../src/styles/\"\n } else {\n // Without srcDir and styles at root: app/globals.css -> ../styles/\n cssFile = \"app/globals.css\"\n importPath = \"../styles/\"\n }\n break\n\n case FRAMEWORKS[\"next-pages\"].name:\n // Next.js Pages Router\n if (hasSrcDir) {\n // With srcDir: src/pages/_app.tsx imports from ../styles/globals.css\n cssFile = \"src/styles/globals.css\"\n importPath = \"./\"\n } else if (stylesInSrc) {\n // Without srcDir but styles in src: pages/_app.tsx imports from ../src/styles/\n cssFile = \"src/styles/globals.css\"\n importPath = \"./\"\n } else {\n // Without srcDir: styles/globals.css\n cssFile = \"styles/globals.css\"\n importPath = \"./\"\n }\n break\n\n case FRAMEWORKS.vite.name:\n // Vite - typically src/index.css or src/main.css\n cssFile = \"src/index.css\" // or src/main.css\n importPath = \"./styles/\"\n break\n\n case FRAMEWORKS[\"react-router\"].name:\n // React Router - similar to Vite, uses src structure\n cssFile = \"src/index.css\" // or src/main.css\n importPath = \"./styles/\"\n break\n\n case FRAMEWORKS[\"tanstack-start\"].name:\n // TanStack Start - Vite-based, uses src structure\n cssFile = \"src/index.css\" // or src/main.css\n importPath = \"./styles/\"\n break\n\n case FRAMEWORKS.astro.name:\n // Astro - typically has styles imported in layout files\n if (stylesInSrc) {\n cssFile = \"src/layouts/Layout.astro\" // or src/pages/index.astro\n importPath = \"../styles/\"\n } else {\n cssFile = \"src/layouts/Layout.astro\"\n importPath = \"../../styles/\" // If styles at root\n }\n break\n\n case FRAMEWORKS.laravel.name:\n // Laravel - uses resources/css/app.css\n cssFile = \"resources/css/app.css\"\n // Laravel styles would be in resources/styles/\n importPath = \"../styles/\"\n break\n\n case FRAMEWORKS.manual.name:\n default:\n // Manual/Unknown - make best guess based on config\n if (hasSrcDir || stylesInSrc) {\n cssFile = \"src/index.css\"\n importPath = \"./styles/\"\n } else {\n cssFile = \"your main CSS file\"\n importPath = \"./styles/\"\n }\n break\n }\n\n return { cssFile, importPath }\n}\n\n/**\n * Show styles setup message to remind users to configure styles\n */\nexport function showStylesConfigurationMessage(\n framework?: Framework,\n config?: Config\n) {\n const fileExtension = detectStyleFileExtension(config)\n const { cssFile, importPath } = calculateStylesImportPath(framework, config)\n\n const content = [\n \"The editor requires these style imports:\",\n \"\",\n `Add to ${colors.cyan(cssFile)}:`,\n \"\",\n colors.yellow(` @import '${importPath}_variables.${fileExtension}';`),\n colors.yellow(\n ` @import '${importPath}_keyframe-animations.${fileExtension}';`\n ),\n \"\",\n \"Without these imports, the editor will not display correctly.\",\n \"\",\n `Setup guide: ${colors.cyan(\"https://tiptap.dev/docs/ui-components/getting-started/style\")}`,\n ]\n\n const box = createWarningBox(\"Action Required: Import Styles\", content)\n logLines(box)\n}\n\n/**\n * Show package manager consistency warning\n */\nexport function showPackageManagerWarning(projectPackageManager: string) {\n const content = [\n `Your project uses ${colors.cyan(projectPackageManager)} as its package manager.`,\n \"\",\n \"For consistency, use the same package manager for all operations:\",\n `• Install dependencies: ${colors.yellow(`${projectPackageManager} install`)}`,\n `• Add packages: ${colors.yellow(`${projectPackageManager} add [package]`)}`,\n `• Run scripts: ${colors.yellow(`${projectPackageManager} run [script]`)}`,\n \"\",\n \"Mixing package managers (npm, pnpm, yarn) can cause conflicts.\",\n ]\n\n const box = createInfoBox(\"Package Manager Detected\", content)\n logLines(box)\n}\n\n/**\n * Show combined Notion setup message with environment variables\n */\nexport function showNotionSetupMessage(framework: Framework) {\n const prefix = getFrameworkEnvPrefix(framework)\n\n const content = [\n \"The Notion template requires these environment variables:\",\n \"\",\n colors.yellow(`${prefix}TIPTAP_COLLAB_DOC_PREFIX`) +\n \" - Document prefix (required)\",\n colors.yellow(`${prefix}TIPTAP_COLLAB_APP_ID`) +\n \" - Document Server App ID (required)\",\n colors.yellow(`${prefix}TIPTAP_COLLAB_TOKEN`) +\n \" - JWT token for collaboration (required)\",\n colors.yellow(`${prefix}TIPTAP_AI_APP_ID`) + \" - AI App ID (required)\",\n colors.yellow(`${prefix}TIPTAP_AI_TOKEN`) +\n \" - JWT token for AI (required)\",\n \"\",\n \"Get these credentials from your account at cloud.tiptap.dev\",\n \"\",\n `Setup guide: ${colors.cyan(\"https://tiptap.dev/docs/ui-components/templates/notion-like-editor\")}`,\n ]\n\n const box = createWarningBox(\"Action Required: Environment Setup\", content)\n logLines(box)\n}\n\n/**\n * Show combined Notion template setup message\n */\nexport function showNotionTemplateSetupMessage(\n framework: Framework,\n config?: Config\n) {\n const prefix = getFrameworkEnvPrefix(framework)\n const fileExtension = detectStyleFileExtension(config)\n const { cssFile, importPath } = calculateStylesImportPath(framework, config)\n\n const content = [\n \"The Notion-like template is a complete editor application that requires\",\n \"additional configuration before it can be used:\",\n \"\",\n colors.cyan(\"1. Import Required Styles\"),\n ` Add to ${colors.yellow(cssFile)}:`,\n colors.gray(` @import '${importPath}_variables.${fileExtension}';`),\n colors.gray(\n ` @import '${importPath}_keyframe-animations.${fileExtension}';`\n ),\n \"\",\n colors.cyan(\"2. Add Environment Variables (for collaborative features)\"),\n ` Add to your .env file:`,\n colors.gray(` ${prefix}TIPTAP_COLLAB_DOC_PREFIX - Document prefix`),\n colors.gray(` ${prefix}TIPTAP_COLLAB_APP_ID - Document Server App ID`),\n colors.gray(\n ` ${prefix}TIPTAP_COLLAB_TOKEN - JWT token for collaboration`\n ),\n colors.gray(` ${prefix}TIPTAP_AI_APP_ID - AI App ID`),\n colors.gray(` ${prefix}TIPTAP_AI_TOKEN - JWT token for AI`),\n \"\",\n `Get credentials at ${colors.cyan(\"https://cloud.tiptap.dev\")}`,\n `Setup guide: ${colors.cyan(\"https://tiptap.dev/docs/ui-components/templates/notion-like-editor\")}`,\n ]\n\n const box = createWarningBox(\"Next Steps: Configure your Editor\", content)\n logLines(box)\n}\n\n/**\n * Show Table Node integration guide\n */\nexport function showTableNodeSetupMessage() {\n logger.log(\"\")\n logger.log(colors.cyan(\"→ Table Node integration guide:\"))\n logger.log(\n ` ${colors.dim(\"https://tiptap.dev/docs/ui-components/node-components/table-node#usage\")}`\n )\n logger.log(\"\")\n}\n","import { getConfig } from \"@/src/utils/get-config\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { logger } from \"@/src/utils/logger\"\nimport { Command } from \"commander\"\n\nexport const info = new Command()\n .name(\"info\")\n .description(\"get information about your project\")\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .action(async (opts) => {\n logger.info(\"> project info\")\n console.log(await getProjectInfo(opts.cwd))\n logger.break()\n\n try {\n const config = await getConfig(opts.cwd)\n logger.info(\"> config\")\n console.log(config)\n } catch {\n logger.info(\"\")\n }\n })\n","import path from \"path\"\nimport { Command } from \"commander\"\nimport { confirm, input } from \"@inquirer/prompts\"\nimport { z } from \"zod\"\n\nimport { preFlightInit } from \"@/src/preflights/preflight-init\"\nimport { promptForRegistryComponents } from \"@/src/commands/add\"\nimport { FRAMEWORKS, createProject } from \"@/src/utils/create-project\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { colors } from \"@/src/utils/colors\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { addComponents } from \"@/src/utils/add-components\"\nimport {\n getProjectConfig,\n getProjectInfo,\n ProjectInfo,\n} from \"@/src/utils/get-project-info\"\nimport {\n DEFAULT_COMPONENTS,\n DEFAULT_CONTEXTS,\n DEFAULT_HOOKS,\n DEFAULT_TIPTAP_ICONS,\n DEFAULT_LIB,\n DEFAULT_STYLES,\n DEFAULT_TIPTAP_EXTENSIONS,\n DEFAULT_TIPTAP_NODES,\n DEFAULT_TIPTAP_UI,\n DEFAULT_TIPTAP_UI_PRIMITIVES,\n DEFAULT_TIPTAP_UI_UTILS,\n getConfig,\n rawConfigSchema,\n resolveConfigPaths,\n type Config,\n} from \"@/src/utils/get-config\"\nimport { getRegistryIndex } from \"../utils/registry\"\nimport { ensureAuthForPaidComponents } from \"../utils/auth-check\"\nimport { type Plan } from \"../utils/registry/schema\"\nimport {\n showNotionTemplateSetupMessage,\n showStylesConfigurationMessage,\n showTableNodeSetupMessage,\n} from \"@/src/utils/prompt-messages\"\nimport { Framework } from \"../utils/frameworks\"\nimport {\n createWelcomeBanner,\n logLines,\n createExplanationSection,\n clearTerminal,\n} from \"@/src/utils/cli-ui\"\n\nexport const initOptionsSchema = z.object({\n cwd: z.string(),\n components: z.array(z.string()).optional(),\n silent: z.boolean(),\n isNewProject: z.boolean(),\n srcDir: z.boolean().optional(),\n reactCompiler: z.boolean().optional(),\n framework: z\n .string()\n .optional()\n .refine((val) => !val || FRAMEWORKS[val as keyof typeof FRAMEWORKS], {\n message: \"Invalid framework. Please use 'next' or 'vite'.\",\n }),\n})\n\ntype InitOptions = z.infer<typeof initOptionsSchema> & {\n skipPreflight?: boolean\n}\n\n/**\n * Creates a themed confirmation prompt with consistent styling\n */\nconst createThemedConfirm = (message: string, defaultValue: boolean = true) => {\n return confirm({\n message: colors.reset(message),\n default: defaultValue,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Initialize the CLI command\n */\nexport const init = new Command()\n .name(\"init\")\n .description(\n \"initialize your project and install Tiptap UI components as source code\"\n )\n .argument(\"[components...]\", \"the components to add\")\n .option(\"-f, --framework <framework>\", \"the framework to use. (next, vite)\")\n .option(\n \"-c, --cwd <cwd>\",\n \"the working directory. defaults to the current directory.\",\n process.cwd()\n )\n .option(\"-s, --silent\", \"mute output.\", false)\n .option(\n \"--src-dir\",\n \"use the src directory when creating a new project (specific to next).\",\n false\n )\n .option(\n \"--react-compiler\",\n \"enable React Compiler when creating a new project (specific to next).\",\n false\n )\n .action(async (components, opts) => {\n try {\n // Clear terminal for a fresh start\n clearTerminal()\n\n // Show welcome banner\n const welcomeBanner = createWelcomeBanner(\n \"Tiptap UI Components\",\n \"Install UI components or templates as editable source code in your project\"\n )\n logLines(welcomeBanner)\n\n // Explain what Tiptap CLI does\n const explanation = createExplanationSection(\n \"What are Tiptap UI Components?\",\n [\n \"React UI components that help you develop an editor\",\n \"They install as source code (not npm packages) in your src/components/\",\n \"UI components are a foundation for customization rather than a fixed library\",\n ]\n )\n logLines(explanation)\n\n // Wait for user to press Enter\n await input({\n message: colors.reset(\n `Press ${colors.cyan(\"Enter\")} to initialize a project...`\n ),\n theme: {\n prefix: {\n done: \"\",\n idle: \"\",\n },\n },\n })\n\n // Add visual separation\n logger.log(\"\")\n\n const options = initOptionsSchema.parse({\n cwd: path.resolve(opts.cwd),\n isNewProject: false,\n components,\n ...opts,\n })\n const result = await runInit(options)\n\n // Show success message\n if (result?.filesCreated && result.filesCreated.length > 0) {\n const containsNotion = result.filesCreated.some((path) =>\n path.includes(\"notion\")\n )\n const containsSimpleEditor = result.filesCreated.some(\n (path) => path.includes(\"simple\") && path.includes(\"editor\")\n )\n\n if (containsNotion) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Notion template installed - ${result.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show combined setup message for Notion template\n const framework = result.framework || result.projectInfo?.framework\n if (framework) {\n showNotionTemplateSetupMessage(\n framework as Framework,\n result.config\n )\n }\n } else if (containsSimpleEditor) {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Simple editor template installed - ${result.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration as required\n const framework = result.framework || result.projectInfo?.framework\n if (framework) {\n showStylesConfigurationMessage(\n framework as Framework,\n result.config\n )\n }\n } else {\n // Show single-line success message\n logger.log(\"\")\n logger.log(\n `${colors.green(\"✔\")} Components installed - ${result.filesCreated.length} files added to ${colors.cyan(\"src/components/\")}`\n )\n logger.log(\"\")\n\n // Show styles configuration if UI components were added\n const hasUIComponents = result.filesCreated.some(\n (path) =>\n path.includes(\"tiptap-templates\") || path.includes(\"tiptap-ui\")\n )\n\n if (hasUIComponents) {\n showStylesConfigurationMessage(\n result?.projectInfo?.framework,\n result.config\n )\n }\n\n // Show Table Node integration guide if table-node was installed\n const containsTableNode =\n result.selectedComponents?.includes(\"table-node\")\n if (containsTableNode) {\n showTableNodeSetupMessage()\n }\n }\n }\n\n logger.break()\n } catch (error) {\n logger.break()\n handleError(error)\n }\n })\n\n/**\n * Main initialization function\n */\nexport async function runInit(options: InitOptions) {\n const { cwd, skipPreflight, components, silent } = options\n let updatedOptions = { ...options }\n let newProjectFramework: string | undefined\n\n // Standard return structure creator\n const createResult = (\n config: Config,\n projectInfo: ProjectInfo | null,\n selectedComponents: string[] = [],\n addResult?: {\n filesCreated: string[]\n filesUpdated: string[]\n filesSkipped: string[]\n }\n ) => ({\n config,\n projectInfo,\n framework: newProjectFramework,\n selectedComponents,\n filesCreated: addResult?.filesCreated || [],\n filesUpdated: addResult?.filesUpdated || [],\n filesSkipped: addResult?.filesSkipped || [],\n errors: [],\n })\n\n // Handle preflight checks and project creation\n let projectInfo\n if (!skipPreflight) {\n const preflight = await preFlightInit(options)\n const isMissingDirOrEmptyProject =\n preflight.errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT]\n\n if (isMissingDirOrEmptyProject) {\n const { projectPath, framework } = await createProject(options)\n if (!projectPath) process.exit(0)\n\n updatedOptions = {\n ...updatedOptions,\n cwd: projectPath,\n isNewProject: true,\n }\n newProjectFramework = framework\n logger.log(\"\")\n }\n projectInfo = preflight.projectInfo\n } else {\n projectInfo = await getProjectInfo(cwd)\n }\n\n // Handle monorepo special case\n if (newProjectFramework === \"next-monorepo\") {\n const monorepoWebPath = path.resolve(updatedOptions.cwd, \"apps/web\")\n const config = await getConfig(monorepoWebPath)\n return createResult(config, projectInfo)\n }\n\n // Get configuration\n const projectConfig = await getProjectConfig(updatedOptions.cwd, projectInfo)\n const config = projectConfig\n ? await promptForMinimalConfig(projectConfig)\n : await promptForConfig(await getConfig(updatedOptions.cwd))\n\n logger.log(\"\")\n\n // Handle component selection\n let selectedComponents = components || []\n if (!selectedComponents.length) {\n const shouldAddComponents = await createThemedConfirm(\n \"Would you like to add a template or UI components to your project?\"\n )\n\n if (!shouldAddComponents) {\n const fullConfig = await resolveConfigPaths(updatedOptions.cwd, config)\n return createResult(fullConfig, projectInfo)\n }\n\n selectedComponents = await promptForRegistryComponents(\n { ...updatedOptions, overwrite: false },\n true // Show divider\n )\n\n if (!selectedComponents.length) {\n const fullConfig = await resolveConfigPaths(updatedOptions.cwd, config)\n return createResult(fullConfig, projectInfo)\n }\n }\n\n // Handle registry fetching and authentication for selected components\n let registryIndex\n try {\n registryIndex = await getRegistryIndex()\n if (!registryIndex) {\n throw new Error(\"Failed to fetch registry index.\")\n }\n } catch (error) {\n // Handle 401 auth error with retry\n if (\n error instanceof Error &&\n error.message.includes(\"You are not authorized\")\n ) {\n // Trigger auth flow with assumed paid components\n const assumedPaidComponents = selectedComponents.map((name) => ({\n name,\n plans: [\"start\" as Plan],\n }))\n\n const isAuthenticated = await ensureAuthForPaidComponents(\n assumedPaidComponents,\n updatedOptions.cwd\n )\n\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with paid component download.\"\n )\n logger.log(\n \"You can try again with only free components, or authenticate first.\"\n )\n process.exit(1)\n }\n\n // Retry registry fetch after authentication\n registryIndex = await getRegistryIndex()\n if (!registryIndex) {\n throw new Error(\"Failed to fetch registry index after authentication.\")\n }\n } else {\n throw error\n }\n }\n\n // Map components to details and perform final authentication check\n const selectedComponentDetails = selectedComponents.map((componentName) => {\n const componentInfo = registryIndex.find(\n (item) => item.name === componentName\n )\n return {\n name: componentName,\n plans: componentInfo?.plans || [],\n }\n })\n\n const isAuthenticated = await ensureAuthForPaidComponents(\n selectedComponentDetails,\n updatedOptions.cwd\n )\n\n if (!isAuthenticated) {\n logger.error(\n \"Authentication failed. Cannot proceed with paid component download.\"\n )\n logger.log(\n \"You can try again with only free components, or authenticate first.\"\n )\n process.exit(1)\n }\n\n // Add components and return result\n const fullConfig = await resolveConfigPaths(updatedOptions.cwd, config)\n const addComponentsResult = await addComponents(\n selectedComponents,\n fullConfig,\n {\n overwrite: false,\n silent,\n isNewProject:\n updatedOptions.isNewProject ||\n projectInfo?.framework.name === \"next-app\",\n }\n )\n\n return createResult(\n fullConfig,\n projectInfo,\n selectedComponents,\n addComponentsResult || {\n filesCreated: [],\n filesUpdated: [],\n filesSkipped: [],\n }\n )\n}\n/**\n * Prompt for full configuration\n */\nasync function promptForConfig(defaultConfig: Config | null = null) {\n logger.log(\"\")\n logger.log(colors.cyan(\"Project Configuration\"))\n logger.log(\"\")\n\n const tsx = await createThemedConfirm(\n `Would you like to use ${colors.cyan(\"TypeScript\")} (recommended)?`,\n defaultConfig?.tsx ?? true\n )\n\n const rsc = await createThemedConfirm(\n `Are you using ${colors.cyan(\"React Server Components\")}?`,\n defaultConfig?.rsc ?? true\n )\n\n return rawConfigSchema.parse({\n rsc,\n tsx,\n aliases: {\n components: DEFAULT_COMPONENTS,\n contexts: DEFAULT_CONTEXTS,\n hooks: DEFAULT_HOOKS,\n tiptapIcons: DEFAULT_TIPTAP_ICONS,\n lib: DEFAULT_LIB,\n tiptapExtensions: DEFAULT_TIPTAP_EXTENSIONS,\n tiptapNodes: DEFAULT_TIPTAP_NODES,\n tiptapUi: DEFAULT_TIPTAP_UI,\n tiptapUiPrimitives: DEFAULT_TIPTAP_UI_PRIMITIVES,\n tiptapUiUtils: DEFAULT_TIPTAP_UI_UTILS,\n styles: DEFAULT_STYLES,\n },\n })\n}\n\n/**\n * Prompt for minimal configuration from existing config\n */\nasync function promptForMinimalConfig(defaultConfig: Config) {\n return rawConfigSchema.parse({\n rsc: defaultConfig?.rsc,\n tsx: defaultConfig?.tsx,\n aliases: defaultConfig?.aliases,\n })\n}\n","import path from \"path\"\nimport { initOptionsSchema } from \"@/src/commands/init\"\nimport * as ERRORS from \"@/src/utils/errors\"\nimport { getProjectInfo } from \"@/src/utils/get-project-info\"\nimport { logger } from \"@/src/utils/logger\"\nimport { spinner } from \"@/src/utils/spinner\"\nimport fs from \"fs-extra\"\nimport { z } from \"zod\"\nimport { colors } from \"@/src/utils/colors\"\n\nexport async function preFlightInit(\n options: z.infer<typeof initOptionsSchema>\n) {\n const errors: Record<string, boolean> = {}\n\n // Ensure target directory exists.\n // Check for empty project. We assume if no package.json exists, the project is empty.\n if (\n !fs.existsSync(options.cwd) ||\n !fs.existsSync(path.resolve(options.cwd, \"package.json\"))\n ) {\n errors[ERRORS.MISSING_DIR_OR_EMPTY_PROJECT] = true\n return {\n errors,\n projectInfo: null,\n }\n }\n\n const frameworkSpinner = spinner(`Verifying framework.`, {\n silent: options.silent,\n }).start()\n const projectInfo = await getProjectInfo(options.cwd)\n if (!projectInfo || projectInfo?.framework.name === \"manual\") {\n errors[ERRORS.UNSUPPORTED_FRAMEWORK] = true\n frameworkSpinner?.fail()\n logger.break()\n if (projectInfo?.framework.links.installation) {\n logger.error(\n `We could not detect a supported framework at ${colors.cyan(\n options.cwd\n )}.\\n` +\n `Visit ${colors.cyan(\n projectInfo?.framework.links.installation\n )} to manually configure your project.\\nOnce configured, you can use the cli to add components.`\n )\n }\n logger.break()\n process.exit(0)\n }\n frameworkSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: `Verifying framework. Found ${colors.cyan(projectInfo.framework.label)}.`,\n })\n\n const tsConfigSpinner = spinner(`Validating import alias.`, {\n silent: options.silent,\n }).start()\n if (!projectInfo?.aliasPrefix) {\n errors[ERRORS.IMPORT_ALIAS_MISSING] = true\n tsConfigSpinner?.fail()\n } else {\n tsConfigSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n }\n\n if (Object.keys(errors).length > 0) {\n if (errors[ERRORS.IMPORT_ALIAS_MISSING]) {\n logger.break()\n logger.error(`No import alias found in your tsconfig.json file.`)\n if (projectInfo?.framework.links.installation) {\n logger.error(\n `Visit ${colors.cyan(\n projectInfo?.framework.links.installation\n )} to learn how to set an import alias.`\n )\n }\n }\n\n logger.break()\n process.exit(0)\n }\n\n return {\n errors,\n projectInfo,\n }\n}\n","import os from \"os\"\nimport path from \"path\"\nimport fs from \"fs-extra\"\nimport { execa } from \"execa\"\nimport { z } from \"zod\"\nimport { parse as parseJsonc } from \"jsonc-parser\"\nimport { input } from \"@inquirer/prompts\"\n\nimport { initOptionsSchema } from \"@/src/commands/init\"\nimport select from \"@/src/inquirer/select\"\nimport { colors } from \"@/src/utils/colors\"\nimport { getPackageManager } from \"@/src/utils/get-package-manager\"\nimport { handleError } from \"@/src/utils/handle-error\"\nimport { logger } from \"@/src/utils/logger\"\nimport { spinner } from \"@/src/utils/spinner\"\n\nconst MONOREPO_FRAMEWORK_URL =\n \"https://codeload.github.com/shadcn-ui/ui/tar.gz/main\"\n\nexport const FRAMEWORKS = {\n next: \"next\",\n vite: \"vite\",\n \"next-monorepo\": \"next-monorepo\",\n} as const\n\ntype Framework = keyof typeof FRAMEWORKS\ntype ProjectOptions = Pick<\n z.infer<typeof initOptionsSchema>,\n \"cwd\" | \"srcDir\" | \"components\" | \"framework\" | \"reactCompiler\"\n>\ntype CreateNextOptions = {\n version: string\n cwd: string\n packageManager: string\n srcDir: boolean\n reactCompiler: boolean\n}\ntype CreateViteOptions = {\n cwd: string\n packageManager: string\n projectName: string\n}\ntype CreateMonorepoOptions = {\n packageManager: string\n}\n\n/**\n * Creates a themed input prompt with consistent styling\n */\nconst createThemedInput = (message: string, defaultValue: string = \"\") => {\n return input({\n message: colors.reset(message),\n default: defaultValue,\n required: true,\n validate: (value: string) =>\n value.length > 128 ? `Name should be less than 128 characters.` : true,\n theme: {\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n })\n}\n\n/**\n * Creates a themed select prompt with consistent styling\n */\nconst createThemedSelect = async (\n message: string,\n choices: Array<{ name: string; value: string }>\n) => {\n const instructions = `\\n${colors.gray(\" Use arrow-keys ▲▼ / [Return] to submit\")}\\n`\n\n return select({\n message: colors.reset(message),\n instructions,\n theme: {\n icon: {\n cursor: colors.cyan(\"❯\"),\n },\n prefix: {\n done: colors.cyan(\"✔\"),\n idle: \"?\",\n },\n },\n choices,\n })\n}\n\n/**\n * Creates a new project based on the specified framework\n */\nexport async function createProject(options: ProjectOptions) {\n const normalizedOptions = {\n srcDir: false,\n reactCompiler: false,\n ...options,\n }\n\n let framework: Framework =\n normalizedOptions.framework &&\n FRAMEWORKS[normalizedOptions.framework as Framework]\n ? (normalizedOptions.framework as Framework)\n : \"next\"\n\n let projectName = \"my-app\"\n const nextVersion = \"latest\"\n\n // Only prompt for framework if not already specified\n if (!normalizedOptions.framework) {\n const frameworkPromptMessage = `The path ${colors.cyan(normalizedOptions.cwd)} does not contain a package.json file. Would you like to start a new project?`\n\n const selectedFramework = await createThemedSelect(frameworkPromptMessage, [\n { name: \"Next.js\", value: \"next\" },\n { name: \"Vite + React + TypeScript\", value: \"vite\" },\n // { name: 'Next.js (Monorepo)', value: 'next-monorepo' }\n ])\n\n framework = selectedFramework as Framework\n\n // Add spacing after framework selection\n logger.log(\"\")\n }\n\n // Prompt for project name\n projectName = await createThemedInput(\n \"What is your project named?\",\n projectName\n )\n\n // Get the package manager for the project\n const packageManager = await getPackageManager(normalizedOptions.cwd, {\n withFallback: true,\n })\n\n const projectPath = path.join(normalizedOptions.cwd, projectName)\n\n // Validate path is writable\n await validateProjectPath(normalizedOptions.cwd, projectName)\n\n // Create the project based on framework\n if (framework === FRAMEWORKS.next) {\n await createNextProject(projectPath, {\n version: nextVersion,\n cwd: normalizedOptions.cwd,\n packageManager,\n srcDir: !!normalizedOptions.srcDir,\n reactCompiler: !!normalizedOptions.reactCompiler,\n })\n } else if (framework === FRAMEWORKS.vite) {\n await createViteProject(projectPath, {\n cwd: normalizedOptions.cwd,\n packageManager,\n projectName,\n })\n } else if (framework === FRAMEWORKS[\"next-monorepo\"]) {\n await createMonorepoProject(projectPath, {\n packageManager,\n })\n }\n\n return {\n projectPath,\n projectName,\n framework,\n }\n}\n\n/**\n * Validates that the project path is writable and doesn't already exist\n */\nasync function validateProjectPath(cwd: string, projectName: string) {\n // Check if path is writable\n try {\n await fs.access(cwd, fs.constants.W_OK)\n } catch (error) {\n logger.break()\n logger.error(`The path ${colors.cyan(cwd)} is not writable.`)\n logger.error(\n `It is likely you do not have write permissions for this folder or the path ${colors.cyan(cwd)} does not exist.`\n )\n logger.break()\n process.exit(0)\n }\n\n // Check if project already exists\n if (fs.existsSync(path.resolve(cwd, projectName, \"package.json\"))) {\n logger.break()\n logger.error(\n `A project with the name ${colors.cyan(projectName)} already exists.`\n )\n logger.error(`Please choose a different name and try again.`)\n logger.break()\n process.exit(0)\n }\n}\n\n/**\n * Creates a new Next.js project\n */\nasync function createNextProject(\n projectPath: string,\n options: CreateNextOptions\n) {\n const createSpinner = spinner(\n \"Creating a new Next.js project. This may take a few minutes.\"\n ).start()\n\n // Note: pnpm fails here. Fallback to npx with --use-PACKAGE-MANAGER.\n const args = [\n \"--tailwind\",\n \"--eslint\",\n \"--typescript\",\n \"--app\",\n options.srcDir ? \"--src-dir\" : \"--no-src-dir\",\n \"--no-import-alias\",\n options.reactCompiler ? \"--react-compiler\" : \"--no-react-compiler\",\n `--use-${options.packageManager}`,\n ]\n\n // Add turbopack for Next.js 15+ or canary/latest\n if (\n options.version.startsWith(\"15\") ||\n options.version.startsWith(\"latest\") ||\n options.version.startsWith(\"canary\")\n ) {\n args.push(\"--turbopack\")\n }\n\n try {\n await execa(\n \"npx\",\n [`create-next-app@${options.version}`, projectPath, \"--silent\", ...args],\n { cwd: options.cwd }\n )\n\n await updateReadmeFile(projectPath)\n\n createSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n } catch (error) {\n createSpinner?.fail(\"Something went wrong creating a new Next.js project.\")\n logger.break()\n logger.error(\n `Something went wrong creating a new Next.js project. Please try again.`\n )\n process.exit(0)\n }\n}\n\n/**\n * Creates a new Vite + React + TypeScript project\n */\nasync function createViteProject(\n projectPath: string,\n options: CreateViteOptions\n) {\n const createSpinner = spinner(\n `Creating a new Vite + React + TypeScript project. This may take a few minutes.`\n ).start()\n\n try {\n await execa(\n \"npm\",\n [\n \"create\",\n \"vite@latest\",\n options.projectName,\n \"--\",\n \"--template\",\n \"react-ts\",\n ],\n { cwd: options.cwd }\n )\n\n await execa(options.packageManager, [\"install\"], {\n cwd: projectPath,\n })\n\n await setupViteTsConfig(projectPath, options.packageManager)\n\n await updateReadmeFile(projectPath)\n\n createSpinner.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n })\n } catch (error) {\n createSpinner?.fail(\"Something went wrong creating a new Vite project.\")\n handleError(error)\n }\n}\n\n/**\n * Configures TypeScript and path aliases for a Vite project\n */\nasync function setupViteTsConfig(projectPath: string, packageManager: string) {\n try {\n await setupTsConfigPathAliases(projectPath)\n await setupViteConfigPathAliases(projectPath)\n await installTypesNode(projectPath, packageManager)\n } catch (error) {\n logger.warn(\n \"Failed to set up TypeScript path aliases, but project creation succeeded\"\n )\n }\n}\n\n/**\n * Installs @types/node as a development dependency\n */\nasync function installTypesNode(projectPath: string, packageManager: string) {\n try {\n const devFlag = packageManager === \"npm\" ? \"--save-dev\" : \"-D\"\n\n await execa(\n packageManager,\n [packageManager === \"npm\" ? \"install\" : \"add\", devFlag, \"@types/node\"],\n { cwd: projectPath }\n )\n } catch (error) {\n logger.warn(\"Failed to install @types/node, but project creation succeeded\")\n }\n}\n\n/**\n * Sets up TypeScript configuration files with path aliases\n */\nasync function setupTsConfigPathAliases(projectPath: string) {\n const addAliasToTsConfig = async (tsconfigFile: string) => {\n const tsconfigPath = path.join(projectPath, tsconfigFile)\n if (!(await fs.pathExists(tsconfigPath))) return\n\n const jsonContent = await fs.readFile(tsconfigPath, \"utf-8\")\n const jsonObj = parseJsonc(jsonContent)\n\n jsonObj.compilerOptions = {\n ...jsonObj.compilerOptions,\n baseUrl: \".\",\n paths: {\n ...(jsonObj.compilerOptions?.paths || {}),\n \"@/*\": [\"./src/*\"],\n },\n }\n\n const updatedJson = JSON.stringify(jsonObj, null, 2)\n await fs.writeFile(tsconfigPath, updatedJson)\n }\n\n await addAliasToTsConfig(\"tsconfig.json\")\n await addAliasToTsConfig(\"tsconfig.app.json\")\n}\n\n/**\n * Sets up Vite configuration with path aliases\n */\nasync function setupViteConfigPathAliases(projectPath: string) {\n const viteConfigPath = path.join(projectPath, \"vite.config.ts\")\n const viteConfigContent = await fs.readFile(viteConfigPath, \"utf-8\")\n\n const updatedViteConfig = viteConfigContent\n .replace(\n \"import { defineConfig } from 'vite'\",\n \"import { defineConfig } from 'vite'\\nimport path from 'path'\"\n )\n .replace(\n \"plugins: [react()]\",\n `plugins: [react()],\n resolve: {\n alias: {\n '@': path.resolve(__dirname, './src')\n }\n }`\n )\n\n await fs.writeFile(viteConfigPath, updatedViteConfig)\n}\n\n/**\n * Creates a new Next.js monorepo project\n */\nasync function createMonorepoProject(\n projectPath: string,\n options: CreateMonorepoOptions\n) {\n const createSpinner = spinner(\n `Creating a new Next.js monorepo. This may take a few minutes.`\n ).start()\n\n try {\n await downloadAndExtractFramework(projectPath)\n\n // Run install\n await execa(options.packageManager, [\"install\"], {\n cwd: projectPath,\n })\n\n // Initialize git repository\n await initializeGitRepository(projectPath)\n\n createSpinner?.stopAndPersist({\n symbol: colors.cyan(\"✔\"),\n text: `Created a new Next.js monorepo at ${colors.cyan(projectPath)}`,\n })\n } catch (error) {\n createSpinner?.fail(\"Something went wrong creating a new Next.js monorepo.\")\n handleError(error)\n }\n}\n\n/**\n * Downloads and extracts the monorepo framework\n */\nasync function downloadAndExtractFramework(projectPath: string) {\n // Create temporary directory\n const frameworkPath = path.join(os.tmpdir(), `tiptap-framework-${Date.now()}`)\n await fs.ensureDir(frameworkPath)\n\n // Download framework\n const response = await fetch(MONOREPO_FRAMEWORK_URL)\n if (!response.ok) {\n throw new Error(`Failed to download framework: ${response.statusText}`)\n }\n\n // Write the tar file\n const tarPath = path.resolve(frameworkPath, \"framework.tar.gz\")\n await fs.writeFile(tarPath, Buffer.from(await response.arrayBuffer()))\n\n // Extract framework\n await execa(\"tar\", [\n \"-xzf\",\n tarPath,\n \"-C\",\n frameworkPath,\n \"--strip-components=2\",\n \"ui-main/templates/monorepo-next\",\n ])\n\n // Move to project path and cleanup\n const extractedPath = path.resolve(frameworkPath, \"monorepo-next\")\n await fs.move(extractedPath, projectPath)\n await fs.remove(frameworkPath)\n}\n\n/**\n * Initializes a git repository in the project directory\n */\nasync function initializeGitRepository(projectPath: string) {\n const cwd = process.cwd()\n\n try {\n await execa(\"git\", [\"--version\"], { cwd: projectPath })\n await execa(\"git\", [\"init\"], { cwd: projectPath })\n await execa(\"git\", [\"add\", \"-A\"], { cwd: projectPath })\n await execa(\"git\", [\"commit\", \"-m\", \"Initial commit\"], {\n cwd: projectPath,\n })\n await execa(\"cd\", [cwd])\n } catch (error) {\n logger.warn(\n \"Failed to initialize git repository, but project creation succeeded\"\n )\n }\n}\n\nconst simpleEditorTemplateDocs = `# Simple template\n\nIntegrate the Tiptap open source editor with UI components and open source extensions.\n\nThe Simple Editor Template is a fully working setup for the Tiptap editor. It includes commonly used open source extensions and UI components, all MIT licensed and ready to customize.\n\n**Quick Links:**\n- [View in Full Screen](http://template.tiptap.dev/preview/templates/simple)\n- [GitHub Repository](https://github.com/ueberdosis/tiptap-ui-components/tree/main/apps/web/src/components/tiptap-templates/simple)\n\n## Installation\n\nAdd the Simple Editor Template to your project using the Tiptap CLI:\n\n\\`\\`\\`bash\nnpx @tiptap/cli add simple-editor\n\\`\\`\\`\n\n## Style\n\n> **Missing styles?** If you haven't added the styles yet, make sure to [follow the style setup guide](/ui-components/getting-started/style) to ensure your editor and components render correctly.\n\n## Usage\n\nAfter installation, use the SimpleEditor component in your React or Next.js project:\n\n\\`\\`\\`jsx\nimport { SimpleEditor } from '@/components/tiptap-templates/simple/simple-editor'\n\nexport default function App() {\n return <SimpleEditor />\n}\n\\`\\`\\`\n\n## Features\n\nA fully responsive rich text editor with built-in support for common formatting and layout tools. All components are open source and easy to extend.\n\n- **Responsive design**: Mobile-friendly by default\n- **Dark and light mode**: Supported out-of-the-box\n- **Formatting**: Bold, Italic, Underline\n- **Lists**: Bullet, Ordered, Checkboxes\n- **Text alignment**: Left, Center, Right, Justified\n- **Headings**: Multiple levels via dropdown\n- **Image upload**\n- **Link editing:** UI for adding and editing links\n- **Undo / Redo:** History management\n\n### Used reference components\n\n#### Hooks\n\n- \\`use-mobile\\`\n- \\`use-window-size\\`\n\n#### Icons\n\n- \\`arrow-left-icon\\`\n- \\`highlighter-icon\\`\n- \\`link-icon\\`\n- \\`moon-star-icon\\`\n- \\`sun-icon\\`\n\n#### Extensions\n\n- \\`selection-extension\\`\n- \\`link-extension\\`\n- \\`trailing-node-extension\\`\n\n#### Lib\n\n- \\`tiptap-utils\\`\n\n#### UI Components\n\n- \\`blockquote-button\\`\n- \\`code-block-button\\`\n- \\`color-highlight-button\\`\n- \\`color-highlight-popover\\`\n- \\`heading-button\\`\n- \\`heading-dropdown-menu\\`\n- \\`image-upload-button\\`\n- \\`link-popover\\`\n- \\`list-button\\`\n- \\`list-dropdown-menu\\`\n- \\`mark-button\\`\n- \\`text-align-button\\`\n- \\`undo-redo-button\\`\n\n#### Node Components\n\n- \\`code-block-node\\`\n- \\`image-node\\`\n- \\`image-upload-node\\`\n- \\`list-node\\`\n- \\`paragraph-node\\`\n\n#### Primitives\n\n- \\`button\\`\n- \\`spacer\\`\n- \\`toolbar\\`\n\n## License\n\nThe Simple Editor Template and all included components are MIT licensed. You're free to use, modify, and extend the code as needed.\n\n## Future compatibility\n\nYou can extend this template with additional features as your needs grow.\n\nPaid Tiptap Cloud features will have matching UI components that integrate just as easily! No rework needed.`\n\nconst notionLikeEditorDocs = `# Notion-like Editor\n\nA Notion-style Tiptap editor with collaboration, AI, and rich UI components. Fully customizable and easy to integrate.\n\nThe **Notion-like Editor Template** is a fully featured block-based editor that replicates the familiar Notion experience. It supports collaboration, AI assistance, emoji, drag & drop, advanced formatting—and it's fully customizable.\n\n## Installation\n\nInstall the Notion-like editor with the Tiptap CLI:\n\n\\`\\`\\`bash\nnpx @tiptap/cli add notion-like-editor\n\\`\\`\\`\n\n## Styling\n\n> **Note:** If the editor doesn't look right, make sure you've followed the [style setup guide](/ui-components/getting-started/style).\n\n## Configuration\n\nBefore running the app, configure the required constants inside \\`tiptap-collab-utils.ts\\`. This is necessary to enable features like AI or collaboration.\n\n### Environment Variables\n\nProvide values for the following environment variables:\n\n- \\`TIPTAP_COLLAB_DOC_PREFIX\\` - Prefix for identifying collaborative documents\n- \\`TIPTAP_COLLAB_APP_ID\\` - Your Document Server App ID\n- \\`TIPTAP_COLLAB_TOKEN\\` - JWT token for accessing Collaboration services\n- \\`TIPTAP_AI_APP_ID\\` - Your AI App ID\n- \\`TIPTAP_AI_TOKEN\\` - JWT token for accessing AI services\n\nThe above environment variables should be available in the client-side. Depending on your framework, use the following prefixes to expose them to the client:\n\n- **[Next.js](/ui-components/install/next)**: \\`NEXT_PUBLIC_\\`. For example, \\`NEXT_PUBLIC_TIPTAP_COLLAB_DOC_PREFIX\\`.\n- **[Vite + React](/ui-components/install/vite)**: \\`VITE_\\`. For example, \\`VITE_TIPTAP_COLLAB_DOC_PREFIX\\`.\n- **Other frameworks**: Follow the specific rules of your framework, and define the variables in the \\`tiptap-collab-utils.ts\\` file.\n\n### JWT Authentication\n\nCollaboration and AI features require a valid server-generated JWT token passed to the editor. See the \\`fetchCollabToken\\` function in \\`tiptap-collab-utils.ts\\` for an example.\n\n> See the full guide on JWT authentication at [https://tiptap.dev/docs/guides/authentication](https://tiptap.dev/docs/guides/authentication).\n\n> **Important:** To get started quickly, you can use the example JWT tokens from your Tiptap Cloud account and store them in the \\`TIPTAP_COLLAB_TOKEN\\` and \\`TIPTAP_AI_TOKEN\\` environment variables. However, example JWT tokens are valid for a short time and should not be used in production. In production, implement an API endpoint that generates JWTs on the server side.\n\n### \\`room\\` prop\n\nUse the \\`room\\` prop to distinguish collaborative documents. Each session should use a unique room ID.\n\n## Usage\n\nImport and render the \\`NotionEditor\\` component in your React app:\n\n\\`\\`\\`tsx\nimport { NotionEditor } from '@/components/tiptap-templates/notion/notion-like-editor'\n\nexport default function App() {\n return <NotionEditor room=\"my-document-room\" placeholder=\"Start writing...\" />\n}\n\\`\\`\\`\n\n## Features\n\nThe template includes all the essentials of a modern Notion-style editor:\n\n- **Real-time collaboration**: Live cursors and user presence\n- **AI assistance**: Inline AI tools for writing and editing\n- **Responsive design**: Mobile-ready UI with adaptive toolbars\n- **Dark/light mode**: Fully themed out of the box\n- **Slash commands**: \\`/\\` menu for quick formatting\n- **Floating toolbar**: Context-aware formatting\n- **Drag and drop**: Block-level reordering\n- **Emoji support**: GitHub-style emoji picker\n- **Mentions**: \\`@user\\` autocomplete\n- **Rich formatting**:\n - Bold, italic, underline, strikethrough\n - Highlight and color\n - Superscript / subscript\n - Syntax-highlighted code blocks\n- **Block types**:\n - Headings, lists, blockquotes, dividers, math\n- **Media support**: Drag & drop image upload\n- **Link management**: With inline previews\n- **Text alignment**: Left, center, right, justified\n- **Undo/Redo**: Full editing history\n- **Context menus**: Right-click enhancements\n\n## Component Breakdown\n\n### Hooks\n\n- \\`use-mobile\\`\n- \\`use-window-size\\`\n- \\`use-ui-editor-state\\`\n\n### Icons\n\n- \\`arrow-left-icon\\`\n- \\`chevron-right-icon\\`\n- \\`highlighter-icon\\`\n- \\`link-icon\\`\n- \\`more-vertical-icon\\`\n\n### Tiptap Extensions\n\n- \\`collaboration\\`, \\`collaboration-cursor\\`\n- \\`selection-extension\\`\n- \\`link-extension\\`\n- \\`trailing-node-extension\\`\n- \\`ai-extension\\`\n- \\`emoji-extension\\`\n- \\`mention-extension\\`\n- \\`mathematics-extension\\`\n- \\`unique-id-extension\\`\n\n### Libs\n\n- \\`tiptap-utils\\`\n- \\`tiptap-collab-utils\\`\n\n### UI Components\n\n- \\`ai-menu\\`\n- \\`blockquote-button\\`\n- \\`code-block-button\\`\n- \\`color-highlight-button\\`, \\`color-highlight-popover\\`\n- \\`drag-context-menu\\`\n- \\`emoji-dropdown-menu\\`\n- \\`heading-button\\`, \\`heading-dropdown-menu\\`\n- \\`image-upload-button\\`\n- \\`link-popover\\`\n- \\`list-button\\`, \\`list-dropdown-menu\\`\n- \\`mark-button\\`\n- \\`mention-dropdown-menu\\`\n- \\`slash-dropdown-menu\\`\n- \\`text-align-button\\`\n- \\`turn-into-dropdown\\`\n- \\`undo-redo-button\\`\n\n### Nodes\n\n- \\`code-block-node\\`\n- \\`image-node\\`, \\`image-upload-node\\`\n- \\`list-node\\`\n- \\`paragraph-node\\`\n\n### Notion-specific\n\n- \\`notion-like-editor-header\\`\n- \\`notion-toolbar-floating\\`\n- \\`mobile-toolbar\\`\n- \\`collaboration-users\\`\n- \\`theme-toggle\\`\n\n### Primitives\n\n- \\`button\\`, \\`button-group\\`\n- \\`dropdown-menu\\`\n- \\`separator\\`, \\`spacer\\`, \\`toolbar\\`\n\n### Contexts\n\n- \\`app-context\\`\n- \\`user-context\\`\n- \\`collab-context\\`\n\n## Collaboration\n\nTo use collaboration:\n\n1. Pass a unique \\`room\\` ID to \\`NotionEditor\\`\n2. Enable JWT auth for each user session\n3. User presence and cursors are handled automatically\n4. Operational transformation handles concurrent edits\n5. Sync and save are managed out-of-the-box\n\n\\`\\`\\`tsx\n<NotionEditor room=\"team-notes\" placeholder=\"Share your ideas...\" />\n\\`\\`\\`\n\n## AI Integration\n\nThe built-in AI tools let you:\n\n- **Generate content** from prompts\n- **Improve** existing text\n- **Get smart completions** based on context\n\n> **AI Configuration:** Make sure to configure your AI provider. Check the [AI Generation extension docs](/content-ai/capabilities/generation/overview) for setup steps.\n\n## Extendability\n\nThis template is designed to grow with your needs. New Tiptap Cloud features will be seamlessly compatible with the same UI system—no rewrites required.`\n\nasync function updateReadmeFile(projectPath: string, templateName?: string) {\n const readmePath = path.join(projectPath, \"README.md\")\n\n const templateContent = {\n \"simple-editor\": simpleEditorTemplateDocs,\n \"notion-like-editor\": notionLikeEditorDocs,\n } as const\n\n type TemplateKey = keyof typeof templateContent\n\n const readmeContent =\n templateName && templateName in templateContent\n ? templateContent[templateName as TemplateKey]\n : \"\"\n\n try {\n if (readmeContent.trim()) {\n await fs.writeFile(readmePath, readmeContent, \"utf-8\")\n }\n } catch {\n /* empty */\n }\n}\n","#!/usr/bin/env node\nimport { add } from \"@/src/commands/add\"\nimport { info } from \"@/src/commands/info\"\nimport { init } from \"@/src/commands/init\"\nimport { login, logout, status, license } from \"@/src/commands/auth\"\nimport { Command } from \"commander\"\n\nimport packageJson from \"../package.json\"\n\nprocess.on(\"SIGINT\", () => process.exit(0))\nprocess.on(\"SIGTERM\", () => process.exit(0))\n\nasync function main() {\n const program = new Command()\n .name(\"tiptap\")\n .description(\"add components and dependencies to your project\")\n .version(\n packageJson.version || \"1.0.0\",\n \"-v, --version\",\n \"display the CLI version number\"\n )\n\n program\n .addCommand(init)\n .addCommand(add)\n .addCommand(info)\n .addCommand(login)\n .addCommand(logout)\n .addCommand(status)\n .addCommand(license)\n\n program.parse()\n}\n\nmain()\n","{\n \"name\": \"@tiptap/cli\",\n \"version\": \"3.3.8\",\n \"description\": \"Tiptap CLI\",\n \"publishConfig\": {\n \"access\": \"public\"\n },\n \"author\": {\n \"name\": \"tiptap\",\n \"url\": \"https://github.com/ueberdosis/tiptap\"\n },\n \"files\": [\n \"dist\"\n ],\n \"keywords\": [\n \"cli\",\n \"components\",\n \"nextjs\",\n \"react\",\n \"templates\",\n \"tiptap\",\n \"@tiptap/cli\",\n \"ui\"\n ],\n \"license\": \"SEE LICENSE IN LICENSE.md\",\n \"type\": \"module\",\n \"exports\": {\n \".\": {\n \"types\": \"./dist/index.d.ts\",\n \"default\": \"./dist/index.js\"\n }\n },\n \"bin\": \"./dist/index.js\",\n \"scripts\": {\n \"dev\": \"tsup --watch\",\n \"build\": \"tsup\",\n \"typecheck\": \"tsc --noEmit\",\n \"clean\": \"rm -rf dist\",\n \"start:dev\": \"cross-env REGISTRY_URL=http://localhost:3000 node dist/index.js\",\n \"start:prod\": \"cross-env REGISTRY_URL=https://template.tiptap.dev node dist/index.js\",\n \"start\": \"node dist/index.js\",\n \"pub:beta\": \"pnpm build && pnpm publish --no-git-checks --access public --tag beta\",\n \"pub:release\": \"pnpm build && pnpm publish --access public\"\n },\n \"dependencies\": {\n \"@antfu/ni\": \"^23.3.1\",\n \"@babel/core\": \"^7.28.5\",\n \"@babel/parser\": \"^7.28.5\",\n \"@babel/plugin-transform-typescript\": \"^7.28.5\",\n \"@inquirer/core\": \"^10.3.0\",\n \"@inquirer/figures\": \"^1.0.14\",\n \"@inquirer/prompts\": \"^7.9.0\",\n \"@inquirer/type\": \"^3.0.9\",\n \"ansi-escapes\": \"^7.1.1\",\n \"chalk\": \"^5.6.2\",\n \"commander\": \"^13.1.0\",\n \"conf\": \"^14.0.0\",\n \"cosmiconfig\": \"^9.0.0\",\n \"deepmerge\": \"^4.3.1\",\n \"execa\": \"^9.6.0\",\n \"fast-glob\": \"^3.3.3\",\n \"fs-extra\": \"^11.3.2\",\n \"https-proxy-agent\": \"^7.0.6\",\n \"jsonc-parser\": \"^3.3.1\",\n \"node-fetch\": \"^3.3.2\",\n \"ora\": \"^8.2.0\",\n \"recast\": \"^0.23.11\",\n \"sass\": \"^1.93.2\",\n \"ts-morph\": \"^25.0.1\",\n \"tsconfig-paths\": \"^4.2.0\",\n \"yaml\": \"^2.8.1\",\n \"yoctocolors-cjs\": \"^2.1.3\",\n \"zod\": \"^3.25.76\"\n },\n \"devDependencies\": {\n \"@babel/plugin-transform-typescript\": \"^7.26.5\",\n \"@types/babel__core\": \"^7.20.5\",\n \"@types/conf\": \"^3.0.3\",\n \"@types/fs-extra\": \"^11.0.4\",\n \"@types/prompts\": \"^2.4.9\",\n \"cross-env\": \"^7.0.3\",\n \"tsup\": \"^8.5.0\",\n \"type-fest\": \"^4.41.0\"\n }\n}\n"],"mappings":"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A;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,8GAiH3BC,GAAuB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAA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","names":["path","Command","z","createPrompt","useState","useKeypress","usePrefix","usePagination","useRef","useMemo","useEffect","isBackspaceKey","isEnterKey","isUpKey","isDownKey","isNumberKey","Separator","ValidationError","makeTheme","colors","figures","ansiEscapes","selectTheme","text","isSelectable","item","normalizeChoices","choices","choice","name","normalizedChoice","select_default","config","done","loop","pageSize","instructions","firstRender","theme","status","setStatus","prefix","searchTimeoutRef","showHelpTip","setShowHelpTip","items","bounds","first","last","defaultItemIndex","active","setActive","selectedChoice","key","rl","offset","next","position","searchTerm","matchIndex","message","helpTipTop","helpTipBottom","page","isActive","index","indexLabel","disabledLabel","color","x","cursor","choiceDescription","Separator","input","confirm","checkbox","path","path","createMatchPath","resolveImport","importPath","config","cosmiconfig","fg","loadConfig","z","path","FRAMEWORKS","path","fs","getPackageInfo","cwd","shouldThrow","packageJsonPath","fg","fs","loadConfig","PROJECT_SHARED_IGNORE","getProjectInfo","cwd","configFiles","isSrcDir","isTsx","aliasPrefix","packageJson","fg","fs","path","isTypeScriptProject","getTsConfigAliasPrefix","getPackageInfo","isUsingAppDir","type","FRAMEWORKS","file","dep","tsConfig","loadConfig","alias","paths","getProjectConfig","defaultProjectInfo","existingConfig","projectInfo","getConfig","config","resolveConfigPaths","DEFAULT_COMPONENTS","DEFAULT_CONTEXTS","DEFAULT_HOOKS","DEFAULT_TIPTAP_ICONS","DEFAULT_LIB","DEFAULT_TIPTAP_EXTENSIONS","DEFAULT_TIPTAP_NODES","DEFAULT_TIPTAP_UI","DEFAULT_TIPTAP_UI_PRIMITIVES","DEFAULT_TIPTAP_UI_UTILS","DEFAULT_STYLES","explorer","cosmiconfig","rawConfigSchema","z","configSchema","workspaceConfigSchema","getConfig","cwd","res","projectInfo","getProjectInfo","defaultAliases","applyAliasPrefix","aliases","prefix","key","value","config","resolvedAliases","resolveConfigPaths","tsConfig","loadConfig","resolveImport","path","getWorkspaceConfig","isAliasKey","resolvedPath","packageRoot","findPackageRoot","result","commonRoot","findCommonRoot","relativePath","matchingPackageRoot","fg","pkgPath","pkgDir","parts1","parts2","commonParts","chalk","colors","join","args","logger","colors","fs","preFlightAdd","options","errors","fs","path","config","getConfig","error","logger","colors","path","z","handleError","error","logger","z","key","value","colors","z","registryItemTypeSchema","PAID_PLANS","FREE_PLANS","ALL_PLANS","planSchema","registryItemFileSchema","registryItemSchema","registrySchema","registryIndexSchema","registryResolvedItemsTreeSchema","deepmerge","HttpsProxyAgent","fetch","z","Conf","TokenStorage","logger","prefix","error","msg","token","userInfo","e","loginDate","expiration","bearerToken","authToken","expirationISO","planName","plans","tokenStorage","TokenStorage","logger","REGISTRY_URL","agent","HttpsProxyAgent","getRegistryIndex","result","fetchRegistry","registryIndexSchema","error","logger","handleError","createRegistryError","response","url","errorMessages","urlInfo","colors","tokenStorage","message","fetchComponent","path","headers","getRegistryUrl","fetch","fetchRegistryBatch","componentNames","paths","bearerToken","fetchRegistryDependencies","components","registryResolveItemsTree","names","config","registryItems","resolveRegistryItems","payload","z","registryItemSchema","framework","getProjectInfo","allDependencies","deepmerge","item","allDevDependencies","filteredDevDependencies","filterDevDependenciesByFramework","registryResolvedItemsTreeSchema","name","isUrl","componentName","getRegistryTypeAliasMap","getRegistryParentMap","map","dependency","devDependencies","depsArray","stringDeps","dep","hasSass","hasSassEmbedded","filteredDeps","prefersEmbedded","FRAMEWORKS","prefersRegular","ora","tiptapSpinner","colors","spinner","text","options","ora","detect","fs","path","getPackageManager","targetDir","withFallback","packageManager","userAgent","isBunProject","cwd","hasBunLock","fs","path","hasBunfig","execa","updateDependencies","dependencies","config","options","dependenciesSpinner","spinner","packageManager","getPackageManager","execa","colors","existsSync","fs","path","basename","fs","tmpdir","path","transformImport","sourceFile","config","packageManager","importDeclarations","importDeclaration","moduleSpecifier","updateImportAliases","isBunProject","alias","transformFromAstSync","parse","transformTypescript","recast","PARSE_OPTIONS","transformJsx","sourceFile","config","output","ast","code","result","SyntaxKind","directiveRegex","transformRsc","sourceFile","config","first","Node","SyntaxKind","DEFAULT_EXCLUSIONS","shouldExcludeComponent","componentName","rules","filePath","rule","f","name","ruleName","getFrameworkEnvVarName","constantName","framework","frameworkName","FRAMEWORKS","stripFrameworkPrefix","varName","transformEnvironmentVariables","sourceFile","config","projectInfo","getProjectInfo","nodesToTransform","binaryExpressions","SyntaxKind","binaryExpr","leftText","match","transformedEnvVar","rightSide","newExpression","callExpressions","callExpr","expressionText","args","argText","newArgText","envVarsToTransform","frameworkEnvVarName","newCallExpr","propertyAccessExpressions","propAccess","propAccessText","node","newText","error","transformRemoveComponents","exclusionRules","nodesToModify","importDeclarations","importDeclaration","moduleSpecifier","defaultImport","namedImports","excludedImports","namedImport","excludedImport","exportDeclarations","exportDeclaration","namedExports","excludedExports","namedExport","excludedExport","variableStatements","variableStatement","declarations","excludedDeclarations","declaration","functionDeclarations","functionDeclaration","functionName","interfaceDeclarations","interfaceDeclaration","interfaceName","typeAliases","typeAlias","typeName","propertySignatures","propertySignature","propName","jsxElements","jsxElement","tagName","jsxSelfClosingElements","jsxSelfClosingElement","propertyAssignments","propertyAssignment","propertyName","jsxAttributes","jsxAttribute","attributeName","parameters","parameter","parameterName","paramList","Node","allParams","index","prev","next","i","arg","prevSibling","nextSibling","bindingElements","bindingElement","bindingName","bindingPattern","allBindings","identifiers","identifier","identifierName","parent","parentKind","propAssignment","shorthandPropertyAssignments","shorthandProp","a","b","aStart","action","sass","transformScssToCSS","scssContent","error","Project","ScriptKind","project","Project","createTempSourceFile","filename","dir","fs","path","tmpdir","transform","opts","transformers","transformImport","transformRsc","transformRemoveComponents","isBun","isBunProject","transformScssToCSS","tempFile","sourceFile","ScriptKind","transformer","transformJsx","confirm","updateFiles","files","config","options","result","filesCreatedSpinner","spinner","projectInfo","packageManager","getProjectInfo","getPackageManager","file","filePath","resolveFilePath","findCommonRoot","f","error","fileName","basename","targetDir","path","match","isBunProject","existingFile","existsSync","content","transform","transformImport","transformRsc","transformRemoveComponents","existingFileContent","fs","normalizedExisting","normalizedNew","getNormalizedFileContent","confirm","colors","text","logger","resolveFileTargetDirectory","override","paths","needle","normalizedPaths","p","normalizedNeedle","needleDir","needleSegments","i","testPath","resolvePageTarget","target","framework","resolveNestedFilePath","normalizedFilePath","normalizedTargetDir","fileSegments","targetSegments","lastTargetSegment","commonDirIndex","segment","templateName","relativePath","finalPath","templateMatch","dataPath","z","execa","updateDevDependencies","devDependencies","config","options","devDependenciesSpinner","spinner","packageManager","getPackageManager","execa","colors","addComponents","components","config","options","workspaceConfig","getWorkspaceConfig","addWorkspaceComponents","addProjectComponents","registrySpinner","spinner","tree","registryResolveItemsTree","colors","updateDependencies","updateDevDependencies","updateFiles","handleError","registryItems","resolveRegistryItems","result","fetchRegistry","payload","z","registryItemSchema","registryParentMap","getRegistryParentMap","registryTypeAliasMap","getRegistryTypeAliasMap","filesCreated","filesUpdated","filesSkipped","rootSpinner","component","alias","registryParent","targetConfig","workspaceRoot","findCommonRoot","packageRoot","findPackageRoot","files","file","error","logger","path","toReadableName","input","word","fetch","HttpsProxyAgent","fs","path","os","execa","yaml","TIPTAP_REGISTRY","AUTH_TOKEN_KEY","TIPTAP_PRO_REGISTRY_KEY","addNpmrcToGitignore","cwd","gitignorePath","path","npmrcEntry","gitignoreContent","fs","line","newContent","error","logger","saveAuthToken","token","packageManager","createdNpmrc","saveNpmToken","saveYarnToken","saveToNpmrc","execa","yarnVersion","saveYarnBerryToken","yarnrcPath","yamlObj","yarnrcContent","npmrcPath","npmrcContent","lines","processedKeys","parseNpmrc","contentLines","trimmedLine","index","key","getAuthToken","projectToken","checkProjectNpmrc","getNpmAuthToken","checkGlobalNpmrc","projectNpmrcPath","content","extractAuthToken","stdout","globalNpmrcPath","os","configString","AUTH_API_URL","REGISTRY_URL","httpAgent","HttpsProxyAgent","authenticateUser","email","password","packageManager","writeConfig","cwd","loginSpinner","spinner","tokens","requestAuthTokens","userPlans","plansResponse","fetch","plan","tokenStorage","saveAuthToken","colors","error","response","data","checkAuthStatus","bearerToken","userInfo","expiration","logger","logoutUser","Command","execa","z","confirm","input","passwordPrompt","authOptionsSchema","z","createThemedInput","message","options","input","colors","value","createThemedPassword","passwordPrompt","createThemedConfirm","defaultValue","confirm","getConfigFileName","packageManager","displayTokenInstructions","token","cwd","logger","checkYarnVersion","execa","handleLogin","email","password","writeConfig","showMessage","getPackageManager","configFileName","result","authenticateUser","handleStatusCheck","status","checkAuthStatus","expiryDate","now","daysUntilExpiry","tokenPreview","registryToken","getAuthToken","registryPreview","login","Command","opts","error","handleError","logout","logoutSpinner","spinner","logoutUser","handleLicenseInfo","hasAccepted","tokenStorage","userInfo","handleLicenseForgetMe","license","hasPaidComponents","components","component","plan","PAID_PLANS","promptLicenseAcceptance","selectedComponents","tokenStorage","logger","colors","createThemedConfirm","ensureAuthForPaidComponents","cwd","checkAuthStatus","packageManager","getPackageManager","checkNpmrcConfiguration","createNpmrcConfiguration","handleLogin","error","getAuthToken","configSpinner","spinner","authToken","saveAuthToken","process","getTerminalWidth","createBox","title","content","options","borderColor","padding","topLeft","topRight","bottomLeft","bottomRight","horizontal","vertical","terminalWidth","boxWidth","colorFn","colors","topBorder","bottomBorder","sideBorder","lines","titlePadding","stripAnsi","titleLine","line","strippedLength","paddedLine","createWelcomeBanner","title","subtitle","content","createBox","createWarningBox","title","content","createBox","logLines","lines","line","logger","stripAnsi","str","createExplanationSection","title","points","lines","colors","point","clearTerminal","process","createSpacedDivider","width","getTerminalWidth","colors","existsSync","path","getFrameworkEnvPrefix","framework","frameworkName","FRAMEWORKS","detectStyleFileExtension","config","stylesDir","variablesScss","variablesCss","calculateStylesImportPath","stylesInSrc","hasSrcDir","cssFile","importPath","showStylesConfigurationMessage","fileExtension","content","colors","box","createWarningBox","logLines","showNotionTemplateSetupMessage","framework","config","prefix","getFrameworkEnvPrefix","fileExtension","detectStyleFileExtension","cssFile","importPath","calculateStylesImportPath","content","colors","box","createWarningBox","logLines","showTableNodeSetupMessage","logger","addOptionsSchema","z","PROMPT_PAGE_SIZE","UI","colors","PROMPT_THEME","text","filterFreeTemplates","templates","freeComponents","template","clearPromptLines","lines","i","categorizeRegistryItems","registryIndex","entry","promptForInitialSelection","categories","showDivider","message","choices","isComponentEmpty","logger","UI","createSpacedDivider","selection","select_default","colors","PROMPT_PAGE_SIZE","PROMPT_THEME","createComponentChoices","components","addCategorySection","items","title","filtertedItems","item","Separator","planLabel","paddedName","toReadableName","description","componentMenu","selectedComponents","checkbox","component","templateMenu","name","selectedTemplate","promptForRegistryComponents","options","getRegistryIndex","error","ensureAuthForPaidComponents","handleError","allComponents","filteredTemplates","add","Command","opts","clearTerminal","welcomeBanner","createWelcomeBanner","logLines","explanation","createExplanationSection","input","addOptionsSchema","path","selectedComponentDetails","componentName","componentInfo","errors","config","preFlightAdd","created","addComponents","containsNotion","containsSimpleEditor","projectInfo","getProjectInfo","showNotionTemplateSetupMessage","showStylesConfigurationMessage","showTableNodeSetupMessage","Command","info","opts","logger","getProjectInfo","config","getConfig","path","Command","confirm","input","z","path","fs","preFlightInit","options","errors","fs","path","frameworkSpinner","spinner","projectInfo","getProjectInfo","logger","colors","tsConfigSpinner","os","path","fs","execa","parseJsonc","input","MONOREPO_FRAMEWORK_URL","FRAMEWORKS","createThemedInput","message","defaultValue","input","colors","value","createThemedSelect","choices","instructions","select_default","createProject","options","normalizedOptions","framework","projectName","nextVersion","frameworkPromptMessage","logger","packageManager","getPackageManager","projectPath","path","validateProjectPath","createNextProject","createViteProject","createMonorepoProject","cwd","fs","createSpinner","spinner","args","execa","updateReadmeFile","setupViteTsConfig","error","handleError","setupTsConfigPathAliases","setupViteConfigPathAliases","installTypesNode","addAliasToTsConfig","tsconfigFile","tsconfigPath","jsonContent","jsonObj","parseJsonc","updatedJson","viteConfigPath","updatedViteConfig","downloadAndExtractFramework","initializeGitRepository","frameworkPath","os","response","tarPath","extractedPath","simpleEditorTemplateDocs","notionLikeEditorDocs","templateName","readmePath","templateContent","readmeContent","initOptionsSchema","z","val","FRAMEWORKS","createThemedConfirm","message","defaultValue","confirm","colors","init","Command","components","opts","clearTerminal","welcomeBanner","createWelcomeBanner","logLines","explanation","createExplanationSection","input","logger","options","path","result","runInit","containsNotion","containsSimpleEditor","framework","showNotionTemplateSetupMessage","showStylesConfigurationMessage","showTableNodeSetupMessage","error","handleError","cwd","skipPreflight","silent","updatedOptions","newProjectFramework","createResult","config","projectInfo","selectedComponents","addResult","getProjectInfo","preflight","preFlightInit","projectPath","createProject","monorepoWebPath","getConfig","projectConfig","getProjectConfig","promptForMinimalConfig","promptForConfig","fullConfig","resolveConfigPaths","promptForRegistryComponents","registryIndex","getRegistryIndex","assumedPaidComponents","name","ensureAuthForPaidComponents","selectedComponentDetails","componentName","componentInfo","item","addComponentsResult","addComponents","defaultConfig","tsx","rsc","rawConfigSchema","DEFAULT_COMPONENTS","DEFAULT_CONTEXTS","DEFAULT_HOOKS","DEFAULT_TIPTAP_ICONS","DEFAULT_LIB","DEFAULT_TIPTAP_EXTENSIONS","DEFAULT_TIPTAP_NODES","DEFAULT_TIPTAP_UI","DEFAULT_TIPTAP_UI_PRIMITIVES","DEFAULT_TIPTAP_UI_UTILS","DEFAULT_STYLES","Command","package_default","main","program","Command","package_default","init","add","info","login","logout","status","license"]}
|