From 66581ef58472db51f06894408a0d562e413081aa Mon Sep 17 00:00:00 2001 From: Duarte Date: Sun, 31 May 2026 20:22:50 +0100 Subject: [PATCH] feat: bootstrap project --- .clinrules | 123 + .env.example | 2 + .gitignore | 25 + .npmrc | 1 + .vscode/extensions.json | 3 + README.md | 42 + docs/assets/Refood Rotas-v2.png | Bin 0 -> 48225 bytes docs/developer-profile.md | 17 + docs/project-description.md | 31 + docs/user-stories/00-Generic/US-template.md | 22 + .../00-Generic/US00-bootstrap-admin.md | 19 + docs/user-stories/00-Generic/US01-login.md | 27 + .../00-Generic/US07-menu-gestao.md | 29 + .../00-Generic/US08-registar-entrega.md | 19 + .../00-Generic/US09-registo-entregas-ui.md | 40 + .../US10-nome-beneficiario-botao.md | 26 + .../00-Generic/US11-ajustes-navegacao.md | 26 + .../00-Generic/US12-apagar-entrega.md | 28 + .../00-Generic/US13-gestao-utilizadores.md | 42 + .../00-Generic/US14-homepage-botoes.md | 32 + .../01-Admin/US02-listar-beneficiarios.md | 33 + .../01-Admin/US03-detalhe-beneficiario.md | 37 + .../01-Admin/US04-listar-turnos.md | 32 + .../01-Admin/US05-editar-turnos.md | 34 + .../01-Admin/US06-bootstrap-turnos.md | 36 + drizzle.config.ts | 11 + package-lock.json | 4254 +++++++++++++++++ package.json | 38 + src/app.d.ts | 19 + src/app.html | 12 + src/hooks.server.ts | 84 + src/lib/assets/favicon.svg | 1 + src/lib/index.ts | 1 + src/lib/server/db/index.ts | 60 + src/lib/server/db/schema.ts | 52 + src/routes/+layout.server.ts | 7 + src/routes/+layout.svelte | 127 + src/routes/+page.server.ts | 11 + src/routes/+page.svelte | 95 + .../admin/beneficiarios/+page.server.ts | 45 + src/routes/admin/beneficiarios/+page.svelte | 131 + .../admin/beneficiarios/[id]/+page.server.ts | 120 + .../admin/beneficiarios/[id]/+page.svelte | 144 + .../admin/beneficiarios/novo/+page.server.ts | 83 + .../admin/beneficiarios/novo/+page.svelte | 133 + src/routes/admin/turnos/+page.server.ts | 24 + src/routes/admin/turnos/+page.svelte | 128 + src/routes/admin/turnos/[id]/+page.server.ts | 104 + src/routes/admin/turnos/[id]/+page.svelte | 136 + src/routes/admin/utilizadores/+page.server.ts | 29 + src/routes/admin/utilizadores/+page.svelte | 97 + .../admin/utilizadores/[id]/+page.server.ts | 129 + .../admin/utilizadores/[id]/+page.svelte | 111 + .../admin/utilizadores/novo/+page.server.ts | 91 + .../admin/utilizadores/novo/+page.svelte | 109 + src/routes/entregas/+page.server.ts | 193 + src/routes/entregas/+page.svelte | 333 ++ src/routes/login/+page.server.ts | 92 + src/routes/login/+page.svelte | 111 + src/routes/logout/+page.server.ts | 25 + static/logo.png | Bin 0 -> 48225 bytes static/robots.txt | 3 + svelte.config.js | 20 + tsconfig.json | 20 + vite.config.ts | 6 + 65 files changed, 7915 insertions(+) create mode 100644 .clinrules create mode 100644 .env.example create mode 100644 .gitignore create mode 100644 .npmrc create mode 100644 .vscode/extensions.json create mode 100644 README.md create mode 100644 docs/assets/Refood Rotas-v2.png create mode 100644 docs/developer-profile.md create mode 100644 docs/project-description.md create mode 100644 docs/user-stories/00-Generic/US-template.md create mode 100644 docs/user-stories/00-Generic/US00-bootstrap-admin.md create mode 100644 docs/user-stories/00-Generic/US01-login.md create mode 100644 docs/user-stories/00-Generic/US07-menu-gestao.md create mode 100644 docs/user-stories/00-Generic/US08-registar-entrega.md create mode 100644 docs/user-stories/00-Generic/US09-registo-entregas-ui.md create mode 100644 docs/user-stories/00-Generic/US10-nome-beneficiario-botao.md create mode 100644 docs/user-stories/00-Generic/US11-ajustes-navegacao.md create mode 100644 docs/user-stories/00-Generic/US12-apagar-entrega.md create mode 100644 docs/user-stories/00-Generic/US13-gestao-utilizadores.md create mode 100644 docs/user-stories/00-Generic/US14-homepage-botoes.md create mode 100644 docs/user-stories/01-Admin/US02-listar-beneficiarios.md create mode 100644 docs/user-stories/01-Admin/US03-detalhe-beneficiario.md create mode 100644 docs/user-stories/01-Admin/US04-listar-turnos.md create mode 100644 docs/user-stories/01-Admin/US05-editar-turnos.md create mode 100644 docs/user-stories/01-Admin/US06-bootstrap-turnos.md create mode 100644 drizzle.config.ts create mode 100644 package-lock.json create mode 100644 package.json create mode 100644 src/app.d.ts create mode 100644 src/app.html create mode 100644 src/hooks.server.ts create mode 100644 src/lib/assets/favicon.svg create mode 100644 src/lib/index.ts create mode 100644 src/lib/server/db/index.ts create mode 100644 src/lib/server/db/schema.ts create mode 100644 src/routes/+layout.server.ts create mode 100644 src/routes/+layout.svelte create mode 100644 src/routes/+page.server.ts create mode 100644 src/routes/+page.svelte create mode 100644 src/routes/admin/beneficiarios/+page.server.ts create mode 100644 src/routes/admin/beneficiarios/+page.svelte create mode 100644 src/routes/admin/beneficiarios/[id]/+page.server.ts create mode 100644 src/routes/admin/beneficiarios/[id]/+page.svelte create mode 100644 src/routes/admin/beneficiarios/novo/+page.server.ts create mode 100644 src/routes/admin/beneficiarios/novo/+page.svelte create mode 100644 src/routes/admin/turnos/+page.server.ts create mode 100644 src/routes/admin/turnos/+page.svelte create mode 100644 src/routes/admin/turnos/[id]/+page.server.ts create mode 100644 src/routes/admin/turnos/[id]/+page.svelte create mode 100644 src/routes/admin/utilizadores/+page.server.ts create mode 100644 src/routes/admin/utilizadores/+page.svelte create mode 100644 src/routes/admin/utilizadores/[id]/+page.server.ts create mode 100644 src/routes/admin/utilizadores/[id]/+page.svelte create mode 100644 src/routes/admin/utilizadores/novo/+page.server.ts create mode 100644 src/routes/admin/utilizadores/novo/+page.svelte create mode 100644 src/routes/entregas/+page.server.ts create mode 100644 src/routes/entregas/+page.svelte create mode 100644 src/routes/login/+page.server.ts create mode 100644 src/routes/login/+page.svelte create mode 100644 src/routes/logout/+page.server.ts create mode 100644 static/logo.png create mode 100644 static/robots.txt create mode 100644 svelte.config.js create mode 100644 tsconfig.json create mode 100644 vite.config.ts diff --git a/.clinrules b/.clinrules new file mode 100644 index 0000000..bfbd758 --- /dev/null +++ b/.clinrules @@ -0,0 +1,123 @@ +# .clinrules + +## Project Overview + +This project is a personal web application developed using a unified, full-stack architecture: + +* SvelteKit (latest stable, Node adapter) +* TypeScript +* Bootstrap 5 +* SQLite (local file-based database) +* Drizzle ORM (lightweight, type-safe SQL query builder) +* Caddy or Nginx (production reverse proxy with SSL) + +Primary goals: + +1. Simplicity +2. Minimal operational overhead (suited for a small VPS with 2 cores, 4GB RAM) +3. High readability and maintainability +4. Fast development cycle +5. AI-generated code consistency + +The application is targeted specifically for desktop browsers and tablet devices, and is expected to remain relatively small (<20 database tables) with low concurrency (<5 users). + +--- + +## General Principles + +* Prefer the simplest solution that satisfies the requirement. +* Avoid over-engineering and premature optimization. +* Avoid introducing unnecessary abstractions (e.g., repository patterns). +* Favor explicit code over clever/implicit code. +* Prioritize readability over conciseness. + +--- + +## Architecture (SvelteKit Full-Stack) + +We use SvelteKit's unified server/client model. There is no separate backend service. + +```text +src/ +├── routes/ # SvelteKit pages and server endpoints (+page.svelte, +page.server.ts, +server.ts) +├── lib/ +│ ├── components/ # Reusable Svelte UI components +│ ├── db/ # Database connection, schemas, and migrations +│ │ ├── schema.ts # Drizzle schema definitions +│ │ └── index.ts # SQLite client initialization +│ ├── services/ # Server-side business logic +│ ├── types/ # Shared TypeScript definitions +│ └── utils/ # Helper functions +``` + +Rules: +* Use TypeScript everywhere. +* Keep components focused and small. +* Implement business logic in `lib/services/` or directly inside `+page.server.ts` actions. +* Never query the database directly from frontend code; database queries must occur exclusively in server files (`*.server.ts`). + +--- + +## Database (SQLite + Drizzle) + +Use: +* SQLite (local file: e.g., `data/sqlite.db`) +* Drizzle ORM for schema definitions and migrations + +Rules: +* Define schemas explicitly in `src/lib/db/schema.ts`. +* Use Drizzle Kit for generating and running schema migrations. +* Use UUIDs or auto-incrementing integers for primary keys consistently. +* Define appropriate foreign keys and cascading delete rules. + +--- + +## Authentication + +Use: +* Secure cookie-based sessions (stored in the SQLite database). +* Password hashing using `argon2` or `bcrypt`. +* Manage sessions via SvelteKit server hooks (`src/hooks.server.ts`). +* Avoid external OAuth/identity providers unless explicitly requested. + +--- + +## Bootstrap Rules + +Use Bootstrap 5 as the primary UI framework. + +Rules: +* Prefer standard Bootstrap components before creating custom CSS. +* Avoid unnecessary custom CSS; keep styling simple. +* Favor responsiveness using Bootstrap's responsive grid system and utility classes, with a primary design focus on desktop and tablet screens. + +--- + +## Error Handling + +* Handle errors explicitly on the server side. +* Return user-friendly error messages using SvelteKit's `error` helpers. +* Log technical details server-side. Never expose raw stack traces to the user interface. + +--- + +## Deployment & Ops + +* SvelteKit must be built using the Node adapter (`@sveltejs/adapter-node`) for server-side execution. +* The application runs locally or in production as a Node.js process listening on a port (e.g., `3000`). +* Nginx or Caddy handles SSL termination and reverse proxies requests to port `3000`. + +--- + +## AI Agent Behavior + +Before coding: +1. Understand the requirement. +2. Review existing files and follow established patterns. +3. Minimize changes. + +Prohibitions (do NOT use unless explicitly requested): +* Clean Architecture / CQRS +* Event Sourcing +* Generic Repository Patterns +* Enterprise/Factory-heavy designs diff --git a/.env.example b/.env.example new file mode 100644 index 0000000..b86d245 --- /dev/null +++ b/.env.example @@ -0,0 +1,2 @@ +# Drizzle +DATABASE_URL=local.db diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..23be534 --- /dev/null +++ b/.gitignore @@ -0,0 +1,25 @@ +node_modules + +# Output +.output +.vercel +.netlify +.wrangler +/.svelte-kit +/build + +# OS +.DS_Store +Thumbs.db + +# Env +.env +.env.* +!.env.example +!.env.test + +# Vite +vite.config.js.timestamp-* +vite.config.ts.timestamp-* +# SQLite +*.db diff --git a/.npmrc b/.npmrc new file mode 100644 index 0000000..b6f27f1 --- /dev/null +++ b/.npmrc @@ -0,0 +1 @@ +engine-strict=true diff --git a/.vscode/extensions.json b/.vscode/extensions.json new file mode 100644 index 0000000..28d1e67 --- /dev/null +++ b/.vscode/extensions.json @@ -0,0 +1,3 @@ +{ + "recommendations": ["svelte.svelte-vscode"] +} diff --git a/README.md b/README.md new file mode 100644 index 0000000..209bbee --- /dev/null +++ b/README.md @@ -0,0 +1,42 @@ +# sv + +Everything you need to build a Svelte project, powered by [`sv`](https://github.com/sveltejs/cli). + +## Creating a project + +If you're seeing this, you've probably already done this step. Congrats! + +```sh +# create a new project +npx sv create my-app +``` + +To recreate this project with the same configuration: + +```sh +# recreate this project +npx sv@0.15.3 create --template minimal --types ts --add sveltekit-adapter="adapter:node" drizzle="database:sqlite+sqlite:better-sqlite3" --no-download-check --install npm ./ +``` + +## Developing + +Once you've created a project and installed dependencies with `npm install` (or `pnpm install` or `yarn`), start a development server: + +```sh +npm run dev + +# or start the server and open the app in a new browser tab +npm run dev -- --open +``` + +## Building + +To create a production version of your app: + +```sh +npm run build +``` + +You can preview the production build with `npm run preview`. + +> To deploy your app, you may need to install an [adapter](https://svelte.dev/docs/kit/adapters) for your target environment. diff --git a/docs/assets/Refood Rotas-v2.png b/docs/assets/Refood Rotas-v2.png new file mode 100644 index 0000000000000000000000000000000000000000..426f5f061f430718d7a0ec464a66fad208a3c8a7 GIT binary patch literal 48225 zcmeFZd064{$4-zbRr?6vi8oa>Rt4fOj ze@5QzfhC$3*_heyo8W4|F*PQiWKCsd=>a702LkXG1_6KpzkLKhME~bINDV*> z1NYzk7kb!WU;zy9ssnz^1K|I=ZvlRP`TGKXUY`HI*Z2v&9uR+!)a zoAu=hgx~+0DHig$2HIq37$xP^830y}6{c#d}ZT@6hXJin)}9wA*1_|3?{$7a~RIqK}@z zJpdy8qLVLITJ1oP1^}Q!RY3NGq;N`i4*ROm)J91zL_@|#tlM8Y99(G8*B z=4354JbkFqYeew7Y!8$V@QH#41>skJRccWGag;PPDnzq=qEfT8&X->+aZ3>J!F*+O z34BR}FJB|RKHd8+YXWT$DNJU-UuM_~r>5BjfgVcmvV^5rhHTFKlX&%&lqy{)sOnsTYTi3ny)@uhU$4l zyt{AEljc|>0b+$fLGELih+%N;ZEm_-cz{Px@L&LR!AEgNkX$Pol+ZC{A7?jWz2 zymEILrh(&=qtIi(e-a7x#^z0e4vd267;L!pMY*N}L|Tw4+en-l$r`0Uq{gFq!%$>r zoiawvcYYom8svxxgaJNcfHb*uUTo-0o|gP=9BP^YOz8+Qvz784_#K73e=pCKA_BBz z;F2qZWDfJ|BioXBlA*i|ffP~>^WO!+D$*wFp*T@j!0!$40DKbOTx>WocwYT5 z{M+~Un?TwD^PbMvori3|{_SDl#flT61>_TJZ| zB9rZfV~+7b+=Ekb-0Wa}7l4Y$=NPK}R!%Zc{6qTNAx0_-yr5YE3wPfGl4#6YJmB~2 zi-eGEn3~)4+P5$ADzx_OQ51S$RSPQ4F-NPsj41d*fCAtIM)C=t)-<{v<`0F=h+wTR zGvj+C7=~?7Lg@jYEMHK=`Nzn)Tii#ufSY+&%l@q=-H7R-B`}QB-VO!`eho4dCsxtD zLzVwntyt*m6%}gUnAxD@GKcteB*>@#$jD6k;TG)-?ffnzN`I*NN};nD6x6_3c)MuG zYe0leWD?E?_-C%kbLT*DK(C8+fSi zW#s2W3J$Lerby9`QlWbkPcc`la&Um}8xYj6Jr^4vmt0BrtMYy4V|00SNiL048huhf zU^d2qEBpjkXgAv0(6P7|Gj|jV!``7A2NcC0T z%1A#`1~uL?#aqSU;qjLd?_Wmz9vB{9v07fQ=7x8Q|3#Z(IlVyS$u%cy2qF#X-ODyv zW3JvDq&j`JF*A=pdvUe_#0dHz{3D?y!mGAAi22^q{{mhLOJ9fYbsB z0FMIl0e;EbS@GV*ruR^CZ&;{)ec4$5>lb_kc%P`=|BKKs$esrDb@s?}pH1KTA=O|0 zAUDc7or+x&|I8p02>t#Fpk)QApvB@7h|0P0Mg@VKp8kCgm4p!Yb$*B?ku&qKqaX!H z%@0rjMNU~2Oz@lqXxI-8FOpzht5P4PiOoUw^dJ?5vIU^ce>pVKo_g&!cbQM;|KOdO zvgPf4CiErp1v9arw@qHvFSrru@X8tUL;;j-4mR@Uil9TUMA?gs)Q&KzF|jf~1}o%L z*pjO%mD?H~)T?vNJ)*+}S}oZW&)ek(6_KZ+mH>d4IC!ufhLvMX3r9}1t2)7x!OE}w zizOY)i16*<;ybxaBuwS8q&(0YflIFlzibtr_&~kqz?wmvoGWS| zU)i#WHieenOto8HjWOljzaaddJyn}TBX^@O3Ptoq=~&yncHvvKjUUJhOs0^W5-8%6 zk5wAxTvT8etf307UCN#Iq)xc%fZzf?EH6-2L)_A!RjonlE-;NEaI7fc??I~%3CorF zdH*>#!u1~A^-y8xjpi2^K=|cMmv&teQa+Q38B0nQNKIzQ7>#ftv*;;h7Dc5vIz4_W ztxr!=7fJAW<)i8cp6;#Do!NwGhov!&WN)wv%|Lls{@uE4eEl-uPGY0!8CoG|yqXC3 zkb-o4nf(+M^S(xM4!$UrVlO=J*F<-L)>plG(bFY^^MT^oBl2QsDJ*b;1_}}y+yeDR zP+);@xKtYDzT)p+T4e3-=AVQM;z+kFr6G#UfKR~7lrpnq`C73`m`0@mOsv?<_7eIXq5#*|plSCW=O#1_0c?h@R)yigmt?pa$&j*_q(e?Ig*Fc2r`y z$>3}IQ7M$T{fP=)WYEll6xy&VianD_WiU~vv%DQ8kX_Khk-0`4sTeFU69l#G`&MwT zE4g;qET4jYX$6^+;yCuI39)3mvy`O0g=++Op!)d=?d)R7I=MxS}L99 zridIT+Q-z@2kb{WQ7Mz5;12rWK%x6$7fr3JJ{+S~h7q$AR4t5B=p0hH1~>V1tf$00 z4xT@L7D<~7^-z2@J(C4qF!FX#;c>ol?maH;JH?~5IMUVlURDU`h$uBYqXQIg)M~^f zqzAQU2D81HO})@~S>8)Hga(FD43uiV2Hlx&Q*Z=P>Qc{SH0dmP`l8h#=#!%FX9X=T z9h>g)^N2pLK;8krK!@#%-&bj2iOqLx+tii8!5UlB;uy2G)q568j~KFP=Zv*jz!w7W zB&5)=&nz*mFk)D+CjR8el{n%Z#{dJ8A*g%K8gZW6zFyIt23;%tDX>HbkY#TwvtySj~X6ZTr%FgXN zu*A>sKB~Q41&~oGrOfHX_+3G4VLXqC&8!y zPrbL zq9l$PiKlFp4yX%9S}XYuRqOV*S-Ex zJEr+8@jUf|KmA4%OJE`C-LV0K*oQ4W*9YtF8}41G^A`ZheV%3o5U14*iJq`$nqz!0<>|BBd!Or%=}JW=&kXa?L9-DGRas0T3Vf*RPHH}9 ziw?;n2iqy}M$QoY8-Ugvlr&l=c}1NrsSw@_Z0ylqh|Z7cN8hA?vF7*^yIN`%hY^Mp z#)yYkoavj>Xnw@oOv|de#~(WHhZ=?f<>Z%*56S0SeViP^mtJI{ZYJVo`PUF%oQrQe z+S9ZpKzxCnW%x_aW@g1M9j^$dQaJZn+%w|~pEnx>{kH_DJ#m^XZnpuFfM68 zrpc$t$&c(WM(b)(c^|-Q5Hp8AaB-#{O{0ZltS?hvdWv0Q8eb>#gFYuOcy8S?iI?oN zQEDvM(u?9IG0;8CK3OcY#qA$cr^nA5O$E9!h`yQOrxG@BZ&jP3 za-uE5(ee@$BP#o;CmYL;+~p*?4)-;Dl{?JcV4n8QOTMsIJjBi(#amyJXFu=~Ke4%w zX?n0bT1?-*t#PU?5f){v3n|)aaO{jVSKAlvXRe=B<%6^b zajkG~+UTyInQz)3+vqLP;6687H5QQ7)Z5x7h`}&j!`@qQTDA>A#*E&)EZpeXs~;-M zZ0B%lnImRbiLXx@QnYi2Nr(XD2T)@K2gKlL*l%=Ls~wg@6p+72CTV`;PGahq&)B#! z<5`pv+sH%OaiJU%#~+S?TRz?yqM>e)9(lIV4`|sWJbo5zwRvqee?DKII_PSoZ?v@_ z)!XQ(KYLGPHYH70Y~W!N^8r8u0}GL;zw22?wDl{HBIY>UXm@T~kC?fG)=Swvo%U2J z%n_!O>6xe3e9tC}{j~P27(1!8$6xg?RYn{(ZYAe!d7l&vpK59MZe3GSo;w(Xz9mzZ zqST@Q!Pwx;C*_1GoO=@WCy457ouv%=&AReU`+6ORqsg`|^hVQ39CDHGECQHoF2xn^ z|MEPn&2Jv%Xzq5*h}R;B{qEGrq$b?b}hZMtzLUfg%WM(+W|b3AcuX7 zDrG80TtmDi%7Y-E+3c{Ip3$La&J#ZP%LP9}cHd1R9}62DziGc%s7QVK%66Y8QoDV4 zM^{##UYT|~LHr(CVO8xg)ebVbttIjfY1iBYm^0}ZErYPICYegfjB^$9J3hw$a+nr7VW$^|B z%?o|wn0P=i=!A$U&ox)9;#3k!Ii%{UF}l^-3>r1vO zBX!<~4aBv2tf@TZ;y7Y$<&BV0Y!n-6wvv%%$*405Qgp{z79$%P2WZ(rkpD1t4!Vok zRJm5uW(yl#AIY73z^~pG-P2D=v1Chy(dXNyl9kw4tqt5IwcUpes`dC>+B!V+w%=&G zBI#$x+24quxeTZ8D1RQcs}DR=XB9H-!1y8<=0!*n9X0R8`J*ePC5Ow4H{tw@TS#fn)N-w4Um?Tsca_i)V>3_f zlD>_!JZu{Sh)(#>7%Yv-jWOZe0bYng+a+YpYFR@eLiN~m!ZRshRqp_a5ZB%sSB=^B zJ8Tg5QW2N;1e*AV7~k`_^NVFX%u4G>jz9D+t%sr?9<{+d#o-bVkpl0N0Qy@`>iIpD}e(2y69nnl!wO^Fm8X5XNAoz_?ru!3AF z>xau6gNS=G-_JbLlR048h`#+mM1qYu?+XrgH9&J4F-l2!Dv8%G(A1ahZ+_M$V^QKA z4GOUd<2lp)G2*JIT6$kK@8sNKuOI&YNXN*u7Ct4>qcHKd914vp(M146{WS%B0M^0$ zxwDheAVRH1&i2Vi-+4FgW7qfi^5^`o)wY}TF$)t=Tf~h)MOC!;6WDH5$bXIevYVca|nMbvJ6eFkzb6D8Rk7 zNz0#b-XbS@)TAj}eMY}@zT(|O?WWMmhK2J7-)J;7g3Wi>?%mBp;SHwc75M-yOzB)n%T&D!&$o`jy4WI$WjeQHOZVRO zl9`^CErtslD+7dfBWCigPD?~;=UMC8)f=!QH3+o|Z@(B{m5lq+>e$zGR-bA z_h#vuKWZ0a>YP@6(~FL0fLhg(k^7OZ_6Y6OAq@N*kortoa`WN)Xael6G4rN-vxkm2 z=qaN%uKwrNLlPCXVZJ^6BH{K@2b*etDL)dI=)#0Yu0 zA9F8PW7a{xbxEq+XLw5HV1?>fmG97%%^4B+g|bc$cx+Qj3`f~ry@nZd9cuK>jBnAZ z7EIeOxnSHb3@s4QBe`4`*>0NDuYORSI*a(SDKK23O|0tfb;#&SQ~kV9iWYcA_u*bD zm@8Sd0Kj<3S3ap~qiBR^XJi%CLliK0WS3kT-Bv$Vrj%+N&8@gq`UDoFgE>y364GZ} zRd<&;D(D@L_76Q~ML&7qP$xUSDaGlzL;e>M8r#)t!-3rT1i!^`z!z2py-g|jKX+?= zc}){u)Izwd;TJd5)G&-t^B9wwpV=Y;E95w{h!<24R8B=E_{B9e@)M>uW(0}LIQ)yI z1ASX8DY!SV;v`OK@9epF3jtC=pC|-yTIm72*JW57!bf;Nf18EroO)HCdvUE7H#KtY zrzU`&;Xt=AR-EXFtL{|A_2&F}uwhHG@ngEqv#Y)*Q|@)6BLWSD;n87*A-!!+DU6RV z2;>vg%D@kOt_C?a)w*impjRx_2dWUSSh4gLO0M_`8Fp(?w8rz(V*8g2gveMAo)a+j^+h2UJ4 z6`9ZUiEn!@OMkn`efaNV+n#=D{O2sbcm&(9wWr-GGYz}*Wk1f&ZrHWFmmh1rK_b>ZZ)mGt>9cmFm`uXU3f1Sq3y{SVe4vEvUWP1{D-QcFff_mcD zZ>m(E{e(7F=h!X5X!6or^D{8#PkT3TBH$2N4?o48Tuj3Pcm5HiKF+gfiWv@M8Z0&p zC;`q(`O{0^-fA@wXXHCH#9=RewbQQ~DMcfJJXPwrQe7Vn9Zu^6dxm79eB>CH8TZ;AY|AT;lv@?H?fCc7v`d$2)qCr)<}7okuAb!sb?dy#B7PQQVW=w{pbl>`vcodmyD$8Ux=ZDp;!3diz4@pRr^{}-ck@6A(RGLDxK6sX z{zv8K`fRrGI}8MWdY5O?sh$P9&jtP*S9)xB@^-2aOu&QeK-#zQEv$%&-CEYxH`j|t zb)n(X(~Ou6{6DIVUeUT6-GlLxn&diQB8gHvUYCyB#jktL3F4Yskwz(KwTQ;`n6g%t zYL7bHG+jyu5AoDvYK>*LBB}iV*X9kH^o@kEf{O&6BI$VVEQ!cYdd^`SzyYZiv zczv(!)ROvMYjk0-;feJjI8WTvHsJdI2F;}Nq!zS_O=Q37MSGnt_I?5?`ndaCE$;+y1s z+REko($U}F`UxBvR~2egaxqXPJ52tSwL)}p|NL5z44FIWEdRV}j6ewtfs2UiH46f%h@(J%6AYb1bC$b+} zJTleqV)`p{sVFx5_DSmlC=fw+L1@;NcgymvV}~>>T+X?{44HV2YSSue?EE&~BUMjp7`<60 z5q_K6%izv8{ecA6TOB32`QsLg!HO*LemHAdpI6-St0f_@1C zWh-Z3dQVYxk{K_1)Gp*{jcIu;e7ii27VRhN0{rnUC+Bm2>B-zi2pv1h_X8LgL@>w4 zGy7qevnAPZeGx_2v22T2cwo4pyN7@kjeTg>wE9wUz^Q>#2&+0o;<23C7S@LwWc4pm z6Nx!Wwo|d%9U7WKF7L1y{_-#E8=?ilx+I{xs~1U#Ww#dq577byz_cr?u_a#lcOHNG zyarsMwLIa|mSsGP5ti6@UylfDJYv>}peVvqq)MEq{{m1~FhM?N8d4WS8R7O@FT9qX z1npEmu@at1N%1Up>9$B(HgdK^Ve;O3=8S{jJ3|3C(DzAwH1`gBF*@VwF1E3K}2F1<4w z`@SWgycuvZ@_Hq*1R@U&nL&k1ABq zPLltP4vN89UsfD@RlAdN<5s4_`F6}k=SZ9E>JXs) z%u^4GmL7wXt(Y~C1Q}z2p1!Mn$o_C8g6&&^(H-+Jxp&a)E%&%O=OC9b&Z+FuK~B@@ z?yXSR3<)!k=%mZCIc#d`V(cJDmu96kmnMcZ3jpe)Ks7om$6-9FrAyl%D$QxWidD{Oq`+|AZzhw%wHY z&D^o&x_2^}xW-UNfWx7Cf575d#-h^5b?G3AykCmEx^O_}i~JJ|<*0&@P}f&d=kFfvi{B^Dk8_rY`9$h9+D#?9wmx5V zJ39#1Z?%3m({nMs;3xf4M4R9gKl&_o-Kj)s?Chtztn0O&8&{NY8HGna!;majQzEn7 z4a=?&E#YmDKDO$3i|4Kt5+n49+lY~znsY#MLY$P3+i5QfGc6%?%__q#8qD{dB^ul| zeX4bP5`)~q#bd+v;XACrqP;RJw2c17)6aC5w`o1u-15yXJx5*D^H!^wW!QCIi9|v8 zqAWHr>hRzAFd}J0wQI(}#ot)!jopG;x5md#VH)p8;|7MzH-1ddNptOZR#2vr00ciL$eIJW@om! zoO|rVfZHE0$7LB3T&V6Is(T@AA$;u0`gg%-N8Z%mZv8}`(p);`JjVN-G0CQ|=6n*Q z2EN*f_(5!Gs#w*WT8=hv^s&UbJ%Eq-S?b}i)~R)M>&Vk;;F*x_PTHRFG)7u2-=k@t zTgl8V8g7_W5ZP;|e~2z)=kC_XoXY>nJ(#@#sei$HMd&)@o4`*o+&lzg;0y*-Fe{11 z5|i&FO|yPP@TF&tm>5eg8rtm0;NgaC0k7sDOIpE0$5k}VT@@Oq>Efj8o2`hFdMacp9eH#U6s@o=x%VE3tG zbd9SVm+qHneA#9Kt8)SERWH{42V79nqVe!}W?lG+V?-m7ML zdrcOfeemWonviZ?ZuGFf`p1+kO2PQ?X#KI(KIAFzL-2ezpGgB)fO!QfOqhw=+*7pc zdf@|z#gjcibZzmfVxI*rIsjs4uWDal3+(yXy46V zuP=I5DZEi|X7N67w{6@R4+(eM^1R{Z@M-7P41KFeMYD+q^Is+HRiM8Hq^9K(^Z1@P zf8nxwnh7yL(tTmF;h8WpVd&%!9y;8QGZQO8ZR(ci?G1aPv*pCQNuB$r*4&bcl}E9A znht1Xd_%f(h!;lIQ5}?s)Uyug1Z!oitOv@&u)&j!k_I*tr2V_EzZ9nn*;ifL=#Gjq zcP^y78~H2EG8a&;JDxS-n@F@8^-t{Y31c4TA>;5yO5snLo(kRWPU_zz}^C#y2)P**)x? zw~-EvG#_T+AS?1A{5X%9UNBZah(pYlZ zNRQysA4sKZS*1sa0%q-}4Njh({Z{8=l?F8YoJ+45?#;c`0_003A0Nbj;dNj=w67)$Y6MI;&Lnc)w$Z4?%r1$I5LwJ4>5IkCl+jfUW(6R$gDX$H?oc< z9xf`CPWsigMm|`#S>|ul!Ew==dq+ull3Gguzlsso(#_i?7AwZp72Hp7+<4@WS+z(Dr5Hl$maRbOr&B5cK ze#lBVaM?ra;W{GMk*|tTV!H_o&y1h0rJc!5DOO1u1S`9T3vicbiFjFGiz3=yksPuZQp=Y%X-F@V?vl6|EX|WUMDA*}AAr-B6|JsdutIDT0q(WF{s9G|LQBO7fspRDHj~Vmd;(55>-k6^qet*^Q8@nP@Gbp_C-LCoDz=9$&DR($Xd&RX^$( zX*F0{g>|DT7)GZXIA)#KeNL6&&cK*_%@a}Pwpp?Ocfp-eO)KD*y7}&5pY>h+;TXFW zq~G3`yn2@C^_OoinEZ;ooJF!=*&DJ&(XSq<*{l^jCah(u3E_7!u=^ZWw=+bLEjvn) zhh977c_fHwE>cX=_7C)!F4`^Q$mkBVCI=lN7j-}Ecd?rUOsaDY;mPe&1xV|VPjz~K zPL?J1NF_=bdwNBvCQCae@p_L`tx%$gy;+-XDj zZ=#mn5be4F&!cKf?zzIXPwFf)Ye|Hv-?jPVW|k-JuTuEcJfFAuM*D@{{JhLy*?HD7 ze_D^W)H-f|PG8^lQ%uHJnKd5aN6bpsCh5Z`YZVFtsK7Y>x02W=%E3k7nN%J+&nd?A zf*I-H==$H&TACA2H3H}R`RqjzEp?9kX~Hc14@Qz(zwiI-wm!7EFcEVk^G`;Q9&(s@ ztX!7M5EwNI_}USxu+1nsjk4T8MM=jv?yKpmHjEc051-ivIL46^Uk2w;eWW`o*0Ao@ygwIK zvYgxQuWPni%Ue6y)k!>qDS&1eHDFM}z_TloR4h42;^}ojY(3Z>_7m(H{l_iL z!lan@XyBhdz7Dfc1z`v!(mFKihXCx%tDXUsQ15EfWyDZ3`+R*YRNMP+uc#~Z6c4w^-Zf|J81DJi z=x#v(DqfrNN(^Wy4EXcyINk&sPS*4MWz)eh*o&3o^$hj@;pR1VIyjmVV|e2Lz@vkP zaM>e`CQ~@Hdn_k^w;?cM$u=AW+RF7+Bs(!9#5Cx%6O0}gGuoeO?X-ty;=U4U=X zp=>fguf&^i9|L0vQpf9h^k6eiavzZwC7QB6qj{8^o1NZbfhX;b!+~%73i7;1-@O_$ z=DttFwa_oqdZgqqGLa!YGz1U`cvu2=(FzCK-YW>*~!3=T;o^IHv>4jhLRfOo(@5ku(y2 zAPV(Y?|m&HXDEs`|PQQ2`vRe&NRbrk=6mL0wZ5{E*3*^v$1URrlx03(Y3baoi7$pu0WOVlsu zFG9(GtljdW3m%rIp;>d^b145NMPe2@%cUEg%XYm`^ulZ+e&czp2P~rfWsjcKu^DJ& z1d-wEuCajIsTic>-R9EVzo5QYcF5E~|Ie+uTeWHE2i?Sqe&aaYZky)6IF4~JeC{76 z0}G98xXz=-RjhF&iJ)2A4wDNJ=7fOwPo*~^27dMFRM!nuq_IluDl9h?BZ-DlUnGk` zolNm{sQ)B}f;?LSbZlJ}=oF9IL6Cm?52U+omt`8DtHcznDfkFGIJgr?2ea2M_*Jn^ zKo#xhJGoa2rr*rLn$$(ALZRnNW9C~AJK&DmZ;q++plLUxLbjubHO#aM{4NO8LN#plQoSIv6e3!Mh0T8&o#8UhGCVTVaM)qz?eJy8?vp^SD@tT;*3 zJl)N5k)}zIQq$1de|g&!9FLm+xmlF8jY`0mlNaksHmhg@#vNy(Q>*otny{mJ+A-p0 zOehkaORo7{J>fO#ZCn-%CZ>|jZ;KMQ@S1yrh)uDW0W{pUiFiQFCE9Z962k+cjx?>I!!gUQ28?cwxj;CRfhqKzlt^P5+VTme zI}zz-!yEPFPjOqdX*m3Qf5mDz(MM1G{$xeX-7{F6)noJDdC5j@F*`=8JU ze3)R57LsZXCL~wY!eLTZjJJ>;lrvDndyQ||wN!2|M(QF?X!0*>yK$BPMWYdPL}q(aVM)|`mLtMDkxNGOfr3FP%d=9=5i6!6u+|IGg zIgL1c(faVeXA}O?PDt%~f)1BhU_#!P0?Y{IOiT5_kP*2e3X|KD zA+>#(bH-O1$o(${;M=QKwyV`WOE2JWFHzE^e3ybhjO_i?>{VKJMS3hG z=+@at|94V{EKyTX#k)lJjO5yKq|_?tg?KPV-bp~SwaC!kZ|BCH0J|{Ws6g0GcsjM3 zG7kp0d!QB9BYHSb(})aI@#72_DqKlfcT9T;H#(I~R5b$t0sV{1Zo+57@0pf_S(MeV z-q&B(-KNH8gWPbKHE^zv>sZ|6uu=6djkM$~=YU;s-fm?V65Af-b)oPY(Tj8V4pe~w z?)NoPwo3h-G*=-==DlAr=?opoRQWTg(^g zbFwYMRRGHxKSt5pG6RulYE&D#!AN3~nUX0AxOm2yv%g>+md~X@!xJg6CQHfRh|OU z;&afR7Rv?Y;pfM^+2P|qD`+XqMzlzAV5OkH$RR{%N85T!61N-j1MK;E32fOdd-iU5 zkP{5ojTcW%Y2C`l%&iA_Zet>}GNO*tq2HJEoODH{eyEc?F1&d) zP?Zg86`qq@7y^L$Nc;QKC@Hz|U0=!B+5(wK;w|NR@26`6-N!qlGdv_AN3S_8=CUfr z)%V-D7z~(2xM1~7lCk{{*aH#}Pb!rn>LcVDAI@zI2KrC@ z%BRu){Bc`kbN#k(|KPuw(ON){L!SR_I)hGyUiLMOs$~<1EJGTqn!C9`B;{xj)~`ei zEF0q0Y8Jo)vS6Nir=s^VmF)RV`Ly$&5VT^&TCU$vbNIpnzh1JSfJ7ixBVG9-)1BBPvD|8r;T+|m_ih!pqsPusaWS4e=|JM$ zHwll!v*3s{gAuN5!LpOtyxC7hg7Zvw6fH^YrHL^xtn#4Xz;%$z6OZ0->nTY$vz6sm z1my(R@eazKHW6mJ3v2QkL01$x<8%0#i*Nc|Hx>D6B{*5e3klV6Mec~<@Ev4Mt$HdkQOWo>iWTBkKrC&{&F z`yKJOq`2lzPDmKK>b*uUR`ioq9inp4%Q;DXf?mSrE#5eAyZI`5#z7Ar=vJ&B=GG`_zPd+s*=7D90W?0BFJq zST!floWUGp$;Y?ncWb(zkG%^RIX~zmv{1jTfF}POH}HJ^KA0z8t^R7}rtM3B*wmy; zP1!yHKb?gqT5~Pn`jS4k3Fc4d#3v)|mpx|w(M>IHQ@PvK*(t5K&$7>yNW!;$gOod# zh)v127Z-+aw7i1%7_~G?JowKYH4^`YIW)WzBgD^6a!&<(V&QyqA3|_>Yg`8;zPDdI z8SeX#~@R*%nql5 zjFFD98Fsh|MPOdY2s1ei)!)+8wIHHYCb|{gLs_6__!aBa_i!RYFN^&`QnTZ(6+XoC z1k`z3dpJecKDg5z?nuw%9 z19OH@-uiyR?zCTb2DpT>EHW3?ol!9?d0>`rHDUv@r~h-a66Orl^IsxM*pFP|8#U`B zTlH$ghq4uowpOrx6dtL-tI=TFL1Eg7 zJ#bT-hQVPJHH(Ird%}a6Gt9K9IR(P{p{~uk7YZ{U_w>W41$`b~Qmq2oka?1|{lzQ; ziD7cKt%IyL5|6D8ReK1q{Kk^qezh;{GVAydci(j)S&2nxmgu&O3OV5ku zo1x!n+4q#A=<43EF^PNQPB5c}S7tdyC7vjP1wc#uS^?AaFG;vQO)raKG4!~5>-q>m zg9*XT0sG=VIGdY)p9}II6h}^kFBU^WgXt1fz!sQOROi+& z*N;Bp5V4r)Nh)?Q#bbQf!%f8?0d+{RueJXG5P!n!^;f3S(d@4WEIrFJKOOPaSH6|`ddFOa1t>ys_|ENma*6&#K? zA@r?=jrHCPCq~?11$-69|MxgKm;O*w5#TCk0=6|ocXjCkN-rBqVwHnd3yL?|<)75xfzlH^PIH zJF;bXP-l~qZ%!?d!3?wAZ(SU5g3|c2i=F@a7_##TZ23l+s^b(|`?CqHcjzK<2S{J2 zjnMeRq7Hq~s@-8>dlb)l^2?f~A7%_Gep7CzKTWrDnNEk5bw|%z^QW~pk&n0N9>pd0P6=Qy-*=F5=T;h&m|(E{O`GU*FW6K9Fj@h=snjxgNTR4tphv` z(pX@0z zYDcY}@?@h6^4H$Y$?K4@GDn7o?q=Por{xp_Uan?@6D-hw7V@K4KhK`LVyWHXD3%{; z(N-TuzQcPfAAG-GR+XmLs9pZ|_Cd`kK#6`{)bws~+@>hewN&?Fxh0@*AHmWMb%hhu zf&!RgR`r!%I4Fy@f;xpDf0BQsWs%7j>pv6MZ50=NOLmDB4|6>8od~gyO!}ziP$lqy zhl2lQx-<&NDRBwy1wr^w9uKErVh$7tpmyccf&-J{o?G%x+qxEsn2xV%z9fA2l3qT8a;Mu?S1 z>o$&*}HoXtB9_ZIc$h~C7Q_x+zw7=rM{1aW?4+D5f%xn zymJ!l_oY%_y85hm*scS%se%aYBPHt(KM&7P&YLPdH5eA-Jw~l3-iPCE6(zQK^(R{% z-x{-eZ>nBy^ni{Su@aj~?eaX+bDwTbuwD3z8xF7f3 z$@Dw{4_|a55ijj7uHz?!ONcE4is7Ax-2j#GHM~XgPxDHCiDLaf0kw&*_LElKV%`q@ zGKaAJ{e&C`_GaglZ#QuIx0OcNo@eJh5&;jsqeLPt+9uF)ziWX{eNvo+nD!7HBYo0> z8o}JzBWImox4$|dKl$Ns&9N2lC_DlR%^jt5NO75m!oMep^J$JWhFRc8$Jl*Gk&7&SQ+}Crs9ZD4XEV2Yr=x8^xM5Eh12(%X zQJQ&HwC&Fx-U~yX_-h&wP6)xKQ$z_rHFwv+8HE%j7!49;e5mYZjI7CGvaek#blS{w zkT115$(ZeOgURz^Irh83gl)yGzX?|0XqKd0trO0U?FI5ch@AiyAufR3@(Eu0fIva9^Bns26qh(VQ?Q@2WOjS-@W!n z?0%UqJ>6Y(s=Dgbk^5Ng^BX^C4dg(>_0-VJE8~2#4eUz{uz9ZOipp`LmD?$bVsOpY zH?qipFq!&1<+&|%!xeeKnF(Y%G$3O22+i0G-(XjNO%pc~*fjYcFX-&6v(FlX_^@-w2gSrV_^rjccH$Y zp5hn*_udLSp_+nU=F@KWyz@Y*c=Kp`LlJ-n47x`OoWFsEe+ejsgjzG2Qhk)`dHGvq z>DmOYzom(b0d9#{O9oB`ACaDf%v4WOT77K;yZE8E-d30IF`t_PGy1uQ7rCA&C2G4c zJWSV%0ULZ5SV|7H$6hUqv!0iD3N}_lYuVPa9xHd|FW>Pk1myzW!gd?mXPQo!;Fi?= z2EFb4%lxU(A^zH^l2`S4mKDSv218*@e zb2Yns<$3Y(6VRwD3UwKUw(Lbw$FSCMe(?Ne3QVircYz?O5)!1XRn8~qki?MnDGb8T zF$fi$s*)=hLe%ty*87GDrqKdf&`95&0Sd+O%P@}G6S-CcmxXkdA(r*2v~OI+iG&S7 z@OI{2P2p4nlROR9U)UOw4envOkmzMA@KO2HXu5L4Kjvrug*snJppCi|ai_1@2I;LA zUiuZA5jZ<(DdRU{HJY96`|4eUI#=RV^Xh7&IKJFOF5!p-b6Ayo1?sKWE-6^wZ#%b1 zy%|TQ69Q%p*#KL;umn-t4nB19!G&e};Egh3{(FIYFkp(*gc^sVW_~?_5fyD+nb)5C z_|_Z%=``0=v~IuY?h=tee}Mzf9hG#z^ysbU80+FI)*9j5_%DNni>4Y)+#SDM8y+=< zrBuo^%IT7Slze2R?ZhqGSSr1F@vSMo$#qFNxwYgE86{)<-u#PioxrK*IN?o9>Pm!R zmOXgJz{*dOxh;HB0SN}4Vkc=hJZsGXEToF#4l6iCOwJZoE|9oOkL4rJKHBM zGq>kdb0Dv8rlm}Y`aWD`^$6kCm++R&hS)Ky*4SqBUi?sL9U~E z5S0!@*N&3CuH++dzZJ;^F2TB`u!=bLbkRy$#C1w;N94bAGatlfAdmJ1=ov6)Gn8F8 zlt+IqG#tFFH}3zJwq=%p;y~KVNL(eOB)0>Y_syCOqMpRu`&E)c}J{=S`l%z~ii zObjck&_J{FDYn{~BFqRdebQk|rSQOFzJ-v&ccAZ2snyy)Oy#-nWlEdBtM`@?WkmXI z&x|eL%z3_JHPOAmSp1$mjC;T^DA6Pv{w6tfav0*}pPn0SugNGnd=k-ff`Rg`@JW~o z(y5mow?5WGys$st+4x!O$t2lpwh86uOKxk(2EqsNSC=el`iqReV6)Xb|Lgs9lw#gD z{fDUG!jP(x@x{jsKo%(9(4s3mCP{!izxq5s)Jx&LMeOqv&qpHxUc6k?3Lz&B=dYKN zC)|7UgFdRU!=qM>HN5TojSOAMt;1fV{Rg4n_s~9OtWv(hLa}ulUkTUs;^e&_2XdUH z>_x-7NnbsOv>q_>3-qFs!*l2N3seF~8b(2q6ffq!r%u)->bysm_G-DmZMjgKObdDv z4zNgKy`zwyXEAVPb`?69xnrFKdlBYeZtJRr{*E!HmYxvy^!Rm3peZKfI&lrUJ98hh@qp=kaRTxFY7mHzk65#y@LDB#8ViUBvGw$tT ztOjw{wS@)FFI#&$h6fgB4F4@4yZ~g6IaBE~WiCLt&w4|XQs2ZIN&+W{KgjZ4OVsA1 zlI){yxOsk)`(Q6RD7_*kAej}1O81r4fO-Cd_6F#qj2Cm10IUAMd_$5P3P|D^nbxBZT)7*zS{KWyv60pJ9NaWi!ngqiD1thEW-tbKE+Ox2NpG$6zclY=UyrU@ej+@OQ{k(nCrRn#iX<^W{MK% z>lQg&rq)Xas;D=CsXN5VU$I15FT7dO0ArdVVGuob1<~OHbN3To(aPv1yz$I+Wqrfo zi_2bEOer1rH^PP!(=z1xhO9Kgg1%6>LLH@{gOr)(k#OocPto!_@}v>OuQO2SllSRc z2pghgedFP+cJ7SJ3I;iR7tGjO2}xp#Q%5}va}vzwFD~QeC8|oK@j-461BCfQK|7Zn zWy#Tle3GLkYp;E}oF|n&(~7V>W7!v#6r`MTy!#wn}Z$b@N zvl-~)E^x91kp&}-wof<3m}84@mey*c#Td&Oy)*;SNdO&M5&l#s7J?K$JqdX$Z%zbT z`!LMb{rjN(`8Nt+I)QxI!b)=%x9|59>D*kr8A$UqqU7u<@j!HVPxqqgsZa=K)HNOE zTyL%Y9!@lu1APNMz43@-r(FS^34XzVlN@SYlBQS*{2lAbzP1un(gj7fncjm>SB8WY zB5SFFCtA#b^CK43(^aT`vB8X+-2GlSfmJc-6C?&3__;D#!BH1+p&vwa)FWxn$4<454b{DzpT@oF5yq@FF(G9_ua$u~J)e)f_4 z=}Nu4xf(2n*b>+JNTsf{tmtJ-uHzZwaX$ZdMgLtx{f~d(nim)B60| zx2G;ey)>3U22W28^Ae~8(VeyXGl9O10mIYo9O^8%fT8Ub6$t^N5MqANi4}$edf1b} z33N=nSCBv~PGI5HV)=d`fLzg$Axsm%=FmM|OX-?Qbx6k)mx^Ne^Pp$+^F!W?I&3u1 zx5uZa>iv+WKO_Z?NH+DVJse}7LOmcEUad%=D@=g?Bb4u~=gnqvq1!yn;o8HFs`ZDg zly@^81o{CSZvMN9_-ejVho^yRFVrJb18`cDpZeYxko0{)I8hTCUzQ~UF)uNA3;g>B zfYJa7@y_*V4r>eFA4rV*GY&I+`;TG7@YG68d)?j@d_AjOb&2Zyk}1)D(nu zQzHxV6aO@al8efaTuk_bt5HD5Pt(JrjPg)~kUY1bQEl`6$PWc&f$XLigr-QKyC>*O z+Metifj8XlxSvqVFtS6q+%q%)e$syroSo;~VVg45y?||ZP}4<|4g$$MD@0Gd*4H}v zm1S`JQZ~;MO_T)m4gB9or}|@x-3qE>r=$bx2BzD@OVGFUrwb-O1lIf`Atb``ZYz|r zTq@<1k-&>PfXxb&W^+X7@@{YrHa?=cqNEbSb&&_#2C#(xwT$TV)X+b`p*1|{ie%mk zr|(sMLMr|D{@WEnhiZ&^x5`n~?|DBbc+o*Cv`-h}oh;FsyUlH_cQMX~-&D6(kJ$Nx zD*!Fvx>12^J&J_nuTKR<+DYS9Xtsp;|R0yL>7y{cVI_0M-m)0)naPSYvBzsbZibBv0*;kcRK7?C$@~Hqfi5NJgG3$v6D1T0;QL%xC|7 zl#~*BDU)@2@1IrQIk66b6g%-63ud3>^XX|NO~alV@7f*yt9RitwRdRtY9o?xIQ(fX zc!Js;hwF$YP3qKhp&SSo74v3vT@065ei2iu1pQ|v0F6n*gE4J@bu`qR7PgXFfTE&? zDhQlF|2GUwC}shVnLoT>b|O~*@?)-umg>OX8TST^ME>MFZRh-4(>G7rTNCcVkWmVu zvIG;kNg#it04znIwCKiZ)t{d%3L`z(l1IB+d7jouY``u78bh-ugTH8CwT6EkL;+)z zwP!&<%EV8P!%Pf(_*xk*v4ToDkgloZ4 z4TqWmvcyCg{?j7#--E$u<4MZGg{xbc&;vz^(lHIBLC9w;i^g0W$_r2i+SAbTQn_9@ zDH%6-T7rw=3eOqUWn@Z87`Vf~0K??{gi2b%5`Y)3NH632U`mMA#vmTD7ObJHN;PiS9y|3)W#*(P!I_-!yZcEYpqxNp)Wu^Kw>cH zbc`wDcV^w;T~21Ig5nH@YQ@`@eDpn9u~uz`_V9^&lbgLSC8D>jeQ@Dd(?QaS{q7MYOBHZt(1h6emPZpSBS%R13FS z`16bt{qw|wBFP2dCI$5Xely@IUE11=&`A5V8y6}KTqmnB2FI!%1%&1B^syj)5`G!i z7q{*9JRezW;sJwe7wO~plN>PTYDE2zFKWIpf47_-DkbPI{Q~^|Ki!Xf%!O1{XKC`! zm_uDNGuE!Gbo8#~$kSCJpeN*G0U0jw?)6)on6425WcZH*BW3;5P#}es`ReW4UlvvTHKRdsEzTse(TT=f1Flt7dl40nn|GrNn zBV-~Gohan3Dw2G$r7#MnT*ac7$YkKJG-|LIEi@@n5nwfTLj`#}ecz|UH5!4Ihq203 zE*TV3Hg8gppD2E~DJKaf=;eH^{?9P`;@?eeI+bRx>DjbMw~&7SU+XhdHCD zsG$U|R4!hwLPzb=aKPJEHy8jc!~gSWrFkLyl#9BU)0nX(S6N%*?6^KC@6WD*;}o6M z_3bxM9WW4~RVek7ejOhPB=odWU0WC@DS-K@n>@B01RWWNx}`=VB(jXJi;zc|Z zbzHBp@<7k` z8}K!B1Z$X`Um&y;-FnWT-&Jkmk{q(m~KkM_d;$rLK z99hoiVCZUU{4)ikub0 zi$2jBfW8@FUs6UKs)0aY=}#2$3vPnxj}k}e@utZFHz~&KMY5!Vf-YyzH~U6j?tR-v z@#TLz#G$wLa56ufKnnlTrsjIdu;AF1qY)R<`~G@~Gn{^r_%f z@7l=Q!v6Ri8zx!Im?7$l52-Bd>T>=@TdK!t^HI7i6&uqIzs9LFX@1mD`TISJiunsz zw3Y{m&!3EA1N<(w75HN{ih>-fUnn(xVxNLC$e%uZElp|V;eEmJmSrora$$*#1p2h` zS|V25OWDfZN@hh(?O&0F0u!V=j+*j1Sxl&Hc5gwl?|{t;_Zt?KD^=AwC(f-jwqW=o zB?xqi5mpNNh{P6SQXOMX8+XeYmI7!yPm13EX9EKw_pE*q8_72i(kybJ(QgT16i&L5O)Ew$(?mwKyavL8f{We$v zZ)*0_l3sVedVcf~J>9s^F`e|;LeBmK|Fat?71M7cAoJGE3De9VApBSO*29|^v@mJr zo?gJOgEp&L@bj}q-b1^V%+>>AGM|`R3IKg{cWjEA7>TtvrnUDKWRPPJW3X#gcyvJ} z?I&Y(ifZxgdtK!e^d-@R@jONvIW8hQSmbmXcSfoeFa-JS$ozb8-l*Ql85j=|9-SYB z8O=s%y1m_!+v?9B>6mTPbe=QAifZv3y6(R_FXwya!Pp5L5jSJ93u@(dMMp@izDlPS zo)>DX_P_lQmSq$g5EzU$F)Qd3IJ3>@Q^w<0<-7UtHz>bQZCL5N3lb$aCkt)Y{u+j3kcAwi z%*jBL`CHT83i3@#-bCATKJI+~xVxbAo@t-d^PWnTl_CPSFndS4NI+kGI4iVpYh`ck zm)Rd6U6b0)>F5P~UV30L*2*2TRYWGKt4z$BEwW{xAx*%6_2G0&^-RcJE89PB;18w%z_@A3P;lFj?@KYsODGvPxbOvc`wIP_Ydy zpTNIuG4s5DU;I~$3u9R7FW5Oj?VZyrz)(v%E_L*=OUX7%(N&#WPIDytU!Xd7!sqEj zgh!_PYao+5jT`m^g=@6%w|ZSO*dLk{wkMqt)wo#fr;W2!v=tnhq|RwL#gsM3Pjd_D zBfgw&6y;5%Ty7pPRVeOU@H_vdt}B20jV^h`Xgl~i8B@rqaFiKNi&3awU10T4lf?OG z=c`Fy71O8*w;!!b_Aapz@82+)Oe+N+O7(i-J)mY8EbUxXnUz-`i;IfJeCSxWJ>4)<@45;6l*5k~RsrKNvMYVxSo}?2#{{ldE+KQ``O3Oxal7= zLi9&8k_s#M{JHO*$o7?ufL>FJE!LSfm%PAbL~;F=V%@0rI}sbloXQT0ZZ!%wAUK!SWqcqXIP6chJ#9b(|8#O)%gG?dA~qo*Plr2nw988I87oK zt#X*~Od^-AHXU(KcGM80=H*;%7YYfFmGS8Q(K+pOu44>0%M0VtU-xBK-shusKL%V6 zM_|55BMARU4W{7_Icy22mcv_9gfaj}eT)JKY>J2MK{~@$V=y}fC-R&NFTDbKfE@k2D_naDt^ubW* zYfc@3Pl_rMyDQwHBYLz-#zG4!D1yCyxy!rNR}5}6@D55K`b|hPnsCDMDnF>x=jqcZ z-6W@+S*bMlhcmgT9wz)y+-SOP5_hRd@s4)g_do3iC+V>EOwGX=Ntq1|c0trbiUHn@gI#A?1w73KL+o=+)p7<$`%wa>sTr0mh4g?B{rgPY8^w;iECa2*+I)O~HrHG3$!3DVLx?Aox6AKw@1+}@1- zrAEjAfnJ{o6+Dtx4Dn+^zH_T5fMFBc5bt%X9KZsEtG*>ss0POZct<=nc?*`)!3=Rp zpnw3knlsH8%b6HxDN*%9|7DFW6`#b)FJ@g94ckBTYc}j z@x{FCr-nIA2ClUeV|A-}7<)PQdZlFQnr3|6piZ8k6WpwEq#FwWx%++IWEaITF|ZJD zX0L7J`vCvsD+C>Fy(2o=ax?pP3A)+N0YDVMOt739upj9s$GB|}T4OZN6{x;TeoV*x z#6X{~Perg~SJ(QEzq58NxO_+_oeSN|a)Ic_VAtlF*G9O_uyYQS0x<3YKo_$lB0pTE z+_;)wmlxaeEeE`nYx(GgMu^Z_BAbTd->Hs34@yb6)y!q&$yO zZ;$dGLE|%!V<}cfJ4osC!(23KOrg!! zXV`*$=74KPDhnL=sFS*t5>^N26=o(KV^jwy7jV@3VvU|XnHEl&($@C;rWR(lzFL`i z5Yp0H69iwoE6-Eao11brs|~ky*m52n=p$8^g#rlh7T-FU zN)l5L)J4LBrQaX1szs@3Te|lD9!YF{r8dUdxGRs^iH=4!i`(VR`3shAqwS0RH9#C3q7%Nus^@sZyz(# z1dqs*4ftdL41?!X)IgDg%^k3F^-HS;n5uTre`5}Lvn+J;e%)RDfO|16?=v1S_n&YgtEBp4IaLz3AXg%VAs#5qe zc(aV)6fqNcCpI-iBo2MN7*)#_g*NKu7!vwmUC6S-g|pJUZilkd*j_(Rh^UUdEnSw| zDa5@f*^X~hn@o>uMJwcbIq$wU-o}i7V{F*04aCJ*@}&aN1b&NawY-JQ%fn`o-Y#{f zK&0X1W|o%>ErY0;V4)Wt?|qWq!>1E;+sIOpeIGJUH}M98DKaS&16m+MU{L2!%iF{q zz|gHh+Xiy)kSvVFp$Twppe>9GQ1eJ^l(&G!=<)udXsBmAC`n1h5WCaXJ?GrtE=ZM7 zF^4`)oy1X*pvJ~nzVz;3WV(+vR3IdQ1c&6}{iu!I-XSd(UM@Dth3-RUnx}AJ(PCAv ztQ3n)N4;fLxoDv;b;~W%(xYGOE)Tl2s-MFPr~ipAAdIR=q_VTlf;yTjX*qg=(? zqxqv|p4yl_GAa!-w&vV$4Iot9C2i?Zu=X|qcCJ;u^GD_D zF$n1+Fgi-vK>X8V15|Sxb-Hi4^xQR6Cm$M~8U~?1RCMr4S!kY4~4ie!Q&eW%J=DM$lC51flLuUr0OAf*+a`iDK>;l`+ zTXbJ1$n+V(>4WHofpg(vR{{voKTo*eB%-u;!>Nt8b-oXW$eiToWUM0RIzw+wotuIX z?ghf7qiQzQqK_7k9{fj+WqPRqKUcAf#1}&Y4~VmJ!+&)&w8iC?_JK;DjVhbxulwC0 znqY(}u_GWHE;yPRy$ZJ$=_6`2Q4p)gwy^c&Y=L_Nv` zxopWVlhG_sLtMO|#yEp&uPM&$MD|oA*8q1_8trM&l>G?%UxH( zB4*osCfw;w4E7L&83%?pl7ZC+RBV>44uEl>ce218wtw8#Hf~sKAnNig7L_A?YSwUa z6frkAY==puX?tPvPrW~@ZAsJl#!-d#r0VrIjb8^`omp1tXT4)CBK6}j6-2=W39wBe zUt^@Kr6IP$@D!)$#7A^LgBM2+jk@k(yO&kQ*S7@o=i9x#gI!<%)$YF6GSjRg>`Ald z=WZz)*b3ispM?Ri;-SU&VD|Dh4ZGVq9a-L}JcF_R>$i>850Qj)ID`g~#=F+ck&U5*<2>TPp6B!M-!l*`K}XnP#Vv%GUdAHuCFt zkFPt-f1dDfn9j*m`ic}uw%$+8ts53XfvgGkqqF#fzo*O?7K=Q61WB{&xBeU{gDoYD zghH9D{AMxTHHqiesy3WG6$pZ{Sdu?>X5{%PXGu}TC4>P4_x;^sj*I7nPEm`6h z*jwOZq=lA;YU{Jv^C14QTL(0m%vXo{9gL##Ul;WBgI z<-)w5MQ&g4E2#5koV8&KKim@8P5IKXSUd%{p|4#oJ&O$vCY;?!!+V5gR7eLTY1`dL z>OwyB@HSi+6sOpUT;<^iJ$}(+BW}0@^oQfhE;5MTH8+^$3}WA1y;q&;*z0B2{WX+3 z)QZeOE=_h{xww3NV@cmD&B8QR?G~u#M7OXy<5A@OC(#2b>7Mh2jG4rJrSb5*{kR$c z%|x%?ya|K$dp=?pZOzbnbXh0}RwBgjUpk!=l9rf#;nNHU2yk-CQo=T{_vH#cqH#(* z5wEbQfVSw%=0lmjJRY8!n0t9v(fpgv`Ug2zNMrT!RCZusrfm%Z0CZXI>Y=mC#xwTZ zj4d7zE2FAGAV~*6%j&Jt6aEHLYVame7n11sC@u64`ZBKMi+9;)JKV4KI*FgDHAo)Z zJU_aQ1O8f^Les{}`?5aZw`@U*pw^#SWUu-LZiBbulKdx&_DDdG7Fb-3M@u8Lcu5`q z^eUplGsN2Y|d8m=BcQ7`NEuStnzo zm2st2UaYhqmuuNfrZGw$N3?nu1af^4TwKG4Qo$7gJR61JYP{U{3`G0#O-tvR!;=%)!PNQQm9?pS&0|2-%U(T$IkUXaN;JV-_yVm6&y^ zo`M*OKm<|08%yR4trP3O@+}YcS~n>WfLgy(_$P47=rWm}xpU2h5!}?p3@LJ=i4du- zx#toyt@+4Jl+GLl~{v^OGeQ#^#2Jm9QLGaGR8tOyqLOTKg)X%`!l8{ygKAB4|)RLu&kF}PEJ)Y_Q2-h;7?nQ^*qbxnF2CArrks(gW`J5xV`N1?PsG#sNPNj z-@2Jvfs^E+`8&0fMZNzjv8rp$x5x|$vcthn>CVi`PcRK`)=VTh zZlQgzI55J&(l{Ca%N)q+m4aotn@UfSq%N>y#&Es@oPuwBMC82qU(LUY+b7|8Cx9w0 zIav?`tQ09I?qzh^WNSzq@*&K)2ooC0X%?)T_DknV(?0o?zm45CA$G89{fRL^p&q)Qj*W_}HMV=nv*ArOnDBy zl(l?X|9+2`;8x(Bg7{;RgouM7%4Z-jk6$#LU>{`9lJb zS5_}N6sSBcq{7q6#e4PE=y3k4xgsV%;utpd&q>lk-`fNBKFXr?Wzz-PibGX0&C*Zx)v-z+a$H7Pg z_eu0B9xgk`3n~5!rt!I$_->+1lz^^tU~DwQc(`s%&$KGl=9wapu+{qo?@zcY!nz7- z=p;e*?`B=LMnmaOeHrWP7b+tZucnO~3_3o*zc<>7KxYc96(Mx013yeN6uPA%P&e`?mM@iz6mS8-Zmg_t61TXI2{ep|eupU?Ke2AH0-No-r-;``GtR-&!>HlGK=`LiF55`hcbx zSRojAB)fa#&E?0*vaV=kJ=@0hd*lI_Qt?xtB5dWW^zW{YcJna6YI87pO)M6i73^w@ z0*yobmKgi&ZVXNyQ7jbNx|?x$Hm2=nibz(PiLQdT_I-{Qo?0e8hxhZ2n>6-aIj^Gd zOTwzK)L;i=!Te-cRz3sf>u!b4{+|WBSvuI2Ug`Ix%hbY)wI!Ll;ia==7b1OHFF(a^ z_W3hatJahg)ka~7?0XgaD;$|)DB^_uvYpAic(_25Qy&qz3dJh{w3tI@O!j2%Vr1va zzm1u*Q9zK>TsOQix4}a4FlCQwI3fn~e4wMI8>prD3+qCXg;Crs9(<>A)VsJeI>6_v z*iiRbnaoNx-TAlGQtR@3)9ifH*h1eSbe=>(kwNbtEeQ`WBN2SsbHAs9n#WqQ9~ZAA z$?7~w*knQue4xc=Ogu|92T&&vO7iaexa!5qgw0Pb4jCwwO!+~x8>(lE zB~V!ZGo@?Xr2btl5cjdii%$W{RXBy{#TW`ixH6p-)zYi??1`5DA@iAsq1BbfkmdgA zu^*>o7-1C2xO~WKmutQ!cwPKCt#&EMvk+FRDtybs8T^pDjysQE>3F))CuFETCR6A~ z+P5oAv-slsAi(k6U>7}GO>H0XQyXhZ>vXlhmT;>Vx*!A+f0(z3zzrIu%}EsK_Vce5 z%ike18;_fTA^|o)Qq$qxUMvj5YDbCwT@5^fDUXbkCLo7fZ~t{G%%=}5H0Jq1Mry1^ zT>U)B7bUm4rR@v1d*PNMm`owHsCHqYC+oG6;iF`#e754rMrOI)ID2`2bZ4lt?Qgwf zjD-{!UPc}DeJGzCq39NBu(GSYZ~M@4LzA}1bkxdTH~qrfjIcngSgQ+*x`5#DiF)2# zeoisJ*oj*i&o(JLmn=T%WG*20rufX5Tr_@Fxo)2RgJph6&FIIa*IH_}=Zw7Df2CS& zDRxs1YB%gLW?Xeu^Lp~H@QTQBs^lCSNCStvtpzvZfo-*swnG~V@bwun1m5go=Ak7a zx%mhMcAA=)B>hZDpoZQ8sxa z{L2bqWn7{mxvElb*~@}G!O^C(DL2J<);djg6Ih@{JfX9+kaM}OC3x#$yKDiTHvz+v zzErZ`c83n9rzt*eL~m&MrZk*h9`Y{!^*m%=-1f`7?OHy(K3SeDC4ED^FJ}_rJ+fBe zn{dtPLGtQb99t=5NeXKFx-AQ}`WV+@VKG1Lw@POA5+f>{0h{Egiyy``fL%cS9KP? zCpdPaK1*bO2)Qj?B=9c0MRxBM^;EhmTc-6x91R0!fm@-a&C3i$J|UNhtYBG+oj5j$ zaY@mif0Hh&Kces9=V^>xnt{3Q!GSi0^F{goTDBZuqOQT2VeuE&B-7dEC2Q3y9$Ila^BYB5P2bi zB29WmZ>xaZlZD z#{mQOx+W7!44S2Q5i>}GH&%Z^AHzC;3{!L!fJ5h^i@Jg|4*P81jU2kAqW}(eUpoaG z9(R`Uf_(oH5(H)c&*DmmlM!Gte~2iHOZNi@wweT}_T>c)-5yYcgCvDxn(y9Mlt-P( z5&SXY8Jf7MNXax8a6pcCJ%l{SM8dJ^0z>O%rCc{ef>>Sg?wu`b9TMQ+nh=hc`r zvZ`lR+7cD|vP6mW|JbM=UtO}y@{fr_30UJ%BU@NYAq;rkHZ^`j?-PzSRHcLsCCPW{ z%XU$vrWk>`3jNjYsrb;9@WfW06=z|Jer5ab;G^gEDp2BOgSZNV)-3eofcptIk)x|> z?US$9ZW|YZEdgU@47)>0v`%)94OF;5{icn{)tHiG){=svctx2*DwOir*Tk(Ul6)D- zYS%N>*P@>Ps6-7FR~UXtEwx=~G-=6vn3K8w-5x+D2mbuj6)?QGXHiRIBnjI|wZV&s zU(#*m_z1U%b8|>kGf#Lr$}iQQ|55#h8=o(6WZ-&jj8zLDwsne;hJk>0OXsmK*~oz9>C zIGMW_w^D1htF^Hlt%Q1lwh;zai8>F-a=|oN0UlBjUKS_%AU@qw&S)Yr_s(PkdrNgy zZ9$b>N%MipxP*T}hYyvOcL=YGyDsM18Z**>;;AENj88i~Y4P!;eD0+3s5 z$j%nLJ{@~9-53ysG+MQ2oT#&j8M(#rb=B+AOw|oj0}e}hvg=r-bpjuvC_cJ)Rw;w! zUcP~Eq~C@9TG-uZUt^h)oV{R~@771by7(H*;-zrT%d6D}F9?n?Jzt1a&$FYiH}KyM z(6JM>bb8%&BSvk=qp2i4^I;*uZax6aoZxSK$#|AFSb@X3SdhQm+4{zFDuiEeB8dIi zVaMq2mV6ayL+ec$rj|nLJ15AmQ%OFV8{Hk`Wr6({42aSCyHH3{8LWxt(J@1K`os*? zfTRj}j@U$_NlB>3Y7kCo*fgSI-u0w$jI!O<>TwYRv+vDklZbiPC0YG!nx7=odu;Rj z7Vi{lTs3@T{?OhbzfA#W(|?QGX|Jv)LOJPfEHJei$Dlo??rk{;&6wDO(TJt9v|R>t zgPE6F%}PR>Ir3AC)0=)t68#B=WsNG|KYyO`7b|AKai-BphgNv^)bH6hWq8BrtRM%c z+!QGz#7iL&PWn(plzm>=sBW=$MHUsvTVyaE^K5+V7ImXcyH0(0hbck$j{|v!U zLP}X6RdY-%D^cQLd!TKm-`y|P4|+knwo7iIleA=Q*ISC{U{N!^=K0Ez96S@EV3NCYcsM%*K#X9!lhOCO@ z=B6v;mh7U4dE?S0lmXh>!JXS(c6b8ubBt; zY#-VWn9Z8Qt@C^Fm`jiZT|^RjZFz+V+RV$g{D0Z7S4XD0Q&mF^*W(H3=)*Mw>we6= zt@F$fN#y9x#HQ-41A1{ zq*J{A)=T7`mCt1n)2sDVd7^Zn{-Zdw8)N%OYD@CO%Td~S1hf@}Ksgc)k2~Qe*{RI9t;v*8PF+ zqf{D+3b$0+Ij^X>xeJSXnhBGj$IrEowu zKydLt96X}*Nc5#{D2mQVMT9%0qo8m~5PAQr?l{a+pJe0>pY54q;RLta(2Tx-3zX9F z%;X=ODM-?<7MrrbJtO%WDZhdzoKrr98vof(7HI>-Q*!*&I7&QE|MX zkKd+Qc}Sz-<(yAcUMoU+t>^m{h&6XPWvY6H*@IS{@lJ=^JwrQIDJP-KbsH~l=>YX5 z@eMNJ^6x!^^Z4M1m)b|kSydsvTy=$SF6@DozFylJp!x+%L-kG-n?g8&1T1DIfbhC8 zr>{w4-(0d59w@R|PUM&30Ws@kAn35x{{D5v{wO=Gf{sVzV{>a&)~S`RetQZo!v6j! zcAMa3hZ`m}U?n-~Zb^6Npkt83n}ltrt-a})MYW<)HrS0)oyQfuOxV*Q$cQ?S1~kx; z6fWM#s>2(H>FyVzz9GUdTerNRUdbec9V3J-ZxJO<>7G(Q#plH*vv9CV#Crf(dHz11 zYdQbb3rz~~Mb?HfC=Lmw_W~U8S36)(;)y@3p4a8F^1}ISb5*TQW_SrK&?#)=omlt$ zUTlg{*W83Ejg!&^uxQ7#w)IjI9k4#sXtA06C2djNel;eR7_QvoqWZ~-l+9fzt{PJa z5x;2iFCL>w8A!x+wkktiloK$ESGsh2`_P_51KkxVO@~3_iErD>n@|c%3Q{(^{sq7q zQ?#XoYp`+Ovi$3j&xcZ_yUXtXuJ(Cfwnq&&7=ItpSFw8AN zF8t}nth@J`i@w2~Q_!dMw`FuBWaH%A!YE|0>zVV0>s0ct($snx9`!;_zT?j#3`DEf zANp1#l7{C&1zP6;8G67m#^wiEKGj0z*ds-yRhS)6ZN(sG`3FN+svKbKVX(NZ2#0;! zX; z?8r0N(;1pqq>A{_#hS50FR|Vi&reDE_qGZnI71D5pF0XllC0g+J_0D$k^jd%=k(JC@Cb=rZrIGkjQty+NyNhbprKM;c;a^dUq3ob{ z6D&-!^^OZ|uq>%g?yO5~r&lCZsWrQ@k&&)pY1X&yt6&D9tcfhA_ySRYaQ#y-!O8oz zPU{=yAHE;pacG=Bse6w6#O9NHnTziFtCO026L2^CAsL&%4#3PyB9>N^qOhrUH|JDO z#$ci=?mcJz%?|EyiDiNlm}84t>j4WY&i1~qe4Zv{W&Uxs6`O1p*IYoYYEvqM3}T%L(q0*?VJe(O zCC&hw^Jjt3uzqd}M(jNsw0^zt(6WAq+TJH+lKK8}$@->vc(Hgyu{&*IAOjK^*=RrR z$H2^B4g^*$X664O%XM+KQl$Bdz#NCXf5flfNp<0@zYxqu^A0G`QcYnZ6Xtc9Ci2n! z=ey^-4Fq9a(p+T>HFx$?bi$fb7lhM-hzbb=%#+U5GDP%g>5HOpxdH2+68HW5uz`^2 z!td}z;b39=Ih@T&`QfUOiipo_ZT6h1lR^B10;6t1Hogxa)yD{)$`z%J*OS2> z!pVrrJ3!>{xc7>a(_j`uw#9s}!l3j~q2u~ktY`k0l0u(2hDV~Dnt)11KP^4DKq0BZ7l0rzfSTx|7_dZ&<-mAsRH2skS^?bp6J>gY2(0qx@p@ z&fmI2GlmsiROOj)aF{dQSkXEQ3N7`P$mk%P=49lOg3$`-XD& zMNOjDv`B%2jrUgNw+@Ae?{umw*lg&F!|9S~Xj%ZvVu&8;`jP@NI&oEs9_jX#K>ZFn z`^_7b>Vl8ZZCQ0^E8AqQDIY$np1*c&fp!^A7FwMCfPeY|wx9g-v0fLF? zovx-|cM+r?On$L)PG~xLSaP}fTZ*X+N2%=cB0J?l55`guT4s7&MKB@xjQ^hU_&J|G z;sv{Tm-HQiY=c{wg}c0Sy%E0SF?m8O*2=qIiD6)T>UAG%xQp++F%nm~p=iOtND*Ot zsUUJ^2|LwNJmdl6p}i1?zTM!%rBBdmYXp?nbl)~i(bR_?lfvIE=s!Cu87!BN=qmv| zPAuFfrhtFqs38AL0SHxmKmxolY130TC<7f#q4senKt}*1BScIdl2DMi>mE}C6sgl^ zA5Z9=I>a+yCJ?>+bP}Uut@r2v6j|N6Y&c6K*(O04#~J{>sW_Urt>@02vn}lA*B3+& z=SmRwea8ykLup#7;y2*i?|SFKSZft~{ijx5?-FE(3KLX&jO@q7hDZFi)42U_kuG@M zS@O618YH4(l{ianeu7DyZG9K3MYtPQ1i1t-4?O#s^0icPI9x{Ma4a@TlqLesU;?Zs z526lZ5Zj;lbit6^f&F;%$)4?4GR}p3n)Ag{xEkV;!Tf)f_nlEqc1^ojQ4sKX=pdjV zf)we!DOGw4AYHn2=@3d(K$MOUKuV(Y-g^lO2vP#ld+0=Z389y>dC#}j`G3~?=d80< z{$wS&bKkRP=DKF~>>1C+Xixs418KEg5|;t`jCnz^)$0}hz3^U-R<)*L84b1bZ^rZa zo|Th0f-d)3(brCJ+^FkH^yjd4(D&(N@!ZHuL90ep0~({5xxcVJg1Qvo9?EWCk~Ho; zOHOu+Vv2tZk#%mIO44M#2Q;rs$I!*8tOTayXVaUjIU}c;1KX`lD0)6lKkvyKUWhjL zP(}O`7C2~43XY*QgK^-K?AW09t)N^bscw~LxZ0B4IgvRFI=YJ?1c+6{FShL+`26he za~~+!tj$sGkFgcjm)PR27Si809t-dCGf${=-OE*i`&{id%5v^I5r z`&pz0j=7RsS3dY5N)oup*4A1}7^)!36+qu4n(;Yy!s+#TIzr@Zn1N*l7G=5ErLlzB zKDPCKLFqmkWx1!|64mK@SSpIrhVf4Cy}sK8rr-9|0tx_XP5aI>Xk(Ur<15o2D|9A5 zpV;B3?XYs_Nl)V*zCLg%2YXAAS{{5O(7M-Ok4cct;^TG*hdesKZz+B6D9k=VlTd3h zU1n|z&f4(U!j1etC!=T>doqeo(-uotomRUqRc`8bzG`XAhF8tm5vUUnHhf#>9xPUYLQY*kC+Je{n6#Bcx^C1vP^LsC!w9!#2^`dUj2eHoZBJ7hT7}DO9w)H>V+`&e#3_TEM6so zTza=c*|33cu9Z)`hogSZ+wIz!5v%=y4+%Q}0 zT6|Y((b6?wO-D_67TrI0v{~8L^j`HJ`|>{Tkl)*6_}Q0E=_MsXlYS%25vxFsnaxv( zbQ97vnUTHG0IWA@V_!?v_gOkeSFI^jQdrem`|=UUjm_dRB`TJg9EJ?)@JzNJH+D*Q zHFRLlmy#>nH#BvNndnLAHFUTGc|F)NH1v4JPr^_^TO{zOr zXF@()@T8nkoyiw_-gLZftw(iMbb~PTy(&v^n;j!%{m#fmbs=nVzI~{$Qhyd3!0?<~ zIjK2kW86@hoAAc1`vps&5m{nOgMwz)r{tq&e#7T`$;b#dR|@gBONn23SJBfRf9cDl z8BYpV{GD{3{zK1c3o~N8l;FcwqH;(WK>zX)u6Jokp}+C{ePG;s#Bg&*@h-$O@~S%h zz`%W%4AgdpNGJEbXDKDyAc$_Fbx5QV!u>jvC|V5S&VfB1<6k0=cJ-_Ylt?ObW2P(U zqiotGwtbi1Z`#2N8Y!@RSkz*FBE8p9VQ(enVsaeg3ur*?SYL8SAL?(<&+*TrfTA2a z*D)TUmx_ywJTmRKca@ydXb!3B{}S#E+kxrTvGF`q)e#C=eMN#6P#TsT-Hjh|GD+IH zwE5Iton5O;HPNS0lE+9}!|;?_TeBy8h@aW&wF@pV1O$eQc%NaJ~>8 zWB%$p^z@7n9q{S}c4qSYPrQ9?L9#^==4XBpO<;}W8tVEcynQ7c;qu)x9>rCj{+2qp z%#s;2$mufslHNQ%7!-((Hw)U@xFwSGh|LI7phNK8- zzcBe7&wC_e$!&}bx^p#EQe>i>($6XAGh8npRYL>ymDGkzJ$P+5zOlOa8u(d}&>g6N_SikMzKhN-1Fo%A zBJEGK(3YSA;od6!Ar;@2y5+uO-o;H0WFq}Mq^{PyCSD{Uaqx5xi4&wArtRmn zX6@^)-xE7~eZ5_IpH?5}4j+UVf4srZ&~&nxHW`-8@7V~us;9hHEw4{1dG=B9-xnM| zvFUVyJ)bYo{YQA+)mfRi(cB^FN<@&J^2PX6H?>A*+229d)|^tiO_J$-FosY(%=tKH z(v2z1vk&K_6?#XzL9ZEpRGU8@R1oxy=0TXoOkN zDFle#HRg+UUC=Yo-Btv(=!+!gT8%*|>vds|>@SF0b}VWde-E-b_iyQ3oqbe%u>5C3 z`MYLwTMOwBm?Z+n?7SYCRSWR`yB|8QY8D*ts$AL4KGe}8^W6E;-BGb9N2b6F$;a7+ z_aI9U`B3D(Ws`5l8U<%XcFgThNa))g5selbR{Lc@MC0mZNopL6-*qlb19y|MS$8G*luv+|G&#!nnV zAW5eQU|?k6LfEeShf~M#o}KBh^Xr(cF~<+G|4`)~N~rSWG`F}pDkiM7h;hoae%`$G z3aW_R=)?fgBjquCl=~ z{*a9}6XE5sdiv&)X*wnDy-1*5ar0-fh-7|>E~%5iLSalt_kp$E!yTFo%$;APq1-3K z65TOrE3@z5;I8Te)H}lQ6HZv`den=cg-x4k$~TjoUKNq)S@kC+4Ie8^U2K#Wi+u|8 zn6SfUm2ib?gkpv^pxYoqRwg29ZG-g_4-R3V82%o+! zK!Y?0xhhy-Q?TkV6lp5VU|!QLnVcy=ooIa!aKbb2q?<_}4v*J&&UchAmD7%LXHB}b z7`aP(6?+z{ewjfRN;^<(fVO9rp)If0itODFxNZL;q7ke`K7~dHX4QC?$^&|L%H0$_`eyLPb-g)&W19#CDARRaY1k0%^aLhaktIC8+0T>sBcT2@=(Y*2b90&4NIR$7v& zO8;#OPq|!^^kEb^pV(-NIIan96|R*oK?IV!UKH4Sio`n)4C%DL6=GNwRjoypT8`dC z_665u@W>=gxAe!&qd<@66zLa1gPqH-zkO39Sa3=*!t+({5nc6POd`ll@;TGu7SpW0 z=n>4i<*a+{9O~J(HB*3Sd0yNc2d%Bcvp%ej5t+_OG<*5k`P0+j(dLvf%r{RJ7jsK- z=K(sSGazp9UxGC+Fm8UK%VYi)t4~f(VJfSz+LnnrVbkbiT9)v#-m^b5WcjRETn>+} zdy=tv(mtz;*Ox6IbUzcFVd__IdP-f!vg^hw6A)1cf$(}YyHxraIT zGy-mbf(UNE+{rVNz=vI}8Z@k+u}3dOl!wMAvtz}}5=HYs_Hs)({R0NP=Y1}oq*`+m z#)vuZfTjBsCCi?bMu&#@vs+D@Tb5A_`BF^>P|(^Cw2Z7TkxLi;Al0h;l4$Jh7)SNV zA}GT*sfw6;JH}sq243zi=hUGE*T*91tY-@S&}<`LdF`YiVw+i;SKlR;tWGVAurOv__9 zpBS04%|p>1G)yS!TR+OwxiNK-zW4jkA)A&F*hGF?A?cQZU&Zxg26=szZeaG9ogLJl zjfbfdkVJ6yeMWx`*&Swynwb0<1XPzF4!Wx@OK+m`x2PHM>D!Tk6KqpG?3sfgit=gBG8blc9d*x|pOdp^kdmQBOM8 z{0%AL^I`&R1_)g$*>U>!?wN-#??k(5ue<7N0<=rm4H` zI^S;Q!64+=ONGM^szr>-e9%c(O}9zP&+XTzcg^i%1*foE9^LuUn19^wupE|_+XtC~ zy{WMl;xP`Bd<>T!m$C)Ja%9xoaFwne`_5e-dDh61zNTO=I^6!MB$hGRdm>wR{?BP2 zg9{Kyh0^+53J)fk#434Bqh`E- zDa<_1tMEF=NdM2qSm3$nZ3*#qa9WJ{NlQNnvWA1O$j(?5_~hqQO0nk0au8SsIAQES z9bVuE5$-xK=&wkhuKv)F=+R>}eG(!zsjtu#ea|X&<7Ox)+QL;dssQ^rh2^QqcF>4j ze)DvG%o%Qa&&LJUXH78#T{|_N0r3NA}$-C;5~+9JyV$HAGqam z(;3M^e09#6_$;xx?*p0Fe$F1Uqhq+cCE&a5PYaBqRN(D0j&^f|TDpg7?Pi@90(7|E zme$2j##?D*#2{5$vQ&1DJXXgr6cBl2?=4(wH1S*7gd?L&%LNeMU2KUcJ0NzCVqTs-nbBtvF{P@2M<%uc*(i}xN006Ms&AbO^Mhd;=JSxzNamQR)60Xco6ic|FBe5`e7bXe#k(tTY{w!0I9E-e z)=@c;_?eA;kGkAY>kNA}SC15Dl8P=lr%<(m&d_k-3>Al4zDb?!Q`?mK2x6j3!j+`b zEwliRSAbW540#wqeGz2WajoxO+O{NC5<4EAR2yoRN-x1|t0jFQST_7VYZb*Rv33m z-EJy&?dz%gA$Nfg%-vCAr2ggn$mWI$_TfxUuYKQJpWGO{H`q13*bGS)g|TC&e-hx`E}lmlAtbEbrG2LIQ6ZCNlOjme z86xwK3GFMLLe{d7K=jmgImjLs|zzqo3T%16JWs)Q3DQ-~0F1IyLPKHa#|a#mr_2-Z8HgTf`mK5;v#) z%K2l!%iR|5RP*lBzZ+eu6%nl5@1l4@bpqBF~Dm8jMxbP-0SUsZc-9 zGpxEh<=S#CuIb>gwl&kZeET7pc0b`icuCN+kM+ru4wmwc?tx6D!|mD9n$qq>ZsXBn zV*}AlF7Rk;2sU>1msHE02q}Mv&vHv(WWo7NzLl%oNV@QcUgT(04LV zjcc41JEFGhv50c3&Vr?cuV3q-_%(^`CS8|G=!T~3%xuy-CaoGx8EHRSIa5)k>!B0_9@SJz~A%|#@SuV4t@#VDKyw~FPgIR51 zWG%QpiIGBsq-=tKyV_(suA5V}mwz*3gk3SydD<+7OOFmQ{;p8yN&9DVhK;_SQXm8# zaC4iJ)#y}_Bn5?F+hJYCz+apVhIMb}GZZ2UAow9TNatUjb485JG>tw4a>;8Z=FbFv$fQy8Ki{zNpyR#@p#wr@`F8spw zBh549@2(QZ5#?;7PD@T|vPB|@wKaE-mhR!-aT`^|=4eGSfaB)mP=dNh+?wA#>`1WA zAMD7GL9NS-l>foY%=vU5%<4pCuHfV|(}sk&I5&1pV8GR5X7mgU#nNG+pNeR!Y5I&fA;diC%3bU`&HTNu@ck4 zzlKe|yTIVG+}?~989s~YCt;NIovgAStixjbw@s_w#0icL4h{|*K)#zdQ`iicLkjha zeYP?ElDNqIK1jZfLbjT{7APqUxUb!B^$DuwnSoFd;23%t&vdo4KNUPUQxOQWTnz^M z2Re88g@p9zNI2vR-sFkRWqpVyiaXJjUR+p!1SE7gi{E(v%;ZEC={VM2IaO&Fqf$Fq zXNOJ^;_z0rvN+nAKgn&$H*dKB?$2SYguA(#4dH8fvcEcb)gJTsVf4t2vkpwNKQi!O zqQtZjA?~F@WvH8KQ7x6&@#y@g44eiM0683+Ef@7aaDr=L`_eg^1%NY&@4m!u%@}he z<>}2-*r?i1FM57a($UdDX?Wye`t!7cF3$W`iz(3&nFP|H#o*D`<({ON2Vy#OVRRxc zT=42XAl8j>ZMv{8@$tZK9_;UXu2$RF+Fsz0muZrI75k+5+Y`y0&+1^wDN0Z51nmbO zOG=ug6xP3;Z%ufrn>CPQb{9CDq>jnrTFgmp%eguo0S1`wS$~mXC6Ihpd5*_za`dC- zeBE3O?DBlD&U(DeVtuqYzT-O^GC+p|rVorMmm20FE)JyDKR5T<-oy(nH1^Ww>RSd< zbA$N?W`4_m2Qmj=;f7t_5R`!Kg+ccCwGkadPUD&)2vvjEdXC4k3FWPi_h^};=qIZk zYc1Mt+ZX8-8;!hc4$=tQhcu|DsC?-#vb4;Al!S+ef9aOh*H45T=Xw-aqpcLLQQXg9 zoJ;cF#&E-ha_tJ%2QtGTq*A->#B(G;#rpggt``f$NycOa0)vbzA&$S;}WC4Pv01qxKc7sEXBQc9Pl2Sjz=# z)Krb@Y>7bdQAy(#hiOBVU{Ib1woju}#ugd6DabLBr=1BfajA>UVBw(>f8Q2A9X%m0Y*^zdpA_)!eH=xfBBvtl9PlSbqpFCMvPBKsQzp-=s>X|&B z$S_I=yecSM{qsE-LJGXQCI{I-TGaaf(nD15YVQ}|c>2sF@x!_Yt?w_+PgR%y&DGW{ zN810gtyC`E{PF(A8cAC)nY8GeKi{&lvZ&1i+*W$O5>r15xI8}`D>X-^q%?qgkBq!m zFGAo74tfUV14p1^DB-^J31Z+eq%NXt;|z>os@65BLk=S9d%9VhUB1$y%_A;;0{l=? zM=N}SSDcWiqqCEmQ(rCROu}s;q>s|%BPm0J+?s9z{)nwCF6GN~v);a)c=_f1%{mf4Qs$aNV{y*=_&t zz?eBq>e(}m#OpgAV1+L8&~M|PsArYexGgH?UobN>%i3*iB6;RkUR;q2$mkk?lLE+7 z`?K(&d^RBVB#xLqX%i7PyElqbjXOJU;rf6I_?;c?0=Nic3aSG@?oLl2BM($RGW-n= z+Yd})1)bWTCdPs`|Em^0-2%J(E*F-yo7dah%OK(X(n=jm@dtI~Z8g{uBrnf!I?G~d zN_50}1rYn0hHAm%TEJ~&Vptq>v>Odd%{*3mk9Rwnd^RVA05JM*)#u8F61fWy$N+YD zro4@5mN}Zck;~Sr`(T?2m|hNK6e1m4K=4b;h8yd9F);sa##Ht7R)xTWq}_|>a%Avz97o)!Q_dY8IK&z_aQ zE-!dm&h~QDQ>nOKY1O;i_&s!#Io}^Lc5P-wkNoXj+kp<_8n0ym0p(&#{dRv*XP?9a zOi{Ke2G`zF>pPkcV=|G>?7jpF^}^C}Aw|eh11a6?ySv~r(@@XrMg9Ccuy>_lb(P{`l5dr$>^FhMY;zk{WSKQXGnHZz&DsDt$f}^Cq-52*287kytCk;tX(N*X zh>~OmRpuZjBz#6Qu`}ipD6&mHcG{y~$`y5-1IQ6L zp?XvZpeUMFAV(uzTnf5B-t1q?HIf;hK_s}Qps1)~gO16-#6FVCsyG->Vgg>JJK?F0 z;gA@WE|MroSy>stwbLx>{OlN)j_4ILXY6GmA>g@!3R{4ZnTk;kKpbjny_Nma0MMU_ zEQO6_B9t?sYoFgj5plPOsa`I}_A!nC+E{Bpq)69)ycDkq;fjckj*g1bn|E#dNa7ys zpQDL1`^NK_Km$axGUN{)NZR$KRaFVDn(hHg3_R0%CKNzuDg@>HL9e0!NiTh_HX5_zd_Wm2abmCJi3{+rc8 z4#R-tZ%)_aKK;W2Fnx)URLB)$V)O8vmd3zqXYNIQ(FllM3a;NLCuf0I1HYxfF}va! zvo=v_hv$*v_uI41FPd@dWcU?9os{z<&((jq8_uCG>@r;!aJ;v>y9@AkR4io&_I8W% zN8=~xa|>PLKbd|(=lHR}(}V1s928JWayE@75KXu?X>Np!_910jR8v>%RV0PP<|<$(2vgoHSZ6y#HPfQJ|0=U)=G z1BNr4N^4I*Ar3%F4umBS7#O7N`W~z@(22P(t(UeuQg5fy)W zbG%J=LVhaK-s}T9(YN0qp0Hc!~<3xuQ&xn3CK4`ln{PS$1kC;4g7W!=-l8@K_{cX8iy;5 zbU+=1?n7{JpdG1<2q31YO5_q=TnO&|pe52_TQ2o4+ zkelg#6)Ll+K-0QDc%SXXPeLXx{i0++M5aecb-(nf8V6HiY1y(H2+=&6!c3bj#v6UM zff0f*yP~4vU~?*Wbggk4B>^M^LPp@~M1Z3KkK^uYkbn5NCy_h8L$>P+t5?Y{!v8cO zX2Rq8W!8~gK7(1xwKLwSf>2M5wSQ=7S9f*i4#3ZWf(*Vo1xApyr{^>676!rKz#A1W zArPJyYG;023|!{eR9^mgd4`qIF^u^1DVFH@JoDN$lq2|;lcXqv!>S3V!8fmfzXBr5 zE+4IRHP4rn$6l+ftQ@Ijiz?mQibbR^rstXm?1n-{8$4H;;q;y>D%7nL76c}gAZWD* zamm?M<93!C`;#Y%*a{;9kV9BCiA5>LKLN=7rNbE*_Ek`qRi2oZR^$OUmztS!I06Tm_`mN{nwyPH>2mPS=g*%(aGa#r22v7P z?r;A7`3~aC*bWlln1j~xbFSuK0BLc!N-I!-R7hfaIycF?R*+IV`vKgapwFTi z>>PiEYl3tL|1Gin2jS7t7yCn+ri@dLn5KH7BETKtnC}7EdZlj$G86#(2vPwe?&LC5 zuT!=#*G&tQ;fkIKj+zDHM?eBaC7wxJTU-3}&?}nmrq**1GQ(&jeaj$yk&IFefMO1c z0=O#xaf9lj)|)qPK$u4C@y}Iu0FD!k4{5*>G6g)0DjlR9OqGG5ATFYTCslowi@wyC z091fm>WHE*95Dk_VHKa3)P5EIj1;go3(X=mNoXR0?uS)7j;(3N{2r4Jk7H3<>wllj zYtae_Ge9BMX1S}(#XOP!?KIyS3P32&yyYtOvnc`)XtdCvR4$AZaEB`@w>DDf+5q+} z)y0R&@;pe$wxJ83*#I^HWb=1uT`kZn3_9Huu`d!!PTL(ZFt^WX&dXzmYaMRQq$VT` z17-X1<8tPC9xF)hY=B@}WHz7@LwvQzIaUk!>LB~>2g+x|FHQla=VK4Ly4fj zG)hd=rhI&Sv#`r%K`O;a8a}rLdHcQ9nkkp5GK*kA(&eQk5Z|gVbFZdl||0Y;A2Fu6&4w6`D34fW%nVfHx2bi06Sv%MXkC^oiZD!a7?8evxwdK(|n} znY0+imz?|R?GIx)7XKR3<}^4<#GG^F+O-R7V6FiBlR6%yqJ=$H)a(T%&vx3x$NI~3 zKo-Qu9Ru916aq&i3&1*UMUv7_Dj7$S9#|I+EO~Wx^*E)-%C5!91t77NmDPxUGBEZf z5$w~oWtF}gO%Y&Kzh-4UMmMLqxw(P-P`siXV2*lAUvlm{1FKMqVH`ZF0r~}a1PeL; z1)vInslv`*I#L#C1*|%wO>14!1w$1SFsnnksyBY90wcJjy~3EjzsOikF@U6i0~7gO zzsg7zp+GRIlzr$t)991bozj_!$Pg$q0Nx#Tw#YPSqMr23R7Y1g`>8Kjf`I)2C6I@b zx{5dg4kqkUux-S|#64qu?Hd~#z&$UoUw7O}7Iro=F-eOtzp+V_{%A0mkjw?sWJuQ! zQfU?%(Kr_5gN-&lz>rZg#fvqEWXVKlmw1cN0S{WJ| z%HFLiZMiVAn=J%>*`PO7LxjTwMAm!@4sy#x-uwG_#MJ9qEagCMEi0}G@?#vs1$fnW+cnlCIxfqZl0ncYJ& z@OLldrD6c(<^4jmo5W+Dc>C?AJZ$jzdt!pOA!&q1AUOes0$dI4A|U7hP)$HU1I&hi z;5FC(#RrHm8|=$#1kbfIg+Dmm4vgB=Q4xDOkNEN99q?B4j~~c*a!ozyAs}Fv1-k^j zO#e<~>iu2jVn&ueT=R=WQ@wq}X@^O{<@PP#`~r4{6g0J7KM%`!gfF;hXV>$uFN1b} zJY "Beneficiários", onde lhe é apresentada uma tabela com a listagem de todos os beneficiários registados. A listagem permite pesquisar e filtrar os beneficiários de forma rápida. + +## Critérios de Aceitação + +### 1. Interface Gráfica (UI) +- **Tabela de Beneficiários**: Deve conter as seguintes colunas: + + - **Número** (Número de beneficiário) + - **Nome** (Nome do beneficiário) + - **Nº Pessoas** (Número de pessoas do agregado familiar) + - **Estado** (Ativo / Inativo) + - **Ações** (Botões para Editar/Inativar/Ver Detalhes) +- **Filtros e Pesquisa**: + - Barra de pesquisa por Nome ou número + - Filtro por Estado (Todos, Ativos, Inativos). +- **Botão "Novo Beneficiário"**: Um botão destacado (ex: cor primária/verde) posicionado no topo da página para criar um novo beneficiário. +- **Paginação**: Caso existam muitos beneficiários, a tabela deve ser paginada (ex: 15 por página). + +### 2. Comportamento e Regras de Negócio +- Apenas utilizadores com a função **Admin** podem aceder a esta página. +- Se um utilizador sem permissões tentar aceder, o sistema deve apresentar uma página de erro 403 (Acesso Negado) ou redirecionar para a página inicial com mensagem de erro. +- A listagem deve ser ordenada alfabeticamente por Nome por defeito. + +### 3. Integração de Dados / Segurança +- Os dados devem ser lidos diretamente da tabela de beneficiários da base de dados SQLite. +- A consulta à base de dados deve ser executada exclusivamente no servidor (`+page.server.ts`). diff --git a/docs/user-stories/01-Admin/US03-detalhe-beneficiario.md b/docs/user-stories/01-Admin/US03-detalhe-beneficiario.md new file mode 100644 index 0000000..a9d88c1 --- /dev/null +++ b/docs/user-stories/01-Admin/US03-detalhe-beneficiario.md @@ -0,0 +1,37 @@ +# US03 - Detalhe e Edição de Beneficiário (Admin) + +**Como** Administrador do RefoodOne +**Quero** visualizar, criar e editar as informações de um beneficiário específico +**Para** manter os dados dos beneficiários atualizados no sistema. + +## Descrição do Fluxo +Este ecrã serve dois propósitos: +1. **Criação**: Acedido através do botão "Novo Beneficiário" na listagem (US02), abrindo o formulário vazio para preenchimento. +2. **Edição/Visualização**: Acedido através do botão de ação "Editar" na listagem (US02), abrindo o formulário pré-preenchido com os dados do beneficiário selecionado. + +## Critérios de Aceitação + +### 1. Interface Gráfica (UI) +- **Campos do Formulário**: + - **Número** (obrigatório, numérico único - identificador do beneficiário no sistema) + - **Nome** (obrigatório, texto) + - **Contacto** (obrigatório, número de telefone/telemóvel válido) + - **Nº Pessoas do Agregado** (obrigatório, numérico, mínimo 1) + - **Observações** (opcional, área de texto livre para notas adicionais) + - **Estado** (Ativo / Inativo - apenas na edição) +- **Botões de Ação**: + - **Guardar** (submete o formulário e guarda os dados) + - **Cancelar** (volta para a listagem sem guardar alterações) + +### 2. Comportamento e Regras de Negócio +- Apenas utilizadores com a função **Admin** podem aceder/gravar neste ecrã. +- **Validações**: + - O campo **Número** deve ser único na base de dados. Se o Administrador tentar guardar um número já existente, o sistema deve exibir um aviso claro em PT-PT. + - Todos os campos obrigatórios devem ser validados antes de permitir guardar. +- **Redirecionamento**: + - Após guardar com sucesso (inserir ou atualizar), o sistema deve redirecionar o utilizador de volta para a listagem de beneficiários (US02) com uma mensagem de sucesso (ex: *"Beneficiário guardado com sucesso"*). + - Clicar em Cancelar deve redirecionar de volta para a listagem (US02) sem efetuar qualquer alteração. + +### 3. Integração de Dados / Segurança +- As operações de escrita (INSERT/UPDATE) devem ser efetuadas de forma segura na base de dados SQLite através do Drizzle ORM. +- O processamento do formulário deve ser feito inteiramente no servidor (`+page.server.ts` actions). diff --git a/docs/user-stories/01-Admin/US04-listar-turnos.md b/docs/user-stories/01-Admin/US04-listar-turnos.md new file mode 100644 index 0000000..79395cc --- /dev/null +++ b/docs/user-stories/01-Admin/US04-listar-turnos.md @@ -0,0 +1,32 @@ +# US04 - Listar Turnos (Admin) + +**Como** Administrador ou Gestor de Turnos do RefoodOne +**Quero** visualizar a lista de todos os turnos de entregas registados no sistema +**Para** consultar o seu horário atual e os dias em que são realizados. + +## Descrição do Fluxo +O utilizador acede ao menu de administração correspondente aos "Turnos", onde lhe é apresentada uma tabela com os turnos configurados no sistema (ex: T1, T2, T3), indicando os seus horários e os dias da semana em que ocorrem. + +## Critérios de Aceitação + +### 1. Interface Gráfica (UI) +- **Tabela de Turnos**: Deve conter as seguintes colunas: + - **Identificador** (ex: T1, T2, T3) + - **Horário** (ex: 14h30 - 16h30) + - **Duração** (ex: 2h) + - **Dias de Funcionamento** (ex: Terças e Quintas) + - **Ações** (Botão para Editar) +- **Idioma**: Todos os textos e cabeçalhos devem estar em PT-PT. + +### 2. Comportamento e Regras de Negócio +- Apenas utilizadores com as funções de **Admin** ou **Gestor de Turnos** podem aceder a esta listagem. +- Por defeito, o sistema deve apresentar os turnos configurados atualmente: + - **T1**: 14h30 - 16h30 + - **T2**: 16h30 - 18h30 + - **T3**: 18h30 - 20h30 +- Por defeito, os dias de funcionamento são as **3ªs feiras (Terças)** e **5ªs feiras (Quintas)**. +- A listagem deve ser ordenada por ordem cronológica de horário de início. + +### 3. Integração de Dados / Segurança +- Os dados devem ser lidos da base de dados SQLite através das tabelas de configuração/turnos do sistema. +- A consulta à base de dados deve ser executada exclusivamente no servidor (`+page.server.ts`). diff --git a/docs/user-stories/01-Admin/US05-editar-turnos.md b/docs/user-stories/01-Admin/US05-editar-turnos.md new file mode 100644 index 0000000..092eb7d --- /dev/null +++ b/docs/user-stories/01-Admin/US05-editar-turnos.md @@ -0,0 +1,34 @@ +# US05 - Editar Horário e Dias de Turno (Admin) + +**Como** Administrador ou Gestor de Turnos do RefoodOne +**Quero** editar o horário (horas de início e fim) e os dias da semana de um turno específico +**Para** adaptar o funcionamento das entregas conforme a disponibilidade dos voluntários e as necessidades da Refood PdN. + +## Descrição do Fluxo +O utilizador clica no botão "Editar" de um turno específico na listagem de turnos (US04). É apresentado um formulário pré-preenchido onde pode alterar a hora de início, a hora de fim e selecionar/deselecionar os dias da semana em que o turno é realizado. + +## Critérios de Aceitação + +### 1. Interface Gráfica (UI) +- **Campos do Formulário**: + - **Identificador** (Apenas leitura/desativado, ex: "T1") + - **Hora de Início** (Obrigatório, seletor de tempo no formato HH:MM) + - **Hora de Fim** (Obrigatório, seletor de tempo no formato HH:MM) + - **Dias da Semana** (Obrigatório, checkboxes permitindo selecionar múltiplos dias, ex: Segunda a Domingo) +- **Botões de Ação**: + - **Guardar** (Submete o formulário e grava as alterações) + - **Cancelar** (Volta para a listagem sem guardar) + +### 2. Comportamento e Regras de Negócio +- Apenas utilizadores com as funções de **Admin** ou **Gestor de Turnos** podem aceder a este ecrã e guardar alterações. +- **Validações**: + - A hora de fim deve ser posterior à hora de início. + - A duração configurada deve respeitar as regras do sistema (ex: 2 horas por turno por defeito, ou emitir um aviso/validação caso não seja). + - Pelo menos um dia da semana deve ser selecionado (não é permitido ter um turno ativo sem dias associados). +- **Redirecionamento**: + - Após guardar com sucesso, redirecionar para a listagem de turnos (US04) com uma mensagem de sucesso em PT-PT (ex: *"Horário do turno guardado com sucesso"*). + - Clicar em Cancelar redireciona de volta para a listagem (US04) sem efetuar qualquer alteração. + +### 3. Integração de Dados / Segurança +- As alterações de horário e dias devem ser guardadas com segurança na base de dados SQLite através do Drizzle ORM. +- O processamento da ação do formulário deve ocorrer no servidor (`+page.server.ts` actions). diff --git a/docs/user-stories/01-Admin/US06-bootstrap-turnos.md b/docs/user-stories/01-Admin/US06-bootstrap-turnos.md new file mode 100644 index 0000000..2e84e17 --- /dev/null +++ b/docs/user-stories/01-Admin/US06-bootstrap-turnos.md @@ -0,0 +1,36 @@ +# US06 - Inicialização (Bootstrap) de Turnos + +**Como** Sistema do RefoodOne +**Quero** inicializar a base de dados com os turnos predefinidos (T1, T2 e T3) +**Para** garantir que a aplicação começa a funcionar com uma configuração base válida e sem necessidade de introdução manual de dados. + +## Descrição do Fluxo +Este é um processo automatizado executado pelo sistema (ex: através de um script de *seeding* ou na inicialização da base de dados). O sistema verifica se a tabela de turnos está vazia e, caso esteja, insere os três turnos base com os horários e dias da semana padrão. + +## Critérios de Aceitação + +### 1. Interface Gráfica (UI) +- Não aplicável (processo de sistema em segundo plano). + +### 2. Comportamento e Regras de Negócio +- **Verificação de Existência**: O bootstrap apenas deve ser executado se a tabela de turnos na base de dados SQLite estiver completamente vazia. Se já existirem dados, o processo não deve fazer nada (para evitar sobrescrever alterações manuais feitas pelo Administrador). +- **Dados Padrão a Inserir**: + - **Turno T1**: + - Código/Identificador: `T1` + - Hora de Início: `14:30` + - Hora de Fim: `16:30` + - Dias da Semana: Terça-feira (3ªf) e Quinta-feira (5ªf) + - **Turno T2**: + - Código/Identificador: `T2` + - Hora de Início: `16:30` + - Hora de Fim: `18:30` + - Dias da Semana: Terça-feira (3ªf) e Quinta-feira (5ªf) + - **Turno T3**: + - Código/Identificador: `T3` + - Hora de Início: `18:30` + - Hora de Fim: `20:30` + - Dias da Semana: Terça-feira (3ªf) e Quinta-feira (5ªf) + +### 3. Integração de Dados / Segurança +- A inserção dos dados deve ser feita de forma segura utilizando o Drizzle ORM num script de seed (`seed.ts` ou semelhante) ou num mecanismo executado durante o arranque do servidor. +- Os dias da semana devem ser armazenados num formato estruturado (ex: JSON array ou tabela de junção) para fácil manipulação pelas US04 e US05. diff --git a/drizzle.config.ts b/drizzle.config.ts new file mode 100644 index 0000000..9136a6d --- /dev/null +++ b/drizzle.config.ts @@ -0,0 +1,11 @@ +import { defineConfig } from 'drizzle-kit'; + +if (!process.env.DATABASE_URL) throw new Error('DATABASE_URL is not set'); + +export default defineConfig({ + schema: './src/lib/server/db/schema.ts', + dialect: 'sqlite', + dbCredentials: { url: process.env.DATABASE_URL }, + verbose: true, + strict: false +}); diff --git a/package-lock.json b/package-lock.json new file mode 100644 index 0000000..cc3de93 --- /dev/null +++ b/package-lock.json @@ -0,0 +1,4254 @@ +{ + "name": "refood-one", + "version": "0.0.1", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "refood-one", + "version": "0.0.1", + "dependencies": { + "@popperjs/core": "^2.11.8", + "bcrypt": "^6.0.0", + "better-sqlite3": "^12.8.0", + "bootstrap": "^5.3.8" + }, + "devDependencies": { + "@sveltejs/adapter-node": "^5.5.4", + "@sveltejs/kit": "^2.57.0", + "@sveltejs/vite-plugin-svelte": "^7.0.0", + "@types/bcrypt": "^6.0.0", + "@types/better-sqlite3": "^7.6.13", + "@types/node": "^24", + "drizzle-kit": "^0.31.10", + "drizzle-orm": "^0.45.2", + "svelte": "^5.55.2", + "svelte-check": "^4.4.6", + "typescript": "^6.0.2", + "vite": "^8.0.7" + } + }, + "node_modules/@drizzle-team/brocli": { + "version": "0.10.2", + "resolved": "https://registry.npmjs.org/@drizzle-team/brocli/-/brocli-0.10.2.tgz", + "integrity": "sha512-z33Il7l5dKjUgGULTqBsQBQwckHh5AbIuxhdsIxDDiZAzBOrZO6q9ogcWC65kU382AfynTfgNumVcNIjuIua6w==", + "dev": true, + "license": "Apache-2.0" + }, + "node_modules/@emnapi/core": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.10.0.tgz", + "integrity": "sha512-yq6OkJ4p82CAfPl0u9mQebQHKPJkY7WrIuk205cTYnYe+k2Z8YBh11FrbRG/H6ihirqcacOgl2BIO8oyMQLeXw==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@emnapi/wasi-threads": "1.2.1", + "tslib": "^2.4.0" + } + }, + "node_modules/@emnapi/runtime": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.10.0.tgz", + "integrity": "sha512-ewvYlk86xUoGI0zQRNq/mC+16R1QeDlKQy21Ki3oSYXNgLb45GV1P6A0M+/s6nyCuNDqe5VpaY84BzXGwVbwFA==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.4.0" + } + }, + "node_modules/@emnapi/wasi-threads": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@emnapi/wasi-threads/-/wasi-threads-1.2.1.tgz", + "integrity": "sha512-uTII7OYF+/Mes/MrcIOYp5yOtSMLBWSIoLPpcgwipoiKbli6k322tcoFsxoIIxPDqW01SQGAgko4EzZi2BNv2w==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.4.0" + } + }, + "node_modules/@esbuild-kit/core-utils": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/@esbuild-kit/core-utils/-/core-utils-3.3.2.tgz", + "integrity": "sha512-sPRAnw9CdSsRmEtnsl2WXWdyquogVpB3yZ3dgwJfe8zrOzTsV7cJvmwrKVa+0ma5BoiGJ+BoqkMvawbayKUsqQ==", + "deprecated": "Merged into tsx: https://tsx.is", + "dev": true, + "license": "MIT", + "dependencies": { + "esbuild": "~0.18.20", + "source-map-support": "^0.5.21" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/android-arm": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.18.20.tgz", + "integrity": "sha512-fyi7TDI/ijKKNZTUJAQqiG5T7YjJXgnzkURqmGj13C6dCqckZBLdl4h7bkhHt/t0WP+zO9/zwroDvANaOqO5Sw==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/android-arm64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.18.20.tgz", + "integrity": "sha512-Nz4rJcchGDtENV0eMKUNa6L12zz2zBDXuhj/Vjh18zGqB44Bi7MBMSXjgunJgjRhCmKOjnPuZp4Mb6OKqtMHLQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/android-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.18.20.tgz", + "integrity": "sha512-8GDdlePJA8D6zlZYJV/jnrRAi6rOiNaCC/JclcXpB+KIuvfBN4owLtgzY2bsxnx666XjJx2kDPUmnTtR8qKQUg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/darwin-arm64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.18.20.tgz", + "integrity": "sha512-bxRHW5kHU38zS2lPTPOyuyTm+S+eobPUnTNkdJEfAddYgEcll4xkT8DB9d2008DtTbl7uJag2HuE5NZAZgnNEA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/darwin-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.18.20.tgz", + "integrity": "sha512-pc5gxlMDxzm513qPGbCbDukOdsGtKhfxD1zJKXjCCcU7ju50O7MeAZ8c4krSJcOIJGFR+qx21yMMVYwiQvyTyQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/freebsd-arm64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.18.20.tgz", + "integrity": "sha512-yqDQHy4QHevpMAaxhhIwYPMv1NECwOvIpGCZkECn8w2WFHXjEwrBn3CeNIYsibZ/iZEUemj++M26W3cNR5h+Tw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/freebsd-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.18.20.tgz", + "integrity": "sha512-tgWRPPuQsd3RmBZwarGVHZQvtzfEBOreNuxEMKFcd5DaDn2PbBxfwLcj4+aenoh7ctXcbXmOQIn8HI6mCSw5MQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-arm": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.18.20.tgz", + "integrity": "sha512-/5bHkMWnq1EgKr1V+Ybz3s1hWXok7mDFUMQ4cG10AfW3wL02PSZi5kFpYKrptDsgb2WAJIvRcDm+qIvXf/apvg==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-arm64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.18.20.tgz", + "integrity": "sha512-2YbscF+UL7SQAVIpnWvYwM+3LskyDmPhe31pE7/aoTMFKKzIc9lLbyGUpmmb8a8AixOL61sQ/mFh3jEjHYFvdA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-ia32": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.18.20.tgz", + "integrity": "sha512-P4etWwq6IsReT0E1KHU40bOnzMHoH73aXp96Fs8TIT6z9Hu8G6+0SHSw9i2isWrD2nbx2qo5yUqACgdfVGx7TA==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-loong64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.18.20.tgz", + "integrity": "sha512-nXW8nqBTrOpDLPgPY9uV+/1DjxoQ7DoB2N8eocyq8I9XuqJ7BiAMDMf9n1xZM9TgW0J8zrquIb/A7s3BJv7rjg==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-mips64el": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.18.20.tgz", + "integrity": "sha512-d5NeaXZcHp8PzYy5VnXV3VSd2D328Zb+9dEq5HE6bw6+N86JVPExrA6O68OPwobntbNJ0pzCpUFZTo3w0GyetQ==", + "cpu": [ + "mips64el" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-ppc64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.18.20.tgz", + "integrity": "sha512-WHPyeScRNcmANnLQkq6AfyXRFr5D6N2sKgkFo2FqguP44Nw2eyDlbTdZwd9GYk98DZG9QItIiTlFLHJHjxP3FA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-riscv64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.18.20.tgz", + "integrity": "sha512-WSxo6h5ecI5XH34KC7w5veNnKkju3zBRLEQNY7mv5mtBmrP/MjNBCAlsM2u5hDBlS3NGcTQpoBvRzqBcRtpq1A==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-s390x": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.18.20.tgz", + "integrity": "sha512-+8231GMs3mAEth6Ja1iK0a1sQ3ohfcpzpRLH8uuc5/KVDFneH6jtAJLFGafpzpMRO6DzJ6AvXKze9LfFMrIHVQ==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/linux-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.18.20.tgz", + "integrity": "sha512-UYqiqemphJcNsFEskc73jQ7B9jgwjWrSayxawS6UVFZGWrAAtkzjxSqnoclCXxWtfwLdzU+vTpcNYhpn43uP1w==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/netbsd-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.18.20.tgz", + "integrity": "sha512-iO1c++VP6xUBUmltHZoMtCUdPlnPGdBom6IrO4gyKPFFVBKioIImVooR5I83nTew5UOYrk3gIJhbZh8X44y06A==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/openbsd-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.18.20.tgz", + "integrity": "sha512-e5e4YSsuQfX4cxcygw/UCPIEP6wbIL+se3sxPdCiMbFLBWu0eiZOJ7WoD+ptCLrmjZBK1Wk7I6D/I3NglUGOxg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/sunos-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.18.20.tgz", + "integrity": "sha512-kDbFRFp0YpTQVVrqUd5FTYmWo45zGaXe0X8E1G/LKFC0v8x0vWrhOWSLITcCn63lmZIxfOMXtCfti/RxN/0wnQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/win32-arm64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.18.20.tgz", + "integrity": "sha512-ddYFR6ItYgoaq4v4JmQQaAI5s7npztfV4Ag6NrhiaW0RrnOXqBkgwZLofVTlq1daVTQNhtI5oieTvkRPfZrePg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/win32-ia32": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.18.20.tgz", + "integrity": "sha512-Wv7QBi3ID/rROT08SABTS7eV4hX26sVduqDOTe1MvGMjNd3EjOz4b7zeexIR62GTIEKrfJXKL9LFxTYgkyeu7g==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/@esbuild/win32-x64": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.18.20.tgz", + "integrity": "sha512-kTdfRcSiDfQca/y9QIkng02avJ+NCaQvrMejlsB3RRv5sE9rRoeBPISaZpKxHELzRxZyLvNts1P27W3wV+8geQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild-kit/core-utils/node_modules/esbuild": { + "version": "0.18.20", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.18.20.tgz", + "integrity": "sha512-ceqxoedUrcayh7Y7ZX6NdbbDzGROiyVBgC4PriJThBKSVPWnnFHZAkfI1lJT8QFkOwH4qOS2SJkS4wvpGl8BpA==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=12" + }, + "optionalDependencies": { + "@esbuild/android-arm": "0.18.20", + "@esbuild/android-arm64": "0.18.20", + "@esbuild/android-x64": "0.18.20", + "@esbuild/darwin-arm64": "0.18.20", + "@esbuild/darwin-x64": "0.18.20", + "@esbuild/freebsd-arm64": "0.18.20", + "@esbuild/freebsd-x64": "0.18.20", + "@esbuild/linux-arm": "0.18.20", + "@esbuild/linux-arm64": "0.18.20", + "@esbuild/linux-ia32": "0.18.20", + "@esbuild/linux-loong64": "0.18.20", + "@esbuild/linux-mips64el": "0.18.20", + "@esbuild/linux-ppc64": "0.18.20", + "@esbuild/linux-riscv64": "0.18.20", + "@esbuild/linux-s390x": "0.18.20", + "@esbuild/linux-x64": "0.18.20", + "@esbuild/netbsd-x64": "0.18.20", + "@esbuild/openbsd-x64": "0.18.20", + "@esbuild/sunos-x64": "0.18.20", + "@esbuild/win32-arm64": "0.18.20", + "@esbuild/win32-ia32": "0.18.20", + "@esbuild/win32-x64": "0.18.20" + } + }, + "node_modules/@esbuild-kit/esm-loader": { + "version": "2.6.5", + "resolved": "https://registry.npmjs.org/@esbuild-kit/esm-loader/-/esm-loader-2.6.5.tgz", + "integrity": "sha512-FxEMIkJKnodyA1OaCUoEvbYRkoZlLZ4d/eXFu9Fh8CbBBgP5EmZxrfTRyN0qpXZ4vOvqnE5YdRdcrmUUXuU+dA==", + "deprecated": "Merged into tsx: https://tsx.is", + "dev": true, + "license": "MIT", + "dependencies": { + "@esbuild-kit/core-utils": "^3.3.2", + "get-tsconfig": "^4.7.0" + } + }, + "node_modules/@esbuild/aix-ppc64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.28.0.tgz", + "integrity": "sha512-lhRUCeuOyJQURhTxl4WkpFTjIsbDayJHih5kZC1giwE+MhIzAb7mEsQMqMf18rHLsrb5qI1tafG20mLxEWcWlA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "aix" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-arm": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.28.0.tgz", + "integrity": "sha512-wqh0ByljabXLKHeWXYLqoJ5jKC4XBaw6Hk08OfMrCRd2nP2ZQ5eleDZC41XHyCNgktBGYMbqnrJKq/K/lzPMSQ==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.28.0.tgz", + "integrity": "sha512-+WzIXQOSaGs33tLEgYPYe/yQHf0WTU0X42Jca3y8NWMbUVhp7rUnw+vAsRC/QiDrdD31IszMrZy+qwPOPjd+rw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/android-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.28.0.tgz", + "integrity": "sha512-+VJggoaKhk2VNNqVL7f6S189UzShHC/mR9EE8rDdSkdpN0KflSwWY/gWjDrNxxisg8Fp1ZCD9jLMo4m0OUfeUA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/darwin-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.28.0.tgz", + "integrity": "sha512-0T+A9WZm+bZ84nZBtk1ckYsOvyA3x7e2Acj1KdVfV4/2tdG4fzUp91YHx+GArWLtwqp77pBXVCPn2We7Letr0Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/darwin-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.28.0.tgz", + "integrity": "sha512-fyzLm/DLDl/84OCfp2f/XQ4flmORsjU7VKt8HLjvIXChJoFFOIL6pLJPH4Yhd1n1gGFF9mPwtlN5Wf82DZs+LQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/freebsd-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.28.0.tgz", + "integrity": "sha512-l9GeW5UZBT9k9brBYI+0WDffcRxgHQD8ShN2Ur4xWq/NFzUKm3k5lsH4PdaRgb2w7mI9u61nr2gI2mLI27Nh3Q==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/freebsd-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.28.0.tgz", + "integrity": "sha512-BXoQai/A0wPO6Es3yFJ7APCiKGc1tdAEOgeTNy3SsB491S3aHn4S4r3e976eUnPdU+NbdtmBuLncYir2tMU9Nw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-arm": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.28.0.tgz", + "integrity": "sha512-CjaaREJagqJp7iTaNQjjidaNbCKYcd4IDkzbwwxtSvjI7NZm79qiHc8HqciMddQ6CKvJT6aBd8lO9kN/ZudLlw==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.28.0.tgz", + "integrity": "sha512-RVyzfb3FWsGA55n6WY0MEIEPURL1FcbhFE6BffZEMEekfCzCIMtB5yyDcFnVbTnwk+CLAgTujmV/Lgvih56W+A==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-ia32": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.28.0.tgz", + "integrity": "sha512-KBnSTt1kxl9x70q+ydterVdl+Cn0H18ngRMRCEQfrbqdUuntQQ0LoMZv47uB97NljZFzY6HcfqEZ2SAyIUTQBQ==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-loong64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.28.0.tgz", + "integrity": "sha512-zpSlUce1mnxzgBADvxKXX5sl8aYQHo2ezvMNI8I0lbblJtp8V4odlm3Yzlj7gPyt3T8ReksE6bK+pT3WD+aJRg==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-mips64el": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.28.0.tgz", + "integrity": "sha512-2jIfP6mmjkdmeTlsX/9vmdmhBmKADrWqN7zcdtHIeNSCH1SqIoNI63cYsjQR8J+wGa4Y5izRcSHSm8K3QWmk3w==", + "cpu": [ + "mips64el" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-ppc64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.28.0.tgz", + "integrity": "sha512-bc0FE9wWeC0WBm49IQMPSPILRocGTQt3j5KPCA8os6VprfuJ7KD+5PzESSrJ6GmPIPJK965ZJHTUlSA6GNYEhg==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-riscv64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.28.0.tgz", + "integrity": "sha512-SQPZOwoTTT/HXFXQJG/vBX8sOFagGqvZyXcgLA3NhIqcBv1BJU1d46c0rGcrij2B56Z2rNiSLaZOYW5cUk7yLQ==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-s390x": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.28.0.tgz", + "integrity": "sha512-SCfR0HN8CEEjnYnySJTd2cw0k9OHB/YFzt5zgJEwa+wL/T/raGWYMBqwDNAC6dqFKmJYZoQBRfHjgwLHGSrn3Q==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/linux-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.28.0.tgz", + "integrity": "sha512-us0dSb9iFxIi8srnpl931Nvs65it/Jd2a2K3qs7fz2WfGPHqzfzZTfec7oxZJRNPXPnNYZtanmRc4AL/JwVzHQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/netbsd-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.28.0.tgz", + "integrity": "sha512-CR/RYotgtCKwtftMwJlUU7xCVNg3lMYZ0RzTmAHSfLCXw3NtZtNpswLEj/Kkf6kEL3Gw+BpOekRX0BYCtklhUw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/netbsd-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.28.0.tgz", + "integrity": "sha512-nU1yhmYutL+fQ71Kxnhg8uEOdC0pwEW9entHykTgEbna2pw2dkbFSMeqjjyHZoCmt8SBkOSvV+yNmm94aUrrqw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openbsd-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.28.0.tgz", + "integrity": "sha512-cXb5vApOsRsxsEl4mcZ1XY3D4DzcoMxR/nnc4IyqYs0rTI8ZKmW6kyyg+11Z8yvgMfAEldKzP7AdP64HnSC/6g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openbsd-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.28.0.tgz", + "integrity": "sha512-8wZM2qqtv9UP3mzy7HiGYNH/zjTA355mpeuA+859TyR+e+Tc08IHYpLJuMsfpDJwoLo1ikIJI8jC3GFjnRClzA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/openharmony-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/openharmony-arm64/-/openharmony-arm64-0.28.0.tgz", + "integrity": "sha512-FLGfyizszcef5C3YtoyQDACyg95+dndv79i2EekILBofh5wpCa1KuBqOWKrEHZg3zrL3t5ouE5jgr94vA+Wb2w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openharmony" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/sunos-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.28.0.tgz", + "integrity": "sha512-1ZgjUoEdHZZl/YlV76TSCz9Hqj9h9YmMGAgAPYd+q4SicWNX3G5GCyx9uhQWSLcbvPW8Ni7lj4gDa1T40akdlw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-arm64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.28.0.tgz", + "integrity": "sha512-Q9StnDmQ/enxnpxCCLSg0oo4+34B9TdXpuyPeTedN/6+iXBJ4J+zwfQI28u/Jl40nOYAxGoNi7mFP40RUtkmUA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-ia32": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.28.0.tgz", + "integrity": "sha512-zF3ag/gfiCe6U2iczcRzSYJKH1DCI+ByzSENHlM2FcDbEeo5Zd2C86Aq0tKUYAJJ1obRP84ymxIAksZUcdztHA==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@esbuild/win32-x64": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.28.0.tgz", + "integrity": "sha512-pEl1bO9mfAmIC+tW5btTmrKaujg3zGtUmWNdCw/xs70FBjwAL3o9OEKNHvNmnyylD6ubxUERiEhdsL0xBQ9efw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/@jridgewell/gen-mapping": { + "version": "0.3.13", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz", + "integrity": "sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/sourcemap-codec": "^1.5.0", + "@jridgewell/trace-mapping": "^0.3.24" + } + }, + "node_modules/@jridgewell/remapping": { + "version": "2.3.5", + "resolved": "https://registry.npmjs.org/@jridgewell/remapping/-/remapping-2.3.5.tgz", + "integrity": "sha512-LI9u/+laYG4Ds1TDKSJW2YPrIlcVYOwi2fUC6xB43lueCjgxV4lffOCZCtYFiH6TNOX+tQKXx97T4IKHbhyHEQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/gen-mapping": "^0.3.5", + "@jridgewell/trace-mapping": "^0.3.24" + } + }, + "node_modules/@jridgewell/resolve-uri": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", + "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.5.5", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz", + "integrity": "sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==", + "dev": true, + "license": "MIT" + }, + "node_modules/@jridgewell/trace-mapping": { + "version": "0.3.31", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.31.tgz", + "integrity": "sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/resolve-uri": "^3.1.0", + "@jridgewell/sourcemap-codec": "^1.4.14" + } + }, + "node_modules/@napi-rs/wasm-runtime": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/@napi-rs/wasm-runtime/-/wasm-runtime-1.1.4.tgz", + "integrity": "sha512-3NQNNgA1YSlJb/kMH1ildASP9HW7/7kYnRI2szWJaofaS1hWmbGI4H+d3+22aGzXXN9IJ+n+GiFVcGipJP18ow==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@tybys/wasm-util": "^0.10.1" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/Brooooooklyn" + }, + "peerDependencies": { + "@emnapi/core": "^1.7.1", + "@emnapi/runtime": "^1.7.1" + } + }, + "node_modules/@oxc-project/types": { + "version": "0.132.0", + "resolved": "https://registry.npmjs.org/@oxc-project/types/-/types-0.132.0.tgz", + "integrity": "sha512-FESMOxil5Se014ui/Eq8fT5uHJo6nIRwH0PfJrZJXs6Gek3ZVFOrpUv3YIZT20m+extU98Hg1Ym72U58rlsxUQ==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/Boshen" + } + }, + "node_modules/@polka/url": { + "version": "1.0.0-next.29", + "resolved": "https://registry.npmjs.org/@polka/url/-/url-1.0.0-next.29.tgz", + "integrity": "sha512-wwQAWhWSuHaag8c4q/KN/vCoeOJYshAIvMQwD4GpSb3OiZklFfvAgmj0VCBBImRpuF/aFgIRzllXlVX93Jevww==", + "dev": true, + "license": "MIT" + }, + "node_modules/@popperjs/core": { + "version": "2.11.8", + "resolved": "https://registry.npmjs.org/@popperjs/core/-/core-2.11.8.tgz", + "integrity": "sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A==", + "license": "MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/popperjs" + } + }, + "node_modules/@rolldown/binding-android-arm64": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-android-arm64/-/binding-android-arm64-1.0.2.tgz", + "integrity": "sha512-ZS4D1JPGn/MYQN/SYDWftIE/nVsM8j/AFOYEzAoOE2O3NktQOZru+/vYXGbR/qtdLdIfGCP0lcoJiYVzsEz+iQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-darwin-arm64": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-arm64/-/binding-darwin-arm64-1.0.2.tgz", + "integrity": "sha512-vdFA9+C/rekyGce7WqHs/xoT0ioZEWaOFyZLIV1mEeNFaFDUQrPIo8Vs2GvJ6eetb3rzDUtUBgzto3ExpXJB3w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-darwin-x64": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-x64/-/binding-darwin-x64-1.0.2.tgz", + "integrity": "sha512-BewSOwTHazv77DTYiAZXSqqKZ4KP/KonFisDMVU7PImxoWfB2aepnPhd2E4SWz3zDzYgDNbs6jBmTdgNnF02GA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-freebsd-x64": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-freebsd-x64/-/binding-freebsd-x64-1.0.2.tgz", + "integrity": "sha512-m41o7M0YWtUdqk61Tb+jnKb2rN++iRdIASlExkUoKfIAH30DOHCB8fVLzSUpbWHHU8esmEioY62PxzexE8MBuA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-linux-arm-gnueabihf": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm-gnueabihf/-/binding-linux-arm-gnueabihf-1.0.2.tgz", + "integrity": "sha512-jcojB9H7W/jS29pMKWAK1N+fU99vXodHDTatS3b3y/XSOCiHo0kkA74pL3jJmkoQtYpOCxDvaKs1fo2Ij/1X5w==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-linux-arm64-gnu": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-gnu/-/binding-linux-arm64-gnu-1.0.2.tgz", + "integrity": "sha512-1jn6qDU5iiOgFgygDzKUuKP0maTi0/f1+sBLgvij/76C77Nm3ts6ufz9Bjg5q5dduxiUIxtq86JIoBvo1xQ4Ig==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-linux-arm64-musl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-musl/-/binding-linux-arm64-musl-1.0.2.tgz", + "integrity": "sha512-QVLO/czFMdoMFSqlX3bcswcJNm/23r+qoa/jgtmFc/qEp6/jXmIkDjF/XIo8dPfGaiwy1xfQn8o77L79GeXFgw==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-linux-ppc64-gnu": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-ppc64-gnu/-/binding-linux-ppc64-gnu-1.0.2.tgz", + "integrity": "sha512-hgO5Abm0w5UL6FEa2iFnZqo2KlK7TQ5QhV5x09hujBf7t5KzHQ1VmfPuTpqRy/rNlSxua3eWH374xxiVrP+lcA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-linux-s390x-gnu": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-s390x-gnu/-/binding-linux-s390x-gnu-1.0.2.tgz", + "integrity": "sha512-fy8rXxuYEu602abC8MUNaPjYLIFzReOaEIEMKMUa0rFEUxNpVXhs15KSSQ4qlqSaM7B6rcj9rDZgADh/IGDzLQ==", + "cpu": [ + "s390x" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-linux-x64-gnu": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-gnu/-/binding-linux-x64-gnu-1.0.2.tgz", + "integrity": "sha512-0+bOkiQ779+r1WpoHOWHqncvyySci0vKph+myNDYb+im6meJAzHQXay6oEgnkHuUGouM1LKTZwqKpBow6Kj7CQ==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-linux-x64-musl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-musl/-/binding-linux-x64-musl-1.0.2.tgz", + "integrity": "sha512-mjSkrzZK5Qsl0a9d1JgILOiuZOSDTVdKENcSXBoqbzSrspLR/4/IRVDo5wd2GgZjNss/viBFJdeq+j7qH2nypw==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-openharmony-arm64": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-openharmony-arm64/-/binding-openharmony-arm64-1.0.2.tgz", + "integrity": "sha512-1v5vHasdfQAZoEHakBV72LIFAC9JjnymsiKxp+GEr/ma3+NJCPSaYK+qavInOovJkgwFrs7GccX2d6IgDA3Z5w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openharmony" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-wasm32-wasi": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-wasm32-wasi/-/binding-wasm32-wasi-1.0.2.tgz", + "integrity": "sha512-mb1VobWn6NheziTk5/WEaR6AKVbrwT5sOi6C7zk3gy/pD1qtJfU1j4PgTo2NJnOtbL9Dl3Aeei8w9jJ7qC2jZQ==", + "cpu": [ + "wasm32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "@emnapi/core": "1.10.0", + "@emnapi/runtime": "1.10.0", + "@napi-rs/wasm-runtime": "^1.1.4" + }, + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-win32-arm64-msvc": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-win32-arm64-msvc/-/binding-win32-arm64-msvc-1.0.2.tgz", + "integrity": "sha512-SqKonF56vA/L2yHwHYcEp2P34URpOZ7d1fS635cTkpDnUtEGdUbhI6NzsPdqeSWvAAeGDrxjWjNmibDIdFf9/A==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/binding-win32-x64-msvc": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@rolldown/binding-win32-x64-msvc/-/binding-win32-x64-msvc-1.0.2.tgz", + "integrity": "sha512-v7qRI7gXLRINcOGXt+7YmAZ6iFuyZVMIoXAxhd8oP+DR9dLfL9GfNIx7PLMxmhZdvq8waUJBQiWN9EKNy+TRBQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": "^20.19.0 || >=22.12.0" + } + }, + "node_modules/@rolldown/pluginutils": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@rolldown/pluginutils/-/pluginutils-1.0.1.tgz", + "integrity": "sha512-2j9bGt5Jh8hj+vPtgzPtl72j0yRxHAyumoo6TNfAjsLB04UtpSvPbPcDcBMxz7n+9CYB0c1GxQFxYRg2jimqGw==", + "dev": true, + "license": "MIT" + }, + "node_modules/@rollup/plugin-commonjs": { + "version": "29.0.3", + "resolved": "https://registry.npmjs.org/@rollup/plugin-commonjs/-/plugin-commonjs-29.0.3.tgz", + "integrity": "sha512-ZaOxZceP7SOUW7Lqw5IRVweSQYWaeIPnXIGLiB690EBA3FGJTO40EEr2L5yZplJWsgTCogILRSpcAe7+U0Otdg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@rollup/pluginutils": "^5.0.1", + "commondir": "^1.0.1", + "estree-walker": "^2.0.2", + "fdir": "^6.2.0", + "is-reference": "1.2.1", + "magic-string": "^0.30.3", + "picomatch": "^4.0.2" + }, + "engines": { + "node": ">=16.0.0 || 14 >= 14.17" + }, + "peerDependencies": { + "rollup": "^2.68.0||^3.0.0||^4.0.0" + }, + "peerDependenciesMeta": { + "rollup": { + "optional": true + } + } + }, + "node_modules/@rollup/plugin-json": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/@rollup/plugin-json/-/plugin-json-6.1.0.tgz", + "integrity": "sha512-EGI2te5ENk1coGeADSIwZ7G2Q8CJS2sF120T7jLw4xFw9n7wIOXHo+kIYRAoVpJAN+kmqZSoO3Fp4JtoNF4ReA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@rollup/pluginutils": "^5.1.0" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "rollup": "^1.20.0||^2.0.0||^3.0.0||^4.0.0" + }, + "peerDependenciesMeta": { + "rollup": { + "optional": true + } + } + }, + "node_modules/@rollup/plugin-node-resolve": { + "version": "16.0.3", + "resolved": "https://registry.npmjs.org/@rollup/plugin-node-resolve/-/plugin-node-resolve-16.0.3.tgz", + "integrity": "sha512-lUYM3UBGuM93CnMPG1YocWu7X802BrNF3jW2zny5gQyLQgRFJhV1Sq0Zi74+dh/6NBx1DxFC4b4GXg9wUCG5Qg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@rollup/pluginutils": "^5.0.1", + "@types/resolve": "1.20.2", + "deepmerge": "^4.2.2", + "is-module": "^1.0.0", + "resolve": "^1.22.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "rollup": "^2.78.0||^3.0.0||^4.0.0" + }, + "peerDependenciesMeta": { + "rollup": { + "optional": true + } + } + }, + "node_modules/@rollup/pluginutils": { + "version": "5.4.0", + "resolved": "https://registry.npmjs.org/@rollup/pluginutils/-/pluginutils-5.4.0.tgz", + "integrity": "sha512-MfPp06CjRLfXQ3wY0R8vJDYBy/MvVcc9OulEfR0B8Iv9ko+GCNaRZ+EpJYFl27LhKsZK0o420sYCRHCjfCgeUg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "^1.0.0", + "estree-walker": "^2.0.2", + "picomatch": "^4.0.2" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "rollup": "^1.20.0||^2.0.0||^3.0.0||^4.0.0" + }, + "peerDependenciesMeta": { + "rollup": { + "optional": true + } + } + }, + "node_modules/@rollup/rollup-android-arm-eabi": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.60.4.tgz", + "integrity": "sha512-F5QXMSiFebS9hKZj02XhWLLnRpJ3B3AROP0tWbFBSj+6kCbg5m9j5JoHKd4mmSVy5mS/IMQloYgYxCuJC0fxEQ==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-android-arm64": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.60.4.tgz", + "integrity": "sha512-GxxTKApUpzRhof7poWvCJHRF51C67u1R7D6DiluBE8wKU1u5GWE8t+v81JvJYtbawoBFX1hLv5Ei4eVjkWokaw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-darwin-arm64": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.60.4.tgz", + "integrity": "sha512-tua0TaJxMOB1R0V0RS1jFZ/RpURFDJIOR2A6jWwQeawuFyS4gBW+rntLRaQd0EQ4bd6Vp44Z2rXW+YYDBsj6IA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-darwin-x64": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.60.4.tgz", + "integrity": "sha512-CSKq7MsP+5PFIcydhAiR1K0UhEI1A2jWXVKHPCBZ151yOutENwvnPocgVHkivu2kviURtCEB6zUQw0vs8RrhMg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-freebsd-arm64": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.60.4.tgz", + "integrity": "sha512-+O8OkVdyvXMtJEciu2wS/pzm1IxntEEQx3z5TAVy4l32G0etZn+RsA48ARRrFm6Ri8fvqPQfgrvNxSjKAbnd3g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-freebsd-x64": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.60.4.tgz", + "integrity": "sha512-Iw3oMskH3AfNuhU0MSN7vNbdi4me/NiYo2azqPz/Le16zHSa+3RRmliCMWWQmh4lcndccU40xcJuTYJZxNo/lw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-linux-arm-gnueabihf": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.60.4.tgz", + "integrity": "sha512-EIPRXTVQpHyF8WOo219AD2yEltPehLTcTMz2fn6JsatLYSzQf00hj3rulF+yauOlF9/FtM2WpkT/hJh/KJFGhA==", + "cpu": [ + "arm" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm-musleabihf": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.60.4.tgz", + "integrity": "sha512-J3Yh9PzzF1Ovah2At+lHiGQdsYgArxBbXv/zHfSyaiFQEqvNv7DcW98pCrmdjCZBrqBiKrKKe2V+aaSGWuBe/w==", + "cpu": [ + "arm" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.60.4.tgz", + "integrity": "sha512-BFDEZMYfUvLn37ONE1yMBojPxnMlTFsdyNoqncT0qFq1mAfllL+ATMMJd8TeuVMiX84s1KbcxcZbXInmcO2mRg==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-musl": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.60.4.tgz", + "integrity": "sha512-pc9EYOSlOgdQ2uPl1o9PF6/kLSgaUosia7gOuS8mB69IxJvlclko1MECXysjs5ryez1/5zjYqx3+xYU0TU6R1A==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-loong64-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.60.4.tgz", + "integrity": "sha512-NxnomyxYerDh5n4iLrNa+sH+Z+U4BMEE46V2PgQ/hoB909i8gV1M5wPojWg9fk1jWpO3IQnOs20K4wyZuFLEFQ==", + "cpu": [ + "loong64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-loong64-musl": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.60.4.tgz", + "integrity": "sha512-nbJnQ8a3z1mtmrwImCYhc6BGpThAyYVRQxw9uKSKG4wR6aAYno9sVjJ0zaZcW9BPJX1GbrDPf+SvdWjgTuDmnw==", + "cpu": [ + "loong64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-ppc64-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.60.4.tgz", + "integrity": "sha512-2EU6acNrQLd8tYvo/LXW535wupT3m6fo7HKo6lr7ktQoItxTyOL1ZCR/GfGCuXl2vR+zmfI6eRXkSemafv+iVg==", + "cpu": [ + "ppc64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-ppc64-musl": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.60.4.tgz", + "integrity": "sha512-WeBtoMuaMxiiIrO2IYP3xs6GMWkJP2C0EoT8beTLkUPmzV1i/UcOSVw1d5r9KBODtHKilG5yFxsGRnBbK3wJ4A==", + "cpu": [ + "ppc64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.60.4.tgz", + "integrity": "sha512-FJHFfqpKUI3A10WrWKiFbBZ7yVbGT4q4B5o1qKFFojqpaYoh9LrQgqWCmmcxQzVSXYtyB5bzkXrYzlHTs21MYA==", + "cpu": [ + "riscv64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-musl": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.60.4.tgz", + "integrity": "sha512-mcEl6CUT5IAUmQf1m9FYSmVqCJlpQ8r8eyftFUHG8i9OhY7BkBXSUdnLH5DOf0wCOjcP9v/QO93zpmF1SptCCw==", + "cpu": [ + "riscv64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-s390x-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.60.4.tgz", + "integrity": "sha512-ynt3JxVd2w2buzoKDWIyiV1pJW93xlQic1THVLXilz429oijRpSHivZAgp65KBu+cMcgf1eVVjdnTLvPxgCuoQ==", + "cpu": [ + "s390x" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.60.4.tgz", + "integrity": "sha512-Boiz5+MsaROEWDf+GGEwF8VMHGhlUoQMtIPjOgA5fv4osupqTVnJteQNKJwUcnUog2G55jYXH7KZFFiJe0TEzQ==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-musl": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.60.4.tgz", + "integrity": "sha512-+qfSY27qIrFfI/Hom04KYFw3GKZSGU4lXus51wsb5EuySfFlWRwjkKWoE9emgRw/ukoT4Udsj4W/+xxG8VbPKg==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-openbsd-x64": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.60.4.tgz", + "integrity": "sha512-VpTfOPHgVXEBeeR8hZ2O0F3aSso+JDWqTWmTmzcQKted54IAdUVbxE+j/MVxUsKa8L20HJhv3vUezVPoquqWjA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ] + }, + "node_modules/@rollup/rollup-openharmony-arm64": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.60.4.tgz", + "integrity": "sha512-IPOsh5aRYuLv/nkU51X10Bf75Bsf6+gZdx1X+QP5QM6lIJFHHqbHLG0uJn/hWthzo13UAc2umiUorqZy3axoZg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openharmony" + ] + }, + "node_modules/@rollup/rollup-win32-arm64-msvc": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.60.4.tgz", + "integrity": "sha512-4QzE9E81OohJ/HKzHhsqU+zcYYojVOXlFMs1DdyMT6qXl/niOH7AVElmmEdUNHHS/oRkc++d5k6Vy85zFs0DEw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-ia32-msvc": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.60.4.tgz", + "integrity": "sha512-zTPgT1YuHHcd+Tmx7h8aml0FWFVelV5N54oHow9SLj+GfoDy/huQ+UV396N/C7KpMDMiPspRktzM1/0r1usYEA==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-gnu": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.60.4.tgz", + "integrity": "sha512-DRS4G7mi9lJxqEDezIkKCaUIKCrLUUDCUaCsTPCi/rtqaC6D/jjwslMQyiDU50Ka0JKpeXeRBFBAXwArY52vBw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-msvc": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.60.4.tgz", + "integrity": "sha512-QVTUovf40zgTqlFVrKA1uXMVvU2QWEFWfAH8Wdc48IxLvrJMQVMBRjuQyUpzZCDkakImib9eVazbWlC6ksWtJw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@standard-schema/spec": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@standard-schema/spec/-/spec-1.1.0.tgz", + "integrity": "sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==", + "dev": true, + "license": "MIT" + }, + "node_modules/@sveltejs/acorn-typescript": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/@sveltejs/acorn-typescript/-/acorn-typescript-1.0.10.tgz", + "integrity": "sha512-4WfKk68eTih+MiJD4fSbxN7E8kVBmTMPWHUPYjvl2N0rMs53YLTT8/YjKU5Dtnz5LqDjl7LEw4U7lXR2W3J5WA==", + "dev": true, + "license": "MIT", + "peerDependencies": { + "acorn": "^8.9.0" + } + }, + "node_modules/@sveltejs/adapter-node": { + "version": "5.5.4", + "resolved": "https://registry.npmjs.org/@sveltejs/adapter-node/-/adapter-node-5.5.4.tgz", + "integrity": "sha512-45X92CXW+2J8ZUzPv3eLlKWEzINKiiGeFWTjyER4ZN4sGgNoaoeSkCY/QYNxHpPXy71QPsctwccBo9jJs0ySPQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@rollup/plugin-commonjs": "^29.0.0", + "@rollup/plugin-json": "^6.1.0", + "@rollup/plugin-node-resolve": "^16.0.0", + "rollup": "^4.59.0" + }, + "peerDependencies": { + "@sveltejs/kit": "^2.4.0" + } + }, + "node_modules/@sveltejs/kit": { + "version": "2.61.1", + "resolved": "https://registry.npmjs.org/@sveltejs/kit/-/kit-2.61.1.tgz", + "integrity": "sha512-Ny8s1SR1TyQS2hD2Rvw0XKzU2Nw1eUF52dTb6T2bdcgz7wSC+Nyb5IwjWYlR4b2dvbbR5NJDiQwHg3rnNseghg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@standard-schema/spec": "^1.0.0", + "@sveltejs/acorn-typescript": "^1.0.9", + "@types/cookie": "^0.6.0", + "acorn": "^8.16.0", + "cookie": "^0.6.0", + "devalue": "^5.8.1", + "esm-env": "^1.2.2", + "kleur": "^4.1.5", + "magic-string": "^0.30.5", + "mrmime": "^2.0.0", + "set-cookie-parser": "^3.0.0", + "sirv": "^3.0.0" + }, + "bin": { + "svelte-kit": "svelte-kit.js" + }, + "engines": { + "node": ">=18.13" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.0.0", + "@sveltejs/vite-plugin-svelte": "^3.0.0 || ^4.0.0-next.1 || ^5.0.0 || ^6.0.0-next.0 || ^7.0.0", + "svelte": "^4.0.0 || ^5.0.0-next.0", + "typescript": "^5.3.3 || ^6.0.0", + "vite": "^5.0.3 || ^6.0.0 || ^7.0.0-beta.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "@opentelemetry/api": { + "optional": true + }, + "typescript": { + "optional": true + } + } + }, + "node_modules/@sveltejs/vite-plugin-svelte": { + "version": "7.1.2", + "resolved": "https://registry.npmjs.org/@sveltejs/vite-plugin-svelte/-/vite-plugin-svelte-7.1.2.tgz", + "integrity": "sha512-DrUBA2UXRfDmUX/ZTiEopd3X40yavsJF1FX2RygcuIScHL7o5YX1fMvoYnDhjeJQC4weCOklirpNWlcb2NiSeA==", + "dev": true, + "license": "MIT", + "dependencies": { + "deepmerge": "^4.3.1", + "magic-string": "^0.30.21", + "obug": "^2.1.0", + "vitefu": "^1.1.2" + }, + "engines": { + "node": "^20.19 || ^22.12 || >=24" + }, + "peerDependencies": { + "svelte": "^5.46.4", + "vite": "^8.0.0-beta.7 || ^8.0.0" + } + }, + "node_modules/@tybys/wasm-util": { + "version": "0.10.2", + "resolved": "https://registry.npmjs.org/@tybys/wasm-util/-/wasm-util-0.10.2.tgz", + "integrity": "sha512-RoBvJ2X0wuKlWFIjrwffGw1IqZHKQqzIchKaadZZfnNpsAYp2mM0h36JtPCjNDAHGgYez/15uMBpfGwchhiMgg==", + "dev": true, + "license": "MIT", + "optional": true, + "dependencies": { + "tslib": "^2.4.0" + } + }, + "node_modules/@types/bcrypt": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/@types/bcrypt/-/bcrypt-6.0.0.tgz", + "integrity": "sha512-/oJGukuH3D2+D+3H4JWLaAsJ/ji86dhRidzZ/Od7H/i8g+aCmvkeCc6Ni/f9uxGLSQVCRZkX2/lqEFG2BvWtlQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/better-sqlite3": { + "version": "7.6.13", + "resolved": "https://registry.npmjs.org/@types/better-sqlite3/-/better-sqlite3-7.6.13.tgz", + "integrity": "sha512-NMv9ASNARoKksWtsq/SHakpYAYnhBrQgGD8zkLYk/jaK8jUGn08CfEdTRgYhMypUQAfzSP8W6gNLe0q19/t4VA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/cookie": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.6.0.tgz", + "integrity": "sha512-4Kh9a6B2bQciAhf7FSuMRRkUWecJgJu9nPnx3yzpsfXX/c50REIqpHY4C82bXP90qrLtXtkDxTZosYO3UpOwlA==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/estree": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.9.tgz", + "integrity": "sha512-GhdPgy1el4/ImP05X05Uw4cw2/M93BCUmnEvWZNStlCzEKME4Fkk+YpoA5OiHNQmoS7Cafb8Xa3Pya8m1Qrzeg==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/node": { + "version": "24.12.4", + "resolved": "https://registry.npmjs.org/@types/node/-/node-24.12.4.tgz", + "integrity": "sha512-GUUEShf+PBCGW2KaXwcIt3Yk+e3pkKwWKb9GSyM9WQVE+ep2jzmHdGsHzu4wgcZy5fN9FBdVzjpBQsYlpfpgLA==", + "dev": true, + "license": "MIT", + "dependencies": { + "undici-types": "~7.16.0" + } + }, + "node_modules/@types/resolve": { + "version": "1.20.2", + "resolved": "https://registry.npmjs.org/@types/resolve/-/resolve-1.20.2.tgz", + "integrity": "sha512-60BCwRFOZCQhDncwQdxxeOEEkbc5dIMccYLwbxsS4TUNeVECQ/pBJ0j09mrHOl/JJvpRPGwO9SvE4nR2Nb/a4Q==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/trusted-types": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/@types/trusted-types/-/trusted-types-2.0.7.tgz", + "integrity": "sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==", + "dev": true, + "license": "MIT" + }, + "node_modules/acorn": { + "version": "8.16.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.16.0.tgz", + "integrity": "sha512-UVJyE9MttOsBQIDKw1skb9nAwQuR5wuGD3+82K6JgJlm/Y+KI92oNsMNGZCYdDsVtRHSak0pcV5Dno5+4jh9sw==", + "dev": true, + "license": "MIT", + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/aria-query": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.3.1.tgz", + "integrity": "sha512-Z/ZeOgVl7bcSYZ/u/rh0fOpvEpq//LZmdbkXyc7syVzjPAhfOa9ebsdTSjEBDU4vs5nC98Kfduj1uFo0qyET3g==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/axobject-query": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-4.1.0.tgz", + "integrity": "sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==", + "dev": true, + "license": "Apache-2.0", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/bcrypt": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/bcrypt/-/bcrypt-6.0.0.tgz", + "integrity": "sha512-cU8v/EGSrnH+HnxV2z0J7/blxH8gq7Xh2JFT6Aroax7UohdmiJJlxApMxtKfuI7z68NvvVcmR78k2LbT6efhRg==", + "hasInstallScript": true, + "license": "MIT", + "dependencies": { + "node-addon-api": "^8.3.0", + "node-gyp-build": "^4.8.4" + }, + "engines": { + "node": ">= 18" + } + }, + "node_modules/better-sqlite3": { + "version": "12.10.0", + "resolved": "https://registry.npmjs.org/better-sqlite3/-/better-sqlite3-12.10.0.tgz", + "integrity": "sha512-CyzaZRQKyHkB2ZInfTTl2nvT33EbDpjkLEbE8/Zck3Ll6O0qqvuGdrJ45HgtH+HykRg88ITY3AdreBGN70aBSQ==", + "hasInstallScript": true, + "license": "MIT", + "dependencies": { + "bindings": "^1.5.0", + "prebuild-install": "^7.1.1" + }, + "engines": { + "node": "20.x || 22.x || 23.x || 24.x || 25.x || 26.x" + } + }, + "node_modules/bindings": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.5.0.tgz", + "integrity": "sha512-p2q/t/mhvuOj/UeLlV6566GD/guowlr0hHxClI0W9m7MWYkL1F0hLo+0Aexs9HSPCtR1SXQ0TD3MMKrXZajbiQ==", + "license": "MIT", + "dependencies": { + "file-uri-to-path": "1.0.0" + } + }, + "node_modules/bl": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", + "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", + "license": "MIT", + "dependencies": { + "buffer": "^5.5.0", + "inherits": "^2.0.4", + "readable-stream": "^3.4.0" + } + }, + "node_modules/bootstrap": { + "version": "5.3.8", + "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.8.tgz", + "integrity": "sha512-HP1SZDqaLDPwsNiqRqi5NcP0SSXciX2s9E+RyqJIIqGo+vJeN5AJVM98CXmW/Wux0nQ5L7jeWUdplCEf0Ee+tg==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/twbs" + }, + { + "type": "opencollective", + "url": "https://opencollective.com/bootstrap" + } + ], + "license": "MIT", + "peerDependencies": { + "@popperjs/core": "^2.11.8" + } + }, + "node_modules/buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT", + "dependencies": { + "base64-js": "^1.3.1", + "ieee754": "^1.1.13" + } + }, + "node_modules/buffer-from": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/chokidar": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.3.tgz", + "integrity": "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==", + "dev": true, + "license": "MIT", + "dependencies": { + "readdirp": "^4.0.1" + }, + "engines": { + "node": ">= 14.16.0" + }, + "funding": { + "url": "https://paulmillr.com/funding/" + } + }, + "node_modules/chownr": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", + "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==", + "license": "ISC" + }, + "node_modules/clsx": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/clsx/-/clsx-2.1.1.tgz", + "integrity": "sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/commondir": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", + "integrity": "sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==", + "dev": true, + "license": "MIT" + }, + "node_modules/cookie": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.6.0.tgz", + "integrity": "sha512-U71cyTamuh1CRNCfpGY6to28lxvNwPG4Guz/EVjgf3Jmzv0vlDp1atT9eS5dDjMYHucpHbWns6Lwf3BKz6svdw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/decompress-response": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", + "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", + "license": "MIT", + "dependencies": { + "mimic-response": "^3.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "license": "MIT", + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/deepmerge": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.1.tgz", + "integrity": "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/detect-libc": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.1.2.tgz", + "integrity": "sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==", + "license": "Apache-2.0", + "engines": { + "node": ">=8" + } + }, + "node_modules/devalue": { + "version": "5.8.1", + "resolved": "https://registry.npmjs.org/devalue/-/devalue-5.8.1.tgz", + "integrity": "sha512-4CXDYRBGqN+57wVJkuXBYmpAVUSg3L6JAQa/DFqm238G73E1wuyc/JhGQJzN7vUf/CMphYau2zXbfWzDR5aTEw==", + "dev": true, + "license": "MIT" + }, + "node_modules/drizzle-kit": { + "version": "0.31.10", + "resolved": "https://registry.npmjs.org/drizzle-kit/-/drizzle-kit-0.31.10.tgz", + "integrity": "sha512-7OZcmQUrdGI+DUNNsKBn1aW8qSoKuTH7d0mYgSP8bAzdFzKoovxEFnoGQp2dVs82EOJeYycqRtciopszwUf8bw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@drizzle-team/brocli": "^0.10.2", + "@esbuild-kit/esm-loader": "^2.5.5", + "esbuild": "^0.25.4", + "tsx": "^4.21.0" + }, + "bin": { + "drizzle-kit": "bin.cjs" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/aix-ppc64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.25.12.tgz", + "integrity": "sha512-Hhmwd6CInZ3dwpuGTF8fJG6yoWmsToE+vYgD4nytZVxcu1ulHpUQRAB1UJ8+N1Am3Mz4+xOByoQoSZf4D+CpkA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "aix" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/android-arm": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.25.12.tgz", + "integrity": "sha512-VJ+sKvNA/GE7Ccacc9Cha7bpS8nyzVv0jdVgwNDaR4gDMC/2TTRc33Ip8qrNYUcpkOHUT5OZ0bUcNNVZQ9RLlg==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/android-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.25.12.tgz", + "integrity": "sha512-6AAmLG7zwD1Z159jCKPvAxZd4y/VTO0VkprYy+3N2FtJ8+BQWFXU+OxARIwA46c5tdD9SsKGZ/1ocqBS/gAKHg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/android-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.25.12.tgz", + "integrity": "sha512-5jbb+2hhDHx5phYR2By8GTWEzn6I9UqR11Kwf22iKbNpYrsmRB18aX/9ivc5cabcUiAT/wM+YIZ6SG9QO6a8kg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/darwin-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.25.12.tgz", + "integrity": "sha512-N3zl+lxHCifgIlcMUP5016ESkeQjLj/959RxxNYIthIg+CQHInujFuXeWbWMgnTo4cp5XVHqFPmpyu9J65C1Yg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/darwin-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.25.12.tgz", + "integrity": "sha512-HQ9ka4Kx21qHXwtlTUVbKJOAnmG1ipXhdWTmNXiPzPfWKpXqASVcWdnf2bnL73wgjNrFXAa3yYvBSd9pzfEIpA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/freebsd-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.25.12.tgz", + "integrity": "sha512-gA0Bx759+7Jve03K1S0vkOu5Lg/85dou3EseOGUes8flVOGxbhDDh/iZaoek11Y8mtyKPGF3vP8XhnkDEAmzeg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/freebsd-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.25.12.tgz", + "integrity": "sha512-TGbO26Yw2xsHzxtbVFGEXBFH0FRAP7gtcPE7P5yP7wGy7cXK2oO7RyOhL5NLiqTlBh47XhmIUXuGciXEqYFfBQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-arm": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.25.12.tgz", + "integrity": "sha512-lPDGyC1JPDou8kGcywY0YILzWlhhnRjdof3UlcoqYmS9El818LLfJJc3PXXgZHrHCAKs/Z2SeZtDJr5MrkxtOw==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.25.12.tgz", + "integrity": "sha512-8bwX7a8FghIgrupcxb4aUmYDLp8pX06rGh5HqDT7bB+8Rdells6mHvrFHHW2JAOPZUbnjUpKTLg6ECyzvas2AQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-ia32": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.25.12.tgz", + "integrity": "sha512-0y9KrdVnbMM2/vG8KfU0byhUN+EFCny9+8g202gYqSSVMonbsCfLjUO+rCci7pM0WBEtz+oK/PIwHkzxkyharA==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-loong64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.25.12.tgz", + "integrity": "sha512-h///Lr5a9rib/v1GGqXVGzjL4TMvVTv+s1DPoxQdz7l/AYv6LDSxdIwzxkrPW438oUXiDtwM10o9PmwS/6Z0Ng==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-mips64el": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.25.12.tgz", + "integrity": "sha512-iyRrM1Pzy9GFMDLsXn1iHUm18nhKnNMWscjmp4+hpafcZjrr2WbT//d20xaGljXDBYHqRcl8HnxbX6uaA/eGVw==", + "cpu": [ + "mips64el" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-ppc64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.25.12.tgz", + "integrity": "sha512-9meM/lRXxMi5PSUqEXRCtVjEZBGwB7P/D4yT8UG/mwIdze2aV4Vo6U5gD3+RsoHXKkHCfSxZKzmDssVlRj1QQA==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-riscv64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.25.12.tgz", + "integrity": "sha512-Zr7KR4hgKUpWAwb1f3o5ygT04MzqVrGEGXGLnj15YQDJErYu/BGg+wmFlIDOdJp0PmB0lLvxFIOXZgFRrdjR0w==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-s390x": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.25.12.tgz", + "integrity": "sha512-MsKncOcgTNvdtiISc/jZs/Zf8d0cl/t3gYWX8J9ubBnVOwlk65UIEEvgBORTiljloIWnBzLs4qhzPkJcitIzIg==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/linux-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.25.12.tgz", + "integrity": "sha512-uqZMTLr/zR/ed4jIGnwSLkaHmPjOjJvnm6TVVitAa08SLS9Z0VM8wIRx7gWbJB5/J54YuIMInDquWyYvQLZkgw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/netbsd-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.25.12.tgz", + "integrity": "sha512-xXwcTq4GhRM7J9A8Gv5boanHhRa/Q9KLVmcyXHCTaM4wKfIpWkdXiMog/KsnxzJ0A1+nD+zoecuzqPmCRyBGjg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/netbsd-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.25.12.tgz", + "integrity": "sha512-Ld5pTlzPy3YwGec4OuHh1aCVCRvOXdH8DgRjfDy/oumVovmuSzWfnSJg+VtakB9Cm0gxNO9BzWkj6mtO1FMXkQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/openbsd-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.25.12.tgz", + "integrity": "sha512-fF96T6KsBo/pkQI950FARU9apGNTSlZGsv1jZBAlcLL1MLjLNIWPBkj5NlSz8aAzYKg+eNqknrUJ24QBybeR5A==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/openbsd-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.25.12.tgz", + "integrity": "sha512-MZyXUkZHjQxUvzK7rN8DJ3SRmrVrke8ZyRusHlP+kuwqTcfWLyqMOE3sScPPyeIXN/mDJIfGXvcMqCgYKekoQw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/openharmony-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/openharmony-arm64/-/openharmony-arm64-0.25.12.tgz", + "integrity": "sha512-rm0YWsqUSRrjncSXGA7Zv78Nbnw4XL6/dzr20cyrQf7ZmRcsovpcRBdhD43Nuk3y7XIoW2OxMVvwuRvk9XdASg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openharmony" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/sunos-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.25.12.tgz", + "integrity": "sha512-3wGSCDyuTHQUzt0nV7bocDy72r2lI33QL3gkDNGkod22EsYl04sMf0qLb8luNKTOmgF/eDEDP5BFNwoBKH441w==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/win32-arm64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.25.12.tgz", + "integrity": "sha512-rMmLrur64A7+DKlnSuwqUdRKyd3UE7oPJZmnljqEptesKM8wx9J8gx5u0+9Pq0fQQW8vqeKebwNXdfOyP+8Bsg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/win32-ia32": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.25.12.tgz", + "integrity": "sha512-HkqnmmBoCbCwxUKKNPBixiWDGCpQGVsrQfJoVGYLPT41XWF8lHuE5N6WhVia2n4o5QK5M4tYr21827fNhi4byQ==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/@esbuild/win32-x64": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.25.12.tgz", + "integrity": "sha512-alJC0uCZpTFrSL0CCDjcgleBXPnCrEAhTBILpeAp7M/OFgoqtAetfBzX0xM00MUsVVPpVjlPuMbREqnZCXaTnA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=18" + } + }, + "node_modules/drizzle-kit/node_modules/esbuild": { + "version": "0.25.12", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.25.12.tgz", + "integrity": "sha512-bbPBYYrtZbkt6Os6FiTLCTFxvq4tt3JKall1vRwshA3fdVztsLAatFaZobhkBC8/BrPetoa0oksYoKXoG4ryJg==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "@esbuild/aix-ppc64": "0.25.12", + "@esbuild/android-arm": "0.25.12", + "@esbuild/android-arm64": "0.25.12", + "@esbuild/android-x64": "0.25.12", + "@esbuild/darwin-arm64": "0.25.12", + "@esbuild/darwin-x64": "0.25.12", + "@esbuild/freebsd-arm64": "0.25.12", + "@esbuild/freebsd-x64": "0.25.12", + "@esbuild/linux-arm": "0.25.12", + "@esbuild/linux-arm64": "0.25.12", + "@esbuild/linux-ia32": "0.25.12", + "@esbuild/linux-loong64": "0.25.12", + "@esbuild/linux-mips64el": "0.25.12", + "@esbuild/linux-ppc64": "0.25.12", + "@esbuild/linux-riscv64": "0.25.12", + "@esbuild/linux-s390x": "0.25.12", + "@esbuild/linux-x64": "0.25.12", + "@esbuild/netbsd-arm64": "0.25.12", + "@esbuild/netbsd-x64": "0.25.12", + "@esbuild/openbsd-arm64": "0.25.12", + "@esbuild/openbsd-x64": "0.25.12", + "@esbuild/openharmony-arm64": "0.25.12", + "@esbuild/sunos-x64": "0.25.12", + "@esbuild/win32-arm64": "0.25.12", + "@esbuild/win32-ia32": "0.25.12", + "@esbuild/win32-x64": "0.25.12" + } + }, + "node_modules/drizzle-orm": { + "version": "0.45.2", + "resolved": "https://registry.npmjs.org/drizzle-orm/-/drizzle-orm-0.45.2.tgz", + "integrity": "sha512-kY0BSaTNYWnoDMVoyY8uxmyHjpJW1geOmBMdSSicKo9CIIWkSxMIj2rkeSR51b8KAPB7m+qysjuHme5nKP+E5Q==", + "dev": true, + "license": "Apache-2.0", + "peerDependencies": { + "@aws-sdk/client-rds-data": ">=3", + "@cloudflare/workers-types": ">=4", + "@electric-sql/pglite": ">=0.2.0", + "@libsql/client": ">=0.10.0", + "@libsql/client-wasm": ">=0.10.0", + "@neondatabase/serverless": ">=0.10.0", + "@op-engineering/op-sqlite": ">=2", + "@opentelemetry/api": "^1.4.1", + "@planetscale/database": ">=1.13", + "@prisma/client": "*", + "@tidbcloud/serverless": "*", + "@types/better-sqlite3": "*", + "@types/pg": "*", + "@types/sql.js": "*", + "@upstash/redis": ">=1.34.7", + "@vercel/postgres": ">=0.8.0", + "@xata.io/client": "*", + "better-sqlite3": ">=7", + "bun-types": "*", + "expo-sqlite": ">=14.0.0", + "gel": ">=2", + "knex": "*", + "kysely": "*", + "mysql2": ">=2", + "pg": ">=8", + "postgres": ">=3", + "sql.js": ">=1", + "sqlite3": ">=5" + }, + "peerDependenciesMeta": { + "@aws-sdk/client-rds-data": { + "optional": true + }, + "@cloudflare/workers-types": { + "optional": true + }, + "@electric-sql/pglite": { + "optional": true + }, + "@libsql/client": { + "optional": true + }, + "@libsql/client-wasm": { + "optional": true + }, + "@neondatabase/serverless": { + "optional": true + }, + "@op-engineering/op-sqlite": { + "optional": true + }, + "@opentelemetry/api": { + "optional": true + }, + "@planetscale/database": { + "optional": true + }, + "@prisma/client": { + "optional": true + }, + "@tidbcloud/serverless": { + "optional": true + }, + "@types/better-sqlite3": { + "optional": true + }, + "@types/pg": { + "optional": true + }, + "@types/sql.js": { + "optional": true + }, + "@upstash/redis": { + "optional": true + }, + "@vercel/postgres": { + "optional": true + }, + "@xata.io/client": { + "optional": true + }, + "better-sqlite3": { + "optional": true + }, + "bun-types": { + "optional": true + }, + "expo-sqlite": { + "optional": true + }, + "gel": { + "optional": true + }, + "knex": { + "optional": true + }, + "kysely": { + "optional": true + }, + "mysql2": { + "optional": true + }, + "pg": { + "optional": true + }, + "postgres": { + "optional": true + }, + "prisma": { + "optional": true + }, + "sql.js": { + "optional": true + }, + "sqlite3": { + "optional": true + } + } + }, + "node_modules/end-of-stream": { + "version": "1.4.5", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.5.tgz", + "integrity": "sha512-ooEGc6HP26xXq/N+GCGOT0JKCLDGrq2bQUZrQ7gyrJiZANJ/8YDTxTpQBXGMn+WbIQXNVpyWymm7KYVICQnyOg==", + "license": "MIT", + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/es-errors": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", + "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/esbuild": { + "version": "0.28.0", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.28.0.tgz", + "integrity": "sha512-sNR9MHpXSUV/XB4zmsFKN+QgVG82Cc7+/aaxJ8Adi8hyOac+EXptIp45QBPaVyX3N70664wRbTcLTOemCAnyqw==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=18" + }, + "optionalDependencies": { + "@esbuild/aix-ppc64": "0.28.0", + "@esbuild/android-arm": "0.28.0", + "@esbuild/android-arm64": "0.28.0", + "@esbuild/android-x64": "0.28.0", + "@esbuild/darwin-arm64": "0.28.0", + "@esbuild/darwin-x64": "0.28.0", + "@esbuild/freebsd-arm64": "0.28.0", + "@esbuild/freebsd-x64": "0.28.0", + "@esbuild/linux-arm": "0.28.0", + "@esbuild/linux-arm64": "0.28.0", + "@esbuild/linux-ia32": "0.28.0", + "@esbuild/linux-loong64": "0.28.0", + "@esbuild/linux-mips64el": "0.28.0", + "@esbuild/linux-ppc64": "0.28.0", + "@esbuild/linux-riscv64": "0.28.0", + "@esbuild/linux-s390x": "0.28.0", + "@esbuild/linux-x64": "0.28.0", + "@esbuild/netbsd-arm64": "0.28.0", + "@esbuild/netbsd-x64": "0.28.0", + "@esbuild/openbsd-arm64": "0.28.0", + "@esbuild/openbsd-x64": "0.28.0", + "@esbuild/openharmony-arm64": "0.28.0", + "@esbuild/sunos-x64": "0.28.0", + "@esbuild/win32-arm64": "0.28.0", + "@esbuild/win32-ia32": "0.28.0", + "@esbuild/win32-x64": "0.28.0" + } + }, + "node_modules/esm-env": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/esm-env/-/esm-env-1.2.2.tgz", + "integrity": "sha512-Epxrv+Nr/CaL4ZcFGPJIYLWFom+YeV1DqMLHJoEd9SYRxNbaFruBwfEX/kkHUJf55j2+TUbmDcmuilbP1TmXHA==", + "dev": true, + "license": "MIT" + }, + "node_modules/esrap": { + "version": "2.2.9", + "resolved": "https://registry.npmjs.org/esrap/-/esrap-2.2.9.tgz", + "integrity": "sha512-4KijP+NxCWthMCUC3qHbE6n4vCjqgJS1uAYKhuT/GWfFTf1Qyive2TgOjep+gzbSzRfnNyaN/UU9YmdOt8Eg0A==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/sourcemap-codec": "^1.4.15" + }, + "peerDependencies": { + "@typescript-eslint/types": "^8.2.0" + }, + "peerDependenciesMeta": { + "@typescript-eslint/types": { + "optional": true + } + } + }, + "node_modules/estree-walker": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/estree-walker/-/estree-walker-2.0.2.tgz", + "integrity": "sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==", + "dev": true, + "license": "MIT" + }, + "node_modules/expand-template": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-2.0.3.tgz", + "integrity": "sha512-XYfuKMvj4O35f/pOXLObndIRvyQ+/+6AhODh+OKWj9S9498pHHn/IMszH+gt0fBCRWMNfk1ZSp5x3AifmnI2vg==", + "license": "(MIT OR WTFPL)", + "engines": { + "node": ">=6" + } + }, + "node_modules/fdir": { + "version": "6.5.0", + "resolved": "https://registry.npmjs.org/fdir/-/fdir-6.5.0.tgz", + "integrity": "sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12.0.0" + }, + "peerDependencies": { + "picomatch": "^3 || ^4" + }, + "peerDependenciesMeta": { + "picomatch": { + "optional": true + } + } + }, + "node_modules/file-uri-to-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", + "integrity": "sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==", + "license": "MIT" + }, + "node_modules/fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "license": "MIT" + }, + "node_modules/fsevents": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/function-bind": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", + "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-tsconfig": { + "version": "4.14.0", + "resolved": "https://registry.npmjs.org/get-tsconfig/-/get-tsconfig-4.14.0.tgz", + "integrity": "sha512-yTb+8DXzDREzgvYmh6s9vHsSVCHeC0G3PI5bEXNBHtmshPnO+S5O7qgLEOn0I5QvMy6kpZN8K1NKGyilLb93wA==", + "dev": true, + "license": "MIT", + "dependencies": { + "resolve-pkg-maps": "^1.0.0" + }, + "funding": { + "url": "https://github.com/privatenumber/get-tsconfig?sponsor=1" + } + }, + "node_modules/github-from-package": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/github-from-package/-/github-from-package-0.0.0.tgz", + "integrity": "sha512-SyHy3T1v2NUXn29OsWdxmK6RwHD+vkj3v8en8AOBZ1wBQ/hCAQ5bAQTD02kW4W9tUp/3Qh6J8r9EvntiyCmOOw==", + "license": "MIT" + }, + "node_modules/hasown": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.4.tgz", + "integrity": "sha512-T2UbfbBEF32wiepXIsMlTW9+dDYC6wMh/t/vYA4tuOMKqWz/n3vr1NFSxQiyP+zk2mXsoMA/i/7qV6LKut1t1A==", + "dev": true, + "license": "MIT", + "dependencies": { + "function-bind": "^1.1.2" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "BSD-3-Clause" + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "license": "ISC" + }, + "node_modules/ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "license": "ISC" + }, + "node_modules/is-core-module": { + "version": "2.16.2", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.2.tgz", + "integrity": "sha512-evOr8xfXKxE6qSR0hSXL2r3sd7ALj8+7jQEUvPYcm5sgZFdJ+AYzT6yNmJenvIYQBgIGwfwz08sL8zoL7yq2BA==", + "dev": true, + "license": "MIT", + "dependencies": { + "hasown": "^2.0.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-module": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-module/-/is-module-1.0.0.tgz", + "integrity": "sha512-51ypPSPCoTEIN9dy5Oy+h4pShgJmPCygKfyRCISBI+JoWT/2oJvK8QPxmwv7b/p239jXrm9M1mlQbyKJ5A152g==", + "dev": true, + "license": "MIT" + }, + "node_modules/is-reference": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-reference/-/is-reference-1.2.1.tgz", + "integrity": "sha512-U82MsXXiFIrjCK4otLT+o2NA2Cd2g5MLoOVXUZjIOhLurrRxpEXzI8O0KZHr3IjLvlAH1kTPYSuqer5T9ZVBKQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "*" + } + }, + "node_modules/kleur": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", + "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/lightningcss": { + "version": "1.32.0", + "resolved": "https://registry.npmjs.org/lightningcss/-/lightningcss-1.32.0.tgz", + "integrity": "sha512-NXYBzinNrblfraPGyrbPoD19C1h9lfI/1mzgWYvXUTe414Gz/X1FD2XBZSZM7rRTrMA8JL3OtAaGifrIKhQ5yQ==", + "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.32.0", + "lightningcss-darwin-arm64": "1.32.0", + "lightningcss-darwin-x64": "1.32.0", + "lightningcss-freebsd-x64": "1.32.0", + "lightningcss-linux-arm-gnueabihf": "1.32.0", + "lightningcss-linux-arm64-gnu": "1.32.0", + "lightningcss-linux-arm64-musl": "1.32.0", + "lightningcss-linux-x64-gnu": "1.32.0", + "lightningcss-linux-x64-musl": "1.32.0", + "lightningcss-win32-arm64-msvc": "1.32.0", + "lightningcss-win32-x64-msvc": "1.32.0" + } + }, + "node_modules/lightningcss-android-arm64": { + "version": "1.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-android-arm64/-/lightningcss-android-arm64-1.32.0.tgz", + "integrity": "sha512-YK7/ClTt4kAK0vo6w3X+Pnm0D2cf2vPHbhOXdoNti1Ga0al1P4TBZhwjATvjNwLEBCnKvjJc2jQgHXH0NEwlAg==", + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-darwin-arm64/-/lightningcss-darwin-arm64-1.32.0.tgz", + "integrity": "sha512-RzeG9Ju5bag2Bv1/lwlVJvBE3q6TtXskdZLLCyfg5pt+HLz9BqlICO7LZM7VHNTTn/5PRhHFBSjk5lc4cmscPQ==", + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-darwin-x64/-/lightningcss-darwin-x64-1.32.0.tgz", + "integrity": "sha512-U+QsBp2m/s2wqpUYT/6wnlagdZbtZdndSmut/NJqlCcMLTWp5muCrID+K5UJ6jqD2BFshejCYXniPDbNh73V8w==", + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-freebsd-x64/-/lightningcss-freebsd-x64-1.32.0.tgz", + "integrity": "sha512-JCTigedEksZk3tHTTthnMdVfGf61Fky8Ji2E4YjUTEQX14xiy/lTzXnu1vwiZe3bYe0q+SpsSH/CTeDXK6WHig==", + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-linux-arm-gnueabihf/-/lightningcss-linux-arm-gnueabihf-1.32.0.tgz", + "integrity": "sha512-x6rnnpRa2GL0zQOkt6rts3YDPzduLpWvwAF6EMhXFVZXD4tPrBkEFqzGowzCsIWsPjqSK+tyNEODUBXeeVHSkw==", + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-linux-arm64-gnu/-/lightningcss-linux-arm64-gnu-1.32.0.tgz", + "integrity": "sha512-0nnMyoyOLRJXfbMOilaSRcLH3Jw5z9HDNGfT/gwCPgaDjnx0i8w7vBzFLFR1f6CMLKF8gVbebmkUN3fa/kQJpQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-linux-arm64-musl/-/lightningcss-linux-arm64-musl-1.32.0.tgz", + "integrity": "sha512-UpQkoenr4UJEzgVIYpI80lDFvRmPVg6oqboNHfoH4CQIfNA+HOrZ7Mo7KZP02dC6LjghPQJeBsvXhJod/wnIBg==", + "cpu": [ + "arm64" + ], + "dev": true, + "libc": [ + "musl" + ], + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-linux-x64-gnu/-/lightningcss-linux-x64-gnu-1.32.0.tgz", + "integrity": "sha512-V7Qr52IhZmdKPVr+Vtw8o+WLsQJYCTd8loIfpDaMRWGUZfBOYEJeyJIkqGIDMZPwPx24pUMfwSxxI8phr/MbOA==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "glibc" + ], + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-linux-x64-musl/-/lightningcss-linux-x64-musl-1.32.0.tgz", + "integrity": "sha512-bYcLp+Vb0awsiXg/80uCRezCYHNg1/l3mt0gzHnWV9XP1W5sKa5/TCdGWaR/zBM2PeF/HbsQv/j2URNOiVuxWg==", + "cpu": [ + "x64" + ], + "dev": true, + "libc": [ + "musl" + ], + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-win32-arm64-msvc/-/lightningcss-win32-arm64-msvc-1.32.0.tgz", + "integrity": "sha512-8SbC8BR40pS6baCM8sbtYDSwEVQd4JlFTOlaD3gWGHfThTcABnNDBda6eTZeqbofalIJhFx0qKzgHJmcPTnGdw==", + "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.32.0", + "resolved": "https://registry.npmjs.org/lightningcss-win32-x64-msvc/-/lightningcss-win32-x64-msvc-1.32.0.tgz", + "integrity": "sha512-Amq9B/SoZYdDi1kFrojnoqPLxYhQ4Wo5XiL8EVJrVsB8ARoC1PWW6VGtT0WKCemjy8aC+louJnjS7U18x3b06Q==", + "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-character": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/locate-character/-/locate-character-3.0.0.tgz", + "integrity": "sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA==", + "dev": true, + "license": "MIT" + }, + "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/mimic-response": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", + "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", + "license": "MIT", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/minimist": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz", + "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==", + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/mkdirp-classic": { + "version": "0.5.3", + "resolved": "https://registry.npmjs.org/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz", + "integrity": "sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==", + "license": "MIT" + }, + "node_modules/mri": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mri/-/mri-1.2.0.tgz", + "integrity": "sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=4" + } + }, + "node_modules/mrmime": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/mrmime/-/mrmime-2.0.1.tgz", + "integrity": "sha512-Y3wQdFg2Va6etvQ5I82yUhGdsKrcYox6p7FfL1LbK2J4V01F9TGlepTIhnK24t7koZibmg82KGglhA1XK5IsLQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=10" + } + }, + "node_modules/nanoid": { + "version": "3.3.12", + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.12.tgz", + "integrity": "sha512-ZB9RH/39qpq5Vu6Y+NmUaFhQR6pp+M2Xt76XBnEwDaGcVAqhlvxrl3B2bKS5D3NH3QR76v3aSrKaF/Kiy7lEtQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/ai" + } + ], + "license": "MIT", + "bin": { + "nanoid": "bin/nanoid.cjs" + }, + "engines": { + "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" + } + }, + "node_modules/napi-build-utils": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/napi-build-utils/-/napi-build-utils-2.0.0.tgz", + "integrity": "sha512-GEbrYkbfF7MoNaoh2iGG84Mnf/WZfB0GdGEsM8wz7Expx/LlWf5U8t9nvJKXSp3qr5IsEbK04cBGhol/KwOsWA==", + "license": "MIT" + }, + "node_modules/node-abi": { + "version": "3.92.0", + "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-3.92.0.tgz", + "integrity": "sha512-KdHvFWZjEKDf0cakgFjebl371GPsISX2oZHcuyKqM7DtogIsHrqKeLTo8wBHxaXRAQlY2PsPlZmfo+9ZCxEREQ==", + "license": "MIT", + "dependencies": { + "semver": "^7.3.5" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/node-addon-api": { + "version": "8.8.0", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-8.8.0.tgz", + "integrity": "sha512-c5Ko1fZJIJmzhFIkhRN76WTq+fC6tWnGy9CXA0fA+XygsWZmEwG8vmbkNqxMyoaa0Tin4djul49NzdVcJJcjeA==", + "license": "MIT", + "engines": { + "node": "^18 || ^20 || >= 21" + } + }, + "node_modules/node-gyp-build": { + "version": "4.8.4", + "resolved": "https://registry.npmjs.org/node-gyp-build/-/node-gyp-build-4.8.4.tgz", + "integrity": "sha512-LA4ZjwlnUblHVgq0oBF3Jl/6h/Nvs5fzBLwdEF4nuxnFdsfajde4WfxtJr3CaiH+F6ewcIB/q4jQ4UzPyid+CQ==", + "license": "MIT", + "bin": { + "node-gyp-build": "bin.js", + "node-gyp-build-optional": "optional.js", + "node-gyp-build-test": "build-test.js" + } + }, + "node_modules/obug": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/obug/-/obug-2.1.1.tgz", + "integrity": "sha512-uTqF9MuPraAQ+IsnPf366RG4cP9RtUi7MLO1N3KEc+wb0a6yKpeL0lmk2IB1jY5KHPAlTc6T/JRdC/YqxHNwkQ==", + "dev": true, + "funding": [ + "https://github.com/sponsors/sxzz", + "https://opencollective.com/debug" + ], + "license": "MIT" + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", + "license": "ISC", + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/path-parse": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", + "dev": true, + "license": "MIT" + }, + "node_modules/picocolors": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz", + "integrity": "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==", + "dev": true, + "license": "ISC" + }, + "node_modules/picomatch": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.4.tgz", + "integrity": "sha512-QP88BAKvMam/3NxH6vj2o21R6MjxZUAd6nlwAS/pnGvN9IVLocLHxGYIzFhg6fUQ+5th6P4dv4eW9jX3DSIj7A==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/postcss": { + "version": "8.5.15", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.15.tgz", + "integrity": "sha512-FfR8sjd4em2T6fb3I2MwAJU7HWVMr9zba+enmQeeWFfCbm+UOC/0X4DS8XtpUTMwWMGbjKYP7xjfNekzyGmB3A==", + "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.12", + "picocolors": "^1.1.1", + "source-map-js": "^1.2.1" + }, + "engines": { + "node": "^10 || ^12 || >=14" + } + }, + "node_modules/prebuild-install": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/prebuild-install/-/prebuild-install-7.1.3.tgz", + "integrity": "sha512-8Mf2cbV7x1cXPUILADGI3wuhfqWvtiLA1iclTDbFRZkgRQS0NqsPZphna9V+HyTEadheuPmjaJMsbzKQFOzLug==", + "deprecated": "No longer maintained. Please contact the author of the relevant native addon; alternatives are available.", + "license": "MIT", + "dependencies": { + "detect-libc": "^2.0.0", + "expand-template": "^2.0.3", + "github-from-package": "0.0.0", + "minimist": "^1.2.3", + "mkdirp-classic": "^0.5.3", + "napi-build-utils": "^2.0.0", + "node-abi": "^3.3.0", + "pump": "^3.0.0", + "rc": "^1.2.7", + "simple-get": "^4.0.0", + "tar-fs": "^2.0.0", + "tunnel-agent": "^0.6.0" + }, + "bin": { + "prebuild-install": "bin.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/pump": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.4.tgz", + "integrity": "sha512-VS7sjc6KR7e1ukRFhQSY5LM2uBWAUPiOPa/A3mkKmiMwSmRFUITt0xuj+/lesgnCv+dPIEYlkzrcyXgquIHMcA==", + "license": "MIT", + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "node_modules/rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "license": "(BSD-2-Clause OR MIT OR Apache-2.0)", + "dependencies": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "bin": { + "rc": "cli.js" + } + }, + "node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/readdirp": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.1.2.tgz", + "integrity": "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 14.18.0" + }, + "funding": { + "type": "individual", + "url": "https://paulmillr.com/funding/" + } + }, + "node_modules/resolve": { + "version": "1.22.12", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.12.tgz", + "integrity": "sha512-TyeJ1zif53BPfHootBGwPRYT1RUt6oGWsaQr8UyZW/eAm9bKoijtvruSDEmZHm92CwS9nj7/fWttqPCgzep8CA==", + "dev": true, + "license": "MIT", + "dependencies": { + "es-errors": "^1.3.0", + "is-core-module": "^2.16.1", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/resolve-pkg-maps": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/resolve-pkg-maps/-/resolve-pkg-maps-1.0.0.tgz", + "integrity": "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==", + "dev": true, + "license": "MIT", + "funding": { + "url": "https://github.com/privatenumber/resolve-pkg-maps?sponsor=1" + } + }, + "node_modules/rolldown": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/rolldown/-/rolldown-1.0.2.tgz", + "integrity": "sha512-oZx5zVDtVB44AW3eaifgDml1gWRDZGvjcfdxonE4swNPG98PrrXjaO/KrnUjzlMnztCCRVlUueA1kCXhARGk6g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@oxc-project/types": "=0.132.0", + "@rolldown/pluginutils": "^1.0.0" + }, + "bin": { + "rolldown": "bin/cli.mjs" + }, + "engines": { + "node": "^20.19.0 || >=22.12.0" + }, + "optionalDependencies": { + "@rolldown/binding-android-arm64": "1.0.2", + "@rolldown/binding-darwin-arm64": "1.0.2", + "@rolldown/binding-darwin-x64": "1.0.2", + "@rolldown/binding-freebsd-x64": "1.0.2", + "@rolldown/binding-linux-arm-gnueabihf": "1.0.2", + "@rolldown/binding-linux-arm64-gnu": "1.0.2", + "@rolldown/binding-linux-arm64-musl": "1.0.2", + "@rolldown/binding-linux-ppc64-gnu": "1.0.2", + "@rolldown/binding-linux-s390x-gnu": "1.0.2", + "@rolldown/binding-linux-x64-gnu": "1.0.2", + "@rolldown/binding-linux-x64-musl": "1.0.2", + "@rolldown/binding-openharmony-arm64": "1.0.2", + "@rolldown/binding-wasm32-wasi": "1.0.2", + "@rolldown/binding-win32-arm64-msvc": "1.0.2", + "@rolldown/binding-win32-x64-msvc": "1.0.2" + } + }, + "node_modules/rollup": { + "version": "4.60.4", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.60.4.tgz", + "integrity": "sha512-WHeFSbZYsPu3+bLoNRUuAO+wavNlocOPf3wSHTP7hcFKVnJeWsYlCDbr3mTS14FCizf9ccIxXA8sGL8zKeQN3g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "1.0.8" + }, + "bin": { + "rollup": "dist/bin/rollup" + }, + "engines": { + "node": ">=18.0.0", + "npm": ">=8.0.0" + }, + "optionalDependencies": { + "@rollup/rollup-android-arm-eabi": "4.60.4", + "@rollup/rollup-android-arm64": "4.60.4", + "@rollup/rollup-darwin-arm64": "4.60.4", + "@rollup/rollup-darwin-x64": "4.60.4", + "@rollup/rollup-freebsd-arm64": "4.60.4", + "@rollup/rollup-freebsd-x64": "4.60.4", + "@rollup/rollup-linux-arm-gnueabihf": "4.60.4", + "@rollup/rollup-linux-arm-musleabihf": "4.60.4", + "@rollup/rollup-linux-arm64-gnu": "4.60.4", + "@rollup/rollup-linux-arm64-musl": "4.60.4", + "@rollup/rollup-linux-loong64-gnu": "4.60.4", + "@rollup/rollup-linux-loong64-musl": "4.60.4", + "@rollup/rollup-linux-ppc64-gnu": "4.60.4", + "@rollup/rollup-linux-ppc64-musl": "4.60.4", + "@rollup/rollup-linux-riscv64-gnu": "4.60.4", + "@rollup/rollup-linux-riscv64-musl": "4.60.4", + "@rollup/rollup-linux-s390x-gnu": "4.60.4", + "@rollup/rollup-linux-x64-gnu": "4.60.4", + "@rollup/rollup-linux-x64-musl": "4.60.4", + "@rollup/rollup-openbsd-x64": "4.60.4", + "@rollup/rollup-openharmony-arm64": "4.60.4", + "@rollup/rollup-win32-arm64-msvc": "4.60.4", + "@rollup/rollup-win32-ia32-msvc": "4.60.4", + "@rollup/rollup-win32-x64-gnu": "4.60.4", + "@rollup/rollup-win32-x64-msvc": "4.60.4", + "fsevents": "~2.3.2" + } + }, + "node_modules/rollup/node_modules/@types/estree": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", + "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", + "dev": true, + "license": "MIT" + }, + "node_modules/sade": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/sade/-/sade-1.8.1.tgz", + "integrity": "sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A==", + "dev": true, + "license": "MIT", + "dependencies": { + "mri": "^1.1.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/semver": { + "version": "7.8.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.8.1.tgz", + "integrity": "sha512-rkVq3IXh+4FDGch+KwzX3aV9W3kO54GyEgpvBzSyctDA6Xtd7RJQV1xmXbeQp5v7+VzLOfVqiutSE6GICgPFvg==", + "license": "ISC", + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/set-cookie-parser": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/set-cookie-parser/-/set-cookie-parser-3.1.0.tgz", + "integrity": "sha512-kjnC1DXBHcxaOaOXBHBeRtltsDG2nUiUni+jP92M9gYdW12rsmx92UsfpH7o5tDRs7I1ZZPSQJQGv3UaRfCiuw==", + "dev": true, + "license": "MIT" + }, + "node_modules/simple-concat": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.1.tgz", + "integrity": "sha512-cSFtAPtRhljv69IK0hTVZQ+OfE9nePi/rtJmw5UjHeVyVroEqJXP1sFztKUy1qU+xvz3u/sfYJLa947b7nAN2Q==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/simple-get": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-4.0.1.tgz", + "integrity": "sha512-brv7p5WgH0jmQJr1ZDDfKDOSeWWg+OVypG99A/5vYGPqJ6pxiaHLy8nxtFjBA7oMa01ebA9gfh1uMCFqOuXxvA==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT", + "dependencies": { + "decompress-response": "^6.0.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" + } + }, + "node_modules/sirv": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/sirv/-/sirv-3.0.2.tgz", + "integrity": "sha512-2wcC/oGxHis/BoHkkPwldgiPSYcpZK3JU28WoMVv55yHJgcZ8rlXvuG9iZggz+sU1d4bRgIGASwyWqjxu3FM0g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@polka/url": "^1.0.0-next.24", + "mrmime": "^2.0.0", + "totalist": "^3.0.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "license": "BSD-3-Clause", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/source-map-js": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", + "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", + "dev": true, + "license": "BSD-3-Clause", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/source-map-support": { + "version": "0.5.21", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", + "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", + "dev": true, + "license": "MIT", + "dependencies": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, + "node_modules/string_decoder": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", + "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==", + "license": "MIT", + "dependencies": { + "safe-buffer": "~5.2.0" + } + }, + "node_modules/strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/supports-preserve-symlinks-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", + "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/svelte": { + "version": "5.56.0", + "resolved": "https://registry.npmjs.org/svelte/-/svelte-5.56.0.tgz", + "integrity": "sha512-kTXr26t1bchFp28ROrb957LtbujpBmBDibmqMGziVpUs7awBi96TGgX6SovrA8BNoEUDVRK2Fb9FkeYlGspoVg==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/remapping": "^2.3.4", + "@jridgewell/sourcemap-codec": "^1.5.0", + "@sveltejs/acorn-typescript": "^1.0.10", + "@types/estree": "^1.0.5", + "@types/trusted-types": "^2.0.7", + "acorn": "^8.12.1", + "aria-query": "5.3.1", + "axobject-query": "^4.1.0", + "clsx": "^2.1.1", + "devalue": "^5.8.1", + "esm-env": "^1.2.1", + "esrap": "^2.2.9", + "is-reference": "^3.0.3", + "locate-character": "^3.0.0", + "magic-string": "^0.30.11", + "zimmerframe": "^1.1.2" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/svelte-check": { + "version": "4.4.8", + "resolved": "https://registry.npmjs.org/svelte-check/-/svelte-check-4.4.8.tgz", + "integrity": "sha512-67adfgBox5eNSNIvIIwgFizKGdcRrGpiMoNO2obHcYuLz7iTa8Xgm/NGU3ntMFnNm8K1grFOIG6HhMLX/vcN8w==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/trace-mapping": "^0.3.25", + "chokidar": "^4.0.1", + "fdir": "^6.2.0", + "picocolors": "^1.0.0", + "sade": "^1.7.4" + }, + "bin": { + "svelte-check": "bin/svelte-check" + }, + "engines": { + "node": ">= 18.0.0" + }, + "peerDependencies": { + "svelte": "^4.0.0 || ^5.0.0-next.0", + "typescript": ">=5.0.0" + } + }, + "node_modules/svelte/node_modules/is-reference": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/is-reference/-/is-reference-3.0.3.tgz", + "integrity": "sha512-ixkJoqQvAP88E6wLydLGGqCJsrFUnqoH6HnaczB8XmDH1oaWU+xxdptvikTgaEhtZ53Ky6YXiBuUI2WXLMCwjw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "^1.0.6" + } + }, + "node_modules/tar-fs": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.4.tgz", + "integrity": "sha512-mDAjwmZdh7LTT6pNleZ05Yt65HC3E+NiQzl672vQG38jIrehtJk/J3mNwIg+vShQPcLF/LV7CMnDW6vjj6sfYQ==", + "license": "MIT", + "dependencies": { + "chownr": "^1.1.1", + "mkdirp-classic": "^0.5.2", + "pump": "^3.0.0", + "tar-stream": "^2.1.4" + } + }, + "node_modules/tar-stream": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", + "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", + "license": "MIT", + "dependencies": { + "bl": "^4.0.3", + "end-of-stream": "^1.4.1", + "fs-constants": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/tinyglobby": { + "version": "0.2.16", + "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.16.tgz", + "integrity": "sha512-pn99VhoACYR8nFHhxqix+uvsbXineAasWm5ojXoN8xEwK5Kd3/TrhNn1wByuD52UxWRLy8pu+kRMniEi6Eq9Zg==", + "dev": true, + "license": "MIT", + "dependencies": { + "fdir": "^6.5.0", + "picomatch": "^4.0.4" + }, + "engines": { + "node": ">=12.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/SuperchupuDev" + } + }, + "node_modules/totalist": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/totalist/-/totalist-3.0.1.tgz", + "integrity": "sha512-sf4i37nQ2LBx4m3wB74y+ubopq6W/dIzXg0FDGjsYnZHVa1Da8FH853wlL2gtUhg+xJXjfk3kUZS3BRoQeoQBQ==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, + "node_modules/tslib": { + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", + "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", + "dev": true, + "license": "0BSD", + "optional": true + }, + "node_modules/tsx": { + "version": "4.22.3", + "resolved": "https://registry.npmjs.org/tsx/-/tsx-4.22.3.tgz", + "integrity": "sha512-mdoNxBC/cSQObGGVQ5Bpn5i+yv7j68gk3Nfm3wFjcJg3Z0Mix9jzAFfP12prmm5eVGmDKtp0yyArrs0Q+8gZHg==", + "dev": true, + "license": "MIT", + "dependencies": { + "esbuild": "~0.28.0" + }, + "bin": { + "tsx": "dist/cli.mjs" + }, + "engines": { + "node": ">=18.0.0" + }, + "optionalDependencies": { + "fsevents": "~2.3.3" + } + }, + "node_modules/tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha512-McnNiV1l8RYeY8tBgEpuodCC1mLUdbSN+CYBL7kJsJNInOP8UjDDEwdk6Mw60vdLLrr5NHKZhMAOSrR2NZuQ+w==", + "license": "Apache-2.0", + "dependencies": { + "safe-buffer": "^5.0.1" + }, + "engines": { + "node": "*" + } + }, + "node_modules/typescript": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-6.0.3.tgz", + "integrity": "sha512-y2TvuxSZPDyQakkFRPZHKFm+KKVqIisdg9/CZwm9ftvKXLP8NRWj38/ODjNbr43SsoXqNuAisEf1GdCxqWcdBw==", + "dev": true, + "license": "Apache-2.0", + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=14.17" + } + }, + "node_modules/undici-types": { + "version": "7.16.0", + "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.16.0.tgz", + "integrity": "sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==", + "dev": true, + "license": "MIT" + }, + "node_modules/util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", + "license": "MIT" + }, + "node_modules/vite": { + "version": "8.0.14", + "resolved": "https://registry.npmjs.org/vite/-/vite-8.0.14.tgz", + "integrity": "sha512-s4BJJ+5y1pYL6Otw51FHhVJQhPnuRinKig64g/1+EUNaJsd3gCKdD31IPFvswUgW9/60QT9oFHbZHbQK5imcxw==", + "dev": true, + "license": "MIT", + "dependencies": { + "lightningcss": "^1.32.0", + "picomatch": "^4.0.4", + "postcss": "^8.5.15", + "rolldown": "1.0.2", + "tinyglobby": "^0.2.16" + }, + "bin": { + "vite": "bin/vite.js" + }, + "engines": { + "node": "^20.19.0 || >=22.12.0" + }, + "funding": { + "url": "https://github.com/vitejs/vite?sponsor=1" + }, + "optionalDependencies": { + "fsevents": "~2.3.3" + }, + "peerDependencies": { + "@types/node": "^20.19.0 || >=22.12.0", + "@vitejs/devtools": "^0.1.18", + "esbuild": "^0.27.0 || ^0.28.0", + "jiti": ">=1.21.0", + "less": "^4.0.0", + "sass": "^1.70.0", + "sass-embedded": "^1.70.0", + "stylus": ">=0.54.8", + "sugarss": "^5.0.0", + "terser": "^5.16.0", + "tsx": "^4.8.1", + "yaml": "^2.4.2" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + }, + "@vitejs/devtools": { + "optional": true + }, + "esbuild": { + "optional": true + }, + "jiti": { + "optional": true + }, + "less": { + "optional": true + }, + "sass": { + "optional": true + }, + "sass-embedded": { + "optional": true + }, + "stylus": { + "optional": true + }, + "sugarss": { + "optional": true + }, + "terser": { + "optional": true + }, + "tsx": { + "optional": true + }, + "yaml": { + "optional": true + } + } + }, + "node_modules/vitefu": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/vitefu/-/vitefu-1.1.3.tgz", + "integrity": "sha512-ub4okH7Z5KLjb6hDyjqrGXqWtWvoYdU3IGm/NorpgHncKoLTCfRIbvlhBm7r0YstIaQRYlp4yEbFqDcKSzXSSg==", + "dev": true, + "license": "MIT", + "workspaces": [ + "tests/deps/*", + "tests/projects/*", + "tests/projects/workspace/packages/*" + ], + "peerDependencies": { + "vite": "^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "vite": { + "optional": true + } + } + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", + "license": "ISC" + }, + "node_modules/zimmerframe": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/zimmerframe/-/zimmerframe-1.1.4.tgz", + "integrity": "sha512-B58NGBEoc8Y9MWWCQGl/gq9xBCe4IiKM0a2x7GZdQKOW5Exr8S1W24J6OgM1njK8xCRGvAJIL/MxXHf6SkmQKQ==", + "dev": true, + "license": "MIT" + } + } +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..ea9a238 --- /dev/null +++ b/package.json @@ -0,0 +1,38 @@ +{ + "name": "refood-one", + "private": true, + "version": "0.0.1", + "type": "module", + "scripts": { + "dev": "vite dev --host", + "build": "vite build", + "preview": "vite preview", + "prepare": "svelte-kit sync || echo ''", + "check": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json", + "check:watch": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json --watch", + "db:push": "drizzle-kit push", + "db:generate": "drizzle-kit generate", + "db:migrate": "drizzle-kit migrate", + "db:studio": "drizzle-kit studio" + }, + "devDependencies": { + "@sveltejs/adapter-node": "^5.5.4", + "@sveltejs/kit": "^2.57.0", + "@sveltejs/vite-plugin-svelte": "^7.0.0", + "@types/bcrypt": "^6.0.0", + "@types/better-sqlite3": "^7.6.13", + "@types/node": "^24", + "drizzle-kit": "^0.31.10", + "drizzle-orm": "^0.45.2", + "svelte": "^5.55.2", + "svelte-check": "^4.4.6", + "typescript": "^6.0.2", + "vite": "^8.0.7" + }, + "dependencies": { + "@popperjs/core": "^2.11.8", + "bcrypt": "^6.0.0", + "better-sqlite3": "^12.8.0", + "bootstrap": "^5.3.8" + } +} diff --git a/src/app.d.ts b/src/app.d.ts new file mode 100644 index 0000000..80abb84 --- /dev/null +++ b/src/app.d.ts @@ -0,0 +1,19 @@ +// See https://svelte.dev/docs/kit/types#app.d.ts +// for information about these interfaces +declare global { + namespace App { + // interface Error {} + interface Locals { + user: { + id: string; + username: string; + role: string; + } | null; + } + // interface PageData {} + // interface PageState {} + // interface Platform {} + } +} + +export {}; diff --git a/src/app.html b/src/app.html new file mode 100644 index 0000000..6a2bb58 --- /dev/null +++ b/src/app.html @@ -0,0 +1,12 @@ + + + + + + + %sveltekit.head% + + +
%sveltekit.body%
+ + diff --git a/src/hooks.server.ts b/src/hooks.server.ts new file mode 100644 index 0000000..ccdc718 --- /dev/null +++ b/src/hooks.server.ts @@ -0,0 +1,84 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq } from 'drizzle-orm'; +import { redirect, type Handle } from '@sveltejs/kit'; + +export const handle: Handle = async ({ event, resolve }) => { + const sessionId = event.cookies.get('session'); + event.locals.user = null; + + if (sessionId) { + try { + // Query session and join with user info + const result = db + .select({ + session: schema.sessions, + user: schema.users + }) + .from(schema.sessions) + .innerJoin(schema.users, eq(schema.sessions.userId, schema.users.id)) + .where(eq(schema.sessions.id, sessionId)) + .get(); + + if (result) { + const { session, user } = result; + + if (session.expiresAt > Date.now()) { + event.locals.user = { + id: user.id, + username: user.username, + role: user.role + }; + } else { + // Session expired, clean up + db.delete(schema.sessions).where(eq(schema.sessions.id, sessionId)).run(); + event.cookies.delete('session', { path: '/' }); + } + } else { + // Invalid session cookie + event.cookies.delete('session', { path: '/' }); + } + } catch (err) { + console.error('Error in session auth hook:', err); + } + } + + const path = event.url.pathname; + + // Route protection + if (path.startsWith('/admin')) { + if (!event.locals.user) { + throw redirect(303, `/login?redirectTo=${encodeURIComponent(path)}`); + } + + const role = event.locals.user.role; + + if (path.startsWith('/admin/turnos')) { + if (role !== 'admin' && role !== 'shift_manager') { + if (role === 'volunteer') { + throw redirect(303, '/entregas'); + } + throw redirect(303, '/login'); + } + } else { + if (role !== 'admin') { + if (role === 'volunteer') { + throw redirect(303, '/entregas'); + } + throw redirect(303, '/login'); + } + } + } + + if (path.startsWith('/entregas')) { + if (!event.locals.user) { + throw redirect(303, `/login?redirectTo=${encodeURIComponent(path)}`); + } + } + + if (path === '/login' && event.locals.user) { + throw redirect(303, '/'); + } + + return resolve(event); +}; diff --git a/src/lib/assets/favicon.svg b/src/lib/assets/favicon.svg new file mode 100644 index 0000000..cc5dc66 --- /dev/null +++ b/src/lib/assets/favicon.svg @@ -0,0 +1 @@ +svelte-logo \ No newline at end of file diff --git a/src/lib/index.ts b/src/lib/index.ts new file mode 100644 index 0000000..856f2b6 --- /dev/null +++ b/src/lib/index.ts @@ -0,0 +1 @@ +// place files you want to import through the `$lib` alias in this folder. diff --git a/src/lib/server/db/index.ts b/src/lib/server/db/index.ts new file mode 100644 index 0000000..a0e999b --- /dev/null +++ b/src/lib/server/db/index.ts @@ -0,0 +1,60 @@ +import { drizzle } from 'drizzle-orm/better-sqlite3'; +import Database from 'better-sqlite3'; +import * as schema from './schema'; +import { env } from '$env/dynamic/private'; +import bcrypt from 'bcrypt'; + +if (!env.DATABASE_URL) throw new Error('DATABASE_URL is not set'); + +const client = new Database(env.DATABASE_URL); + +export const db = drizzle(client, { schema }); + +// Seed admin user if the users table is empty (US00) +try { + const usersList = db.select().from(schema.users).all(); + if (usersList.length === 0) { + console.log('Seeding default admin user (refoodpdn)...'); + const passwordHash = bcrypt.hashSync('rpdn!2512', 10); + db.insert(schema.users).values({ + username: 'refoodpdn', + passwordHash: passwordHash, + role: 'admin' + }).run(); + console.log('Default admin user seeded successfully.'); + } +} catch (err) { + console.error('Failed to seed default admin user:', err); +} + +// Seed default shifts if the shifts table is empty (US06) +try { + const shiftsList = db.select().from(schema.shifts).all(); + if (shiftsList.length === 0) { + console.log('Seeding default shifts (T1, T2, T3)...'); + db.insert(schema.shifts).values([ + { + code: 'T1', + startTime: '14:30', + endTime: '16:30', + days: '2,4' // Tuesday and Thursday + }, + { + code: 'T2', + startTime: '16:30', + endTime: '18:30', + days: '2,4' + }, + { + code: 'T3', + startTime: '18:30', + endTime: '20:30', + days: '2,4' + } + ]).run(); + console.log('Default shifts seeded successfully.'); + } +} catch (err) { + console.error('Failed to seed default shifts:', err); +} + diff --git a/src/lib/server/db/schema.ts b/src/lib/server/db/schema.ts new file mode 100644 index 0000000..ff81c55 --- /dev/null +++ b/src/lib/server/db/schema.ts @@ -0,0 +1,52 @@ +import { integer, sqliteTable, text } from 'drizzle-orm/sqlite-core'; + +export const users = sqliteTable('users', { + id: text('id').primaryKey().$defaultFn(() => crypto.randomUUID()), + username: text('username').notNull().unique(), + passwordHash: text('password_hash').notNull(), + role: text('role').notNull(), // 'admin' | 'shift_manager' | 'volunteer' + createdAt: integer('created_at').notNull().$defaultFn(() => Date.now()) +}); + +export const sessions = sqliteTable('sessions', { + id: text('id').primaryKey().$defaultFn(() => crypto.randomUUID()), + userId: text('user_id') + .notNull() + .references(() => users.id, { onDelete: 'cascade' }), + expiresAt: integer('expires_at').notNull() +}); + +export const beneficiaries = sqliteTable('beneficiaries', { + id: text('id').primaryKey().$defaultFn(() => crypto.randomUUID()), + number: integer('number').notNull().unique(), + name: text('name').notNull(), + contact: text('contact').notNull(), + householdSize: integer('household_size').notNull().default(1), + observations: text('observations'), + status: text('status').notNull().default('ativo'), // 'ativo' | 'inativo' + createdAt: integer('created_at').notNull().$defaultFn(() => Date.now()), + updatedAt: integer('updated_at').notNull().$defaultFn(() => Date.now()) +}); + +export const shifts = sqliteTable('shifts', { + id: text('id').primaryKey().$defaultFn(() => crypto.randomUUID()), + code: text('code').notNull().unique(), // 'T1', 'T2', 'T3' + startTime: text('start_time').notNull(), // '14:30' + endTime: text('end_time').notNull(), // '16:30' + days: text('days').notNull(), // '2,4' (Tuesday, Thursday) + createdAt: integer('created_at').notNull().$defaultFn(() => Date.now()), + updatedAt: integer('updated_at').notNull().$defaultFn(() => Date.now()) +}); + +export const deliveries = sqliteTable('deliveries', { + id: text('id').primaryKey().$defaultFn(() => crypto.randomUUID()), + beneficiaryId: text('beneficiary_id') + .notNull() + .references(() => beneficiaries.id, { onDelete: 'cascade' }), + shiftId: text('shift_id') + .notNull() + .references(() => shifts.id, { onDelete: 'cascade' }), + date: text('date').notNull(), // 'YYYY-MM-DD' + createdAt: integer('created_at').notNull().$defaultFn(() => Date.now()) +}); + diff --git a/src/routes/+layout.server.ts b/src/routes/+layout.server.ts new file mode 100644 index 0000000..ec238fd --- /dev/null +++ b/src/routes/+layout.server.ts @@ -0,0 +1,7 @@ +import type { LayoutServerLoad } from './$types'; + +export const load: LayoutServerLoad = async ({ locals }) => { + return { + user: locals.user + }; +}; diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte new file mode 100644 index 0000000..a6ed2cd --- /dev/null +++ b/src/routes/+layout.svelte @@ -0,0 +1,127 @@ + + + + + + + + + +
+ {#if data?.user} + + {/if} + +
+ {@render children()} +
+
+ + diff --git a/src/routes/+page.server.ts b/src/routes/+page.server.ts new file mode 100644 index 0000000..593b3da --- /dev/null +++ b/src/routes/+page.server.ts @@ -0,0 +1,11 @@ +import { redirect } from '@sveltejs/kit'; +import type { PageServerLoad } from './$types'; + +export const load: PageServerLoad = async ({ locals }) => { + if (!locals.user) { + throw redirect(303, '/login'); + } + return { + user: locals.user + }; +}; diff --git a/src/routes/+page.svelte b/src/routes/+page.svelte new file mode 100644 index 0000000..b56e048 --- /dev/null +++ b/src/routes/+page.svelte @@ -0,0 +1,95 @@ + + + + Painel Principal - RefoodOne + + +
+
+
+

Olá, {data.user.username}!

+

Selecione uma opção para começar

+
+ +
+ + +
+ + + + +
+ Entregas +
+ + {#if data.user.role === 'admin'} + + +
+ + + + +
+ Beneficiários +
+ + + +
+ + + + +
+ Utilizadores +
+ {/if} +
+
+
+ + diff --git a/src/routes/admin/beneficiarios/+page.server.ts b/src/routes/admin/beneficiarios/+page.server.ts new file mode 100644 index 0000000..600678d --- /dev/null +++ b/src/routes/admin/beneficiarios/+page.server.ts @@ -0,0 +1,45 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { asc, eq, or, like } from 'drizzle-orm'; +import type { PageServerLoad } from './$types'; + +export const load: PageServerLoad = async ({ url }) => { + const search = url.searchParams.get('search') || ''; + const status = url.searchParams.get('status') || ''; + + try { + let query = db.select().from(schema.beneficiaries); + + // We can fetch all and filter in memory since table size is guaranteed to be small (<20 tables, low concurrency). + // This keeps SQLite query logic extremely simple and readable. + let list = query.orderBy(asc(schema.beneficiaries.name)).all(); + + if (search) { + const searchLower = search.toLowerCase(); + list = list.filter( + (b) => + b.name.toLowerCase().includes(searchLower) || + b.number.toString().includes(searchLower) || + (b.contact && b.contact.includes(searchLower)) + ); + } + + if (status && status !== 'todos') { + list = list.filter((b) => b.status === status); + } + + return { + beneficiaries: list, + search, + status: status || 'todos' + }; + } catch (err) { + console.error('Error loading beneficiaries:', err); + return { + beneficiaries: [], + search, + status: status || 'todos', + error: 'Erro ao carregar a lista de beneficiários.' + }; + } +}; diff --git a/src/routes/admin/beneficiarios/+page.svelte b/src/routes/admin/beneficiarios/+page.svelte new file mode 100644 index 0000000..2c86ed0 --- /dev/null +++ b/src/routes/admin/beneficiarios/+page.svelte @@ -0,0 +1,131 @@ + + + + Beneficiários - RefoodOne + + +
+ {#if successMessage} + + {/if} + +
+
+

Beneficiários

+

Gerir a listagem de beneficiários e agregados familiares

+
+ + + + + Novo Beneficiário + +
+ +
+
+
+ + +
+ +
+ + +
+ +
+ +
+
+
+ +
+
+ + + + + + + + + + + + + {#if data.beneficiaries.length === 0} + + + + {:else} + {#each data.beneficiaries as beneficiary} + + + + + + + + + {/each} + {/if} + +
NúmeroNomeContactoAgregadoEstadoAções
+ + + +

Nenhum beneficiário encontrado.

+
+ #{beneficiary.number} + + {beneficiary.name} + + {beneficiary.contact} + + {beneficiary.householdSize} + + {#if beneficiary.status === 'ativo'} + Ativo + {:else} + Inativo + {/if} + + + + + + Editar + +
+
+
+
diff --git a/src/routes/admin/beneficiarios/[id]/+page.server.ts b/src/routes/admin/beneficiarios/[id]/+page.server.ts new file mode 100644 index 0000000..f94ad85 --- /dev/null +++ b/src/routes/admin/beneficiarios/[id]/+page.server.ts @@ -0,0 +1,120 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq, and, ne } from 'drizzle-orm'; +import { error, fail, redirect } from '@sveltejs/kit'; +import type { Actions, PageServerLoad } from './$types'; + +export const load: PageServerLoad = async ({ params }) => { + const id = params.id; + + try { + const beneficiary = db + .select() + .from(schema.beneficiaries) + .where(eq(schema.beneficiaries.id, id)) + .get(); + + if (!beneficiary) { + throw error(404, 'Beneficiário não encontrado'); + } + + return { + beneficiary + }; + } catch (err) { + if (err && typeof err === 'object' && 'status' in err && err.status === 404) { + throw err; + } + console.error('Error loading beneficiary details:', err); + throw error(500, 'Ocorreu um erro ao carregar os dados do beneficiário.'); + } +}; + +export const actions: Actions = { + default: async ({ params, request }) => { + const id = params.id; + const data = await request.formData(); + const numberStr = data.get('number')?.toString().trim(); + const name = data.get('name')?.toString().trim(); + const contact = data.get('contact')?.toString().trim(); + const householdSizeStr = data.get('householdSize')?.toString().trim(); + const observations = data.get('observations')?.toString().trim(); + const status = data.get('status')?.toString().trim(); + + // Basic validation + if (!numberStr || !name || !contact || !householdSizeStr || !status) { + return fail(400, { + success: false, + error: 'Todos os campos obrigatórios devem ser preenchidos.' + }); + } + + const number = parseInt(numberStr, 10); + const householdSize = parseInt(householdSizeStr, 10); + + if (isNaN(number) || number <= 0) { + return fail(400, { + success: false, + error: 'O número de beneficiário deve ser um número inteiro positivo.' + }); + } + + if (isNaN(householdSize) || householdSize < 1) { + return fail(400, { + success: false, + error: 'O agregado familiar deve ter pelo menos 1 pessoa.' + }); + } + + if (status !== 'ativo' && status !== 'inativo') { + return fail(400, { + success: false, + error: 'Estado inválido selecionado.' + }); + } + + try { + // Check if new number conflicts with another beneficiary (excluding self) + const existingConflict = db + .select() + .from(schema.beneficiaries) + .where( + and( + eq(schema.beneficiaries.number, number), + ne(schema.beneficiaries.id, id) + ) + ) + .get(); + + if (existingConflict) { + return fail(400, { + success: false, + error: `O número de beneficiário #${number} já está atribuído a outro registo.` + }); + } + + // Update details + db.update(schema.beneficiaries) + .set({ + number, + name, + contact, + householdSize, + observations, + status, + updatedAt: Date.now() + }) + .where(eq(schema.beneficiaries.id, id)) + .run(); + } catch (err) { + console.error('Error updating beneficiary details:', err); + return fail(500, { + success: false, + error: 'Erro ao guardar as alterações na base de dados.' + }); + } + + // Redirect on success + throw redirect(303, `/admin/beneficiarios?success=${encodeURIComponent('Alterações guardadas com sucesso.')}`); + } +}; diff --git a/src/routes/admin/beneficiarios/[id]/+page.svelte b/src/routes/admin/beneficiarios/[id]/+page.svelte new file mode 100644 index 0000000..6553cc9 --- /dev/null +++ b/src/routes/admin/beneficiarios/[id]/+page.svelte @@ -0,0 +1,144 @@ + + + + Editar Beneficiário - RefoodOne + + +
+
+ + + + + Voltar para a lista + +

Editar Beneficiário

+

Atualizar informações do beneficiário #{beneficiary.number}

+
+ + {#if form?.error} + + {/if} + +
+
{ + isLoading = true; + return async ({ update }) => { + isLoading = false; + await update(); + }; + }}> +
+
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+
+ +
+ + Cancelar + + +
+
+
+
diff --git a/src/routes/admin/beneficiarios/novo/+page.server.ts b/src/routes/admin/beneficiarios/novo/+page.server.ts new file mode 100644 index 0000000..c555067 --- /dev/null +++ b/src/routes/admin/beneficiarios/novo/+page.server.ts @@ -0,0 +1,83 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq } from 'drizzle-orm'; +import { fail, redirect } from '@sveltejs/kit'; +import type { Actions } from './$types'; + +export const actions: Actions = { + default: async ({ request }) => { + const data = await request.formData(); + const numberStr = data.get('number')?.toString().trim(); + const name = data.get('name')?.toString().trim(); + const contact = data.get('contact')?.toString().trim(); + const householdSizeStr = data.get('householdSize')?.toString().trim(); + const observations = data.get('observations')?.toString().trim(); + + // Basic validation + if (!numberStr || !name || !contact || !householdSizeStr) { + return fail(400, { + success: false, + error: 'Todos os campos obrigatórios devem ser preenchidos.' + }); + } + + const number = parseInt(numberStr, 10); + const householdSize = parseInt(householdSizeStr, 10); + + if (isNaN(number) || number <= 0) { + return fail(400, { + success: false, + error: 'O número de beneficiário deve ser um número inteiro positivo.' + }); + } + + if (isNaN(householdSize) || householdSize < 1) { + return fail(400, { + success: false, + error: 'O agregado familiar deve ter pelo menos 1 pessoa.' + }); + } + + try { + // Check if number is unique + const existing = db + .select() + .from(schema.beneficiaries) + .where(eq(schema.beneficiaries.number, number)) + .get(); + + if (existing) { + return fail(400, { + success: false, + number, + name, + contact, + householdSize, + observations, + error: `O número de beneficiário #${number} já se encontra registado.` + }); + } + + // Insert beneficiary + db.insert(schema.beneficiaries) + .values({ + number, + name, + contact, + householdSize, + observations, + status: 'ativo' + }) + .run(); + } catch (err) { + console.error('Error creating beneficiary:', err); + return fail(500, { + success: false, + error: 'Ocorreu um erro ao guardar o beneficiário. Tente novamente.' + }); + } + + // Redirect on success + throw redirect(303, `/admin/beneficiarios?success=${encodeURIComponent('Beneficiário guardado com sucesso.')}`); + } +}; diff --git a/src/routes/admin/beneficiarios/novo/+page.svelte b/src/routes/admin/beneficiarios/novo/+page.svelte new file mode 100644 index 0000000..3d64080 --- /dev/null +++ b/src/routes/admin/beneficiarios/novo/+page.svelte @@ -0,0 +1,133 @@ + + + + Novo Beneficiário - RefoodOne + + +
+
+ + + + + Voltar para a lista + +

Novo Beneficiário

+

Adicionar um novo beneficiário ao sistema

+
+ + {#if form?.error} + + {/if} + +
+
{ + isLoading = true; + return async ({ update }) => { + isLoading = false; + await update(); + }; + }}> +
+
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+
+ +
+ + Cancelar + + +
+
+
+
diff --git a/src/routes/admin/turnos/+page.server.ts b/src/routes/admin/turnos/+page.server.ts new file mode 100644 index 0000000..ae957a1 --- /dev/null +++ b/src/routes/admin/turnos/+page.server.ts @@ -0,0 +1,24 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { asc } from 'drizzle-orm'; +import type { PageServerLoad } from './$types'; + +export const load: PageServerLoad = async () => { + try { + const list = db + .select() + .from(schema.shifts) + .orderBy(asc(schema.shifts.startTime)) + .all(); + + return { + shifts: list + }; + } catch (err) { + console.error('Error loading shifts:', err); + return { + shifts: [], + error: 'Erro ao carregar a lista de turnos.' + }; + } +}; diff --git a/src/routes/admin/turnos/+page.svelte b/src/routes/admin/turnos/+page.svelte new file mode 100644 index 0000000..4808f6c --- /dev/null +++ b/src/routes/admin/turnos/+page.svelte @@ -0,0 +1,128 @@ + + + + Gestão de Turnos - RefoodOne + + +
+ {#if successMessage} + + {/if} + + {#if data.error} + + {/if} + +
+
+

Gestão de Turnos

+

Configurar os horários padrão e dias de funcionamento das entregas da Refood PdN

+
+
+ +
+
+ + + + + + + + + + + + {#if data.shifts.length === 0} + + + + {:else} + {#each data.shifts as shift} + + + + + + + + {/each} + {/if} + +
TurnoHorárioDuraçãoDias de FuncionamentoAções
+ + + +

Nenhum turno configurado no sistema.

+
+ {shift.code} + + {shift.startTime} - {shift.endTime} + + {calculateDuration(shift.startTime, shift.endTime)} + + + {formatDays(shift.days)} + + + + + + + Editar + +
+
+
+
diff --git a/src/routes/admin/turnos/[id]/+page.server.ts b/src/routes/admin/turnos/[id]/+page.server.ts new file mode 100644 index 0000000..93ea96c --- /dev/null +++ b/src/routes/admin/turnos/[id]/+page.server.ts @@ -0,0 +1,104 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq } from 'drizzle-orm'; +import { error, fail, redirect } from '@sveltejs/kit'; +import type { Actions, PageServerLoad } from './$types'; + +export const load: PageServerLoad = async ({ params }) => { + const id = params.id; + + try { + const shift = db + .select() + .from(schema.shifts) + .where(eq(schema.shifts.id, id)) + .get(); + + if (!shift) { + throw error(404, 'Turno não encontrado'); + } + + return { + shift + }; + } catch (err) { + if (err && typeof err === 'object' && 'status' in err && err.status === 404) { + throw err; + } + console.error('Error loading shift details:', err); + throw error(500, 'Ocorreu um erro ao carregar os dados do turno.'); + } +}; + +export const actions: Actions = { + default: async ({ params, request }) => { + const id = params.id; + const data = await request.formData(); + const startTime = data.get('startTime')?.toString().trim(); + const endTime = data.get('endTime')?.toString().trim(); + const daysArray = data.getAll('days').map((d) => d.toString().trim()); + + if (!startTime || !endTime) { + return fail(400, { + success: false, + error: 'As horas de início e fim são obrigatórias.' + }); + } + + if (daysArray.length === 0) { + return fail(400, { + success: false, + error: 'Deve selecionar pelo menos um dia da semana.' + }); + } + + // Validate time format and values (HH:MM) + const timeRegex = /^([0-1]?[0-9]|2[0-3]):[0-5][0-9]$/; + if (!timeRegex.test(startTime) || !timeRegex.test(endTime)) { + return fail(400, { + success: false, + error: 'Formato de hora inválido. Use o formato HH:MM.' + }); + } + + const [startH, startM] = startTime.split(':').map(Number); + const [endH, endM] = endTime.split(':').map(Number); + const startMinutes = startH * 60 + startM; + const endMinutes = endH * 60 + endM; + + if (endMinutes <= startMinutes) { + return fail(400, { + success: false, + error: 'A hora de fim deve ser posterior à hora de início.' + }); + } + + // Days should be sorted so it is stored consistently + const sortedDays = daysArray + .map(Number) + .filter((d) => d >= 1 && d <= 7) + .sort((a, b) => a - b) + .map(String) + .join(','); + + try { + db.update(schema.shifts) + .set({ + startTime, + endTime, + days: sortedDays, + updatedAt: Date.now() + }) + .where(eq(schema.shifts.id, id)) + .run(); + } catch (err) { + console.error('Error updating shift:', err); + return fail(500, { + success: false, + error: 'Erro ao guardar as alterações na base de dados.' + }); + } + + throw redirect(303, `/admin/turnos?success=${encodeURIComponent('Horário do turno guardado com sucesso.')}`); + } +}; diff --git a/src/routes/admin/turnos/[id]/+page.svelte b/src/routes/admin/turnos/[id]/+page.svelte new file mode 100644 index 0000000..4c9fa6a --- /dev/null +++ b/src/routes/admin/turnos/[id]/+page.svelte @@ -0,0 +1,136 @@ + + + + Editar Turno - RefoodOne + + +
+
+ + + + + Voltar para a lista + +

Editar Turno

+

Atualizar horário e dias de funcionamento do turno {shift.code}

+
+ + {#if form?.error} + + {/if} + +
+
{ + isLoading = true; + return async ({ update }) => { + isLoading = false; + await update(); + }; + }}> +
+
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ Dias de Funcionamento * +
+ {#each weekdays as day} +
+
+ + +
+
+ {/each} +
+
+
+ +
+ + Cancelar + + +
+
+
+
diff --git a/src/routes/admin/utilizadores/+page.server.ts b/src/routes/admin/utilizadores/+page.server.ts new file mode 100644 index 0000000..df2cd50 --- /dev/null +++ b/src/routes/admin/utilizadores/+page.server.ts @@ -0,0 +1,29 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { asc } from 'drizzle-orm'; +import type { PageServerLoad } from './$types'; + +export const load: PageServerLoad = async () => { + try { + const list = db + .select({ + id: schema.users.id, + username: schema.users.username, + role: schema.users.role, + createdAt: schema.users.createdAt + }) + .from(schema.users) + .orderBy(asc(schema.users.username)) + .all(); + + return { + users: list + }; + } catch (err) { + console.error('Error loading users:', err); + return { + users: [], + error: 'Erro ao carregar a lista de utilizadores.' + }; + } +}; diff --git a/src/routes/admin/utilizadores/+page.svelte b/src/routes/admin/utilizadores/+page.svelte new file mode 100644 index 0000000..126ca6c --- /dev/null +++ b/src/routes/admin/utilizadores/+page.svelte @@ -0,0 +1,97 @@ + + + + Utilizadores - RefoodOne + + +
+ {#if successMessage} + + {/if} + + {#if data.error} + + {/if} + +
+
+

Utilizadores

+

Gerir contas de utilizadores e permissões de acesso

+
+ + + + + Novo Utilizador + +
+ +
+
+ + + + + + + + + + {#if data.users.length === 0} + + + + {:else} + {#each data.users as u} + + + + + + {/each} + {/if} + +
NomeRoleAções
+

Nenhum utilizador encontrado.

+
+ {u.username} + + + {getRoleLabel(u.role)} + + + + Editar + +
+
+
+
diff --git a/src/routes/admin/utilizadores/[id]/+page.server.ts b/src/routes/admin/utilizadores/[id]/+page.server.ts new file mode 100644 index 0000000..7abed73 --- /dev/null +++ b/src/routes/admin/utilizadores/[id]/+page.server.ts @@ -0,0 +1,129 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq, and, ne } from 'drizzle-orm'; +import { error, fail, redirect } from '@sveltejs/kit'; +import type { Actions, PageServerLoad } from './$types'; +import bcrypt from 'bcrypt'; + +export const load: PageServerLoad = async ({ params }) => { + const id = params.id; + + try { + const user = db + .select({ + id: schema.users.id, + username: schema.users.username, + role: schema.users.role, + createdAt: schema.users.createdAt + }) + .from(schema.users) + .where(eq(schema.users.id, id)) + .get(); + + if (!user) { + throw error(404, 'Utilizador não encontrado'); + } + + return { + targetUser: user + }; + } catch (err) { + if (err && typeof err === 'object' && 'status' in err && err.status === 404) { + throw err; + } + console.error('Error loading user details:', err); + throw error(500, 'Ocorreu um erro ao carregar os dados do utilizador.'); + } +}; + +export const actions: Actions = { + default: async ({ params, request }) => { + const id = params.id; + const data = await request.formData(); + const username = data.get('username')?.toString().trim(); + const role = data.get('role')?.toString().trim(); + const password = data.get('password')?.toString(); + const confirmPassword = data.get('confirmPassword')?.toString(); + + if (!username || !role) { + return fail(400, { + success: false, + error: 'Nome de utilizador e Perfil são campos obrigatórios.' + }); + } + + if (role !== 'admin' && role !== 'shift_manager' && role !== 'volunteer') { + return fail(400, { + success: false, + error: 'Perfil selecionado é inválido.' + }); + } + + let shouldUpdatePassword = false; + if (password || confirmPassword) { + shouldUpdatePassword = true; + if (password !== confirmPassword) { + return fail(400, { + success: false, + error: 'As palavras-passe introduzidas não coincidem.' + }); + } + if (password!.length < 4) { + return fail(400, { + success: false, + error: 'A palavra-passe deve ter pelo menos 4 caracteres.' + }); + } + } + + try { + // Check if username conflicts with another user (excluding self) + const existingConflict = db + .select() + .from(schema.users) + .where( + and( + eq(schema.users.username, username), + ne(schema.users.id, id) + ) + ) + .get(); + + if (existingConflict) { + return fail(400, { + success: false, + error: 'O nome de utilizador já está a ser utilizado por outra conta.' + }); + } + + // Update values + if (shouldUpdatePassword) { + const passwordHash = bcrypt.hashSync(password!, 10); + db.update(schema.users) + .set({ + username, + role, + passwordHash + }) + .where(eq(schema.users.id, id)) + .run(); + } else { + db.update(schema.users) + .set({ + username, + role + }) + .where(eq(schema.users.id, id)) + .run(); + } + } catch (err) { + console.error('Error updating user:', err); + return fail(500, { + success: false, + error: 'Erro ao guardar as alterações na base de dados.' + }); + } + + throw redirect(303, `/admin/utilizadores?success=${encodeURIComponent('Alterações guardadas com sucesso.')}`); + } +}; diff --git a/src/routes/admin/utilizadores/[id]/+page.svelte b/src/routes/admin/utilizadores/[id]/+page.svelte new file mode 100644 index 0000000..73ceab0 --- /dev/null +++ b/src/routes/admin/utilizadores/[id]/+page.svelte @@ -0,0 +1,111 @@ + + + + Editar Utilizador - RefoodOne + + +
+
+ + + + + Voltar para a lista + +

Editar Utilizador

+

Atualizar informações da conta de {user.username}

+
+ + {#if form?.error} + + {/if} + +
+
{ + isLoading = true; + return async ({ update }) => { + isLoading = false; + await update(); + }; + }}> +
+
+ + +
+ +
+ + +
+ +
+ +
+
Alterar Palavra-passe
+

Deixe estes campos em branco se não pretender alterar a palavra-passe atual.

+
+ +
+ + +
+ +
+ + +
+
+ +
+ + Cancelar + + +
+
+
+
diff --git a/src/routes/admin/utilizadores/novo/+page.server.ts b/src/routes/admin/utilizadores/novo/+page.server.ts new file mode 100644 index 0000000..e8be8ea --- /dev/null +++ b/src/routes/admin/utilizadores/novo/+page.server.ts @@ -0,0 +1,91 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq } from 'drizzle-orm'; +import { fail, redirect } from '@sveltejs/kit'; +import type { Actions } from './$types'; +import bcrypt from 'bcrypt'; + +export const actions: Actions = { + default: async ({ request }) => { + const data = await request.formData(); + const username = data.get('username')?.toString().trim(); + const role = data.get('role')?.toString().trim(); + const password = data.get('password')?.toString(); + const confirmPassword = data.get('confirmPassword')?.toString(); + + if (!username || !role || !password || !confirmPassword) { + return fail(400, { + success: false, + username, + role, + error: 'Todos os campos obrigatórios devem ser preenchidos.' + }); + } + + if (role !== 'admin' && role !== 'shift_manager' && role !== 'volunteer') { + return fail(400, { + success: false, + username, + role, + error: 'Perfil selecionado é inválido.' + }); + } + + if (password !== confirmPassword) { + return fail(400, { + success: false, + username, + role, + error: 'As palavras-passe introduzidas não coincidem.' + }); + } + + if (password.length < 4) { + return fail(400, { + success: false, + username, + role, + error: 'A palavra-passe deve ter pelo menos 4 caracteres.' + }); + } + + try { + // Check if username already exists + const existing = db + .select() + .from(schema.users) + .where(eq(schema.users.username, username)) + .get(); + + if (existing) { + return fail(400, { + success: false, + username, + role, + error: 'O nome de utilizador já está a ser utilizado.' + }); + } + + // Insert user + const passwordHash = bcrypt.hashSync(password, 10); + db.insert(schema.users) + .values({ + username, + role, + passwordHash, + createdAt: Date.now() + }) + .run(); + } catch (err) { + console.error('Error creating user:', err); + return fail(500, { + success: false, + username, + role, + error: 'Erro interno ao guardar o utilizador. Tente novamente.' + }); + } + + throw redirect(303, `/admin/utilizadores?success=${encodeURIComponent('Utilizador criado com sucesso.')}`); + } +}; diff --git a/src/routes/admin/utilizadores/novo/+page.svelte b/src/routes/admin/utilizadores/novo/+page.svelte new file mode 100644 index 0000000..19e2950 --- /dev/null +++ b/src/routes/admin/utilizadores/novo/+page.svelte @@ -0,0 +1,109 @@ + + + + Novo Utilizador - RefoodOne + + +
+
+ + + + + Voltar para a lista + +

Novo Utilizador

+

Criar uma nova conta de acesso ao sistema

+
+ + {#if form?.error} + + {/if} + +
+
{ + isLoading = true; + return async ({ update }) => { + isLoading = false; + await update(); + }; + }}> +
+
+ + +
+ +
+ + +
+ +
+ +
Definir Palavra-passe
+ +
+ + +
+ +
+ + +
+
+ +
+ + Cancelar + + +
+
+
+
diff --git a/src/routes/entregas/+page.server.ts b/src/routes/entregas/+page.server.ts new file mode 100644 index 0000000..9a8865f --- /dev/null +++ b/src/routes/entregas/+page.server.ts @@ -0,0 +1,193 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq, and, asc } from 'drizzle-orm'; +import { fail, redirect } from '@sveltejs/kit'; +import type { Actions, PageServerLoad } from './$types'; + +export const load: PageServerLoad = async ({ locals }) => { + if (!locals.user) { + throw redirect(303, '/login'); + } + + const todayStr = new Date().toLocaleDateString('sv-SE', { timeZone: 'Europe/Lisbon' }); // 'YYYY-MM-DD' + + try { + // Fetch active beneficiaries sorted by their unique number + const activeBeneficiaries = db + .select() + .from(schema.beneficiaries) + .where(eq(schema.beneficiaries.status, 'ativo')) + .orderBy(asc(schema.beneficiaries.number)) + .all(); + + // Fetch all shifts + const shiftsList = db + .select() + .from(schema.shifts) + .orderBy(asc(schema.shifts.startTime)) + .all(); + + // Fetch today's deliveries with associated beneficiary and shift details + const todayDeliveries = db + .select({ + id: schema.deliveries.id, + date: schema.deliveries.date, + createdAt: schema.deliveries.createdAt, + beneficiary: schema.beneficiaries, + shift: schema.shifts + }) + .from(schema.deliveries) + .innerJoin(schema.beneficiaries, eq(schema.deliveries.beneficiaryId, schema.beneficiaries.id)) + .innerJoin(schema.shifts, eq(schema.deliveries.shiftId, schema.shifts.id)) + .where(eq(schema.deliveries.date, todayStr)) + .all(); + + // Compile the list of beneficiary IDs who already received a basket today + const deliveredIds = todayDeliveries.map((d) => d.beneficiary.id); + + return { + beneficiaries: activeBeneficiaries, + shifts: shiftsList, + todayDeliveries, + deliveredIds + }; + } catch (err) { + console.error('Error loading deliveries page:', err); + return { + beneficiaries: [], + shifts: [], + todayDeliveries: [], + deliveredIds: [], + error: 'Erro ao carregar os dados de entregas.' + }; + } +}; + +export const actions: Actions = { + registar: async ({ request, locals }) => { + if (!locals.user) { + return fail(401, { error: 'Sessão expirada. Faça login novamente.' }); + } + + const data = await request.formData(); + const beneficiaryId = data.get('beneficiaryId')?.toString(); + + if (!beneficiaryId) { + return fail(400, { error: 'O ID do beneficiário é obrigatório.' }); + } + + const todayStr = new Date().toLocaleDateString('sv-SE', { timeZone: 'Europe/Lisbon' }); // 'YYYY-MM-DD' + + try { + // 1. Verify beneficiary exists and is active + const beneficiary = db + .select() + .from(schema.beneficiaries) + .where(eq(schema.beneficiaries.id, beneficiaryId)) + .get(); + + if (!beneficiary) { + return fail(404, { error: 'Beneficiário não encontrado.' }); + } + + if (beneficiary.status !== 'ativo') { + return fail(400, { error: 'O beneficiário não se encontra ativo.' }); + } + + // 2. Prevent duplicate deliveries on the same day + const existing = db + .select() + .from(schema.deliveries) + .where( + and( + eq(schema.deliveries.beneficiaryId, beneficiaryId), + eq(schema.deliveries.date, todayStr) + ) + ) + .get(); + + if (existing) { + return fail(400, { error: `O beneficiário #${beneficiary.number} já recebeu um cabaz hoje.` }); + } + + // 3. Resolve shift automatically based on current day and time + const shifts = db.select().from(schema.shifts).all(); + if (shifts.length === 0) { + return fail(500, { error: 'Não existem turnos configurados no sistema.' }); + } + + const now = new Date(); + const dayOfWeek = now.getDay(); // 0 = Sunday, 1 = Monday, ..., 6 = Saturday + const mappedDay = dayOfWeek === 0 ? 7 : dayOfWeek; // Map Sunday to 7 + const currentMinutes = now.getHours() * 60 + now.getMinutes(); + + let activeShiftId = ''; + + // Try to find exact match: day of week and current time in shift window + for (const s of shifts) { + const days = s.days.split(',').map(Number); + if (days.includes(mappedDay)) { + const [startH, startM] = s.startTime.split(':').map(Number); + const [endH, endM] = s.endTime.split(':').map(Number); + const startMin = startH * 60 + startM; + const endMin = endH * 60 + endM; + + if (currentMinutes >= startMin && currentMinutes <= endMin) { + activeShiftId = s.id; + break; + } + } + } + + // Fallback: If no shift matches the time, find first shift today + if (!activeShiftId) { + const shiftsToday = shifts.filter((s) => s.days.split(',').map(Number).includes(mappedDay)); + if (shiftsToday.length > 0) { + activeShiftId = shiftsToday[0].id; + } else { + // Fallback to first configured shift + activeShiftId = shifts[0].id; + } + } + + // 4. Insert delivery record + db.insert(schema.deliveries) + .values({ + beneficiaryId, + shiftId: activeShiftId, + date: todayStr, + createdAt: Date.now() + }) + .run(); + + return { success: true }; + } catch (err) { + console.error('Error logging delivery:', err); + return fail(500, { error: 'Erro ao registar a entrega na base de dados.' }); + } + }, + apagar: async ({ request, locals }) => { + if (!locals.user) { + return fail(401, { error: 'Sessão expirada. Faça login novamente.' }); + } + + const data = await request.formData(); + const deliveryId = data.get('deliveryId')?.toString(); + + if (!deliveryId) { + return fail(400, { error: 'O ID do registo de entrega é obrigatório.' }); + } + + try { + // Delete the delivery record + db.delete(schema.deliveries) + .where(eq(schema.deliveries.id, deliveryId)) + .run(); + + return { success: true }; + } catch (err) { + console.error('Error deleting delivery:', err); + return fail(500, { error: 'Erro ao apagar o registo de entrega.' }); + } + } +}; diff --git a/src/routes/entregas/+page.svelte b/src/routes/entregas/+page.svelte new file mode 100644 index 0000000..7602ef6 --- /dev/null +++ b/src/routes/entregas/+page.svelte @@ -0,0 +1,333 @@ + + + + Registo de Entregas - RefoodOne + + +
+
+
+

Registo de Entregas

+

Selecione o número do beneficiário para registar a entrega do cabaz de hoje

+
+
+ + + + + {new Date().toLocaleDateString('pt-PT', { timeZone: 'Europe/Lisbon', weekday: 'long', year: 'numeric', month: 'long', day: 'numeric' })} +
+
+ + {#if form?.error} + + {/if} + + +
+
Selecione o Beneficiário
+ {#if data.beneficiaries.length === 0} +
+ + + +

Não existem beneficiários ativos registados no sistema.

+
+ {:else} +
+ {#each data.beneficiaries as beneficiary} + {@const isDelivered = deliveredSet.has(beneficiary.id)} + + {/each} +
+ {/if} +
+ + +
+
+
Entregas de Hoje
+
+
+ + + + + + + + + + + + {#if data.todayDeliveries.length === 0} + + + + {:else} + {#each data.todayDeliveries as delivery} + + + + + + + + {/each} + {/if} + +
NúmeroNome do BeneficiárioTurnoHora do RegistoAções
+ Nenhum cabaz entregue hoje. +
+ #{delivery.beneficiary.number} + + {delivery.beneficiary.name} + + + {delivery.shift.code} ({delivery.shift.startTime} - {delivery.shift.endTime}) + + + {formatTime(delivery.createdAt)} + + +
+
+
+
+ + +{#if activeModalBeneficiary} + + +{/if} + +{#if activeDeleteDelivery} + + +{/if} + + diff --git a/src/routes/login/+page.server.ts b/src/routes/login/+page.server.ts new file mode 100644 index 0000000..c47df03 --- /dev/null +++ b/src/routes/login/+page.server.ts @@ -0,0 +1,92 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq } from 'drizzle-orm'; +import { fail, redirect } from '@sveltejs/kit'; +import type { Actions, PageServerLoad } from './$types'; +import bcrypt from 'bcrypt'; + +export const load: PageServerLoad = async ({ locals }) => { + // If already logged in, redirect them + if (locals.user) { + throw redirect(303, '/'); + } + return {}; +}; + +export const actions: Actions = { + default: async ({ request, cookies, url }) => { + const data = await request.formData(); + const username = data.get('username')?.toString().trim(); + const password = data.get('password')?.toString(); + + if (!username || !password) { + return fail(400, { + success: false, + error: 'Utilizador e palavra-passe são obrigatórios.' + }); + } + + try { + // Find user + const user = db + .select() + .from(schema.users) + .where(eq(schema.users.username, username)) + .get(); + + if (!user) { + return fail(400, { + success: false, + error: 'Utilizador ou palavra-passe incorretos.' + }); + } + + // Verify password hash + const passwordValid = bcrypt.compareSync(password, user.passwordHash); + if (!passwordValid) { + return fail(400, { + success: false, + error: 'Utilizador ou palavra-passe incorretos.' + }); + } + + // Create session (expires in 7 days) + const sessionId = crypto.randomUUID(); + const expiresAt = Date.now() + 7 * 24 * 60 * 60 * 1000; + + db.insert(schema.sessions) + .values({ + id: sessionId, + userId: user.id, + expiresAt + }) + .run(); + + // Set session cookie + cookies.set('session', sessionId, { + path: '/', + httpOnly: true, + sameSite: 'lax', + secure: true, + maxAge: 60 * 60 * 24 * 7 // 7 days in seconds + }); + + // Redirect + const redirectTo = url.searchParams.get('redirectTo') || ''; + if (redirectTo && redirectTo.startsWith('/')) { + throw redirect(303, redirectTo); + } + + throw redirect(303, '/'); + } catch (err) { + if (err && typeof err === 'object' && 'status' in err && err.status === 303) { + throw err; // Re-throw SvelteKit redirect + } + console.error('Error during login action:', err); + return fail(500, { + success: false, + error: 'Ocorreu um erro no servidor. Tente novamente mais tarde.' + }); + } + } +}; diff --git a/src/routes/login/+page.svelte b/src/routes/login/+page.svelte new file mode 100644 index 0000000..09bc01c --- /dev/null +++ b/src/routes/login/+page.svelte @@ -0,0 +1,111 @@ + + + + Login - RefoodOne + + + + + diff --git a/src/routes/logout/+page.server.ts b/src/routes/logout/+page.server.ts new file mode 100644 index 0000000..8dc9955 --- /dev/null +++ b/src/routes/logout/+page.server.ts @@ -0,0 +1,25 @@ +import { db } from '$lib/server/db'; +import * as schema from '$lib/server/db/schema'; +import { eq } from 'drizzle-orm'; +import { redirect } from '@sveltejs/kit'; +import type { Actions } from './$types'; + +export const actions: Actions = { + default: async ({ cookies }) => { + const sessionId = cookies.get('session'); + + if (sessionId) { + try { + // Delete session from DB + db.delete(schema.sessions).where(eq(schema.sessions.id, sessionId)).run(); + } catch (err) { + console.error('Error deleting session during logout:', err); + } + + // Clear cookie + cookies.delete('session', { path: '/' }); + } + + throw redirect(303, '/login'); + } +}; diff --git a/static/logo.png b/static/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..426f5f061f430718d7a0ec464a66fad208a3c8a7 GIT binary patch literal 48225 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 filename.split(/[/\\]/).includes('node_modules') ? undefined : true + }, + kit: { + adapter: adapter(), + typescript: { + config: (config) => ({ + ...config, + include: [...config.include, '../drizzle.config.ts'] + }) + } + } +}; + +export default config; diff --git a/tsconfig.json b/tsconfig.json new file mode 100644 index 0000000..2c2ed3c --- /dev/null +++ b/tsconfig.json @@ -0,0 +1,20 @@ +{ + "extends": "./.svelte-kit/tsconfig.json", + "compilerOptions": { + "rewriteRelativeImportExtensions": true, + "allowJs": true, + "checkJs": true, + "esModuleInterop": true, + "forceConsistentCasingInFileNames": true, + "resolveJsonModule": true, + "skipLibCheck": true, + "sourceMap": true, + "strict": true, + "moduleResolution": "bundler" + } + // Path aliases are handled by https://svelte.dev/docs/kit/configuration#alias + // except $lib which is handled by https://svelte.dev/docs/kit/configuration#files + // + // To make changes to top-level options such as include and exclude, we recommend extending + // the generated config; see https://svelte.dev/docs/kit/configuration#typescript +} diff --git a/vite.config.ts b/vite.config.ts new file mode 100644 index 0000000..bbf8c7d --- /dev/null +++ b/vite.config.ts @@ -0,0 +1,6 @@ +import { sveltekit } from '@sveltejs/kit/vite'; +import { defineConfig } from 'vite'; + +export default defineConfig({ + plugins: [sveltekit()] +});