feat(scanner): ean-barcode mit der handykamera scannen
Knopf im Katalog neben "Set anlegen": Strichcode ins Bild halten, und entweder oeffnet sich das passende Set oder das Formular "Neues Set" mit ausgefuellter EAN. Dekodiert wird im Browser mit zxing, das nur beim Oeffnen des Scanners nachgeladen wird - nichts verlaesst das Geraet, und die Katalogseite bleibt leicht fuer alle, die nie scannen. Jeder gelesene Code wird gegen seine Pruefziffer geprueft, bevor er verwendet wird. Ohne das wuerde eine falsch erkannte Ziffer stillschweigend ein zweites Katalog-Set fuer ein Set anlegen, das es schon gibt; bei einem Fehlversuch scannt die Kamera einfach weiter. Die Kamera braucht wie Passkeys einen sicheren Kontext. Fehlt HTTPS oder wird der Zugriff abgelehnt, steht das als deutscher Hinweis im Dialog statt einer stummen schwarzen Flaeche. 8 Unit-Tests mit echten EAN-13-, EAN-8- und UPC-A-Beispielen. Refs Phase 2 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
+75
-73
@@ -1,73 +1,75 @@
|
||||
{
|
||||
"name": "bricktrack",
|
||||
"version": "0.1.0",
|
||||
"private": true,
|
||||
"description": "Self-hosted Verwaltung fuer Spielzeug-Set-Sammlungen (Lego, Playmobil, Cobi, ...)",
|
||||
"packageManager": "pnpm@10.34.5",
|
||||
"engines": {
|
||||
"node": ">=22"
|
||||
},
|
||||
"scripts": {
|
||||
"dev": "next dev",
|
||||
"build": "next build",
|
||||
"start": "next start",
|
||||
"lint": "eslint .",
|
||||
"typecheck": "tsc --noEmit",
|
||||
"db:generate": "drizzle-kit generate",
|
||||
"db:migrate": "tsx scripts/migrate.ts",
|
||||
"db:seed": "tsx scripts/seed.ts",
|
||||
"db:studio": "drizzle-kit studio",
|
||||
"test": "vitest run",
|
||||
"test:watch": "vitest",
|
||||
"test:e2e": "node scripts/reset-e2e.mjs && playwright test",
|
||||
"screenshots": "node scripts/screenshots-prepare.mjs && playwright test --config=playwright.screenshots.config.ts"
|
||||
},
|
||||
"dependencies": {
|
||||
"@better-auth/passkey": "^1.7.3",
|
||||
"better-auth": "^1.7.3",
|
||||
"better-sqlite3": "^13.0.3",
|
||||
"class-variance-authority": "^0.7.1",
|
||||
"cn": "^0.2.6",
|
||||
"date-fns": "^4.4.0",
|
||||
"drizzle-orm": "^0.45.2",
|
||||
"lucide-react": "^1.41.0",
|
||||
"next": "15.5.25",
|
||||
"next-themes": "^0.4.6",
|
||||
"pdfjs-dist": "^6.3.289",
|
||||
"radix-ui": "^1.6.7",
|
||||
"react": "19.1.0",
|
||||
"react-dom": "19.1.0",
|
||||
"server-only": "^0.0.1",
|
||||
"sharp": "^0.35.4",
|
||||
"sonner": "^2.0.8",
|
||||
"tw-animate-css": "^1.4.0",
|
||||
"zod": "^4.5.4"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@eslint/eslintrc": "^3",
|
||||
"@playwright/test": "^1.63.0",
|
||||
"@tailwindcss/postcss": "^4",
|
||||
"@types/better-sqlite3": "^9.6.0",
|
||||
"@types/node": "^20",
|
||||
"@types/react": "^19",
|
||||
"@types/react-dom": "^19",
|
||||
"dotenv": "^17.4.2",
|
||||
"drizzle-kit": "^0.31.10",
|
||||
"esbuild": "^0.25.12",
|
||||
"eslint": "^9",
|
||||
"eslint-config-next": "15.5.25",
|
||||
"shadcn": "^4.21.0",
|
||||
"tailwindcss": "^4",
|
||||
"tsx": "^4.23.13",
|
||||
"typescript": "^5",
|
||||
"vitest": "^5.0.0"
|
||||
},
|
||||
"pnpm": {
|
||||
"onlyBuiltDependencies": [
|
||||
"better-sqlite3",
|
||||
"esbuild",
|
||||
"sharp",
|
||||
"unrs-resolver"
|
||||
]
|
||||
}
|
||||
}
|
||||
{
|
||||
"name": "bricktrack",
|
||||
"version": "0.1.0",
|
||||
"private": true,
|
||||
"description": "Self-hosted Verwaltung fuer Spielzeug-Set-Sammlungen (Lego, Playmobil, Cobi, ...)",
|
||||
"packageManager": "pnpm@10.34.5",
|
||||
"engines": {
|
||||
"node": ">=22"
|
||||
},
|
||||
"scripts": {
|
||||
"dev": "next dev",
|
||||
"build": "next build",
|
||||
"start": "next start",
|
||||
"lint": "eslint .",
|
||||
"typecheck": "tsc --noEmit",
|
||||
"db:generate": "drizzle-kit generate",
|
||||
"db:migrate": "tsx scripts/migrate.ts",
|
||||
"db:seed": "tsx scripts/seed.ts",
|
||||
"db:studio": "drizzle-kit studio",
|
||||
"test": "vitest run",
|
||||
"test:watch": "vitest",
|
||||
"test:e2e": "node scripts/reset-e2e.mjs && playwright test",
|
||||
"screenshots": "node scripts/screenshots-prepare.mjs && playwright test --config=playwright.screenshots.config.ts"
|
||||
},
|
||||
"dependencies": {
|
||||
"@better-auth/passkey": "^1.7.3",
|
||||
"@zxing/browser": "^0.2.1",
|
||||
"@zxing/library": "^0.23.0",
|
||||
"better-auth": "^1.7.3",
|
||||
"better-sqlite3": "^13.0.3",
|
||||
"class-variance-authority": "^0.7.1",
|
||||
"cn": "^0.2.6",
|
||||
"date-fns": "^4.4.0",
|
||||
"drizzle-orm": "^0.45.2",
|
||||
"lucide-react": "^1.41.0",
|
||||
"next": "15.5.25",
|
||||
"next-themes": "^0.4.6",
|
||||
"pdfjs-dist": "^6.3.289",
|
||||
"radix-ui": "^1.6.7",
|
||||
"react": "19.1.0",
|
||||
"react-dom": "19.1.0",
|
||||
"server-only": "^0.0.1",
|
||||
"sharp": "^0.35.4",
|
||||
"sonner": "^2.0.8",
|
||||
"tw-animate-css": "^1.4.0",
|
||||
"zod": "^4.5.4"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@eslint/eslintrc": "^3",
|
||||
"@playwright/test": "^1.63.0",
|
||||
"@tailwindcss/postcss": "^4",
|
||||
"@types/better-sqlite3": "^9.6.0",
|
||||
"@types/node": "^20",
|
||||
"@types/react": "^19",
|
||||
"@types/react-dom": "^19",
|
||||
"dotenv": "^17.4.2",
|
||||
"drizzle-kit": "^0.31.10",
|
||||
"esbuild": "^0.25.12",
|
||||
"eslint": "^9",
|
||||
"eslint-config-next": "15.5.25",
|
||||
"shadcn": "^4.21.0",
|
||||
"tailwindcss": "^4",
|
||||
"tsx": "^4.23.13",
|
||||
"typescript": "^5",
|
||||
"vitest": "^5.0.0"
|
||||
},
|
||||
"pnpm": {
|
||||
"onlyBuiltDependencies": [
|
||||
"better-sqlite3",
|
||||
"esbuild",
|
||||
"sharp",
|
||||
"unrs-resolver"
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user