Caution
This library is deprecated. Please use vite-ssr-components instead for a more modern and efficient approach to SSR with Vite.
See the Migration Guide below for instructions on how to migrate.
hono-vite-react-stack is a Vite plugin for creating web apps that run on Cloudflare Workers using Hono and React. The stack consists of the following.
- Hono - Web application framework for server-side rendering with React. It is also possible to create APIs.
- React - UI library. It can be used not only for server-side SSR, but also for client-side use.
- Tailwind CSS - A CSS library.
- Cloudflare Workers - You can deploy your application to Cloudflare Workers. It also emulates the Cloudflare Workers environment during development, just like Wrangler.
- Vite - Used for the development server and build. By using this plugin, you can easily develop using this stack and build the server side and client side.
npx giget@latest gh:yusukebe/hono-vite-react-stack-example my-app
Configuration file:
// vite.config.ts
import { defineConfig } from 'vite'
import reactStack from 'hono-vite-react-stack'
export default defineConfig({
plugins: [reactStack()],
})
Start development server:
vite dev
Build:
vite build && vite build --ssr
You need to place the files as follows.
src/server/index.tsx
- Hono applicationsrc/client/index.tsx
- Client entry pointsrc/style.css
- CSS file
In addition, the following will be output when building.
dist-server/index.js
- Server filedist/*
- Client files
Components solve the problem of different file paths during development and build.
import { Script, Link } from 'hono-vite-react-stack/components'
export const renderer = reactRenderer(({ children }) => {
return (
<html>
<head>
<meta charSet='UTF-8' />
<meta name='viewport' content='width=device-width, initial-scale=1.0' />
<Script />
<Link href='/src/style.css' rel='stylesheet' />
</head>
<body>{children}</body>
</html>
)
})
If you want to change the path of the client entry point, add a src
attribute to the Script
component and set the path.
// src/client/main.tsx
import { Script, Link } from 'hono-vite-react-stack/components'
import { reactRenderer } from '@hono/react-renderer'
export const renderer = reactRenderer(({ children }) => {
return (
<html>
<head>
{/** Add src attribute to Script component */}
<Script src='/src/client/main.tsx' />
</head>
<body>{children}</body>
</html>
)
})
For the build, you can specify it in the vite.config.ts
.
// vite.config.ts
import reactStack from 'hono-vite-react-stack'
import { defineConfig } from 'vite'
export default defineConfig({
plugins: [
reactStack({
clientEntry: './src/client/main.tsx',
}),
],
})
Creating a project using Durable Objects requires some additional steps. If you have defined a Durable Object class named MyDurableObject
and exported it in src/server/do.ts
:
// src/server/do.ts
import { DurableObject } from 'cloudflare:workers'
export class MyDurableObject extends DurableObject<Bindings> {
constructor(ctx: DurableObjectState, env: Bindings) {
super(ctx, env)
}
async sayHello(name: string): Promise<string> {
return `Hello, ${name}!`
}
}
You should import and export it at src/server/index.tsx
.
// src/server/index.tsx
export { MyDurableObject } from './do'
And write vite.config.ts
as follows. This is a bit of a hack.
// vite.config.ts
import reactStack from 'hono-vite-react-stack'
import { defineConfig } from 'vite'
import { defaultOptions as buildDefaultOptions } from '@hono/vite-build/cloudflare-workers'
export default defineConfig({
build: {
rollupOptions: {
external: ['cloudflare:workers'],
},
},
plugins: [
reactStack({
buildPluginOptions: {
entryContentAfterHooks: [
...buildDefaultOptions.entryContentAfterHooks,
() => `export { MyDurableObject } from "/src/server/do"`,
],
entryContentDefaultExportHook: buildDefaultOptions.entryContentDefaultExportHook,
},
}),
],
})
Directory structure:
.
├── package.json
├── public
├── src
│ ├── client
│ │ ├── app.tsx
│ │ └── index.tsx
│ ├── server
│ │ ├── index.tsx
│ │ └── renderer.tsx
│ └── style.css
├── tsconfig.json
├── vite.config.ts
├── worker-configuration.d.ts
└── wrangler.jsonc
wrangler.json
:
Commands:
"dev": "vite",
"build": "vite build && vite build --ssr",
"preview": "wrangler dev dist-server/index.js",
"deploy": "$npm_execpath run build && wrangler deploy dist-server/index.js",
See more: https://github.com/yusukebe/hono-vite-react-stack-example
To migrate to the new vite-ssr-components library:
-
Install the new library:
npm uninstall hono-vite-react-stack npm i -D vite-ssr-components
-
Update your vite.config.ts:
// Before import reactStack from 'hono-vite-react-stack' // After import ssrPlugin from 'vite-ssr-components/plugin' export default defineConfig({ plugins: [ssrPlugin()], })
-
Update component imports:
// Before import { Script, Link } from 'hono-vite-react-stack/components' // After import { Script, Link, ViteClient } from 'vite-ssr-components/react'
For detailed migration instructions and new features, please refer to the vite-ssr-components documentation.
Yusuke Wada https://github.com/yusukebe
MIT