docs(core): restructure & update intro page

Co-authored-by: Isaac Mann <isaacplmann@gmail.com>
This commit is contained in:
Juri 2023-08-02 15:08:10 +02:00 committed by Juri Strumpflohner
parent 90ca436d81
commit dd377d4597
21 changed files with 1123 additions and 144 deletions

View File

@ -201,7 +201,7 @@ Yarn related information.
##### Youtube
Embed a YouTube video directly with the following shortcode, control the title and the associated width.
Embed a YouTube video directly with the following shortcode, control the title and the associated width. `src` can be the Youtube URL from the browser, the "share" button (short YT url) or the embed URL.
```markdown
{% youtube

View File

@ -4,16 +4,21 @@
Here are some of our feature highlights:
{% cards cols="2" %}
{% card title="Combine the Power of Nx Graph and Nx Console" type="video" url="https://youtu.be/ZST_rmhzRXI" /%}
{% /cards %}
{% youtube
src="https://youtu.be/ZST_rmhzRXI"
title="Nx Console Run UI Form"
width="100%" /%}
## Breaking Changes
Use [the `nx migrate` command](/core-features/automate-updating-dependencies) to automatically account for these breaking changes.
{% cards cols="2" %}
{% cards cols="1" smCols="2" mdCols="3" %}
{% card title="Removed UMD format support for rollup" type="external" url="https://github.com/nrwl/nx/pull/12426" /%}
{% card title="Removed --only-failed option" type="external" url="https://github.com/nrwl/nx/pull/12471" /%}
{% card title="Infer projects from package.json and project.json" description="Nx will now also include folders with package.json/project.json in its graph of projects. You can ignore any unwanted projects by adding the directory to .nxignore." type="external" url="https://github.com/nrwl/nx/releases/tag/15.0.0" /%}
{% /cards %}

View File

@ -8,7 +8,7 @@ title="What&#39;s new in Nx 15.3?"
/%}
Here are some of our feature highlights:
{% cards cols="2" %}
{% cards cols="1" smCols="2" mdCols="2" lgCols="3" %}
{% card title="Introducing the Nx Task Graph Visualization" type="video" url="https://youtu.be/wOE3r4299fs" /%}
{% card title="Standalone Applications with Nx" type="video" url="https://youtu.be/qEaVzh-oBBc" /%}
{% card title="Add Nx to any Project" type="video" url="https://youtu.be/VmGCZ77ao_I" /%}

View File

@ -9,6 +9,6 @@ title="Nx 15.4 is out! Here&#39;s all you need to know"
Here are some of our feature highlights:
{% cards cols="2" %}
{% cards cols="2" smCol="2" mdCol="2" lgCol="2" %}
{% card title="One Command to Run Multiple Tasks in Parallel" type="video" url="https://youtu.be/ROTO89i5m_4" /%}
{% /cards %}

View File

@ -33,7 +33,7 @@
"disableCollapsible": false
},
{
"name": "5 min Tutorials",
"name": "Tutorials",
"path": "/getting-started/tutorials",
"id": "tutorials",
"isExternal": false,
@ -109,7 +109,7 @@
"disableCollapsible": false
},
{
"name": "5 min Tutorials",
"name": "Tutorials",
"path": "/getting-started/tutorials",
"id": "tutorials",
"isExternal": false,

View File

@ -37,7 +37,7 @@
},
{
"id": "tutorials",
"name": "5 min Tutorials",
"name": "Tutorials",
"description": "Get started with basic information, concepts and tutorials.",
"file": "",
"itemList": [
@ -133,7 +133,7 @@
},
"/getting-started/tutorials": {
"id": "tutorials",
"name": "5 min Tutorials",
"name": "Tutorials",
"description": "Get started with basic information, concepts and tutorials.",
"file": "",
"itemList": [

View File

@ -29,7 +29,7 @@
"file": "shared/getting-started/why-nx"
},
{
"name": "5 min Tutorials",
"name": "Tutorials",
"id": "tutorials",
"description": "Get started with basic information, concepts and tutorials.",
"itemList": [

View File

@ -1,5 +1,10 @@
# What is Nx Cloud?
{% youtube
src="https://www.youtube.com/embed/NZF0ZJpgaJM?si=1KJRAWJJmfw9c0c0"
title="What is Nx Cloud?"
width="100%" /%}
Nx partitions a command into smaller tasks and runs them in parallel, in the correct order. Nx Cloud takes it one step further and [runs any command across multiple machines](/core-features/distribute-task-execution), while giving you a consolidated view of the command as if it ran locally.
Nx caches the output of any previously run command such as testing and building, so it can replay the cached results instead of rerunning it. Nx Cloud allows you to [share the computation cache](/core-features/remote-cache) across everyone in your team and CI.

View File

@ -1,100 +1,91 @@
# Intro to Nx
Nx is a powerful open-source build system that provides tools and techniques for enhancing developer productivity, optimizing CI performance, and maintaining code quality. Find out more about [why you should use Nx](/getting-started/why-nx).
Nx is a powerful open-source build system that provides tools and techniques for enhancing developer productivity, optimizing CI performance, and maintaining code quality. [Check out our video](/getting-started/why-nx) to learn more about what Nx is about.
If instead you want to jump right into it, run the following command. It will guide you through the setup:
## Core Features
{% tabs %}
{% tab label="npm" %}
- **Run Tasks Efficiently**: Nx [runs tasks in parallel](/core-features/run-tasks) and orders the tasks based on the dependencies between them.
- **Cache Locally & Remotely**: With [local](/core-features/cache-task-results) and [remote caching](/core-features/remote-cache), Nx prevents unnecessary re-runs of tasks, saving you valuable dev time.
- **Automate Dependency Updates**: if you leverage Nx plugins you gain additional features such as [code generation](/core-features/plugin-features/use-code-generators) and tools to [automatically upgrade](core-features/automate-updating-dependencies) your codebase and dependencies.
- **Make it Your Own**: Nx is highly customizable and extensible. Fine-tune it by [creating your own plugins](/extending-nx/intro/getting-started) and optionally [share them with the community](/extending-nx/tutorials/publish-plugin#publish-your-nx-plugin).
<!-- - **Monorepo and Single Projects**: Nx supports both, monorepos as well as single-project (standalone) workspaces. -->
Find out more about [why you should use Nx](/getting-started/why-nx) or browse our [core features](/core-features).
## Try Nx Yourself!
```shell
npx create-nx-workspace
npx create-nx-workspace@latest
```
{% /tab %}
{% tab label="yarn" %}
## Learn Nx
```shell
npx create-nx-workspace --pm yarn
```
{% cards cols="2" lgCols="6" mdCols="4" smCols="2" %}
{% /tab %}
{% tab label="pnpm" %}
{% link-card title="Nx in 10 minutes!" type="video" url="https://youtu.be/-_4WMl-Fn0w" icon="nx" /%}
```shell
npx create-nx-workspace --pm pnpm
```
{% link-card title="What is Nx Cloud?" type="video" url="https://youtu.be/NZF0ZJpgaJM" icon="nxcloud" /%}
{% /tab %}
{% /tabs %}
{% link-card title="PNPM Monorepos with Nx" type="video" url="https://youtu.be/ngdoUQBvAjo" icon="pnpm" /%}
You can use Nx to quickly scaffold a new project or even an entire monorepo. It can be incrementally adopted and will grow with your project as it scales.
{% cards cols="3" %}
{% title-card title="New Monorepo" url="#get-started-with-the-basics" /%}
{% title-card title="Choose a Stack" url="#learn-about-nx-and-your-favorite-stack" /%}
{% title-card title="Add to an Existing Project" url="#adding-nx-to-an-existing-project" /%}
{% link-card title="More On Youtube" type="video" url="https://www.youtube.com/@nxdevtools" icon="youtube" /%}
{% /cards %}
## Get Started with the Basics
{% cards cols="2" lgCols="6" mdCols="5" smCols="2" %}
Its modular architecture lets you adopt Nx for package-based monorepos in combination with NPM, Yarn or PNPM, or create a fully integrated monorepo using Nx plugins. Learn more with the tutorials below.
{% link-card title="Package Based Monorepos" type="tutorial" url="/getting-started/tutorials/package-based-repo-tutorial" icon="jsMono" /%}
{% personas %}
{% persona type="javascript" title="New Package-Based Repo" url="/getting-started/tutorials/package-based-repo-tutorial" %}
Create a monorepo with Yarn, NPM or PNPM. Nx makes it fast, but lets you run things your way.
{% link-card title="Integrated Monorepos" type="tutorial" url="/getting-started/tutorials/integrated-repo-tutorial" icon="nx" /%}
- [Get started with your package-based repo](/getting-started/tutorials/package-based-repo-tutorial)
{% link-card title="Single React App" type="tutorial" url="/getting-started/tutorials/react-standalone-tutorial" icon="react" /%}
{% /persona %}
{% link-card title="Single Angular App" type="tutorial" url="/getting-started/tutorials/angular-standalone-tutorial" icon="angular" /%}
{% persona type="integrated" title="New Integrated Repo" url="/getting-started/tutorials/integrated-repo-tutorial" %}
{% link-card title="Single Node App" type="tutorial" url="/getting-started/tutorials/node-server-tutorial" icon="node" /%}
Get a pre-configured setup. Nx configures your favorite frameworks and lets you focus on shipping features.
<!-- {% link-card title="React Monorepo" type="tutorial" url="/getting-started/tutorials/react-standalone-tutorial" icon="reactMono" /%}
- [Get started with your integrated repo](/getting-started/tutorials/integrated-repo-tutorial)
{% link-card title="Angular Monorepo" type="tutorial" url="/getting-started/tutorials/angular-standalone-tutorial" icon="angularMono" /%}
{% /persona %}
{% /personas %}
{% link-card title="Node Monorepo" type="tutorial" url="/getting-started/tutorials/node-server-tutorial" icon="nodeMono" /%} -->
{% /cards %}
## Learn About Nx and Your Favorite Stack
## Pick Your Stack!
Nx works well not just for monorepos. Nx plugins help you scaffold new projects with pre-configured tooling and modularize your codebase with local libraries.
{% cards cols="3" lgCols="8" mdCols="6" smCols="5" moreLink="/showcase/example-repos" %}
{% cards cols="3" %}
{% link-card title="Express" appearance="small" url="/packages/express" icon="express" /%}
{% link-card title="Vue" appearance="small" url="/showcase/example-repos/add-vue" icon="vue" /%}
{% link-card title="Next" appearance="small" url="/packages/next" icon="nextjs" /%}
{% link-card title="Nuxt" appearance="small" url="/showcase/example-repos/add-nuxt" icon="nuxt" /%}
{% link-card title="Nest" appearance="small" url="/packages/nest" icon="nestjs" /%}
{% link-card title="Remix" appearance="small" url="/recipes/react/remix" icon="remix" /%}
{% link-card title="Expo" appearance="small" url="/packages/expo" icon="expo" /%}
{% link-card title="React Native" appearance="small" url="/packages/react-native" icon="react" /%}
{% link-card title="Fastify" appearance="small" url="/showcase/example-repos/mongo-fastify" icon="fastify" /%}
{% link-card title="Deno" appearance="small" url="https://github.com/nrwl/nx-labs/tree/main/packages/deno" icon="deno" /%}
{% link-card title="Svelte" appearance="small" url="/showcase/example-repos/add-svelte" icon="svelte" /%}
{% link-card title="Solid" appearance="small" url="/showcase/example-repos/add-solid" icon="solid" /%}
{% link-card title="Lit" appearance="small" url="/showcase/example-repos/add-lit" icon="lit" /%}
{% link-card title="Astro" appearance="small" url="/showcase/example-repos/add-astro" icon="astro" /%}
{% link-card title="Qwik" appearance="small" url="/showcase/example-repos/add-qwik" icon="qwik" /%}
{% persona type="react" title="Create a React app" url="/getting-started/tutorials/react-standalone-tutorial" %}
A modern React setup with built-in support for Vite, ESLint, Cypress, and more. Think CRA but modern, always up-to-date and scalable.
- [Create a React app](/getting-started/tutorials/react-standalone-tutorial)
{% /persona %}
{% persona type="angular" title="Create an Angular app" url="/getting-started/tutorials/angular-standalone-tutorial" %}
A modern Angular development experience powered by advanced generators and integrations with modern tooling.
- [Create an Angular app](/getting-started/tutorials/angular-standalone-tutorial)
{% /persona %}
{% persona type="node" title="Create a Node server" url="/getting-started/tutorials/node-server-tutorial" %}
A modern Node server with scaffolding for Express, Fastify or Koa. There's also Docker support built-in.
- [Create a Node server](/getting-started/tutorials/node-server-tutorial)
{% /persona %}
{% link-card title="Rust" appearance="small" url="/showcase/example-repos/add-rust" icon="rust" /%}
{% link-card title="Go" appearance="small" url="https://github.com/nrwl/nx-recipes/blob/main/go/README.md" icon="go" /%}
{% link-card title=".NET" appearance="small" url="https://github.com/nrwl/nx-recipes/tree/main/dot-net-standalone" icon="dotnet" /%}
{% link-card title="Cypress" appearance="small" url="/packages/cypress" icon="cypress" /%}
{% link-card title="Playwright" appearance="small" url="/packages/playwright" icon="playwright" /%}
{% link-card title="Vite" appearance="small" url="/packages/vite" icon="vite" /%}
{% link-card title="Storybook" appearance="small" url="/packages/storybook" icon="storybook" /%}
{% link-card title="Jest" appearance="small" url="/packages/jest" icon="jest" /%}
{% link-card title="Rspack" appearance="small" url="packages/rspack" icon="rspack" /%}
{% /cards %}
## Adding Nx to an Existing Project
## Have an Existing Project? Add Nx to it!
If you have an existing project and want to adopt Nx or migrate to Nx just run the following command which guides you through the migration process:
@ -104,22 +95,23 @@ npx nx@latest init
Alternatively, here are some recipes that give you more details based on the technology stack you're using:
{% cards cols="2" %}
{% cards cols="2" mdCols="4" smCols="2" moreLink="/recipes/adopting-nx" %}
{% persona type="extend" title="Add to Existing Monorepo" url="/recipes/adopting-nx/adding-to-monorepo" %}
Add Nx to your existing NPM/YARN/PNPM workspace
{% /persona %}
{% link-card title="Add to Existing Monorepo" appearance="small" url="/recipes/adopting-nx/adding-to-monorepo" icon="pnpm" /%}
{% persona title="Add to any Project" type="extend" url="/recipes/adopting-nx/adding-to-existing-project" %}
Add Nx to a project
{% /persona %}
{% link-card title="Add to Any Project" appearance="small" url="/recipes/adopting-nx/adding-to-existing-project" icon="nx" /%}
{% persona title="Migrate from CRA" type="react" url="/recipes/react/migration-cra" %}
Migrate from a CRA setup and automatically switch to Vite
{% /persona %}
{% link-card title="Migrate from CRA" appearance="small" url="/recipes/react/migration-cra" icon="cra" /%}
{% persona title="Migrate from Angular CLI" type="angular" url="/recipes/angular/migration/angular" %}
Automatically migrate from the Angular CLI
{% /persona %}
{% link-card title="Migrate from Angular CLI" appearance="small" url="/recipes/angular/migration/angular" icon="angular" /%}
{% /cards %}
## Connect With Us
Connect on our channels and with the Nx Community to ask questions, get help and keep up to date with the latest news.
- Join our [Discord Community](http://go.nx.dev/community)
- Subscribe to our [Youtube Channel](https://www.youtube.com/@nxdevtools)
- Follow us on [Twitter](https://twitter.com/nxdevtools)
- Subscribe [to our tech newsletter](https://go.nrwl.io/nx-newsletter)

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 78 KiB

Binary file not shown.

View File

@ -2,12 +2,12 @@
Nx plugins contain [generators](/core-features/plugin-features/use-code-generators) and [executors](/core-features/plugin-features/use-task-executors) that extend the capabilities of an Nx workspace. They can be shared as npm packages or referenced locally within the same repo.
{% cards cols="2" %}
{% cards cols="4" %}
{% title-card title="Use a Plugin" url="#use-a-plugin" /%}
{% title-card title="Create a Local Plugin" url="#create-a-local-plugin" /%}
{% title-card title="Maintain a Published Plugin" url="#maintain-a-published-plugin" /%}
{% title-card title="Advanced Plugins" url="#advanced-plugins" /%}
{% link-card title="Use a Plugin" url="#use-a-plugin" /%}
{% link-card title="Create a Plugin" url="#create-a-local-plugin" /%}
{% link-card title="Maintain a Published Plugin" url="#maintain-a-published-plugin" /%}
{% link-card title="Advanced Plugins" url="#advanced-plugins" /%}
{% /cards %}

View File

@ -2,11 +2,11 @@
The code for this example is available on GitHub:
{% github-repository url="https://github.com/nrwl/nx-recipes/tree/main/solidjs" %}
{% github-repository url="https://github.com/nrwl/nx-recipes/tree/main/solidjs" /%}
**Supported Features**
Because we are not using an Nx plugin for Solid, there are few items we'll have to configure manually. We'll have to
Because we are not using an Nx plugin for Solid, there are a few items we'll have to configure manually. We'll have to
configure our own build system. There are no pre-created Solid-specific code generators. And we'll have to take care of
updating any framework dependencies as needed.

View File

@ -4,7 +4,7 @@
- [Intro to Nx](/getting-started/intro)
- [Installation](/getting-started/installation)
- [Why Nx?](/getting-started/why-nx)
- [5 min Tutorials](/getting-started/tutorials)
- [Tutorials](/getting-started/tutorials)
- [Package-Based Monorepo](/getting-started/tutorials/package-based-repo-tutorial)
- [Integrated Monorepo](/getting-started/tutorials/integrated-repo-tutorial)
- [React Standalone](/getting-started/tutorials/react-standalone-tutorial)

View File

@ -116,3 +116,24 @@ iframe[src*='youtube'] {
opacity: 1;
visibility: visible;
}
/* Dark mode */
html.dark .adaptive-icon {
/* fill: white; */
filter: invert(1);
}
.adaptive-icon {
fill: black;
}
/* [data-theme='light'] .adaptive-icon {
fill: white;
} */
/* Light mode */
/* @media (prefers-color-scheme: light) {
.adaptive-icon {
fill: #000000;
}
} */

View File

@ -17,8 +17,8 @@ import { CustomLink } from './lib/nodes/link.component';
import { link } from './lib/nodes/link.schema';
import { Callout } from './lib/tags/callout.component';
import { callout } from './lib/tags/callout.schema';
import { Card, Cards, TitleCard } from './lib/tags/cards.component';
import { card, cards, titleCard } from './lib/tags/cards.schema';
import { Card, Cards, LinkCard } from './lib/tags/cards.component';
import { card, cards, linkCard } from './lib/tags/cards.schema';
import { GithubRepository } from './lib/tags/github-repository.component';
import { githubRepository } from './lib/tags/github-repository.schema';
import { StackblitzButton } from './lib/tags/stackblitz-button.component';
@ -43,6 +43,7 @@ import {
terminalVideo,
} from './lib/tags/terminal-video.component';
import { VideoLink, videoLink } from './lib/tags/video-link.component';
// import { SvgAnimation, svgAnimation } from './lib/tags/svg-animation.component';
import { Pill } from './lib/tags/pill.component';
import { pill } from './lib/tags/pill.schema';
@ -63,6 +64,7 @@ export const getMarkdocCustomConfig = (
callout,
card,
cards,
'link-card': linkCard,
'github-repository': githubRepository,
'stackblitz-button': stackblitzButton,
graph,
@ -75,16 +77,17 @@ export const getMarkdocCustomConfig = (
'side-by-side': sideBySide,
tab,
tabs,
'title-card': titleCard,
youtube,
'terminal-video': terminalVideo,
'video-link': videoLink,
// 'svg-animation': svgAnimation,
},
},
components: {
Callout,
Card,
Cards,
LinkCard,
CustomLink,
Fence,
GithubRepository,
@ -100,10 +103,10 @@ export const getMarkdocCustomConfig = (
SideBySide,
Tab,
Tabs,
TitleCard,
YouTube,
TerminalVideo,
VideoLink,
// SvgAnimation,
},
});

File diff suppressed because one or more lines are too long

View File

@ -4,29 +4,110 @@ import {
DocumentIcon,
PlayCircleIcon,
} from '@heroicons/react/24/outline';
import { frameworkIcons } from '../icons';
import { cx } from '@nx/nx-dev/ui-primitives';
import { ReactNode } from 'react';
export function Cards({
cols = 2,
smCols = 3,
mdCols = 4,
lgCols = 4,
children,
moreLink,
}: {
cols: number;
smCols: number;
mdCols: number;
lgCols: number;
children: ReactNode;
moreLink?: string;
}): JSX.Element {
const gridColums: { [key: number]: string } = {
1: 'lg:grid-cols-1',
2: 'lg:grid-cols-2',
3: 'lg:grid-cols-3',
4: 'lg:grid-cols-4',
const calcCols = (cols: number, size: '' | 'lg' | 'md' | 'sm') => {
if (size === '') return `grid-cols-${cols}`;
return `${size}:grid-cols-${cols}`;
};
// <div className="mt-8 grid grid-cols-2 lg:grid-cols-5 md:grid-cols-3 sm:grid-cols-2 gap-4">
return (
<div className={`mt-8 grid grid-cols-1 gap-4 ${gridColums[cols]}`}>
<div
className={`mt-8 grid gap-4 ${calcCols(cols, '')} ${calcCols(
smCols,
'sm'
)} ${calcCols(mdCols, 'md')} ${calcCols(lgCols, 'lg')}`}
>
{children}
{moreLink && (
<div className="flex justify-end mt-2 col-span-full">
<a
className="transition-all duration-200 ease-in-out flex items-center no-underline text-sm px-4 py-0 border-transparent hover:text-slate-900 dark:hover:text-sky-400 whitespace-nowrap font-semibold group"
href={moreLink}
>
Browse more
<span
className="pl-1 transition-all duration-200 ease-in-out group-hover:translate-x-1"
aria-hidden="true"
>
</span>
</a>
</div>
)}
</div>
);
}
export function LinkCard({
title,
type,
icon,
url,
appearance = 'default',
}: {
title: string;
type: string;
icon: string; // `icon` is the link to the SVG file
url: string;
appearance?: 'default' | 'small';
}): JSX.Element {
return (
<a
key={title}
href={url}
className="no-prose relative col-span-1 flex flex-col items-center rounded-md border border-slate-200 bg-slate-50/40 p-4 text-center font-semibold shadow-sm transition focus-within:ring-2 focus-within:ring-blue-500 focus-within:ring-offset-2 hover:bg-slate-100 dark:border-slate-800/40 dark:bg-slate-800/60 dark:hover:bg-slate-800"
style={{ textDecorationLine: 'none' }}
>
{icon && (
<div
className={cx(
'flex items-center justify-center w-24 h-24 rounded-lg mb-2',
{
'h-12 w-12': appearance === 'small',
}
)}
>
{icon && frameworkIcons[icon]?.image}
</div>
)}
<div className={cx('pt-4', { 'pt-2': appearance === 'small' })}>
{appearance === 'small' && type ? null : (
<div className="text-xs font-medium text-slate-600 dark:text-slate-300 uppercase mb-1">
{type}
</div>
)}
<h3
className={cx(
'text-lg font-semibold text-slate-900 dark:text-white m-0',
{ 'text-sm font-normal': appearance === 'small' }
)}
>
{title}
</h3>
</div>
</a>
);
}
export function Card({
description,
title,
@ -79,23 +160,3 @@ export function Card({
</div>
);
}
export function TitleCard({
title,
url,
}: {
title: string;
url: string;
}): JSX.Element {
return (
<a
key={title}
href={url}
className="relative col-span-1 flex items-center rounded-md border border-slate-200 bg-slate-50/40 p-4 text-left text-lg font-semibold shadow-sm transition focus-within:ring-2 focus-within:ring-blue-500 focus-within:ring-offset-2 hover:bg-slate-50 dark:border-slate-800/40 dark:bg-slate-800/60 dark:hover:bg-slate-800 lg:justify-center lg:text-center"
style={{ textDecorationLine: 'none' }}
>
<span className="absolute inset-0" />
{title}
</a>
);
}

View File

@ -5,7 +5,49 @@ export const cards: Schema = {
attributes: {
cols: {
type: 'Number',
description: 'The number of colums per row',
required: true,
},
smCols: {
type: 'Number',
required: true,
},
mdCols: {
type: 'Number',
required: true,
},
lgCols: {
type: 'Number',
required: true,
},
moreLink: {
type: 'String',
required: false,
},
},
};
export const linkCard: Schema = {
render: 'LinkCard',
attributes: {
title: {
type: 'String',
required: true,
},
type: {
type: 'String',
required: true,
},
icon: {
type: 'String',
required: false,
},
url: {
type: 'String',
default: '',
},
appearance: {
type: 'String',
default: 'default',
},
},
};
@ -31,16 +73,3 @@ export const card: Schema = {
},
},
};
export const titleCard: Schema = {
render: 'TitleCard',
attributes: {
title: {
type: 'String',
required: true,
},
url: {
type: 'String',
required: true,
},
},
};

View File

@ -23,6 +23,29 @@ export const youtube: Schema = {
},
};
function computeEmbedURL(youtubeURL: string) {
let match;
if (youtubeURL.indexOf('embed') > -1) {
// we already have the embed URL, so just ignore
return youtubeURL;
}
// Check for 'https://www.youtube.com/watch?v=' format
match = youtubeURL.match(/youtube\.com\/watch\?v=([a-zA-Z0-9_-]+)/);
if (match && match[1]) {
return 'https://www.youtube.com/embed/' + match[1];
}
// Check for 'https://youtu.be/' format
match = youtubeURL.match(/youtu\.be\/([a-zA-Z0-9_-]+)/);
if (match && match[1]) {
return 'https://www.youtube.com/embed/' + match[1];
}
throw new Error(`Could not properly compute the embed URL for ${youtubeURL}`);
}
export function YouTube(props: {
title: string;
caption: string;
@ -34,7 +57,7 @@ export function YouTube(props: {
{' '}
{/* Center alignment applied to the container */}
<iframe
src={props.src}
src={computeEmbedURL(props.src)}
title={props.title}
width={props.width || '100%'}
allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture; fullscreen"

View File

@ -37,7 +37,7 @@ function removeAnchors(linkPath: string): string {
function extractAllLinks(basePath: string): Record<string, string[]> {
return glob.sync(`${basePath}/**/*.md`).reduce((acc, path) => {
const fileContents = readFileContents(path);
const cardLinks = (fileContents.match(/url="(.*)"/g) || []).map((v) =>
const cardLinks = (fileContents.match(/url="(.*?)"/g) || []).map((v) =>
v.slice(5, -1)
);
const links = parseLinks(fileContents)