Compare commits

...

6 Commits

Author SHA1 Message Date
rxf
8bfc2b685b V 1.2.1 Berechnugn der Resttsage auch beim Start 2026-03-23 10:08:03 +01:00
rxf
229cbf7223 nochmal 2026-03-19 11:29:36 +01:00
rxf
704a8f09b7 Buid-Date updated 2026-03-19 11:29:08 +01:00
rxf
23ac4ed8d7 V1.2.0 deploy.sh angepasst
try/catch be SQL-Abfragen
2026-03-15 13:56:16 +01:00
rxf
7da9e27687 V 1.1.0 2026-03-12 09:12:45 +01:00
rxf
0faa144e4f nun Ohne Tailwind 2026-03-12 09:11:43 +01:00
14 changed files with 274 additions and 711 deletions

View File

@@ -16,6 +16,8 @@ COPY . .
# Standalone-Output aktiviert kleinste Images # Standalone-Output aktiviert kleinste Images
ENV NEXT_TELEMETRY_DISABLED=1 ENV NEXT_TELEMETRY_DISABLED=1
ARG BUILD_DATE
ENV NEXT_PUBLIC_BUILD_DATE=$BUILD_DATE
RUN npm run build RUN npm run build
# ── Stage 3: Produktions-Image ──────────────────────────────────────────────── # ── Stage 3: Produktions-Image ────────────────────────────────────────────────

View File

@@ -5,6 +5,10 @@ import { checkAblauf } from '@/lib/checkAblauf';
import moment from 'moment'; import moment from 'moment';
import { Tablette, DataResponse } from '@/types/tablette'; import { Tablette, DataResponse } from '@/types/tablette';
// Verhindert Caching der Route
export const dynamic = 'force-dynamic';
export const revalidate = 0;
function formatDate(dt: Date | string | null): string { function formatDate(dt: Date | string | null): string {
if (!dt) return ''; if (!dt) return '';
const d = moment(dt); const d = moment(dt);
@@ -22,23 +26,28 @@ export async function GET(req: NextRequest) {
const sord = searchParams.get('sord') === 'asc' ? 'ASC' : 'DESC'; const sord = searchParams.get('sord') === 'asc' ? 'ASC' : 'DESC';
const col = `\`${sidx}\``; const col = `\`${sidx}\``;
try {
const [rows] = await pool.query<RowDataPacket[]>( const [rows] = await pool.query<RowDataPacket[]>(
`SELECT tab, pday, cnt, at, akt, until, warn, rem, \`order\` `SELECT tab, pday, cnt, at, rem, \`order\`
FROM tabletten FROM tabletten
ORDER BY ${col} ${sord}, rem DESC, tab ASC` ORDER BY ${col} ${sord}, rem DESC, tab ASC`
); );
const values: Tablette[] = rows.map((r) => ({ const values: Tablette[] = rows.map((r) => {
tab: r.tab, // Berechne die aktuellen Werte dynamisch basierend auf dem heutigen Datum
pday: r.pday, const calculated = checkAblauf({ cnt: r.cnt, pday: r.pday, at: r.at });
cnt: r.cnt, return {
at: formatDate(r.at), tab: r.tab,
akt: r.akt, pday: r.pday,
until: formatDate(r.until), cnt: r.cnt,
warn: r.warn === 1 || r.warn === true, at: formatDate(r.at),
rem: r.rem, akt: calculated.akt,
order: r.order, until: formatDate(calculated.until),
})); warn: calculated.warn,
rem: r.rem,
order: r.order,
};
});
const result: DataResponse = { const result: DataResponse = {
total: 1, total: 1,
@@ -48,6 +57,10 @@ export async function GET(req: NextRequest) {
}; };
return NextResponse.json(result); return NextResponse.json(result);
} catch (err) {
console.error('[GET /api/data]', err);
return NextResponse.json({ error: String(err) }, { status: 500 });
}
} }
// POST /api/data // POST /api/data

View File

@@ -1,22 +1,15 @@
@import "tailwindcss";
:root { :root {
--background: #ffffff; --background: #ffffff;
--foreground: #171717; --foreground: #171717;
} }
@theme inline {
--color-background: var(--background);
--color-foreground: var(--foreground);
--font-sans: var(--font-geist-sans);
--font-mono: var(--font-geist-mono);
}
body { body {
background: var(--background); background: var(--background);
color: var(--foreground); color: var(--foreground);
font-family: "Lucida Grande", Helvetica, Arial, sans-serif; font-family: "Lucida Grande", Helvetica, Arial, sans-serif;
font-size: 14px; font-size: 14px;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
} }
main { main {
@@ -49,7 +42,10 @@ main {
.btn-icon { background: none; border: none; cursor: pointer; font-size: 16px; padding: 0; } .btn-icon { background: none; border: none; cursor: pointer; font-size: 16px; padding: 0; }
/* ---- Table ---- */ /* ---- Table ---- */
.table-container { overflow-x: auto; } .table-container {
overflow-x: auto;
width: 100%;
}
.main-table { .main-table {
width: 100%; width: 100%;
@@ -118,3 +114,172 @@ main {
} }
.modal input:disabled { background: #eee; color: #777; } .modal input:disabled { background: #eee; color: #777; }
.modal-buttons { display: flex; gap: 8px; justify-content: flex-end; margin-top: 8px; } .modal-buttons { display: flex; gap: 8px; justify-content: flex-end; margin-top: 8px; }
/* ---- App Layout ---- */
.app-wrapper {
min-height: 100vh;
padding: 32px 16px;
}
.app-container {
max-width: 1264px;
margin: 0 auto;
border: 2px solid black;
border-radius: 12px;
background-color: #d1d5db;
padding: 24px;
}
.app-title {
font-size: 2.25rem;
font-weight: bold;
text-align: center;
margin-bottom: 24px;
letter-spacing: -0.025em;
}
.app-inner {
width: 97%;
margin: 0 auto;
}
.app-logout-bar {
display: flex;
justify-content: flex-end;
margin-bottom: -2px;
}
.btn-logout {
padding: 8px 16px;
background-color: #dc2626;
color: white;
font-size: 0.875rem;
border: none;
border-radius: 8px;
box-shadow: 0 1px 3px rgba(0,0,0,0.2);
cursor: pointer;
}
.btn-logout:hover { background-color: #b91c1c; }
.app-main {
width: 96%;
border: 2px solid black;
border-radius: 8px;
padding: 24px;
background-color: #FFFFDD;
}
.app-footer {
margin-top: 32px;
display: flex;
justify-content: space-between;
align-items: center;
font-size: 0.875rem;
color: #4b5563;
padding: 0 16px;
}
.app-footer a:hover { text-decoration: underline; }
/* ---- Login Page ---- */
.login-wrapper {
min-height: 100vh;
background-color: white;
padding: 16px;
}
.login-outer {
max-width: 72rem;
margin: 0 auto;
border: 2px solid black;
border-radius: 8px;
padding: 24px;
background-color: #FFFFDD;
}
.login-header {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 24px;
}
.login-page-title {
font-size: 1.875rem;
font-weight: bold;
}
.login-center {
display: flex;
justify-content: center;
padding: 40px 0;
}
.login-card {
width: 100%;
max-width: 24rem;
background: white;
border: 1px solid #d1d5db;
border-radius: 12px;
box-shadow: 0 4px 6px rgba(0,0,0,0.1);
padding: 32px;
box-sizing: border-box;
}
.login-card-title {
font-size: 1.25rem;
font-weight: 600;
color: #111827;
margin-bottom: 24px;
text-align: center;
}
.login-form {
display: flex;
flex-direction: column;
gap: 20px;
}
.login-label {
display: block;
font-size: 0.875rem;
font-weight: 500;
color: #374151;
margin-bottom: 4px;
}
.login-input {
width: 100%;
padding: 8px 12px;
border: 2px solid #9ca3af;
border-radius: 8px;
background: white;
color: #111827;
font-size: 0.875rem;
outline: none;
box-sizing: border-box;
}
.login-input:focus { border-color: #3b82f6; }
.login-input:disabled { opacity: 0.6; cursor: not-allowed; }
.login-error {
background-color: #fef2f2;
border: 1px solid #fca5a5;
color: #b91c1c;
padding: 8px 12px;
border-radius: 8px;
font-size: 0.875rem;
}
.login-submit {
width: 100%;
padding: 8px 16px;
background-color: #85B7D7;
color: black;
font-weight: 500;
border: none;
border-radius: 8px;
font-size: 0.875rem;
cursor: pointer;
}
.login-submit:hover:not(:disabled) { background-color: #6a9fc5; }
.login-submit:disabled { opacity: 0.5; cursor: not-allowed; }

View File

@@ -1,17 +1,6 @@
import type { Metadata } from "next"; import type { Metadata } from "next";
import { Geist, Geist_Mono } from "next/font/google";
import "./globals.css"; import "./globals.css";
const geistSans = Geist({
variable: "--font-geist-sans",
subsets: ["latin"],
});
const geistMono = Geist_Mono({
variable: "--font-geist-mono",
subsets: ["latin"],
});
export const metadata: Metadata = { export const metadata: Metadata = {
title: "Tabletten-Übersicht", title: "Tabletten-Übersicht",
description: "Verwaltung von Medikamenten und Tabletten", description: "Verwaltung von Medikamenten und Tabletten",
@@ -24,9 +13,7 @@ export default function RootLayout({
}>) { }>) {
return ( return (
<html lang="en"> <html lang="en">
<body <body>
className={`${geistSans.variable} ${geistMono.variable} antialiased`}
>
{children} {children}
</body> </body>
</html> </html>

View File

@@ -7,19 +7,19 @@ export default function LoginPage() {
const [state, loginAction, isPending] = useActionState(login, undefined); const [state, loginAction, isPending] = useActionState(login, undefined);
return ( return (
<div className="min-h-screen bg-white py-4 px-4"> <div className="login-wrapper">
<main className="max-w-6xl mx-auto border-2 border-black rounded-lg p-6 bg-[#FFFFDD]"> <main className="login-outer">
<div className="flex justify-between items-center mb-6"> <div className="login-header">
<h1 className="text-3xl font-bold">Tabletten-Übersicht</h1> <h1 className="login-page-title">Tabletten-Übersicht</h1>
</div> </div>
<div className="flex justify-center py-10"> <div className="login-center">
<div className="w-full max-w-sm bg-white border border-gray-300 rounded-xl shadow-md p-8"> <div className="login-card">
<h2 className="text-xl font-semibold text-gray-900 mb-6 text-center">Anmeldung</h2> <h2 className="login-card-title">Anmeldung</h2>
<form action={loginAction} className="space-y-5"> <form action={loginAction} className="login-form">
<div> <div>
<label htmlFor="username" className="block text-sm font-medium text-gray-700 mb-1"> <label htmlFor="username" className="login-label">
Benutzername Benutzername
</label> </label>
<input <input
@@ -28,14 +28,14 @@ export default function LoginPage() {
type="text" type="text"
required required
autoComplete="off" autoComplete="off"
className="w-full px-3 py-2 border-2 border-gray-400 rounded-lg bg-white text-gray-900 focus:border-blue-500 focus:outline-none text-sm" className="login-input"
placeholder="Benutzername" placeholder="Benutzername"
disabled={isPending} disabled={isPending}
/> />
</div> </div>
<div> <div>
<label htmlFor="password" className="block text-sm font-medium text-gray-700 mb-1"> <label htmlFor="password" className="login-label">
Passwort Passwort
</label> </label>
<input <input
@@ -44,14 +44,14 @@ export default function LoginPage() {
type="password" type="password"
required required
autoComplete="new-password" autoComplete="new-password"
className="w-full px-3 py-2 border-2 border-gray-400 rounded-lg bg-white text-gray-900 focus:border-blue-500 focus:outline-none text-sm" className="login-input"
placeholder="Passwort" placeholder="Passwort"
disabled={isPending} disabled={isPending}
/> />
</div> </div>
{state?.error && ( {state?.error && (
<div className="bg-red-50 border border-red-300 text-red-700 px-3 py-2 rounded-lg text-sm"> <div className="login-error">
{state.error} {state.error}
</div> </div>
)} )}
@@ -59,7 +59,7 @@ export default function LoginPage() {
<button <button
type="submit" type="submit"
disabled={isPending} disabled={isPending}
className="w-full py-2 px-4 bg-[#85B7D7] hover:bg-[#6a9fc5] text-black font-medium rounded-lg transition-colors disabled:opacity-50 disabled:cursor-not-allowed text-sm" className="login-submit"
> >
{isPending ? 'Anmeldung läuft...' : 'Anmelden'} {isPending ? 'Anmeldung läuft...' : 'Anmelden'}
</button> </button>

View File

@@ -1,5 +1,6 @@
'use client'; 'use client';
import { useState } from 'react';
import LogoutButton from '@/components/LogoutButton'; import LogoutButton from '@/components/LogoutButton';
import packageJson from '@/package.json'; import packageJson from '@/package.json';
@@ -9,29 +10,31 @@ interface AppLayoutProps {
export default function AppLayout({ children }: AppLayoutProps) { export default function AppLayout({ children }: AppLayoutProps) {
const version = packageJson.version; const version = packageJson.version;
const buildDate = process.env.NEXT_PUBLIC_BUILD_DATE || new Date().toLocaleDateString('de-DE', { day: '2-digit', month: '2-digit', year: 'numeric' }); const [buildDate] = useState(() =>
process.env.NEXT_PUBLIC_BUILD_DATE || new Date().toLocaleDateString('de-DE', { day: '2-digit', month: '2-digit', year: 'numeric' })
);
return ( return (
<div className="min-h-screen py-8 px-4"> <div className="app-wrapper">
<div className="max-w-316 mx-auto border-2 border-black rounded-xl bg-gray-200 p-6"> <div className="app-container">
{/* Seitentitel */} {/* Seitentitel */}
<h1 className="text-4xl font-bold text-center mb-6 tracking-tight">Tabletten-Check</h1> <h1 className="app-title">Tabletten-Check</h1>
<div className="max-w-6xl mx-auto"> <div className="app-inner">
{/* Logout-Button oben rechts */} {/* Logout-Button oben rechts */}
<div className="flex justify-end -mb-0.5"> <div className="app-logout-bar">
<LogoutButton className="px-4 py-2 bg-red-600 hover:bg-red-700 text-white text-sm rounded-lg shadow-md" /> <LogoutButton className="btn-logout" />
</div> </div>
{/* Inhaltsbereich */} {/* Inhaltsbereich */}
<main className="border-2 border-black rounded-lg p-6 bg-[#FFFFDD]"> <main className="app-main">
{children} {children}
</main> </main>
<footer className="mt-8 flex justify-between items-center text-sm text-gray-600 px-4"> <footer className="app-footer">
<a href="mailto:rxf@gmx.de" className="hover:underline"> <a href="mailto:rxf@gmx.de">
mailto:rxf@gmx.de mailto:rxf@gmx.de
</a> </a>
<div>Version {version} {buildDate}</div> <div>Version {version} {buildDate}</div>

View File

@@ -15,7 +15,7 @@ export default function LogoutButton({ className, children }: LogoutButtonProps)
return ( return (
<button <button
onClick={handleLogout} onClick={handleLogout}
className={className || 'px-4 py-2 bg-red-600 hover:bg-red-700 text-white rounded-lg transition-colors'} className={className || 'btn-logout'}
> >
{children || 'Abmelden'} {children || 'Abmelden'}
</button> </button>

View File

@@ -29,6 +29,10 @@ export default function TablettenTable() {
try { try {
const res = await fetch(`/api/data?sidx=${sortField}&sord=${sortDir}`); const res = await fetch(`/api/data?sidx=${sortField}&sord=${sortDir}`);
const json = await res.json(); const json = await res.json();
if (!res.ok) {
setError(`Fehler beim Laden: ${json.error ?? res.status}`);
return;
}
setRows(json.values || []); setRows(json.values || []);
} catch { } catch {
setError('Fehler beim Laden der Daten.'); setError('Fehler beim Laden der Daten.');

View File

@@ -1,21 +1,22 @@
#!/bin/bash #!/bin/bash
# Deploy Script für tabletten # Deploy Script für laufschrift
# Baut das Docker Image und lädt es zu docker.citysensor.de hoch # Baut das Docker Image und lädt es zu docker.citysensor.de hoch
set -e set -e
# Konfiguration # Konfiguration
REGISTRY="docker.citysensor.de" REGISTRY="docker.citysensor.de"
IMAGE_NAME="tabletten" IMAGE_NAME="tabletten"
TAG="${1:-latest}" # Erster Parameter oder "latest" TAG="${TAG:-$(date +%Y%m%d%H%M)}" # default Datum
FULL_IMAGE="${REGISTRY}/${IMAGE_NAME}:${TAG}" FULL_IMAGE="${REGISTRY}/${IMAGE_NAME}:${TAG}"
# Build-Datum # Build-Datum
BUILD_DATE=$(date +%d.%m.%Y) BUILD_DATE=$(date +%d.%m.%Y)
echo "==========================================" echo "=========================================="
echo "Tabletten Deploy Script" echo " Deploy Script"
echo "==========================================" echo "=========================================="
echo "Registry: ${REGISTRY}" echo "Registry: ${REGISTRY}"
echo "Image: ${IMAGE_NAME}" echo "Image: ${IMAGE_NAME}"
@@ -46,6 +47,13 @@ docker buildx build \
--push \ --push \
. .
# 4. Keep :latest in sync for simple rollbacks and manual usage.
echo ">>> Tagge das image zusätzlich als :latest ..."
docker buildx imagetools create \
-t "${REGISTRY}/${IMAGE_NAME}:latest" \
"${FULL_IMAGE}"
echo ">>> Build und Push erfolgreich!" echo ">>> Build und Push erfolgreich!"
echo "" echo ""

21
docker-compose.local.yml Normal file
View File

@@ -0,0 +1,21 @@
# docker-compose.local.yml
# Lokaler Betrieb MySQL läuft bereits auf dem Host (localhost)
#
# Start:
# BUILD_DATE=$(date +%d.%m.%Y) docker compose -f docker-compose.local.yml up --build
services:
app:
build:
context: .
dockerfile: Dockerfile
args:
BUILD_DATE: "$(date +%d.%m.%Y)"
restart: unless-stopped
ports:
- "3000:3000"
environment:
# MySQL DB_HOST überschreibt localhost aus .env.local
DB_HOST: host.docker.internal
env_file:
- .env.local

View File

@@ -15,6 +15,8 @@ services:
build: build:
context: . context: .
dockerfile: Dockerfile dockerfile: Dockerfile
args:
BUILD_DATE: "$(date +%d.%m.%Y)"
platforms: platforms:
- linux/amd64 - linux/amd64
- linux/arm64 - linux/arm64

644
package-lock.json generated
View File

@@ -1,12 +1,12 @@
{ {
"name": "tabletten_next", "name": "tabletten_next",
"version": "0.1.0", "version": "1.0.0",
"lockfileVersion": 3, "lockfileVersion": 3,
"requires": true, "requires": true,
"packages": { "packages": {
"": { "": {
"name": "tabletten_next", "name": "tabletten_next",
"version": "0.1.0", "version": "1.0.0",
"dependencies": { "dependencies": {
"jose": "^6.2.1", "jose": "^6.2.1",
"moment": "^2.30.1", "moment": "^2.30.1",
@@ -18,7 +18,6 @@
"react-dom": "19.2.3" "react-dom": "19.2.3"
}, },
"devDependencies": { "devDependencies": {
"@tailwindcss/postcss": "^4",
"@types/node": "^20", "@types/node": "^20",
"@types/node-schedule": "^2.1.8", "@types/node-schedule": "^2.1.8",
"@types/nodemailer": "^7.0.11", "@types/nodemailer": "^7.0.11",
@@ -27,23 +26,9 @@
"eslint": "^9", "eslint": "^9",
"eslint-config-next": "16.1.6", "eslint-config-next": "16.1.6",
"mongodb": "^7.1.0", "mongodb": "^7.1.0",
"tailwindcss": "^4",
"typescript": "^5" "typescript": "^5"
} }
}, },
"node_modules/@alloc/quick-lru": {
"version": "5.2.0",
"resolved": "https://registry.npmjs.org/@alloc/quick-lru/-/quick-lru-5.2.0.tgz",
"integrity": "sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw==",
"dev": true,
"license": "MIT",
"engines": {
"node": ">=10"
},
"funding": {
"url": "https://github.com/sponsors/sindresorhus"
}
},
"node_modules/@babel/code-frame": { "node_modules/@babel/code-frame": {
"version": "7.29.0", "version": "7.29.0",
"resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.29.0.tgz", "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.29.0.tgz",
@@ -1261,277 +1246,6 @@
"tslib": "^2.8.0" "tslib": "^2.8.0"
} }
}, },
"node_modules/@tailwindcss/node": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/node/-/node-4.2.1.tgz",
"integrity": "sha512-jlx6sLk4EOwO6hHe1oCGm1Q4AN/s0rSrTTPBGPM0/RQ6Uylwq17FuU8IeJJKEjtc6K6O07zsvP+gDO6MMWo7pg==",
"dev": true,
"license": "MIT",
"dependencies": {
"@jridgewell/remapping": "^2.3.5",
"enhanced-resolve": "^5.19.0",
"jiti": "^2.6.1",
"lightningcss": "1.31.1",
"magic-string": "^0.30.21",
"source-map-js": "^1.2.1",
"tailwindcss": "4.2.1"
}
},
"node_modules/@tailwindcss/oxide": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide/-/oxide-4.2.1.tgz",
"integrity": "sha512-yv9jeEFWnjKCI6/T3Oq50yQEOqmpmpfzG1hcZsAOaXFQPfzWprWrlHSdGPEF3WQTi8zu8ohC9Mh9J470nT5pUw==",
"dev": true,
"license": "MIT",
"engines": {
"node": ">= 20"
},
"optionalDependencies": {
"@tailwindcss/oxide-android-arm64": "4.2.1",
"@tailwindcss/oxide-darwin-arm64": "4.2.1",
"@tailwindcss/oxide-darwin-x64": "4.2.1",
"@tailwindcss/oxide-freebsd-x64": "4.2.1",
"@tailwindcss/oxide-linux-arm-gnueabihf": "4.2.1",
"@tailwindcss/oxide-linux-arm64-gnu": "4.2.1",
"@tailwindcss/oxide-linux-arm64-musl": "4.2.1",
"@tailwindcss/oxide-linux-x64-gnu": "4.2.1",
"@tailwindcss/oxide-linux-x64-musl": "4.2.1",
"@tailwindcss/oxide-wasm32-wasi": "4.2.1",
"@tailwindcss/oxide-win32-arm64-msvc": "4.2.1",
"@tailwindcss/oxide-win32-x64-msvc": "4.2.1"
}
},
"node_modules/@tailwindcss/oxide-android-arm64": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-android-arm64/-/oxide-android-arm64-4.2.1.tgz",
"integrity": "sha512-eZ7G1Zm5EC8OOKaesIKuw77jw++QJ2lL9N+dDpdQiAB/c/B2wDh0QPFHbkBVrXnwNugvrbJFk1gK2SsVjwWReg==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"android"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-darwin-arm64": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-darwin-arm64/-/oxide-darwin-arm64-4.2.1.tgz",
"integrity": "sha512-q/LHkOstoJ7pI1J0q6djesLzRvQSIfEto148ppAd+BVQK0JYjQIFSK3JgYZJa+Yzi0DDa52ZsQx2rqytBnf8Hw==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"darwin"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-darwin-x64": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-darwin-x64/-/oxide-darwin-x64-4.2.1.tgz",
"integrity": "sha512-/f/ozlaXGY6QLbpvd/kFTro2l18f7dHKpB+ieXz+Cijl4Mt9AI2rTrpq7V+t04nK+j9XBQHnSMdeQRhbGyt6fw==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"darwin"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-freebsd-x64": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-freebsd-x64/-/oxide-freebsd-x64-4.2.1.tgz",
"integrity": "sha512-5e/AkgYJT/cpbkys/OU2Ei2jdETCLlifwm7ogMC7/hksI2fC3iiq6OcXwjibcIjPung0kRtR3TxEITkqgn0TcA==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"freebsd"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-linux-arm-gnueabihf": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-arm-gnueabihf/-/oxide-linux-arm-gnueabihf-4.2.1.tgz",
"integrity": "sha512-Uny1EcVTTmerCKt/1ZuKTkb0x8ZaiuYucg2/kImO5A5Y/kBz41/+j0gxUZl+hTF3xkWpDmHX+TaWhOtba2Fyuw==",
"cpu": [
"arm"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-linux-arm64-gnu": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-arm64-gnu/-/oxide-linux-arm64-gnu-4.2.1.tgz",
"integrity": "sha512-CTrwomI+c7n6aSSQlsPL0roRiNMDQ/YzMD9EjcR+H4f0I1SQ8QqIuPnsVp7QgMkC1Qi8rtkekLkOFjo7OlEFRQ==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-linux-arm64-musl": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-arm64-musl/-/oxide-linux-arm64-musl-4.2.1.tgz",
"integrity": "sha512-WZA0CHRL/SP1TRbA5mp9htsppSEkWuQ4KsSUumYQnyl8ZdT39ntwqmz4IUHGN6p4XdSlYfJwM4rRzZLShHsGAQ==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-linux-x64-gnu": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-x64-gnu/-/oxide-linux-x64-gnu-4.2.1.tgz",
"integrity": "sha512-qMFzxI2YlBOLW5PhblzuSWlWfwLHaneBE0xHzLrBgNtqN6mWfs+qYbhryGSXQjFYB1Dzf5w+LN5qbUTPhW7Y5g==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-linux-x64-musl": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-linux-x64-musl/-/oxide-linux-x64-musl-4.2.1.tgz",
"integrity": "sha512-5r1X2FKnCMUPlXTWRYpHdPYUY6a1Ar/t7P24OuiEdEOmms5lyqjDRvVY1yy9Rmioh+AunQ0rWiOTPE8F9A3v5g==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-wasm32-wasi": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-wasm32-wasi/-/oxide-wasm32-wasi-4.2.1.tgz",
"integrity": "sha512-MGFB5cVPvshR85MTJkEvqDUnuNoysrsRxd6vnk1Lf2tbiqNlXpHYZqkqOQalydienEWOHHFyyuTSYRsLfxFJ2Q==",
"bundleDependencies": [
"@napi-rs/wasm-runtime",
"@emnapi/core",
"@emnapi/runtime",
"@tybys/wasm-util",
"@emnapi/wasi-threads",
"tslib"
],
"cpu": [
"wasm32"
],
"dev": true,
"license": "MIT",
"optional": true,
"dependencies": {
"@emnapi/core": "^1.8.1",
"@emnapi/runtime": "^1.8.1",
"@emnapi/wasi-threads": "^1.1.0",
"@napi-rs/wasm-runtime": "^1.1.1",
"@tybys/wasm-util": "^0.10.1",
"tslib": "^2.8.1"
},
"engines": {
"node": ">=14.0.0"
}
},
"node_modules/@tailwindcss/oxide-win32-arm64-msvc": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-win32-arm64-msvc/-/oxide-win32-arm64-msvc-4.2.1.tgz",
"integrity": "sha512-YlUEHRHBGnCMh4Nj4GnqQyBtsshUPdiNroZj8VPkvTZSoHsilRCwXcVKnG9kyi0ZFAS/3u+qKHBdDc81SADTRA==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"win32"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/oxide-win32-x64-msvc": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/oxide-win32-x64-msvc/-/oxide-win32-x64-msvc-4.2.1.tgz",
"integrity": "sha512-rbO34G5sMWWyrN/idLeVxAZgAKWrn5LiR3/I90Q9MkA67s6T1oB0xtTe+0heoBvHSpbU9Mk7i6uwJnpo4u21XQ==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT",
"optional": true,
"os": [
"win32"
],
"engines": {
"node": ">= 20"
}
},
"node_modules/@tailwindcss/postcss": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/@tailwindcss/postcss/-/postcss-4.2.1.tgz",
"integrity": "sha512-OEwGIBnXnj7zJeonOh6ZG9woofIjGrd2BORfvE5p9USYKDCZoQmfqLcfNiRWoJlRWLdNPn2IgVZuWAOM4iTYMw==",
"dev": true,
"license": "MIT",
"dependencies": {
"@alloc/quick-lru": "^5.2.0",
"@tailwindcss/node": "4.2.1",
"@tailwindcss/oxide": "4.2.1",
"postcss": "^8.5.6",
"tailwindcss": "4.2.1"
}
},
"node_modules/@tybys/wasm-util": { "node_modules/@tybys/wasm-util": {
"version": "0.10.1", "version": "0.10.1",
"resolved": "https://registry.npmjs.org/@tybys/wasm-util/-/wasm-util-0.10.1.tgz", "resolved": "https://registry.npmjs.org/@tybys/wasm-util/-/wasm-util-0.10.1.tgz",
@@ -2887,8 +2601,8 @@
"version": "2.1.2", "version": "2.1.2",
"resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.2.tgz", "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.2.tgz",
"integrity": "sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==", "integrity": "sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==",
"devOptional": true,
"license": "Apache-2.0", "license": "Apache-2.0",
"optional": true,
"engines": { "engines": {
"node": ">=8" "node": ">=8"
} }
@@ -2935,20 +2649,6 @@
"dev": true, "dev": true,
"license": "MIT" "license": "MIT"
}, },
"node_modules/enhanced-resolve": {
"version": "5.20.0",
"resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.20.0.tgz",
"integrity": "sha512-/ce7+jQ1PQ6rVXwe+jKEg5hW5ciicHwIQUagZkp6IufBoY3YDgdTTY1azVs0qoRgVmvsNB+rbjLJxDAeHHtwsQ==",
"dev": true,
"license": "MIT",
"dependencies": {
"graceful-fs": "^4.2.4",
"tapable": "^2.3.0"
},
"engines": {
"node": ">=10.13.0"
}
},
"node_modules/es-abstract": { "node_modules/es-abstract": {
"version": "1.24.1", "version": "1.24.1",
"resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.1.tgz", "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.24.1.tgz",
@@ -3918,13 +3618,6 @@
"url": "https://github.com/sponsors/ljharb" "url": "https://github.com/sponsors/ljharb"
} }
}, },
"node_modules/graceful-fs": {
"version": "4.2.11",
"resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.11.tgz",
"integrity": "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==",
"dev": true,
"license": "ISC"
},
"node_modules/has-bigints": { "node_modules/has-bigints": {
"version": "1.1.0", "version": "1.1.0",
"resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz", "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.1.0.tgz",
@@ -4557,16 +4250,6 @@
"node": ">= 0.4" "node": ">= 0.4"
} }
}, },
"node_modules/jiti": {
"version": "2.6.1",
"resolved": "https://registry.npmjs.org/jiti/-/jiti-2.6.1.tgz",
"integrity": "sha512-ekilCSN1jwRvIbgeg/57YFh8qQDNbwDb9xT/qu2DAHbFFZUicIl4ygVaAvzveMhMVr3LnpSKTNnwt8PoOfmKhQ==",
"dev": true,
"license": "MIT",
"bin": {
"jiti": "lib/jiti-cli.mjs"
}
},
"node_modules/jose": { "node_modules/jose": {
"version": "6.2.1", "version": "6.2.1",
"resolved": "https://registry.npmjs.org/jose/-/jose-6.2.1.tgz", "resolved": "https://registry.npmjs.org/jose/-/jose-6.2.1.tgz",
@@ -4703,267 +4386,6 @@
"node": ">= 0.8.0" "node": ">= 0.8.0"
} }
}, },
"node_modules/lightningcss": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss/-/lightningcss-1.31.1.tgz",
"integrity": "sha512-l51N2r93WmGUye3WuFoN5k10zyvrVs0qfKBhyC5ogUQ6Ew6JUSswh78mbSO+IU3nTWsyOArqPCcShdQSadghBQ==",
"dev": true,
"license": "MPL-2.0",
"dependencies": {
"detect-libc": "^2.0.3"
},
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
},
"optionalDependencies": {
"lightningcss-android-arm64": "1.31.1",
"lightningcss-darwin-arm64": "1.31.1",
"lightningcss-darwin-x64": "1.31.1",
"lightningcss-freebsd-x64": "1.31.1",
"lightningcss-linux-arm-gnueabihf": "1.31.1",
"lightningcss-linux-arm64-gnu": "1.31.1",
"lightningcss-linux-arm64-musl": "1.31.1",
"lightningcss-linux-x64-gnu": "1.31.1",
"lightningcss-linux-x64-musl": "1.31.1",
"lightningcss-win32-arm64-msvc": "1.31.1",
"lightningcss-win32-x64-msvc": "1.31.1"
}
},
"node_modules/lightningcss-android-arm64": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-android-arm64/-/lightningcss-android-arm64-1.31.1.tgz",
"integrity": "sha512-HXJF3x8w9nQ4jbXRiNppBCqeZPIAfUo8zE/kOEGbW5NZvGc/K7nMxbhIr+YlFlHW5mpbg/YFPdbnCh1wAXCKFg==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"android"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-darwin-arm64": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-darwin-arm64/-/lightningcss-darwin-arm64-1.31.1.tgz",
"integrity": "sha512-02uTEqf3vIfNMq3h/z2cJfcOXnQ0GRwQrkmPafhueLb2h7mqEidiCzkE4gBMEH65abHRiQvhdcQ+aP0D0g67sg==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"darwin"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-darwin-x64": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-darwin-x64/-/lightningcss-darwin-x64-1.31.1.tgz",
"integrity": "sha512-1ObhyoCY+tGxtsz1lSx5NXCj3nirk0Y0kB/g8B8DT+sSx4G9djitg9ejFnjb3gJNWo7qXH4DIy2SUHvpoFwfTA==",
"cpu": [
"x64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"darwin"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-freebsd-x64": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-freebsd-x64/-/lightningcss-freebsd-x64-1.31.1.tgz",
"integrity": "sha512-1RINmQKAItO6ISxYgPwszQE1BrsVU5aB45ho6O42mu96UiZBxEXsuQ7cJW4zs4CEodPUioj/QrXW1r9pLUM74A==",
"cpu": [
"x64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"freebsd"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-linux-arm-gnueabihf": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-linux-arm-gnueabihf/-/lightningcss-linux-arm-gnueabihf-1.31.1.tgz",
"integrity": "sha512-OOCm2//MZJ87CdDK62rZIu+aw9gBv4azMJuA8/KB74wmfS3lnC4yoPHm0uXZ/dvNNHmnZnB8XLAZzObeG0nS1g==",
"cpu": [
"arm"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-linux-arm64-gnu": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-linux-arm64-gnu/-/lightningcss-linux-arm64-gnu-1.31.1.tgz",
"integrity": "sha512-WKyLWztD71rTnou4xAD5kQT+982wvca7E6QoLpoawZ1gP9JM0GJj4Tp5jMUh9B3AitHbRZ2/H3W5xQmdEOUlLg==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-linux-arm64-musl": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-linux-arm64-musl/-/lightningcss-linux-arm64-musl-1.31.1.tgz",
"integrity": "sha512-mVZ7Pg2zIbe3XlNbZJdjs86YViQFoJSpc41CbVmKBPiGmC4YrfeOyz65ms2qpAobVd7WQsbW4PdsSJEMymyIMg==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-linux-x64-gnu": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-linux-x64-gnu/-/lightningcss-linux-x64-gnu-1.31.1.tgz",
"integrity": "sha512-xGlFWRMl+0KvUhgySdIaReQdB4FNudfUTARn7q0hh/V67PVGCs3ADFjw+6++kG1RNd0zdGRlEKa+T13/tQjPMA==",
"cpu": [
"x64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-linux-x64-musl": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-linux-x64-musl/-/lightningcss-linux-x64-musl-1.31.1.tgz",
"integrity": "sha512-eowF8PrKHw9LpoZii5tdZwnBcYDxRw2rRCyvAXLi34iyeYfqCQNA9rmUM0ce62NlPhCvof1+9ivRaTY6pSKDaA==",
"cpu": [
"x64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-win32-arm64-msvc": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-win32-arm64-msvc/-/lightningcss-win32-arm64-msvc-1.31.1.tgz",
"integrity": "sha512-aJReEbSEQzx1uBlQizAOBSjcmr9dCdL3XuC/6HLXAxmtErsj2ICo5yYggg1qOODQMtnjNQv2UHb9NpOuFtYe4w==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"win32"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/lightningcss-win32-x64-msvc": {
"version": "1.31.1",
"resolved": "https://registry.npmjs.org/lightningcss-win32-x64-msvc/-/lightningcss-win32-x64-msvc-1.31.1.tgz",
"integrity": "sha512-I9aiFrbd7oYHwlnQDqr1Roz+fTz61oDDJX7n9tYF9FJymH1cIN1DtKw3iYt6b8WZgEjoNwVSncwF4wx/ZedMhw==",
"cpu": [
"x64"
],
"dev": true,
"license": "MPL-2.0",
"optional": true,
"os": [
"win32"
],
"engines": {
"node": ">= 12.0.0"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/parcel"
}
},
"node_modules/locate-path": { "node_modules/locate-path": {
"version": "6.0.0", "version": "6.0.0",
"resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz",
@@ -5046,16 +4468,6 @@
"node": ">=12" "node": ">=12"
} }
}, },
"node_modules/magic-string": {
"version": "0.30.21",
"resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.30.21.tgz",
"integrity": "sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==",
"dev": true,
"license": "MIT",
"dependencies": {
"@jridgewell/sourcemap-codec": "^1.5.5"
}
},
"node_modules/math-intrinsics": { "node_modules/math-intrinsics": {
"version": "1.1.0", "version": "1.1.0",
"resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz",
@@ -5662,35 +5074,6 @@
"node": ">= 0.4" "node": ">= 0.4"
} }
}, },
"node_modules/postcss": {
"version": "8.5.8",
"resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.8.tgz",
"integrity": "sha512-OW/rX8O/jXnm82Ey1k44pObPtdblfiuWnrd8X7GJ7emImCOstunGbXUpp7HdBrFQX6rJzn3sPT397Wp5aCwCHg==",
"dev": true,
"funding": [
{
"type": "opencollective",
"url": "https://opencollective.com/postcss/"
},
{
"type": "tidelift",
"url": "https://tidelift.com/funding/github/npm/postcss"
},
{
"type": "github",
"url": "https://github.com/sponsors/ai"
}
],
"license": "MIT",
"dependencies": {
"nanoid": "^3.3.11",
"picocolors": "^1.1.1",
"source-map-js": "^1.2.1"
},
"engines": {
"node": "^10 || ^12 || >=14"
}
},
"node_modules/prelude-ls": { "node_modules/prelude-ls": {
"version": "1.2.1", "version": "1.2.1",
"resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz",
@@ -6423,27 +5806,6 @@
"url": "https://github.com/sponsors/ljharb" "url": "https://github.com/sponsors/ljharb"
} }
}, },
"node_modules/tailwindcss": {
"version": "4.2.1",
"resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-4.2.1.tgz",
"integrity": "sha512-/tBrSQ36vCleJkAOsy9kbNTgaxvGbyOamC30PRePTQe/o1MFwEKHQk4Cn7BNGaPtjp+PuUrByJehM1hgxfq4sw==",
"dev": true,
"license": "MIT"
},
"node_modules/tapable": {
"version": "2.3.0",
"resolved": "https://registry.npmjs.org/tapable/-/tapable-2.3.0.tgz",
"integrity": "sha512-g9ljZiwki/LfxmQADO3dEY1CbpmXT5Hm2fJ+QaGKwSXUylMybePR7/67YW7jOrrvjEgL1Fmz5kzyAjWVWLlucg==",
"dev": true,
"license": "MIT",
"engines": {
"node": ">=6"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/webpack"
}
},
"node_modules/tinyglobby": { "node_modules/tinyglobby": {
"version": "0.2.15", "version": "0.2.15",
"resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.15.tgz", "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.15.tgz",

View File

@@ -1,6 +1,6 @@
{ {
"name": "tabletten_next", "name": "tabletten_next",
"version": "1.0.0", "version": "1.2.1",
"private": true, "private": true,
"scripts": { "scripts": {
"dev": "next dev", "dev": "next dev",
@@ -19,7 +19,6 @@
"react-dom": "19.2.3" "react-dom": "19.2.3"
}, },
"devDependencies": { "devDependencies": {
"@tailwindcss/postcss": "^4",
"@types/node": "^20", "@types/node": "^20",
"@types/node-schedule": "^2.1.8", "@types/node-schedule": "^2.1.8",
"@types/nodemailer": "^7.0.11", "@types/nodemailer": "^7.0.11",
@@ -28,7 +27,6 @@
"eslint": "^9", "eslint": "^9",
"eslint-config-next": "16.1.6", "eslint-config-next": "16.1.6",
"mongodb": "^7.1.0", "mongodb": "^7.1.0",
"tailwindcss": "^4",
"typescript": "^5" "typescript": "^5"
} }
} }

View File

@@ -1,7 +1,5 @@
const config = { const config = {
plugins: { plugins: {},
"@tailwindcss/postcss": {},
},
}; };
export default config; export default config;