1# React Hono Val Town Project Starter Template
2
3This is a starter template for a full-stack app in a Val Town Project. The app itself is a simple persistent message board.
12## Serving assets to the frontend
13
14This backend HTTP server is responsible for serving all static assets to the browser to render the app, including HTML, JavaScript (including all client-side React), CSS, and even the favicon SVG.
15
16In a normal server environment, you would likely use a middleware [like this one](https://hono.dev/docs/getting-started/nodejs#serve-static-files) to serve static files. Some frameworks or deployment platforms automatically make any content inside a `public/` folder public.
26## CRUD API Routes
27
28This app has two CRUD API routes: for reading and inserting into the messages table. They both speak JSON, which is standard. They import their functions from `/backend/database/queries.ts`. These routes are called from the React app to refresh and update data.
29
30## Errors
8## Migrations
9
10In `backend/database/migrations.ts`, this app creates a new SQLite table `reactHonoStarter_messages` to store messages.
11
12This "migration" runs once on every app startup because it's imported in `index.ts`. You can comment this line out for a slight (30ms) performance improvement on cold starts. It's left in so that users who fork this project will have the migration run correctly.
1import { sqlite } from "https://esm.town/v/stevekrouse/sqlite";
2
3export const tableName = "reactHonoStarter_messages";
4export const USERS = "USERS";
5export async function createTables() {
9const app = new Hono();
10
11// 🚀 Serve frontend React shell at "/"
12app.get("/", async (c) => {
13 let html = await readFile("/frontend/index.html", import.meta.url);
1// /frontend/index.tsx
2/** @jsxImportSource https://esm.sh/react@18.2.0 */
3import { createRoot } from "https://esm.sh/react-dom@18.2.0/client";
4import App from "./App.tsx";
5
1/** @jsxImportSource https://esm.sh/react */
2import { useEffect, useState } from "https://esm.sh/react@19.0.0";
3import { createRoot } from "https://esm.sh/react-dom@19.0.0/client";
4import { Promo } from "./scanner.http.tsx";
5
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import { useState } from "https://esm.sh/react@18.2.0";
3
4export function App() {
4 <meta charset="UTF-8">
5 <meta name="viewport" content="width=device-width, initial-scale=1.0">
6 <title>React Hono Val Town Starter</title>
7 <script src="https://cdn.tailwindcss.com"></script>
8 <link rel="icon" href="/public/favicon.svg" sizes="any" type="image/svg+xml">
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import { createRoot } from "https://esm.sh/react-dom@18.2.0/client";
3import { App } from "./components/App.tsx";
4