mirror of
https://github.com/zen-browser/www.git
synced 2025-07-08 01:10:02 +02:00
Merge branch 'main' into refactor/app
This commit is contained in:
commit
da8dfd63bd
26 changed files with 948 additions and 371 deletions
37
.editorconfig
Normal file
37
.editorconfig
Normal file
|
@ -0,0 +1,37 @@
|
|||
# EditorConfig is awesome: https://EditorConfig.org
|
||||
|
||||
# top-most EditorConfig file
|
||||
root = true
|
||||
|
||||
# Default settings for all files
|
||||
[*]
|
||||
charset = utf-8
|
||||
end_of_line = lf
|
||||
insert_final_newline = true
|
||||
trim_trailing_whitespace = true
|
||||
indent_style = space
|
||||
indent_size = 2
|
||||
|
||||
# Markdown files
|
||||
[*.{md,markdown}]
|
||||
trim_trailing_whitespace = false
|
||||
|
||||
# YAML files
|
||||
[*.{yml,yaml}]
|
||||
indent_size = 2
|
||||
|
||||
# JSON files
|
||||
[*.{json,jsonc}]
|
||||
indent_size = 2
|
||||
|
||||
# TypeScript and JavaScript files
|
||||
[*.{ts,tsx,js,jsx}]
|
||||
indent_size = 2
|
||||
|
||||
# Astro files
|
||||
[*.astro]
|
||||
indent_size = 2
|
||||
|
||||
# Configuration files
|
||||
[{*.config.js,*.config.ts}]
|
||||
indent_size = 2
|
3
.github/workflows/prbuildcheck.yml
vendored
3
.github/workflows/prbuildcheck.yml
vendored
|
@ -21,5 +21,8 @@ jobs:
|
|||
- name: Install dependencies
|
||||
run: npm install --no-frozen-lockfile
|
||||
|
||||
- name: Run Biome check
|
||||
run: npx biome check ./src
|
||||
|
||||
- name: Build project
|
||||
run: npm run build
|
||||
|
|
1
.husky/pre-commit
Normal file
1
.husky/pre-commit
Normal file
|
@ -0,0 +1 @@
|
|||
npx lint-staged
|
|
@ -1,9 +0,0 @@
|
|||
/** @type {import('prettier').Config} */
|
||||
export default {
|
||||
printWidth: 80,
|
||||
tabWidth: 2,
|
||||
semi: false,
|
||||
singleQuote: true,
|
||||
endOfLine: 'lf',
|
||||
plugins: ['prettier-plugin-astro', 'prettier-plugin-tailwindcss'],
|
||||
}
|
35
biome.json
Normal file
35
biome.json
Normal file
|
@ -0,0 +1,35 @@
|
|||
{
|
||||
"$schema": "https://biomejs.dev/schemas/1.9.4/schema.json",
|
||||
"organizeImports": {
|
||||
"enabled": true
|
||||
},
|
||||
"linter": {
|
||||
"enabled": true,
|
||||
"rules": {
|
||||
"recommended": true,
|
||||
"nursery": {
|
||||
"useSortedClasses": "info"
|
||||
}
|
||||
}
|
||||
},
|
||||
"formatter": {
|
||||
"enabled": true,
|
||||
"indentStyle": "space",
|
||||
"indentWidth": 2,
|
||||
"lineWidth": 128,
|
||||
"useEditorconfig": true
|
||||
},
|
||||
"files": {
|
||||
"ignore": [
|
||||
"node_modules",
|
||||
".git",
|
||||
"dist"
|
||||
]
|
||||
},
|
||||
"javascript": {
|
||||
"formatter": {
|
||||
"quoteStyle": "single",
|
||||
"semicolons": "asNeeded"
|
||||
}
|
||||
}
|
||||
}
|
698
package-lock.json
generated
698
package-lock.json
generated
|
@ -28,14 +28,14 @@
|
|||
"motion": "^11.13.5",
|
||||
"postcss": "^8.5.1",
|
||||
"preact": "^10.26.2",
|
||||
"prettier": "^3.3.3",
|
||||
"prettier-plugin-astro": "^0.14.1",
|
||||
"prettier-plugin-tailwindcss": "^0.6.6",
|
||||
"sharp": "^0.33.5",
|
||||
"tailwindcss": "^3.4.15",
|
||||
"typescript": "^5.6.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@biomejs/biome": "^1.9.4",
|
||||
"husky": "^9.1.7",
|
||||
"lint-staged": "^15.2.7",
|
||||
"wrangler": "^3.94.0"
|
||||
}
|
||||
},
|
||||
|
@ -843,6 +843,170 @@
|
|||
"node": ">=6.9.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/biome": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/biome/-/biome-1.9.4.tgz",
|
||||
"integrity": "sha512-1rkd7G70+o9KkTn5KLmDYXihGoTaIGO9PIIN2ZB7UJxFrWw04CZHPYiMRjYsaDvVV7hP1dYNRLxSANLaBFGpog==",
|
||||
"dev": true,
|
||||
"hasInstallScript": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"bin": {
|
||||
"biome": "bin/biome"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
},
|
||||
"funding": {
|
||||
"type": "opencollective",
|
||||
"url": "https://opencollective.com/biome"
|
||||
},
|
||||
"optionalDependencies": {
|
||||
"@biomejs/cli-darwin-arm64": "1.9.4",
|
||||
"@biomejs/cli-darwin-x64": "1.9.4",
|
||||
"@biomejs/cli-linux-arm64": "1.9.4",
|
||||
"@biomejs/cli-linux-arm64-musl": "1.9.4",
|
||||
"@biomejs/cli-linux-x64": "1.9.4",
|
||||
"@biomejs/cli-linux-x64-musl": "1.9.4",
|
||||
"@biomejs/cli-win32-arm64": "1.9.4",
|
||||
"@biomejs/cli-win32-x64": "1.9.4"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-darwin-arm64": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-arm64/-/cli-darwin-arm64-1.9.4.tgz",
|
||||
"integrity": "sha512-bFBsPWrNvkdKrNCYeAp+xo2HecOGPAy9WyNyB/jKnnedgzl4W4Hb9ZMzYNbf8dMCGmUdSavlYHiR01QaYR58cw==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"darwin"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-darwin-x64": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-x64/-/cli-darwin-x64-1.9.4.tgz",
|
||||
"integrity": "sha512-ngYBh/+bEedqkSevPVhLP4QfVPCpb+4BBe2p7Xs32dBgs7rh9nY2AIYUL6BgLw1JVXV8GlpKmb/hNiuIxfPfZg==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"darwin"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-linux-arm64": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64/-/cli-linux-arm64-1.9.4.tgz",
|
||||
"integrity": "sha512-fJIW0+LYujdjUgJJuwesP4EjIBl/N/TcOX3IvIHJQNsAqvV2CHIogsmA94BPG6jZATS4Hi+xv4SkBBQSt1N4/g==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-linux-arm64-musl": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64-musl/-/cli-linux-arm64-musl-1.9.4.tgz",
|
||||
"integrity": "sha512-v665Ct9WCRjGa8+kTr0CzApU0+XXtRgwmzIf1SeKSGAv+2scAlW6JR5PMFo6FzqqZ64Po79cKODKf3/AAmECqA==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-linux-x64": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64/-/cli-linux-x64-1.9.4.tgz",
|
||||
"integrity": "sha512-lRCJv/Vi3Vlwmbd6K+oQ0KhLHMAysN8lXoCI7XeHlxaajk06u7G+UsFSO01NAs5iYuWKmVZjmiOzJ0OJmGsMwg==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-linux-x64-musl": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64-musl/-/cli-linux-x64-musl-1.9.4.tgz",
|
||||
"integrity": "sha512-gEhi/jSBhZ2m6wjV530Yy8+fNqG8PAinM3oV7CyO+6c3CEh16Eizm21uHVsyVBEB6RIM8JHIl6AGYCv6Q6Q9Tg==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"linux"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-win32-arm64": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-win32-arm64/-/cli-win32-arm64-1.9.4.tgz",
|
||||
"integrity": "sha512-tlbhLk+WXZmgwoIKwHIHEBZUwxml7bRJgk0X2sPyNR3S93cdRq6XulAZRQJ17FYGGzWne0fgrXBKpl7l4M87Hg==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"win32"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@biomejs/cli-win32-x64": {
|
||||
"version": "1.9.4",
|
||||
"resolved": "https://registry.npmjs.org/@biomejs/cli-win32-x64/-/cli-win32-x64-1.9.4.tgz",
|
||||
"integrity": "sha512-8Y5wMhVIPaWe6jw2H+KlEm4wP/f7EW3810ZLmDlrEEy5KvBsb9ECEfu/kMWD484ijfQ8+nIi0giMgu9g1UAuuA==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
"dev": true,
|
||||
"license": "MIT OR Apache-2.0",
|
||||
"optional": true,
|
||||
"os": [
|
||||
"win32"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@capsizecss/unpack": {
|
||||
"version": "2.4.0",
|
||||
"resolved": "https://registry.npmjs.org/@capsizecss/unpack/-/unpack-2.4.0.tgz",
|
||||
|
@ -2753,6 +2917,22 @@
|
|||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/ansi-escapes": {
|
||||
"version": "7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-7.0.0.tgz",
|
||||
"integrity": "sha512-GdYO7a61mR0fOlAsvC9/rIHf7L96sBc6dEWzeOu+KAea5bZyQRPIpojrVoI4AXGJS/ycu/fBTdLrUkA4ODrvjw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"environment": "^1.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/ansi-regex": {
|
||||
"version": "6.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz",
|
||||
|
@ -3784,6 +3964,39 @@
|
|||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/cli-cursor": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-5.0.0.tgz",
|
||||
"integrity": "sha512-aCj4O5wKyszjMmDT4tZj93kxyydN/K5zPWSCe6/0AV/AA1pqe5ZBIw0a2ZfPQV7lL5/yb5HsUreJ6UFAF1tEQw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"restore-cursor": "^5.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/cli-truncate": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/cli-truncate/-/cli-truncate-4.0.0.tgz",
|
||||
"integrity": "sha512-nPdaFdQ0h/GEigbPClz11D0v/ZJEwxmeVZGeMo3Z5StPtUTkA9o1lD6QwoirYiSDzbcwn2XcjwmCp68W1IS4TA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"slice-ansi": "^5.0.0",
|
||||
"string-width": "^7.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/cliui": {
|
||||
"version": "8.0.1",
|
||||
"resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz",
|
||||
|
@ -3930,6 +4143,13 @@
|
|||
"simple-swizzle": "^0.2.2"
|
||||
}
|
||||
},
|
||||
"node_modules/colorette": {
|
||||
"version": "2.0.20",
|
||||
"resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz",
|
||||
"integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==",
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/comma-separated-tokens": {
|
||||
"version": "2.0.3",
|
||||
"resolved": "https://registry.npmjs.org/comma-separated-tokens/-/comma-separated-tokens-2.0.3.tgz",
|
||||
|
@ -4312,6 +4532,19 @@
|
|||
"url": "https://github.com/fb55/entities?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/environment": {
|
||||
"version": "1.1.0",
|
||||
"resolved": "https://registry.npmjs.org/environment/-/environment-1.1.0.tgz",
|
||||
"integrity": "sha512-xUtoPkMggbz0MPyPiIWr1Kp4aeWJjDZ6SMvURhimjdZgsRuDplF5/s9hcgGhyXMhs+6vpnuoiZ2kFiu3FMnS8Q==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/es-module-lexer": {
|
||||
"version": "1.6.0",
|
||||
"resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-1.6.0.tgz",
|
||||
|
@ -4394,6 +4627,30 @@
|
|||
"integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/execa": {
|
||||
"version": "8.0.1",
|
||||
"resolved": "https://registry.npmjs.org/execa/-/execa-8.0.1.tgz",
|
||||
"integrity": "sha512-VyhnebXciFV2DESc+p6B+y0LjSm0krU4OgJN44qFAhBY0TJ+1V61tYD2+wHusZ6F9n5K+vl8k0sTy7PEfV4qpg==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"cross-spawn": "^7.0.3",
|
||||
"get-stream": "^8.0.1",
|
||||
"human-signals": "^5.0.0",
|
||||
"is-stream": "^3.0.0",
|
||||
"merge-stream": "^2.0.0",
|
||||
"npm-run-path": "^5.1.0",
|
||||
"onetime": "^6.0.0",
|
||||
"signal-exit": "^4.1.0",
|
||||
"strip-final-newline": "^3.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=16.17"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sindresorhus/execa?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/exit-hook": {
|
||||
"version": "2.2.1",
|
||||
"resolved": "https://registry.npmjs.org/exit-hook/-/exit-hook-2.2.1.tgz",
|
||||
|
@ -4659,6 +4916,19 @@
|
|||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/get-stream": {
|
||||
"version": "8.0.1",
|
||||
"resolved": "https://registry.npmjs.org/get-stream/-/get-stream-8.0.1.tgz",
|
||||
"integrity": "sha512-VaUJspBffn/LMCJVoMvSAdmscJyS1auj5Zulnn5UoYcY531UWmdwhRWkcGKnGU93m5HSXP9LP2usOryrBtQowA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=16"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/github-slugger": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/github-slugger/-/github-slugger-2.0.0.tgz",
|
||||
|
@ -4959,6 +5229,32 @@
|
|||
"integrity": "sha512-er295DKPVsV82j5kw1Gjt+ADA/XYHsajl82cGNQG2eyoPkvgUhX+nDIyelzhIWbbsXP39EHcI6l5tYs2FYqYXQ==",
|
||||
"license": "BSD-2-Clause"
|
||||
},
|
||||
"node_modules/human-signals": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/human-signals/-/human-signals-5.0.0.tgz",
|
||||
"integrity": "sha512-AXcZb6vzzrFAUE61HnN4mpLqd/cSIwNQjtNWR0euPm6y0iqx3G4gOXaIDdtdDwZmhwe82LA6+zinmW4UBWVePQ==",
|
||||
"dev": true,
|
||||
"license": "Apache-2.0",
|
||||
"engines": {
|
||||
"node": ">=16.17.0"
|
||||
}
|
||||
},
|
||||
"node_modules/husky": {
|
||||
"version": "9.1.7",
|
||||
"resolved": "https://registry.npmjs.org/husky/-/husky-9.1.7.tgz",
|
||||
"integrity": "sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"bin": {
|
||||
"husky": "bin.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/typicode"
|
||||
}
|
||||
},
|
||||
"node_modules/import-meta-resolve": {
|
||||
"version": "4.1.0",
|
||||
"resolved": "https://registry.npmjs.org/import-meta-resolve/-/import-meta-resolve-4.1.0.tgz",
|
||||
|
@ -5095,6 +5391,19 @@
|
|||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/is-stream": {
|
||||
"version": "3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/is-stream/-/is-stream-3.0.0.tgz",
|
||||
"integrity": "sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": "^12.20.0 || ^14.13.1 || >=16.0.0"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/is-wsl": {
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-3.1.0.tgz",
|
||||
|
@ -5227,12 +5536,121 @@
|
|||
"integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/lint-staged": {
|
||||
"version": "15.5.2",
|
||||
"resolved": "https://registry.npmjs.org/lint-staged/-/lint-staged-15.5.2.tgz",
|
||||
"integrity": "sha512-YUSOLq9VeRNAo/CTaVmhGDKG+LBtA8KF1X4K5+ykMSwWST1vDxJRB2kv2COgLb1fvpCo+A/y9A0G0znNVmdx4w==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"chalk": "^5.4.1",
|
||||
"commander": "^13.1.0",
|
||||
"debug": "^4.4.0",
|
||||
"execa": "^8.0.1",
|
||||
"lilconfig": "^3.1.3",
|
||||
"listr2": "^8.2.5",
|
||||
"micromatch": "^4.0.8",
|
||||
"pidtree": "^0.6.0",
|
||||
"string-argv": "^0.3.2",
|
||||
"yaml": "^2.7.0"
|
||||
},
|
||||
"bin": {
|
||||
"lint-staged": "bin/lint-staged.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18.12.0"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://opencollective.com/lint-staged"
|
||||
}
|
||||
},
|
||||
"node_modules/lint-staged/node_modules/commander": {
|
||||
"version": "13.1.0",
|
||||
"resolved": "https://registry.npmjs.org/commander/-/commander-13.1.0.tgz",
|
||||
"integrity": "sha512-/rFeCpNJQbhSZjGVwO9RFV3xPqbnERS8MmIQzCtD/zl6gpJuV/bMLuN92oG3F7d8oDEHHRrujSXNUr8fpjntKw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
},
|
||||
"node_modules/listr2": {
|
||||
"version": "8.3.3",
|
||||
"resolved": "https://registry.npmjs.org/listr2/-/listr2-8.3.3.tgz",
|
||||
"integrity": "sha512-LWzX2KsqcB1wqQ4AHgYb4RsDXauQiqhjLk+6hjbaeHG4zpjjVAB6wC/gz6X0l+Du1cN3pUB5ZlrvTbhGSNnUQQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"cli-truncate": "^4.0.0",
|
||||
"colorette": "^2.0.20",
|
||||
"eventemitter3": "^5.0.1",
|
||||
"log-update": "^6.1.0",
|
||||
"rfdc": "^1.4.1",
|
||||
"wrap-ansi": "^9.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/lodash": {
|
||||
"version": "4.17.21",
|
||||
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz",
|
||||
"integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/log-update": {
|
||||
"version": "6.1.0",
|
||||
"resolved": "https://registry.npmjs.org/log-update/-/log-update-6.1.0.tgz",
|
||||
"integrity": "sha512-9ie8ItPR6tjY5uYJh8K/Zrv/RMZ5VOlOWvtZdEHYSTFKZfIBPQa9tOAEeAWhd+AnIneLJ22w5fjOYtoutpWq5w==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"ansi-escapes": "^7.0.0",
|
||||
"cli-cursor": "^5.0.0",
|
||||
"slice-ansi": "^7.1.0",
|
||||
"strip-ansi": "^7.1.0",
|
||||
"wrap-ansi": "^9.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/log-update/node_modules/is-fullwidth-code-point": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-5.0.0.tgz",
|
||||
"integrity": "sha512-OVa3u9kkBbw7b8Xw5F9P+D/T9X+Z4+JruYVNapTjPYZYUznQ5YfWeFkOj606XYYW8yugTfC8Pj0hYqvi4ryAhA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"get-east-asian-width": "^1.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/log-update/node_modules/slice-ansi": {
|
||||
"version": "7.1.0",
|
||||
"resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-7.1.0.tgz",
|
||||
"integrity": "sha512-bSiSngZ/jWeX93BqeIAbImyTbEihizcwNjFoRUIY/T1wWQsfsm2Vw1agPKylXvQTU7iASGdHhyqRlqQzfz+Htg==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"ansi-styles": "^6.2.1",
|
||||
"is-fullwidth-code-point": "^5.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/chalk/slice-ansi?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/longest-streak": {
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz",
|
||||
|
@ -5531,6 +5949,13 @@
|
|||
"integrity": "sha512-IEn+pegP1aManZuckezWCO+XZQDplx1366JoVhTpMpBB1sPey/SbveZQUosKiKiGYjg1wH4pMlNgXbCiYgihQA==",
|
||||
"license": "CC0-1.0"
|
||||
},
|
||||
"node_modules/merge-stream": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz",
|
||||
"integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==",
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/merge2": {
|
||||
"version": "1.4.1",
|
||||
"resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz",
|
||||
|
@ -6128,6 +6553,32 @@
|
|||
"node": ">=10.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/mimic-fn": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz",
|
||||
"integrity": "sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/mimic-function": {
|
||||
"version": "5.0.1",
|
||||
"resolved": "https://registry.npmjs.org/mimic-function/-/mimic-function-5.0.1.tgz",
|
||||
"integrity": "sha512-VP79XUPxV2CigYP3jWwAUFSku2aKqBH7uTAapFWCBqutsbmDo96KY5o8uh6U+/YSIn5OxJnXp73beVkpqMIGhA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/miniflare": {
|
||||
"version": "3.20250214.0",
|
||||
"resolved": "https://registry.npmjs.org/miniflare/-/miniflare-3.20250214.0.tgz",
|
||||
|
@ -6396,6 +6847,35 @@
|
|||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/npm-run-path": {
|
||||
"version": "5.3.0",
|
||||
"resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-5.3.0.tgz",
|
||||
"integrity": "sha512-ppwTtiJZq0O/ai0z7yfudtBpWIoxM8yE6nHi1X47eFR2EWORqfbu6CnPlNsjeN683eT0qG6H/Pyf9fCcvjnnnQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"path-key": "^4.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^12.20.0 || ^14.13.1 || >=16.0.0"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/npm-run-path/node_modules/path-key": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/path-key/-/path-key-4.0.0.tgz",
|
||||
"integrity": "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/nth-check": {
|
||||
"version": "2.1.1",
|
||||
"resolved": "https://registry.npmjs.org/nth-check/-/nth-check-2.1.1.tgz",
|
||||
|
@ -6444,6 +6924,22 @@
|
|||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/onetime": {
|
||||
"version": "6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/onetime/-/onetime-6.0.0.tgz",
|
||||
"integrity": "sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"mimic-fn": "^4.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/oniguruma-parser": {
|
||||
"version": "0.12.0",
|
||||
"resolved": "https://registry.npmjs.org/oniguruma-parser/-/oniguruma-parser-0.12.0.tgz",
|
||||
|
@ -6626,6 +7122,19 @@
|
|||
"url": "https://github.com/sponsors/jonschlinkert"
|
||||
}
|
||||
},
|
||||
"node_modules/pidtree": {
|
||||
"version": "0.6.0",
|
||||
"resolved": "https://registry.npmjs.org/pidtree/-/pidtree-0.6.0.tgz",
|
||||
"integrity": "sha512-eG2dWTVw5bzqGRztnHExczNxt5VGsE6OwTeCG3fdUf9KBsZzO3R5OIIIzWR+iZA0NtZ+RDVdaoE2dK1cn6jH4g==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"bin": {
|
||||
"pidtree": "bin/pidtree.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.10"
|
||||
}
|
||||
},
|
||||
"node_modules/pify": {
|
||||
"version": "2.3.0",
|
||||
"resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
|
||||
|
@ -6830,6 +7339,8 @@
|
|||
"resolved": "https://registry.npmjs.org/prettier/-/prettier-3.5.2.tgz",
|
||||
"integrity": "sha512-lc6npv5PH7hVqozBR7lkBNOGXV9vMwROAPlumdBkX0wTbbzPu/U1hk5yL8p2pt4Xoc+2mkT8t/sow2YrV/M5qg==",
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"peer": true,
|
||||
"bin": {
|
||||
"prettier": "bin/prettier.cjs"
|
||||
},
|
||||
|
@ -6845,6 +7356,8 @@
|
|||
"resolved": "https://registry.npmjs.org/prettier-plugin-astro/-/prettier-plugin-astro-0.14.1.tgz",
|
||||
"integrity": "sha512-RiBETaaP9veVstE4vUwSIcdATj6dKmXljouXc/DDNwBSPTp8FRkLGDSGFClKsAFeeg+13SB0Z1JZvbD76bigJw==",
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"peer": true,
|
||||
"dependencies": {
|
||||
"@astrojs/compiler": "^2.9.1",
|
||||
"prettier": "^3.0.0",
|
||||
|
@ -6854,84 +7367,6 @@
|
|||
"node": "^14.15.0 || >=16.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/prettier-plugin-tailwindcss": {
|
||||
"version": "0.6.11",
|
||||
"resolved": "https://registry.npmjs.org/prettier-plugin-tailwindcss/-/prettier-plugin-tailwindcss-0.6.11.tgz",
|
||||
"integrity": "sha512-YxaYSIvZPAqhrrEpRtonnrXdghZg1irNg4qrjboCXrpybLWVs55cW2N3juhspVJiO0JBvYJT8SYsJpc8OQSnsA==",
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=14.21.3"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@ianvs/prettier-plugin-sort-imports": "*",
|
||||
"@prettier/plugin-pug": "*",
|
||||
"@shopify/prettier-plugin-liquid": "*",
|
||||
"@trivago/prettier-plugin-sort-imports": "*",
|
||||
"@zackad/prettier-plugin-twig": "*",
|
||||
"prettier": "^3.0",
|
||||
"prettier-plugin-astro": "*",
|
||||
"prettier-plugin-css-order": "*",
|
||||
"prettier-plugin-import-sort": "*",
|
||||
"prettier-plugin-jsdoc": "*",
|
||||
"prettier-plugin-marko": "*",
|
||||
"prettier-plugin-multiline-arrays": "*",
|
||||
"prettier-plugin-organize-attributes": "*",
|
||||
"prettier-plugin-organize-imports": "*",
|
||||
"prettier-plugin-sort-imports": "*",
|
||||
"prettier-plugin-style-order": "*",
|
||||
"prettier-plugin-svelte": "*"
|
||||
},
|
||||
"peerDependenciesMeta": {
|
||||
"@ianvs/prettier-plugin-sort-imports": {
|
||||
"optional": true
|
||||
},
|
||||
"@prettier/plugin-pug": {
|
||||
"optional": true
|
||||
},
|
||||
"@shopify/prettier-plugin-liquid": {
|
||||
"optional": true
|
||||
},
|
||||
"@trivago/prettier-plugin-sort-imports": {
|
||||
"optional": true
|
||||
},
|
||||
"@zackad/prettier-plugin-twig": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-astro": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-css-order": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-import-sort": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-jsdoc": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-marko": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-multiline-arrays": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-organize-attributes": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-organize-imports": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-sort-imports": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-style-order": {
|
||||
"optional": true
|
||||
},
|
||||
"prettier-plugin-svelte": {
|
||||
"optional": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"node_modules/printable-characters": {
|
||||
"version": "1.0.42",
|
||||
"resolved": "https://registry.npmjs.org/printable-characters/-/printable-characters-1.0.42.tgz",
|
||||
|
@ -7248,6 +7683,39 @@
|
|||
"url": "https://github.com/sponsors/ljharb"
|
||||
}
|
||||
},
|
||||
"node_modules/restore-cursor": {
|
||||
"version": "5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-5.1.0.tgz",
|
||||
"integrity": "sha512-oMA2dcrw6u0YfxJQXm342bFKX/E4sG9rbTzO9ptUcR/e8A33cHuvStiYOwH7fszkZlZ1z/ta9AAoPk2F4qIOHA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"onetime": "^7.0.0",
|
||||
"signal-exit": "^4.1.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/restore-cursor/node_modules/onetime": {
|
||||
"version": "7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/onetime/-/onetime-7.0.0.tgz",
|
||||
"integrity": "sha512-VXJjc87FScF88uafS3JllDgvAm+c/Slfz06lorj2uAY34rlUu0Nt+v8wreiImcrgAjjIHp1rXpTDlLOGw29WwQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"mimic-function": "^5.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/restructure": {
|
||||
"version": "3.0.2",
|
||||
"resolved": "https://registry.npmjs.org/restructure/-/restructure-3.0.2.tgz",
|
||||
|
@ -7325,6 +7793,13 @@
|
|||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/rfdc": {
|
||||
"version": "1.4.1",
|
||||
"resolved": "https://registry.npmjs.org/rfdc/-/rfdc-1.4.1.tgz",
|
||||
"integrity": "sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==",
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/rollup": {
|
||||
"version": "4.40.0",
|
||||
"resolved": "https://registry.npmjs.org/rollup/-/rollup-4.40.0.tgz",
|
||||
|
@ -7448,13 +7923,17 @@
|
|||
"version": "0.0.15",
|
||||
"resolved": "https://registry.npmjs.org/s.color/-/s.color-0.0.15.tgz",
|
||||
"integrity": "sha512-AUNrbEUHeKY8XsYr/DYpl+qk5+aM+DChopnWOPEzn8YKzOhv4l2zH6LzZms3tOZP3wwdOyc0RmTciyi46HLIuA==",
|
||||
"license": "MIT"
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"peer": true
|
||||
},
|
||||
"node_modules/sass-formatter": {
|
||||
"version": "0.7.9",
|
||||
"resolved": "https://registry.npmjs.org/sass-formatter/-/sass-formatter-0.7.9.tgz",
|
||||
"integrity": "sha512-CWZ8XiSim+fJVG0cFLStwDvft1VI7uvXdCNJYXhDvowiv+DsbD1nXLiQ4zrE5UBvj5DWZJ93cwN0NX5PMsr1Pw==",
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"peer": true,
|
||||
"dependencies": {
|
||||
"suf-log": "^2.5.3"
|
||||
}
|
||||
|
@ -7623,6 +8102,36 @@
|
|||
"integrity": "sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/slice-ansi": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-5.0.0.tgz",
|
||||
"integrity": "sha512-FC+lgizVPfie0kkhqUScwRu1O/lF6NOgJmlCgK+/LYxDCTk8sGelYaHDhFcDN+Sn3Cv+3VSa4Byeo+IMCzpMgQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"ansi-styles": "^6.0.0",
|
||||
"is-fullwidth-code-point": "^4.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/chalk/slice-ansi?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/slice-ansi/node_modules/is-fullwidth-code-point": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-4.0.0.tgz",
|
||||
"integrity": "sha512-O4L094N2/dZ7xqVdrXhh9r1KODPJpFms8B5sGdJLPy664AgvXsreZUyCQQNItZRDlYug4xStLjNp/sz3HvBowQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/smol-toml": {
|
||||
"version": "1.3.4",
|
||||
"resolved": "https://registry.npmjs.org/smol-toml/-/smol-toml-1.3.4.tgz",
|
||||
|
@ -7706,6 +8215,16 @@
|
|||
"integrity": "sha512-TlnjJ1C0QrmxRNrON00JvaFFlNh5TTG00APw23j74ET7gkQpTASi6/L2fuiav8pzK715HXtUeClpBTw2NPSn6w==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/string-argv": {
|
||||
"version": "0.3.2",
|
||||
"resolved": "https://registry.npmjs.org/string-argv/-/string-argv-0.3.2.tgz",
|
||||
"integrity": "sha512-aqD2Q0144Z+/RqG52NeHEkZauTAUWJO8c6yTftGJKO3Tja5tUgIfmIl6kExvhtxSDP7fXB6DvzkfMpCd/F3G+Q==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=0.6.19"
|
||||
}
|
||||
},
|
||||
"node_modules/string-width": {
|
||||
"version": "7.2.0",
|
||||
"resolved": "https://registry.npmjs.org/string-width/-/string-width-7.2.0.tgz",
|
||||
|
@ -7816,6 +8335,19 @@
|
|||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/strip-final-newline": {
|
||||
"version": "3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-3.0.0.tgz",
|
||||
"integrity": "sha512-dOESqjYr96iWYylGObzd39EuNTa5VJxyvVAEm5Jnh7KGo75V43Hk1odPQkNDyXNmUR6k+gEiDVXnjB8HJ3crXw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/strnum": {
|
||||
"version": "1.1.1",
|
||||
"resolved": "https://registry.npmjs.org/strnum/-/strnum-1.1.1.tgz",
|
||||
|
@ -7855,6 +8387,8 @@
|
|||
"resolved": "https://registry.npmjs.org/suf-log/-/suf-log-2.5.3.tgz",
|
||||
"integrity": "sha512-KvC8OPjzdNOe+xQ4XWJV2whQA0aM1kGVczMQ8+dStAO6KfEB140JEVQ9dE76ONZ0/Ylf67ni4tILPJB41U0eow==",
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"peer": true,
|
||||
"dependencies": {
|
||||
"s.color": "0.0.15"
|
||||
}
|
||||
|
|
16
package.json
16
package.json
|
@ -8,7 +8,10 @@
|
|||
"build": "astro check && astro build",
|
||||
"preview": "astro preview --port 3000",
|
||||
"wrangler": "wrangler",
|
||||
"astro": "astro"
|
||||
"astro": "astro",
|
||||
"lint": "biome lint ./src",
|
||||
"format": "biome format ./src --write",
|
||||
"prepare": "husky"
|
||||
},
|
||||
"dependencies": {
|
||||
"@astrojs/check": "^0.9.4",
|
||||
|
@ -31,14 +34,19 @@
|
|||
"motion": "^11.13.5",
|
||||
"postcss": "^8.5.1",
|
||||
"preact": "^10.26.2",
|
||||
"prettier": "^3.3.3",
|
||||
"prettier-plugin-astro": "^0.14.1",
|
||||
"prettier-plugin-tailwindcss": "^0.6.6",
|
||||
"sharp": "^0.33.5",
|
||||
"tailwindcss": "^3.4.15",
|
||||
"typescript": "^5.6.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@biomejs/biome": "^1.9.4",
|
||||
"husky": "^9.1.7",
|
||||
"lint-staged": "^15.2.7",
|
||||
"wrangler": "^3.94.0"
|
||||
},
|
||||
"lint-staged": {
|
||||
"src/**/*.{ts,tsx,astro,js,jsx}": [
|
||||
"biome check --write ./src"
|
||||
]
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,15 +3,7 @@ import { getLocale, getPath } from '~/utils/i18n'
|
|||
|
||||
const locale = getLocale(Astro)
|
||||
const getLocalePath = getPath(locale)
|
||||
const {
|
||||
class: className,
|
||||
isPrimary,
|
||||
isAlert,
|
||||
isBordered,
|
||||
href,
|
||||
id,
|
||||
extra,
|
||||
} = Astro.props
|
||||
const { class: className, isPrimary, isAlert, isBordered, href, id, extra } = Astro.props
|
||||
---
|
||||
|
||||
{
|
||||
|
|
|
@ -19,15 +19,9 @@ const {
|
|||
},
|
||||
} = getUI(locale)
|
||||
|
||||
const {
|
||||
title1 = features.title1,
|
||||
title2 = features.title2,
|
||||
title3 = features.title3,
|
||||
} = Astro.props
|
||||
const { title1 = features.title1, title2 = features.title2, title3 = features.title3 } = Astro.props
|
||||
|
||||
const descriptions = Object.values(features.featureTabs).map(
|
||||
(tab) => tab.description,
|
||||
)
|
||||
const descriptions = Object.values(features.featureTabs).map((tab) => tab.description)
|
||||
---
|
||||
|
||||
<section
|
||||
|
|
|
@ -91,11 +91,7 @@ export default function ModsList({ allMods, locale }: ModsListProps) {
|
|||
<button
|
||||
type="button"
|
||||
onClick={() => navigatePage(page - 1)}
|
||||
className={`px-3 py-2 ${
|
||||
page === 1
|
||||
? 'pointer-events-none text-gray-400'
|
||||
: 'text-dark hover:text-gray-600'
|
||||
}`}
|
||||
className={`px-3 py-2 ${page === 1 ? 'pointer-events-none text-gray-400' : 'text-dark hover:text-gray-600'}`}
|
||||
>
|
||||
<
|
||||
</button>
|
||||
|
@ -113,10 +109,8 @@ export default function ModsList({ allMods, locale }: ModsListProps) {
|
|||
)
|
||||
}
|
||||
return (
|
||||
<span className="text-sm">
|
||||
{value
|
||||
.replace('{totalPages}', totalPages.toString())
|
||||
.replace('{totalItems}', totalItems.toString())}
|
||||
<span key={value} className="text-sm">
|
||||
{value.replace('{totalPages}', totalPages.toString()).replace('{totalItems}', totalItems.toString())}
|
||||
</span>
|
||||
)
|
||||
})}
|
||||
|
@ -124,11 +118,7 @@ export default function ModsList({ allMods, locale }: ModsListProps) {
|
|||
<button
|
||||
type="button"
|
||||
onClick={() => navigatePage(page + 1)}
|
||||
className={`px-3 py-2 ${
|
||||
page === totalPages
|
||||
? 'pointer-events-none text-gray-400'
|
||||
: 'text-dark hover:text-gray-600'
|
||||
}`}
|
||||
className={`px-3 py-2 ${page === totalPages ? 'pointer-events-none text-gray-400' : 'text-dark hover:text-gray-600'}`}
|
||||
>
|
||||
>
|
||||
</button>
|
||||
|
@ -155,10 +145,11 @@ export default function ModsList({ allMods, locale }: ModsListProps) {
|
|||
<button
|
||||
type="button"
|
||||
onClick={toggleCreatedSort}
|
||||
className="text-md flex items-center gap-2 px-4 py-2 font-semibold"
|
||||
className="flex items-center gap-2 px-4 py-2 font-semibold text-md"
|
||||
>
|
||||
{mods.sort.lastCreated}
|
||||
<span
|
||||
// biome-ignore lint/security/noDangerouslySetInnerHtml: Icons are safe
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: getSortIcon(createdSort).html[0],
|
||||
}}
|
||||
|
@ -170,10 +161,11 @@ export default function ModsList({ allMods, locale }: ModsListProps) {
|
|||
<button
|
||||
type="button"
|
||||
onClick={toggleUpdatedSort}
|
||||
className="text-md flex items-center gap-2 px-4 py-2 font-semibold"
|
||||
className="flex items-center gap-2 px-4 py-2 font-semibold text-md"
|
||||
>
|
||||
{mods.sort.lastUpdated}
|
||||
<span
|
||||
// biome-ignore lint/security/noDangerouslySetInnerHtml: Icons are safe
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: getSortIcon(updatedSort).html[0],
|
||||
}}
|
||||
|
@ -182,7 +174,7 @@ export default function ModsList({ allMods, locale }: ModsListProps) {
|
|||
</div>
|
||||
|
||||
<div className="flex items-center gap-2 px-4 py-2">
|
||||
<label htmlFor="limit" className="text-md font-semibold">
|
||||
<label htmlFor="limit" className="font-semibold text-md">
|
||||
{mods.sort.perPage}
|
||||
</label>
|
||||
<select
|
||||
|
@ -217,20 +209,17 @@ export default function ModsList({ allMods, locale }: ModsListProps) {
|
|||
/>
|
||||
</div>
|
||||
<div>
|
||||
<h2 className="text-lg font-bold">
|
||||
{mod.name}{' '}
|
||||
<span className="ml-1 text-sm font-normal">
|
||||
by @{mod.author}
|
||||
</span>
|
||||
<h2 className="font-bold text-lg">
|
||||
{mod.name} <span className="ml-1 font-normal text-sm">by @{mod.author}</span>
|
||||
</h2>
|
||||
<p className="text-sm font-thin">{mod.description}</p>
|
||||
<p className="font-thin text-sm">{mod.description}</p>
|
||||
</div>
|
||||
</a>
|
||||
))
|
||||
) : (
|
||||
<div className="col-span-4 grid place-items-center gap-4 place-self-center px-8 text-center">
|
||||
<h2 className="text-lg font-bold">{mods.noResults}</h2>
|
||||
<p className="text-sm font-thin">{mods.noResultsDescription}</p>
|
||||
<h2 className="font-bold text-lg">{mods.noResults}</h2>
|
||||
<p className="font-thin text-sm">{mods.noResultsDescription}</p>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
|
|
|
@ -4,11 +4,7 @@ import { Info } from 'lucide-astro'
|
|||
|
||||
import { releaseNotes as releaseNotesData } from '~/release-notes'
|
||||
import { getLocale, getPath, getUI } from '~/utils/i18n'
|
||||
import {
|
||||
type BreakingChange,
|
||||
type ReleaseNote,
|
||||
getReleaseNoteFirefoxVersion,
|
||||
} from '../release-notes'
|
||||
import { type BreakingChange, type ReleaseNote, getReleaseNoteFirefoxVersion } from '../release-notes'
|
||||
export type Props = ReleaseNote
|
||||
const { isTwilight, ...props } = Astro.props
|
||||
|
||||
|
@ -22,16 +18,14 @@ const {
|
|||
},
|
||||
} = getUI(locale)
|
||||
|
||||
let date
|
||||
let date: Date | undefined
|
||||
if (props.date) {
|
||||
const [day, month, year] = props.date.split('/')
|
||||
date = new Date(Date.parse(`${year}-${month}-${day}`))
|
||||
}
|
||||
|
||||
const ffVersion = getReleaseNoteFirefoxVersion(props)
|
||||
const currentReleaseIndex = releaseNotesData.findIndex(
|
||||
(releaseNote: ReleaseNote) => releaseNote.version === props.version,
|
||||
)
|
||||
const currentReleaseIndex = releaseNotesData.findIndex((releaseNote: ReleaseNote) => releaseNote.version === props.version)
|
||||
const prevReleaseNote = releaseNotesData[currentReleaseIndex + 1]
|
||||
let compareLink = ''
|
||||
if (prevReleaseNote && !isTwilight) {
|
||||
|
|
|
@ -2,13 +2,7 @@
|
|||
const { gap = 4 } = Astro.props
|
||||
|
||||
import { icon, library } from '@fortawesome/fontawesome-svg-core'
|
||||
import {
|
||||
faBluesky,
|
||||
faGithub,
|
||||
faMastodon,
|
||||
faReddit,
|
||||
faXTwitter,
|
||||
} from '@fortawesome/free-brands-svg-icons'
|
||||
import { faBluesky, faGithub, faMastodon, faReddit, faXTwitter } from '@fortawesome/free-brands-svg-icons'
|
||||
|
||||
library.add(faMastodon, faBluesky, faGithub, faXTwitter, faReddit)
|
||||
const Mastodon = icon({ prefix: 'fab', iconName: 'mastodon' })
|
||||
|
|
|
@ -1,10 +1,25 @@
|
|||
---
|
||||
interface ReleaseInfo {
|
||||
label?: string
|
||||
link: string
|
||||
checksum?: string
|
||||
}
|
||||
|
||||
interface PlatformReleases {
|
||||
universal?: ReleaseInfo
|
||||
all?: ReleaseInfo
|
||||
tarball?: ReleaseInfo
|
||||
x86_64?: { tarball: ReleaseInfo } | ReleaseInfo
|
||||
arm64?: ReleaseInfo
|
||||
flathub?: { all: ReleaseInfo }
|
||||
}
|
||||
|
||||
interface Props {
|
||||
platform: 'mac' | 'windows' | 'linux'
|
||||
icon: string[]
|
||||
title: string
|
||||
description: string
|
||||
releases: Record<string, any>
|
||||
releases: PlatformReleases
|
||||
}
|
||||
|
||||
const { platform, icon, title, description, releases } = Astro.props
|
||||
|
@ -32,7 +47,7 @@ import DownloadCard from './ButtonCard.astro'
|
|||
{
|
||||
platform === 'linux' ? (
|
||||
<>
|
||||
<div>
|
||||
{releases.flathub && releases.flathub.all.label && <div>
|
||||
<h4 class="mb-3 text-lg font-medium">Package Managers</h4>
|
||||
<div class="space-y-3">
|
||||
<DownloadCard
|
||||
|
@ -41,8 +56,8 @@ import DownloadCard from './ButtonCard.astro'
|
|||
variant="flathub"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
</div>}
|
||||
{releases.x86_64 && 'tarball' in releases.x86_64 && <div>
|
||||
<h4 class="mb-3 text-lg font-medium">Tarball</h4>
|
||||
<div class="grid grid-cols-1 gap-3 sm:grid-cols-2">
|
||||
<DownloadCard
|
||||
|
@ -53,23 +68,38 @@ import DownloadCard from './ButtonCard.astro'
|
|||
/>
|
||||
<DownloadCard
|
||||
label="ARM64"
|
||||
href={releases.aarch64.tarball.link}
|
||||
href={releases.x86_64.tarball.link}
|
||||
variant="aarch64"
|
||||
checksum={releases.aarch64.tarball.checksum}
|
||||
checksum={releases.x86_64.tarball.checksum}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>}
|
||||
</>
|
||||
) : (
|
||||
<div class="space-y-4">
|
||||
{Object.entries(releases).map(([variant, releaseNote]) => (
|
||||
<DownloadCard
|
||||
label={releaseNote.label}
|
||||
href={releaseNote.link}
|
||||
variant={variant}
|
||||
checksum={releaseNote.checksum}
|
||||
/>
|
||||
))}
|
||||
<div class="space-y-3">
|
||||
{releases.universal && releases.universal.label && (
|
||||
<DownloadCard
|
||||
label={releases.universal.label}
|
||||
href={releases.universal.link}
|
||||
checksum={releases.universal.checksum}
|
||||
/>
|
||||
)}
|
||||
{releases.x86_64 && 'tarball' in releases.x86_64 && releases.x86_64.tarball && releases.x86_64.tarball.label && (
|
||||
<DownloadCard
|
||||
label={releases.x86_64.tarball.label}
|
||||
href={releases.x86_64.tarball.link}
|
||||
checksum={releases.x86_64.tarball.checksum}
|
||||
/>
|
||||
)}
|
||||
{releases.arm64 && releases.arm64.label && (
|
||||
<DownloadCard
|
||||
label={releases.arm64.label}
|
||||
href={releases.arm64.link}
|
||||
checksum={releases.arm64.checksum}
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
|
|
@ -70,9 +70,7 @@ export function useModsSearch(mods: ZenTheme[]) {
|
|||
searchParams.delete('limit')
|
||||
}
|
||||
|
||||
const newUrl = `${window.location.pathname}${
|
||||
searchParams.toString() ? `?${searchParams.toString()}` : ''
|
||||
}`
|
||||
const newUrl = `${window.location.pathname}${searchParams.toString() ? `?${searchParams.toString()}` : ''}`
|
||||
|
||||
if (state.page > 1) {
|
||||
window.history.pushState({}, '', newUrl)
|
||||
|
@ -92,16 +90,14 @@ export function useModsSearch(mods: ZenTheme[]) {
|
|||
mod.name.toLowerCase().includes(searchTerm) ||
|
||||
mod.description.toLowerCase().includes(searchTerm) ||
|
||||
mod.author.toLowerCase().includes(searchTerm) ||
|
||||
(mod.tags?.some((tag) => tag.toLowerCase().includes(searchTerm)) ??
|
||||
false),
|
||||
(mod.tags?.some((tag) => tag.toLowerCase().includes(searchTerm)) ?? false),
|
||||
)
|
||||
}
|
||||
|
||||
// Sort by createdAt if chosen
|
||||
if (state.createdSort !== 'default') {
|
||||
filtered.sort((a, b) => {
|
||||
const diff =
|
||||
new Date(a.createdAt).getTime() - new Date(b.createdAt).getTime()
|
||||
const diff = new Date(a.createdAt).getTime() - new Date(b.createdAt).getTime()
|
||||
return state.createdSort === 'asc' ? diff : -diff
|
||||
})
|
||||
}
|
||||
|
@ -109,8 +105,7 @@ export function useModsSearch(mods: ZenTheme[]) {
|
|||
// Sort by updatedAt if chosen
|
||||
if (state.updatedSort !== 'default') {
|
||||
filtered.sort((a, b) => {
|
||||
const diff =
|
||||
new Date(a.updatedAt).getTime() - new Date(b.updatedAt).getTime()
|
||||
const diff = new Date(a.updatedAt).getTime() - new Date(b.updatedAt).getTime()
|
||||
return state.updatedSort === 'asc' ? diff : -diff
|
||||
})
|
||||
}
|
||||
|
@ -131,12 +126,7 @@ export function useModsSearch(mods: ZenTheme[]) {
|
|||
const toggleCreatedSort = () => {
|
||||
setState((prev) => ({
|
||||
...prev,
|
||||
createdSort:
|
||||
prev.createdSort === 'default'
|
||||
? 'asc'
|
||||
: prev.createdSort === 'asc'
|
||||
? 'desc'
|
||||
: 'default',
|
||||
createdSort: prev.createdSort === 'default' ? 'asc' : prev.createdSort === 'asc' ? 'desc' : 'default',
|
||||
page: 1, // Reset page when sort changes
|
||||
}))
|
||||
}
|
||||
|
@ -144,12 +134,7 @@ export function useModsSearch(mods: ZenTheme[]) {
|
|||
const toggleUpdatedSort = () => {
|
||||
setState((prev) => ({
|
||||
...prev,
|
||||
updatedSort:
|
||||
prev.updatedSort === 'default'
|
||||
? 'asc'
|
||||
: prev.updatedSort === 'asc'
|
||||
? 'desc'
|
||||
: 'default',
|
||||
updatedSort: prev.updatedSort === 'default' ? 'asc' : prev.updatedSort === 'asc' ? 'desc' : 'default',
|
||||
page: 1, // Reset page when sort changes
|
||||
}))
|
||||
}
|
||||
|
|
|
@ -1,23 +1,23 @@
|
|||
---
|
||||
interface Props {
|
||||
title: string;
|
||||
description?: string;
|
||||
ogImage?: string;
|
||||
isHome?: boolean;
|
||||
redirect?: string;
|
||||
title: string
|
||||
description?: string
|
||||
ogImage?: string
|
||||
isHome?: boolean
|
||||
redirect?: string
|
||||
}
|
||||
|
||||
const { title, description, ogImage, isHome, redirect } = Astro.props;
|
||||
const { title, description, ogImage, isHome, redirect } = Astro.props
|
||||
const defaultDescription =
|
||||
"Zen Browser is built for speed, security, and true privacy. Download now to enjoy a beautifully-designed, distraction-free web experience packed with features.";
|
||||
const defaultOgImage = "/share-pic.png";
|
||||
import "@fontsource/bricolage-grotesque/400.css";
|
||||
import "@fontsource/bricolage-grotesque/500.css";
|
||||
import "@fontsource/bricolage-grotesque/600.css";
|
||||
import Footer from "~/components/Footer.astro";
|
||||
import NavBar from "~/components/NavBar.astro";
|
||||
import { getLocale } from "~/utils/i18n";
|
||||
const locale = getLocale(Astro);
|
||||
'Zen Browser is built for speed, security, and true privacy. Download now to enjoy a beautifully-designed, distraction-free web experience packed with features.'
|
||||
const defaultOgImage = '/share-pic.png'
|
||||
import '@fontsource/bricolage-grotesque/400.css'
|
||||
import '@fontsource/bricolage-grotesque/500.css'
|
||||
import '@fontsource/bricolage-grotesque/600.css'
|
||||
import Footer from '~/components/Footer.astro'
|
||||
import NavBar from '~/components/NavBar.astro'
|
||||
import { getLocale } from '~/utils/i18n'
|
||||
const locale = getLocale(Astro)
|
||||
---
|
||||
|
||||
<script is:inline data-cfasync="false">
|
||||
|
|
|
@ -1,16 +1,16 @@
|
|||
---
|
||||
import Button from "~/components/Button.astro";
|
||||
import Description from "~/components/Description.astro";
|
||||
import Layout from "~/layouts/Layout.astro";
|
||||
import { getLocale, getUI } from "~/utils/i18n";
|
||||
export { getStaticPaths } from "~/utils/i18n";
|
||||
import Button from '~/components/Button.astro'
|
||||
import Description from '~/components/Description.astro'
|
||||
import Layout from '~/layouts/Layout.astro'
|
||||
import { getLocale, getUI } from '~/utils/i18n'
|
||||
export { getStaticPaths } from '~/utils/i18n'
|
||||
|
||||
const locale = getLocale(Astro);
|
||||
const locale = getLocale(Astro)
|
||||
|
||||
const {
|
||||
routes: { about },
|
||||
layout,
|
||||
} = getUI(locale);
|
||||
routes: { about },
|
||||
layout,
|
||||
} = getUI(locale)
|
||||
---
|
||||
|
||||
<Layout
|
||||
|
|
|
@ -8,12 +8,7 @@ import { getChecksums } from '~/utils/githubChecksums'
|
|||
import { getLocale, getUI } from '~/utils/i18n'
|
||||
|
||||
import { icon, library } from '@fortawesome/fontawesome-svg-core'
|
||||
import {
|
||||
faApple,
|
||||
faGithub,
|
||||
faLinux,
|
||||
faWindows,
|
||||
} from '@fortawesome/free-brands-svg-icons'
|
||||
import { faApple, faGithub, faLinux, faWindows } from '@fortawesome/free-brands-svg-icons'
|
||||
import { ExternalLink, Lock } from 'lucide-astro'
|
||||
|
||||
export { getStaticPaths } from '~/utils/i18n'
|
||||
|
|
|
@ -10,12 +10,9 @@ const RSS_ENTRY_LIMIT = 20
|
|||
* Handles the GET request for the `feed.xml` endpoint.
|
||||
* @returns The RSS feed for the Zen Browser release notes.
|
||||
*/
|
||||
export function GET(context: any) {
|
||||
export function GET(context: { url: URL }) {
|
||||
// Just in case the release notes array is empty for whatever reason.
|
||||
const latestDate =
|
||||
releaseNotes.length > 0
|
||||
? formatRssDate(releaseNotes[0].date as string)
|
||||
: new Date()
|
||||
const latestDate = releaseNotes.length > 0 ? formatRssDate(releaseNotes[0].date as string) : new Date()
|
||||
|
||||
const rssData: RSSOptions = {
|
||||
title: 'Zen Browser Release Notes',
|
||||
|
@ -89,14 +86,8 @@ function formatReleaseNote(releaseNote: ReleaseNote) {
|
|||
content += `<p>${releaseNote.extra.replace(/(\n)/g, '<br />')}</p>`
|
||||
}
|
||||
|
||||
content += addReleaseNoteSection(
|
||||
'⚠️ Breaking changes',
|
||||
releaseNote.breakingChanges?.map(breakingChangeToReleaseNote),
|
||||
)
|
||||
content += addReleaseNoteSection(
|
||||
'✓ Fixes',
|
||||
releaseNote.fixes?.map(fixToReleaseNote),
|
||||
)
|
||||
content += addReleaseNoteSection('⚠️ Breaking changes', releaseNote.breakingChanges?.map(breakingChangeToReleaseNote))
|
||||
content += addReleaseNoteSection('✓ Fixes', releaseNote.fixes?.map(fixToReleaseNote))
|
||||
content += addReleaseNoteSection('🖌 Theme Changes', releaseNote.themeChanges)
|
||||
content += addReleaseNoteSection('⭐ Features', releaseNote.features)
|
||||
|
||||
|
@ -109,19 +100,17 @@ function addReleaseNoteSection(title: string, items?: string[]): string {
|
|||
}
|
||||
|
||||
let content = `<h2>${title}</h2>`
|
||||
content += `<ul>`
|
||||
content += '<ul>'
|
||||
for (const item of items) {
|
||||
if (item && item.length > 0) {
|
||||
content += `<li>${item}</li>`
|
||||
}
|
||||
}
|
||||
content += `</ul>`
|
||||
content += '</ul>'
|
||||
return content
|
||||
}
|
||||
|
||||
function fixToReleaseNote(
|
||||
fix?: Exclude<ReleaseNote['fixes'], undefined>[number],
|
||||
) {
|
||||
function fixToReleaseNote(fix?: Exclude<ReleaseNote['fixes'], undefined>[number]) {
|
||||
if (typeof fix === 'string') {
|
||||
return fix
|
||||
}
|
||||
|
@ -137,18 +126,12 @@ function fixToReleaseNote(
|
|||
return note
|
||||
}
|
||||
|
||||
function breakingChangeToReleaseNote(
|
||||
breakingChange?: Exclude<ReleaseNote['breakingChanges'], undefined>[number],
|
||||
) {
|
||||
function breakingChangeToReleaseNote(breakingChange?: Exclude<ReleaseNote['breakingChanges'], undefined>[number]) {
|
||||
if (typeof breakingChange === 'string') {
|
||||
return breakingChange
|
||||
}
|
||||
|
||||
if (
|
||||
!breakingChange ||
|
||||
!breakingChange.description ||
|
||||
breakingChange.description.length === 0
|
||||
) {
|
||||
if (!breakingChange || !breakingChange.description || breakingChange.description.length === 0) {
|
||||
return ''
|
||||
}
|
||||
|
||||
|
@ -156,19 +139,12 @@ function breakingChangeToReleaseNote(
|
|||
}
|
||||
|
||||
function pubDate(date?: Date) {
|
||||
date ??= new Date()
|
||||
const newDate = date ?? new Date()
|
||||
|
||||
const pieces = date.toString().split(' ')
|
||||
const pieces = newDate.toString().split(' ')
|
||||
const offsetTime = pieces[5].match(/[-+]\d{4}/)
|
||||
const offset = offsetTime ? offsetTime : pieces[5]
|
||||
const parts = [
|
||||
pieces[0] + ',',
|
||||
pieces[2],
|
||||
pieces[1],
|
||||
pieces[3],
|
||||
pieces[4],
|
||||
offset,
|
||||
]
|
||||
const parts = [`${pieces[0]},`, pieces[2], pieces[1], pieces[3], pieces[4], offset]
|
||||
|
||||
return parts.join(' ')
|
||||
}
|
||||
|
|
|
@ -43,7 +43,7 @@ const dates = {
|
|||
updatedAt: getLocalizedDate(mod.updatedAt),
|
||||
}
|
||||
|
||||
const locale = getLocale(Astro)
|
||||
const locale = getLocale(Astro as { params: { locale?: string } })
|
||||
|
||||
const {
|
||||
routes: {
|
||||
|
|
|
@ -15,7 +15,7 @@ export async function getStaticPaths() {
|
|||
const i18nPaths = getI18nPaths()
|
||||
|
||||
return i18nPaths.flatMap(({ params: { locale } }) => [
|
||||
...releaseNotes.map((release: any) => ({
|
||||
...releaseNotes.map((release) => ({
|
||||
params: { slug: release.version, locale },
|
||||
props: { ...release },
|
||||
})),
|
||||
|
|
|
@ -5,10 +5,7 @@ import Button from '~/components/Button.astro'
|
|||
import Description from '~/components/Description.astro'
|
||||
import ReleaseNoteItem from '~/components/ReleaseNoteItem.astro'
|
||||
import Layout from '~/layouts/Layout.astro'
|
||||
import {
|
||||
releaseNotes as releaseNotesData,
|
||||
releaseNotesTwilight,
|
||||
} from '~/release-notes'
|
||||
import { releaseNotes as releaseNotesData, releaseNotesTwilight } from '~/release-notes'
|
||||
import { getLocale, getUI } from '~/utils/i18n'
|
||||
export { getStaticPaths } from '~/utils/i18n'
|
||||
|
||||
|
|
|
@ -22,10 +22,7 @@ const {
|
|||
} = getUI(locale)
|
||||
|
||||
// Just redirect to the release notes if we are in a patch version
|
||||
if (
|
||||
latestVersion.version.split('.').length > 2 &&
|
||||
whatsNewText[1] !== latestVersion.version
|
||||
) {
|
||||
if (latestVersion.version.split('.').length > 2 && whatsNewText[1] !== latestVersion.version) {
|
||||
return Astro.redirect(`/release-notes#${latestVersion.version}`)
|
||||
}
|
||||
---
|
||||
|
|
|
@ -26,9 +26,7 @@ export interface ReleaseNote {
|
|||
export const releaseNotes: ReleaseNote[] = releaseNotesStable.reverse()
|
||||
export { default as releaseNotesTwilight } from './release-notes/twilight.json'
|
||||
|
||||
export function getReleaseNoteFirefoxVersion(
|
||||
releaseNote: ReleaseNote,
|
||||
): string | null {
|
||||
export function getReleaseNoteFirefoxVersion(releaseNote: ReleaseNote): string | null {
|
||||
// Check if "firefox" is on the feature list
|
||||
for (const feature of releaseNote.features || []) {
|
||||
if (feature.toLowerCase().includes('firefox')) {
|
||||
|
|
|
@ -31,10 +31,7 @@
|
|||
"version": "1.0.0-a.2",
|
||||
"date": "12/07/2024",
|
||||
"extra": "This release is the second alpha release of the 1.0.0-alpha series. It includes a lot of bug fixes and improvements given the feedback we received from the first alpha release. This release is still not considered stable, but it's a big step towards the first stable release.",
|
||||
"features": [
|
||||
"Added support for macOS aaarch64!",
|
||||
"Some performance improvements"
|
||||
],
|
||||
"features": ["Added support for macOS aaarch64!", "Some performance improvements"],
|
||||
"fixes": [
|
||||
{
|
||||
"description": "Fixed rounded corners of browser views for some websites",
|
||||
|
@ -49,18 +46,13 @@
|
|||
"issue": 50
|
||||
}
|
||||
],
|
||||
"breakingChanges": [
|
||||
"Removed support window's stub installer. It's under development."
|
||||
]
|
||||
"breakingChanges": ["Removed support window's stub installer. It's under development."]
|
||||
},
|
||||
{
|
||||
"version": "1.0.0-a.3",
|
||||
"date": "14/07/2024",
|
||||
"extra": "This release is the third alpha release of the 1.0.0-alpha series. One big feature of this release is the new workspaces feature. This feature allows you to create different workspaces with different tabs and configurations. This release also includes a lot of bug fixes and improvements.",
|
||||
"features": [
|
||||
"Added support for workspaces (Experimental)",
|
||||
"Better support for macOS aarch64"
|
||||
],
|
||||
"features": ["Added support for workspaces (Experimental)", "Better support for macOS aarch64"],
|
||||
"fixes": [
|
||||
{
|
||||
"description": "Fixed subwindows not being displayed correctly",
|
||||
|
@ -262,9 +254,7 @@
|
|||
"issue": 89
|
||||
}
|
||||
],
|
||||
"breakingChanges": [
|
||||
"Changed the ID for flatpak to io.github.zen_browser.zen"
|
||||
]
|
||||
"breakingChanges": ["Changed the ID for flatpak to io.github.zen_browser.zen"]
|
||||
},
|
||||
{
|
||||
"version": "1.0.0-a.11",
|
||||
|
@ -310,9 +300,7 @@
|
|||
"issue": 124
|
||||
}
|
||||
],
|
||||
"breakingChanges": [
|
||||
"Changed the ID for AppImage to io.github.zen_browser.zen"
|
||||
]
|
||||
"breakingChanges": ["Changed the ID for AppImage to io.github.zen_browser.zen"]
|
||||
},
|
||||
{
|
||||
"version": "1.0.0-a.12",
|
||||
|
@ -613,10 +601,7 @@
|
|||
"version": "1.0.0-a.30",
|
||||
"date": "26/08/2024",
|
||||
"extra": "This release is the thirtieth alpha release of the 1.0.0-alpha series.",
|
||||
"features": [
|
||||
"Added support for 24 more languages!",
|
||||
"Update installed mods from the browser settings"
|
||||
],
|
||||
"features": ["Added support for 24 more languages!", "Update installed mods from the browser settings"],
|
||||
"fixes": [
|
||||
{
|
||||
"description": "Letterboxing option is missing",
|
||||
|
@ -904,10 +889,7 @@
|
|||
"description": "Fixed Mods not being applied to every single window opened"
|
||||
}
|
||||
],
|
||||
"breakingChanges": [
|
||||
"Removed Galaxy and Dream mods",
|
||||
"Removed the 'legacy-toolbar' preference"
|
||||
],
|
||||
"breakingChanges": ["Removed Galaxy and Dream mods", "Removed the 'legacy-toolbar' preference"],
|
||||
"themeChanges": [
|
||||
"Themes will now be able to have string and number values",
|
||||
"The configuration schema for mods has been updated. All current mods have been updated automatically."
|
||||
|
@ -947,11 +929,7 @@
|
|||
"image": false,
|
||||
"workflowId": 11020784612,
|
||||
"extra": "This update is a small patch to fix some issues that weren't addressed in the previous release!",
|
||||
"features": [
|
||||
"Moved application menu button to the right",
|
||||
"Added new shortcuts",
|
||||
"Collapsed tab sidebar is now smaller"
|
||||
],
|
||||
"features": ["Moved application menu button to the right", "Added new shortcuts", "Collapsed tab sidebar is now smaller"],
|
||||
"fixes": [
|
||||
{
|
||||
"description": "Fixed issue with hovering over window control buttons (macOS)"
|
||||
|
@ -1155,10 +1133,7 @@
|
|||
"description": "Fixed about page linking 'global Community' to a Mozilla page"
|
||||
}
|
||||
],
|
||||
"features": [
|
||||
"About page will now display the Firefox version used",
|
||||
"Disabled forcing container grouping for workspaces"
|
||||
]
|
||||
"features": ["About page will now display the Firefox version used", "Disabled forcing container grouping for workspaces"]
|
||||
},
|
||||
{
|
||||
"version": "1.0.1-a.11",
|
||||
|
@ -1299,9 +1274,7 @@
|
|||
"description": "Fixed sidebar webpanels being in a darker contrast"
|
||||
}
|
||||
],
|
||||
"features": [
|
||||
"Added a confirmation dialog when the gradient generator has successfully saved the gradient"
|
||||
]
|
||||
"features": ["Added a confirmation dialog when the gradient generator has successfully saved the gradient"]
|
||||
},
|
||||
{
|
||||
"version": "1.0.1-a.15",
|
||||
|
@ -1347,9 +1320,7 @@
|
|||
"issue": 2413
|
||||
}
|
||||
],
|
||||
"breakingChanges": [
|
||||
"Changed the default layout of the customizable UI buttons"
|
||||
],
|
||||
"breakingChanges": ["Changed the default layout of the customizable UI buttons"],
|
||||
"features": [
|
||||
"Added Zen Glance!",
|
||||
"Updated to the latest stable version of Firefox (132.0)",
|
||||
|
@ -2159,10 +2130,7 @@
|
|||
"date": "30/01/2025",
|
||||
"workflowId": 13062083313,
|
||||
"extra": "Quick fix for a critical bug that was introduced in the previous release.",
|
||||
"fixes": [
|
||||
"Fixed the browser not opening when having multiple windows",
|
||||
"Fixed macos fullscreen having a weird shadow"
|
||||
]
|
||||
"fixes": ["Fixed the browser not opening when having multiple windows", "Fixed macos fullscreen having a weird shadow"]
|
||||
},
|
||||
{
|
||||
"version": "1.7.5b",
|
||||
|
@ -2221,9 +2189,7 @@
|
|||
"Fixed opening glance tabs on essentials messing up the sidebar",
|
||||
"Fixed pinned tabs appearing on normal container after a restart"
|
||||
],
|
||||
"features": [
|
||||
"Tabs can now be dragged into pinned tabs by dragging them into the workspace indicator"
|
||||
],
|
||||
"features": ["Tabs can now be dragged into pinned tabs by dragging them into the workspace indicator"],
|
||||
"workflowId": 13209591935,
|
||||
"date": "08/02/2025"
|
||||
},
|
||||
|
@ -2315,9 +2281,7 @@
|
|||
"Fixed pinning a tab adding them to the essentials container",
|
||||
"Other small fixes for compact mode not animating properly"
|
||||
],
|
||||
"features": [
|
||||
"localhost and http URL will no longer be trimmed in single toolbar layout"
|
||||
],
|
||||
"features": ["localhost and http URL will no longer be trimmed in single toolbar layout"],
|
||||
"workflowId": 13530880093,
|
||||
"date": "25/02/2025"
|
||||
},
|
||||
|
@ -2731,25 +2695,25 @@
|
|||
"fixes": [
|
||||
"Fixed issues with toast notifications not being hidden after a timeout and displaying when they shouldn't",
|
||||
{
|
||||
"description": "Fixed macos close buttons being misaligned on collapsed sidebar",
|
||||
"description": "Fixed MacOS close buttons being misaligned on the collapsed sidebar",
|
||||
"issue": 7129
|
||||
},
|
||||
{
|
||||
"description": "Fixed the download animation appearing on all the windows",
|
||||
"description": "Fixed the download animation appearing on all windows",
|
||||
"issue": 8247
|
||||
},
|
||||
{
|
||||
"description": "When using Tabs on the Right, the Glance controls are on the wrong side",
|
||||
"description": "Fixed Glance controls appearing on the wrong side when 'Tabs on the Right' was used",
|
||||
"issue": 7910
|
||||
},
|
||||
"Fixed various issues with the urlbar on double toolbar mode",
|
||||
"Fixed various issues with the URL bar on double toolbar mode",
|
||||
"Fixed some issues with restoring the previous session"
|
||||
],
|
||||
"features": [
|
||||
"Updated firefox 138.0.3",
|
||||
"For macos users, dragging tabs and changing the texture for the workspace's background now provides haptic feedback (zen.haptic-feedback.enabled)",
|
||||
"The 'copy current url' toast now displays a share icon (only on windows and macos)",
|
||||
"The urlbar now can search through renamed pinned tabs"
|
||||
"Updated to Firefox 138.0.3",
|
||||
"For MacOS users, dragging tabs and changing the texture for the workspace's background now provides haptic feedback (zen.haptic-feedback.enabled)",
|
||||
"The 'copy current url' toast now displays a share icon (only on windows and MacOS)",
|
||||
"The URL bar can now search through renamed pinned tabs"
|
||||
],
|
||||
"workflowId": 15003870178,
|
||||
"date": "14/05/2025"
|
||||
|
@ -2758,10 +2722,7 @@
|
|||
"version": "1.12.5b",
|
||||
"image": false,
|
||||
"extra": "",
|
||||
"fixes": [
|
||||
"Fixed a weird shadow with the URL bar.",
|
||||
"Fixed all tabs button appearing unexpectedly."
|
||||
],
|
||||
"fixes": ["Fixed a weird shadow with the URL bar.", "Fixed all tabs button appearing unexpectedly."],
|
||||
"features": [],
|
||||
"workflowId": 15024223699,
|
||||
"date": "14/05/2025"
|
||||
|
|
|
@ -3,29 +3,25 @@
|
|||
* Returns a mapping from filename to checksum.
|
||||
*/
|
||||
export async function getChecksums() {
|
||||
const res = await fetch(
|
||||
'https://api.github.com/repos/zen-browser/desktop/releases/latest',
|
||||
{
|
||||
headers: {
|
||||
Accept: 'application/vnd.github+json',
|
||||
'X-GitHub-Api-Version': '2022-11-28',
|
||||
'User-Agent': 'zen-browser-checksum-fetcher',
|
||||
},
|
||||
const res = await fetch('https://api.github.com/repos/zen-browser/desktop/releases/latest', {
|
||||
headers: {
|
||||
Accept: 'application/vnd.github+json',
|
||||
'X-GitHub-Api-Version': '2022-11-28',
|
||||
'User-Agent': 'zen-browser-checksum-fetcher',
|
||||
},
|
||||
)
|
||||
if (!res.ok)
|
||||
throw new Error('Failed to fetch GitHub release: ' + res.statusText)
|
||||
})
|
||||
if (!res.ok) throw new Error(`Failed to fetch GitHub release: ${res.statusText}`)
|
||||
const data = await res.json()
|
||||
const body = data.body as string
|
||||
|
||||
// Extract the checksum block
|
||||
const match = body.match(/File Checksums \(SHA-256\)[\s\S]*?```([\s\S]*?)```/)
|
||||
const checksums: Record<string, string> = {}
|
||||
if (match && match[1]) {
|
||||
match[1].split('\n').forEach((line) => {
|
||||
if (match?.[1]) {
|
||||
for (const line of match[1].split('\n')) {
|
||||
const [hash, filename] = line.trim().split(/\s+/, 2)
|
||||
if (hash && filename) checksums[filename] = hash
|
||||
})
|
||||
}
|
||||
}
|
||||
return checksums
|
||||
}
|
||||
|
|
|
@ -2,76 +2,142 @@ import type { GetStaticPaths } from 'astro'
|
|||
import { CONSTANT } from '~/constants'
|
||||
import UI_EN from '~/i18n/en/translation.json'
|
||||
|
||||
/**
|
||||
* Represents the available locales in the application
|
||||
* @typedef {string} Locale
|
||||
*/
|
||||
export type Locale = (typeof locales)[number]
|
||||
|
||||
/**
|
||||
* Generates a localized path by prefixing the locale if necessary
|
||||
* @param {Locale} [locale] - The current locale
|
||||
* @returns {function(string): string} A function that transforms paths based on the locale
|
||||
*/
|
||||
export const getPath = (locale?: Locale) => (path: string) => {
|
||||
if (locale && !path.startsWith(`/${locale}`)) {
|
||||
if (locale && locale !== CONSTANT.I18N.DEFAULT_LOCALE && !path.startsWith(`/${locale}`)) {
|
||||
return `/${locale}${path.startsWith('/') ? '' : '/'}${path}`
|
||||
}
|
||||
return path
|
||||
}
|
||||
|
||||
export const getLocale = (Astro: any) => {
|
||||
if (Astro.params.locale) {
|
||||
/**
|
||||
* Extracts the current locale from Astro's params, defaulting to the default locale
|
||||
* @param {Object} Astro - Astro's context object
|
||||
* @param {Object} [Astro.params] - Routing parameters
|
||||
* @param {string} [Astro.params.locale] - The current locale parameter
|
||||
* @returns {Locale} The determined locale
|
||||
*/
|
||||
export const getLocale = (Astro: { params?: { locale?: string } }) => {
|
||||
if (Astro.params?.locale) {
|
||||
return Astro.params.locale as Locale
|
||||
}
|
||||
return CONSTANT.I18N.DEFAULT_LOCALE as Locale
|
||||
}
|
||||
|
||||
/**
|
||||
* List of all supported locales
|
||||
* @type {Locale[]}
|
||||
*/
|
||||
export const locales = CONSTANT.I18N.LOCALES.map(({ value }) => value)
|
||||
|
||||
const otherLocales = CONSTANT.I18N.LOCALES.filter(
|
||||
({ value }) => value !== CONSTANT.I18N.DEFAULT_LOCALE,
|
||||
)
|
||||
/**
|
||||
* List of locales excluding the default locale
|
||||
* @type {Locale[]}
|
||||
*/
|
||||
const otherLocales = CONSTANT.I18N.LOCALES.filter(({ value }) => value !== CONSTANT.I18N.DEFAULT_LOCALE)
|
||||
|
||||
/**
|
||||
* Retrieves locales other than the default locale
|
||||
* @returns {Locale[]} Array of non-default locales
|
||||
*/
|
||||
export const getOtherLocales = () => otherLocales
|
||||
|
||||
/**
|
||||
* Type definition for UI translations based on the English translation
|
||||
* @typedef {Object} UI
|
||||
*/
|
||||
export type UI = typeof UI_EN
|
||||
|
||||
/**
|
||||
* Mapping of locales to their UI translation objects
|
||||
* @type {Object.<Locale, UI>}
|
||||
*/
|
||||
export const ui = { en: UI_EN }
|
||||
|
||||
/**
|
||||
* Retrieves UI translations for a given locale, merging with default translations
|
||||
* @param {Locale} [locale] - The target locale for translations
|
||||
* @returns {UI} Merged UI translations
|
||||
*/
|
||||
export const getUI = (locale?: Locale | string): UI => {
|
||||
const validLocale = locales.includes(locale as Locale)
|
||||
? locale
|
||||
: CONSTANT.I18N.DEFAULT_LOCALE
|
||||
const validLocale = locales.includes(locale as Locale) ? locale : CONSTANT.I18N.DEFAULT_LOCALE
|
||||
const defaultUI = ui[CONSTANT.I18N.DEFAULT_LOCALE]
|
||||
const localeUI = ui[validLocale as Locale]
|
||||
|
||||
function deepMerge<T>(defaultObj: T, overrideObj: Partial<T>): T {
|
||||
if (typeof defaultObj !== 'object' || defaultObj === null)
|
||||
/**
|
||||
* Recursively merges two objects, with the override object taking precedence
|
||||
* @template T
|
||||
* @param {T} defaultObj - The default object to merge from
|
||||
* @param {Partial<T>} overrideObj - The object to merge over the default
|
||||
* @returns {T} The deeply merged object
|
||||
*/
|
||||
function deepMerge<T extends object>(defaultObj: T, overrideObj: Partial<T>): T {
|
||||
// Handle non-object cases
|
||||
if (typeof defaultObj !== 'object' || defaultObj === null) {
|
||||
return (overrideObj ?? defaultObj) as T
|
||||
if (typeof overrideObj !== 'object' || overrideObj === null)
|
||||
}
|
||||
if (typeof overrideObj !== 'object' || overrideObj === null) {
|
||||
return (overrideObj ?? defaultObj) as T
|
||||
const result: any = Array.isArray(defaultObj)
|
||||
? [...defaultObj]
|
||||
: { ...defaultObj }
|
||||
for (const key in defaultObj) {
|
||||
if (Object.prototype.hasOwnProperty.call(defaultObj, key)) {
|
||||
result[key] = deepMerge(
|
||||
(defaultObj as any)[key],
|
||||
(overrideObj as any)?.[key],
|
||||
)
|
||||
}
|
||||
|
||||
// Create a new object or array based on the default object's type
|
||||
const result = Array.isArray(defaultObj) ? [...defaultObj] : { ...defaultObj }
|
||||
|
||||
// Merge properties from the default object
|
||||
for (const key of Object.keys(defaultObj) as Array<keyof T>) {
|
||||
const defaultValue = defaultObj[key]
|
||||
const overrideValue = overrideObj[key]
|
||||
|
||||
// Recursively merge nested objects
|
||||
if (
|
||||
defaultValue !== null &&
|
||||
overrideValue !== null &&
|
||||
typeof defaultValue === 'object' &&
|
||||
typeof overrideValue === 'object'
|
||||
) {
|
||||
// Type assertion to handle nested merging
|
||||
;(result as Record<keyof T, unknown>)[key] = deepMerge(defaultValue as object, overrideValue as Partial<object>)
|
||||
} else if (overrideValue !== undefined) {
|
||||
// Override with the new value if it exists
|
||||
;(result as Record<keyof T, unknown>)[key] = overrideValue
|
||||
}
|
||||
}
|
||||
for (const key in overrideObj) {
|
||||
|
||||
// Add any new properties from overrideObj
|
||||
for (const key of Object.keys(overrideObj) as Array<keyof T>) {
|
||||
if (!(key in defaultObj)) {
|
||||
result[key] = (overrideObj as any)[key]
|
||||
;(result as Record<keyof T, unknown>)[key] = overrideObj[key]
|
||||
}
|
||||
}
|
||||
|
||||
return result as T
|
||||
}
|
||||
|
||||
return deepMerge<UI>(defaultUI, localeUI)
|
||||
return deepMerge(defaultUI, localeUI)
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates static paths for internationalization
|
||||
* @type {GetStaticPaths}
|
||||
* @returns {Array} An array of static paths for different locales
|
||||
*/
|
||||
export const getStaticPaths = (() => {
|
||||
return [
|
||||
{
|
||||
params: { locale: undefined },
|
||||
props: { locale: CONSTANT.I18N.DEFAULT_LOCALE },
|
||||
},
|
||||
...CONSTANT.I18N.LOCALES.filter(
|
||||
({ value }) => value !== CONSTANT.I18N.DEFAULT_LOCALE,
|
||||
).map(({ value }) => ({
|
||||
...CONSTANT.I18N.LOCALES.filter(({ value }) => value !== CONSTANT.I18N.DEFAULT_LOCALE).map(({ value }) => ({
|
||||
params: { locale: value },
|
||||
props: {
|
||||
locale: value,
|
||||
|
@ -80,6 +146,10 @@ export const getStaticPaths = (() => {
|
|||
]
|
||||
}) satisfies GetStaticPaths
|
||||
|
||||
/**
|
||||
* Retrieves all available locales, including both default and non-default
|
||||
* @returns {Locale[]} Combined array of all locales
|
||||
*/
|
||||
export const getLocales = () => {
|
||||
return [...locales, ...otherLocales]
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue