@analogjs/content 3.0.0-beta.40 → 3.0.0-beta.41

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.
@@ -2,7 +2,7 @@ import { n as parseRawContentFileAsync, t as parseRawContentFile } from "./parse
2
2
  import { _ as NoopContentRenderer, a as injectContentFileLoader, c as injectContentFilesMap, d as CONTENT_LOCALE, f as filterByLocale, g as ContentRenderer, h as withLocaleCandidates, i as CONTENT_FILE_LOADER, l as RenderTaskService, m as withLocale, n as injectContentListLoader, o as withContentFileLoader, p as injectContentLocale, r as withContentListLoader, s as injectContentFiles, t as CONTENT_LIST_LOADER, u as CONTENT_FILES_TOKEN } from "./content-list-loader.mjs";
3
3
  import { t as FrontmatterValidationError } from "./frontmatter-validation-error.mjs";
4
4
  import * as i0 from "@angular/core";
5
- import { Component, Directive, HostListener, InjectionToken, Input, NgZone, PLATFORM_ID, ViewEncapsulation, computed, inject, input } from "@angular/core";
5
+ import { Component, Directive, ElementRef, HostListener, InjectionToken, Input, NgZone, PLATFORM_ID, ViewEncapsulation, computed, inject, input } from "@angular/core";
6
6
  import { DOCUMENT, Location, isPlatformBrowser } from "@angular/common";
7
7
  import { ActivatedRoute, Router } from "@angular/router";
8
8
  import { Observable, firstValueFrom, from, isObservable, of } from "rxjs";
@@ -13,11 +13,14 @@ import { takeUntilDestroyed, toSignal } from "@angular/core/rxjs-interop";
13
13
  var AnchorNavigationDirective = class AnchorNavigationDirective {
14
14
  constructor() {
15
15
  this.document = inject(DOCUMENT);
16
+ this.host = inject(ElementRef);
16
17
  this.location = inject(Location);
17
18
  this.router = inject(Router);
18
19
  }
19
- handleNavigation(element) {
20
- if (element instanceof HTMLAnchorElement && isInternalUrl(element, this.document) && hasTargetSelf(element) && !hasDownloadAttribute(element)) {
20
+ handleNavigation(target, event) {
21
+ if (event && shouldSkipClick(event)) return true;
22
+ const element = target instanceof Element ? target.closest("a") : null;
23
+ if (element && this.host.nativeElement.contains(element) && isInternalUrl(element, this.document) && hasTargetSelf(element) && !hasDownloadAttribute(element)) {
21
24
  const { pathname, search, hash } = element;
22
25
  const isFragmentOnly = element.getAttribute("href")?.startsWith("#");
23
26
  const resolvedPathname = isFragmentOnly ? this.document.location.pathname : pathname;
@@ -45,7 +48,7 @@ var AnchorNavigationDirective = class AnchorNavigationDirective {
45
48
  type: AnchorNavigationDirective,
46
49
  isStandalone: true,
47
50
  selector: "[analogAnchorNavigation]",
48
- host: { listeners: { "click": "handleNavigation($event.target)" } },
51
+ host: { listeners: { "click": "handleNavigation($event.target,$event)" } },
49
52
  ngImport: i0
50
53
  });
51
54
  }
@@ -64,9 +67,12 @@ i0.ɵɵngDeclareClassMetadata({
64
67
  }],
65
68
  propDecorators: { handleNavigation: [{
66
69
  type: HostListener,
67
- args: ["click", ["$event.target"]]
70
+ args: ["click", ["$event.target", "$event"]]
68
71
  }] }
69
72
  });
73
+ function shouldSkipClick(event) {
74
+ return event.defaultPrevented || event.button !== 0 || event.ctrlKey || event.metaKey || event.shiftKey || event.altKey;
75
+ }
70
76
  function hasDownloadAttribute(anchorElement) {
71
77
  return anchorElement.getAttribute("download") !== null;
72
78
  }
@@ -1 +1 @@
1
- {"version":3,"file":"analogjs-content.mjs","names":[],"sources":["../../src/lib/anchor-navigation.directive.ts","../../src/lib/parse-content-file.ts","../../src/lib/utils/zone-wait-for.ts","../../src/lib/content.ts","../../src/lib/provide-content.ts","../../src/lib/markdown-route.component.ts","../../src/lib/markdown.component.ts"],"sourcesContent":["import { Directive, HostListener, inject } from '@angular/core';\nimport { DOCUMENT, Location } from '@angular/common';\nimport { Router } from '@angular/router';\n\n@Directive({\n selector: '[analogAnchorNavigation]',\n standalone: true,\n})\nexport class AnchorNavigationDirective {\n private readonly document = inject(DOCUMENT);\n private readonly location = inject(Location);\n private readonly router = inject(Router);\n\n @HostListener('click', ['$event.target'])\n handleNavigation(element: EventTarget | null): boolean {\n if (\n element instanceof HTMLAnchorElement &&\n isInternalUrl(element, this.document) &&\n hasTargetSelf(element) &&\n !hasDownloadAttribute(element)\n ) {\n const { pathname, search, hash } = element;\n // A `<base>` element makes the browser resolve fragment-only hrefs\n // (e.g. `href=\"#some-id\"`) against the base URL rather than the\n // current document, so `pathname`/`search` come back as the base's\n // rather than the current page's. Fall back to the document's own\n // location in that case, or an in-page anchor link would navigate\n // to the base route and lose the fragment there.\n const isFragmentOnly = element.getAttribute('href')?.startsWith('#');\n const resolvedPathname = isFragmentOnly\n ? this.document.location.pathname\n : pathname;\n const resolvedSearch = isFragmentOnly\n ? this.document.location.search\n : search;\n const url = this.location.normalize(\n `${resolvedPathname}${resolvedSearch}${hash}`,\n );\n this.router.navigateByUrl(url);\n\n return false;\n }\n\n return true;\n }\n}\n\nfunction hasDownloadAttribute(anchorElement: HTMLAnchorElement): boolean {\n return anchorElement.getAttribute('download') !== null;\n}\n\nfunction hasTargetSelf(anchorElement: HTMLAnchorElement): boolean {\n return !anchorElement.target || anchorElement.target === '_self';\n}\n\nfunction isInternalUrl(\n anchorElement: HTMLAnchorElement,\n document: Document,\n): boolean {\n return (\n anchorElement.host === document.location.host &&\n anchorElement.protocol === document.location.protocol\n );\n}\n","export type ContentFileModule<\n Attributes extends Record<string, any> = Record<string, any>,\n> = {\n default: string;\n metadata: Attributes;\n};\n\nexport type ContentFileLoader = () => Promise<string | ContentFileModule>;\n\n/**\n * Reads a loaded content file. Build-time content modules carry their\n * frontmatter as `metadata`; raw strings from custom loaders are parsed\n * with a lazily loaded frontmatter parser.\n */\nexport async function parseContentFile<\n Attributes extends Record<string, any> = Record<string, any>,\n>(\n file: string | ContentFileModule,\n): Promise<{ content: string; attributes: Attributes }> {\n if (typeof file !== 'string') {\n return { content: file.default, attributes: file.metadata as Attributes };\n }\n\n const { parseRawContentFile } = await import('./parse-raw-content-file');\n return parseRawContentFile<Attributes>(file);\n}\n","import { firstValueFrom, isObservable, Observable } from 'rxjs';\n\ndeclare const Zone: any;\n\nexport async function waitFor<T>(prom: Promise<T> | Observable<T>): Promise<T> {\n if (isObservable(prom)) {\n prom = firstValueFrom(prom);\n }\n\n if (typeof Zone === 'undefined') {\n return prom;\n }\n\n const macroTask = Zone.current.scheduleMacroTask(\n `AnalogContentResolve-${Math.random()}`,\n () => {\n /* noop */\n },\n {},\n () => {\n /* noop */\n },\n );\n return prom.then((p: T) => {\n macroTask.invoke();\n return p;\n });\n}\n","/// <reference types=\"vite/client\" />\n\nimport { inject } from '@angular/core';\nimport { ActivatedRoute } from '@angular/router';\nimport { from, Observable, of } from 'rxjs';\nimport { finalize, map, switchMap, tap } from 'rxjs/operators';\n\nimport { ContentFile } from './content-file';\nimport { ContentRenderer } from './content-renderer';\nimport { CONTENT_LOCALE, withLocaleCandidates } from './content-locale';\nimport { CONTENT_FILES_TOKEN } from './content-files-token';\nimport {\n type ContentFileLoader,\n type ContentFileModule,\n parseContentFile,\n} from './parse-content-file';\nimport { waitFor } from './utils/zone-wait-for';\nimport { RenderTaskService } from './render-task.service';\n\nfunction getContentFile<\n Attributes extends Record<string, any> = Record<string, any>,\n>(\n contentFiles: Record<string, ContentFileLoader>,\n prefix: string,\n slug: string,\n fallback: string,\n renderTaskService: RenderTaskService,\n contentRenderer: ContentRenderer,\n locale?: string | null,\n): Observable<ContentFile<Attributes | Record<string, never>>> {\n // Normalize file keys so both \"/src/content/...\" and \"/<project>/src/content/...\" resolve.\n const normalizedFiles: Record<string, ContentFileLoader> = {};\n for (const [key, resolver] of Object.entries(contentFiles)) {\n const normalizedKey = key\n .replace(/^(?:.*?)\\/content(?=\\/)/, '/src/content')\n .replace(/\\/{2,}/g, '/');\n normalizedFiles[normalizedKey] = resolver;\n }\n\n const base = `/src/content/${prefix}${slug}`.replace(/\\/{2,}/g, '/');\n const candidates = [`${base}.md`, `${base}/index.md`];\n\n const allCandidates = withLocaleCandidates(candidates, locale);\n const matchKey = allCandidates.find((k) => k in normalizedFiles);\n const contentFile = matchKey ? normalizedFiles[matchKey] : undefined;\n const resolvedBase = (matchKey || `${base}.md`).replace(/\\.md$/, '');\n\n if (!contentFile) {\n return of({\n filename: resolvedBase,\n attributes: {},\n slug: '',\n content: fallback,\n toc: [],\n });\n }\n\n const contentTask = renderTaskService.addRenderTask();\n return new Observable<string | ContentFileModule>((observer) => {\n // `waitFor` is a no-op in non-Zone environments (browser without zone.js),\n // so this branch works for both SSR and client. Keeping a single path also\n // avoids Rolldown evaluating `import.meta.env.SSR` at library-build time\n // and eliminating the task-clearing branch, which caused SSR to hang once\n // the content map resolved a real lazy import.\n waitFor(contentFile()).then((content) => {\n observer.next(content);\n observer.complete();\n\n setTimeout(() => renderTaskService.clearRenderTask(contentTask), 10);\n });\n }).pipe(\n switchMap((contentFile) => parseContentFile<Attributes>(contentFile)),\n switchMap(({ content, attributes }) =>\n from(contentRenderer.render(content)).pipe(\n map((rendered) => ({\n filename: resolvedBase,\n slug,\n attributes,\n content,\n toc: rendered.toc ?? [],\n })),\n ),\n ),\n finalize(() => {\n if (import.meta.env.SSR !== true) {\n renderTaskService.clearRenderTask(contentTask);\n }\n }),\n );\n}\n\n/**\n * Retrieves the static content using the provided param and/or prefix.\n *\n * @param param route parameter (default: 'slug')\n * @param fallback fallback text if content file is not found (default: 'No Content Found')\n */\nexport function injectContent<\n Attributes extends Record<string, any> = Record<string, any>,\n>(\n param:\n | string\n | {\n param: string;\n subdirectory: string;\n }\n | {\n customFilename: string;\n } = 'slug',\n fallback = 'No Content Found',\n): Observable<ContentFile<Attributes | Record<string, never>>> {\n const contentFiles = inject(CONTENT_FILES_TOKEN);\n const contentRenderer = inject(ContentRenderer);\n const renderTaskService = inject(RenderTaskService);\n const locale = inject(CONTENT_LOCALE, { optional: true });\n const task = renderTaskService.addRenderTask();\n\n if (typeof param === 'string' || 'param' in param) {\n const prefix = typeof param === 'string' ? '' : `${param.subdirectory}/`;\n const route = inject(ActivatedRoute);\n const paramKey = typeof param === 'string' ? param : param.param;\n return route.paramMap.pipe(\n map((params) => params.get(paramKey)),\n switchMap((slug) => {\n if (slug) {\n return getContentFile<Attributes>(\n contentFiles,\n prefix,\n slug,\n fallback,\n renderTaskService,\n contentRenderer,\n locale,\n );\n }\n return of({\n filename: '',\n slug: '',\n attributes: {},\n content: fallback,\n toc: [],\n });\n }),\n tap(() => renderTaskService.clearRenderTask(task)),\n );\n } else {\n return getContentFile<Attributes>(\n contentFiles,\n '',\n param.customFilename,\n fallback,\n renderTaskService,\n contentRenderer,\n locale,\n ).pipe(tap(() => renderTaskService.clearRenderTask(task)));\n }\n}\n","import { Provider, InjectionToken } from '@angular/core';\nimport { ContentRenderer, NoopContentRenderer } from './content-renderer';\nimport { RenderTaskService } from './render-task.service';\nimport { withContentFileLoader } from './content-file-loader';\nimport { withContentListLoader } from './content-list-loader';\n\nexport interface MarkdownRendererOptions {\n loadMermaid?: () => Promise<typeof import('mermaid')>;\n}\n\nconst CONTENT_RENDERER_PROVIDERS: Provider[] = [\n {\n provide: ContentRenderer,\n useClass: NoopContentRenderer,\n },\n withContentFileLoader(),\n withContentListLoader(),\n];\n\nexport function withMarkdownRenderer(\n options?: MarkdownRendererOptions,\n): Provider {\n return [\n CONTENT_RENDERER_PROVIDERS,\n options?.loadMermaid\n ? [\n {\n provide: MERMAID_IMPORT_TOKEN,\n useFactory: options.loadMermaid,\n },\n ]\n : [],\n ];\n}\n\nexport function provideContent(...features: Provider[]): Provider[] {\n return [\n { provide: RenderTaskService, useClass: RenderTaskService },\n ...features,\n ];\n}\n\nexport const MERMAID_IMPORT_TOKEN: InjectionToken<\n Promise<typeof import('mermaid')>\n> = new InjectionToken<Promise<typeof import('mermaid')>>('mermaid_import');\n","import {\n AfterViewChecked,\n Component,\n inject,\n Input,\n ViewEncapsulation,\n} from '@angular/core';\nimport { DomSanitizer, SafeHtml } from '@angular/platform-browser';\nimport { ActivatedRoute } from '@angular/router';\n\nimport { ContentRenderer } from './content-renderer';\nimport { AnchorNavigationDirective } from './anchor-navigation.directive';\n\n@Component({\n selector: 'analog-markdown-route',\n standalone: true,\n imports: [],\n hostDirectives: [AnchorNavigationDirective],\n preserveWhitespaces: true,\n encapsulation: ViewEncapsulation.None,\n template: `<div [innerHTML]=\"content\" [class]=\"classes\"></div>`,\n})\nexport default class AnalogMarkdownRouteComponent implements AfterViewChecked {\n private sanitizer = inject(DomSanitizer);\n private route = inject(ActivatedRoute);\n contentRenderer: ContentRenderer = inject(ContentRenderer);\n\n protected content: SafeHtml = this.sanitizer.bypassSecurityTrustHtml(\n this.route.snapshot.data['renderedAnalogContent'],\n );\n\n @Input() classes = 'analog-markdown-route';\n\n ngAfterViewChecked(): void {\n this.contentRenderer.enhance();\n }\n}\n","import { isPlatformBrowser } from '@angular/common';\nimport {\n AfterViewChecked,\n Component,\n InputSignal,\n NgZone,\n PLATFORM_ID,\n Signal,\n ViewEncapsulation,\n computed,\n inject,\n input,\n} from '@angular/core';\nimport { takeUntilDestroyed, toSignal } from '@angular/core/rxjs-interop';\nimport { DomSanitizer, SafeHtml } from '@angular/platform-browser';\nimport { ActivatedRoute, Data } from '@angular/router';\nimport { from, Observable, of } from 'rxjs';\nimport { catchError, map, switchMap } from 'rxjs/operators';\n\nimport { AnchorNavigationDirective } from './anchor-navigation.directive';\nimport { ContentRenderer } from './content-renderer';\nimport { MERMAID_IMPORT_TOKEN } from './provide-content';\n\n@Component({\n selector: 'analog-markdown',\n standalone: true,\n hostDirectives: [AnchorNavigationDirective],\n preserveWhitespaces: true,\n encapsulation: ViewEncapsulation.None,\n template: ` <div [innerHTML]=\"htmlContent()\" [class]=\"classes()\"></div> `,\n})\nexport default class AnalogMarkdownComponent implements AfterViewChecked {\n private sanitizer = inject(DomSanitizer);\n private route = inject(ActivatedRoute);\n private zone = inject(NgZone);\n private readonly platformId = inject(PLATFORM_ID);\n private readonly mermaidImport = inject(MERMAID_IMPORT_TOKEN, {\n optional: true,\n });\n private mermaid: typeof import('mermaid') | undefined;\n\n private contentSource: Signal<SafeHtml | string | undefined> = toSignal(\n this.getContentSource(),\n );\n readonly htmlContent: Signal<SafeHtml | string | undefined> = computed(() => {\n const inputContent = this.content();\n\n if (inputContent) {\n return this.sanitizer.bypassSecurityTrustHtml(inputContent as string);\n }\n\n return this.contentSource();\n });\n readonly content: InputSignal<string | object | null | undefined> = input<\n string | object | null\n >();\n readonly classes: InputSignal<string> = input('analog-markdown');\n\n contentRenderer: ContentRenderer = inject(ContentRenderer);\n\n constructor() {\n if (isPlatformBrowser(this.platformId) && this.mermaidImport) {\n // Mermaid can only be loaded on client side\n this.loadMermaid(this.mermaidImport);\n }\n }\n\n getContentSource(): Observable<SafeHtml | string> {\n return this.route.data.pipe(\n map<Data, string>((data) => data['_analogContent'] ?? ''),\n switchMap((contentString) => this.renderContent(contentString)),\n map((content) => this.sanitizer.bypassSecurityTrustHtml(content)),\n catchError((e) => of(`There was an error ${e}`)),\n );\n }\n\n async renderContent(content: string): Promise<string> {\n const rendered = await this.contentRenderer.render(content);\n return rendered.content;\n }\n\n ngAfterViewChecked(): void {\n this.contentRenderer.enhance();\n this.zone.runOutsideAngular(() => this.mermaid?.default.run());\n }\n\n private loadMermaid(mermaidImport: Promise<typeof import('mermaid')>) {\n this.zone.runOutsideAngular(() =>\n // Wrap into an observable to avoid redundant initialization once\n // the markdown component is destroyed before the promise is resolved.\n from(mermaidImport)\n .pipe(takeUntilDestroyed())\n .subscribe((mermaid) => {\n this.mermaid = mermaid;\n this.mermaid.default.initialize({ startOnLoad: false });\n // Explicitly running mermaid as ngAfterViewChecked\n // has probably already been called\n this.mermaid?.default.run();\n }),\n );\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"analogjs-content.mjs","names":[],"sources":["../../src/lib/anchor-navigation.directive.ts","../../src/lib/parse-content-file.ts","../../src/lib/utils/zone-wait-for.ts","../../src/lib/content.ts","../../src/lib/provide-content.ts","../../src/lib/markdown-route.component.ts","../../src/lib/markdown.component.ts"],"sourcesContent":["import { Directive, ElementRef, HostListener, inject } from '@angular/core';\nimport { DOCUMENT, Location } from '@angular/common';\nimport { Router } from '@angular/router';\n\n@Directive({\n selector: '[analogAnchorNavigation]',\n standalone: true,\n})\nexport class AnchorNavigationDirective {\n private readonly document = inject(DOCUMENT);\n private readonly host = inject<ElementRef<HTMLElement>>(ElementRef);\n private readonly location = inject(Location);\n private readonly router = inject(Router);\n\n @HostListener('click', ['$event.target', '$event'])\n handleNavigation(target: EventTarget | null, event?: MouseEvent): boolean {\n if (event && shouldSkipClick(event)) {\n return true;\n }\n\n const element = target instanceof Element ? target.closest('a') : null;\n if (\n element &&\n this.host.nativeElement.contains(element) &&\n isInternalUrl(element, this.document) &&\n hasTargetSelf(element) &&\n !hasDownloadAttribute(element)\n ) {\n const { pathname, search, hash } = element;\n // A `<base>` element makes the browser resolve fragment-only hrefs\n // (e.g. `href=\"#some-id\"`) against the base URL rather than the\n // current document, so `pathname`/`search` come back as the base's\n // rather than the current page's. Fall back to the document's own\n // location in that case, or an in-page anchor link would navigate\n // to the base route and lose the fragment there.\n const isFragmentOnly = element.getAttribute('href')?.startsWith('#');\n const resolvedPathname = isFragmentOnly\n ? this.document.location.pathname\n : pathname;\n const resolvedSearch = isFragmentOnly\n ? this.document.location.search\n : search;\n const url = this.location.normalize(\n `${resolvedPathname}${resolvedSearch}${hash}`,\n );\n this.router.navigateByUrl(url);\n\n return false;\n }\n\n return true;\n }\n}\n\nfunction shouldSkipClick(event: MouseEvent): boolean {\n return (\n event.defaultPrevented ||\n event.button !== 0 ||\n event.ctrlKey ||\n event.metaKey ||\n event.shiftKey ||\n event.altKey\n );\n}\n\nfunction hasDownloadAttribute(anchorElement: HTMLAnchorElement): boolean {\n return anchorElement.getAttribute('download') !== null;\n}\n\nfunction hasTargetSelf(anchorElement: HTMLAnchorElement): boolean {\n return !anchorElement.target || anchorElement.target === '_self';\n}\n\nfunction isInternalUrl(\n anchorElement: HTMLAnchorElement,\n document: Document,\n): boolean {\n return (\n anchorElement.host === document.location.host &&\n anchorElement.protocol === document.location.protocol\n );\n}\n","export type ContentFileModule<\n Attributes extends Record<string, any> = Record<string, any>,\n> = {\n default: string;\n metadata: Attributes;\n};\n\nexport type ContentFileLoader = () => Promise<string | ContentFileModule>;\n\n/**\n * Reads a loaded content file. Build-time content modules carry their\n * frontmatter as `metadata`; raw strings from custom loaders are parsed\n * with a lazily loaded frontmatter parser.\n */\nexport async function parseContentFile<\n Attributes extends Record<string, any> = Record<string, any>,\n>(\n file: string | ContentFileModule,\n): Promise<{ content: string; attributes: Attributes }> {\n if (typeof file !== 'string') {\n return { content: file.default, attributes: file.metadata as Attributes };\n }\n\n const { parseRawContentFile } = await import('./parse-raw-content-file');\n return parseRawContentFile<Attributes>(file);\n}\n","import { firstValueFrom, isObservable, Observable } from 'rxjs';\n\ndeclare const Zone: any;\n\nexport async function waitFor<T>(prom: Promise<T> | Observable<T>): Promise<T> {\n if (isObservable(prom)) {\n prom = firstValueFrom(prom);\n }\n\n if (typeof Zone === 'undefined') {\n return prom;\n }\n\n const macroTask = Zone.current.scheduleMacroTask(\n `AnalogContentResolve-${Math.random()}`,\n () => {\n /* noop */\n },\n {},\n () => {\n /* noop */\n },\n );\n return prom.then((p: T) => {\n macroTask.invoke();\n return p;\n });\n}\n","/// <reference types=\"vite/client\" />\n\nimport { inject } from '@angular/core';\nimport { ActivatedRoute } from '@angular/router';\nimport { from, Observable, of } from 'rxjs';\nimport { finalize, map, switchMap, tap } from 'rxjs/operators';\n\nimport { ContentFile } from './content-file';\nimport { ContentRenderer } from './content-renderer';\nimport { CONTENT_LOCALE, withLocaleCandidates } from './content-locale';\nimport { CONTENT_FILES_TOKEN } from './content-files-token';\nimport {\n type ContentFileLoader,\n type ContentFileModule,\n parseContentFile,\n} from './parse-content-file';\nimport { waitFor } from './utils/zone-wait-for';\nimport { RenderTaskService } from './render-task.service';\n\nfunction getContentFile<\n Attributes extends Record<string, any> = Record<string, any>,\n>(\n contentFiles: Record<string, ContentFileLoader>,\n prefix: string,\n slug: string,\n fallback: string,\n renderTaskService: RenderTaskService,\n contentRenderer: ContentRenderer,\n locale?: string | null,\n): Observable<ContentFile<Attributes | Record<string, never>>> {\n // Normalize file keys so both \"/src/content/...\" and \"/<project>/src/content/...\" resolve.\n const normalizedFiles: Record<string, ContentFileLoader> = {};\n for (const [key, resolver] of Object.entries(contentFiles)) {\n const normalizedKey = key\n .replace(/^(?:.*?)\\/content(?=\\/)/, '/src/content')\n .replace(/\\/{2,}/g, '/');\n normalizedFiles[normalizedKey] = resolver;\n }\n\n const base = `/src/content/${prefix}${slug}`.replace(/\\/{2,}/g, '/');\n const candidates = [`${base}.md`, `${base}/index.md`];\n\n const allCandidates = withLocaleCandidates(candidates, locale);\n const matchKey = allCandidates.find((k) => k in normalizedFiles);\n const contentFile = matchKey ? normalizedFiles[matchKey] : undefined;\n const resolvedBase = (matchKey || `${base}.md`).replace(/\\.md$/, '');\n\n if (!contentFile) {\n return of({\n filename: resolvedBase,\n attributes: {},\n slug: '',\n content: fallback,\n toc: [],\n });\n }\n\n const contentTask = renderTaskService.addRenderTask();\n return new Observable<string | ContentFileModule>((observer) => {\n // `waitFor` is a no-op in non-Zone environments (browser without zone.js),\n // so this branch works for both SSR and client. Keeping a single path also\n // avoids Rolldown evaluating `import.meta.env.SSR` at library-build time\n // and eliminating the task-clearing branch, which caused SSR to hang once\n // the content map resolved a real lazy import.\n waitFor(contentFile()).then((content) => {\n observer.next(content);\n observer.complete();\n\n setTimeout(() => renderTaskService.clearRenderTask(contentTask), 10);\n });\n }).pipe(\n switchMap((contentFile) => parseContentFile<Attributes>(contentFile)),\n switchMap(({ content, attributes }) =>\n from(contentRenderer.render(content)).pipe(\n map((rendered) => ({\n filename: resolvedBase,\n slug,\n attributes,\n content,\n toc: rendered.toc ?? [],\n })),\n ),\n ),\n finalize(() => {\n if (import.meta.env.SSR !== true) {\n renderTaskService.clearRenderTask(contentTask);\n }\n }),\n );\n}\n\n/**\n * Retrieves the static content using the provided param and/or prefix.\n *\n * @param param route parameter (default: 'slug')\n * @param fallback fallback text if content file is not found (default: 'No Content Found')\n */\nexport function injectContent<\n Attributes extends Record<string, any> = Record<string, any>,\n>(\n param:\n | string\n | {\n param: string;\n subdirectory: string;\n }\n | {\n customFilename: string;\n } = 'slug',\n fallback = 'No Content Found',\n): Observable<ContentFile<Attributes | Record<string, never>>> {\n const contentFiles = inject(CONTENT_FILES_TOKEN);\n const contentRenderer = inject(ContentRenderer);\n const renderTaskService = inject(RenderTaskService);\n const locale = inject(CONTENT_LOCALE, { optional: true });\n const task = renderTaskService.addRenderTask();\n\n if (typeof param === 'string' || 'param' in param) {\n const prefix = typeof param === 'string' ? '' : `${param.subdirectory}/`;\n const route = inject(ActivatedRoute);\n const paramKey = typeof param === 'string' ? param : param.param;\n return route.paramMap.pipe(\n map((params) => params.get(paramKey)),\n switchMap((slug) => {\n if (slug) {\n return getContentFile<Attributes>(\n contentFiles,\n prefix,\n slug,\n fallback,\n renderTaskService,\n contentRenderer,\n locale,\n );\n }\n return of({\n filename: '',\n slug: '',\n attributes: {},\n content: fallback,\n toc: [],\n });\n }),\n tap(() => renderTaskService.clearRenderTask(task)),\n );\n } else {\n return getContentFile<Attributes>(\n contentFiles,\n '',\n param.customFilename,\n fallback,\n renderTaskService,\n contentRenderer,\n locale,\n ).pipe(tap(() => renderTaskService.clearRenderTask(task)));\n }\n}\n","import { Provider, InjectionToken } from '@angular/core';\nimport { ContentRenderer, NoopContentRenderer } from './content-renderer';\nimport { RenderTaskService } from './render-task.service';\nimport { withContentFileLoader } from './content-file-loader';\nimport { withContentListLoader } from './content-list-loader';\n\nexport interface MarkdownRendererOptions {\n loadMermaid?: () => Promise<typeof import('mermaid')>;\n}\n\nconst CONTENT_RENDERER_PROVIDERS: Provider[] = [\n {\n provide: ContentRenderer,\n useClass: NoopContentRenderer,\n },\n withContentFileLoader(),\n withContentListLoader(),\n];\n\nexport function withMarkdownRenderer(\n options?: MarkdownRendererOptions,\n): Provider {\n return [\n CONTENT_RENDERER_PROVIDERS,\n options?.loadMermaid\n ? [\n {\n provide: MERMAID_IMPORT_TOKEN,\n useFactory: options.loadMermaid,\n },\n ]\n : [],\n ];\n}\n\nexport function provideContent(...features: Provider[]): Provider[] {\n return [\n { provide: RenderTaskService, useClass: RenderTaskService },\n ...features,\n ];\n}\n\nexport const MERMAID_IMPORT_TOKEN: InjectionToken<\n Promise<typeof import('mermaid')>\n> = new InjectionToken<Promise<typeof import('mermaid')>>('mermaid_import');\n","import {\n AfterViewChecked,\n Component,\n inject,\n Input,\n ViewEncapsulation,\n} from '@angular/core';\nimport { DomSanitizer, SafeHtml } from '@angular/platform-browser';\nimport { ActivatedRoute } from '@angular/router';\n\nimport { ContentRenderer } from './content-renderer';\nimport { AnchorNavigationDirective } from './anchor-navigation.directive';\n\n@Component({\n selector: 'analog-markdown-route',\n standalone: true,\n imports: [],\n hostDirectives: [AnchorNavigationDirective],\n preserveWhitespaces: true,\n encapsulation: ViewEncapsulation.None,\n template: `<div [innerHTML]=\"content\" [class]=\"classes\"></div>`,\n})\nexport default class AnalogMarkdownRouteComponent implements AfterViewChecked {\n private sanitizer = inject(DomSanitizer);\n private route = inject(ActivatedRoute);\n contentRenderer: ContentRenderer = inject(ContentRenderer);\n\n protected content: SafeHtml = this.sanitizer.bypassSecurityTrustHtml(\n this.route.snapshot.data['renderedAnalogContent'],\n );\n\n @Input() classes = 'analog-markdown-route';\n\n ngAfterViewChecked(): void {\n this.contentRenderer.enhance();\n }\n}\n","import { isPlatformBrowser } from '@angular/common';\nimport {\n AfterViewChecked,\n Component,\n InputSignal,\n NgZone,\n PLATFORM_ID,\n Signal,\n ViewEncapsulation,\n computed,\n inject,\n input,\n} from '@angular/core';\nimport { takeUntilDestroyed, toSignal } from '@angular/core/rxjs-interop';\nimport { DomSanitizer, SafeHtml } from '@angular/platform-browser';\nimport { ActivatedRoute, Data } from '@angular/router';\nimport { from, Observable, of } from 'rxjs';\nimport { catchError, map, switchMap } from 'rxjs/operators';\n\nimport { AnchorNavigationDirective } from './anchor-navigation.directive';\nimport { ContentRenderer } from './content-renderer';\nimport { MERMAID_IMPORT_TOKEN } from './provide-content';\n\n@Component({\n selector: 'analog-markdown',\n standalone: true,\n hostDirectives: [AnchorNavigationDirective],\n preserveWhitespaces: true,\n encapsulation: ViewEncapsulation.None,\n template: ` <div [innerHTML]=\"htmlContent()\" [class]=\"classes()\"></div> `,\n})\nexport default class AnalogMarkdownComponent implements AfterViewChecked {\n private sanitizer = inject(DomSanitizer);\n private route = inject(ActivatedRoute);\n private zone = inject(NgZone);\n private readonly platformId = inject(PLATFORM_ID);\n private readonly mermaidImport = inject(MERMAID_IMPORT_TOKEN, {\n optional: true,\n });\n private mermaid: typeof import('mermaid') | undefined;\n\n private contentSource: Signal<SafeHtml | string | undefined> = toSignal(\n this.getContentSource(),\n );\n readonly htmlContent: Signal<SafeHtml | string | undefined> = computed(() => {\n const inputContent = this.content();\n\n if (inputContent) {\n return this.sanitizer.bypassSecurityTrustHtml(inputContent as string);\n }\n\n return this.contentSource();\n });\n readonly content: InputSignal<string | object | null | undefined> = input<\n string | object | null\n >();\n readonly classes: InputSignal<string> = input('analog-markdown');\n\n contentRenderer: ContentRenderer = inject(ContentRenderer);\n\n constructor() {\n if (isPlatformBrowser(this.platformId) && this.mermaidImport) {\n // Mermaid can only be loaded on client side\n this.loadMermaid(this.mermaidImport);\n }\n }\n\n getContentSource(): Observable<SafeHtml | string> {\n return this.route.data.pipe(\n map<Data, string>((data) => data['_analogContent'] ?? ''),\n switchMap((contentString) => this.renderContent(contentString)),\n map((content) => this.sanitizer.bypassSecurityTrustHtml(content)),\n catchError((e) => of(`There was an error ${e}`)),\n );\n }\n\n async renderContent(content: string): Promise<string> {\n const rendered = await this.contentRenderer.render(content);\n return rendered.content;\n }\n\n ngAfterViewChecked(): void {\n this.contentRenderer.enhance();\n this.zone.runOutsideAngular(() => this.mermaid?.default.run());\n }\n\n private loadMermaid(mermaidImport: Promise<typeof import('mermaid')>) {\n this.zone.runOutsideAngular(() =>\n // Wrap into an observable to avoid redundant initialization once\n // the markdown component is destroyed before the promise is resolved.\n from(mermaidImport)\n .pipe(takeUntilDestroyed())\n .subscribe((mermaid) => {\n this.mermaid = mermaid;\n this.mermaid.default.initialize({ startOnLoad: false });\n // Explicitly running mermaid as ngAfterViewChecked\n // has probably already been called\n this.mermaid?.default.run();\n }),\n );\n }\n}\n"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@analogjs/content",
3
- "version": "3.0.0-beta.40",
3
+ "version": "3.0.0-beta.41",
4
4
  "description": "Content Rendering for Analog",
5
5
  "type": "module",
6
6
  "author": "Brandon Roberts <robertsbt@gmail.com>",
@@ -91,8 +91,8 @@
91
91
  "tslib": "^2.3.0"
92
92
  },
93
93
  "devDependencies": {
94
- "@analogjs/vite-plugin-angular": "3.0.0-beta.40",
95
- "@analogjs/vitest-angular": "3.0.0-beta.40",
94
+ "@analogjs/vite-plugin-angular": "3.0.0-beta.41",
95
+ "@analogjs/vitest-angular": "3.0.0-beta.41",
96
96
  "@nx/devkit": "24.0.0"
97
97
  },
98
98
  "ng-update": {
@@ -1,9 +1,10 @@
1
1
  import * as i0 from "@angular/core";
2
2
  export declare class AnchorNavigationDirective {
3
3
  private readonly document;
4
+ private readonly host;
4
5
  private readonly location;
5
6
  private readonly router;
6
- handleNavigation(element: EventTarget | null): boolean;
7
+ handleNavigation(target: EventTarget | null, event?: MouseEvent): boolean;
7
8
  static ɵfac: i0.ɵɵFactoryDeclaration<AnchorNavigationDirective, never>;
8
9
  static ɵdir: i0.ɵɵDirectiveDeclaration<AnchorNavigationDirective, "[analogAnchorNavigation]", never, {}, {}, never, never, true, never>;
9
10
  }