189- **Imports:** Use `https://esm.sh` for npm and Deno dependencies to ensure compatibility on server and browser
190- **Storage Strategy:** Only use backend storage if explicitly required; prefer simple static client-side sites
191- **React Configuration:** When using React libraries, pin versions with `?deps=react@18.2.0,react-dom@18.2.0` and start the file with `/** @jsxImportSource https://esm.sh/react@18.2.0 */`
192- Ensure all React dependencies and sub-dependencies are pinned to the same version
193- **Styling:** Default to using TailwindCSS via `<script src="https://cdn.twind.style" crossorigin></script>` unless otherwise specified
194
275 - Always run table creation before querying
276
2773. **React Configuration:**
278 - All React dependencies must be pinned to 18.2.0
279 - Always include `@jsxImportSource https://esm.sh/react@18.2.0` at the top of React files
280 - Rendering issues often come from mismatched React versions
281
2824. **File Handling:**
34
35If you want more interactivity, check out this
36[React starter](https://www.val.town/x/std/reactHonoStarter).
37
38### ← favicon.svg
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import React, { useState, useRef, useEffect } from "https://esm.sh/react@18.2.0?deps=react@18.2.0";
3import type { Message, ConversationWithMessages, ConversationParticipant } from "../../shared/types.ts";
4import InviteModal from "./InviteModal.tsx";
44 }, [message]);
45
46 const handleSubmit = async (e: React.FormEvent) => {
47 e.preventDefault();
48 if (!message.trim() || isSending) return;
59 };
60
61 const handleKeyDown = (e: React.KeyboardEvent) => {
62 if (e.key === 'Enter' && !e.shiftKey) {
63 e.preventDefault();
32
33- `backend/` - Hono API server with authentication and group chat
34- `frontend/` - React chat interface with group features
35- `shared/` - Shared TypeScript types
36
38
39- **Backend**: Hono, LastLogin auth, SQLite, OpenAI, Server-Sent Events
40- **Frontend**: React, TailwindCSS, Real-time SSE connections
41- **Database**: SQLite with participant and invitation tables
42
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import React, { useState, useEffect } from "https://esm.sh/react@18.2.0?deps=react@18.2.0";
3import LoginPage from "./LoginPage.tsx";
4import ConversationList from "./ConversationList.tsx";
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import React from "https://esm.sh/react@18.2.0?deps=react@18.2.0";
3import type { ConversationWithParticipants } from "../../shared/types.ts";
4
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import React, { useState, useEffect } from "https://esm.sh/react@18.2.0?deps=react@18.2.0";
3import type { ConversationParticipant } from "../../shared/types.ts";
4
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import React, { useState, useEffect } from "https://esm.sh/react@18.2.0?deps=react@18.2.0";
3import { LoginWithGoogleButton } from "https://esm.town/v/stevekrouse/LoginWithGoogleButton";
4import type { InviteDetails } from "../../shared/types.ts";
1/** @jsxImportSource https://esm.sh/react@18.2.0 */
2import React, { useState } from "https://esm.sh/react@18.2.0?deps=react@18.2.0";
3import type { InviteRequest } from "../../shared/types.ts";
4
22 const [error, setError] = useState('');
23
24 const handleSubmit = async (e: React.FormEvent) => {
25 e.preventDefault();
26 if (!email.trim() || isLoading) return;
1# Frontend
2
3React-based chat interface with TailwindCSS styling.
4
5## Components
28## State Management
29
30- React hooks for local state
31- Automatic conversation loading
32- Real-time UI updates