mirror of
https://github.com/fosrl/pangolin.git
synced 2026-04-11 21:56:45 +00:00
Compare commits
7 Commits
dev
...
dependabot
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
a601985544 | ||
|
|
3436105bec | ||
|
|
4b3375ab8e | ||
|
|
6ce165bfd5 | ||
|
|
035644eaf7 | ||
|
|
16e7233a3e | ||
|
|
1f74e1b320 |
1
.github/CODEOWNERS
vendored
1
.github/CODEOWNERS
vendored
@@ -1 +0,0 @@
|
|||||||
* @oschwartz10612 @miloschwartz
|
|
||||||
@@ -2113,11 +2113,9 @@
|
|||||||
"addDomainToEnableCustomAuthPages": "Users will be able to access the organization's login page and complete resource authentication using this domain.",
|
"addDomainToEnableCustomAuthPages": "Users will be able to access the organization's login page and complete resource authentication using this domain.",
|
||||||
"selectDomainForOrgAuthPage": "Select a domain for the organization's authentication page",
|
"selectDomainForOrgAuthPage": "Select a domain for the organization's authentication page",
|
||||||
"domainPickerProvidedDomain": "Provided Domain",
|
"domainPickerProvidedDomain": "Provided Domain",
|
||||||
"domainPickerFreeProvidedDomain": "Provided Domain",
|
"domainPickerFreeProvidedDomain": "Free Provided Domain",
|
||||||
"domainPickerFreeDomainsPaidFeature": "Provided domains are a paid feature. Subscribe to get a domain included with your plan — no need to bring your own.",
|
|
||||||
"domainPickerVerified": "Verified",
|
"domainPickerVerified": "Verified",
|
||||||
"domainPickerUnverified": "Unverified",
|
"domainPickerUnverified": "Unverified",
|
||||||
"domainPickerManual": "Manual",
|
|
||||||
"domainPickerInvalidSubdomainStructure": "This subdomain contains invalid characters or structure. It will be sanitized automatically when you save.",
|
"domainPickerInvalidSubdomainStructure": "This subdomain contains invalid characters or structure. It will be sanitized automatically when you save.",
|
||||||
"domainPickerError": "Error",
|
"domainPickerError": "Error",
|
||||||
"domainPickerErrorLoadDomains": "Failed to load organization domains",
|
"domainPickerErrorLoadDomains": "Failed to load organization domains",
|
||||||
|
|||||||
172
package-lock.json
generated
172
package-lock.json
generated
@@ -12,7 +12,7 @@
|
|||||||
"@asteasolutions/zod-to-openapi": "8.4.1",
|
"@asteasolutions/zod-to-openapi": "8.4.1",
|
||||||
"@aws-sdk/client-s3": "3.1011.0",
|
"@aws-sdk/client-s3": "3.1011.0",
|
||||||
"@faker-js/faker": "10.3.0",
|
"@faker-js/faker": "10.3.0",
|
||||||
"@headlessui/react": "2.2.9",
|
"@headlessui/react": "2.2.10",
|
||||||
"@hookform/resolvers": "5.2.2",
|
"@hookform/resolvers": "5.2.2",
|
||||||
"@monaco-editor/react": "4.7.0",
|
"@monaco-editor/react": "4.7.0",
|
||||||
"@node-rs/argon2": "2.0.2",
|
"@node-rs/argon2": "2.0.2",
|
||||||
@@ -36,9 +36,9 @@
|
|||||||
"@radix-ui/react-tabs": "1.1.13",
|
"@radix-ui/react-tabs": "1.1.13",
|
||||||
"@radix-ui/react-toast": "1.2.15",
|
"@radix-ui/react-toast": "1.2.15",
|
||||||
"@radix-ui/react-tooltip": "1.2.8",
|
"@radix-ui/react-tooltip": "1.2.8",
|
||||||
"@react-email/components": "1.0.8",
|
"@react-email/components": "1.0.11",
|
||||||
"@react-email/render": "2.0.4",
|
"@react-email/render": "2.0.5",
|
||||||
"@react-email/tailwind": "2.0.5",
|
"@react-email/tailwind": "2.0.7",
|
||||||
"@simplewebauthn/browser": "13.3.0",
|
"@simplewebauthn/browser": "13.3.0",
|
||||||
"@simplewebauthn/server": "13.3.0",
|
"@simplewebauthn/server": "13.3.0",
|
||||||
"@tailwindcss/forms": "0.5.11",
|
"@tailwindcss/forms": "0.5.11",
|
||||||
@@ -55,33 +55,33 @@
|
|||||||
"cors": "2.8.6",
|
"cors": "2.8.6",
|
||||||
"crypto-js": "4.2.0",
|
"crypto-js": "4.2.0",
|
||||||
"d3": "7.9.0",
|
"d3": "7.9.0",
|
||||||
"drizzle-orm": "0.45.1",
|
"drizzle-orm": "0.45.2",
|
||||||
"express": "5.2.1",
|
"express": "5.2.1",
|
||||||
"express-rate-limit": "8.3.0",
|
"express-rate-limit": "8.3.2",
|
||||||
"glob": "13.0.6",
|
"glob": "13.0.6",
|
||||||
"helmet": "8.1.0",
|
"helmet": "8.1.0",
|
||||||
"http-errors": "2.0.1",
|
"http-errors": "2.0.1",
|
||||||
"input-otp": "1.4.2",
|
"input-otp": "1.4.2",
|
||||||
"ioredis": "5.10.0",
|
"ioredis": "5.10.1",
|
||||||
"jmespath": "0.16.0",
|
"jmespath": "0.16.0",
|
||||||
"js-yaml": "4.1.1",
|
"js-yaml": "4.1.1",
|
||||||
"jsonwebtoken": "9.0.3",
|
"jsonwebtoken": "9.0.3",
|
||||||
"lucide-react": "0.577.0",
|
"lucide-react": "0.577.0",
|
||||||
"maxmind": "5.0.5",
|
"maxmind": "5.0.6",
|
||||||
"moment": "2.30.1",
|
"moment": "2.30.1",
|
||||||
"next": "15.5.14",
|
"next": "15.5.14",
|
||||||
"next-intl": "4.8.3",
|
"next-intl": "4.8.3",
|
||||||
"next-themes": "0.4.6",
|
"next-themes": "0.4.6",
|
||||||
"nextjs-toploader": "3.9.17",
|
"nextjs-toploader": "3.9.17",
|
||||||
"node-cache": "5.1.2",
|
"node-cache": "5.1.2",
|
||||||
"nodemailer": "8.0.4",
|
"nodemailer": "8.0.5",
|
||||||
"oslo": "1.2.1",
|
"oslo": "1.2.1",
|
||||||
"pg": "8.20.0",
|
"pg": "8.20.0",
|
||||||
"posthog-node": "5.28.0",
|
"posthog-node": "5.28.0",
|
||||||
"qrcode.react": "4.2.0",
|
"qrcode.react": "4.2.0",
|
||||||
"react": "19.2.4",
|
"react": "19.2.5",
|
||||||
"react-day-picker": "9.14.0",
|
"react-day-picker": "9.14.0",
|
||||||
"react-dom": "19.2.4",
|
"react-dom": "19.2.5",
|
||||||
"react-easy-sort": "1.8.0",
|
"react-easy-sort": "1.8.0",
|
||||||
"react-hook-form": "7.71.2",
|
"react-hook-form": "7.71.2",
|
||||||
"react-icons": "5.6.0",
|
"react-icons": "5.6.0",
|
||||||
@@ -89,13 +89,13 @@
|
|||||||
"reodotdev": "1.1.0",
|
"reodotdev": "1.1.0",
|
||||||
"resend": "6.9.2",
|
"resend": "6.9.2",
|
||||||
"semver": "7.7.4",
|
"semver": "7.7.4",
|
||||||
"sshpk": "^1.18.0",
|
"sshpk": "1.18.0",
|
||||||
"stripe": "20.4.1",
|
"stripe": "20.4.1",
|
||||||
"swagger-ui-express": "5.0.1",
|
"swagger-ui-express": "5.0.1",
|
||||||
"tailwind-merge": "3.5.0",
|
"tailwind-merge": "3.5.0",
|
||||||
"topojson-client": "3.1.0",
|
"topojson-client": "3.1.0",
|
||||||
"tw-animate-css": "1.4.0",
|
"tw-animate-css": "1.4.0",
|
||||||
"use-debounce": "^10.1.0",
|
"use-debounce": "10.1.1",
|
||||||
"uuid": "13.0.0",
|
"uuid": "13.0.0",
|
||||||
"vaul": "1.1.2",
|
"vaul": "1.1.2",
|
||||||
"visionscarto-world-atlas": "1.0.0",
|
"visionscarto-world-atlas": "1.0.0",
|
||||||
@@ -124,13 +124,13 @@
|
|||||||
"@types/js-yaml": "4.0.9",
|
"@types/js-yaml": "4.0.9",
|
||||||
"@types/jsonwebtoken": "9.0.10",
|
"@types/jsonwebtoken": "9.0.10",
|
||||||
"@types/node": "25.3.5",
|
"@types/node": "25.3.5",
|
||||||
"@types/nodemailer": "7.0.11",
|
"@types/nodemailer": "8.0.0",
|
||||||
"@types/nprogress": "0.2.3",
|
"@types/nprogress": "0.2.3",
|
||||||
"@types/pg": "8.18.0",
|
"@types/pg": "8.18.0",
|
||||||
"@types/react": "19.2.14",
|
"@types/react": "19.2.14",
|
||||||
"@types/react-dom": "19.2.3",
|
"@types/react-dom": "19.2.3",
|
||||||
"@types/semver": "7.7.1",
|
"@types/semver": "7.7.1",
|
||||||
"@types/sshpk": "^1.17.4",
|
"@types/sshpk": "1.17.4",
|
||||||
"@types/swagger-ui-express": "4.1.8",
|
"@types/swagger-ui-express": "4.1.8",
|
||||||
"@types/topojson-client": "3.1.5",
|
"@types/topojson-client": "3.1.5",
|
||||||
"@types/ws": "8.18.1",
|
"@types/ws": "8.18.1",
|
||||||
@@ -2247,9 +2247,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@headlessui/react": {
|
"node_modules/@headlessui/react": {
|
||||||
"version": "2.2.9",
|
"version": "2.2.10",
|
||||||
"resolved": "https://registry.npmjs.org/@headlessui/react/-/react-2.2.9.tgz",
|
"resolved": "https://registry.npmjs.org/@headlessui/react/-/react-2.2.10.tgz",
|
||||||
"integrity": "sha512-Mb+Un58gwBn0/yWZfyrCh0TJyurtT+dETj7YHleylHk5od3dv2XqETPGWMyQ5/7sYN7oWdyM1u9MvC0OC8UmzQ==",
|
"integrity": "sha512-5pVLNK9wlpxTUTy9GpgbX/SdcRh+HBnPktjM2wbiLTH4p+2EPHBO1aoSryUCuKUIItdDWO9ITlhUL8UnUN/oIA==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@floating-ui/react": "^0.26.16",
|
"@floating-ui/react": "^0.26.16",
|
||||||
@@ -6386,18 +6386,6 @@
|
|||||||
"react-dom": "^16.8.0 || ^17.0.0-rc.1 || ^18.0.0 || ^19.0.0-rc.1"
|
"react-dom": "^16.8.0 || ^17.0.0-rc.1 || ^18.0.0 || ^19.0.0-rc.1"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@react-email/body": {
|
|
||||||
"version": "0.2.1",
|
|
||||||
"resolved": "https://registry.npmjs.org/@react-email/body/-/body-0.2.1.tgz",
|
|
||||||
"integrity": "sha512-ljDiQiJDu/Fq//vSIIP0z5Nuvt4+DX1RqGasstChDGJB/14ogd4VdNS9aacoede/ZjGy3o3Qb+cxyS+XgM6SwQ==",
|
|
||||||
"license": "MIT",
|
|
||||||
"engines": {
|
|
||||||
"node": ">=20.0.0"
|
|
||||||
},
|
|
||||||
"peerDependencies": {
|
|
||||||
"react": "^18.0 || ^19.0 || ^19.0.0-rc"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"node_modules/@react-email/button": {
|
"node_modules/@react-email/button": {
|
||||||
"version": "0.2.1",
|
"version": "0.2.1",
|
||||||
"resolved": "https://registry.npmjs.org/@react-email/button/-/button-0.2.1.tgz",
|
"resolved": "https://registry.npmjs.org/@react-email/button/-/button-0.2.1.tgz",
|
||||||
@@ -6450,12 +6438,12 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@react-email/components": {
|
"node_modules/@react-email/components": {
|
||||||
"version": "1.0.8",
|
"version": "1.0.11",
|
||||||
"resolved": "https://registry.npmjs.org/@react-email/components/-/components-1.0.8.tgz",
|
"resolved": "https://registry.npmjs.org/@react-email/components/-/components-1.0.11.tgz",
|
||||||
"integrity": "sha512-zY81ED6o5MWMzBkr9uZFuT24lWarT+xIbOZxI6C9dsFmCWBczM8IE1BgOI8rhpUK4JcYVDy1uKxYAFqsx2Bc4w==",
|
"integrity": "sha512-s0CX31+S/u1MhBWYFAuZru0NHNExTY+OeZC9OrGyzl8PGQ0Iz/4gq3O4rHUVuA1D7FjAcPbwG1Up0yey/Xh6dw==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@react-email/body": "0.2.1",
|
"@react-email/body": "0.3.0",
|
||||||
"@react-email/button": "0.2.1",
|
"@react-email/button": "0.2.1",
|
||||||
"@react-email/code-block": "0.2.1",
|
"@react-email/code-block": "0.2.1",
|
||||||
"@react-email/code-inline": "0.0.6",
|
"@react-email/code-inline": "0.0.6",
|
||||||
@@ -6470,10 +6458,10 @@
|
|||||||
"@react-email/link": "0.0.13",
|
"@react-email/link": "0.0.13",
|
||||||
"@react-email/markdown": "0.0.18",
|
"@react-email/markdown": "0.0.18",
|
||||||
"@react-email/preview": "0.0.14",
|
"@react-email/preview": "0.0.14",
|
||||||
"@react-email/render": "2.0.4",
|
"@react-email/render": "2.0.5",
|
||||||
"@react-email/row": "0.0.13",
|
"@react-email/row": "0.0.13",
|
||||||
"@react-email/section": "0.0.17",
|
"@react-email/section": "0.0.17",
|
||||||
"@react-email/tailwind": "2.0.5",
|
"@react-email/tailwind": "2.0.7",
|
||||||
"@react-email/text": "0.1.6"
|
"@react-email/text": "0.1.6"
|
||||||
},
|
},
|
||||||
"engines": {
|
"engines": {
|
||||||
@@ -6483,6 +6471,18 @@
|
|||||||
"react": "^18.0 || ^19.0 || ^19.0.0-rc"
|
"react": "^18.0 || ^19.0 || ^19.0.0-rc"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@react-email/components/node_modules/@react-email/body": {
|
||||||
|
"version": "0.3.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@react-email/body/-/body-0.3.0.tgz",
|
||||||
|
"integrity": "sha512-uGo0BOOzjbMUo3lu+BIDWayvn5o6Xyfmnlla5VGf05n8gHMvO1ll7U4FtzWe3hxMLwt53pmc4iE0M+B5slG+Ug==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=20.0.0"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"react": "^18.0 || ^19.0 || ^19.0.0-rc"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/@react-email/container": {
|
"node_modules/@react-email/container": {
|
||||||
"version": "0.0.16",
|
"version": "0.0.16",
|
||||||
"resolved": "https://registry.npmjs.org/@react-email/container/-/container-0.0.16.tgz",
|
"resolved": "https://registry.npmjs.org/@react-email/container/-/container-0.0.16.tgz",
|
||||||
@@ -6854,9 +6854,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@react-email/render": {
|
"node_modules/@react-email/render": {
|
||||||
"version": "2.0.4",
|
"version": "2.0.5",
|
||||||
"resolved": "https://registry.npmjs.org/@react-email/render/-/render-2.0.4.tgz",
|
"resolved": "https://registry.npmjs.org/@react-email/render/-/render-2.0.5.tgz",
|
||||||
"integrity": "sha512-kht2oTFQ1SwrLpd882ahTvUtNa9s53CERHstiTbzhm6aR2Hbykp/mQ4tpPvsBGkKAEvKRlDEoooh60Uk6nHK1g==",
|
"integrity": "sha512-oAsSpY/vYt9ReDcRQDBLxENwCNAklkE6bvP5Kl9ZlmVr/RZpfhloJp8xc/OZki/YF2nisRRX50aEy8P9v3R5GA==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"html-to-text": "^9.0.5",
|
"html-to-text": "^9.0.5",
|
||||||
@@ -6895,9 +6895,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@react-email/tailwind": {
|
"node_modules/@react-email/tailwind": {
|
||||||
"version": "2.0.5",
|
"version": "2.0.7",
|
||||||
"resolved": "https://registry.npmjs.org/@react-email/tailwind/-/tailwind-2.0.5.tgz",
|
"resolved": "https://registry.npmjs.org/@react-email/tailwind/-/tailwind-2.0.7.tgz",
|
||||||
"integrity": "sha512-7Ey+kiWliJdxPMCLYsdDts8ffp4idlP//w4Ui3q/A5kokVaLSNKG8DOg/8qAuzWmRiGwNQVOKBk7PXNlK5W+sg==",
|
"integrity": "sha512-kGw80weVFXikcnCXbigTGXGWQ0MRCSYNCudcdkWxebkWYd0FG6/NPoN3V1p/u68/4+NxZwYPVi2fhnp0x23HdA==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"tailwindcss": "^4.1.18"
|
"tailwindcss": "^4.1.18"
|
||||||
@@ -6906,17 +6906,17 @@
|
|||||||
"node": ">=20.0.0"
|
"node": ">=20.0.0"
|
||||||
},
|
},
|
||||||
"peerDependencies": {
|
"peerDependencies": {
|
||||||
"@react-email/body": "0.2.1",
|
"@react-email/body": ">=0",
|
||||||
"@react-email/button": "0.2.1",
|
"@react-email/button": ">=0",
|
||||||
"@react-email/code-block": "0.2.1",
|
"@react-email/code-block": ">=0",
|
||||||
"@react-email/code-inline": "0.0.6",
|
"@react-email/code-inline": ">=0",
|
||||||
"@react-email/container": "0.0.16",
|
"@react-email/container": ">=0",
|
||||||
"@react-email/heading": "0.0.16",
|
"@react-email/heading": ">=0",
|
||||||
"@react-email/hr": "0.0.12",
|
"@react-email/hr": ">=0",
|
||||||
"@react-email/img": "0.0.12",
|
"@react-email/img": ">=0",
|
||||||
"@react-email/link": "0.0.13",
|
"@react-email/link": ">=0",
|
||||||
"@react-email/preview": "0.0.14",
|
"@react-email/preview": ">=0",
|
||||||
"@react-email/text": "0.1.6",
|
"@react-email/text": ">=0",
|
||||||
"react": "^18.0 || ^19.0 || ^19.0.0-rc"
|
"react": "^18.0 || ^19.0 || ^19.0.0-rc"
|
||||||
},
|
},
|
||||||
"peerDependenciesMeta": {
|
"peerDependenciesMeta": {
|
||||||
@@ -8979,9 +8979,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@types/nodemailer": {
|
"node_modules/@types/nodemailer": {
|
||||||
"version": "7.0.11",
|
"version": "8.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/@types/nodemailer/-/nodemailer-7.0.11.tgz",
|
"resolved": "https://registry.npmjs.org/@types/nodemailer/-/nodemailer-8.0.0.tgz",
|
||||||
"integrity": "sha512-E+U4RzR2dKrx+u3N4DlsmLaDC6mMZOM/TPROxA0UAPiTgI0y4CEFBmZE+coGWTjakDriRsXG368lNk1u9Q0a2g==",
|
"integrity": "sha512-fyf8jWULsCo0d0BuoQ75i6IeoHs47qcqxWc7yUdUcV0pOZGjUTTOvwdG1PRXUDqN/8A64yQdQdnA2pZgcdi+cA==",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
@@ -11731,9 +11731,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/drizzle-orm": {
|
"node_modules/drizzle-orm": {
|
||||||
"version": "0.45.1",
|
"version": "0.45.2",
|
||||||
"resolved": "https://registry.npmjs.org/drizzle-orm/-/drizzle-orm-0.45.1.tgz",
|
"resolved": "https://registry.npmjs.org/drizzle-orm/-/drizzle-orm-0.45.2.tgz",
|
||||||
"integrity": "sha512-Te0FOdKIistGNPMq2jscdqngBRfBpC8uMFVwqjf6gtTVJHIQ/dosgV/CLBU2N4ZJBsXL5savCba9b0YJskKdcA==",
|
"integrity": "sha512-kY0BSaTNYWnoDMVoyY8uxmyHjpJW1geOmBMdSSicKo9CIIWkSxMIj2rkeSR51b8KAPB7m+qysjuHme5nKP+E5Q==",
|
||||||
"license": "Apache-2.0",
|
"license": "Apache-2.0",
|
||||||
"peerDependencies": {
|
"peerDependencies": {
|
||||||
"@aws-sdk/client-rds-data": ">=3",
|
"@aws-sdk/client-rds-data": ">=3",
|
||||||
@@ -12951,9 +12951,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/express-rate-limit": {
|
"node_modules/express-rate-limit": {
|
||||||
"version": "8.3.0",
|
"version": "8.3.2",
|
||||||
"resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-8.3.0.tgz",
|
"resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-8.3.2.tgz",
|
||||||
"integrity": "sha512-KJzBawY6fB9FiZGdE/0aftepZ91YlaGIrV8vgblRM3J8X+dHx/aiowJWwkx6LIGyuqGiANsjSwwrbb8mifOJ4Q==",
|
"integrity": "sha512-77VmFeJkO0/rvimEDuUC5H30oqUC4EyOhyGccfqoLebB0oiEYfM7nwPrsDsBL1gsTpwfzX8SFy2MT3TDyRq+bg==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"ip-address": "10.1.0"
|
"ip-address": "10.1.0"
|
||||||
@@ -13950,9 +13950,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/ioredis": {
|
"node_modules/ioredis": {
|
||||||
"version": "5.10.0",
|
"version": "5.10.1",
|
||||||
"resolved": "https://registry.npmjs.org/ioredis/-/ioredis-5.10.0.tgz",
|
"resolved": "https://registry.npmjs.org/ioredis/-/ioredis-5.10.1.tgz",
|
||||||
"integrity": "sha512-HVBe9OFuqs+Z6n64q09PQvP1/R4Bm+30PAyyD4wIEqssh3v9L21QjCVk4kRLucMBcDokJTcLjsGeVRlq/nH6DA==",
|
"integrity": "sha512-HuEDBTI70aYdx1v6U97SbNx9F1+svQKBDo30o0b9fw055LMepzpOOd0Ccg9Q6tbqmBSJaMuY0fB7yw9/vjBYCA==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@ioredis/commands": "1.5.1",
|
"@ioredis/commands": "1.5.1",
|
||||||
@@ -15098,13 +15098,13 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/maxmind": {
|
"node_modules/maxmind": {
|
||||||
"version": "5.0.5",
|
"version": "5.0.6",
|
||||||
"resolved": "https://registry.npmjs.org/maxmind/-/maxmind-5.0.5.tgz",
|
"resolved": "https://registry.npmjs.org/maxmind/-/maxmind-5.0.6.tgz",
|
||||||
"integrity": "sha512-1lcH2kMjbBpCFhuHaMU32vz8CuOsKttRcWMQyXvtlklopCzN7NNHSVR/h9RYa8JPuFTGmkn2vYARm+7cIGuqDw==",
|
"integrity": "sha512-5bvd/u+kIaTqaGM+xkXjatzQw1dQfSmlLggr2W1EKMyMxSgx2woZyusLpNpZ4DdPmL+1bbJWeo4LXsi6bC0Iew==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"mmdb-lib": "3.0.2",
|
"mmdb-lib": "3.0.2",
|
||||||
"tiny-lru": "11.4.7"
|
"tiny-lru": "13.0.0"
|
||||||
},
|
},
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=12",
|
"node": ">=12",
|
||||||
@@ -15646,9 +15646,9 @@
|
|||||||
"license": "MIT"
|
"license": "MIT"
|
||||||
},
|
},
|
||||||
"node_modules/nodemailer": {
|
"node_modules/nodemailer": {
|
||||||
"version": "8.0.4",
|
"version": "8.0.5",
|
||||||
"resolved": "https://registry.npmjs.org/nodemailer/-/nodemailer-8.0.4.tgz",
|
"resolved": "https://registry.npmjs.org/nodemailer/-/nodemailer-8.0.5.tgz",
|
||||||
"integrity": "sha512-k+jf6N8PfQJ0Fe8ZhJlgqU5qJU44Lpvp2yvidH3vp1lPnVQMgi4yEEMPXg5eJS1gFIJTVq1NHBk7Ia9ARdSBdQ==",
|
"integrity": "sha512-0PF8Yb1yZuQfQbq+5/pZJrtF6WQcjTd5/S4JOHs9PGFxuTqoB/icwuB44pOdURHJbRKX1PPoJZtY7R4VUoCC8w==",
|
||||||
"license": "MIT-0",
|
"license": "MIT-0",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=6.0.0"
|
"node": ">=6.0.0"
|
||||||
@@ -16888,9 +16888,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/react": {
|
"node_modules/react": {
|
||||||
"version": "19.2.4",
|
"version": "19.2.5",
|
||||||
"resolved": "https://registry.npmjs.org/react/-/react-19.2.4.tgz",
|
"resolved": "https://registry.npmjs.org/react/-/react-19.2.5.tgz",
|
||||||
"integrity": "sha512-9nfp2hYpCwOjAN+8TZFGhtWEwgvWHXqESH8qT89AT/lWklpLON22Lc8pEtnpsZz7VmawabSU0gCjnj8aC0euHQ==",
|
"integrity": "sha512-llUJLzz1zTUBrskt2pwZgLq59AemifIftw4aB7JxOqf1HY2FDaGDxgwpAPVzHU1kdWabH7FauP4i1oEeer2WCA==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=0.10.0"
|
"node": ">=0.10.0"
|
||||||
@@ -16919,15 +16919,15 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/react-dom": {
|
"node_modules/react-dom": {
|
||||||
"version": "19.2.4",
|
"version": "19.2.5",
|
||||||
"resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.4.tgz",
|
"resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.5.tgz",
|
||||||
"integrity": "sha512-AXJdLo8kgMbimY95O2aKQqsz2iWi9jMgKJhRBAxECE4IFxfcazB2LmzloIoibJI3C12IlY20+KFaLv+71bUJeQ==",
|
"integrity": "sha512-J5bAZz+DXMMwW/wV3xzKke59Af6CHY7G4uYLN1OvBcKEsWOs4pQExj86BBKamxl/Ik5bx9whOrvBlSDfWzgSag==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"scheduler": "^0.27.0"
|
"scheduler": "^0.27.0"
|
||||||
},
|
},
|
||||||
"peerDependencies": {
|
"peerDependencies": {
|
||||||
"react": "^19.2.4"
|
"react": "^19.2.5"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/react-easy-sort": {
|
"node_modules/react-easy-sort": {
|
||||||
@@ -18733,12 +18733,12 @@
|
|||||||
"license": "MIT"
|
"license": "MIT"
|
||||||
},
|
},
|
||||||
"node_modules/tiny-lru": {
|
"node_modules/tiny-lru": {
|
||||||
"version": "11.4.7",
|
"version": "13.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/tiny-lru/-/tiny-lru-11.4.7.tgz",
|
"resolved": "https://registry.npmjs.org/tiny-lru/-/tiny-lru-13.0.0.tgz",
|
||||||
"integrity": "sha512-w/Te7uMUVeH0CR8vZIjr+XiN41V+30lkDdK+NRIDCUYKKuL9VcmaUEmaPISuwGhLlrTGh5yu18lENtR9axSxYw==",
|
"integrity": "sha512-xDHxKKS1FdF0Tv2P+QT7IeSEg74K/8cEDzbv3Tv6UyHHUgBOjOiQiBp818MGj66dhurQus/IBcoAbwIKtSGc6Q==",
|
||||||
"license": "BSD-3-Clause",
|
"license": "BSD-3-Clause",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=12"
|
"node": ">=14"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/tinyexec": {
|
"node_modules/tinyexec": {
|
||||||
@@ -19329,9 +19329,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/use-debounce": {
|
"node_modules/use-debounce": {
|
||||||
"version": "10.1.0",
|
"version": "10.1.1",
|
||||||
"resolved": "https://registry.npmjs.org/use-debounce/-/use-debounce-10.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/use-debounce/-/use-debounce-10.1.1.tgz",
|
||||||
"integrity": "sha512-lu87Za35V3n/MyMoEpD5zJv0k7hCn0p+V/fK2kWD+3k2u3kOCwO593UArbczg1fhfs2rqPEnHpULJ3KmGdDzvg==",
|
"integrity": "sha512-kvds8BHR2k28cFsxW8k3nc/tRga2rs1RHYCqmmGqb90MEeE++oALwzh2COiuBLO1/QXiOuShXoSN2ZpWnMmvuQ==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">= 16.0.0"
|
"node": ">= 16.0.0"
|
||||||
|
|||||||
26
package.json
26
package.json
@@ -35,7 +35,7 @@
|
|||||||
"@asteasolutions/zod-to-openapi": "8.4.1",
|
"@asteasolutions/zod-to-openapi": "8.4.1",
|
||||||
"@aws-sdk/client-s3": "3.1011.0",
|
"@aws-sdk/client-s3": "3.1011.0",
|
||||||
"@faker-js/faker": "10.3.0",
|
"@faker-js/faker": "10.3.0",
|
||||||
"@headlessui/react": "2.2.9",
|
"@headlessui/react": "2.2.10",
|
||||||
"@hookform/resolvers": "5.2.2",
|
"@hookform/resolvers": "5.2.2",
|
||||||
"@monaco-editor/react": "4.7.0",
|
"@monaco-editor/react": "4.7.0",
|
||||||
"@node-rs/argon2": "2.0.2",
|
"@node-rs/argon2": "2.0.2",
|
||||||
@@ -59,9 +59,9 @@
|
|||||||
"@radix-ui/react-tabs": "1.1.13",
|
"@radix-ui/react-tabs": "1.1.13",
|
||||||
"@radix-ui/react-toast": "1.2.15",
|
"@radix-ui/react-toast": "1.2.15",
|
||||||
"@radix-ui/react-tooltip": "1.2.8",
|
"@radix-ui/react-tooltip": "1.2.8",
|
||||||
"@react-email/components": "1.0.8",
|
"@react-email/components": "1.0.11",
|
||||||
"@react-email/render": "2.0.4",
|
"@react-email/render": "2.0.5",
|
||||||
"@react-email/tailwind": "2.0.5",
|
"@react-email/tailwind": "2.0.7",
|
||||||
"@simplewebauthn/browser": "13.3.0",
|
"@simplewebauthn/browser": "13.3.0",
|
||||||
"@simplewebauthn/server": "13.3.0",
|
"@simplewebauthn/server": "13.3.0",
|
||||||
"@tailwindcss/forms": "0.5.11",
|
"@tailwindcss/forms": "0.5.11",
|
||||||
@@ -78,33 +78,33 @@
|
|||||||
"cors": "2.8.6",
|
"cors": "2.8.6",
|
||||||
"crypto-js": "4.2.0",
|
"crypto-js": "4.2.0",
|
||||||
"d3": "7.9.0",
|
"d3": "7.9.0",
|
||||||
"drizzle-orm": "0.45.1",
|
"drizzle-orm": "0.45.2",
|
||||||
"express": "5.2.1",
|
"express": "5.2.1",
|
||||||
"express-rate-limit": "8.3.0",
|
"express-rate-limit": "8.3.2",
|
||||||
"glob": "13.0.6",
|
"glob": "13.0.6",
|
||||||
"helmet": "8.1.0",
|
"helmet": "8.1.0",
|
||||||
"http-errors": "2.0.1",
|
"http-errors": "2.0.1",
|
||||||
"input-otp": "1.4.2",
|
"input-otp": "1.4.2",
|
||||||
"ioredis": "5.10.0",
|
"ioredis": "5.10.1",
|
||||||
"jmespath": "0.16.0",
|
"jmespath": "0.16.0",
|
||||||
"js-yaml": "4.1.1",
|
"js-yaml": "4.1.1",
|
||||||
"jsonwebtoken": "9.0.3",
|
"jsonwebtoken": "9.0.3",
|
||||||
"lucide-react": "0.577.0",
|
"lucide-react": "0.577.0",
|
||||||
"maxmind": "5.0.5",
|
"maxmind": "5.0.6",
|
||||||
"moment": "2.30.1",
|
"moment": "2.30.1",
|
||||||
"next": "15.5.14",
|
"next": "15.5.14",
|
||||||
"next-intl": "4.8.3",
|
"next-intl": "4.8.3",
|
||||||
"next-themes": "0.4.6",
|
"next-themes": "0.4.6",
|
||||||
"nextjs-toploader": "3.9.17",
|
"nextjs-toploader": "3.9.17",
|
||||||
"node-cache": "5.1.2",
|
"node-cache": "5.1.2",
|
||||||
"nodemailer": "8.0.4",
|
"nodemailer": "8.0.5",
|
||||||
"oslo": "1.2.1",
|
"oslo": "1.2.1",
|
||||||
"pg": "8.20.0",
|
"pg": "8.20.0",
|
||||||
"posthog-node": "5.28.0",
|
"posthog-node": "5.28.0",
|
||||||
"qrcode.react": "4.2.0",
|
"qrcode.react": "4.2.0",
|
||||||
"react": "19.2.4",
|
"react": "19.2.5",
|
||||||
"react-day-picker": "9.14.0",
|
"react-day-picker": "9.14.0",
|
||||||
"react-dom": "19.2.4",
|
"react-dom": "19.2.5",
|
||||||
"react-easy-sort": "1.8.0",
|
"react-easy-sort": "1.8.0",
|
||||||
"react-hook-form": "7.71.2",
|
"react-hook-form": "7.71.2",
|
||||||
"react-icons": "5.6.0",
|
"react-icons": "5.6.0",
|
||||||
@@ -118,7 +118,7 @@
|
|||||||
"tailwind-merge": "3.5.0",
|
"tailwind-merge": "3.5.0",
|
||||||
"topojson-client": "3.1.0",
|
"topojson-client": "3.1.0",
|
||||||
"tw-animate-css": "1.4.0",
|
"tw-animate-css": "1.4.0",
|
||||||
"use-debounce": "10.1.0",
|
"use-debounce": "10.1.1",
|
||||||
"uuid": "13.0.0",
|
"uuid": "13.0.0",
|
||||||
"vaul": "1.1.2",
|
"vaul": "1.1.2",
|
||||||
"visionscarto-world-atlas": "1.0.0",
|
"visionscarto-world-atlas": "1.0.0",
|
||||||
@@ -147,7 +147,7 @@
|
|||||||
"@types/js-yaml": "4.0.9",
|
"@types/js-yaml": "4.0.9",
|
||||||
"@types/jsonwebtoken": "9.0.10",
|
"@types/jsonwebtoken": "9.0.10",
|
||||||
"@types/node": "25.3.5",
|
"@types/node": "25.3.5",
|
||||||
"@types/nodemailer": "7.0.11",
|
"@types/nodemailer": "8.0.0",
|
||||||
"@types/nprogress": "0.2.3",
|
"@types/nprogress": "0.2.3",
|
||||||
"@types/pg": "8.18.0",
|
"@types/pg": "8.18.0",
|
||||||
"@types/react": "19.2.14",
|
"@types/react": "19.2.14",
|
||||||
|
|||||||
@@ -19,8 +19,7 @@ export enum TierFeature {
|
|||||||
SshPam = "sshPam",
|
SshPam = "sshPam",
|
||||||
FullRbac = "fullRbac",
|
FullRbac = "fullRbac",
|
||||||
SiteProvisioningKeys = "siteProvisioningKeys", // handle downgrade by revoking keys if needed
|
SiteProvisioningKeys = "siteProvisioningKeys", // handle downgrade by revoking keys if needed
|
||||||
SIEM = "siem", // handle downgrade by disabling SIEM integrations
|
SIEM = "siem" // handle downgrade by disabling SIEM integrations
|
||||||
DomainNamespaces = "domainNamespaces" // handle downgrade by removing custom domain namespaces
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export const tierMatrix: Record<TierFeature, Tier[]> = {
|
export const tierMatrix: Record<TierFeature, Tier[]> = {
|
||||||
@@ -57,6 +56,5 @@ export const tierMatrix: Record<TierFeature, Tier[]> = {
|
|||||||
[TierFeature.SshPam]: ["tier1", "tier3", "enterprise"],
|
[TierFeature.SshPam]: ["tier1", "tier3", "enterprise"],
|
||||||
[TierFeature.FullRbac]: ["tier1", "tier2", "tier3", "enterprise"],
|
[TierFeature.FullRbac]: ["tier1", "tier2", "tier3", "enterprise"],
|
||||||
[TierFeature.SiteProvisioningKeys]: ["tier3", "enterprise"],
|
[TierFeature.SiteProvisioningKeys]: ["tier3", "enterprise"],
|
||||||
[TierFeature.SIEM]: ["enterprise"],
|
[TierFeature.SIEM]: ["enterprise"]
|
||||||
[TierFeature.DomainNamespaces]: ["tier1", "tier2", "tier3", "enterprise"]
|
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -22,15 +22,11 @@ import { OpenAPITags, registry } from "@server/openApi";
|
|||||||
import { db, domainNamespaces, resources } from "@server/db";
|
import { db, domainNamespaces, resources } from "@server/db";
|
||||||
import { inArray } from "drizzle-orm";
|
import { inArray } from "drizzle-orm";
|
||||||
import { CheckDomainAvailabilityResponse } from "@server/routers/domain/types";
|
import { CheckDomainAvailabilityResponse } from "@server/routers/domain/types";
|
||||||
import { build } from "@server/build";
|
|
||||||
import { isSubscribed } from "#private/lib/isSubscribed";
|
|
||||||
import { tierMatrix } from "@server/lib/billing/tierMatrix";
|
|
||||||
|
|
||||||
const paramsSchema = z.strictObject({});
|
const paramsSchema = z.strictObject({});
|
||||||
|
|
||||||
const querySchema = z.strictObject({
|
const querySchema = z.strictObject({
|
||||||
subdomain: z.string(),
|
subdomain: z.string()
|
||||||
// orgId: build === "saas" ? z.string() : z.string().optional() // Required for saas, optional otherwise
|
|
||||||
});
|
});
|
||||||
|
|
||||||
registry.registerPath({
|
registry.registerPath({
|
||||||
@@ -62,23 +58,6 @@ export async function checkDomainNamespaceAvailability(
|
|||||||
}
|
}
|
||||||
const { subdomain } = parsedQuery.data;
|
const { subdomain } = parsedQuery.data;
|
||||||
|
|
||||||
// if (
|
|
||||||
// build == "saas" &&
|
|
||||||
// !isSubscribed(orgId!, tierMatrix.domainNamespaces)
|
|
||||||
// ) {
|
|
||||||
// // return not available
|
|
||||||
// return response<CheckDomainAvailabilityResponse>(res, {
|
|
||||||
// data: {
|
|
||||||
// available: false,
|
|
||||||
// options: []
|
|
||||||
// },
|
|
||||||
// success: true,
|
|
||||||
// error: false,
|
|
||||||
// message: "Your current subscription does not support custom domain namespaces. Please upgrade to access this feature.",
|
|
||||||
// status: HttpCode.OK
|
|
||||||
// });
|
|
||||||
// }
|
|
||||||
|
|
||||||
const namespaces = await db.select().from(domainNamespaces);
|
const namespaces = await db.select().from(domainNamespaces);
|
||||||
let possibleDomains = namespaces.map((ns) => {
|
let possibleDomains = namespaces.map((ns) => {
|
||||||
const desired = `${subdomain}.${ns.domainNamespaceId}`;
|
const desired = `${subdomain}.${ns.domainNamespaceId}`;
|
||||||
|
|||||||
@@ -22,9 +22,6 @@ import { eq, sql } from "drizzle-orm";
|
|||||||
import logger from "@server/logger";
|
import logger from "@server/logger";
|
||||||
import { fromError } from "zod-validation-error";
|
import { fromError } from "zod-validation-error";
|
||||||
import { OpenAPITags, registry } from "@server/openApi";
|
import { OpenAPITags, registry } from "@server/openApi";
|
||||||
import { isSubscribed } from "#private/lib/isSubscribed";
|
|
||||||
import { build } from "@server/build";
|
|
||||||
import { tierMatrix } from "@server/lib/billing/tierMatrix";
|
|
||||||
|
|
||||||
const paramsSchema = z.strictObject({});
|
const paramsSchema = z.strictObject({});
|
||||||
|
|
||||||
@@ -40,8 +37,7 @@ const querySchema = z.strictObject({
|
|||||||
.optional()
|
.optional()
|
||||||
.default("0")
|
.default("0")
|
||||||
.transform(Number)
|
.transform(Number)
|
||||||
.pipe(z.int().nonnegative()),
|
.pipe(z.int().nonnegative())
|
||||||
// orgId: build === "saas" ? z.string() : z.string().optional() // Required for saas, optional otherwise
|
|
||||||
});
|
});
|
||||||
|
|
||||||
async function query(limit: number, offset: number) {
|
async function query(limit: number, offset: number) {
|
||||||
@@ -103,26 +99,6 @@ export async function listDomainNamespaces(
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
// if (
|
|
||||||
// build == "saas" &&
|
|
||||||
// !isSubscribed(orgId!, tierMatrix.domainNamespaces)
|
|
||||||
// ) {
|
|
||||||
// return response<ListDomainNamespacesResponse>(res, {
|
|
||||||
// data: {
|
|
||||||
// domainNamespaces: [],
|
|
||||||
// pagination: {
|
|
||||||
// total: 0,
|
|
||||||
// limit,
|
|
||||||
// offset
|
|
||||||
// }
|
|
||||||
// },
|
|
||||||
// success: true,
|
|
||||||
// error: false,
|
|
||||||
// message: "No namespaces found. Your current subscription does not support custom domain namespaces. Please upgrade to access this feature.",
|
|
||||||
// status: HttpCode.OK
|
|
||||||
// });
|
|
||||||
// }
|
|
||||||
|
|
||||||
const domainNamespacesList = await query(limit, offset);
|
const domainNamespacesList = await query(limit, offset);
|
||||||
|
|
||||||
const [{ count }] = await db
|
const [{ count }] = await db
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import { Request, Response, NextFunction } from "express";
|
import { Request, Response, NextFunction } from "express";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
import { db, domainNamespaces, loginPage } from "@server/db";
|
import { db, loginPage } from "@server/db";
|
||||||
import {
|
import {
|
||||||
domains,
|
domains,
|
||||||
orgDomains,
|
orgDomains,
|
||||||
@@ -24,8 +24,6 @@ import { build } from "@server/build";
|
|||||||
import { createCertificate } from "#dynamic/routers/certificates/createCertificate";
|
import { createCertificate } from "#dynamic/routers/certificates/createCertificate";
|
||||||
import { getUniqueResourceName } from "@server/db/names";
|
import { getUniqueResourceName } from "@server/db/names";
|
||||||
import { validateAndConstructDomain } from "@server/lib/domainUtils";
|
import { validateAndConstructDomain } from "@server/lib/domainUtils";
|
||||||
import { isSubscribed } from "#dynamic/lib/isSubscribed";
|
|
||||||
import { tierMatrix } from "@server/lib/billing/tierMatrix";
|
|
||||||
|
|
||||||
const createResourceParamsSchema = z.strictObject({
|
const createResourceParamsSchema = z.strictObject({
|
||||||
orgId: z.string()
|
orgId: z.string()
|
||||||
@@ -195,27 +193,6 @@ async function createHttpResource(
|
|||||||
const subdomain = parsedBody.data.subdomain;
|
const subdomain = parsedBody.data.subdomain;
|
||||||
const stickySession = parsedBody.data.stickySession;
|
const stickySession = parsedBody.data.stickySession;
|
||||||
|
|
||||||
if (
|
|
||||||
build == "saas" &&
|
|
||||||
!isSubscribed(orgId!, tierMatrix.domainNamespaces)
|
|
||||||
) {
|
|
||||||
// check if this domain id is a namespace domain and if so, reject
|
|
||||||
const domain = await db
|
|
||||||
.select()
|
|
||||||
.from(domainNamespaces)
|
|
||||||
.where(eq(domainNamespaces.domainId, domainId))
|
|
||||||
.limit(1);
|
|
||||||
|
|
||||||
if (domain.length > 0) {
|
|
||||||
return next(
|
|
||||||
createHttpError(
|
|
||||||
HttpCode.BAD_REQUEST,
|
|
||||||
"Your current subscription does not support custom domain namespaces. Please upgrade to access this feature."
|
|
||||||
)
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Validate domain and construct full domain
|
// Validate domain and construct full domain
|
||||||
const domainResult = await validateAndConstructDomain(
|
const domainResult = await validateAndConstructDomain(
|
||||||
domainId,
|
domainId,
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import { Request, Response, NextFunction } from "express";
|
import { Request, Response, NextFunction } from "express";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
import { db, domainNamespaces, loginPage } from "@server/db";
|
import { db, loginPage } from "@server/db";
|
||||||
import {
|
import {
|
||||||
domains,
|
domains,
|
||||||
Org,
|
Org,
|
||||||
@@ -25,7 +25,6 @@ import { validateAndConstructDomain } from "@server/lib/domainUtils";
|
|||||||
import { build } from "@server/build";
|
import { build } from "@server/build";
|
||||||
import { isLicensedOrSubscribed } from "#dynamic/lib/isLicencedOrSubscribed";
|
import { isLicensedOrSubscribed } from "#dynamic/lib/isLicencedOrSubscribed";
|
||||||
import { tierMatrix } from "@server/lib/billing/tierMatrix";
|
import { tierMatrix } from "@server/lib/billing/tierMatrix";
|
||||||
import { isSubscribed } from "#dynamic/lib/isSubscribed";
|
|
||||||
|
|
||||||
const updateResourceParamsSchema = z.strictObject({
|
const updateResourceParamsSchema = z.strictObject({
|
||||||
resourceId: z.string().transform(Number).pipe(z.int().positive())
|
resourceId: z.string().transform(Number).pipe(z.int().positive())
|
||||||
@@ -319,27 +318,6 @@ async function updateHttpResource(
|
|||||||
if (updateData.domainId) {
|
if (updateData.domainId) {
|
||||||
const domainId = updateData.domainId;
|
const domainId = updateData.domainId;
|
||||||
|
|
||||||
if (
|
|
||||||
build == "saas" &&
|
|
||||||
!isSubscribed(resource.orgId, tierMatrix.domainNamespaces)
|
|
||||||
) {
|
|
||||||
// check if this domain id is a namespace domain and if so, reject
|
|
||||||
const domain = await db
|
|
||||||
.select()
|
|
||||||
.from(domainNamespaces)
|
|
||||||
.where(eq(domainNamespaces.domainId, domainId))
|
|
||||||
.limit(1);
|
|
||||||
|
|
||||||
if (domain.length > 0) {
|
|
||||||
return next(
|
|
||||||
createHttpError(
|
|
||||||
HttpCode.BAD_REQUEST,
|
|
||||||
"Your current subscription does not support custom domain namespaces. Please upgrade to access this feature."
|
|
||||||
)
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Validate domain and construct full domain
|
// Validate domain and construct full domain
|
||||||
const domainResult = await validateAndConstructDomain(
|
const domainResult = await validateAndConstructDomain(
|
||||||
domainId,
|
domainId,
|
||||||
@@ -388,7 +366,7 @@ async function updateHttpResource(
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (build != "oss") {
|
if (build != "oss") {
|
||||||
const existingLoginPages = await db
|
const existingLoginPages = await db
|
||||||
.select()
|
.select()
|
||||||
|
|||||||
@@ -235,9 +235,7 @@ export default async function migration() {
|
|||||||
for (const row of existingUserInviteRoles) {
|
for (const row of existingUserInviteRoles) {
|
||||||
await db.execute(sql`
|
await db.execute(sql`
|
||||||
INSERT INTO "userInviteRoles" ("inviteId", "roleId")
|
INSERT INTO "userInviteRoles" ("inviteId", "roleId")
|
||||||
SELECT ${row.inviteId}, ${row.roleId}
|
VALUES (${row.inviteId}, ${row.roleId})
|
||||||
WHERE EXISTS (SELECT 1 FROM "userInvites" WHERE "inviteId" = ${row.inviteId})
|
|
||||||
AND EXISTS (SELECT 1 FROM "roles" WHERE "roleId" = ${row.roleId})
|
|
||||||
ON CONFLICT DO NOTHING
|
ON CONFLICT DO NOTHING
|
||||||
`);
|
`);
|
||||||
}
|
}
|
||||||
@@ -260,10 +258,7 @@ export default async function migration() {
|
|||||||
for (const row of existingUserOrgRoles) {
|
for (const row of existingUserOrgRoles) {
|
||||||
await db.execute(sql`
|
await db.execute(sql`
|
||||||
INSERT INTO "userOrgRoles" ("userId", "orgId", "roleId")
|
INSERT INTO "userOrgRoles" ("userId", "orgId", "roleId")
|
||||||
SELECT ${row.userId}, ${row.orgId}, ${row.roleId}
|
VALUES (${row.userId}, ${row.orgId}, ${row.roleId})
|
||||||
WHERE EXISTS (SELECT 1 FROM "user" WHERE "id" = ${row.userId})
|
|
||||||
AND EXISTS (SELECT 1 FROM "orgs" WHERE "orgId" = ${row.orgId})
|
|
||||||
AND EXISTS (SELECT 1 FROM "roles" WHERE "roleId" = ${row.roleId})
|
|
||||||
ON CONFLICT DO NOTHING
|
ON CONFLICT DO NOTHING
|
||||||
`);
|
`);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -145,7 +145,7 @@ export default async function migration() {
|
|||||||
).run();
|
).run();
|
||||||
|
|
||||||
db.prepare(
|
db.prepare(
|
||||||
`INSERT INTO '__new_userOrgs'("userId", "orgId", "isOwner", "autoProvisioned", "pamUsername") SELECT "userId", "orgId", "isOwner", "autoProvisioned", "pamUsername" FROM 'userOrgs' WHERE EXISTS (SELECT 1 FROM 'user' WHERE id = userOrgs.userId) AND EXISTS (SELECT 1 FROM 'orgs' WHERE orgId = userOrgs.orgId);`
|
`INSERT INTO '__new_userOrgs'("userId", "orgId", "isOwner", "autoProvisioned", "pamUsername") SELECT "userId", "orgId", "isOwner", "autoProvisioned", "pamUsername" FROM 'userOrgs';`
|
||||||
).run();
|
).run();
|
||||||
db.prepare(`DROP TABLE 'userOrgs';`).run();
|
db.prepare(`DROP TABLE 'userOrgs';`).run();
|
||||||
db.prepare(
|
db.prepare(
|
||||||
@@ -246,15 +246,12 @@ export default async function migration() {
|
|||||||
// Re-insert the preserved invite role assignments into the new userInviteRoles table
|
// Re-insert the preserved invite role assignments into the new userInviteRoles table
|
||||||
if (existingUserInviteRoles.length > 0) {
|
if (existingUserInviteRoles.length > 0) {
|
||||||
const insertUserInviteRole = db.prepare(
|
const insertUserInviteRole = db.prepare(
|
||||||
`INSERT OR IGNORE INTO 'userInviteRoles' ("inviteId", "roleId")
|
`INSERT OR IGNORE INTO 'userInviteRoles' ("inviteId", "roleId") VALUES (?, ?)`
|
||||||
SELECT ?, ?
|
|
||||||
WHERE EXISTS (SELECT 1 FROM 'userInvites' WHERE inviteId = ?)
|
|
||||||
AND EXISTS (SELECT 1 FROM 'roles' WHERE roleId = ?)`
|
|
||||||
);
|
);
|
||||||
|
|
||||||
const insertAll = db.transaction(() => {
|
const insertAll = db.transaction(() => {
|
||||||
for (const row of existingUserInviteRoles) {
|
for (const row of existingUserInviteRoles) {
|
||||||
insertUserInviteRole.run(row.inviteId, row.roleId, row.inviteId, row.roleId);
|
insertUserInviteRole.run(row.inviteId, row.roleId);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -268,16 +265,12 @@ export default async function migration() {
|
|||||||
// Re-insert the preserved role assignments into the new userOrgRoles table
|
// Re-insert the preserved role assignments into the new userOrgRoles table
|
||||||
if (existingUserOrgRoles.length > 0) {
|
if (existingUserOrgRoles.length > 0) {
|
||||||
const insertUserOrgRole = db.prepare(
|
const insertUserOrgRole = db.prepare(
|
||||||
`INSERT OR IGNORE INTO 'userOrgRoles' ("userId", "orgId", "roleId")
|
`INSERT OR IGNORE INTO 'userOrgRoles' ("userId", "orgId", "roleId") VALUES (?, ?, ?)`
|
||||||
SELECT ?, ?, ?
|
|
||||||
WHERE EXISTS (SELECT 1 FROM 'user' WHERE id = ?)
|
|
||||||
AND EXISTS (SELECT 1 FROM 'orgs' WHERE orgId = ?)
|
|
||||||
AND EXISTS (SELECT 1 FROM 'roles' WHERE roleId = ?)`
|
|
||||||
);
|
);
|
||||||
|
|
||||||
const insertAll = db.transaction(() => {
|
const insertAll = db.transaction(() => {
|
||||||
for (const row of existingUserOrgRoles) {
|
for (const row of existingUserOrgRoles) {
|
||||||
insertUserOrgRole.run(row.userId, row.orgId, row.roleId, row.userId, row.orgId, row.roleId);
|
insertUserOrgRole.run(row.userId, row.orgId, row.roleId);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -10,7 +10,6 @@ import { authCookieHeader } from "@app/lib/api/cookies";
|
|||||||
import { GetDNSRecordsResponse } from "@server/routers/domain";
|
import { GetDNSRecordsResponse } from "@server/routers/domain";
|
||||||
import DNSRecordsTable from "@app/components/DNSRecordTable";
|
import DNSRecordsTable from "@app/components/DNSRecordTable";
|
||||||
import DomainCertForm from "@app/components/DomainCertForm";
|
import DomainCertForm from "@app/components/DomainCertForm";
|
||||||
import { build } from "@server/build";
|
|
||||||
|
|
||||||
interface DomainSettingsPageProps {
|
interface DomainSettingsPageProps {
|
||||||
params: Promise<{ domainId: string; orgId: string }>;
|
params: Promise<{ domainId: string; orgId: string }>;
|
||||||
@@ -66,14 +65,12 @@ export default async function DomainSettingsPage({
|
|||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
<div className="space-y-6">
|
<div className="space-y-6">
|
||||||
{build != "oss" && env.flags.usePangolinDns ? (
|
<DomainInfoCard
|
||||||
<DomainInfoCard
|
failed={domain.failed}
|
||||||
failed={domain.failed}
|
verified={domain.verified}
|
||||||
verified={domain.verified}
|
type={domain.type}
|
||||||
type={domain.type}
|
errorMessage={domain.errorMessage}
|
||||||
errorMessage={domain.errorMessage}
|
/>
|
||||||
/>
|
|
||||||
) : null}
|
|
||||||
|
|
||||||
<DNSRecordsTable records={dnsRecords} type={domain.type} />
|
<DNSRecordsTable records={dnsRecords} type={domain.type} />
|
||||||
|
|
||||||
|
|||||||
@@ -154,7 +154,7 @@ export default function CreateDomainForm({
|
|||||||
|
|
||||||
const punycodePreview = useMemo(() => {
|
const punycodePreview = useMemo(() => {
|
||||||
if (!baseDomain) return "";
|
if (!baseDomain) return "";
|
||||||
const punycode = toPunycode(baseDomain.toLowerCase());
|
const punycode = toPunycode(baseDomain);
|
||||||
return punycode !== baseDomain.toLowerCase() ? punycode : "";
|
return punycode !== baseDomain.toLowerCase() ? punycode : "";
|
||||||
}, [baseDomain]);
|
}, [baseDomain]);
|
||||||
|
|
||||||
@@ -239,24 +239,21 @@ export default function CreateDomainForm({
|
|||||||
className="space-y-4"
|
className="space-y-4"
|
||||||
id="create-domain-form"
|
id="create-domain-form"
|
||||||
>
|
>
|
||||||
{build != "oss" && env.flags.usePangolinDns ? (
|
<FormField
|
||||||
<FormField
|
control={form.control}
|
||||||
control={form.control}
|
name="type"
|
||||||
name="type"
|
render={({ field }) => (
|
||||||
render={({ field }) => (
|
<FormItem>
|
||||||
<FormItem>
|
<StrategySelect
|
||||||
<StrategySelect
|
options={domainOptions}
|
||||||
options={domainOptions}
|
defaultValue={field.value}
|
||||||
defaultValue={field.value}
|
onChange={field.onChange}
|
||||||
onChange={field.onChange}
|
cols={1}
|
||||||
cols={1}
|
/>
|
||||||
/>
|
<FormMessage />
|
||||||
<FormMessage />
|
</FormItem>
|
||||||
</FormItem>
|
)}
|
||||||
)}
|
/>
|
||||||
/>
|
|
||||||
) : null}
|
|
||||||
|
|
||||||
<FormField
|
<FormField
|
||||||
control={form.control}
|
control={form.control}
|
||||||
name="baseDomain"
|
name="baseDomain"
|
||||||
|
|||||||
@@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
import { Alert, AlertDescription } from "@/components/ui/alert";
|
import { Alert, AlertDescription } from "@/components/ui/alert";
|
||||||
import { Button } from "@/components/ui/button";
|
import { Button } from "@/components/ui/button";
|
||||||
import { Card, CardContent } from "@/components/ui/card";
|
|
||||||
import {
|
import {
|
||||||
Command,
|
Command,
|
||||||
CommandEmpty,
|
CommandEmpty,
|
||||||
@@ -41,12 +40,9 @@ import {
|
|||||||
Check,
|
Check,
|
||||||
CheckCircle2,
|
CheckCircle2,
|
||||||
ChevronsUpDown,
|
ChevronsUpDown,
|
||||||
KeyRound,
|
|
||||||
Zap
|
Zap
|
||||||
} from "lucide-react";
|
} from "lucide-react";
|
||||||
import { useTranslations } from "next-intl";
|
import { useTranslations } from "next-intl";
|
||||||
import { usePaidStatus } from "@/hooks/usePaidStatus";
|
|
||||||
import { TierFeature, tierMatrix } from "@server/lib/billing/tierMatrix";
|
|
||||||
import { toUnicode } from "punycode";
|
import { toUnicode } from "punycode";
|
||||||
import { useCallback, useEffect, useMemo, useState } from "react";
|
import { useCallback, useEffect, useMemo, useState } from "react";
|
||||||
|
|
||||||
@@ -99,7 +95,6 @@ export default function DomainPicker({
|
|||||||
const { env } = useEnvContext();
|
const { env } = useEnvContext();
|
||||||
const api = createApiClient({ env });
|
const api = createApiClient({ env });
|
||||||
const t = useTranslations();
|
const t = useTranslations();
|
||||||
const { hasSaasSubscription } = usePaidStatus();
|
|
||||||
|
|
||||||
const { data = [], isLoading: loadingDomains } = useQuery(
|
const { data = [], isLoading: loadingDomains } = useQuery(
|
||||||
orgQueries.domains({ orgId })
|
orgQueries.domains({ orgId })
|
||||||
@@ -514,11 +509,9 @@ export default function DomainPicker({
|
|||||||
<span className="truncate">
|
<span className="truncate">
|
||||||
{selectedBaseDomain.domain}
|
{selectedBaseDomain.domain}
|
||||||
</span>
|
</span>
|
||||||
{selectedBaseDomain.verified &&
|
{selectedBaseDomain.verified && (
|
||||||
selectedBaseDomain.domainType !==
|
<CheckCircle2 className="h-3 w-3 text-green-500 shrink-0" />
|
||||||
"wildcard" && (
|
)}
|
||||||
<CheckCircle2 className="h-3 w-3 text-green-500 shrink-0" />
|
|
||||||
)}
|
|
||||||
</div>
|
</div>
|
||||||
) : (
|
) : (
|
||||||
t("domainPickerSelectBaseDomain")
|
t("domainPickerSelectBaseDomain")
|
||||||
@@ -581,23 +574,14 @@ export default function DomainPicker({
|
|||||||
}
|
}
|
||||||
</span>
|
</span>
|
||||||
<span className="text-xs text-muted-foreground">
|
<span className="text-xs text-muted-foreground">
|
||||||
{orgDomain.type ===
|
{orgDomain.type.toUpperCase()}{" "}
|
||||||
"wildcard"
|
•{" "}
|
||||||
|
{orgDomain.verified
|
||||||
? t(
|
? t(
|
||||||
"domainPickerManual"
|
"domainPickerVerified"
|
||||||
)
|
)
|
||||||
: (
|
: t(
|
||||||
<>
|
"domainPickerUnverified"
|
||||||
{orgDomain.type.toUpperCase()}{" "}
|
|
||||||
•{" "}
|
|
||||||
{orgDomain.verified
|
|
||||||
? t(
|
|
||||||
"domainPickerVerified"
|
|
||||||
)
|
|
||||||
: t(
|
|
||||||
"domainPickerUnverified"
|
|
||||||
)}
|
|
||||||
</>
|
|
||||||
)}
|
)}
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
@@ -696,23 +680,6 @@ export default function DomainPicker({
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{build === "saas" &&
|
|
||||||
!hasSaasSubscription(
|
|
||||||
tierMatrix[TierFeature.DomainNamespaces]
|
|
||||||
) &&
|
|
||||||
!hideFreeDomain && (
|
|
||||||
<Card className="mt-3 border-black-500/30 bg-linear-to-br from-black-500/10 via-background to-background overflow-hidden">
|
|
||||||
<CardContent className="py-3 px-4">
|
|
||||||
<div className="flex items-center gap-2.5 text-sm text-muted-foreground">
|
|
||||||
<KeyRound className="size-4 shrink-0 text-black-500" />
|
|
||||||
<span>
|
|
||||||
{t("domainPickerFreeDomainsPaidFeature")}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</CardContent>
|
|
||||||
</Card>
|
|
||||||
)}
|
|
||||||
|
|
||||||
{/*showProvidedDomainSearch && build === "saas" && (
|
{/*showProvidedDomainSearch && build === "saas" && (
|
||||||
<Alert>
|
<Alert>
|
||||||
<AlertCircle className="h-4 w-4" />
|
<AlertCircle className="h-4 w-4" />
|
||||||
|
|||||||
@@ -333,8 +333,7 @@ export default function PendingSitesTable({
|
|||||||
"jupiter",
|
"jupiter",
|
||||||
"saturn",
|
"saturn",
|
||||||
"uranus",
|
"uranus",
|
||||||
"neptune",
|
"neptune"
|
||||||
"pluto"
|
|
||||||
].includes(originalRow.exitNodeName.toLowerCase());
|
].includes(originalRow.exitNodeName.toLowerCase());
|
||||||
|
|
||||||
if (isCloudNode) {
|
if (isCloudNode) {
|
||||||
|
|||||||
@@ -342,8 +342,7 @@ export default function SitesTable({
|
|||||||
"jupiter",
|
"jupiter",
|
||||||
"saturn",
|
"saturn",
|
||||||
"uranus",
|
"uranus",
|
||||||
"neptune",
|
"neptune"
|
||||||
"pluto"
|
|
||||||
].includes(originalRow.exitNodeName.toLowerCase());
|
].includes(originalRow.exitNodeName.toLowerCase());
|
||||||
|
|
||||||
if (isCloudNode) {
|
if (isCloudNode) {
|
||||||
|
|||||||
Reference in New Issue
Block a user