vite and react scaffold
This commit is contained in:
@@ -0,0 +1,38 @@
|
||||
<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<link rel="icon" type="image/svg+xml" href="/favicon.svg" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>cruciverb</title>
|
||||
<meta name="description" content="Daily crossword puzzles in five sizes, four game modes, cryptic clues, multiplayer rooms, party games, and a puzzle editor. Self-hosted, federated, CC0." />
|
||||
|
||||
<!-- open graph -->
|
||||
<meta property="og:type" content="website" />
|
||||
<meta property="og:title" content="cruciverb" />
|
||||
<meta property="og:description" content="Daily crossword puzzles in five sizes, four game modes, cryptic clues, multiplayer rooms, party games, and a puzzle editor. Self-hosted, federated, CC0." />
|
||||
<meta property="og:site_name" content="cruciverb" />
|
||||
<meta property="og:image" content="/og-image.png" />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
<meta property="og:image:alt" content="cruciverb - a crossword a day" />
|
||||
|
||||
<!-- twitter card -->
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<meta name="twitter:title" content="cruciverb" />
|
||||
<meta name="twitter:description" content="Daily crossword puzzles in five sizes. Self-hosted, federated, CC0 public domain." />
|
||||
<meta name="twitter:image" content="/og-image.png" />
|
||||
|
||||
<!-- theme color for browsers -->
|
||||
<meta name="theme-color" content="#111111" />
|
||||
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
|
||||
|
||||
<!-- additional seo -->
|
||||
<meta name="author" content="cruciverb" />
|
||||
<meta name="keywords" content="crossword, puzzle, daily crossword, crossword generator, self-hosted, federated, activitypub, multiplayer, party game, cryptic crossword" />
|
||||
</head>
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
<script type="module" src="/src/main.tsx"></script>
|
||||
</body>
|
||||
</html>
|
||||
Generated
+7485
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,40 @@
|
||||
{
|
||||
"name": "frontend",
|
||||
"private": true,
|
||||
"version": "0.0.0",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"dev": "vite",
|
||||
"build": "tsc -b && vite build && vite build --config vite.config.embed.ts",
|
||||
"lint": "eslint .",
|
||||
"preview": "vite preview"
|
||||
},
|
||||
"dependencies": {
|
||||
"@tabler/icons-react": "^3.40.0",
|
||||
"canvas-confetti": "^1.9.4",
|
||||
"i18next": "^25.10.10",
|
||||
"i18next-browser-languagedetector": "^8.2.1",
|
||||
"motion": "^12.38.0",
|
||||
"qrcode.react": "^4.2.0",
|
||||
"react": "^19.2.4",
|
||||
"react-dom": "^19.2.4",
|
||||
"react-i18next": "^16.6.6",
|
||||
"tesseract.js": "^7.0.0",
|
||||
"vite-plugin-pwa": "^1.2.0",
|
||||
"zustand": "^5.0.12"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@eslint/js": "^9.39.4",
|
||||
"@types/node": "^24.12.0",
|
||||
"@types/react": "^19.2.14",
|
||||
"@types/react-dom": "^19.2.3",
|
||||
"@vitejs/plugin-react": "^6.0.1",
|
||||
"eslint": "^9.39.4",
|
||||
"eslint-plugin-react-hooks": "^7.0.1",
|
||||
"eslint-plugin-react-refresh": "^0.5.2",
|
||||
"globals": "^17.4.0",
|
||||
"typescript": "~5.9.3",
|
||||
"typescript-eslint": "^8.57.0",
|
||||
"vite": "^8.0.1"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
import { defineConfig } from 'vite'
|
||||
import react from '@vitejs/plugin-react'
|
||||
|
||||
export default defineConfig({
|
||||
plugins: [react()],
|
||||
build: {
|
||||
outDir: 'dist/embed',
|
||||
emptyOutDir: true,
|
||||
rollupOptions: {
|
||||
input: 'src/embed.tsx',
|
||||
output: {
|
||||
entryFileNames: 'embed.js',
|
||||
assetFileNames: 'embed.[ext]',
|
||||
},
|
||||
},
|
||||
},
|
||||
server: {
|
||||
port: 5174,
|
||||
proxy: {
|
||||
'/api': 'http://localhost:8090',
|
||||
},
|
||||
},
|
||||
})
|
||||
@@ -0,0 +1,70 @@
|
||||
import { defineConfig } from 'vite'
|
||||
import react from '@vitejs/plugin-react'
|
||||
import { VitePWA } from 'vite-plugin-pwa'
|
||||
|
||||
export default defineConfig({
|
||||
plugins: [
|
||||
react(),
|
||||
VitePWA({
|
||||
registerType: 'autoUpdate',
|
||||
includeAssets: ['favicon.svg', 'models/**/*'],
|
||||
manifest: {
|
||||
name: 'cruciverb',
|
||||
short_name: 'cruciverb',
|
||||
description: 'a crossword a day',
|
||||
theme_color: '#111111',
|
||||
background_color: '#111111',
|
||||
display: 'standalone',
|
||||
start_url: '/',
|
||||
icons: [
|
||||
{ src: '/favicon.svg', sizes: 'any', type: 'image/svg+xml', purpose: 'any maskable' },
|
||||
],
|
||||
},
|
||||
workbox: {
|
||||
globPatterns: ['**/*.{js,css,html,svg,woff2,ttf}'],
|
||||
runtimeCaching: [
|
||||
{
|
||||
urlPattern: /^\/api\/puzzles\/daily\/.*/,
|
||||
handler: 'NetworkFirst',
|
||||
options: {
|
||||
cacheName: 'daily-puzzles',
|
||||
expiration: { maxEntries: 20, maxAgeSeconds: 86400 },
|
||||
networkTimeoutSeconds: 5,
|
||||
},
|
||||
},
|
||||
{
|
||||
urlPattern: /^\/api\/me$/,
|
||||
handler: 'NetworkFirst',
|
||||
options: {
|
||||
cacheName: 'session',
|
||||
expiration: { maxEntries: 1, maxAgeSeconds: 3600 },
|
||||
networkTimeoutSeconds: 3,
|
||||
},
|
||||
},
|
||||
{
|
||||
urlPattern: /^\/api\/.*/,
|
||||
handler: 'NetworkOnly',
|
||||
},
|
||||
{
|
||||
urlPattern: /^\/feeds\/.*/,
|
||||
handler: 'NetworkFirst',
|
||||
options: {
|
||||
cacheName: 'feeds',
|
||||
expiration: { maxEntries: 5, maxAgeSeconds: 3600 },
|
||||
},
|
||||
},
|
||||
],
|
||||
},
|
||||
}),
|
||||
],
|
||||
server: {
|
||||
port: 5173,
|
||||
proxy: {
|
||||
'/api': { target: 'http://localhost:8090', ws: true },
|
||||
'/feeds': { target: 'http://localhost:8090' },
|
||||
'/.well-known': { target: 'http://localhost:8090' },
|
||||
'/nodeinfo': { target: 'http://localhost:8090' },
|
||||
'/inbox': { target: 'http://localhost:8090' },
|
||||
},
|
||||
},
|
||||
})
|
||||
Reference in New Issue
Block a user