I'm trying to use Bun and it's optimized built-in React library, without a framework, to build a simple one-page form application. I found work-arounds for dealing with icons and css, but ran into trouble getting onInput events to fire. I'm new to React, so decided to see if I could get a simple onClick example to work from Quick Start - React -> Updating The Screen.
I already had bun installed, of course. I setup the project on Arch Linux with these commands:
% mkdir reactTryingStuff
% cd reactTryingStuff
% bun init
% bun add react react-dom
% bun add @types/react-dom -d
% mv index.ts index.tsx
I edited package.json to add a start script:
{
"name": "reacttryingstuff",
"module": "index.tsx",
"type": "module",
"scripts": {
"start": "bun --watch run index.tsx"
},
"devDependencies": {
"@types/react-dom": "^18.2.8",
"bun-types": "latest"
},
"peerDependencies": {
"typescript": "^5.0.0"
},
"dependencies": {
"react": "^18.2.0",
"react-dom": "^18.2.0"
}
}
I edited index.tsx to setup the server:
import { renderToReadableStream } from "react-dom/server";
import MyApp from "./App";
const server = Bun.serve({
port: 2000,
async fetch(req) {
const url = new URL(req.url);
// render App.tsx for root path
if (url.pathname === "/") {
const stream = await renderToReadableStream(<MyApp />);
return new Response(stream, {
headers: { "Content-Type": "text/html" },
});
}
return new Response("Not Found", { status: 404 });
},
});
console.log(`Listening on http://localhost:${server.port}`);
I copied App.js from Quick Start - React -> Updating The Screen and put it in file called App.tsx because I'm trying to learn typescript as well and also wanted it to show any errors right away.
App.tsx:
import { useState } from 'react';
export default function MyApp() {
return (
<div>
<h1>Counters that update separately</h1>
<MyButton />
<MyButton />
</div>
);
}
function MyButton() {
const [count, setCount] = useState(0);
function handleClick() {
setCount(count + 1);
}
return (
<button onClick={handleClick}>
Clicked {count} times
</button>
);
}
Then I started the server:
bun start
It looked as expected, but the buttons do nothing when clicked. I've determined that the onClick event never fires.
Is there anyway to serve this example starting with bun init (and no other framework) that will be able to use DOM events like onClick?
I found the right way to implement the example suggested in Quick Start - React -> Updating The Screen. After setting up the project the same as in my question,
App.tsxcan stay as it was (which was directly copied from the Quick Start link). However,index.tsxneeds to be completely different:index.tsxI get a typescript error in my editor about not finding 'document', but everything works anyway. The next step is to build the application:
% bun build ./index.tsx --outdir ./MyAppThat will create
./MyApp/index.js. Now create the following./MyApp/index.htmlFinally, serve
MyAppwith:% bunx serve MyAppEverything works the same as at Quick Start - React -> Updating The Screen.
The information about how to do a client-side server with bun isn't easy to find for a noob like me. The method that worked came from Bun's documentation on Bun.build.