메인 컨텐츠로 이동
Version: 2.0.0-beta.15

Lifecycle API

During the build, plugins are loaded in parallel to fetch their own contents and render them to routes. Plugins may also configure webpack or post-process the generated files.

async loadContent()

Plugins should use this lifecycle to fetch from data sources (filesystem, remote API, headless CMS, etc.) or do some server processing. The return value is the content it needs.

For example, this plugin below return a random integer between 1 to 10 as content.

docusaurus-plugin/src/index.js
module.exports = function (context, options) {
return {
name: 'docusaurus-plugin',
async loadContent() {
return 1 + Math.floor(Math.random() * 10);
},
};
};

async contentLoaded({content, actions})

The data that was loaded in loadContent will be consumed in contentLoaded. It can be rendered to routes, registered as global data, etc.

content

contentLoaded will be called after loadContent is done. The return value of loadContent() will be passed to contentLoaded as content.

actions

actions은 세 가지 함수를 포함하고 있습니다.

addRoute(config: RouteConfig): void

웹 사이트에 추가할 경로를 만듭니다.

interface RouteConfig {
path: string;
component: string;
modules?: RouteModule;
routes?: RouteConfig[];
exact?: boolean;
priority?: number;
}
interface RouteModule {
[module: string]: Module | RouteModule | RouteModule[];
}
type Module =
| {
path: string;
__import?: boolean;
query?: ParsedUrlQueryInput;
}
| string;

createData(name: string, data: any): Promise<string>

A declarative callback to create static data (generally JSON or string) which can later be provided to your routes as props. Takes the file name and data to be stored, and returns the actual data file's path.

For example, this plugin below creates a /friends page which displays Your friends are: Yangshun, Sebastien:

website/src/components/Friends.js
import React from 'react';

export default function FriendsComponent({friends}) {
return <div>Your friends are {friends.join(',')}</div>;
}
docusaurus-friends-plugin/src/index.js
export default function friendsPlugin(context, options) {
return {
name: 'docusaurus-friends-plugin',
async contentLoaded({content, actions}) {
const {createData, addRoute} = actions;
// Create friends.json
const friends = ['Yangshun', 'Sebastien'];
const friendsJsonPath = await createData(
'friends.json',
JSON.stringify(friends),
);

// Add the '/friends' routes, and ensure it receives the friends props
addRoute({
path: '/friends',
component: '@site/src/components/Friends.js',
modules: {
// propName -> JSON file path
friends: friendsJsonPath,
},
exact: true,
});
},
};
}

setGlobalData(data: any): void

This function permits one to create some global plugin data that can be read from any page, including the pages created by other plugins, and your theme layout.

This data becomes accessible to your client-side/theme code through the useGlobalData and usePluginData hooks.

caution

전역 데이터는 말 그대로 전역적인 특성을 가집니다. 여러분의 사이트 모든 페이지 로딩 시간에 영향을 미칠 수 있으므로 작은 크기로 유지하기를 권장합니다. 가능하면 createData를 활용하거나 각 페이지 데이터를 사용하세요.

For example, this plugin below creates a /friends page which displays Your friends are: Yangshun, Sebastien:

website/src/components/Friends.js
import React from 'react';
import {usePluginData} from '@docusaurus/useGlobalData';

export default function FriendsComponent() {
const {friends} = usePluginData('my-friends-plugin');
return <div>Your friends are {friends.join(',')}</div>;
}
docusaurus-friends-plugin/src/index.js
export default function friendsPlugin(context, options) {
return {
name: 'docusaurus-friends-plugin',
async contentLoaded({content, actions}) {
const {setGlobalData, addRoute} = actions;
// Create friends global data
setGlobalData({friends: ['Yangshun', 'Sebastien']});

// Add the '/friends' routes
addRoute({
path: '/friends',
component: '@site/src/components/Friends.js',
exact: true,
});
},
};
}

configureWebpack(config, isServer, utils, content)

내부 웹팩 설정을 수정합니다. 반환되는 값이 자바스크립트 오브젝트라면 webpack-merge를 사용해 마지막 설정과 합쳐집니다. If it is a function, it will be called and receive config as the first argument and an isServer flag as the second argument.

caution

configureWebpack API는 조만간 (configureWebpack({config, isServer, utils, content})) 오브젝트 형태로 수정될 겁니다.

config

configureWebpack은 클라이언트/서버 빌드 시 만들어지는 config를 사용합니다. 전달된 config를 기본으로 적절하게 다른 설정과 합치는 작업을 진행할 수 있습니다.

isServer

configureWebpack은 서버와 클라이언트 빌드 시 호출됩니다. 서버 빌드 시에는 true값을 받고 클라이언트 빌드 시에는 false 값을 받아 isServer 인자값으로 사용합니다.

utils

configureWebpack은 util 오브젝트를 인자로 받을 수 있습니다.

  • getStyleLoaders(isServer: boolean, cssOptions: {[key: string]: any}): Loader[]
  • getJSLoader(isServer: boolean, cacheOptions?: {}): Loader | null

조건에 따라 웹팩 설정을 받기 위해 사용할 수 있습니다.

For example, this plugin below modify the webpack config to transpile .foo files.

docusaurus-plugin/src/index.js
module.exports = function (context, options) {
return {
name: 'custom-docusaurus-plugin',
configureWebpack(config, isServer, utils) {
const {getCacheLoader} = utils;
return {
module: {
rules: [
{
test: /\.foo$/,
use: [getCacheLoader(isServer), 'my-custom-webpack-loader'],
},
],
},
};
},
};
};

content

configureWebpack은 플러그인에 의해 로딩된 콘텐츠를 모두 호출할 수 있습니다.

합치기 전략

webpack-merge를 사용해 플러그인의 웹팩 설정을 전역 웹팩 설정과 합칠 수 있습니다.

이때 합치기 전략을 설정할 수 있습니다. 예를 들어 웹팩에 적용할 규칙을 뒤에 추가하는 대신 앞에 삽입할 수 있습니다.

docusaurus-plugin/src/index.js
module.exports = function (context, options) {
return {
name: 'custom-docusaurus-plugin',
configureWebpack(config, isServer, utils) {
return {
mergeStrategy: {'module.rules': 'prepend'},
module: {rules: [myRuleToPrepend]},
};
},
};
};

좀 더 자세한 내용은 웹팩 합치기 전략 가이드 문서를 참고하세요.

configurePostCss(options)

클라이언트 번들 생성 시 postcss-loaderpostcssOptions을 수정합니다.

변경된 postcssOptions 값을 반환해야 합니다.

기본적으로 postcssOptions는 아래와 같은 형식입니다.

const postcssOptions = {
ident: 'postcss',
plugins: [require('autoprefixer')],
};

예:

docusaurus-plugin/src/index.js
module.exports = function (context, options) {
return {
name: 'docusaurus-plugin',
configurePostCss(postcssOptions) {
// 새로운 PostCSS 플러그인을 추가합니다.
postcssOptions.plugins.push(require('postcss-import'));
return postcssOptions;
},
};
};

postBuild(props)

(제품) 빌드가 완료되면 호출됩니다.

interface Props {
siteDir: string;
generatedFilesDir: string;
siteConfig: DocusaurusConfig;
outDir: string;
baseUrl: string;
headTags: string;
preBodyTags: string;
postBodyTags: string;
routesPaths: string[];
plugins: Plugin<any>[];
content: Content;
}

예:

docusaurus-plugin/src/index.js
module.exports = function (context, options) {
return {
name: 'docusaurus-plugin',
async postBuild({siteConfig = {}, routesPaths = [], outDir}) {
// Print out to console all the rendered routes.
routesPaths.map((route) => {
console.log(route);
});
},
};
};

injectHtmlTags({content})

도큐사우루스에서 생성한 HTML에 head, body HTML 태그를 추가합니다.

injectHtmlTags는 플러그인에 의해 로딩된 콘텐츠를 모두 호출할 수 있습니다.

function injectHtmlTags(): {
headTags?: HtmlTags;
preBodyTags?: HtmlTags;
postBodyTags?: HtmlTags;
};

type HtmlTags = string | HtmlTagObject | (string | HtmlTagObject)[];

interface HtmlTagObject {
/**
* HTML 태그 속성
* 예 `{'disabled': true, 'value': 'demo', 'rel': 'preconnect'}`
*/
attributes?: {
[attributeName: string]: string | boolean;
};
/**
* 태그 이름. `div`, `script`, `link`, `meta`
*/
tagName: string;
/**
* The inner HTML
*/
innerHTML?: string;
}

예:

docusaurus-plugin/src/index.js
module.exports = function (context, options) {
return {
name: 'docusaurus-plugin',
loadContent: async () => {
return {remoteHeadTags: await fetchHeadTagsFromAPI()};
},
injectHtmlTags({content}) {
return {
headTags: [
{
tagName: 'link',
attributes: {
rel: 'preconnect',
href: 'https://www.github.com',
},
},
...content.remoteHeadTags,
],
preBodyTags: [
{
tagName: 'script',
attributes: {
charset: 'utf-8',
src: '/noflash.js',
},
},
],
postBodyTags: [`<div> This is post body </div>`],
};
},
};
};

getClientModules()

Returns an array of paths to the modules that are to be imported into the client bundle. 리액트에서 초기 UI를 렌더링 처리하기 전에 전역으로 모듈을 가져옵니다.

예를 들어 인자로 전달받은 options에서 customCss 또는 customJs 파일 경로를 반환받아 테마에서 로드하게 하려면 아래와 같이 작성할 수 있습니다.

my-theme/src/index.js
const path = require('path');

module.exports = function (context, options) {
const {customCss, customJs} = options || {};
return {
name: 'name-of-my-theme',
getClientModules() {
return [customCss, customJs];
},
};
};