vike-react 0.0.0 → 0.1.1
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/components/usePageContext.d.ts +1 -0
- package/dist/components/usePageContext.js +1 -0
- package/dist/renderer/+config.d.ts +50 -0
- package/dist/renderer/+config.js +27 -0
- package/dist/renderer/PageContextProvider.d.ts +10 -0
- package/dist/renderer/PageContextProvider.js +19 -0
- package/dist/renderer/getPageElement.d.ts +3 -0
- package/dist/renderer/getPageElement.js +18 -0
- package/dist/renderer/getTitle.d.ts +7 -0
- package/dist/renderer/getTitle.js +33 -0
- package/dist/renderer/onRenderClient.d.ts +3 -0
- package/dist/renderer/onRenderClient.js +22 -0
- package/dist/renderer/onRenderHtml.d.ts +5 -0
- package/dist/renderer/onRenderHtml.js +39 -0
- package/dist/renderer/types.d.ts +28 -0
- package/dist/renderer/types.js +1 -0
- package/dist/renderer/utils/getGlobalObject.d.ts +4 -0
- package/dist/renderer/utils/getGlobalObject.js +7 -0
- package/dist/renderer/utils/isCallable.d.ts +1 -0
- package/dist/renderer/utils/isCallable.js +3 -0
- package/package.json +53 -1
- package/types.d.ts +5 -0
- package/readme.md +0 -3
@@ -0,0 +1 @@
|
|
1
|
+
export { usePageContext } from '../renderer/PageContextProvider';
|
@@ -0,0 +1 @@
|
|
1
|
+
export { usePageContext } from '../renderer/PageContextProvider';
|
@@ -0,0 +1,50 @@
|
|
1
|
+
import type { Config } from 'vite-plugin-ssr/types';
|
2
|
+
import type { Component } from './types';
|
3
|
+
export type ConfigEnhanced = Config & Partial<VikeReactConfig & {
|
4
|
+
Page: Component;
|
5
|
+
}>;
|
6
|
+
export type VikeReactConfig = {
|
7
|
+
/** React element renderer and appended into <head></head> */
|
8
|
+
Head: Component;
|
9
|
+
Layout: Component;
|
10
|
+
/** <title>${title}</title> */
|
11
|
+
title: string;
|
12
|
+
/** <meta name="description" content="${description}" /> */
|
13
|
+
description: string;
|
14
|
+
/** <link rel="icon" href="${favicon}" /> */
|
15
|
+
favicon: string;
|
16
|
+
/** <html lang="${lang}">
|
17
|
+
*
|
18
|
+
* @default 'en'
|
19
|
+
*
|
20
|
+
*/
|
21
|
+
lang: string;
|
22
|
+
};
|
23
|
+
declare const _default: {
|
24
|
+
onRenderHtmlPath: string;
|
25
|
+
onRenderClientPath: string;
|
26
|
+
passToClient: string[];
|
27
|
+
clientRouting: true;
|
28
|
+
hydrationCanBeAborted: true;
|
29
|
+
meta: {
|
30
|
+
Head: {
|
31
|
+
env: "server-only";
|
32
|
+
};
|
33
|
+
Layout: {
|
34
|
+
env: "server-and-client";
|
35
|
+
};
|
36
|
+
title: {
|
37
|
+
env: "server-and-client";
|
38
|
+
};
|
39
|
+
description: {
|
40
|
+
env: "server-only";
|
41
|
+
};
|
42
|
+
favicon: {
|
43
|
+
env: "server-only";
|
44
|
+
};
|
45
|
+
lang: {
|
46
|
+
env: "server-only";
|
47
|
+
};
|
48
|
+
};
|
49
|
+
};
|
50
|
+
export default _default;
|
@@ -0,0 +1,27 @@
|
|
1
|
+
export default {
|
2
|
+
onRenderHtmlPath: 'vike-react/renderer/onRenderHtml',
|
3
|
+
onRenderClientPath: 'vike-react/renderer/onRenderClient',
|
4
|
+
passToClient: ['pageProps', 'title'],
|
5
|
+
clientRouting: true,
|
6
|
+
hydrationCanBeAborted: true,
|
7
|
+
meta: {
|
8
|
+
Head: {
|
9
|
+
env: 'server-only'
|
10
|
+
},
|
11
|
+
Layout: {
|
12
|
+
env: 'server-and-client'
|
13
|
+
},
|
14
|
+
title: {
|
15
|
+
env: 'server-and-client'
|
16
|
+
},
|
17
|
+
description: {
|
18
|
+
env: 'server-only'
|
19
|
+
},
|
20
|
+
favicon: {
|
21
|
+
env: 'server-only'
|
22
|
+
},
|
23
|
+
lang: {
|
24
|
+
env: 'server-only'
|
25
|
+
}
|
26
|
+
}
|
27
|
+
};
|
@@ -0,0 +1,10 @@
|
|
1
|
+
export { PageContextProvider };
|
2
|
+
export { usePageContext };
|
3
|
+
import React from 'react';
|
4
|
+
import { PageContext } from './types';
|
5
|
+
declare function PageContextProvider({ pageContext, children }: {
|
6
|
+
pageContext: PageContext;
|
7
|
+
children: React.ReactNode;
|
8
|
+
}): JSX.Element;
|
9
|
+
/** Access the pageContext from any React component */
|
10
|
+
declare function usePageContext(): PageContext;
|
@@ -0,0 +1,19 @@
|
|
1
|
+
export { PageContextProvider };
|
2
|
+
export { usePageContext };
|
3
|
+
import React, { useContext } from 'react';
|
4
|
+
import { getGlobalObject } from './utils/getGlobalObject.js';
|
5
|
+
const { Context } = getGlobalObject('PageContextProvider.ts', {
|
6
|
+
Context: React.createContext(undefined)
|
7
|
+
});
|
8
|
+
function PageContextProvider({ pageContext, children }) {
|
9
|
+
if (!pageContext)
|
10
|
+
throw new Error('Argument pageContext missing');
|
11
|
+
return React.createElement(Context.Provider, { value: pageContext }, children);
|
12
|
+
}
|
13
|
+
/** Access the pageContext from any React component */
|
14
|
+
function usePageContext() {
|
15
|
+
const pageContext = useContext(Context);
|
16
|
+
if (!pageContext)
|
17
|
+
throw new Error('<PageContextProvider> is needed for being able to use usePageContext()');
|
18
|
+
return pageContext;
|
19
|
+
}
|
@@ -0,0 +1,18 @@
|
|
1
|
+
export { getPageElement };
|
2
|
+
import React from 'react';
|
3
|
+
import { PageContextProvider } from './PageContextProvider.js';
|
4
|
+
function getPageElement(pageContext) {
|
5
|
+
var _a, _b;
|
6
|
+
const Layout = (_a = pageContext.config.Layout) !== null && _a !== void 0 ? _a : PassThrough;
|
7
|
+
const Wrapper = (_b = pageContext.config.Wrapper) !== null && _b !== void 0 ? _b : PassThrough;
|
8
|
+
const { Page, pageProps } = pageContext;
|
9
|
+
const page = (React.createElement(React.StrictMode, null,
|
10
|
+
React.createElement(PageContextProvider, { pageContext: pageContext },
|
11
|
+
React.createElement(Wrapper, null,
|
12
|
+
React.createElement(Layout, null,
|
13
|
+
React.createElement(Page, { ...pageProps }))))));
|
14
|
+
return page;
|
15
|
+
}
|
16
|
+
function PassThrough({ children }) {
|
17
|
+
return React.createElement(React.Fragment, null, children);
|
18
|
+
}
|
@@ -0,0 +1,33 @@
|
|
1
|
+
export { getTitle };
|
2
|
+
import { isCallable } from './utils/isCallable.js';
|
3
|
+
function getTitle(pageContext) {
|
4
|
+
var _a;
|
5
|
+
if (pageContext.title) {
|
6
|
+
if (typeof pageContext.title !== 'string') {
|
7
|
+
throw new Error('pageContext.title should be a string');
|
8
|
+
}
|
9
|
+
return pageContext.title;
|
10
|
+
}
|
11
|
+
else {
|
12
|
+
const titleConfig = (_a = pageContext.configEntries.title) === null || _a === void 0 ? void 0 : _a[0];
|
13
|
+
if (!titleConfig) {
|
14
|
+
return null;
|
15
|
+
}
|
16
|
+
const title = titleConfig.configValue;
|
17
|
+
if (typeof title === 'string') {
|
18
|
+
return title;
|
19
|
+
}
|
20
|
+
if (!title) {
|
21
|
+
return null;
|
22
|
+
}
|
23
|
+
const { configDefinedAt } = titleConfig;
|
24
|
+
if (isCallable(title)) {
|
25
|
+
const val = title(pageContext);
|
26
|
+
if (typeof val !== 'string') {
|
27
|
+
throw new Error(configDefinedAt + ' should return a string');
|
28
|
+
}
|
29
|
+
return val;
|
30
|
+
}
|
31
|
+
throw new Error(configDefinedAt + ' should be a string or a function returning a string');
|
32
|
+
}
|
33
|
+
}
|
@@ -0,0 +1,22 @@
|
|
1
|
+
export default onRenderClient;
|
2
|
+
import ReactDOM from 'react-dom/client';
|
3
|
+
import { getTitle } from './getTitle.js';
|
4
|
+
import { getPageElement } from './getPageElement.js';
|
5
|
+
let root;
|
6
|
+
async function onRenderClient(pageContext) {
|
7
|
+
const page = getPageElement(pageContext);
|
8
|
+
const container = document.getElementById('page-view');
|
9
|
+
if (pageContext.isHydration) {
|
10
|
+
root = ReactDOM.hydrateRoot(container, page);
|
11
|
+
}
|
12
|
+
else {
|
13
|
+
if (!root) {
|
14
|
+
root = ReactDOM.createRoot(container);
|
15
|
+
}
|
16
|
+
root.render(page);
|
17
|
+
}
|
18
|
+
const title = getTitle(pageContext);
|
19
|
+
if (title !== null) {
|
20
|
+
document.title = title;
|
21
|
+
}
|
22
|
+
}
|
@@ -0,0 +1,39 @@
|
|
1
|
+
export default onRenderHtml;
|
2
|
+
import { renderToString } from 'react-dom/server';
|
3
|
+
import { escapeInject, dangerouslySkipEscape } from 'vite-plugin-ssr/server';
|
4
|
+
import { getTitle } from './getTitle.js';
|
5
|
+
import { getPageElement } from './getPageElement.js';
|
6
|
+
import { PageContextProvider } from './PageContextProvider.js';
|
7
|
+
import React from 'react';
|
8
|
+
async function onRenderHtml(pageContext) {
|
9
|
+
const page = getPageElement(pageContext);
|
10
|
+
const pageHtml = renderToString(page);
|
11
|
+
const title = getTitle(pageContext);
|
12
|
+
const titleTag = !title ? '' : escapeInject `<title>${title}</title>`;
|
13
|
+
const { description } = pageContext.config;
|
14
|
+
const descriptionTag = !description ? '' : escapeInject `<meta name="description" content="${description}" />`;
|
15
|
+
const { favicon } = pageContext.config;
|
16
|
+
const faviconTag = !favicon ? '' : escapeInject `<link rel="icon" href="${favicon}" />`;
|
17
|
+
const Head = pageContext.config.Head || (() => React.createElement(React.Fragment, null));
|
18
|
+
const head = (React.createElement(React.StrictMode, null,
|
19
|
+
React.createElement(PageContextProvider, { pageContext: pageContext },
|
20
|
+
React.createElement(Head, null))));
|
21
|
+
const headHtml = renderToString(head);
|
22
|
+
const lang = pageContext.config.lang || 'en';
|
23
|
+
const documentHtml = escapeInject `<!DOCTYPE html>
|
24
|
+
<html lang='${lang}'>
|
25
|
+
<head>
|
26
|
+
<meta charset="UTF-8" />
|
27
|
+
${faviconTag}
|
28
|
+
${titleTag}
|
29
|
+
${descriptionTag}
|
30
|
+
${dangerouslySkipEscape(headHtml)}
|
31
|
+
</head>
|
32
|
+
<body>
|
33
|
+
<div id="page-view">${dangerouslySkipEscape(pageHtml)}</div>
|
34
|
+
</body>
|
35
|
+
</html>`;
|
36
|
+
return {
|
37
|
+
documentHtml
|
38
|
+
};
|
39
|
+
}
|
@@ -0,0 +1,28 @@
|
|
1
|
+
export type { PageContextServer };
|
2
|
+
export type { PageContextClient };
|
3
|
+
export type { PageContext };
|
4
|
+
export type { PageProps };
|
5
|
+
export type { Page };
|
6
|
+
export type { Component };
|
7
|
+
import type { PageContextBuiltIn, PageContextBuiltInClientWithClientRouting as PageContextBuiltInClient } from 'vite-plugin-ssr/types';
|
8
|
+
import type { ConfigEnhanced } from './+config';
|
9
|
+
import type { ReactElement } from 'react';
|
10
|
+
type Component = (props: any) => ReactElement;
|
11
|
+
type Page = (pageProps: PageProps) => ReactElement;
|
12
|
+
type PageProps = Record<string, unknown>;
|
13
|
+
type WrapperComponent = ({ children }: {
|
14
|
+
children: any;
|
15
|
+
}) => ReactElement;
|
16
|
+
export type PageContextCommon = {
|
17
|
+
Page: Page;
|
18
|
+
pageProps?: PageProps;
|
19
|
+
config: {
|
20
|
+
Layout?: WrapperComponent;
|
21
|
+
Wrapper?: WrapperComponent;
|
22
|
+
};
|
23
|
+
};
|
24
|
+
type PageContextServer = PageContextBuiltIn<Page> & PageContextCommon & {
|
25
|
+
config: Partial<ConfigEnhanced>;
|
26
|
+
};
|
27
|
+
type PageContextClient = PageContextBuiltInClient<Page> & PageContextCommon;
|
28
|
+
type PageContext = PageContextClient | PageContextServer;
|
@@ -0,0 +1 @@
|
|
1
|
+
export {};
|
@@ -0,0 +1,7 @@
|
|
1
|
+
export function getGlobalObject(
|
2
|
+
// We use the filename as key; each `getGlobalObject()` call should live in a unique filename.
|
3
|
+
key, defaultValue) {
|
4
|
+
const allGlobalObjects = (globalThis.__vite_plugin_ssr = globalThis.__vite_plugin_ssr || {});
|
5
|
+
const globalObject = (allGlobalObjects[key] = allGlobalObjects[key] || defaultValue);
|
6
|
+
return globalObject;
|
7
|
+
}
|
@@ -0,0 +1 @@
|
|
1
|
+
export declare function isCallable<T extends (...args: unknown[]) => unknown>(thing: T | unknown): thing is T;
|
package/package.json
CHANGED
@@ -1,4 +1,56 @@
|
|
1
1
|
{
|
2
2
|
"name": "vike-react",
|
3
|
-
"version": "0.
|
3
|
+
"version": "0.1.1",
|
4
|
+
"type": "module",
|
5
|
+
"main": "./dist/renderer/+config.js",
|
6
|
+
"types": "./dist/renderer/_config.d.ts",
|
7
|
+
"exports": {
|
8
|
+
".": "./dist/renderer/+config.js",
|
9
|
+
"./renderer/onRenderHtml": "./dist/renderer/onRenderHtml.js",
|
10
|
+
"./renderer/onRenderClient": "./dist/renderer/onRenderClient.js",
|
11
|
+
"./usePageContext": "./dist/components/usePageContext.js"
|
12
|
+
},
|
13
|
+
"dependencies": {},
|
14
|
+
"scripts": {
|
15
|
+
"dev": "tsc --watch",
|
16
|
+
"build": "rm -rf dist/ && tsc",
|
17
|
+
"release": "release-me patch"
|
18
|
+
},
|
19
|
+
"peerDependencies": {
|
20
|
+
"react": "18.x.x",
|
21
|
+
"react-dom": "18.x.x",
|
22
|
+
"vite": "^4.3.8",
|
23
|
+
"vite-plugin-ssr": "^0.4.127"
|
24
|
+
},
|
25
|
+
"devDependencies": {
|
26
|
+
"@brillout/release-me": "^0.1.3",
|
27
|
+
"@types/node": "^18.15.3",
|
28
|
+
"@types/react": "^18.0.8",
|
29
|
+
"@types/react-dom": "^18.0.3",
|
30
|
+
"react": "^18.0.0",
|
31
|
+
"react-dom": "^18.0.0",
|
32
|
+
"typescript": "^5.0.2"
|
33
|
+
},
|
34
|
+
"typesVersions": {
|
35
|
+
"*": {
|
36
|
+
".": [
|
37
|
+
"./dist/renderer/+config.d.ts"
|
38
|
+
],
|
39
|
+
"usePageContext": [
|
40
|
+
"./dist/components/usePageContext.d.ts"
|
41
|
+
],
|
42
|
+
"renderer/onRenderHtml": [
|
43
|
+
"./dist/renderer/onRenderHtml.d.ts"
|
44
|
+
],
|
45
|
+
"renderer/onRenderClient": [
|
46
|
+
"./dist/renderer/onRenderClient.d.ts"
|
47
|
+
]
|
48
|
+
}
|
49
|
+
},
|
50
|
+
"files": [
|
51
|
+
"dist/",
|
52
|
+
"types.d.ts"
|
53
|
+
],
|
54
|
+
"repository": "github:brillout/vike-react",
|
55
|
+
"license": "MIT"
|
4
56
|
}
|
package/types.d.ts
ADDED
package/readme.md
DELETED