Skip to content

Commit

Permalink
Small thingies (#23)
Browse files Browse the repository at this point in the history
* feat: example extra_js integrity

* feat: auto import type definitions

* fix: cheatsheet-rtl syntax issues

* feat: versioned docs paths validation
  • Loading branch information
HiDeoo authored and julien-deramond committed Mar 24, 2023
1 parent 900315c commit d3e6e81
Show file tree
Hide file tree
Showing 7 changed files with 108 additions and 7 deletions.
4 changes: 2 additions & 2 deletions site-new/src/assets/examples/cheatsheet-rtl/index.astro
Original file line number Diff line number Diff line change
Expand Up @@ -1345,13 +1345,13 @@ export const direction = 'rtl'
</div>

<div>
Example showMarkup={false} code={`
<Example showMarkup={false} code={`
<button type="button" class="btn btn-lg btn-danger" data-bs-toggle="popover" title="عنوان الصندوق المنبثق" data-bs-content="وإليك بعض المحتويات الرائعة. إنه آسر للغاية. أليس كذلك؟">
انقر لعرض/إخفاء الصندوق المنبثق
</button>
`} />

Example showMarkup={false} code={`
<Example showMarkup={false} code={`
<button type="button" class="btn btn-secondary" data-bs-container="body" data-bs-toggle="popover" data-bs-placement="top" data-bs-content="نجمٌ و لكنه ليس في السماء، بل في أعماق البحار و المحيطات!">
انبثاق إلى الأعلى
</button>
Expand Down
2 changes: 0 additions & 2 deletions site-new/src/content/docs/getting-started/introduction.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,6 @@ aliases:
- "/docs/getting-started/"
- "/getting-started/"
toc: true

# TODO: Astro doesn't seem to check bad URLs which is the case with Hugo. Maybe something to configure somewhere?
---

## Quick start
Expand Down
8 changes: 7 additions & 1 deletion site-new/src/layouts/ExamplesLayout.astro
Original file line number Diff line number Diff line change
Expand Up @@ -195,7 +195,13 @@ const htmlProps: HTMLAttributes<'html'> = direction === 'rtl' ? { lang: 'ar', di
<Fragment>
<script is:inline {...getVersionedBsJsProps()} />
{extra_js?.map((js) => (
<script is:inline async={js.async} src={js.src} />
<script
is:inline
async={js.async}
src={js.src}
integrity={js.integrity}
crossorigin={js.integrity ? 'anonymous' : undefined}
/>
))}
</Fragment>
)
Expand Down
34 changes: 33 additions & 1 deletion site-new/src/libs/astro.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,13 @@ import { getConfig } from './config'
import { rehypeBsTable } from './rehype'
import { remarkBsConfig, remarkBsDocsref } from './remark'
import { configurePrism } from './prism'
import { docsDirectory, getDocsFsPath, getDocsPublicFsPath, getDocsStaticFsPath } from './path'
import {
docsDirectory,
getDocsFsPath,
getDocsPublicFsPath,
getDocsStaticFsPath,
validateVersionedDocsPaths,
} from './path'

// A list of directories in `src/components` that contains components that will be auto imported in all pages for
// convenience.
Expand Down Expand Up @@ -69,6 +75,9 @@ export function bootstrap(): AstroIntegration[] {
copyStatic()
aliasStatic()
},
'astro:build:done': ({ dir }) => {
validateVersionedDocsPaths(dir)
},
},
},
// https://github.com/withastro/astro/issues/6475
Expand All @@ -81,6 +90,7 @@ export function bootstrap(): AstroIntegration[] {

function bootstrap_auto_import() {
const autoImportedComponents: string[] = []
const autoImportedComponentDefinitions: string[] = []

for (const autoImportedComponentDirectory of autoImportedComponentDirectories) {
const components = fs.readdirSync(path.join(getDocsFsPath(), 'src/components', autoImportedComponentDirectory), {
Expand All @@ -92,10 +102,32 @@ function bootstrap_auto_import() {
autoImportedComponents.push(
`./${path.posix.join(docsDirectory, 'src/components', autoImportedComponentDirectory, component.name)}`
)

if (component.name.endsWith('.astro')) {
autoImportedComponentDefinitions.push(
`export const ${component.name.replace('.astro', '')}: typeof import('@shortcodes/${
component.name
}').default`
)
}
}
}
}

const autoImportedComponentDefinition = `/**
* DO NOT EDIT THIS FILE MANUALLY.
*
* This file is automatically generated by the Boostrap Astro Integration.
* It contains the type definitions for the components that are auto imported in all pages.
* @see site/src/libs/astro.ts
*/
export declare global {
${autoImportedComponentDefinitions.join('\n ')}
}
`

fs.writeFileSync(path.join(getDocsFsPath(), 'src/types/auto-import.d.ts'), autoImportedComponentDefinition)

return autoImport({
imports: autoImportedComponents,
})
Expand Down
1 change: 1 addition & 0 deletions site-new/src/libs/examples.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ export const exampleFrontmatterSchema = z.object({
extra_js: z
.object({
async: z.boolean().optional(),
integrity: z.string().optional(),
src: z.string(),
})
.array()
Expand Down
46 changes: 45 additions & 1 deletion site-new/src/libs/path.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,45 @@
import fs from 'node:fs'
import path from 'node:path'
import { getConfig } from './config'

// The docs directory path relative to the root of the project.
export const docsDirectory = getConfig().docsDir

// A list of all the docs paths that were generated during a build.
const generatedVersionedDocsPaths: string[] = []

export function getVersionedDocsPath(docsPath: string): string {
const { docs_version } = getConfig()

return `/docs/${docs_version}/${docsPath.replace(/^\//, '')}`
const sanitizedDocsPath = docsPath.replace(/^\//, '')

if (import.meta.env.PROD) {
generatedVersionedDocsPaths.push(sanitizedDocsPath)
}

return `/docs/${docs_version}/${sanitizedDocsPath}`
}

// Validate that all the generated versioned docs paths point to an existing page or asset.
// This is useful to catch typos in docs paths.
// Note: this function is only called during a production build.
// Note: this could at some point be refactored to use Astro list of generated `routes` accessible in the
// `astro:build:done` integration hook. Altho as of 03/14/2023, this is not possible due to the route's data only
// containing informations regarding the last page generated page for dynamic routes.
// @see https://github.com/withastro/astro/issues/5802
export function validateVersionedDocsPaths(distUrl: URL) {
const { docs_version } = getConfig()

for (const docsPath of generatedVersionedDocsPaths) {
const sanitizedDocsPath = sanitizeVersionedDocsPathForValidation(docsPath)
const absoluteDocsPath = path.join(distUrl.pathname, 'docs', docs_version, sanitizedDocsPath)

const docsPathExists = fs.existsSync(absoluteDocsPath)

if (!docsPathExists) {
throw new Error(`A versioned docs path was generated but does not point to a valid page or asset: '${docsPath}'.`)
}
}
}

export function getDocsRelativePath(docsPath: string) {
Expand All @@ -25,3 +57,15 @@ export function getDocsPublicFsPath() {
export function getDocsFsPath() {
return path.join(process.cwd(), docsDirectory)
}

function sanitizeVersionedDocsPathForValidation(docsPath: string) {
// Remove the hash part of the path if any.
let sanitizedDocsPath = docsPath.split('#')[0]

// Append the `index.html` part if the path doesn't have an extension.
if (!sanitizedDocsPath.includes('.')) {
sanitizedDocsPath = path.join(sanitizedDocsPath, 'index.html')
}

return sanitizedDocsPath
}
20 changes: 20 additions & 0 deletions site-new/src/types/auto-import.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
/**
* DO NOT EDIT THIS FILE MANUALLY.
*
* This file is automatically generated by the Boostrap Astro Integration.
* It contains the type definitions for the components that are auto imported in all pages.
* @see site/src/libs/astro.ts
*/
export declare global {
export const AddedIn: typeof import('@shortcodes/AddedIn.astro').default
export const BsTable: typeof import('@shortcodes/BsTable.astro').default
export const Callout: typeof import('@shortcodes/Callout.astro').default
export const CalloutDeprecatedDarkVariants: typeof import('@shortcodes/CalloutDeprecatedDarkVariants.astro').default
export const Code: typeof import('@shortcodes/Code.astro').default
export const DeprecatedIn: typeof import('@shortcodes/DeprecatedIn.astro').default
export const Example: typeof import('@shortcodes/Example.astro').default
export const JsDismiss: typeof import('@shortcodes/JsDismiss.astro').default
export const Placeholder: typeof import('@shortcodes/Placeholder.astro').default
export const ScssDocs: typeof import('@shortcodes/ScssDocs.astro').default
export const Table: typeof import('@shortcodes/Table.astro').default
}

0 comments on commit d3e6e81

Please sign in to comment.