mirror of
https://github.com/umami-software/umami.git
synced 2025-12-06 01:18:00 +01:00
Merge branch 'dev' into analytics
This commit is contained in:
commit
54dbb43b5c
29 changed files with 810 additions and 11176 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
|
@ -18,6 +18,7 @@ node_modules
|
|||
/public/script.js
|
||||
/geo
|
||||
/dist
|
||||
src/generated/prisma/
|
||||
|
||||
# misc
|
||||
.DS_Store
|
||||
|
|
|
|||
16
README.md
16
README.md
|
|
@ -38,18 +38,12 @@ A detailed getting started guide can be found at [umami.is/docs](https://umami.i
|
|||
- A server with Node.js version 18.18 or newer
|
||||
- A database. Umami supports [MariaDB](https://www.mariadb.org/) (minimum v10.5), [MySQL](https://www.mysql.com/) (minimum v8.0) and [PostgreSQL](https://www.postgresql.org/) (minimum v12.14) databases.
|
||||
|
||||
### Install Yarn
|
||||
|
||||
```bash
|
||||
npm install -g yarn
|
||||
```
|
||||
|
||||
### Get the Source Code and Install Packages
|
||||
|
||||
```bash
|
||||
git clone https://github.com/umami-software/umami.git
|
||||
cd umami
|
||||
yarn install
|
||||
npm install
|
||||
```
|
||||
|
||||
### Configure Umami
|
||||
|
|
@ -70,7 +64,7 @@ mysql://username:mypassword@localhost:3306/mydb
|
|||
### Build the Application
|
||||
|
||||
```bash
|
||||
yarn build
|
||||
npm build
|
||||
```
|
||||
|
||||
*The build step will create tables in your database if you are installing for the first time. It will also create a login user with username **admin** and password **umami**.*
|
||||
|
|
@ -78,7 +72,7 @@ yarn build
|
|||
### Start the Application
|
||||
|
||||
```bash
|
||||
yarn start
|
||||
npm run start
|
||||
```
|
||||
|
||||
*By default, this will launch the application on `http://localhost:3000`. You will need to either [proxy](https://docs.nginx.com/nginx/admin-guide/web-server/reverse-proxy/) requests from your web server or change the [port](https://nextjs.org/docs/api-reference/cli#production) to serve the application directly.*
|
||||
|
|
@ -113,8 +107,8 @@ To get the latest features, simply do a pull, install any new dependencies, and
|
|||
|
||||
```bash
|
||||
git pull
|
||||
yarn install
|
||||
yarn build
|
||||
npm install
|
||||
npm run build
|
||||
```
|
||||
|
||||
To update the Docker image, simply pull the new images and rebuild:
|
||||
|
|
|
|||
103
db/clickhouse/migrations/07_add_distinct_id.sql
Normal file
103
db/clickhouse/migrations/07_add_distinct_id.sql
Normal file
|
|
@ -0,0 +1,103 @@
|
|||
-- add tag column
|
||||
ALTER TABLE umami.website_event ADD COLUMN "distinct_id" String AFTER "tag";
|
||||
ALTER TABLE umami.website_event_stats_hourly ADD COLUMN "distinct_id" String AFTER "tag";
|
||||
ALTER TABLE umami.session_data ADD COLUMN "distinct_id" String AFTER "data_type";
|
||||
|
||||
-- update materialized view
|
||||
DROP TABLE umami.website_event_stats_hourly_mv;
|
||||
|
||||
CREATE MATERIALIZED VIEW umami.website_event_stats_hourly_mv
|
||||
TO umami.website_event_stats_hourly
|
||||
AS
|
||||
SELECT
|
||||
website_id,
|
||||
session_id,
|
||||
visit_id,
|
||||
hostname,
|
||||
browser,
|
||||
os,
|
||||
device,
|
||||
screen,
|
||||
language,
|
||||
country,
|
||||
region,
|
||||
city,
|
||||
entry_url,
|
||||
exit_url,
|
||||
url_paths as url_path,
|
||||
url_query,
|
||||
utm_source,
|
||||
utm_medium,
|
||||
utm_campaign,
|
||||
utm_content,
|
||||
utm_term,
|
||||
referrer_domain,
|
||||
page_title,
|
||||
gclid,
|
||||
fbclid,
|
||||
msclkid,
|
||||
ttclid,
|
||||
li_fat_id,
|
||||
twclid,
|
||||
event_type,
|
||||
event_name,
|
||||
views,
|
||||
min_time,
|
||||
max_time,
|
||||
tag,
|
||||
distinct_id,
|
||||
timestamp as created_at
|
||||
FROM (SELECT
|
||||
website_id,
|
||||
session_id,
|
||||
visit_id,
|
||||
hostname,
|
||||
browser,
|
||||
os,
|
||||
device,
|
||||
screen,
|
||||
language,
|
||||
country,
|
||||
region,
|
||||
city,
|
||||
argMinState(url_path, created_at) entry_url,
|
||||
argMaxState(url_path, created_at) exit_url,
|
||||
arrayFilter(x -> x != '', groupArray(url_path)) as url_paths,
|
||||
arrayFilter(x -> x != '', groupArray(url_query)) url_query,
|
||||
arrayFilter(x -> x != '', groupArray(utm_source)) utm_source,
|
||||
arrayFilter(x -> x != '', groupArray(utm_medium)) utm_medium,
|
||||
arrayFilter(x -> x != '', groupArray(utm_campaign)) utm_campaign,
|
||||
arrayFilter(x -> x != '', groupArray(utm_content)) utm_content,
|
||||
arrayFilter(x -> x != '', groupArray(utm_term)) utm_term,
|
||||
arrayFilter(x -> x != '', groupArray(referrer_domain)) referrer_domain,
|
||||
arrayFilter(x -> x != '', groupArray(page_title)) page_title,
|
||||
arrayFilter(x -> x != '', groupArray(gclid)) gclid,
|
||||
arrayFilter(x -> x != '', groupArray(fbclid)) fbclid,
|
||||
arrayFilter(x -> x != '', groupArray(msclkid)) msclkid,
|
||||
arrayFilter(x -> x != '', groupArray(ttclid)) ttclid,
|
||||
arrayFilter(x -> x != '', groupArray(li_fat_id)) li_fat_id,
|
||||
arrayFilter(x -> x != '', groupArray(twclid)) twclid,
|
||||
event_type,
|
||||
if(event_type = 2, groupArray(event_name), []) event_name,
|
||||
sumIf(1, event_type = 1) views,
|
||||
min(created_at) min_time,
|
||||
max(created_at) max_time,
|
||||
arrayFilter(x -> x != '', groupArray(tag)) tag,
|
||||
distinct_id,
|
||||
toStartOfHour(created_at) timestamp
|
||||
FROM umami.website_event
|
||||
GROUP BY website_id,
|
||||
session_id,
|
||||
visit_id,
|
||||
hostname,
|
||||
browser,
|
||||
os,
|
||||
device,
|
||||
screen,
|
||||
language,
|
||||
country,
|
||||
region,
|
||||
city,
|
||||
event_type,
|
||||
distinct_id,
|
||||
timestamp);
|
||||
|
|
@ -38,6 +38,7 @@ CREATE TABLE umami.website_event
|
|||
event_type UInt32,
|
||||
event_name String,
|
||||
tag String,
|
||||
distinct_id String,
|
||||
created_at DateTime('UTC'),
|
||||
job_id Nullable(UUID)
|
||||
)
|
||||
|
|
@ -75,6 +76,7 @@ CREATE TABLE umami.session_data
|
|||
number_value Nullable(Decimal64(4)),
|
||||
date_value Nullable(DateTime('UTC')),
|
||||
data_type UInt32,
|
||||
distinct_id String,
|
||||
created_at DateTime('UTC'),
|
||||
job_id Nullable(UUID)
|
||||
)
|
||||
|
|
@ -120,6 +122,7 @@ CREATE TABLE umami.website_event_stats_hourly
|
|||
min_time SimpleAggregateFunction(min, DateTime('UTC')),
|
||||
max_time SimpleAggregateFunction(max, DateTime('UTC')),
|
||||
tag SimpleAggregateFunction(groupArrayArray, Array(String)),
|
||||
distinct_id,
|
||||
created_at Datetime('UTC')
|
||||
)
|
||||
ENGINE = AggregatingMergeTree
|
||||
|
|
@ -172,6 +175,7 @@ SELECT
|
|||
min_time,
|
||||
max_time,
|
||||
tag,
|
||||
distinct_id,
|
||||
timestamp as created_at
|
||||
FROM (SELECT
|
||||
website_id,
|
||||
|
|
@ -209,6 +213,7 @@ FROM (SELECT
|
|||
min(created_at) min_time,
|
||||
max(created_at) max_time,
|
||||
arrayFilter(x -> x != '', groupArray(tag)) tag,
|
||||
distinct_id String,
|
||||
toStartOfHour(created_at) timestamp
|
||||
FROM umami.website_event
|
||||
GROUP BY website_id,
|
||||
|
|
@ -224,6 +229,7 @@ GROUP BY website_id,
|
|||
region,
|
||||
city,
|
||||
event_type,
|
||||
distinct_id,
|
||||
timestamp);
|
||||
|
||||
-- projections
|
||||
|
|
|
|||
5
db/mysql/migrations/10_add_distinct_id/migration.sql
Normal file
5
db/mysql/migrations/10_add_distinct_id/migration.sql
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
-- AlterTable
|
||||
ALTER TABLE `session` ADD COLUMN `distinct_id` VARCHAR(50) NULL;
|
||||
|
||||
-- AlterTable
|
||||
ALTER TABLE `session_data` ADD COLUMN `distinct_id` VARCHAR(50) NULL;
|
||||
|
|
@ -1,3 +1,3 @@
|
|||
# Please do not edit this file manually
|
||||
# It should be added in your version-control system (e.g., Git)
|
||||
provider = "mysql"
|
||||
provider = "mysql"
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
generator client {
|
||||
provider = "prisma-client-js"
|
||||
output = "../src/generated/prisma"
|
||||
binaryTargets = ["native"]
|
||||
}
|
||||
|
||||
|
|
@ -29,17 +30,18 @@ model User {
|
|||
}
|
||||
|
||||
model Session {
|
||||
id String @id @unique @map("session_id") @db.VarChar(36)
|
||||
websiteId String @map("website_id") @db.VarChar(36)
|
||||
browser String? @db.VarChar(20)
|
||||
os String? @db.VarChar(20)
|
||||
device String? @db.VarChar(20)
|
||||
screen String? @db.VarChar(11)
|
||||
language String? @db.VarChar(35)
|
||||
country String? @db.Char(2)
|
||||
region String? @db.Char(20)
|
||||
city String? @db.VarChar(50)
|
||||
createdAt DateTime? @default(now()) @map("created_at") @db.Timestamp(0)
|
||||
id String @id @unique @map("session_id") @db.VarChar(36)
|
||||
websiteId String @map("website_id") @db.VarChar(36)
|
||||
browser String? @db.VarChar(20)
|
||||
os String? @db.VarChar(20)
|
||||
device String? @db.VarChar(20)
|
||||
screen String? @db.VarChar(11)
|
||||
language String? @db.VarChar(35)
|
||||
country String? @db.Char(2)
|
||||
region String? @db.Char(20)
|
||||
city String? @db.VarChar(50)
|
||||
distinctId String? @map("distinct_id") @db.VarChar(50)
|
||||
createdAt DateTime? @default(now()) @map("created_at") @db.Timestamp(0)
|
||||
|
||||
websiteEvent WebsiteEvent[]
|
||||
sessionData SessionData[]
|
||||
|
|
@ -165,6 +167,7 @@ model SessionData {
|
|||
numberValue Decimal? @map("number_value") @db.Decimal(19, 4)
|
||||
dateValue DateTime? @map("date_value") @db.Timestamp(0)
|
||||
dataType Int @map("data_type") @db.UnsignedInt
|
||||
distinctId String? @map("distinct_id") @db.VarChar(50)
|
||||
createdAt DateTime? @default(now()) @map("created_at") @db.Timestamp(0)
|
||||
|
||||
website Website @relation(fields: [websiteId], references: [id])
|
||||
|
|
|
|||
|
|
@ -0,0 +1,5 @@
|
|||
-- AlterTable
|
||||
ALTER TABLE "session" ADD COLUMN "distinct_id" VARCHAR(50);
|
||||
|
||||
-- AlterTable
|
||||
ALTER TABLE "session_data" ADD COLUMN "distinct_id" VARCHAR(50);
|
||||
|
|
@ -1,3 +1,3 @@
|
|||
# Please do not edit this file manually
|
||||
# It should be added in your version-control system (e.g., Git)
|
||||
provider = "postgresql"
|
||||
provider = "postgresql"
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
generator client {
|
||||
provider = "prisma-client-js"
|
||||
output = "../src/generated/prisma"
|
||||
binaryTargets = ["native"]
|
||||
}
|
||||
|
||||
|
|
@ -29,17 +30,18 @@ model User {
|
|||
}
|
||||
|
||||
model Session {
|
||||
id String @id @unique @map("session_id") @db.Uuid
|
||||
websiteId String @map("website_id") @db.Uuid
|
||||
browser String? @db.VarChar(20)
|
||||
os String? @db.VarChar(20)
|
||||
device String? @db.VarChar(20)
|
||||
screen String? @db.VarChar(11)
|
||||
language String? @db.VarChar(35)
|
||||
country String? @db.Char(2)
|
||||
region String? @db.VarChar(20)
|
||||
city String? @db.VarChar(50)
|
||||
createdAt DateTime? @default(now()) @map("created_at") @db.Timestamptz(6)
|
||||
id String @id @unique @map("session_id") @db.Uuid
|
||||
websiteId String @map("website_id") @db.Uuid
|
||||
browser String? @db.VarChar(20)
|
||||
os String? @db.VarChar(20)
|
||||
device String? @db.VarChar(20)
|
||||
screen String? @db.VarChar(11)
|
||||
language String? @db.VarChar(35)
|
||||
country String? @db.Char(2)
|
||||
region String? @db.VarChar(20)
|
||||
city String? @db.VarChar(50)
|
||||
distinctId String? @map("distinct_id") @db.VarChar(50)
|
||||
createdAt DateTime? @default(now()) @map("created_at") @db.Timestamptz(6)
|
||||
|
||||
websiteEvent WebsiteEvent[]
|
||||
sessionData SessionData[]
|
||||
|
|
@ -165,6 +167,7 @@ model SessionData {
|
|||
numberValue Decimal? @map("number_value") @db.Decimal(19, 4)
|
||||
dateValue DateTime? @map("date_value") @db.Timestamptz(6)
|
||||
dataType Int @map("data_type") @db.Integer
|
||||
distinctId String? @map("distinct_id") @db.VarChar(50)
|
||||
createdAt DateTime? @default(now()) @map("created_at") @db.Timestamptz(6)
|
||||
|
||||
website Website @relation(fields: [websiteId], references: [id])
|
||||
|
|
|
|||
|
|
@ -1,8 +1,6 @@
|
|||
import dotenv from 'dotenv';
|
||||
import 'dotenv/config';
|
||||
import { createRequire } from 'module';
|
||||
|
||||
dotenv.config();
|
||||
|
||||
const require = createRequire(import.meta.url);
|
||||
const pkg = require('./package.json');
|
||||
|
||||
|
|
|
|||
|
|
@ -72,11 +72,10 @@
|
|||
"@dicebear/core": "^9.2.1",
|
||||
"@fontsource/inter": "^4.5.15",
|
||||
"@hello-pangea/dnd": "^17.0.0",
|
||||
"@prisma/client": "6.1.0",
|
||||
"@prisma/extension-read-replicas": "^0.4.0",
|
||||
"@prisma/client": "6.6.0",
|
||||
"@prisma/extension-read-replicas": "^0.4.1",
|
||||
"@react-spring/web": "^9.7.3",
|
||||
"@tanstack/react-query": "^5.28.6",
|
||||
"@umami/prisma-client": "^0.14.0",
|
||||
"@umami/redis-client": "^0.26.0",
|
||||
"bcryptjs": "^2.4.3",
|
||||
"chalk": "^4.1.1",
|
||||
|
|
@ -107,7 +106,7 @@
|
|||
"next": "15.3.0",
|
||||
"node-fetch": "^3.2.8",
|
||||
"npm-run-all": "^4.1.5",
|
||||
"prisma": "6.1.0",
|
||||
"prisma": "6.6.0",
|
||||
"pure-rand": "^6.1.0",
|
||||
"react": "^19.0.0",
|
||||
"react-basics": "^0.126.0",
|
||||
|
|
|
|||
518
pnpm-lock.yaml
generated
518
pnpm-lock.yaml
generated
|
|
@ -27,20 +27,17 @@ importers:
|
|||
specifier: ^17.0.0
|
||||
version: 17.0.0(@types/react@19.1.2)(react-dom@19.1.0(react@19.1.0))(react@19.1.0)
|
||||
'@prisma/client':
|
||||
specifier: 6.1.0
|
||||
version: 6.1.0(prisma@6.1.0)
|
||||
specifier: 6.6.0
|
||||
version: 6.6.0(prisma@6.6.0(typescript@5.8.3))(typescript@5.8.3)
|
||||
'@prisma/extension-read-replicas':
|
||||
specifier: ^0.4.0
|
||||
version: 0.4.1(@prisma/client@6.1.0(prisma@6.1.0))
|
||||
specifier: ^0.4.1
|
||||
version: 0.4.1(@prisma/client@6.6.0(prisma@6.6.0(typescript@5.8.3))(typescript@5.8.3))
|
||||
'@react-spring/web':
|
||||
specifier: ^9.7.3
|
||||
version: 9.7.5(react-dom@19.1.0(react@19.1.0))(react@19.1.0)
|
||||
'@tanstack/react-query':
|
||||
specifier: ^5.28.6
|
||||
version: 5.74.3(react@19.1.0)
|
||||
'@umami/prisma-client':
|
||||
specifier: ^0.14.0
|
||||
version: 0.14.0(@prisma/client@6.1.0(prisma@6.1.0))(@prisma/extension-read-replicas@0.4.1(@prisma/client@6.1.0(prisma@6.1.0)))
|
||||
'@umami/redis-client':
|
||||
specifier: ^0.26.0
|
||||
version: 0.26.0
|
||||
|
|
@ -132,8 +129,8 @@ importers:
|
|||
specifier: ^4.1.5
|
||||
version: 4.1.5
|
||||
prisma:
|
||||
specifier: 6.1.0
|
||||
version: 6.1.0
|
||||
specifier: 6.6.0
|
||||
version: 6.6.0(typescript@5.8.3)
|
||||
pure-rand:
|
||||
specifier: ^6.1.0
|
||||
version: 6.1.0
|
||||
|
|
@ -355,6 +352,47 @@ importers:
|
|||
specifier: ^5.5.3
|
||||
version: 5.8.3
|
||||
|
||||
dist:
|
||||
dependencies:
|
||||
'@tanstack/react-query':
|
||||
specifier: ^4.33.0
|
||||
version: 4.36.1(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
|
||||
classnames:
|
||||
specifier: ^2.3.1
|
||||
version: 2.5.1
|
||||
colord:
|
||||
specifier: ^2.9.2
|
||||
version: 2.9.3
|
||||
date-fns-tz:
|
||||
specifier: ^1.1.4
|
||||
version: 1.3.8(date-fns@2.30.0)
|
||||
immer:
|
||||
specifier: ^9.0.12
|
||||
version: 9.0.21
|
||||
moment-timezone:
|
||||
specifier: ^0.5.35
|
||||
version: 0.5.48
|
||||
next:
|
||||
specifier: ^13.4.0
|
||||
version: 13.5.11(@babel/core@7.26.10)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
|
||||
next-basics:
|
||||
specifier: ^0.36.0
|
||||
version: 0.36.0(next@13.5.11(@babel/core@7.26.10)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
|
||||
react:
|
||||
specifier: ^18.2.0
|
||||
version: 18.3.1
|
||||
react-dom:
|
||||
specifier: ^18.2.0
|
||||
version: 18.3.1(react@18.3.1)
|
||||
react-intl:
|
||||
specifier: ^5.24.7
|
||||
version: 5.25.1(react@18.3.1)(typescript@4.9.5)
|
||||
zustand:
|
||||
specifier: ^4.3.8
|
||||
version: 4.5.6(@types/react@19.1.2)(immer@9.0.21)(react@18.3.1)
|
||||
|
||||
src/generated/prisma: {}
|
||||
|
||||
packages:
|
||||
|
||||
'@ampproject/remapping@2.3.0':
|
||||
|
|
@ -1509,6 +1547,9 @@ packages:
|
|||
'@formatjs/ecma402-abstract@2.2.4':
|
||||
resolution: {integrity: sha512-lFyiQDVvSbQOpU+WFd//ILolGj4UgA/qXrKeZxdV14uKiAUiPAtX6XAn7WBCRi7Mx6I7EybM9E5yYn4BIpZWYg==}
|
||||
|
||||
'@formatjs/fast-memoize@1.2.1':
|
||||
resolution: {integrity: sha512-Rg0e76nomkz3vF9IPlKeV+Qynok0r7YZjL6syLz4/urSg0IbjPZCB/iYUMNsYA643gh4mgrX3T7KEIFIxJBQeg==}
|
||||
|
||||
'@formatjs/fast-memoize@2.2.3':
|
||||
resolution: {integrity: sha512-3jeJ+HyOfu8osl3GNSL4vVHUuWFXR03Iz9jjgI7RwjG6ysu/Ymdr0JRCPHfF5yGbTE6JCrd63EpvX1/WybYRbA==}
|
||||
|
||||
|
|
@ -1524,9 +1565,15 @@ packages:
|
|||
'@formatjs/icu-skeleton-parser@1.8.8':
|
||||
resolution: {integrity: sha512-vHwK3piXwamFcx5YQdCdJxUQ1WdTl6ANclt5xba5zLGDv5Bsur7qz8AD7BevaKxITwpgDeU0u8My3AIibW9ywA==}
|
||||
|
||||
'@formatjs/intl-displaynames@5.4.3':
|
||||
resolution: {integrity: sha512-4r12A3mS5dp5hnSaQCWBuBNfi9Amgx2dzhU4lTFfhSxgb5DOAiAbMpg6+7gpWZgl4ahsj3l2r/iHIjdmdXOE2Q==}
|
||||
|
||||
'@formatjs/intl-displaynames@6.8.5':
|
||||
resolution: {integrity: sha512-85b+GdAKCsleS6cqVxf/Aw/uBd+20EM0wDpgaxzHo3RIR3bxF4xCJqH/Grbzx8CXurTgDDZHPdPdwJC+May41w==}
|
||||
|
||||
'@formatjs/intl-listformat@6.5.3':
|
||||
resolution: {integrity: sha512-ozpz515F/+3CU+HnLi5DYPsLa6JoCfBggBSSg/8nOB5LYSFW9+ZgNQJxJ8tdhKYeODT+4qVHX27EeJLoxLGLNg==}
|
||||
|
||||
'@formatjs/intl-listformat@7.7.5':
|
||||
resolution: {integrity: sha512-Wzes10SMNeYgnxYiKsda4rnHP3Q3II4XT2tZyOgnH5fWuHDtIkceuWlRQNsvrI3uiwP4hLqp2XdQTCsfkhXulg==}
|
||||
|
||||
|
|
@ -1547,6 +1594,14 @@ packages:
|
|||
typescript:
|
||||
optional: true
|
||||
|
||||
'@formatjs/intl@2.2.1':
|
||||
resolution: {integrity: sha512-vgvyUOOrzqVaOFYzTf2d3+ToSkH2JpR7x/4U1RyoHQLmvEaTQvXJ7A2qm1Iy3brGNXC/+/7bUlc3lpH+h/LOJA==}
|
||||
peerDependencies:
|
||||
typescript: ^4.5
|
||||
peerDependenciesMeta:
|
||||
typescript:
|
||||
optional: true
|
||||
|
||||
'@formatjs/ts-transformer@2.13.0':
|
||||
resolution: {integrity: sha512-mu7sHXZk1NWZrQ3eUqugpSYo8x5/tXkrI4uIbFqCEC0eNgQaIcoKgVeDFgDAcgG+cEme2atAUYSFF+DFWC4org==}
|
||||
peerDependencies:
|
||||
|
|
@ -1804,54 +1859,111 @@ packages:
|
|||
resolution: {integrity: sha512-j/Jt/MMFy70f1LIa6qkviNWVoEIoF9ZICdDC3TF/IvStxWHGAYHm8pkqqbi1VqzjUEDUNu1ZGjo+VElZyenRBg==}
|
||||
engines: {node: '>=18.0.0'}
|
||||
|
||||
'@next/env@13.5.11':
|
||||
resolution: {integrity: sha512-fbb2C7HChgM7CemdCY+y3N1n8pcTKdqtQLbC7/EQtPdLvlMUT9JX/dBYl8MMZAtYG4uVMyPFHXckb68q/NRwqg==}
|
||||
|
||||
'@next/env@15.3.0':
|
||||
resolution: {integrity: sha512-6mDmHX24nWlHOlbwUiAOmMyY7KELimmi+ed8qWcJYjqXeC+G6JzPZ3QosOAfjNwgMIzwhXBiRiCgdh8axTTdTA==}
|
||||
|
||||
'@next/eslint-plugin-next@14.2.28':
|
||||
resolution: {integrity: sha512-GQUPA1bTZy5qZdPV5MOHB18465azzhg8xm5o2SqxMF+h1rWNjB43y6xmIPHG5OV2OiU3WxuINpusXom49DdaIQ==}
|
||||
|
||||
'@next/swc-darwin-arm64@13.5.9':
|
||||
resolution: {integrity: sha512-pVyd8/1y1l5atQRvOaLOvfbmRwefxLhqQOzYo/M7FQ5eaRwA1+wuCn7t39VwEgDd7Aw1+AIWwd+MURXUeXhwDw==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [darwin]
|
||||
|
||||
'@next/swc-darwin-arm64@15.3.0':
|
||||
resolution: {integrity: sha512-PDQcByT0ZfF2q7QR9d+PNj3wlNN4K6Q8JoHMwFyk252gWo4gKt7BF8Y2+KBgDjTFBETXZ/TkBEUY7NIIY7A/Kw==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [darwin]
|
||||
|
||||
'@next/swc-darwin-x64@13.5.9':
|
||||
resolution: {integrity: sha512-DwdeJqP7v8wmoyTWPbPVodTwCybBZa02xjSJ6YQFIFZFZ7dFgrieKW4Eo0GoIcOJq5+JxkQyejmI+8zwDp3pwA==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [darwin]
|
||||
|
||||
'@next/swc-darwin-x64@15.3.0':
|
||||
resolution: {integrity: sha512-m+eO21yg80En8HJ5c49AOQpFDq+nP51nu88ZOMCorvw3g//8g1JSUsEiPSiFpJo1KCTQ+jm9H0hwXK49H/RmXg==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [darwin]
|
||||
|
||||
'@next/swc-linux-arm64-gnu@13.5.9':
|
||||
resolution: {integrity: sha512-wdQsKsIsGSNdFojvjW3Ozrh8Q00+GqL3wTaMjDkQxVtRbAqfFBtrLPO0IuWChVUP2UeuQcHpVeUvu0YgOP00+g==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-linux-arm64-gnu@15.3.0':
|
||||
resolution: {integrity: sha512-H0Kk04ZNzb6Aq/G6e0un4B3HekPnyy6D+eUBYPJv9Abx8KDYgNMWzKt4Qhj57HXV3sTTjsfc1Trc1SxuhQB+Tg==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-linux-arm64-musl@13.5.9':
|
||||
resolution: {integrity: sha512-6VpS+bodQqzOeCwGxoimlRoosiWlSc0C224I7SQWJZoyJuT1ChNCo+45QQH+/GtbR/s7nhaUqmiHdzZC9TXnXA==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-linux-arm64-musl@15.3.0':
|
||||
resolution: {integrity: sha512-k8GVkdMrh/+J9uIv/GpnHakzgDQhrprJ/FbGQvwWmstaeFG06nnAoZCJV+wO/bb603iKV1BXt4gHG+s2buJqZA==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-linux-x64-gnu@13.5.9':
|
||||
resolution: {integrity: sha512-XxG3yj61WDd28NA8gFASIR+2viQaYZEFQagEodhI/R49gXWnYhiflTeeEmCn7Vgnxa/OfK81h1gvhUZ66lozpw==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-linux-x64-gnu@15.3.0':
|
||||
resolution: {integrity: sha512-ZMQ9yzDEts/vkpFLRAqfYO1wSpIJGlQNK9gZ09PgyjBJUmg8F/bb8fw2EXKgEaHbCc4gmqMpDfh+T07qUphp9A==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-linux-x64-musl@13.5.9':
|
||||
resolution: {integrity: sha512-/dnscWqfO3+U8asd+Fc6dwL2l9AZDl7eKtPNKW8mKLh4Y4wOpjJiamhe8Dx+D+Oq0GYVjuW0WwjIxYWVozt2bA==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-linux-x64-musl@15.3.0':
|
||||
resolution: {integrity: sha512-RFwq5VKYTw9TMr4T3e5HRP6T4RiAzfDJ6XsxH8j/ZeYq2aLsBqCkFzwMI0FmnSsLaUbOb46Uov0VvN3UciHX5A==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
|
||||
'@next/swc-win32-arm64-msvc@13.5.9':
|
||||
resolution: {integrity: sha512-T/iPnyurOK5a4HRUcxAlss8uzoEf5h9tkd+W2dSWAfzxv8WLKlUgbfk+DH43JY3Gc2xK5URLuXrxDZ2mGfk/jw==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [win32]
|
||||
|
||||
'@next/swc-win32-arm64-msvc@15.3.0':
|
||||
resolution: {integrity: sha512-a7kUbqa/k09xPjfCl0RSVAvEjAkYBYxUzSVAzk2ptXiNEL+4bDBo9wNC43G/osLA/EOGzG4CuNRFnQyIHfkRgQ==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [win32]
|
||||
|
||||
'@next/swc-win32-ia32-msvc@13.5.9':
|
||||
resolution: {integrity: sha512-BLiPKJomaPrTAb7ykjA0LPcuuNMLDVK177Z1xe0nAem33+9FIayU4k/OWrtSn9SAJW/U60+1hoey5z+KCHdRLQ==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [ia32]
|
||||
os: [win32]
|
||||
|
||||
'@next/swc-win32-x64-msvc@13.5.9':
|
||||
resolution: {integrity: sha512-/72/dZfjXXNY/u+n8gqZDjI6rxKMpYsgBBYNZKWOQw0BpBF7WCnPflRy3ZtvQ2+IYI3ZH2bPyj7K+6a6wNk90Q==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [win32]
|
||||
|
||||
'@next/swc-win32-x64-msvc@15.3.0':
|
||||
resolution: {integrity: sha512-vHUQS4YVGJPmpjn7r5lEZuMhK5UQBNBRSB+iGDvJjaNk649pTIcRluDWNb9siunyLLiu/LDPHfvxBtNamyuLTw==}
|
||||
engines: {node: '>= 10'}
|
||||
|
|
@ -1878,34 +1990,40 @@ packages:
|
|||
resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==}
|
||||
engines: {node: '>=14'}
|
||||
|
||||
'@prisma/client@6.1.0':
|
||||
resolution: {integrity: sha512-AbQYc5+EJKm1Ydfq3KxwcGiy7wIbm4/QbjCKWWoNROtvy7d6a3gmAGkKjK0iUCzh+rHV8xDhD5Cge8ke/kiy5Q==}
|
||||
'@prisma/client@6.6.0':
|
||||
resolution: {integrity: sha512-vfp73YT/BHsWWOAuthKQ/1lBgESSqYqAWZEYyTdGXyFAHpmewwWL2Iz6ErIzkj4aHbuc6/cGSsE6ZY+pBO04Cg==}
|
||||
engines: {node: '>=18.18'}
|
||||
peerDependencies:
|
||||
prisma: '*'
|
||||
typescript: '>=5.1.0'
|
||||
peerDependenciesMeta:
|
||||
prisma:
|
||||
optional: true
|
||||
typescript:
|
||||
optional: true
|
||||
|
||||
'@prisma/debug@6.1.0':
|
||||
resolution: {integrity: sha512-0himsvcM4DGBTtvXkd2Tggv6sl2JyUYLzEGXXleFY+7Kp6rZeSS3hiTW9mwtUlXrwYbJP6pwlVNB7jYElrjWUg==}
|
||||
'@prisma/config@6.6.0':
|
||||
resolution: {integrity: sha512-d8FlXRHsx72RbN8nA2QCRORNv5AcUnPXgtPvwhXmYkQSMF/j9cKaJg+9VcUzBRXGy9QBckNzEQDEJZdEOZ+ubA==}
|
||||
|
||||
'@prisma/engines-version@6.1.0-21.11f085a2012c0f4778414c8db2651556ee0ef959':
|
||||
resolution: {integrity: sha512-PdJqmYM2Fd8K0weOOtQThWylwjsDlTig+8Pcg47/jszMuLL9iLIaygC3cjWJLda69siRW4STlCTMSgOjZzvKPQ==}
|
||||
'@prisma/debug@6.6.0':
|
||||
resolution: {integrity: sha512-DL6n4IKlW5k2LEXzpN60SQ1kP/F6fqaCgU/McgaYsxSf43GZ8lwtmXLke9efS+L1uGmrhtBUP4npV/QKF8s2ZQ==}
|
||||
|
||||
'@prisma/engines@6.1.0':
|
||||
resolution: {integrity: sha512-GnYJbCiep3Vyr1P/415ReYrgJUjP79fBNc1wCo7NP6Eia0CzL2Ot9vK7Infczv3oK7JLrCcawOSAxFxNFsAERQ==}
|
||||
'@prisma/engines-version@6.6.0-53.f676762280b54cd07c770017ed3711ddde35f37a':
|
||||
resolution: {integrity: sha512-JzRaQ5Em1fuEcbR3nUsMNYaIYrOT1iMheenjCvzZblJcjv/3JIuxXN7RCNT5i6lRkLodW5ojCGhR7n5yvnNKrw==}
|
||||
|
||||
'@prisma/engines@6.6.0':
|
||||
resolution: {integrity: sha512-nC0IV4NHh7500cozD1fBoTwTD1ydJERndreIjpZr/S3mno3P6tm8qnXmIND5SwUkibNeSJMpgl4gAnlqJ/gVlg==}
|
||||
|
||||
'@prisma/extension-read-replicas@0.4.1':
|
||||
resolution: {integrity: sha512-mCMDloqUKUwx2o5uedTs1FHX3Nxdt1GdRMoeyp1JggjiwOALmIYWhxfIN08M2BZ0w8SKwvJqicJZMjkQYkkijw==}
|
||||
peerDependencies:
|
||||
'@prisma/client': ^6.5.0
|
||||
|
||||
'@prisma/fetch-engine@6.1.0':
|
||||
resolution: {integrity: sha512-asdFi7TvPlEZ8CzSZ/+Du5wZ27q6OJbRSXh+S8ISZguu+S9KtS/gP7NeXceZyb1Jv1SM1S5YfiCv+STDsG6rrg==}
|
||||
'@prisma/fetch-engine@6.6.0':
|
||||
resolution: {integrity: sha512-Ohfo8gKp05LFLZaBlPUApM0M7k43a0jmo86YY35u1/4t+vuQH9mRGU7jGwVzGFY3v+9edeb/cowb1oG4buM1yw==}
|
||||
|
||||
'@prisma/get-platform@6.1.0':
|
||||
resolution: {integrity: sha512-ia8bNjboBoHkmKGGaWtqtlgQOhCi7+f85aOkPJKgNwWvYrT6l78KgojLekE8zMhVk0R9lWcifV0Pf8l3/15V0Q==}
|
||||
'@prisma/get-platform@6.6.0':
|
||||
resolution: {integrity: sha512-3qCwmnT4Jh5WCGUrkWcc6VZaw0JY7eWN175/pcb5Z6FiLZZ3ygY93UX0WuV41bG51a6JN/oBH0uywJ90Y+V5eA==}
|
||||
|
||||
'@react-spring/animated@9.7.5':
|
||||
resolution: {integrity: sha512-Tqrwz7pIlsSDITzxoLS3n/v/YCUHQdOIKtOJf4yL6kYVSDTSmVK1LI1Q3M/uu2Sx4X3pIWF3xLUhlsA6SPNTNg==}
|
||||
|
|
@ -2120,9 +2238,27 @@ packages:
|
|||
'@swc/helpers@0.5.15':
|
||||
resolution: {integrity: sha512-JQ5TuMi45Owi4/BIMAJBoSQoOJu12oOk/gADqlcUL9JEdHB8vyjUSsxqeNXnmXHjYKMi2WcYtezGEEhqUI/E2g==}
|
||||
|
||||
'@swc/helpers@0.5.2':
|
||||
resolution: {integrity: sha512-E4KcWTpoLHqwPHLxidpOqQbcrZVgi0rsmmZXUle1jXmJfuIf/UWpczUJ7MZZ5tlxytgJXyp0w4PGkkeLiuIdZw==}
|
||||
|
||||
'@tanstack/query-core@4.36.1':
|
||||
resolution: {integrity: sha512-DJSilV5+ytBP1FbFcEJovv4rnnm/CokuVvrBEtW/Va9DvuJ3HksbXUJEpI0aV1KtuL4ZoO9AVE6PyNLzF7tLeA==}
|
||||
|
||||
'@tanstack/query-core@5.74.3':
|
||||
resolution: {integrity: sha512-Mqk+5o3qTuAiZML248XpNH8r2cOzl15+LTbUsZQEwvSvn1GU4VQhvqzAbil36p+MBxpr/58oBSnRzhrBevDhfg==}
|
||||
|
||||
'@tanstack/react-query@4.36.1':
|
||||
resolution: {integrity: sha512-y7ySVHFyyQblPl3J3eQBWpXZkliroki3ARnBKsdJchlgt7yJLRDUcf4B8soufgiYt3pEQIkBWBx1N9/ZPIeUWw==}
|
||||
peerDependencies:
|
||||
react: ^16.8.0 || ^17.0.0 || ^18.0.0
|
||||
react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0
|
||||
react-native: '*'
|
||||
peerDependenciesMeta:
|
||||
react-dom:
|
||||
optional: true
|
||||
react-native:
|
||||
optional: true
|
||||
|
||||
'@tanstack/react-query@5.74.3':
|
||||
resolution: {integrity: sha512-QrycUn0wxjVPzITvQvOxFRdhlAwIoOQSuav7qWD4SWCoKCdLbyRZ2vji2GuBq/glaxbF4wBx3fqcYRDOt8KDTA==}
|
||||
peerDependencies:
|
||||
|
|
@ -2358,12 +2494,6 @@ packages:
|
|||
resolution: {integrity: sha512-JJtkDduxLi9bivAB+cYOVMtbkqdPOhZ+ZI5LC47MIRrDV4Yn2o+ZnW10Nkmr28xRpSpdJ6Sm42Hjf2+REYXm0A==}
|
||||
engines: {node: ^16.0.0 || >=18.0.0}
|
||||
|
||||
'@umami/prisma-client@0.14.0':
|
||||
resolution: {integrity: sha512-62aAE5s5m/M1T88JIvOyZk2LzQIJ/iEeF57ewd/qKKNZdgXfP1aib+IAQ74db85vq6TwFyHMaXBeXztNNby5Fw==}
|
||||
peerDependencies:
|
||||
'@prisma/client': ^4.8.0
|
||||
'@prisma/extension-read-replicas': ^0.3.0
|
||||
|
||||
'@umami/redis-client@0.26.0':
|
||||
resolution: {integrity: sha512-j2vxb1gYF5zfk7BkrHgau2MwKsB5ijbQh2w1WoIvbP41cqTMsFm/zUrjhZ0cP1ZxR/riQR1AWxKmqNggYRZ5eA==}
|
||||
|
||||
|
|
@ -3412,6 +3542,11 @@ packages:
|
|||
resolution: {integrity: sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g==}
|
||||
engines: {node: '>= 0.4'}
|
||||
|
||||
esbuild-register@3.6.0:
|
||||
resolution: {integrity: sha512-H2/S7Pm8a9CL1uhp9OvjwrBh5Pvx0H8qVOxNu8Wed9Y7qv56MPtq+GGM8RJpq6glYJn9Wspr8uw7l55uyinNeg==}
|
||||
peerDependencies:
|
||||
esbuild: '>=0.12 <1'
|
||||
|
||||
esbuild@0.25.2:
|
||||
resolution: {integrity: sha512-16854zccKPnC+toMywC+uKNeYSv+/eXkevRAfwRD/G9Cleq66m8XFIrigkbvauLLlCfDL45Q2cWegSg53gGBnQ==}
|
||||
engines: {node: '>=18'}
|
||||
|
|
@ -3857,6 +3992,9 @@ packages:
|
|||
resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==}
|
||||
engines: {node: '>=10.13.0'}
|
||||
|
||||
glob-to-regexp@0.4.1:
|
||||
resolution: {integrity: sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==}
|
||||
|
||||
glob@10.3.10:
|
||||
resolution: {integrity: sha512-fa46+tv1Ak0UPK1TOy/pZrIybNNt4HCv7SDzwyfiOZkvZLEbjsZkJBPtDHVshZjbecAoAGSC20MjLDG/qr679g==}
|
||||
engines: {node: '>=16 || 14 >=14.17'}
|
||||
|
|
@ -4078,6 +4216,9 @@ packages:
|
|||
intl-messageformat@10.7.7:
|
||||
resolution: {integrity: sha512-F134jIoeYMro/3I0h08D0Yt4N9o9pjddU/4IIxMMURqbAtI2wu70X8hvG1V48W49zXHXv3RKSF/po+0fDfsGjA==}
|
||||
|
||||
intl-messageformat@9.13.0:
|
||||
resolution: {integrity: sha512-7sGC7QnSQGa5LZP7bXLDhVDtQOeKGeBFGHF2Y8LVBwYZoQZCgWeKoPGTa5GMG8g/TzDgeXuYJQis7Ggiw2xTOw==}
|
||||
|
||||
ipaddr.js@2.2.0:
|
||||
resolution: {integrity: sha512-Ag3wB2o37wslZS19hZqorUnrnzSkpOVy+IiiDEiTqNubEYpYuHWIf6K4psgN2ZWKExS4xhVCrRVfb/wfW8fWJA==}
|
||||
engines: {node: '>= 10'}
|
||||
|
|
@ -4868,6 +5009,12 @@ packages:
|
|||
resolution: {integrity: sha512-yx8H/1H5AfnufiLnzzPqPf4yr/dKU9IFT1rPVwSkrKWHsQEeVVd6+X+L0nUbXhlEFTu3y/7hu38CFmEVgzvyeg==}
|
||||
engines: {node: '>=10', npm: '>=6'}
|
||||
|
||||
moment-timezone@0.5.48:
|
||||
resolution: {integrity: sha512-f22b8LV1gbTO2ms2j2z13MuPogNoh5UzxL3nzNAYKGraILnbGc9NEE6dyiiiLv46DGRb8A4kg8UKWLjPthxBHw==}
|
||||
|
||||
moment@2.30.1:
|
||||
resolution: {integrity: sha512-uEmtNhbDOrWPFS+hdjFCBfy9f2YoyzRpwcl+DqpC6taX21FzsTLQVbMV/W7PzNSX6x/bhC1zA3c2UQ5NzH6how==}
|
||||
|
||||
ms@2.1.2:
|
||||
resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==}
|
||||
|
||||
|
|
@ -4882,6 +5029,28 @@ packages:
|
|||
natural-compare@1.4.0:
|
||||
resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==}
|
||||
|
||||
next-basics@0.36.0:
|
||||
resolution: {integrity: sha512-Nwou8pCjFuoD/ZxUw9iKC7hhZeWbo/ng0ze74yck3W89MNc/CepwCDziflAHY5XcmIVNmpXOCu9OfmzTdVRPWQ==}
|
||||
peerDependencies:
|
||||
next: ^13.4.0
|
||||
react: ^18.2.0
|
||||
react-dom: ^18.2.0
|
||||
|
||||
next@13.5.11:
|
||||
resolution: {integrity: sha512-WUPJ6WbAX9tdC86kGTu92qkrRdgRqVrY++nwM+shmWQwmyxt4zhZfR59moXSI4N8GDYCBY3lIAqhzjDd4rTC8Q==}
|
||||
engines: {node: '>=16.14.0'}
|
||||
hasBin: true
|
||||
peerDependencies:
|
||||
'@opentelemetry/api': ^1.1.0
|
||||
react: ^18.2.0
|
||||
react-dom: ^18.2.0
|
||||
sass: ^1.3.0
|
||||
peerDependenciesMeta:
|
||||
'@opentelemetry/api':
|
||||
optional: true
|
||||
sass:
|
||||
optional: true
|
||||
|
||||
next@15.3.0:
|
||||
resolution: {integrity: sha512-k0MgP6BsK8cZ73wRjMazl2y2UcXj49ZXLDEgx6BikWuby/CN+nh81qFFI16edgd7xYpe/jj2OZEIwCoqnzz0bQ==}
|
||||
engines: {node: ^18.18.0 || ^19.8.0 || >= 20.0.0}
|
||||
|
|
@ -5587,10 +5756,15 @@ packages:
|
|||
resolution: {integrity: sha512-Pdlw/oPxN+aXdmM9R00JVC9WVFoCLTKJvDVLgmJ+qAffBMxsV85l/Lu7sNx4zSzPyoL2euImuEwHhOXdEgNFZQ==}
|
||||
engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
|
||||
|
||||
prisma@6.1.0:
|
||||
resolution: {integrity: sha512-aFI3Yi+ApUxkwCJJwyQSwpyzUX7YX3ihzuHNHOyv4GJg3X5tQsmRaJEnZ+ZyfHpMtnyahhmXVfbTZ+lS8ZtfKw==}
|
||||
prisma@6.6.0:
|
||||
resolution: {integrity: sha512-SYCUykz+1cnl6Ugd8VUvtTQq5+j1Q7C0CtzKPjQ8JyA2ALh0EEJkMCS+KgdnvKW1lrxjtjCyJSHOOT236mENYg==}
|
||||
engines: {node: '>=18.18'}
|
||||
hasBin: true
|
||||
peerDependencies:
|
||||
typescript: '>=5.1.0'
|
||||
peerDependenciesMeta:
|
||||
typescript:
|
||||
optional: true
|
||||
|
||||
process@0.11.10:
|
||||
resolution: {integrity: sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==}
|
||||
|
|
@ -5648,6 +5822,11 @@ packages:
|
|||
react: ^18.2.0
|
||||
react-dom: ^18.2.0
|
||||
|
||||
react-dom@18.3.1:
|
||||
resolution: {integrity: sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw==}
|
||||
peerDependencies:
|
||||
react: ^18.3.1
|
||||
|
||||
react-dom@19.1.0:
|
||||
resolution: {integrity: sha512-Xs1hdnE+DyKgeHJeJznQmYMIBG3TKIHJJT95Q58nHLSrElKlGQqDTR2HQ9fx5CN/Gk6Vh/kupBTDLU11/nDk/g==}
|
||||
peerDependencies:
|
||||
|
|
@ -5664,6 +5843,15 @@ packages:
|
|||
peerDependencies:
|
||||
react: ^16.8.0 || ^17 || ^18 || ^19
|
||||
|
||||
react-intl@5.25.1:
|
||||
resolution: {integrity: sha512-pkjdQDvpJROoXLMltkP/5mZb0/XqrqLoPGKUCfbdkP8m6U9xbK40K51Wu+a4aQqTEvEK5lHBk0fWzUV72SJ3Hg==}
|
||||
peerDependencies:
|
||||
react: ^16.3.0 || 17 || 18
|
||||
typescript: ^4.5
|
||||
peerDependenciesMeta:
|
||||
typescript:
|
||||
optional: true
|
||||
|
||||
react-intl@6.8.9:
|
||||
resolution: {integrity: sha512-TUfj5E7lyUDvz/GtovC9OMh441kBr08rtIbgh3p0R8iF3hVY+V2W9Am7rb8BpJ/29BH1utJOqOOhmvEVh3GfZg==}
|
||||
peerDependencies:
|
||||
|
|
@ -5714,6 +5902,10 @@ packages:
|
|||
react: ^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 || ^19.0.0
|
||||
react-dom: ^15.0.0 || ^16.0.0 || ^17.0.0 || ^18.0.0 || ^19.0.0
|
||||
|
||||
react@18.3.1:
|
||||
resolution: {integrity: sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==}
|
||||
engines: {node: '>=0.10.0'}
|
||||
|
||||
react@19.1.0:
|
||||
resolution: {integrity: sha512-FS+XFBNvn3GTAWq26joslQgWNoFu08F4kl0J4CgdNKADkdSGXQyTCnKteIAJy96Br6YbpEU1LSzV5dYtjMkMDg==}
|
||||
engines: {node: '>=0.10.0'}
|
||||
|
|
@ -5935,6 +6127,9 @@ packages:
|
|||
safer-buffer@2.1.2:
|
||||
resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==}
|
||||
|
||||
scheduler@0.23.2:
|
||||
resolution: {integrity: sha512-UOShsPwz7NrMUqhR6t0hWjFduvOzbtv7toDH1/hIrfRNIDBnnBWd0CwJTGvTpngVlmwGCdP9/Zl/tVrDqcuYzQ==}
|
||||
|
||||
scheduler@0.26.0:
|
||||
resolution: {integrity: sha512-NlHwttCI/l5gCPR3D1nNXtWABUmBwvZpEQiD4IXSbIDq8BzLIK/7Ir5gTFSGZDUu37K5cMNp0hFtzO38sC7gWA==}
|
||||
|
||||
|
|
@ -6187,6 +6382,19 @@ packages:
|
|||
style-search@0.1.0:
|
||||
resolution: {integrity: sha512-Dj1Okke1C3uKKwQcetra4jSuk0DqbzbYtXipzFlFMZtowbF1x7BKJwB9AayVMyFARvU8EDrZdcax4At/452cAg==}
|
||||
|
||||
styled-jsx@5.1.1:
|
||||
resolution: {integrity: sha512-pW7uC1l4mBZ8ugbiZrcIsiIvVx1UmTfw7UkC3Um2tmfUq9Bhk8IiyEIPl6F8agHgjzku6j0xQEZbfA5uSgSaCw==}
|
||||
engines: {node: '>= 12.0.0'}
|
||||
peerDependencies:
|
||||
'@babel/core': '*'
|
||||
babel-plugin-macros: '*'
|
||||
react: '>= 16.8.0 || 17.x.x || ^18.0.0-0'
|
||||
peerDependenciesMeta:
|
||||
'@babel/core':
|
||||
optional: true
|
||||
babel-plugin-macros:
|
||||
optional: true
|
||||
|
||||
styled-jsx@5.1.6:
|
||||
resolution: {integrity: sha512-qSVyDTeMotdvQYoHWLNGwRFJHC+i+ZvdBRYosOFgC+Wg1vx4frN2/RG/NA7SYqqvKNLf39P2LSRA2pu6n0XYZA==}
|
||||
engines: {node: '>= 12.0.0'}
|
||||
|
|
@ -6576,6 +6784,10 @@ packages:
|
|||
walker@1.0.8:
|
||||
resolution: {integrity: sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ==}
|
||||
|
||||
watchpack@2.4.0:
|
||||
resolution: {integrity: sha512-Lcvm7MGST/4fup+ifyKi2hjyIAwcdI4HRgtvTpIUxBRhB+RFtUh8XtDOxUfctVCnhVi+QQj49i91OyvzkJl6cg==}
|
||||
engines: {node: '>=10.13.0'}
|
||||
|
||||
web-streams-polyfill@3.3.3:
|
||||
resolution: {integrity: sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==}
|
||||
engines: {node: '>= 8'}
|
||||
|
|
@ -7953,6 +8165,10 @@ snapshots:
|
|||
'@formatjs/intl-localematcher': 0.5.8
|
||||
tslib: 2.8.1
|
||||
|
||||
'@formatjs/fast-memoize@1.2.1':
|
||||
dependencies:
|
||||
tslib: 2.8.1
|
||||
|
||||
'@formatjs/fast-memoize@2.2.3':
|
||||
dependencies:
|
||||
tslib: 2.8.1
|
||||
|
|
@ -7979,12 +8195,24 @@ snapshots:
|
|||
'@formatjs/ecma402-abstract': 2.2.4
|
||||
tslib: 2.8.1
|
||||
|
||||
'@formatjs/intl-displaynames@5.4.3':
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 1.11.4
|
||||
'@formatjs/intl-localematcher': 0.2.25
|
||||
tslib: 2.8.1
|
||||
|
||||
'@formatjs/intl-displaynames@6.8.5':
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 2.2.4
|
||||
'@formatjs/intl-localematcher': 0.5.8
|
||||
tslib: 2.8.1
|
||||
|
||||
'@formatjs/intl-listformat@6.5.3':
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 1.11.4
|
||||
'@formatjs/intl-localematcher': 0.2.25
|
||||
tslib: 2.8.1
|
||||
|
||||
'@formatjs/intl-listformat@7.7.5':
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 2.2.4
|
||||
|
|
@ -8016,6 +8244,18 @@ snapshots:
|
|||
optionalDependencies:
|
||||
typescript: 5.8.3
|
||||
|
||||
'@formatjs/intl@2.2.1(typescript@4.9.5)':
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 1.11.4
|
||||
'@formatjs/fast-memoize': 1.2.1
|
||||
'@formatjs/icu-messageformat-parser': 2.1.0
|
||||
'@formatjs/intl-displaynames': 5.4.3
|
||||
'@formatjs/intl-listformat': 6.5.3
|
||||
intl-messageformat: 9.13.0
|
||||
tslib: 2.8.1
|
||||
optionalDependencies:
|
||||
typescript: 4.9.5
|
||||
|
||||
'@formatjs/ts-transformer@2.13.0(ts-jest@29.3.2(@babel/core@7.26.10)(@jest/transform@29.7.0)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.26.10))(esbuild@0.25.2)(jest@29.7.0(@types/node@22.14.1)(ts-node@10.9.2(@types/node@22.14.1)(typescript@5.8.3)))(typescript@5.8.3))':
|
||||
dependencies:
|
||||
intl-messageformat-parser: 6.1.2
|
||||
|
|
@ -8357,33 +8597,62 @@ snapshots:
|
|||
|
||||
'@netlify/plugin-nextjs@5.10.6': {}
|
||||
|
||||
'@next/env@13.5.11': {}
|
||||
|
||||
'@next/env@15.3.0': {}
|
||||
|
||||
'@next/eslint-plugin-next@14.2.28':
|
||||
dependencies:
|
||||
glob: 10.3.10
|
||||
|
||||
'@next/swc-darwin-arm64@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-darwin-arm64@15.3.0':
|
||||
optional: true
|
||||
|
||||
'@next/swc-darwin-x64@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-darwin-x64@15.3.0':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-arm64-gnu@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-arm64-gnu@15.3.0':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-arm64-musl@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-arm64-musl@15.3.0':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-x64-gnu@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-x64-gnu@15.3.0':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-x64-musl@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-linux-x64-musl@15.3.0':
|
||||
optional: true
|
||||
|
||||
'@next/swc-win32-arm64-msvc@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-win32-arm64-msvc@15.3.0':
|
||||
optional: true
|
||||
|
||||
'@next/swc-win32-ia32-msvc@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-win32-x64-msvc@13.5.9':
|
||||
optional: true
|
||||
|
||||
'@next/swc-win32-x64-msvc@15.3.0':
|
||||
optional: true
|
||||
|
||||
|
|
@ -8404,34 +8673,42 @@ snapshots:
|
|||
'@pkgjs/parseargs@0.11.0':
|
||||
optional: true
|
||||
|
||||
'@prisma/client@6.1.0(prisma@6.1.0)':
|
||||
'@prisma/client@6.6.0(prisma@6.6.0(typescript@5.8.3))(typescript@5.8.3)':
|
||||
optionalDependencies:
|
||||
prisma: 6.1.0
|
||||
prisma: 6.6.0(typescript@5.8.3)
|
||||
typescript: 5.8.3
|
||||
|
||||
'@prisma/debug@6.1.0': {}
|
||||
|
||||
'@prisma/engines-version@6.1.0-21.11f085a2012c0f4778414c8db2651556ee0ef959': {}
|
||||
|
||||
'@prisma/engines@6.1.0':
|
||||
'@prisma/config@6.6.0':
|
||||
dependencies:
|
||||
'@prisma/debug': 6.1.0
|
||||
'@prisma/engines-version': 6.1.0-21.11f085a2012c0f4778414c8db2651556ee0ef959
|
||||
'@prisma/fetch-engine': 6.1.0
|
||||
'@prisma/get-platform': 6.1.0
|
||||
esbuild: 0.25.2
|
||||
esbuild-register: 3.6.0(esbuild@0.25.2)
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
'@prisma/extension-read-replicas@0.4.1(@prisma/client@6.1.0(prisma@6.1.0))':
|
||||
dependencies:
|
||||
'@prisma/client': 6.1.0(prisma@6.1.0)
|
||||
'@prisma/debug@6.6.0': {}
|
||||
|
||||
'@prisma/fetch-engine@6.1.0':
|
||||
dependencies:
|
||||
'@prisma/debug': 6.1.0
|
||||
'@prisma/engines-version': 6.1.0-21.11f085a2012c0f4778414c8db2651556ee0ef959
|
||||
'@prisma/get-platform': 6.1.0
|
||||
'@prisma/engines-version@6.6.0-53.f676762280b54cd07c770017ed3711ddde35f37a': {}
|
||||
|
||||
'@prisma/get-platform@6.1.0':
|
||||
'@prisma/engines@6.6.0':
|
||||
dependencies:
|
||||
'@prisma/debug': 6.1.0
|
||||
'@prisma/debug': 6.6.0
|
||||
'@prisma/engines-version': 6.6.0-53.f676762280b54cd07c770017ed3711ddde35f37a
|
||||
'@prisma/fetch-engine': 6.6.0
|
||||
'@prisma/get-platform': 6.6.0
|
||||
|
||||
'@prisma/extension-read-replicas@0.4.1(@prisma/client@6.6.0(prisma@6.6.0(typescript@5.8.3))(typescript@5.8.3))':
|
||||
dependencies:
|
||||
'@prisma/client': 6.6.0(prisma@6.6.0(typescript@5.8.3))(typescript@5.8.3)
|
||||
|
||||
'@prisma/fetch-engine@6.6.0':
|
||||
dependencies:
|
||||
'@prisma/debug': 6.6.0
|
||||
'@prisma/engines-version': 6.6.0-53.f676762280b54cd07c770017ed3711ddde35f37a
|
||||
'@prisma/get-platform': 6.6.0
|
||||
|
||||
'@prisma/get-platform@6.6.0':
|
||||
dependencies:
|
||||
'@prisma/debug': 6.6.0
|
||||
|
||||
'@react-spring/animated@9.7.5(react@19.1.0)':
|
||||
dependencies:
|
||||
|
|
@ -8666,8 +8943,22 @@ snapshots:
|
|||
dependencies:
|
||||
tslib: 2.8.1
|
||||
|
||||
'@swc/helpers@0.5.2':
|
||||
dependencies:
|
||||
tslib: 2.8.1
|
||||
|
||||
'@tanstack/query-core@4.36.1': {}
|
||||
|
||||
'@tanstack/query-core@5.74.3': {}
|
||||
|
||||
'@tanstack/react-query@4.36.1(react-dom@18.3.1(react@18.3.1))(react@18.3.1)':
|
||||
dependencies:
|
||||
'@tanstack/query-core': 4.36.1
|
||||
react: 18.3.1
|
||||
use-sync-external-store: 1.5.0(react@18.3.1)
|
||||
optionalDependencies:
|
||||
react-dom: 18.3.1(react@18.3.1)
|
||||
|
||||
'@tanstack/react-query@5.74.3(react@19.1.0)':
|
||||
dependencies:
|
||||
'@tanstack/query-core': 5.74.3
|
||||
|
|
@ -8954,15 +9245,6 @@ snapshots:
|
|||
'@typescript-eslint/types': 6.21.0
|
||||
eslint-visitor-keys: 3.4.3
|
||||
|
||||
'@umami/prisma-client@0.14.0(@prisma/client@6.1.0(prisma@6.1.0))(@prisma/extension-read-replicas@0.4.1(@prisma/client@6.1.0(prisma@6.1.0)))':
|
||||
dependencies:
|
||||
'@prisma/client': 6.1.0(prisma@6.1.0)
|
||||
'@prisma/extension-read-replicas': 0.4.1(@prisma/client@6.1.0(prisma@6.1.0))
|
||||
chalk: 4.1.2
|
||||
debug: 4.4.0(supports-color@8.1.1)
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
'@umami/redis-client@0.26.0':
|
||||
dependencies:
|
||||
debug: 4.4.0(supports-color@8.1.1)
|
||||
|
|
@ -10180,6 +10462,13 @@ snapshots:
|
|||
is-date-object: 1.1.0
|
||||
is-symbol: 1.1.1
|
||||
|
||||
esbuild-register@3.6.0(esbuild@0.25.2):
|
||||
dependencies:
|
||||
debug: 4.4.0(supports-color@8.1.1)
|
||||
esbuild: 0.25.2
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
esbuild@0.25.2:
|
||||
optionalDependencies:
|
||||
'@esbuild/aix-ppc64': 0.25.2
|
||||
|
|
@ -10766,6 +11055,8 @@ snapshots:
|
|||
dependencies:
|
||||
is-glob: 4.0.3
|
||||
|
||||
glob-to-regexp@0.4.1: {}
|
||||
|
||||
glob@10.3.10:
|
||||
dependencies:
|
||||
foreground-child: 3.3.1
|
||||
|
|
@ -10975,6 +11266,13 @@ snapshots:
|
|||
'@formatjs/icu-messageformat-parser': 2.9.4
|
||||
tslib: 2.8.1
|
||||
|
||||
intl-messageformat@9.13.0:
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 1.11.4
|
||||
'@formatjs/fast-memoize': 1.2.1
|
||||
'@formatjs/icu-messageformat-parser': 2.1.0
|
||||
tslib: 2.8.1
|
||||
|
||||
ipaddr.js@2.2.0: {}
|
||||
|
||||
is-array-buffer@3.0.5:
|
||||
|
|
@ -11949,6 +12247,12 @@ snapshots:
|
|||
|
||||
mmdb-lib@2.1.1: {}
|
||||
|
||||
moment-timezone@0.5.48:
|
||||
dependencies:
|
||||
moment: 2.30.1
|
||||
|
||||
moment@2.30.1: {}
|
||||
|
||||
ms@2.1.2: {}
|
||||
|
||||
ms@2.1.3: {}
|
||||
|
|
@ -11957,6 +12261,40 @@ snapshots:
|
|||
|
||||
natural-compare@1.4.0: {}
|
||||
|
||||
next-basics@0.36.0(next@13.5.11(@babel/core@7.26.10)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(react-dom@18.3.1(react@18.3.1))(react@18.3.1):
|
||||
dependencies:
|
||||
bcryptjs: 2.4.3
|
||||
jsonwebtoken: 9.0.2
|
||||
next: 13.5.11(@babel/core@7.26.10)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
|
||||
pure-rand: 6.1.0
|
||||
react: 18.3.1
|
||||
react-dom: 18.3.1(react@18.3.1)
|
||||
|
||||
next@13.5.11(@babel/core@7.26.10)(react-dom@18.3.1(react@18.3.1))(react@18.3.1):
|
||||
dependencies:
|
||||
'@next/env': 13.5.11
|
||||
'@swc/helpers': 0.5.2
|
||||
busboy: 1.6.0
|
||||
caniuse-lite: 1.0.30001714
|
||||
postcss: 8.4.31
|
||||
react: 18.3.1
|
||||
react-dom: 18.3.1(react@18.3.1)
|
||||
styled-jsx: 5.1.1(@babel/core@7.26.10)(react@18.3.1)
|
||||
watchpack: 2.4.0
|
||||
optionalDependencies:
|
||||
'@next/swc-darwin-arm64': 13.5.9
|
||||
'@next/swc-darwin-x64': 13.5.9
|
||||
'@next/swc-linux-arm64-gnu': 13.5.9
|
||||
'@next/swc-linux-arm64-musl': 13.5.9
|
||||
'@next/swc-linux-x64-gnu': 13.5.9
|
||||
'@next/swc-linux-x64-musl': 13.5.9
|
||||
'@next/swc-win32-arm64-msvc': 13.5.9
|
||||
'@next/swc-win32-ia32-msvc': 13.5.9
|
||||
'@next/swc-win32-x64-msvc': 13.5.9
|
||||
transitivePeerDependencies:
|
||||
- '@babel/core'
|
||||
- babel-plugin-macros
|
||||
|
||||
next@15.3.0(@babel/core@7.26.10)(react-dom@19.1.0(react@19.1.0))(react@19.1.0):
|
||||
dependencies:
|
||||
'@next/env': 15.3.0
|
||||
|
|
@ -12658,11 +12996,15 @@ snapshots:
|
|||
ansi-styles: 5.2.0
|
||||
react-is: 18.3.1
|
||||
|
||||
prisma@6.1.0:
|
||||
prisma@6.6.0(typescript@5.8.3):
|
||||
dependencies:
|
||||
'@prisma/engines': 6.1.0
|
||||
'@prisma/config': 6.6.0
|
||||
'@prisma/engines': 6.6.0
|
||||
optionalDependencies:
|
||||
fsevents: 2.3.3
|
||||
typescript: 5.8.3
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
process@0.11.10: {}
|
||||
|
||||
|
|
@ -12716,6 +13058,12 @@ snapshots:
|
|||
react-hook-form: 7.55.0(react@19.1.0)
|
||||
react-window: 1.8.11(react-dom@19.1.0(react@19.1.0))(react@19.1.0)
|
||||
|
||||
react-dom@18.3.1(react@18.3.1):
|
||||
dependencies:
|
||||
loose-envify: 1.4.0
|
||||
react: 18.3.1
|
||||
scheduler: 0.23.2
|
||||
|
||||
react-dom@19.1.0(react@19.1.0):
|
||||
dependencies:
|
||||
react: 19.1.0
|
||||
|
|
@ -12730,6 +13078,22 @@ snapshots:
|
|||
dependencies:
|
||||
react: 19.1.0
|
||||
|
||||
react-intl@5.25.1(react@18.3.1)(typescript@4.9.5):
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 1.11.4
|
||||
'@formatjs/icu-messageformat-parser': 2.1.0
|
||||
'@formatjs/intl': 2.2.1(typescript@4.9.5)
|
||||
'@formatjs/intl-displaynames': 5.4.3
|
||||
'@formatjs/intl-listformat': 6.5.3
|
||||
'@types/hoist-non-react-statics': 3.3.6
|
||||
'@types/react': 18.3.20
|
||||
hoist-non-react-statics: 3.3.2
|
||||
intl-messageformat: 9.13.0
|
||||
react: 18.3.1
|
||||
tslib: 2.8.1
|
||||
optionalDependencies:
|
||||
typescript: 4.9.5
|
||||
|
||||
react-intl@6.8.9(react@19.1.0)(typescript@5.8.3):
|
||||
dependencies:
|
||||
'@formatjs/ecma402-abstract': 2.2.4
|
||||
|
|
@ -12782,6 +13146,10 @@ snapshots:
|
|||
react: 19.1.0
|
||||
react-dom: 19.1.0(react@19.1.0)
|
||||
|
||||
react@18.3.1:
|
||||
dependencies:
|
||||
loose-envify: 1.4.0
|
||||
|
||||
react@19.1.0: {}
|
||||
|
||||
read-babelrc-up@1.1.0:
|
||||
|
|
@ -13057,6 +13425,10 @@ snapshots:
|
|||
|
||||
safer-buffer@2.1.2: {}
|
||||
|
||||
scheduler@0.23.2:
|
||||
dependencies:
|
||||
loose-envify: 1.4.0
|
||||
|
||||
scheduler@0.26.0: {}
|
||||
|
||||
schema-utils@2.7.1:
|
||||
|
|
@ -13370,6 +13742,13 @@ snapshots:
|
|||
|
||||
style-search@0.1.0: {}
|
||||
|
||||
styled-jsx@5.1.1(@babel/core@7.26.10)(react@18.3.1):
|
||||
dependencies:
|
||||
client-only: 0.0.1
|
||||
react: 18.3.1
|
||||
optionalDependencies:
|
||||
'@babel/core': 7.26.10
|
||||
|
||||
styled-jsx@5.1.6(@babel/core@7.26.10)(react@19.1.0):
|
||||
dependencies:
|
||||
client-only: 0.0.1
|
||||
|
|
@ -13759,6 +14138,10 @@ snapshots:
|
|||
dependencies:
|
||||
react: 19.1.0
|
||||
|
||||
use-sync-external-store@1.5.0(react@18.3.1):
|
||||
dependencies:
|
||||
react: 18.3.1
|
||||
|
||||
use-sync-external-store@1.5.0(react@19.1.0):
|
||||
dependencies:
|
||||
react: 19.1.0
|
||||
|
|
@ -13804,6 +14187,11 @@ snapshots:
|
|||
dependencies:
|
||||
makeerror: 1.0.12
|
||||
|
||||
watchpack@2.4.0:
|
||||
dependencies:
|
||||
glob-to-regexp: 0.4.1
|
||||
graceful-fs: 4.2.11
|
||||
|
||||
web-streams-polyfill@3.3.3: {}
|
||||
|
||||
which-boxed-primitive@1.1.1:
|
||||
|
|
@ -13943,6 +14331,14 @@ snapshots:
|
|||
|
||||
zod@3.24.3: {}
|
||||
|
||||
zustand@4.5.6(@types/react@19.1.2)(immer@9.0.21)(react@18.3.1):
|
||||
dependencies:
|
||||
use-sync-external-store: 1.5.0(react@18.3.1)
|
||||
optionalDependencies:
|
||||
'@types/react': 19.1.2
|
||||
immer: 9.0.21
|
||||
react: 18.3.1
|
||||
|
||||
zustand@4.5.6(@types/react@19.1.2)(immer@9.0.21)(react@19.1.0):
|
||||
dependencies:
|
||||
use-sync-external-store: 1.5.0(react@19.1.0)
|
||||
|
|
|
|||
10
pnpm-workspace.yaml
Normal file
10
pnpm-workspace.yaml
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
packages:
|
||||
- '**'
|
||||
ignoredBuiltDependencies:
|
||||
- cypress
|
||||
- esbuild
|
||||
- sharp
|
||||
onlyBuiltDependencies:
|
||||
- '@prisma/client'
|
||||
- '@prisma/engines'
|
||||
- prisma
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
module.exports = {
|
||||
plugins: [
|
||||
'postcss-flexbugs-fixes',
|
||||
[
|
||||
'postcss-preset-env',
|
||||
{
|
||||
autoprefixer: {
|
||||
flexbox: 'no-2009',
|
||||
},
|
||||
stage: 3,
|
||||
features: {
|
||||
'custom-properties': false,
|
||||
},
|
||||
},
|
||||
],
|
||||
],
|
||||
};
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
/* eslint-disable no-console */
|
||||
require('dotenv').config();
|
||||
const { PrismaClient } = require('@prisma/client');
|
||||
const { PrismaClient } = require('../src/generated/prisma/index.js');
|
||||
const chalk = require('chalk');
|
||||
const { execSync } = require('child_process');
|
||||
const semver = require('semver');
|
||||
|
|
|
|||
48
scripts/data-migrations/convert-utm-clid-columns.sql
Normal file
48
scripts/data-migrations/convert-utm-clid-columns.sql
Normal file
|
|
@ -0,0 +1,48 @@
|
|||
-----------------------------------------------------
|
||||
-- postgreSQL
|
||||
-----------------------------------------------------
|
||||
UPDATE "website_event" we
|
||||
SET fbclid = url.fbclid,
|
||||
gclid = url.gclid,
|
||||
li_fat_id = url.li_fat_id,
|
||||
msclkid = url.msclkid,
|
||||
ttclid = url.ttclid,
|
||||
twclid = url.twclid,
|
||||
utm_campaign = url.utm_campaign,
|
||||
utm_content = url.utm_content,
|
||||
utm_medium = url.utm_medium,
|
||||
utm_source = url.utm_source,
|
||||
utm_term = url.utm_term
|
||||
FROM (SELECT event_id, website_id, session_id,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)fbclid=([^&]+)', 'i'))[1] AS fbclid,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)gclid=([^&]+)', 'i'))[1] AS gclid,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)li_fat_id=([^&]+)', 'i'))[1] AS li_fat_id,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)msclkid=([^&]+)', 'i'))[1] AS msclkid,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)ttclid=([^&]+)', 'i'))[1] AS ttclid,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)twclid=([^&]+)', 'i'))[1] AS twclid,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)utm_campaign=([^&]+)', 'i'))[1] AS utm_campaign,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)utm_content=([^&]+)', 'i'))[1] AS utm_content,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)utm_medium=([^&]+)', 'i'))[1] AS utm_medium,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)utm_source=([^&]+)', 'i'))[1] AS utm_source,
|
||||
(regexp_matches(url_query, '(?:[&?]|^)utm_term=([^&]+)', 'i'))[1] AS utm_term
|
||||
FROM "website_event") url
|
||||
WHERE we.event_id = url.event_id
|
||||
and we.session_id = url.session_id
|
||||
and we.website_id = url.website_id;
|
||||
|
||||
-----------------------------------------------------
|
||||
-- mySQL
|
||||
-----------------------------------------------------
|
||||
UPDATE `website_event`
|
||||
SET fbclid = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)fbclid=[^&]+'), '=', -1), '&', 1),
|
||||
gclid = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)gclid=[^&]+'), '=', -1), '&', 1),
|
||||
li_fat_id = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)li_fat_id=[^&]+'), '=', -1), '&', 1),
|
||||
msclkid = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)msclkid=[^&]+'), '=', -1), '&', 1),
|
||||
ttclid = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)ttclid=[^&]+'), '=', -1), '&', 1),
|
||||
twclid = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)twclid=[^&]+'), '=', -1), '&', 1),
|
||||
utm_campaign = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)utm_campaign=[^&]+'), '=', -1), '&', 1),
|
||||
utm_content = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)utm_content=[^&]+'), '=', -1), '&', 1),
|
||||
utm_medium = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)utm_medium=[^&]+'), '=', -1), '&', 1),
|
||||
utm_source = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)utm_source=[^&]+'), '=', -1), '&', 1),
|
||||
utm_term = SUBSTRING_INDEX(SUBSTRING_INDEX(REGEXP_SUBSTR(url_query, '(?:[&?]|^)utm_term=[^&]+'), '=', -1), '&', 1)
|
||||
WHERE 1 = 1;
|
||||
|
|
@ -14,7 +14,7 @@ export default function SessionsDataTable({
|
|||
const queryResult = useWebsiteSessions(websiteId);
|
||||
|
||||
return (
|
||||
<DataTable queryResult={queryResult} allowSearch={false} renderEmpty={() => children}>
|
||||
<DataTable queryResult={queryResult} allowSearch={true} renderEmpty={() => children}>
|
||||
{({ data }) => <SessionsTable data={data} showDomain={!websiteId} />}
|
||||
</DataTable>
|
||||
);
|
||||
|
|
|
|||
|
|
@ -18,7 +18,8 @@ export default function SessionInfo({ data }) {
|
|||
<dd>
|
||||
{data?.id} <CopyIcon value={data?.id} />
|
||||
</dd>
|
||||
|
||||
<dt>{formatMessage(labels.distinctId)}</dt>
|
||||
<dd>{data?.distinctId}</dd>
|
||||
<dt>{formatMessage(labels.lastSeen)}</dt>
|
||||
<dd>{formatTimezoneDate(data?.lastAt, 'PPPPpp')}</dd>
|
||||
|
||||
|
|
|
|||
|
|
@ -121,6 +121,7 @@ export async function POST(request: Request) {
|
|||
country,
|
||||
region,
|
||||
city,
|
||||
distinctId: id,
|
||||
});
|
||||
} catch (e: any) {
|
||||
if (!e.message.toLowerCase().includes('unique constraint')) {
|
||||
|
|
@ -144,7 +145,7 @@ export async function POST(request: Request) {
|
|||
const base = hostname ? `https://${hostname}` : 'https://localhost';
|
||||
const currentUrl = new URL(url, base);
|
||||
|
||||
let urlPath = currentUrl.pathname;
|
||||
let urlPath = currentUrl.pathname === '/undefined' ? '' : currentUrl.pathname;
|
||||
const urlQuery = currentUrl.search.substring(1);
|
||||
const urlDomain = currentUrl.hostname.replace(/^www./, '');
|
||||
|
||||
|
|
@ -215,6 +216,7 @@ export async function POST(request: Request) {
|
|||
region,
|
||||
city,
|
||||
tag,
|
||||
distinctId: id,
|
||||
createdAt,
|
||||
});
|
||||
}
|
||||
|
|
@ -228,6 +230,7 @@ export async function POST(request: Request) {
|
|||
websiteId,
|
||||
sessionId,
|
||||
sessionData: data,
|
||||
distinctId: id,
|
||||
createdAt,
|
||||
});
|
||||
}
|
||||
|
|
|
|||
|
|
@ -131,6 +131,7 @@ export const labels = defineMessages({
|
|||
all: { id: 'label.all', defaultMessage: 'All' },
|
||||
session: { id: 'label.session', defaultMessage: 'Session' },
|
||||
sessions: { id: 'label.sessions', defaultMessage: 'Sessions' },
|
||||
distinctId: { id: 'label.distinct-id', defaultMessage: 'Distinct ID' },
|
||||
pageNotFound: { id: 'message.page-not-found', defaultMessage: 'Page not found' },
|
||||
activity: { id: 'label.activity', defaultMessage: 'Activity' },
|
||||
dismiss: { id: 'label.dismiss', defaultMessage: 'Dismiss' },
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
import debug from 'debug';
|
||||
import prisma from '@umami/prisma-client';
|
||||
import { PrismaClient } from '@/generated/prisma/index.js';
|
||||
import { readReplicas } from '@prisma/extension-read-replicas';
|
||||
import { formatInTimeZone } from 'date-fns-tz';
|
||||
import { MYSQL, POSTGRESQL, getDatabaseType } from '@/lib/db';
|
||||
import { SESSION_COLUMNS, OPERATORS, DEFAULT_PAGE_SIZE } from './constants';
|
||||
|
|
@ -10,6 +11,16 @@ import { filtersToArray } from './params';
|
|||
|
||||
const log = debug('umami:prisma');
|
||||
|
||||
const PRISMA = 'prisma';
|
||||
const PRISMA_LOG_OPTIONS = {
|
||||
log: [
|
||||
{
|
||||
emit: 'event',
|
||||
level: 'query',
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
const MYSQL_DATE_FORMATS = {
|
||||
minute: '%Y-%m-%dT%H:%i:00',
|
||||
hour: '%Y-%m-%d %H:00:00',
|
||||
|
|
@ -234,14 +245,16 @@ async function rawQuery(sql: string, data: object): Promise<any> {
|
|||
return db === MYSQL ? '?' : `$${params.length}${type ?? ''}`;
|
||||
});
|
||||
|
||||
return prisma.rawQuery(query, params);
|
||||
return process.env.DATABASE_REPLICA_URL
|
||||
? client.$replica().$queryRawUnsafe(query, ...params)
|
||||
: client.$queryRawUnsafe(query, ...params);
|
||||
}
|
||||
|
||||
async function pagedQuery<T>(model: string, criteria: T, pageParams: PageParams) {
|
||||
const { page = 1, pageSize, orderBy, sortDescending = false } = pageParams || {};
|
||||
const size = +pageSize || DEFAULT_PAGE_SIZE;
|
||||
|
||||
const data = await prisma.client[model].findMany({
|
||||
const data = await client[model].findMany({
|
||||
...criteria,
|
||||
...{
|
||||
...(size > 0 && { take: +size, skip: +size * (+page - 1) }),
|
||||
|
|
@ -255,7 +268,7 @@ async function pagedQuery<T>(model: string, criteria: T, pageParams: PageParams)
|
|||
},
|
||||
});
|
||||
|
||||
const count = await prisma.client[model].count({ where: (criteria as any).where });
|
||||
const count = await client[model].count({ where: (criteria as any).where });
|
||||
|
||||
return { data, count, page: +page, pageSize: size, orderBy };
|
||||
}
|
||||
|
|
@ -323,8 +336,55 @@ function getSearchParameters(query: string, filters: { [key: string]: any }[]) {
|
|||
};
|
||||
}
|
||||
|
||||
function transaction(input: any, options?: any) {
|
||||
return client.$transaction(input, options);
|
||||
}
|
||||
|
||||
function getClient(params?: {
|
||||
logQuery?: boolean;
|
||||
queryLogger?: () => void;
|
||||
replicaUrl?: string;
|
||||
options?: any;
|
||||
}): PrismaClient {
|
||||
const {
|
||||
logQuery = !!process.env.LOG_QUERY,
|
||||
queryLogger,
|
||||
replicaUrl = process.env.DATABASE_REPLICA_URL,
|
||||
options,
|
||||
} = params || {};
|
||||
|
||||
const prisma = new PrismaClient({
|
||||
errorFormat: 'pretty',
|
||||
...(logQuery && PRISMA_LOG_OPTIONS),
|
||||
...options,
|
||||
});
|
||||
|
||||
if (replicaUrl) {
|
||||
prisma.$extends(
|
||||
readReplicas({
|
||||
url: replicaUrl,
|
||||
}),
|
||||
);
|
||||
}
|
||||
|
||||
if (logQuery) {
|
||||
prisma.$on('query' as never, queryLogger || log);
|
||||
}
|
||||
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
global[PRISMA] = prisma;
|
||||
}
|
||||
|
||||
log('Prisma initialized');
|
||||
|
||||
return prisma;
|
||||
}
|
||||
|
||||
const client = global[PRISMA] || getClient();
|
||||
|
||||
export default {
|
||||
...prisma,
|
||||
client,
|
||||
transaction,
|
||||
getAddIntervalQuery,
|
||||
getCastColumnQuery,
|
||||
getDayDiffQuery,
|
||||
|
|
|
|||
|
|
@ -3,13 +3,13 @@ import { REDIS, UmamiRedisClient } from '@umami/redis-client';
|
|||
const enabled = !!process.env.REDIS_URL;
|
||||
|
||||
function getClient() {
|
||||
const client = new UmamiRedisClient(process.env.REDIS_URL);
|
||||
const redis = new UmamiRedisClient(process.env.REDIS_URL);
|
||||
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
global[REDIS] = client;
|
||||
global[REDIS] = redis;
|
||||
}
|
||||
|
||||
return client;
|
||||
return redis;
|
||||
}
|
||||
|
||||
const client = global[REDIS] || getClient();
|
||||
|
|
|
|||
|
|
@ -39,6 +39,7 @@ export async function saveEvent(args: {
|
|||
region?: string;
|
||||
city?: string;
|
||||
tag?: string;
|
||||
distinctId?: string;
|
||||
createdAt?: Date;
|
||||
}) {
|
||||
return runQuery({
|
||||
|
|
@ -182,6 +183,7 @@ async function clickhouseQuery(data: {
|
|||
region?: string;
|
||||
city?: string;
|
||||
tag?: string;
|
||||
distinctId?: string;
|
||||
createdAt?: Date;
|
||||
}) {
|
||||
const {
|
||||
|
|
@ -211,6 +213,7 @@ async function clickhouseQuery(data: {
|
|||
region,
|
||||
city,
|
||||
tag,
|
||||
distinctId,
|
||||
createdAt,
|
||||
...args
|
||||
} = data;
|
||||
|
|
@ -247,6 +250,7 @@ async function clickhouseQuery(data: {
|
|||
event_type: eventName ? EVENT_TYPE.customEvent : EVENT_TYPE.pageView,
|
||||
event_name: eventName ? eventName?.substring(0, EVENT_NAME_LENGTH) : null,
|
||||
tag: tag,
|
||||
distinct_id: distinctId,
|
||||
created_at: getUTCString(createdAt),
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -2,7 +2,19 @@ import { Prisma } from '@prisma/client';
|
|||
import prisma from '@/lib/prisma';
|
||||
|
||||
export async function createSession(data: Prisma.SessionCreateInput) {
|
||||
const { id, websiteId, browser, os, device, screen, language, country, region, city } = data;
|
||||
const {
|
||||
id,
|
||||
websiteId,
|
||||
browser,
|
||||
os,
|
||||
device,
|
||||
screen,
|
||||
language,
|
||||
country,
|
||||
region,
|
||||
city,
|
||||
distinctId,
|
||||
} = data;
|
||||
|
||||
return prisma.client.session.create({
|
||||
data: {
|
||||
|
|
@ -16,6 +28,7 @@ export async function createSession(data: Prisma.SessionCreateInput) {
|
|||
country,
|
||||
region,
|
||||
city,
|
||||
distinctId,
|
||||
},
|
||||
});
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,6 +15,7 @@ async function relationalQuery(websiteId: string, sessionId: string) {
|
|||
return rawQuery(
|
||||
`
|
||||
select id,
|
||||
distinct_id as "distinctId",
|
||||
website_id as "websiteId",
|
||||
hostname,
|
||||
browser,
|
||||
|
|
@ -33,6 +34,7 @@ async function relationalQuery(websiteId: string, sessionId: string) {
|
|||
sum(${getTimestampDiffSQL('min_time', 'max_time')}) as "totaltime"
|
||||
from (select
|
||||
session.session_id as id,
|
||||
session.distinct_id,
|
||||
website_event.visit_id,
|
||||
session.website_id,
|
||||
website_event.hostname,
|
||||
|
|
@ -52,8 +54,8 @@ async function relationalQuery(websiteId: string, sessionId: string) {
|
|||
join website_event on website_event.session_id = session.session_id
|
||||
where session.website_id = {{websiteId::uuid}}
|
||||
and session.session_id = {{sessionId::uuid}}
|
||||
group by session.session_id, visit_id, session.website_id, website_event.hostname, session.browser, session.os, session.device, session.screen, session.language, session.country, session.region, session.city) t
|
||||
group by id, website_id, hostname, browser, os, device, screen, language, country, region, city;
|
||||
group by session.session_id, session.distinct_id, visit_id, session.website_id, website_event.hostname, session.browser, session.os, session.device, session.screen, session.language, session.country, session.region, session.city) t
|
||||
group by id, distinct_id, website_id, hostname, browser, os, device, screen, language, country, region, city;
|
||||
`,
|
||||
{ websiteId, sessionId },
|
||||
).then(result => result?.[0]);
|
||||
|
|
@ -66,6 +68,7 @@ async function clickhouseQuery(websiteId: string, sessionId: string) {
|
|||
`
|
||||
select id,
|
||||
websiteId,
|
||||
distinctId,
|
||||
hostname,
|
||||
browser,
|
||||
os,
|
||||
|
|
@ -83,6 +86,7 @@ async function clickhouseQuery(websiteId: string, sessionId: string) {
|
|||
sum(max_time-min_time) as totaltime
|
||||
from (select
|
||||
session_id as id,
|
||||
distinct_id as distinctId,
|
||||
visit_id,
|
||||
website_id as websiteId,
|
||||
hostname,
|
||||
|
|
@ -101,8 +105,8 @@ async function clickhouseQuery(websiteId: string, sessionId: string) {
|
|||
from website_event_stats_hourly
|
||||
where website_id = {websiteId:UUID}
|
||||
and session_id = {sessionId:UUID}
|
||||
group by session_id, visit_id, website_id, hostname, browser, os, device, screen, language, country, region, city) t
|
||||
group by id, websiteId, hostname, browser, os, device, screen, language, country, region, city;
|
||||
group by session_id, distinct_id, visit_id, website_id, hostname, browser, os, device, screen, language, country, region, city) t
|
||||
group by id, websiteId, distinctId, hostname, browser, os, device, screen, language, country, region, city;
|
||||
`,
|
||||
{ websiteId, sessionId },
|
||||
).then(result => result?.[0]);
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import clickhouse from '@/lib/clickhouse';
|
||||
import { CLICKHOUSE, PRISMA, runQuery } from '@/lib/db';
|
||||
import { CLICKHOUSE, getDatabaseType, POSTGRESQL, PRISMA, runQuery } from '@/lib/db';
|
||||
import prisma from '@/lib/prisma';
|
||||
import { PageParams, QueryFilters } from '@/lib/types';
|
||||
|
||||
|
|
@ -14,10 +14,14 @@ export async function getWebsiteSessions(
|
|||
|
||||
async function relationalQuery(websiteId: string, filters: QueryFilters, pageParams: PageParams) {
|
||||
const { pagedRawQuery, parseFilters } = prisma;
|
||||
const { search } = pageParams;
|
||||
const { filterQuery, params } = await parseFilters(websiteId, {
|
||||
...filters,
|
||||
});
|
||||
|
||||
const db = getDatabaseType();
|
||||
const like = db === POSTGRESQL ? 'ilike' : 'like';
|
||||
|
||||
return pagedRawQuery(
|
||||
`
|
||||
with sessions as (
|
||||
|
|
@ -43,6 +47,15 @@ async function relationalQuery(websiteId: string, filters: QueryFilters, pagePar
|
|||
where website_event.website_id = {{websiteId::uuid}}
|
||||
and website_event.created_at between {{startDate}} and {{endDate}}
|
||||
${filterQuery}
|
||||
${
|
||||
search
|
||||
? `and (distinct_id ${like} {{search}}
|
||||
or city ${like} {{search}}
|
||||
or browser ${like} {{search}}
|
||||
or os ${like} {{search}}
|
||||
or device ${like} {{search}})`
|
||||
: ''
|
||||
}
|
||||
group by session.session_id,
|
||||
session.website_id,
|
||||
website_event.hostname,
|
||||
|
|
@ -58,7 +71,7 @@ async function relationalQuery(websiteId: string, filters: QueryFilters, pagePar
|
|||
limit 1000)
|
||||
select * from sessions
|
||||
`,
|
||||
params,
|
||||
{ ...params, search: `%${search}%` },
|
||||
pageParams,
|
||||
);
|
||||
}
|
||||
|
|
@ -66,6 +79,7 @@ async function relationalQuery(websiteId: string, filters: QueryFilters, pagePar
|
|||
async function clickhouseQuery(websiteId: string, filters: QueryFilters, pageParams?: PageParams) {
|
||||
const { pagedQuery, parseFilters, getDateStringSQL } = clickhouse;
|
||||
const { params, dateQuery, filterQuery } = await parseFilters(websiteId, filters);
|
||||
const { search } = pageParams;
|
||||
|
||||
return pagedQuery(
|
||||
`
|
||||
|
|
@ -91,12 +105,21 @@ async function clickhouseQuery(websiteId: string, filters: QueryFilters, pagePar
|
|||
where website_id = {websiteId:UUID}
|
||||
${dateQuery}
|
||||
${filterQuery}
|
||||
${
|
||||
search
|
||||
? `and ((positionCaseInsensitive(distinct_id, {search:String}) > 0)
|
||||
or (positionCaseInsensitive(city, {search:String}) > 0)
|
||||
or (positionCaseInsensitive(browser, {search:String}) > 0)
|
||||
or (positionCaseInsensitive(os, {search:String}) > 0)
|
||||
or (positionCaseInsensitive(device, {search:String}) > 0))`
|
||||
: ''
|
||||
}
|
||||
group by session_id, website_id, hostname, browser, os, device, screen, language, country, region, city
|
||||
order by lastAt desc
|
||||
limit 1000)
|
||||
select * from sessions
|
||||
`,
|
||||
params,
|
||||
{ ...params, search },
|
||||
pageParams,
|
||||
);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@ export async function saveSessionData(data: {
|
|||
websiteId: string;
|
||||
sessionId: string;
|
||||
sessionData: DynamicData;
|
||||
distinctId?: string;
|
||||
createdAt?: Date;
|
||||
}) {
|
||||
return runQuery({
|
||||
|
|
@ -23,10 +24,11 @@ export async function relationalQuery(data: {
|
|||
websiteId: string;
|
||||
sessionId: string;
|
||||
sessionData: DynamicData;
|
||||
distinctId?: string;
|
||||
createdAt?: Date;
|
||||
}) {
|
||||
const { client } = prisma;
|
||||
const { websiteId, sessionId, sessionData, createdAt } = data;
|
||||
const { websiteId, sessionId, sessionData, distinctId, createdAt } = data;
|
||||
|
||||
const jsonKeys = flattenJSON(sessionData);
|
||||
|
||||
|
|
@ -39,6 +41,7 @@ export async function relationalQuery(data: {
|
|||
numberValue: a.dataType === DATA_TYPE.number ? a.value : null,
|
||||
dateValue: a.dataType === DATA_TYPE.date ? new Date(a.value) : null,
|
||||
dataType: a.dataType,
|
||||
distinctId,
|
||||
createdAt,
|
||||
}));
|
||||
|
||||
|
|
@ -80,9 +83,10 @@ async function clickhouseQuery(data: {
|
|||
websiteId: string;
|
||||
sessionId: string;
|
||||
sessionData: DynamicData;
|
||||
distinctId?: string;
|
||||
createdAt?: Date;
|
||||
}) {
|
||||
const { websiteId, sessionId, sessionData, createdAt } = data;
|
||||
const { websiteId, sessionId, sessionData, distinctId, createdAt } = data;
|
||||
|
||||
const { insert, getUTCString } = clickhouse;
|
||||
const { sendMessage } = kafka;
|
||||
|
|
@ -98,6 +102,7 @@ async function clickhouseQuery(data: {
|
|||
string_value: getStringValue(value, dataType),
|
||||
number_value: dataType === DATA_TYPE.number ? value : null,
|
||||
date_value: dataType === DATA_TYPE.date ? getUTCString(value) : null,
|
||||
distinct_id: distinctId,
|
||||
created_at: getUTCString(createdAt),
|
||||
};
|
||||
});
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue