feat: discord threads (#513)
6
.env.example
Normal file
@@ -0,0 +1,6 @@
|
||||
PUBLIC_APPWRITE_PROJECT_INIT_ID=
|
||||
PUBLIC_APPWRITE_PROJECT_ID=
|
||||
PUBLIC_APPWRITE_DB_MAIN_ID=
|
||||
PUBLIC_APPWRITE_COL_THREADS_ID=
|
||||
PUBLIC_APPWRITE_COL_MESSAGES_ID=
|
||||
PUBLIC_APPWRITE_FN_TLDR_ID=
|
||||
8
.github/workflows/production.yml
vendored
@@ -18,7 +18,7 @@ jobs:
|
||||
uses: actions/checkout@v2
|
||||
|
||||
- name: Login to DockerHub
|
||||
uses: docker/login-action@v1
|
||||
uses: docker/login-action@v1
|
||||
with:
|
||||
registry: ghcr.io
|
||||
username: ${{ github.actor }}
|
||||
@@ -54,6 +54,12 @@ jobs:
|
||||
git checkout ${{ env.TAG }}
|
||||
|
||||
rm -f .env
|
||||
echo "PUBLIC_APPWRITE_PROJECT_INIT_ID=${{ env.PUBLIC_APPWRITE_PROJECT_INIT_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_PROJECT_ID=${{ env.PUBLIC_APPWRITE_PROJECT_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_DB_MAIN_ID=${{ env.PUBLIC_APPWRITE_DB_MAIN_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_COL_THREADS_ID=${{ env.PUBLIC_APPWRITE_COL_THREADS_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_COL_MESSAGES_ID=${{ env.PUBLIC_APPWRITE_COL_MESSAGES_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_FN_TLDR_ID=${{ env.PUBLIC_APPWRITE_FN_TLDR_ID }}" >> .env
|
||||
echo "_APP_VERSION=${{ env.TAG }}" >> .env
|
||||
echo "_APP_DOMAIN=${{ secrets.PRD_APP_DOMAIN }}" >> .env
|
||||
echo "_APP_SYSTEM_SECURITY_EMAIL_ADDRESS=${{ secrets.APP_SYSTEM_SECURITY_EMAIL_ADDRESS }}" >> .env
|
||||
|
||||
8
.github/workflows/staging.yml
vendored
@@ -19,7 +19,7 @@ jobs:
|
||||
uses: actions/checkout@v2
|
||||
|
||||
- name: Login to DockerHub
|
||||
uses: docker/login-action@v1
|
||||
uses: docker/login-action@v1
|
||||
with:
|
||||
registry: ghcr.io
|
||||
username: ${{ github.actor }}
|
||||
@@ -55,6 +55,12 @@ jobs:
|
||||
git checkout ${{ env.TAG }}
|
||||
|
||||
rm -f .env
|
||||
echo "PUBLIC_APPWRITE_PROJECT_INIT_ID=${{ env.PUBLIC_APPWRITE_PROJECT_INIT_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_PROJECT_ID=${{ env.PUBLIC_APPWRITE_PROJECT_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_DB_MAIN_ID=${{ env.PUBLIC_APPWRITE_DB_MAIN_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_COL_THREADS_ID=${{ env.PUBLIC_APPWRITE_COL_THREADS_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_COL_MESSAGES_ID=${{ env.PUBLIC_APPWRITE_COL_MESSAGES_ID }}" >> .env
|
||||
echo "PUBLIC_APPWRITE_FN_TLDR_ID=${{ env.PUBLIC_APPWRITE_FN_TLDR_ID }}" >> .env
|
||||
echo "_APP_VERSION=${{ env.TAG }}" >> .env
|
||||
echo "_APP_DOMAIN=${{ secrets.STG_APP_DOMAIN }}" >> .env
|
||||
echo "_APP_SYSTEM_SECURITY_EMAIL_ADDRESS=${{ secrets.APP_SYSTEM_SECURITY_EMAIL_ADDRESS }}" >> .env
|
||||
|
||||
6
.github/workflows/tests.yml
vendored
@@ -37,4 +37,10 @@ jobs:
|
||||
- name: Build Website
|
||||
env:
|
||||
NODE_OPTIONS: '--max_old_space_size=4096'
|
||||
PUBLIC_APPWRITE_PROJECT_INIT_ID: ${{ secrets.PUBLIC_APPWRITE_PROJECT_INIT_ID }}
|
||||
PUBLIC_APPWRITE_PROJECT_ID: ${{ secrets.PUBLIC_APPWRITE_PROJECT_ID }}
|
||||
PUBLIC_APPWRITE_DB_MAIN_ID: ${{ secrets.PUBLIC_APPWRITE_DB_MAIN_ID }}
|
||||
PUBLIC_APPWRITE_COL_THREADS_ID: ${{ secrets.PUBLIC_APPWRITE_COL_THREADS_ID }}
|
||||
PUBLIC_APPWRITE_COL_MESSAGES_ID: ${{ secrets.PUBLIC_APPWRITE_COL_MESSAGES_ID }}
|
||||
PUBLIC_APPWRITE_FN_TLDR_ID: ${{ secrets.PUBLIC_APPWRITE_FN_TLDR_ID }}
|
||||
run: pnpm run build
|
||||
|
||||
4
.gitignore
vendored
@@ -6,7 +6,9 @@ node_modules
|
||||
/package
|
||||
.env
|
||||
.env.*
|
||||
.envrc
|
||||
!.env.example
|
||||
vite.config.js.timestamp-*
|
||||
vite.config.ts.timestamp-*
|
||||
package-lock.json
|
||||
package-lock.json
|
||||
.tool-versions
|
||||
@@ -60,6 +60,13 @@ services:
|
||||
<<: *x-logging
|
||||
networks:
|
||||
- cloud
|
||||
environment:
|
||||
- PUBLIC_APPWRITE_PROJECT_INIT_ID
|
||||
- PUBLIC_APPWRITE_PROJECT_ID
|
||||
- PUBLIC_APPWRITE_DB_MAIN_ID
|
||||
- PUBLIC_APPWRITE_COL_THREADS_ID
|
||||
- PUBLIC_APPWRITE_COL_MESSAGES_ID
|
||||
- PUBLIC_APPWRITE_FN_TLDR_ID
|
||||
deploy:
|
||||
<<: *x-update-config
|
||||
mode: replicated
|
||||
@@ -68,7 +75,7 @@ services:
|
||||
max_replicas_per_node: 2
|
||||
constraints:
|
||||
- node.role == worker
|
||||
preferences:
|
||||
preferences:
|
||||
- spread: node.role == worker
|
||||
labels:
|
||||
- traefik.enable=true
|
||||
@@ -94,7 +101,7 @@ services:
|
||||
environment:
|
||||
- TIME_BETWEEN_RUNS=3600
|
||||
- UNUSED_TIME=6h
|
||||
|
||||
|
||||
sematext-agent:
|
||||
image: sematext/agent:latest
|
||||
environment:
|
||||
|
||||
@@ -61,6 +61,13 @@ services:
|
||||
<<: *x-logging
|
||||
networks:
|
||||
- cloud
|
||||
environment:
|
||||
- PUBLIC_APPWRITE_PROJECT_INIT_ID
|
||||
- PUBLIC_APPWRITE_PROJECT_ID
|
||||
- PUBLIC_APPWRITE_DB_MAIN_ID
|
||||
- PUBLIC_APPWRITE_COL_THREADS_ID
|
||||
- PUBLIC_APPWRITE_COL_MESSAGES_ID
|
||||
- PUBLIC_APPWRITE_FN_TLDR_ID
|
||||
deploy:
|
||||
<<: *x-update-config
|
||||
mode: replicated
|
||||
@@ -69,7 +76,7 @@ services:
|
||||
max_replicas_per_node: 2
|
||||
constraints:
|
||||
- node.role == worker
|
||||
preferences:
|
||||
preferences:
|
||||
- spread: node.role == worker
|
||||
labels:
|
||||
- traefik.enable=true
|
||||
@@ -96,7 +103,7 @@ services:
|
||||
- RUN_ON_STARTUP=true
|
||||
volumes:
|
||||
- /var/run/docker.sock:/var/run/docker.sock
|
||||
|
||||
|
||||
sematext-agent:
|
||||
image: sematext/agent:latest
|
||||
environment:
|
||||
|
||||
11
package.json
@@ -20,18 +20,19 @@
|
||||
},
|
||||
"devDependencies": {
|
||||
"@melt-ui/pp": "^0.1.4",
|
||||
"@melt-ui/svelte": "^0.60.2",
|
||||
"@melt-ui/svelte": "^0.65.0",
|
||||
"@playwright/test": "^1.40.0",
|
||||
"@sveltejs/adapter-node": "^1.3.1",
|
||||
"@sveltejs/adapter-static": "^2.0.3",
|
||||
"@sveltejs/enhanced-img": "^0.1.2",
|
||||
"@sveltejs/kit": "^1.27.6",
|
||||
"@sveltejs/kit": "^1.27.7",
|
||||
"@types/compression": "^1.7.5",
|
||||
"@types/glob": "^8.1.0",
|
||||
"@types/markdown-it": "^13.0.7",
|
||||
"@types/morgan": "^1.9.9",
|
||||
"@typescript-eslint/eslint-plugin": "^5.62.0",
|
||||
"@typescript-eslint/parser": "^5.62.0",
|
||||
"appwrite": "^13.0.1",
|
||||
"eslint": "^8.54.0",
|
||||
"eslint-config-prettier": "^8.10.0",
|
||||
"eslint-plugin-svelte": "^2.35.1",
|
||||
@@ -40,11 +41,12 @@
|
||||
"oslllo-svg-fixer": "^3.0.0",
|
||||
"prettier": "^2.8.8",
|
||||
"prettier-plugin-svelte": "^2.10.1",
|
||||
"sass": "^1.69.5",
|
||||
"sass": "^1.69.7",
|
||||
"svelte": "^4.2.7",
|
||||
"svelte-check": "^3.6.0",
|
||||
"svelte-markdoc-preprocess": "^1.1.3",
|
||||
"svelte-sequential-preprocessor": "^2.0.1",
|
||||
"sveltekit-search-params": "^1.0.16",
|
||||
"svgo": "^3.0.4",
|
||||
"svgtofont": "^4.0.0",
|
||||
"tslib": "^2.6.2",
|
||||
@@ -66,6 +68,7 @@
|
||||
"markdown-it": "^13.0.2",
|
||||
"meilisearch": "^0.35.1",
|
||||
"motion": "^10.16.4",
|
||||
"sharp": "^0.32.6"
|
||||
"sharp": "^0.32.6",
|
||||
"svelte-markdown": "^0.4.0"
|
||||
}
|
||||
}
|
||||
|
||||
216
pnpm-lock.yaml
generated
@@ -38,29 +38,32 @@ dependencies:
|
||||
sharp:
|
||||
specifier: ^0.32.6
|
||||
version: 0.32.6
|
||||
svelte-markdown:
|
||||
specifier: ^0.4.0
|
||||
version: 0.4.1(svelte@4.2.7)
|
||||
|
||||
devDependencies:
|
||||
'@melt-ui/pp':
|
||||
specifier: ^0.1.4
|
||||
version: 0.1.4(@melt-ui/svelte@0.60.2)(svelte@4.2.7)
|
||||
version: 0.1.4(@melt-ui/svelte@0.65.2)(svelte@4.2.7)
|
||||
'@melt-ui/svelte':
|
||||
specifier: ^0.60.2
|
||||
version: 0.60.2(svelte@4.2.7)
|
||||
specifier: ^0.65.0
|
||||
version: 0.65.2(svelte@4.2.7)
|
||||
'@playwright/test':
|
||||
specifier: ^1.40.0
|
||||
version: 1.40.0
|
||||
'@sveltejs/adapter-node':
|
||||
specifier: ^1.3.1
|
||||
version: 1.3.1(@sveltejs/kit@1.27.6)
|
||||
version: 1.3.1(@sveltejs/kit@1.30.3)
|
||||
'@sveltejs/adapter-static':
|
||||
specifier: ^2.0.3
|
||||
version: 2.0.3(@sveltejs/kit@1.27.6)
|
||||
version: 2.0.3(@sveltejs/kit@1.30.3)
|
||||
'@sveltejs/enhanced-img':
|
||||
specifier: ^0.1.2
|
||||
version: 0.1.5(svelte@4.2.7)
|
||||
'@sveltejs/kit':
|
||||
specifier: ^1.27.6
|
||||
version: 1.27.6(svelte@4.2.7)(vite@4.5.1)
|
||||
specifier: ^1.27.7
|
||||
version: 1.30.3(svelte@4.2.7)(vite@4.5.1)
|
||||
'@types/compression':
|
||||
specifier: ^1.7.5
|
||||
version: 1.7.5
|
||||
@@ -79,6 +82,9 @@ devDependencies:
|
||||
'@typescript-eslint/parser':
|
||||
specifier: ^5.62.0
|
||||
version: 5.62.0(eslint@8.54.0)(typescript@5.3.2)
|
||||
appwrite:
|
||||
specifier: ^13.0.1
|
||||
version: 13.0.1
|
||||
eslint:
|
||||
specifier: ^8.54.0
|
||||
version: 8.54.0
|
||||
@@ -104,20 +110,23 @@ devDependencies:
|
||||
specifier: ^2.10.1
|
||||
version: 2.10.1(prettier@2.8.8)(svelte@4.2.7)
|
||||
sass:
|
||||
specifier: ^1.69.5
|
||||
version: 1.69.5
|
||||
specifier: ^1.69.7
|
||||
version: 1.69.7
|
||||
svelte:
|
||||
specifier: ^4.2.7
|
||||
version: 4.2.7
|
||||
svelte-check:
|
||||
specifier: ^3.6.0
|
||||
version: 3.6.0(postcss@8.4.31)(sass@1.69.5)(svelte@4.2.7)
|
||||
version: 3.6.0(postcss@8.4.31)(sass@1.69.7)(svelte@4.2.7)
|
||||
svelte-markdoc-preprocess:
|
||||
specifier: ^1.1.3
|
||||
version: 1.1.3
|
||||
svelte-sequential-preprocessor:
|
||||
specifier: ^2.0.1
|
||||
version: 2.0.1
|
||||
sveltekit-search-params:
|
||||
specifier: ^1.0.16
|
||||
version: 1.1.1(@sveltejs/kit@1.30.3)(svelte@4.2.7)
|
||||
svgo:
|
||||
specifier: ^3.0.4
|
||||
version: 3.0.4
|
||||
@@ -132,7 +141,7 @@ devDependencies:
|
||||
version: 5.3.2
|
||||
vite:
|
||||
specifier: ^4.5.1
|
||||
version: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
version: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
vite-plugin-dynamic-import:
|
||||
specifier: ^1.5.0
|
||||
version: 1.5.0
|
||||
@@ -141,7 +150,7 @@ devDependencies:
|
||||
version: 1.1.7(vite@4.5.1)
|
||||
vitest:
|
||||
specifier: ^0.32.4
|
||||
version: 0.32.4(sass@1.69.5)
|
||||
version: 0.32.4(sass@1.69.7)
|
||||
|
||||
packages:
|
||||
|
||||
@@ -156,7 +165,6 @@ packages:
|
||||
dependencies:
|
||||
'@jridgewell/gen-mapping': 0.3.3
|
||||
'@jridgewell/trace-mapping': 0.3.20
|
||||
dev: true
|
||||
|
||||
/@appwrite.io/pink-icons@0.1.0-next.9:
|
||||
resolution: {integrity: sha512-6t4Pqt/xugjpJQyaMx1u/7Gt9CkW5iItDAgUKcIMm84E4NbDJq8ZdAhhvctGQQppKUgHDPi+6x1XveUUd7tdbg==}
|
||||
@@ -462,6 +470,12 @@ packages:
|
||||
resolution: {integrity: sha512-dvuCeX5fC9dXgJn9t+X5atfmgQAzUOWqS1254Gh0m6i8wKd10ebXkfNKiRK+1GWi/yTvvLDHpoxLr0xxxeslWw==}
|
||||
dev: true
|
||||
|
||||
/@internationalized/date@3.5.1:
|
||||
resolution: {integrity: sha512-LUQIfwU9e+Fmutc/DpRTGXSdgYZLBegi4wygCWDSVmUdLTaMHsQyASDiJtREwanwKuQLq0hY76fCJ9J/9I2xOQ==}
|
||||
dependencies:
|
||||
'@swc/helpers': 0.5.3
|
||||
dev: true
|
||||
|
||||
/@isaacs/cliui@8.0.2:
|
||||
resolution: {integrity: sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==}
|
||||
engines: {node: '>=12'}
|
||||
@@ -863,28 +877,23 @@ packages:
|
||||
'@jridgewell/set-array': 1.1.2
|
||||
'@jridgewell/sourcemap-codec': 1.4.15
|
||||
'@jridgewell/trace-mapping': 0.3.20
|
||||
dev: true
|
||||
|
||||
/@jridgewell/resolve-uri@3.1.1:
|
||||
resolution: {integrity: sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA==}
|
||||
engines: {node: '>=6.0.0'}
|
||||
dev: true
|
||||
|
||||
/@jridgewell/set-array@1.1.2:
|
||||
resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==}
|
||||
engines: {node: '>=6.0.0'}
|
||||
dev: true
|
||||
|
||||
/@jridgewell/sourcemap-codec@1.4.15:
|
||||
resolution: {integrity: sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==}
|
||||
dev: true
|
||||
|
||||
/@jridgewell/trace-mapping@0.3.20:
|
||||
resolution: {integrity: sha512-R8LcPeWZol2zR8mmH3JeKQ6QRCFb7XgUhV9ZlGhHLGyg4wpPiPZNQOOWhFZhxKw8u//yTbNGI42Bx/3paXEQ+Q==}
|
||||
dependencies:
|
||||
'@jridgewell/resolve-uri': 3.1.1
|
||||
'@jridgewell/sourcemap-codec': 1.4.15
|
||||
dev: true
|
||||
|
||||
/@lit-labs/ssr-dom-shim@1.1.2:
|
||||
resolution: {integrity: sha512-jnOD+/+dSrfTWYfSXBXlo5l5f0q1UuJo3tkbMDCYA2lKUYq79jaxqtGEvnRoh049nt1vdo1+45RinipU6FGY2g==}
|
||||
@@ -911,25 +920,26 @@ packages:
|
||||
'@types/markdown-it': 12.2.3
|
||||
dev: true
|
||||
|
||||
/@melt-ui/pp@0.1.4(@melt-ui/svelte@0.60.2)(svelte@4.2.7):
|
||||
/@melt-ui/pp@0.1.4(@melt-ui/svelte@0.65.2)(svelte@4.2.7):
|
||||
resolution: {integrity: sha512-zR+Kl3CZJPJBHW8V7YcdQCMI/dVcnW9Ct3yGbVaIywYVStVRS7F9uEDOea3xLLT2WTGodQePzPlUn53yKFu87g==}
|
||||
engines: {pnpm: '>=8.6.3'}
|
||||
peerDependencies:
|
||||
'@melt-ui/svelte': '>= 0.29.0'
|
||||
svelte: ^3.55.0 || ^4.0.0 || ^5.0.0-next.1
|
||||
dependencies:
|
||||
'@melt-ui/svelte': 0.60.2(svelte@4.2.7)
|
||||
'@melt-ui/svelte': 0.65.2(svelte@4.2.7)
|
||||
estree-walker: 3.0.3
|
||||
svelte: 4.2.7
|
||||
dev: true
|
||||
|
||||
/@melt-ui/svelte@0.60.2(svelte@4.2.7):
|
||||
resolution: {integrity: sha512-dBGW7dIDBMYchCH0Fx9byqrCYtpkXX1QUGXdv1e2aQE20bDCrQqwVSV0/1iWuJVYyFeo2xUdr0/LVZJ6lOw4mg==}
|
||||
/@melt-ui/svelte@0.65.2(svelte@4.2.7):
|
||||
resolution: {integrity: sha512-BpsSl9Bjp1++8U3+LaDOFUoX/PFQ9N7QWFhlFdUEZduhrbVyU70v9A459SKrQ+esFSjvh1AvqJYkMAUJXJlAmQ==}
|
||||
peerDependencies:
|
||||
svelte: '>=3 <5'
|
||||
dependencies:
|
||||
'@floating-ui/core': 1.5.0
|
||||
'@floating-ui/dom': 1.5.3
|
||||
'@internationalized/date': 3.5.1
|
||||
dequal: 2.0.3
|
||||
focus-trap: 7.5.4
|
||||
nanoid: 4.0.2
|
||||
@@ -1254,7 +1264,7 @@ packages:
|
||||
lit: 2.8.0
|
||||
dev: false
|
||||
|
||||
/@sveltejs/adapter-node@1.3.1(@sveltejs/kit@1.27.6):
|
||||
/@sveltejs/adapter-node@1.3.1(@sveltejs/kit@1.30.3):
|
||||
resolution: {integrity: sha512-A0VgRQDCDPzdLNoiAbcOxGw4zT1Mc+n1LwT1OmO350R7WxrEqdMUChPPOd1iMfIDWlP4ie6E2d/WQf5es2d4Zw==}
|
||||
peerDependencies:
|
||||
'@sveltejs/kit': ^1.0.0
|
||||
@@ -1262,16 +1272,16 @@ packages:
|
||||
'@rollup/plugin-commonjs': 25.0.7(rollup@3.29.4)
|
||||
'@rollup/plugin-json': 6.0.1(rollup@3.29.4)
|
||||
'@rollup/plugin-node-resolve': 15.2.3(rollup@3.29.4)
|
||||
'@sveltejs/kit': 1.27.6(svelte@4.2.7)(vite@4.5.1)
|
||||
'@sveltejs/kit': 1.30.3(svelte@4.2.7)(vite@4.5.1)
|
||||
rollup: 3.29.4
|
||||
dev: true
|
||||
|
||||
/@sveltejs/adapter-static@2.0.3(@sveltejs/kit@1.27.6):
|
||||
/@sveltejs/adapter-static@2.0.3(@sveltejs/kit@1.30.3):
|
||||
resolution: {integrity: sha512-VUqTfXsxYGugCpMqQv1U0LIdbR3S5nBkMMDmpjGVJyM6Q2jHVMFtdWJCkeHMySc6mZxJ+0eZK3T7IgmUCDrcUQ==}
|
||||
peerDependencies:
|
||||
'@sveltejs/kit': ^1.5.0
|
||||
dependencies:
|
||||
'@sveltejs/kit': 1.27.6(svelte@4.2.7)(vite@4.5.1)
|
||||
'@sveltejs/kit': 1.30.3(svelte@4.2.7)(vite@4.5.1)
|
||||
dev: true
|
||||
|
||||
/@sveltejs/enhanced-img@0.1.5(svelte@4.2.7):
|
||||
@@ -1285,8 +1295,8 @@ packages:
|
||||
- svelte
|
||||
dev: true
|
||||
|
||||
/@sveltejs/kit@1.27.6(svelte@4.2.7)(vite@4.5.1):
|
||||
resolution: {integrity: sha512-GsjTkMbKzXdbeRg0tk8S7HNShQ4879ftRr0ZHaZfjbig1xQwG57Bvcm9U9/mpLJtCapLbLWUnygKrgcLISLC8A==}
|
||||
/@sveltejs/kit@1.30.3(svelte@4.2.7)(vite@4.5.1):
|
||||
resolution: {integrity: sha512-0DzVXfU4h+tChFvoc8C61IqErCyskD4ydSIDjpKS2lYlEzIYrtYrY7juSqACFxqcvZAnOEXvSY+zZ8br0+ZMMg==}
|
||||
engines: {node: ^16.14 || >=18}
|
||||
hasBin: true
|
||||
requiresBuild: true
|
||||
@@ -1308,7 +1318,7 @@ packages:
|
||||
svelte: 4.2.7
|
||||
tiny-glob: 0.2.9
|
||||
undici: 5.26.5
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: true
|
||||
@@ -1324,7 +1334,7 @@ packages:
|
||||
'@sveltejs/vite-plugin-svelte': 2.5.2(svelte@4.2.7)(vite@4.5.1)
|
||||
debug: 4.3.4
|
||||
svelte: 4.2.7
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: true
|
||||
@@ -1343,12 +1353,18 @@ packages:
|
||||
magic-string: 0.30.5
|
||||
svelte: 4.2.7
|
||||
svelte-hmr: 0.15.3(svelte@4.2.7)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
vitefu: 0.2.5(vite@4.5.1)
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: true
|
||||
|
||||
/@swc/helpers@0.5.3:
|
||||
resolution: {integrity: sha512-FaruWX6KdudYloq1AHD/4nU+UsMTdNE8CKyrseXWEcgjDAbvkwJg2QGPAnfIJLIWsjZOSPLOAykK6fuYp4vp4A==}
|
||||
dependencies:
|
||||
tslib: 2.6.2
|
||||
dev: true
|
||||
|
||||
/@tokenizer/token@0.3.0:
|
||||
resolution: {integrity: sha512-OvjF+z51L3ov0OyAU0duzsYuvO01PH7x4t6DJx+guahgTnBHkhJdG7soQeTSFLWN3efnHyibZ4Z8l2EuWwJN3A==}
|
||||
dev: true
|
||||
@@ -1408,7 +1424,6 @@ packages:
|
||||
|
||||
/@types/estree@1.0.5:
|
||||
resolution: {integrity: sha512-/kYRxGDLWzHOB7q+wtSUQlFrtcdUccpfy+X+9iMBpHK8QLLhx2wIPYuS5DYtR9Wa/YlZAbIovy7qVdB1Aq6Lyw==}
|
||||
dev: true
|
||||
|
||||
/@types/express-serve-static-core@4.17.41:
|
||||
resolution: {integrity: sha512-OaJ7XLaelTgrvlZD8/aa0vvvxZdUmlCn6MtWeB7TkiKW70BQLc9XEPpDLPdbo52ZhXUCrznlWdCHWxJWtdyajA==}
|
||||
@@ -1476,6 +1491,10 @@ packages:
|
||||
'@types/mdurl': 1.0.5
|
||||
dev: true
|
||||
|
||||
/@types/marked@5.0.2:
|
||||
resolution: {integrity: sha512-OucS4KMHhFzhz27KxmWg7J+kIYqyqoW5kdIEI319hqARQQUTqhao3M/F+uFnDXD0Rg72iDDZxZNxq5gvctmLlg==}
|
||||
dev: false
|
||||
|
||||
/@types/mdurl@1.0.5:
|
||||
resolution: {integrity: sha512-6L6VymKTzYSrEf4Nev4Xa1LCHKrlTlYCBMTlQKFuddo1CvQcE52I0mwfOJayueUC7MJuXOeHTcIU683lzd0cUA==}
|
||||
dev: true
|
||||
@@ -1781,7 +1800,6 @@ packages:
|
||||
resolution: {integrity: sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w==}
|
||||
engines: {node: '>=0.4.0'}
|
||||
hasBin: true
|
||||
dev: true
|
||||
|
||||
/agent-base@6.0.2:
|
||||
resolution: {integrity: sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==}
|
||||
@@ -1864,6 +1882,15 @@ packages:
|
||||
picomatch: 2.3.1
|
||||
dev: true
|
||||
|
||||
/appwrite@13.0.1:
|
||||
resolution: {integrity: sha512-kdOLB5Qbr2beQW72diA/dx8L16LywHcQV1H6oqgGtf64Mo6LsvyIM1hEVxWmFLwAXMaOtsqb7Mcs4+oQHo+WmQ==}
|
||||
dependencies:
|
||||
cross-fetch: 3.1.5
|
||||
isomorphic-form-data: 2.0.0
|
||||
transitivePeerDependencies:
|
||||
- encoding
|
||||
dev: true
|
||||
|
||||
/aproba@2.0.0:
|
||||
resolution: {integrity: sha512-lYe4Gx7QT+MKGbDsA+Z+he/Wtef0BiwDOlK/XkBrdfsh9J/jPPXbX0tE9x9cl27Tmu5gg3QUbUrQYa/y+KOHPQ==}
|
||||
dev: true
|
||||
@@ -1883,7 +1910,6 @@ packages:
|
||||
resolution: {integrity: sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==}
|
||||
dependencies:
|
||||
dequal: 2.0.3
|
||||
dev: true
|
||||
|
||||
/arr-diff@4.0.0:
|
||||
resolution: {integrity: sha512-YVIQ82gZPGBebQV/a8dar4AitzCQs0jjXwMPZllpXMaGjXPYVUawSxQrRsjhjupyVxEvbHgUmIhKVlND+j02kA==}
|
||||
@@ -1927,6 +1953,10 @@ packages:
|
||||
resolution: {integrity: sha512-baNZyqaaLhyLVKm/DlvdW051MSgO6b8eVfIezl9E5PqWxFgzLm/wQntEW4zOytVburDEr0JlALEpdOFwvErLsg==}
|
||||
dev: true
|
||||
|
||||
/asynckit@0.4.0:
|
||||
resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==}
|
||||
dev: true
|
||||
|
||||
/atob@2.1.2:
|
||||
resolution: {integrity: sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==}
|
||||
engines: {node: '>= 4.5.0'}
|
||||
@@ -1950,7 +1980,6 @@ packages:
|
||||
resolution: {integrity: sha512-jsyHu61e6N4Vbz/v18DHwWYKK0bSWLqn47eeDSKPB7m8tqMHF9YJ+mhIk2lVteyZrY8tnSj/jHOv4YiTCuCJgg==}
|
||||
dependencies:
|
||||
dequal: 2.0.3
|
||||
dev: true
|
||||
|
||||
/b4a@1.6.4:
|
||||
resolution: {integrity: sha512-fpWrvyVHEKyeEvbKZTVOeZF3VSKKWtJxFIxX/jaVPf+cLbGUSitjb49pHLqPV2BUNNZ0LcoeEGfE/YCpyDYHIw==}
|
||||
@@ -2276,7 +2305,6 @@ packages:
|
||||
acorn: 8.11.2
|
||||
estree-walker: 3.0.3
|
||||
periscopic: 3.1.0
|
||||
dev: true
|
||||
|
||||
/collection-visit@1.0.0:
|
||||
resolution: {integrity: sha512-lNkKvzEeMBBjUGHZ+q6z9pSJla0KWAQPvtzhEV9+iGyQYG+pBpl7xKDhxoNSOZH2hhv0v5k0y2yAM4o4SjoSkw==}
|
||||
@@ -2318,6 +2346,13 @@ packages:
|
||||
hasBin: true
|
||||
dev: true
|
||||
|
||||
/combined-stream@1.0.8:
|
||||
resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==}
|
||||
engines: {node: '>= 0.8'}
|
||||
dependencies:
|
||||
delayed-stream: 1.0.0
|
||||
dev: true
|
||||
|
||||
/commander@4.1.1:
|
||||
resolution: {integrity: sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==}
|
||||
engines: {node: '>= 6'}
|
||||
@@ -2416,6 +2451,14 @@ packages:
|
||||
resolution: {integrity: sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==}
|
||||
dev: true
|
||||
|
||||
/cross-fetch@3.1.5:
|
||||
resolution: {integrity: sha512-lvb1SBsI0Z7GDwmuid+mU3kWVBwTVUbe7S0H52yaaAdQOXq2YktTCZdlAcNKFzE6QtRz0snpw9bNiPeOIkkQvw==}
|
||||
dependencies:
|
||||
node-fetch: 2.6.7
|
||||
transitivePeerDependencies:
|
||||
- encoding
|
||||
dev: true
|
||||
|
||||
/cross-fetch@3.1.8:
|
||||
resolution: {integrity: sha512-cvA+JwZoU0Xq+h6WkMvAUqPEYy92Obet6UdKLfW60qn99ftItKjB5T+BkyWOFWe2pUyfQ+IJHmpOTznqk1M6Kg==}
|
||||
dependencies:
|
||||
@@ -2457,7 +2500,6 @@ packages:
|
||||
dependencies:
|
||||
mdn-data: 2.0.30
|
||||
source-map-js: 1.0.2
|
||||
dev: true
|
||||
|
||||
/css-what@6.1.0:
|
||||
resolution: {integrity: sha512-HTUrgRJ7r4dsZKU6GjmpfRK1O76h97Z8MfS1G0FozR+oF2kG6Vfe8JE6zwrkbxigziPHinCJ+gCPjA9EaBDtRw==}
|
||||
@@ -2579,6 +2621,11 @@ packages:
|
||||
slash: 3.0.0
|
||||
dev: true
|
||||
|
||||
/delayed-stream@1.0.0:
|
||||
resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==}
|
||||
engines: {node: '>=0.4.0'}
|
||||
dev: true
|
||||
|
||||
/delegates@1.0.0:
|
||||
resolution: {integrity: sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==}
|
||||
dev: true
|
||||
@@ -2591,7 +2638,6 @@ packages:
|
||||
/dequal@2.0.3:
|
||||
resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==}
|
||||
engines: {node: '>=6'}
|
||||
dev: true
|
||||
|
||||
/destroy@1.2.0:
|
||||
resolution: {integrity: sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==}
|
||||
@@ -2938,7 +2984,6 @@ packages:
|
||||
resolution: {integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==}
|
||||
dependencies:
|
||||
'@types/estree': 1.0.5
|
||||
dev: true
|
||||
|
||||
/esutils@2.0.3:
|
||||
resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==}
|
||||
@@ -3177,6 +3222,15 @@ packages:
|
||||
signal-exit: 4.1.0
|
||||
dev: true
|
||||
|
||||
/form-data@2.5.1:
|
||||
resolution: {integrity: sha512-m21N3WOmEEURgk6B9GLOE4RuWOFf28Lhh9qGYeNlGq4VDXUlJy2th2slBNU8Gp8EzloYZOibZJ7t5ecIrFSjVA==}
|
||||
engines: {node: '>= 0.12'}
|
||||
dependencies:
|
||||
asynckit: 0.4.0
|
||||
combined-stream: 1.0.8
|
||||
mime-types: 2.1.35
|
||||
dev: true
|
||||
|
||||
/forwarded@0.2.0:
|
||||
resolution: {integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==}
|
||||
engines: {node: '>= 0.6'}
|
||||
@@ -3759,7 +3813,6 @@ packages:
|
||||
resolution: {integrity: sha512-v3rht/LgVcsdZa3O2Nqs+NMowLOxeOm7Ay9+/ARQ2F+qEoANRcqrjAZKGN0v8ymUetZGgkp26LTnGT7H0Qo9Pg==}
|
||||
dependencies:
|
||||
'@types/estree': 1.0.5
|
||||
dev: true
|
||||
|
||||
/is-windows@1.0.2:
|
||||
resolution: {integrity: sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==}
|
||||
@@ -3786,6 +3839,12 @@ packages:
|
||||
engines: {node: '>=0.10.0'}
|
||||
dev: true
|
||||
|
||||
/isomorphic-form-data@2.0.0:
|
||||
resolution: {integrity: sha512-TYgVnXWeESVmQSg4GLVbalmQ+B4NPi/H4eWxqALKj63KsUrcu301YDjBqaOw3h+cbak7Na4Xyps3BiptHtxTfg==}
|
||||
dependencies:
|
||||
form-data: 2.5.1
|
||||
dev: true
|
||||
|
||||
/jackspeak@2.3.6:
|
||||
resolution: {integrity: sha512-N3yCS/NegsOBokc8GAdM8UcmfsKiSS8cipheD/nivzr700H+nsMOxJjQnvwOcRYVuFkdH0wGUvW2WbXGmrZGbQ==}
|
||||
engines: {node: '>=14'}
|
||||
@@ -3965,7 +4024,6 @@ packages:
|
||||
|
||||
/locate-character@3.0.0:
|
||||
resolution: {integrity: sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA==}
|
||||
dev: true
|
||||
|
||||
/locate-path@6.0.0:
|
||||
resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==}
|
||||
@@ -4020,7 +4078,6 @@ packages:
|
||||
engines: {node: '>=12'}
|
||||
dependencies:
|
||||
'@jridgewell/sourcemap-codec': 1.4.15
|
||||
dev: true
|
||||
|
||||
/make-fetch-happen@10.2.1:
|
||||
resolution: {integrity: sha512-NgOPbRiaQM10DYXvN3/hhGVI2M5MtITFryzBGxHM5p4wnFxsVCbxkrBrDsk+EZ5OB4jEOT7AjDxtdF+KVEFT7w==}
|
||||
@@ -4070,6 +4127,12 @@ packages:
|
||||
uc.micro: 1.0.6
|
||||
dev: false
|
||||
|
||||
/marked@5.1.2:
|
||||
resolution: {integrity: sha512-ahRPGXJpjMjwSOlBoTMZAK7ATXkli5qCPxZ21TG44rx1KEo44bii4ekgTDQPNRQ4Kh7JMb9Ub1PVk1NxRSsorg==}
|
||||
engines: {node: '>= 16'}
|
||||
hasBin: true
|
||||
dev: false
|
||||
|
||||
/maxstache-stream@1.0.4:
|
||||
resolution: {integrity: sha512-v8qlfPN0pSp7bdSoLo1NTjG43GXGqk5W2NWFnOCq2GlmFFqebGzPCjLKSbShuqIOVorOtZSAy7O/S1OCCRONUw==}
|
||||
dependencies:
|
||||
@@ -4089,7 +4152,6 @@ packages:
|
||||
|
||||
/mdn-data@2.0.30:
|
||||
resolution: {integrity: sha512-GaqWWShW4kv/G9IEucWScBx9G1/vsFZZJUO+tD26M8J8z3Kw5RDQjaoZe03YAClgeS/SWPOcb4nkFBTEi5DUEA==}
|
||||
dev: true
|
||||
|
||||
/mdurl@1.0.1:
|
||||
resolution: {integrity: sha512-/sKlQJCBYVY9Ers9hqzKou4H6V5UWc/M59TH2dvkt+84itfnq7uFOMLpOiOS4ujvHP4etln18fmIxA5R5fll0g==}
|
||||
@@ -4158,14 +4220,12 @@ packages:
|
||||
/mime-db@1.52.0:
|
||||
resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==}
|
||||
engines: {node: '>= 0.6'}
|
||||
dev: false
|
||||
|
||||
/mime-types@2.1.35:
|
||||
resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==}
|
||||
engines: {node: '>= 0.6'}
|
||||
dependencies:
|
||||
mime-db: 1.52.0
|
||||
dev: false
|
||||
|
||||
/mime@1.6.0:
|
||||
resolution: {integrity: sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==}
|
||||
@@ -4428,6 +4488,18 @@ packages:
|
||||
/node-addon-api@6.1.0:
|
||||
resolution: {integrity: sha512-+eawOlIgy680F0kBzPUNFhMZGtJ1YmqM6l4+Crf4IkImjYrO/mqPwRMh352g23uIaQKFItcQ64I7KMaJxHgAVA==}
|
||||
|
||||
/node-fetch@2.6.7:
|
||||
resolution: {integrity: sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==}
|
||||
engines: {node: 4.x || >=6.0.0}
|
||||
peerDependencies:
|
||||
encoding: ^0.1.0
|
||||
peerDependenciesMeta:
|
||||
encoding:
|
||||
optional: true
|
||||
dependencies:
|
||||
whatwg-url: 5.0.0
|
||||
dev: true
|
||||
|
||||
/node-fetch@2.7.0:
|
||||
resolution: {integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==}
|
||||
engines: {node: 4.x || >=6.0.0}
|
||||
@@ -4748,7 +4820,6 @@ packages:
|
||||
'@types/estree': 1.0.5
|
||||
estree-walker: 3.0.3
|
||||
is-reference: 3.0.2
|
||||
dev: true
|
||||
|
||||
/phin@2.9.3:
|
||||
resolution: {integrity: sha512-CzFr90qM24ju5f88quFC/6qohjC144rehe5n6DH900lgXmUe86+xCKc10ev56gRKC4/BkHUoG4uSiQgBiIXwDA==}
|
||||
@@ -5182,8 +5253,8 @@ packages:
|
||||
rimraf: 2.7.1
|
||||
dev: true
|
||||
|
||||
/sass@1.69.5:
|
||||
resolution: {integrity: sha512-qg2+UCJibLr2LCVOt3OlPhr/dqVHWOa9XtZf2OjbLs/T4VPSJ00udtgJxH3neXZm+QqX8B+3cU7RaLqp1iVfcQ==}
|
||||
/sass@1.69.7:
|
||||
resolution: {integrity: sha512-rzj2soDeZ8wtE2egyLXgOOHQvaC2iosZrkF6v3EUG+tBwEvhqUCzm0VP3k9gHF9LXbSrRhT5SksoI56Iw8NPnQ==}
|
||||
engines: {node: '>=14.0.0'}
|
||||
hasBin: true
|
||||
dependencies:
|
||||
@@ -5413,7 +5484,6 @@ packages:
|
||||
/source-map-js@1.0.2:
|
||||
resolution: {integrity: sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw==}
|
||||
engines: {node: '>=0.10.0'}
|
||||
dev: true
|
||||
|
||||
/source-map-resolve@0.5.3:
|
||||
resolution: {integrity: sha512-Htz+RnsXWk5+P2slx5Jh3Q66vhQj1Cllm0zvnaY98+NFx+Dv2CF/f5O/t8x+KaNdrdIAsruNzoh/KpialbqAnw==}
|
||||
@@ -5582,7 +5652,7 @@ packages:
|
||||
engines: {node: '>= 0.4'}
|
||||
dev: true
|
||||
|
||||
/svelte-check@3.6.0(postcss@8.4.31)(sass@1.69.5)(svelte@4.2.7):
|
||||
/svelte-check@3.6.0(postcss@8.4.31)(sass@1.69.7)(svelte@4.2.7):
|
||||
resolution: {integrity: sha512-8VfqhfuRJ1sKW+o8isH2kPi0RhjXH1nNsIbCFGyoUHG+ZxVxHYRKcb+S8eaL/1tyj3VGvWYx3Y5+oCUsJgnzcw==}
|
||||
hasBin: true
|
||||
peerDependencies:
|
||||
@@ -5595,7 +5665,7 @@ packages:
|
||||
picocolors: 1.0.0
|
||||
sade: 1.8.1
|
||||
svelte: 4.2.7
|
||||
svelte-preprocess: 5.1.0(postcss@8.4.31)(sass@1.69.5)(svelte@4.2.7)(typescript@5.3.2)
|
||||
svelte-preprocess: 5.1.0(postcss@8.4.31)(sass@1.69.7)(svelte@4.2.7)(typescript@5.3.2)
|
||||
typescript: 5.3.2
|
||||
transitivePeerDependencies:
|
||||
- '@babel/core'
|
||||
@@ -5649,6 +5719,16 @@ packages:
|
||||
- react
|
||||
dev: true
|
||||
|
||||
/svelte-markdown@0.4.1(svelte@4.2.7):
|
||||
resolution: {integrity: sha512-pOlLY6EruKJaWI9my/2bKX8PdTeP5CM0s4VMmwmC2prlOkjAf+AOmTM4wW/l19Y6WZ87YmP8+ZCJCCwBChWjYw==}
|
||||
peerDependencies:
|
||||
svelte: ^4.0.0
|
||||
dependencies:
|
||||
'@types/marked': 5.0.2
|
||||
marked: 5.1.2
|
||||
svelte: 4.2.7
|
||||
dev: false
|
||||
|
||||
/svelte-parse-markup@0.1.2(svelte@4.2.7):
|
||||
resolution: {integrity: sha512-DycY7DJr7VqofiJ63ut1/NEG92HrWWL56VWITn/cJCu+LlZhMoBkBXT4opUitPEEwbq1nMQbv4vTKUfbOqIW1g==}
|
||||
peerDependencies:
|
||||
@@ -5657,7 +5737,7 @@ packages:
|
||||
svelte: 4.2.7
|
||||
dev: true
|
||||
|
||||
/svelte-preprocess@5.1.0(postcss@8.4.31)(sass@1.69.5)(svelte@4.2.7)(typescript@5.3.2):
|
||||
/svelte-preprocess@5.1.0(postcss@8.4.31)(sass@1.69.7)(svelte@4.2.7)(typescript@5.3.2):
|
||||
resolution: {integrity: sha512-EkErPiDzHAc0k2MF5m6vBNmRUh338h2myhinUw/xaqsLs7/ZvsgREiLGj03VrSzbY/TB5ZXgBOsKraFee5yceA==}
|
||||
engines: {node: '>= 14.10.0'}
|
||||
requiresBuild: true
|
||||
@@ -5699,7 +5779,7 @@ packages:
|
||||
detect-indent: 6.1.0
|
||||
magic-string: 0.27.0
|
||||
postcss: 8.4.31
|
||||
sass: 1.69.5
|
||||
sass: 1.69.7
|
||||
sorcery: 0.11.0
|
||||
strip-indent: 3.0.0
|
||||
svelte: 4.2.7
|
||||
@@ -5731,6 +5811,15 @@ packages:
|
||||
locate-character: 3.0.0
|
||||
magic-string: 0.30.5
|
||||
periscopic: 3.1.0
|
||||
|
||||
/sveltekit-search-params@1.1.1(@sveltejs/kit@1.30.3)(svelte@4.2.7):
|
||||
resolution: {integrity: sha512-TVmCa50Cnyryt8UPeFZAE8gMsO80h2kXr531Um0VJaMKK24ZvdR4qbHWyLew9U4d5Flw1w3SbyHWTbLiUGPC7w==}
|
||||
peerDependencies:
|
||||
'@sveltejs/kit': ^1.0.0 || ^2.0.0
|
||||
svelte: ^3.55.0 || ^4.0.0 || ^5.0.0
|
||||
dependencies:
|
||||
'@sveltejs/kit': 1.30.3(svelte@4.2.7)(vite@4.5.1)
|
||||
svelte: 4.2.7
|
||||
dev: true
|
||||
|
||||
/svg-pathdata@6.0.3:
|
||||
@@ -5977,7 +6066,6 @@ packages:
|
||||
|
||||
/tr46@0.0.3:
|
||||
resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==}
|
||||
dev: false
|
||||
|
||||
/ts-interface-checker@0.1.13:
|
||||
resolution: {integrity: sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==}
|
||||
@@ -6177,7 +6265,7 @@ packages:
|
||||
- rollup
|
||||
dev: true
|
||||
|
||||
/vite-node@0.32.4(@types/node@20.9.3)(sass@1.69.5):
|
||||
/vite-node@0.32.4(@types/node@20.9.3)(sass@1.69.7):
|
||||
resolution: {integrity: sha512-L2gIw+dCxO0LK14QnUMoqSYpa9XRGnTTTDjW2h19Mr+GR0EFj4vx52W41gFXfMLqpA00eK4ZjOVYo1Xk//LFEw==}
|
||||
engines: {node: '>=v14.18.0'}
|
||||
hasBin: true
|
||||
@@ -6187,7 +6275,7 @@ packages:
|
||||
mlly: 1.4.2
|
||||
pathe: 1.1.1
|
||||
picocolors: 1.0.0
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
transitivePeerDependencies:
|
||||
- '@types/node'
|
||||
- less
|
||||
@@ -6216,10 +6304,10 @@ packages:
|
||||
dependencies:
|
||||
ansi-colors: 4.1.3
|
||||
pathe: 1.1.1
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
dev: true
|
||||
|
||||
/vite@4.5.1(@types/node@20.9.3)(sass@1.69.5):
|
||||
/vite@4.5.1(@types/node@20.9.3)(sass@1.69.7):
|
||||
resolution: {integrity: sha512-AXXFaAJ8yebyqzoNB9fu2pHoo/nWX+xZlaRwoeYUxEqBO+Zj4msE5G+BhGBll9lYEKv9Hfks52PAF2X7qDYXQA==}
|
||||
engines: {node: ^14.18.0 || >=16.0.0}
|
||||
hasBin: true
|
||||
@@ -6251,7 +6339,7 @@ packages:
|
||||
esbuild: 0.18.20
|
||||
postcss: 8.4.31
|
||||
rollup: 3.29.4
|
||||
sass: 1.69.5
|
||||
sass: 1.69.7
|
||||
optionalDependencies:
|
||||
fsevents: 2.3.3
|
||||
dev: true
|
||||
@@ -6264,10 +6352,10 @@ packages:
|
||||
vite:
|
||||
optional: true
|
||||
dependencies:
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
dev: true
|
||||
|
||||
/vitest@0.32.4(sass@1.69.5):
|
||||
/vitest@0.32.4(sass@1.69.7):
|
||||
resolution: {integrity: sha512-3czFm8RnrsWwIzVDu/Ca48Y/M+qh3vOnF16czJm98Q/AN1y3B6PBsyV8Re91Ty5s7txKNjEhpgtGPcfdbh2MZg==}
|
||||
engines: {node: '>=v14.18.0'}
|
||||
hasBin: true
|
||||
@@ -6319,8 +6407,8 @@ packages:
|
||||
strip-literal: 1.3.0
|
||||
tinybench: 2.5.1
|
||||
tinypool: 0.5.0
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite-node: 0.32.4(@types/node@20.9.3)(sass@1.69.5)
|
||||
vite: 4.5.1(@types/node@20.9.3)(sass@1.69.7)
|
||||
vite-node: 0.32.4(@types/node@20.9.3)(sass@1.69.7)
|
||||
why-is-node-running: 2.2.2
|
||||
transitivePeerDependencies:
|
||||
- less
|
||||
@@ -6334,14 +6422,12 @@ packages:
|
||||
|
||||
/webidl-conversions@3.0.1:
|
||||
resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==}
|
||||
dev: false
|
||||
|
||||
/whatwg-url@5.0.0:
|
||||
resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==}
|
||||
dependencies:
|
||||
tr46: 0.0.3
|
||||
webidl-conversions: 3.0.1
|
||||
dev: false
|
||||
|
||||
/which@2.0.2:
|
||||
resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==}
|
||||
|
||||
@@ -642,7 +642,7 @@
|
||||
{
|
||||
"link": "/docs/models/runtime",
|
||||
"redirect": "/docs/references/cloud/models/runtime"
|
||||
},
|
||||
},
|
||||
{
|
||||
"link": "/docs/installation",
|
||||
"redirect": "/docs/advanced/self-hosting"
|
||||
@@ -659,5 +659,4 @@
|
||||
"link": "/policy/privacy",
|
||||
"redirect": "/privacy"
|
||||
}
|
||||
|
||||
]
|
||||
|
||||
1
src/icons/optimized/ext-link.svg
Normal file
@@ -0,0 +1 @@
|
||||
<svg width="20" height="20" viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M9.814 6.600 L 6.578 6.617 6.460 6.706 C 6.133 6.956,6.164 7.490,6.517 7.690 L 6.650 7.766 9.175 7.766 C 10.564 7.766,11.700 7.778,11.700 7.791 C 11.700 7.805,10.486 9.031,9.002 10.516 C 7.492 12.027,6.288 13.258,6.268 13.311 C 6.213 13.459,6.227 13.690,6.300 13.833 C 6.436 14.100,6.816 14.213,7.093 14.069 C 7.162 14.033,8.403 12.817,9.900 11.319 L 12.583 8.633 12.600 11.208 L 12.617 13.783 12.694 13.892 C 12.934 14.229,13.477 14.205,13.685 13.849 L 13.764 13.715 13.768 10.360 C 13.772 6.725,13.781 6.918,13.594 6.743 C 13.485 6.641,13.289 6.565,13.159 6.575 C 13.099 6.579,11.594 6.590,9.814 6.600 " stroke="none" fill-rule="evenodd" fill="black"></path></svg>
|
||||
|
After Width: | Height: | Size: 770 B |
1
src/icons/optimized/message.svg
Normal file
@@ -0,0 +1 @@
|
||||
<svg width="20" height="20" viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M3.750 3.463 C 3.591 3.536,3.520 3.610,3.451 3.775 C 3.406 3.883,3.400 4.410,3.400 8.263 C 3.400 11.267,3.411 12.658,3.435 12.723 C 3.479 12.839,3.618 12.988,3.750 13.061 C 3.837 13.109,4.005 13.118,5.025 13.127 L 6.200 13.137 6.200 14.620 C 6.200 15.878,6.208 16.121,6.251 16.225 C 6.320 16.390,6.391 16.464,6.550 16.537 C 6.717 16.614,6.881 16.615,7.040 16.541 C 7.108 16.509,8.023 15.733,9.073 14.817 L 10.983 13.150 13.567 13.133 C 15.892 13.118,16.160 13.111,16.250 13.061 C 16.382 12.988,16.521 12.839,16.565 12.723 C 16.589 12.658,16.600 11.266,16.599 8.256 C 16.599 4.084,16.596 3.877,16.537 3.750 C 16.464 3.591,16.390 3.520,16.225 3.451 C 16.116 3.406,15.416 3.400,9.993 3.401 C 4.136 3.401,3.878 3.404,3.750 3.463 M15.400 8.267 L 15.400 11.933 13.015 11.933 C 11.032 11.933,10.615 11.941,10.540 11.980 C 10.490 12.006,9.767 12.621,8.933 13.347 L 7.417 14.667 7.400 13.492 C 7.389 12.687,7.371 12.296,7.345 12.250 C 7.295 12.165,7.138 12.019,7.044 11.971 C 6.994 11.945,6.596 11.933,5.786 11.933 L 4.600 11.933 4.600 8.267 L 4.600 4.600 10.000 4.600 L 15.400 4.600 15.400 8.267 " stroke="none" fill-rule="evenodd" fill="black"></path></svg>
|
||||
|
After Width: | Height: | Size: 1.2 KiB |
@@ -17,26 +17,28 @@ $aw-icon-dark: "\ea10";
|
||||
$aw-icon-discord: "\ea11";
|
||||
$aw-icon-divider-vertical: "\ea12";
|
||||
$aw-icon-download: "\ea13";
|
||||
$aw-icon-github: "\ea14";
|
||||
$aw-icon-google: "\ea15";
|
||||
$aw-icon-hamburger-menu: "\ea16";
|
||||
$aw-icon-light: "\ea17";
|
||||
$aw-icon-linkedin: "\ea18";
|
||||
$aw-icon-location: "\ea19";
|
||||
$aw-icon-logout-left: "\ea1a";
|
||||
$aw-icon-logout-right: "\ea1b";
|
||||
$aw-icon-microsoft: "\ea1c";
|
||||
$aw-icon-minus: "\ea1d";
|
||||
$aw-icon-nuxt: "\ea1e";
|
||||
$aw-icon-platform: "\ea1f";
|
||||
$aw-icon-plus: "\ea20";
|
||||
$aw-icon-product-hunt: "\ea21";
|
||||
$aw-icon-refine: "\ea22";
|
||||
$aw-icon-rest: "\ea23";
|
||||
$aw-icon-search: "\ea24";
|
||||
$aw-icon-star: "\ea25";
|
||||
$aw-icon-system: "\ea26";
|
||||
$aw-icon-twitter: "\ea27";
|
||||
$aw-icon-vue: "\ea28";
|
||||
$aw-icon-x: "\ea29";
|
||||
$aw-icon-youtube: "\ea2a";
|
||||
$aw-icon-ext-link: "\ea14";
|
||||
$aw-icon-github: "\ea15";
|
||||
$aw-icon-google: "\ea16";
|
||||
$aw-icon-hamburger-menu: "\ea17";
|
||||
$aw-icon-light: "\ea18";
|
||||
$aw-icon-linkedin: "\ea19";
|
||||
$aw-icon-location: "\ea1a";
|
||||
$aw-icon-logout-left: "\ea1b";
|
||||
$aw-icon-logout-right: "\ea1c";
|
||||
$aw-icon-message: "\ea1d";
|
||||
$aw-icon-microsoft: "\ea1e";
|
||||
$aw-icon-minus: "\ea1f";
|
||||
$aw-icon-nuxt: "\ea20";
|
||||
$aw-icon-platform: "\ea21";
|
||||
$aw-icon-plus: "\ea22";
|
||||
$aw-icon-product-hunt: "\ea23";
|
||||
$aw-icon-refine: "\ea24";
|
||||
$aw-icon-rest: "\ea25";
|
||||
$aw-icon-search: "\ea26";
|
||||
$aw-icon-star: "\ea27";
|
||||
$aw-icon-system: "\ea28";
|
||||
$aw-icon-twitter: "\ea29";
|
||||
$aw-icon-vue: "\ea2a";
|
||||
$aw-icon-x: "\ea2b";
|
||||
$aw-icon-youtube: "\ea2c";
|
||||
|
||||
@@ -36,26 +36,28 @@
|
||||
.aw-icon-discord:before { content: "\ea11"; }
|
||||
.aw-icon-divider-vertical:before { content: "\ea12"; }
|
||||
.aw-icon-download:before { content: "\ea13"; }
|
||||
.aw-icon-github:before { content: "\ea14"; }
|
||||
.aw-icon-google:before { content: "\ea15"; }
|
||||
.aw-icon-hamburger-menu:before { content: "\ea16"; }
|
||||
.aw-icon-light:before { content: "\ea17"; }
|
||||
.aw-icon-linkedin:before { content: "\ea18"; }
|
||||
.aw-icon-location:before { content: "\ea19"; }
|
||||
.aw-icon-logout-left:before { content: "\ea1a"; }
|
||||
.aw-icon-logout-right:before { content: "\ea1b"; }
|
||||
.aw-icon-microsoft:before { content: "\ea1c"; }
|
||||
.aw-icon-minus:before { content: "\ea1d"; }
|
||||
.aw-icon-nuxt:before { content: "\ea1e"; }
|
||||
.aw-icon-platform:before { content: "\ea1f"; }
|
||||
.aw-icon-plus:before { content: "\ea20"; }
|
||||
.aw-icon-product-hunt:before { content: "\ea21"; }
|
||||
.aw-icon-refine:before { content: "\ea22"; }
|
||||
.aw-icon-rest:before { content: "\ea23"; }
|
||||
.aw-icon-search:before { content: "\ea24"; }
|
||||
.aw-icon-star:before { content: "\ea25"; }
|
||||
.aw-icon-system:before { content: "\ea26"; }
|
||||
.aw-icon-twitter:before { content: "\ea27"; }
|
||||
.aw-icon-vue:before { content: "\ea28"; }
|
||||
.aw-icon-x:before { content: "\ea29"; }
|
||||
.aw-icon-youtube:before { content: "\ea2a"; }
|
||||
.aw-icon-ext-link:before { content: "\ea14"; }
|
||||
.aw-icon-github:before { content: "\ea15"; }
|
||||
.aw-icon-google:before { content: "\ea16"; }
|
||||
.aw-icon-hamburger-menu:before { content: "\ea17"; }
|
||||
.aw-icon-light:before { content: "\ea18"; }
|
||||
.aw-icon-linkedin:before { content: "\ea19"; }
|
||||
.aw-icon-location:before { content: "\ea1a"; }
|
||||
.aw-icon-logout-left:before { content: "\ea1b"; }
|
||||
.aw-icon-logout-right:before { content: "\ea1c"; }
|
||||
.aw-icon-message:before { content: "\ea1d"; }
|
||||
.aw-icon-microsoft:before { content: "\ea1e"; }
|
||||
.aw-icon-minus:before { content: "\ea1f"; }
|
||||
.aw-icon-nuxt:before { content: "\ea20"; }
|
||||
.aw-icon-platform:before { content: "\ea21"; }
|
||||
.aw-icon-plus:before { content: "\ea22"; }
|
||||
.aw-icon-product-hunt:before { content: "\ea23"; }
|
||||
.aw-icon-refine:before { content: "\ea24"; }
|
||||
.aw-icon-rest:before { content: "\ea25"; }
|
||||
.aw-icon-search:before { content: "\ea26"; }
|
||||
.aw-icon-star:before { content: "\ea27"; }
|
||||
.aw-icon-system:before { content: "\ea28"; }
|
||||
.aw-icon-twitter:before { content: "\ea29"; }
|
||||
.aw-icon-vue:before { content: "\ea2a"; }
|
||||
.aw-icon-x:before { content: "\ea2b"; }
|
||||
.aw-icon-youtube:before { content: "\ea2c"; }
|
||||
|
||||
@@ -35,29 +35,31 @@
|
||||
.aw-icon-discord:before { content: "\ea11"; }
|
||||
.aw-icon-divider-vertical:before { content: "\ea12"; }
|
||||
.aw-icon-download:before { content: "\ea13"; }
|
||||
.aw-icon-github:before { content: "\ea14"; }
|
||||
.aw-icon-google:before { content: "\ea15"; }
|
||||
.aw-icon-hamburger-menu:before { content: "\ea16"; }
|
||||
.aw-icon-light:before { content: "\ea17"; }
|
||||
.aw-icon-linkedin:before { content: "\ea18"; }
|
||||
.aw-icon-location:before { content: "\ea19"; }
|
||||
.aw-icon-logout-left:before { content: "\ea1a"; }
|
||||
.aw-icon-logout-right:before { content: "\ea1b"; }
|
||||
.aw-icon-microsoft:before { content: "\ea1c"; }
|
||||
.aw-icon-minus:before { content: "\ea1d"; }
|
||||
.aw-icon-nuxt:before { content: "\ea1e"; }
|
||||
.aw-icon-platform:before { content: "\ea1f"; }
|
||||
.aw-icon-plus:before { content: "\ea20"; }
|
||||
.aw-icon-product-hunt:before { content: "\ea21"; }
|
||||
.aw-icon-refine:before { content: "\ea22"; }
|
||||
.aw-icon-rest:before { content: "\ea23"; }
|
||||
.aw-icon-search:before { content: "\ea24"; }
|
||||
.aw-icon-star:before { content: "\ea25"; }
|
||||
.aw-icon-system:before { content: "\ea26"; }
|
||||
.aw-icon-twitter:before { content: "\ea27"; }
|
||||
.aw-icon-vue:before { content: "\ea28"; }
|
||||
.aw-icon-x:before { content: "\ea29"; }
|
||||
.aw-icon-youtube:before { content: "\ea2a"; }
|
||||
.aw-icon-ext-link:before { content: "\ea14"; }
|
||||
.aw-icon-github:before { content: "\ea15"; }
|
||||
.aw-icon-google:before { content: "\ea16"; }
|
||||
.aw-icon-hamburger-menu:before { content: "\ea17"; }
|
||||
.aw-icon-light:before { content: "\ea18"; }
|
||||
.aw-icon-linkedin:before { content: "\ea19"; }
|
||||
.aw-icon-location:before { content: "\ea1a"; }
|
||||
.aw-icon-logout-left:before { content: "\ea1b"; }
|
||||
.aw-icon-logout-right:before { content: "\ea1c"; }
|
||||
.aw-icon-message:before { content: "\ea1d"; }
|
||||
.aw-icon-microsoft:before { content: "\ea1e"; }
|
||||
.aw-icon-minus:before { content: "\ea1f"; }
|
||||
.aw-icon-nuxt:before { content: "\ea20"; }
|
||||
.aw-icon-platform:before { content: "\ea21"; }
|
||||
.aw-icon-plus:before { content: "\ea22"; }
|
||||
.aw-icon-product-hunt:before { content: "\ea23"; }
|
||||
.aw-icon-refine:before { content: "\ea24"; }
|
||||
.aw-icon-rest:before { content: "\ea25"; }
|
||||
.aw-icon-search:before { content: "\ea26"; }
|
||||
.aw-icon-star:before { content: "\ea27"; }
|
||||
.aw-icon-system:before { content: "\ea28"; }
|
||||
.aw-icon-twitter:before { content: "\ea29"; }
|
||||
.aw-icon-vue:before { content: "\ea2a"; }
|
||||
.aw-icon-x:before { content: "\ea2b"; }
|
||||
.aw-icon-youtube:before { content: "\ea2c"; }
|
||||
|
||||
$aw-icon-apple: "\ea01";
|
||||
$aw-icon-arrow-down: "\ea02";
|
||||
@@ -78,26 +80,28 @@ $aw-icon-dark: "\ea10";
|
||||
$aw-icon-discord: "\ea11";
|
||||
$aw-icon-divider-vertical: "\ea12";
|
||||
$aw-icon-download: "\ea13";
|
||||
$aw-icon-github: "\ea14";
|
||||
$aw-icon-google: "\ea15";
|
||||
$aw-icon-hamburger-menu: "\ea16";
|
||||
$aw-icon-light: "\ea17";
|
||||
$aw-icon-linkedin: "\ea18";
|
||||
$aw-icon-location: "\ea19";
|
||||
$aw-icon-logout-left: "\ea1a";
|
||||
$aw-icon-logout-right: "\ea1b";
|
||||
$aw-icon-microsoft: "\ea1c";
|
||||
$aw-icon-minus: "\ea1d";
|
||||
$aw-icon-nuxt: "\ea1e";
|
||||
$aw-icon-platform: "\ea1f";
|
||||
$aw-icon-plus: "\ea20";
|
||||
$aw-icon-product-hunt: "\ea21";
|
||||
$aw-icon-refine: "\ea22";
|
||||
$aw-icon-rest: "\ea23";
|
||||
$aw-icon-search: "\ea24";
|
||||
$aw-icon-star: "\ea25";
|
||||
$aw-icon-system: "\ea26";
|
||||
$aw-icon-twitter: "\ea27";
|
||||
$aw-icon-vue: "\ea28";
|
||||
$aw-icon-x: "\ea29";
|
||||
$aw-icon-youtube: "\ea2a";
|
||||
$aw-icon-ext-link: "\ea14";
|
||||
$aw-icon-github: "\ea15";
|
||||
$aw-icon-google: "\ea16";
|
||||
$aw-icon-hamburger-menu: "\ea17";
|
||||
$aw-icon-light: "\ea18";
|
||||
$aw-icon-linkedin: "\ea19";
|
||||
$aw-icon-location: "\ea1a";
|
||||
$aw-icon-logout-left: "\ea1b";
|
||||
$aw-icon-logout-right: "\ea1c";
|
||||
$aw-icon-message: "\ea1d";
|
||||
$aw-icon-microsoft: "\ea1e";
|
||||
$aw-icon-minus: "\ea1f";
|
||||
$aw-icon-nuxt: "\ea20";
|
||||
$aw-icon-platform: "\ea21";
|
||||
$aw-icon-plus: "\ea22";
|
||||
$aw-icon-product-hunt: "\ea23";
|
||||
$aw-icon-refine: "\ea24";
|
||||
$aw-icon-rest: "\ea25";
|
||||
$aw-icon-search: "\ea26";
|
||||
$aw-icon-star: "\ea27";
|
||||
$aw-icon-system: "\ea28";
|
||||
$aw-icon-twitter: "\ea29";
|
||||
$aw-icon-vue: "\ea2a";
|
||||
$aw-icon-x: "\ea2b";
|
||||
$aw-icon-youtube: "\ea2c";
|
||||
|
||||
|
Before Width: | Height: | Size: 139 KiB After Width: | Height: | Size: 144 KiB |
|
Before Width: | Height: | Size: 59 KiB After Width: | Height: | Size: 61 KiB |
@@ -113,142 +113,154 @@
|
||||
"className": "aw-icon-download",
|
||||
"unicode": ""
|
||||
},
|
||||
"github": {
|
||||
"ext-link": {
|
||||
"encodedCode": "\\ea14",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-github",
|
||||
"className": "aw-icon-ext-link",
|
||||
"unicode": ""
|
||||
},
|
||||
"google": {
|
||||
"github": {
|
||||
"encodedCode": "\\ea15",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-google",
|
||||
"className": "aw-icon-github",
|
||||
"unicode": ""
|
||||
},
|
||||
"hamburger-menu": {
|
||||
"google": {
|
||||
"encodedCode": "\\ea16",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-hamburger-menu",
|
||||
"className": "aw-icon-google",
|
||||
"unicode": ""
|
||||
},
|
||||
"light": {
|
||||
"hamburger-menu": {
|
||||
"encodedCode": "\\ea17",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-light",
|
||||
"className": "aw-icon-hamburger-menu",
|
||||
"unicode": ""
|
||||
},
|
||||
"linkedin": {
|
||||
"light": {
|
||||
"encodedCode": "\\ea18",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-linkedin",
|
||||
"className": "aw-icon-light",
|
||||
"unicode": ""
|
||||
},
|
||||
"location": {
|
||||
"linkedin": {
|
||||
"encodedCode": "\\ea19",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-location",
|
||||
"className": "aw-icon-linkedin",
|
||||
"unicode": ""
|
||||
},
|
||||
"logout-left": {
|
||||
"location": {
|
||||
"encodedCode": "\\ea1a",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-logout-left",
|
||||
"className": "aw-icon-location",
|
||||
"unicode": ""
|
||||
},
|
||||
"logout-right": {
|
||||
"logout-left": {
|
||||
"encodedCode": "\\ea1b",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-logout-right",
|
||||
"className": "aw-icon-logout-left",
|
||||
"unicode": ""
|
||||
},
|
||||
"microsoft": {
|
||||
"logout-right": {
|
||||
"encodedCode": "\\ea1c",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-microsoft",
|
||||
"className": "aw-icon-logout-right",
|
||||
"unicode": ""
|
||||
},
|
||||
"minus": {
|
||||
"message": {
|
||||
"encodedCode": "\\ea1d",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-minus",
|
||||
"className": "aw-icon-message",
|
||||
"unicode": ""
|
||||
},
|
||||
"nuxt": {
|
||||
"microsoft": {
|
||||
"encodedCode": "\\ea1e",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-nuxt",
|
||||
"className": "aw-icon-microsoft",
|
||||
"unicode": ""
|
||||
},
|
||||
"platform": {
|
||||
"minus": {
|
||||
"encodedCode": "\\ea1f",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-platform",
|
||||
"className": "aw-icon-minus",
|
||||
"unicode": ""
|
||||
},
|
||||
"plus": {
|
||||
"nuxt": {
|
||||
"encodedCode": "\\ea20",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-plus",
|
||||
"className": "aw-icon-nuxt",
|
||||
"unicode": ""
|
||||
},
|
||||
"product-hunt": {
|
||||
"platform": {
|
||||
"encodedCode": "\\ea21",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-product-hunt",
|
||||
"className": "aw-icon-platform",
|
||||
"unicode": ""
|
||||
},
|
||||
"refine": {
|
||||
"plus": {
|
||||
"encodedCode": "\\ea22",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-refine",
|
||||
"className": "aw-icon-plus",
|
||||
"unicode": ""
|
||||
},
|
||||
"rest": {
|
||||
"product-hunt": {
|
||||
"encodedCode": "\\ea23",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-rest",
|
||||
"className": "aw-icon-product-hunt",
|
||||
"unicode": ""
|
||||
},
|
||||
"search": {
|
||||
"refine": {
|
||||
"encodedCode": "\\ea24",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-search",
|
||||
"className": "aw-icon-refine",
|
||||
"unicode": ""
|
||||
},
|
||||
"star": {
|
||||
"rest": {
|
||||
"encodedCode": "\\ea25",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-star",
|
||||
"className": "aw-icon-rest",
|
||||
"unicode": ""
|
||||
},
|
||||
"system": {
|
||||
"search": {
|
||||
"encodedCode": "\\ea26",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-system",
|
||||
"className": "aw-icon-search",
|
||||
"unicode": ""
|
||||
},
|
||||
"twitter": {
|
||||
"star": {
|
||||
"encodedCode": "\\ea27",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-twitter",
|
||||
"className": "aw-icon-star",
|
||||
"unicode": ""
|
||||
},
|
||||
"vue": {
|
||||
"system": {
|
||||
"encodedCode": "\\ea28",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-vue",
|
||||
"className": "aw-icon-system",
|
||||
"unicode": ""
|
||||
},
|
||||
"x": {
|
||||
"twitter": {
|
||||
"encodedCode": "\\ea29",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-x",
|
||||
"className": "aw-icon-twitter",
|
||||
"unicode": ""
|
||||
},
|
||||
"youtube": {
|
||||
"vue": {
|
||||
"encodedCode": "\\ea2a",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-youtube",
|
||||
"className": "aw-icon-vue",
|
||||
"unicode": ""
|
||||
},
|
||||
"x": {
|
||||
"encodedCode": "\\ea2b",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-x",
|
||||
"unicode": ""
|
||||
},
|
||||
"youtube": {
|
||||
"encodedCode": "\\ea2c",
|
||||
"prefix": "aw-icon",
|
||||
"className": "aw-icon-youtube",
|
||||
"unicode": ""
|
||||
}
|
||||
}
|
||||
|
||||
5
src/icons/svg/ext-link.svg
Normal file
@@ -0,0 +1,5 @@
|
||||
<svg width="20" height="20" viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M6.81802 13.5459L13.182 7.18197" stroke="#19191C" stroke-width="1.2" stroke-linecap="round"/>
|
||||
<path d="M6.81802 7.18198H13.182" stroke="#19191C" stroke-width="1.2" stroke-linecap="round"/>
|
||||
<path d="M13.182 13.5459V7.18197" stroke="#19191C" stroke-width="1.2" stroke-linecap="round"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 396 B |
3
src/icons/svg/message.svg
Normal file
@@ -0,0 +1,3 @@
|
||||
<svg width="20" height="20" viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M4 12.5161V4H16V12.5161H10.8L6.8 16V12.5161H4Z" stroke="black" stroke-width="1.2" stroke-linejoin="round" />
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 222 B |
6
src/lib/actions/highlight.ts
Normal file
@@ -0,0 +1,6 @@
|
||||
export const highlight = (node: HTMLElement, text: string[]) => {
|
||||
text.forEach((word) => {
|
||||
const regex = new RegExp(`(${word})`, 'gi');
|
||||
node.innerHTML = node.innerHTML.replace(regex, '<mark>$1</mark>');
|
||||
});
|
||||
};
|
||||
9
src/lib/appwrite/index.ts
Normal file
@@ -0,0 +1,9 @@
|
||||
import { PUBLIC_APPWRITE_PROJECT_ID } from '$env/static/public';
|
||||
import { Client, Databases, Functions } from 'appwrite';
|
||||
|
||||
export const client = new Client();
|
||||
|
||||
client.setEndpoint('https://cloud.appwrite.io/v1').setProject(PUBLIC_APPWRITE_PROJECT_ID);
|
||||
|
||||
export const databases = new Databases(client);
|
||||
export const functions = new Functions(client);
|
||||
24
src/lib/components/DropdownMenu/DropdownCheckboxItem.svelte
Normal file
@@ -0,0 +1,24 @@
|
||||
<script lang="ts">
|
||||
import { DropdownCtx } from './DropdownMenu.svelte';
|
||||
|
||||
export let checked = false;
|
||||
|
||||
const {
|
||||
builders: { createCheckboxItem }
|
||||
} = DropdownCtx.get();
|
||||
|
||||
const {
|
||||
elements: { checkboxItem },
|
||||
states: { checked: localChecked }
|
||||
} = createCheckboxItem({
|
||||
defaultChecked: checked,
|
||||
onCheckedChange({ next }) {
|
||||
checked = !!next;
|
||||
return next;
|
||||
}
|
||||
});
|
||||
|
||||
$: localChecked.set(checked);
|
||||
</script>
|
||||
|
||||
<slot checkboxItem={$checkboxItem} />
|
||||
33
src/lib/components/DropdownMenu/DropdownMenu.svelte
Normal file
@@ -0,0 +1,33 @@
|
||||
<script lang="ts" context="module">
|
||||
const ctxKey = Symbol('dropdown');
|
||||
|
||||
export const DropdownCtx = {
|
||||
get() {
|
||||
return getContext<DropdownMenu>(ctxKey);
|
||||
},
|
||||
set(ctx: DropdownMenu) {
|
||||
setContext(ctxKey, ctx);
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<script lang="ts">
|
||||
import { createDropdownMenu, type DropdownMenu } from '@melt-ui/svelte';
|
||||
import { getContext, setContext } from 'svelte';
|
||||
|
||||
const dropdown = createDropdownMenu({
|
||||
forceVisible: true,
|
||||
positioning: {
|
||||
placement: 'bottom-start'
|
||||
}
|
||||
});
|
||||
|
||||
DropdownCtx.set(dropdown);
|
||||
|
||||
const {
|
||||
elements: { menu, trigger },
|
||||
states: { open }
|
||||
} = dropdown;
|
||||
</script>
|
||||
|
||||
<slot menu={$menu} trigger={$trigger} open={$open} />
|
||||
@@ -31,11 +31,12 @@
|
||||
{ label: 'Databases', href: '/docs/products/databases' },
|
||||
{ label: 'Functions', href: '/docs/products/functions' },
|
||||
{ label: 'Storage', href: '/docs/products/storage' },
|
||||
{ label: 'Realtime', href: '/docs/apis/realtime' }
|
||||
{ label: 'Realtime', href: '/docs/apis/realtime' },
|
||||
],
|
||||
Learn: [
|
||||
{ label: 'Docs', href: '/docs' },
|
||||
{ label: 'Community', href: '/community' },
|
||||
{ label: 'Threads', href: '/threads' },
|
||||
{ label: 'Blog', href: '/blog' },
|
||||
{ label: 'Changelog', href: '/changelog' },
|
||||
{
|
||||
|
||||
@@ -66,3 +66,9 @@
|
||||
</div>
|
||||
</footer>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
.aw-icon-button {
|
||||
display: grid;
|
||||
}
|
||||
</style>
|
||||
13
src/lib/components/SeoOgImage.svelte
Normal file
@@ -0,0 +1,13 @@
|
||||
<script lang="ts">
|
||||
import { buildOpenGraphImage } from '$lib/utils/metadata';
|
||||
|
||||
export let title: string;
|
||||
export let description: string;
|
||||
const ogImage = buildOpenGraphImage(title, description);
|
||||
</script>
|
||||
|
||||
<meta property="og:image" content={ogImage} />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
<meta name="twitter:image" content={ogImage} />
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
14
src/lib/utils/debounce.ts
Normal file
@@ -0,0 +1,14 @@
|
||||
export function createDebounce(delay = 500) {
|
||||
let timeout: NodeJS.Timeout;
|
||||
return {
|
||||
debounce: (callback: () => void) => {
|
||||
clearTimeout(timeout);
|
||||
timeout = setTimeout(callback, delay);
|
||||
},
|
||||
reset: () => clearTimeout(timeout),
|
||||
immediate: (callback: () => void) => {
|
||||
clearTimeout(timeout);
|
||||
callback();
|
||||
}
|
||||
};
|
||||
}
|
||||
9
src/lib/utils/random.ts
Normal file
@@ -0,0 +1,9 @@
|
||||
export const deterministicRandom = <T>(options: T[], seed: string): T => {
|
||||
const index = Math.floor((parseInt(seed, 36) / 36 ** 4) * options.length);
|
||||
|
||||
return options[index];
|
||||
};
|
||||
|
||||
export const random = (min: number, max: number): number => {
|
||||
return Math.floor(Math.random() * (max - min + 1) + min);
|
||||
};
|
||||
@@ -15,9 +15,9 @@
|
||||
|
||||
<script lang="ts">
|
||||
import { MainFooter } from '$lib/components';
|
||||
import SeoOgImage from '$lib/components/SeoOgImage.svelte';
|
||||
import { DocsArticle } from '$lib/layouts';
|
||||
import type { TocItem } from '$lib/layouts/DocsArticle.svelte';
|
||||
import { buildOpenGraphImage } from '$lib/utils/metadata';
|
||||
import { DOCS_TITLE_SUFFIX } from '$routes/titles';
|
||||
import { getContext, setContext } from 'svelte';
|
||||
|
||||
@@ -58,7 +58,6 @@
|
||||
}, []);
|
||||
|
||||
const seoTitle = title + DOCS_TITLE_SUFFIX;
|
||||
const ogImage = buildOpenGraphImage(title, description);
|
||||
</script>
|
||||
|
||||
<svelte:head>
|
||||
@@ -70,12 +69,7 @@
|
||||
<meta name="description" content={description} />
|
||||
<meta property="og:description" content={description} />
|
||||
<meta name="twitter:description" content={description} />
|
||||
<!-- Image -->
|
||||
<meta property="og:image" content={ogImage} />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
<meta name="twitter:image" content={ogImage} />
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<SeoOgImage {title} {description} />
|
||||
</svelte:head>
|
||||
|
||||
<DocsArticle {title} {back} {toc} {date}>
|
||||
|
||||
@@ -1,89 +1,89 @@
|
||||
<script lang="ts">
|
||||
import { Article, FooterNav, MainFooter } from '$lib/components';
|
||||
import { page } from '$app/stores';
|
||||
import { Main } from '$lib/layouts';
|
||||
import { getContext } from 'svelte';
|
||||
import type { PostsData, AuthorData } from '$routes/blog/content';
|
||||
import { BLOG_TITLE_SUFFIX } from '$routes/titles';
|
||||
import { DEFAULT_HOST } from '$lib/utils/metadata';
|
||||
import { page } from '$app/stores';
|
||||
import { Article, FooterNav, MainFooter } from '$lib/components';
|
||||
import { Main } from '$lib/layouts';
|
||||
import { DEFAULT_HOST } from '$lib/utils/metadata';
|
||||
import type { AuthorData, PostsData } from '$routes/blog/content';
|
||||
import { BLOG_TITLE_SUFFIX } from '$routes/titles';
|
||||
import { getContext } from 'svelte';
|
||||
|
||||
export let name: string;
|
||||
export let description: string;
|
||||
export let name: string;
|
||||
export let description: string;
|
||||
|
||||
const pageSlug = $page.url.pathname.substring($page.url.pathname.lastIndexOf('/') + 1);
|
||||
const authors = getContext<AuthorData[]>('authors');
|
||||
const postsList = getContext<PostsData[]>('posts');
|
||||
const posts = postsList.filter((post) => post.category.includes(pageSlug));
|
||||
const pageSlug = $page.url.pathname.substring($page.url.pathname.lastIndexOf('/') + 1);
|
||||
const authors = getContext<AuthorData[]>('authors');
|
||||
const postsList = getContext<PostsData[]>('posts');
|
||||
const posts = postsList.filter((post) => post.category.includes(pageSlug));
|
||||
|
||||
const seoTitle = name + BLOG_TITLE_SUFFIX;
|
||||
const ogImage = DEFAULT_HOST + '/images/open-graph/blog.png';
|
||||
const seoTitle = name + BLOG_TITLE_SUFFIX;
|
||||
const ogImage = DEFAULT_HOST + '/images/open-graph/blog.png';
|
||||
</script>
|
||||
|
||||
<svelte:head>
|
||||
<!-- Titles -->
|
||||
<title>{seoTitle}</title>
|
||||
<meta property="og:title" content={seoTitle} />
|
||||
<meta name="twitter:title" content={seoTitle} />
|
||||
<!-- Desscription -->
|
||||
<meta name="description" content={description} />
|
||||
<meta property="og:description" content={description} />
|
||||
<meta name="twitter:description" content={description} />
|
||||
<!-- Image -->
|
||||
<meta property="og:image" content={ogImage} />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
<meta name="twitter:image" content={ogImage} />
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<!-- Titles -->
|
||||
<title>{seoTitle}</title>
|
||||
<meta property="og:title" content={seoTitle} />
|
||||
<meta name="twitter:title" content={seoTitle} />
|
||||
<!-- Desscription -->
|
||||
<meta name="description" content={description} />
|
||||
<meta property="og:description" content={description} />
|
||||
<meta name="twitter:description" content={description} />
|
||||
<!-- Image -->
|
||||
<meta property="og:image" content={ogImage} />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
<meta name="twitter:image" content={ogImage} />
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
</svelte:head>
|
||||
|
||||
<Main>
|
||||
<div class="aw-big-padding-section-level-1">
|
||||
<div class="aw-big-padding-section-level-2">
|
||||
<div class="aw-container">
|
||||
<a class="aw-link aw-u-color-text-secondary u-cross-baseline" href="/blog">
|
||||
<span class="aw-icon-chevron-left" aria-hidden="true" />
|
||||
<span>Back to blog</span>
|
||||
</a>
|
||||
<div class="aw-category-header u-margin-block-start-24">
|
||||
<div class="aw-category-header-content">
|
||||
<h1 class="aw-display aw-u-color-text-primary">{name}</h1>
|
||||
<p class="aw-category-header-description aw-description">
|
||||
{description}
|
||||
</p>
|
||||
</div>
|
||||
<!-- <div class="aw-input-text-search-wrapper u-inline-width-100-percent-mobile">
|
||||
<div class="aw-big-padding-section-level-1">
|
||||
<div class="aw-big-padding-section-level-2">
|
||||
<div class="aw-container">
|
||||
<a class="aw-link aw-u-color-text-secondary u-cross-baseline" href="/blog">
|
||||
<span class="aw-icon-chevron-left" aria-hidden="true" />
|
||||
<span>Back to blog</span>
|
||||
</a>
|
||||
<div class="aw-category-header u-margin-block-start-24">
|
||||
<div class="aw-category-header-content">
|
||||
<h1 class="aw-display aw-u-color-text-primary">{name}</h1>
|
||||
<p class="aw-category-header-description aw-description">
|
||||
{description}
|
||||
</p>
|
||||
</div>
|
||||
<!-- <div class="aw-input-text-search-wrapper u-inline-width-100-percent-mobile">
|
||||
<span class="icon-search" aria-hidden="true" />
|
||||
<input class="aw-input-text aw-u-block-size-48" type="search" placeholder="Search" />
|
||||
</div> -->
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="u-margin-block-start-48">
|
||||
<ul class="aw-grid-articles">
|
||||
{#each posts as post}
|
||||
{@const author = authors.find((a) => a.slug.includes(post.author))}
|
||||
{#if author}
|
||||
<Article
|
||||
title={post.title}
|
||||
href={post.href}
|
||||
cover={post.cover}
|
||||
date={post.date}
|
||||
timeToRead={post.timeToRead}
|
||||
avatar={author.avatar}
|
||||
author={author.name}
|
||||
/>
|
||||
{/if}
|
||||
{/each}
|
||||
</ul>
|
||||
</div>
|
||||
<div
|
||||
class="aw-big-padding-section-level-2 is-margin-replace-padding u-position-relative u-overflow-hidden"
|
||||
>
|
||||
<div class="aw-container">
|
||||
<FooterNav />
|
||||
<MainFooter />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div></Main
|
||||
<div class="u-margin-block-start-48">
|
||||
<ul class="aw-grid-articles">
|
||||
{#each posts as post}
|
||||
{@const author = authors.find((a) => a.slug.includes(post.author))}
|
||||
{#if author}
|
||||
<Article
|
||||
title={post.title}
|
||||
href={post.href}
|
||||
cover={post.cover}
|
||||
date={post.date}
|
||||
timeToRead={post.timeToRead}
|
||||
avatar={author.avatar}
|
||||
author={author.name}
|
||||
/>
|
||||
{/if}
|
||||
{/each}
|
||||
</ul>
|
||||
</div>
|
||||
<div
|
||||
class="aw-big-padding-section-level-2 is-margin-replace-padding u-position-relative u-overflow-hidden"
|
||||
>
|
||||
<div class="aw-container">
|
||||
<FooterNav />
|
||||
<MainFooter />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div></Main
|
||||
>
|
||||
|
||||
@@ -66,7 +66,7 @@
|
||||
<article class="aw-main-article">
|
||||
<header class="aw-main-article-header">
|
||||
<a
|
||||
class="aw-link aw-u-color-text-secondary u-cross-baseline"
|
||||
class="aw-link is-secondary aw-u-color-text-secondary u-cross-baseline"
|
||||
href="/blog"
|
||||
>
|
||||
<span class="aw-icon-chevron-left" aria-hidden="true" />
|
||||
|
||||
@@ -471,22 +471,10 @@
|
||||
.footer-wrapper {
|
||||
overflow: hidden;
|
||||
|
||||
> img {
|
||||
top: -100px;
|
||||
inline-size: 1700px;
|
||||
max-inline-size: none;
|
||||
max-block-size: none;
|
||||
}
|
||||
|
||||
@media (max-width: 1024px) {
|
||||
.aw-hero {
|
||||
padding-block-start: 5rem;
|
||||
}
|
||||
|
||||
> img {
|
||||
top: -300px;
|
||||
left: -400px;
|
||||
}
|
||||
}
|
||||
|
||||
.aw-hero {
|
||||
|
||||
18
src/routes/threads/(assets)/bg-green.svg
Normal file
@@ -0,0 +1,18 @@
|
||||
<svg width="1000" height="1201" viewBox="0 0 1000 1201" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<g opacity="0.4" filter="url(#filter0_f_173_392)">
|
||||
<ellipse cx="500" cy="600.5" rx="200" ry="300.5" fill="url(#paint0_radial_173_392)" />
|
||||
</g>
|
||||
<defs>
|
||||
<filter id="filter0_f_173_392" x="0" y="0" width="1000" height="1201" filterUnits="userSpaceOnUse"
|
||||
color-interpolation-filters="sRGB">
|
||||
<feFlood flood-opacity="0" result="BackgroundImageFix" />
|
||||
<feBlend mode="normal" in="SourceGraphic" in2="BackgroundImageFix" result="shape" />
|
||||
<feGaussianBlur stdDeviation="150" result="effect1_foregroundBlur_173_392" />
|
||||
</filter>
|
||||
<radialGradient id="paint0_radial_173_392" cx="0" cy="0" r="1" gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="translate(488.004 604.652) rotate(86.015) scale(260.897 198.704)">
|
||||
<stop stop-color="#E7F8F7" />
|
||||
<stop offset="1" stop-color="#85DBD8" />
|
||||
</radialGradient>
|
||||
</defs>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 973 B |
18
src/routes/threads/(assets)/bg-red.svg
Normal file
@@ -0,0 +1,18 @@
|
||||
<svg width="1325" height="1219" viewBox="0 0 1325 1219" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<g opacity="0.4" filter="url(#filter0_f_175_393)">
|
||||
<ellipse cx="662.5" cy="609.5" rx="362.5" ry="309.5" fill="url(#paint0_radial_175_393)" />
|
||||
</g>
|
||||
<defs>
|
||||
<filter id="filter0_f_175_393" x="0" y="0" width="1325" height="1219" filterUnits="userSpaceOnUse"
|
||||
color-interpolation-filters="sRGB">
|
||||
<feFlood flood-opacity="0" result="BackgroundImageFix" />
|
||||
<feBlend mode="normal" in="SourceGraphic" in2="BackgroundImageFix" result="shape" />
|
||||
<feGaussianBlur stdDeviation="150" result="effect1_foregroundBlur_175_393" />
|
||||
</filter>
|
||||
<radialGradient id="paint0_radial_175_393" cx="0" cy="0" r="1" gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="translate(662.5 629.739) rotate(90) scale(289.261 362.5)">
|
||||
<stop offset="0.281696" stop-color="#FE9567" />
|
||||
<stop offset="0.59375" stop-color="#FD366E" />
|
||||
</radialGradient>
|
||||
</defs>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 1.0 KiB |
BIN
src/routes/threads/(assets)/empty-state.png
Normal file
|
After Width: | Height: | Size: 56 KiB |
1
src/routes/threads/+layout.ts
Normal file
@@ -0,0 +1 @@
|
||||
export const prerender = false;
|
||||
245
src/routes/threads/+page.svelte
Normal file
@@ -0,0 +1,245 @@
|
||||
<script lang="ts">
|
||||
import { Main } from '$lib/layouts';
|
||||
import { createDebounce } from '$lib/utils/debounce';
|
||||
import { DEFAULT_DESCRIPTION, DEFAULT_HOST } from '$lib/utils/metadata';
|
||||
import { TITLE_SUFFIX } from '$routes/titles';
|
||||
|
||||
import FooterNav from '$lib/components/FooterNav.svelte';
|
||||
import MainFooter from '$lib/components/MainFooter.svelte';
|
||||
import ThreadCard from './ThreadCard.svelte';
|
||||
|
||||
import { queryParam } from 'sveltekit-search-params';
|
||||
import PreFooter from './PreFooter.svelte';
|
||||
import TagsDropdown from './TagsDropdown.svelte';
|
||||
import { getThreads } from './helpers';
|
||||
|
||||
const title = 'Threads' + TITLE_SUFFIX;
|
||||
const description = DEFAULT_DESCRIPTION;
|
||||
const ogImage = DEFAULT_HOST + '/images/open-graph/website.png';
|
||||
|
||||
export let data;
|
||||
|
||||
let threads = data.threads;
|
||||
|
||||
let searching = false; // Do some sick animation
|
||||
let query = '';
|
||||
|
||||
const handleSearch = async (value: string) => {
|
||||
query = value;
|
||||
searching = true;
|
||||
threads = await getThreads({
|
||||
q: value,
|
||||
tags: selectedTags ?? [],
|
||||
allTags: true
|
||||
});
|
||||
};
|
||||
|
||||
const { debounce, reset } = createDebounce();
|
||||
|
||||
const search = (node: HTMLInputElement) => {
|
||||
const inputHandler = () => {
|
||||
const value = node.value.toLowerCase();
|
||||
|
||||
debounce(() => {
|
||||
handleSearch(value);
|
||||
});
|
||||
};
|
||||
|
||||
const keydownHandler = (event: KeyboardEvent) => {
|
||||
if (event.key === 'Enter') {
|
||||
const value = node.value.toLowerCase();
|
||||
|
||||
reset();
|
||||
handleSearch(value);
|
||||
}
|
||||
};
|
||||
|
||||
node.addEventListener('input', inputHandler);
|
||||
node.addEventListener('keydown', keydownHandler);
|
||||
|
||||
return {
|
||||
destroy() {
|
||||
node.removeEventListener('input', inputHandler);
|
||||
node.removeEventListener('keydown', keydownHandler);
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
const tags = [
|
||||
'Web',
|
||||
'Flutter',
|
||||
'GraphQL',
|
||||
'Cloud',
|
||||
'Self Hosted'
|
||||
];
|
||||
|
||||
const moreTags = [
|
||||
'Tools',
|
||||
'Accounts',
|
||||
'Users',
|
||||
'Teams',
|
||||
'Databases',
|
||||
'Storage',
|
||||
'Functions',
|
||||
'Realtime',
|
||||
'Locale',
|
||||
'Avatars',
|
||||
'Webhooks',
|
||||
'General',
|
||||
'REST API'
|
||||
];
|
||||
const _selectedTags = queryParam<string[]>('tags', {
|
||||
encode(tags) {
|
||||
return tags.join(',');
|
||||
},
|
||||
decode(tags) {
|
||||
return tags?.split(',') ?? [];
|
||||
},
|
||||
defaultValue: []
|
||||
});
|
||||
|
||||
let selectedTags: string[] = [];
|
||||
|
||||
function toggleTag(tag: string) {
|
||||
if (selectedTags.includes(tag)) {
|
||||
selectedTags = selectedTags.filter((t) => t !== tag);
|
||||
} else {
|
||||
selectedTags = [...selectedTags, tag];
|
||||
}
|
||||
handleSearch(query);
|
||||
}
|
||||
</script>
|
||||
|
||||
<svelte:head>
|
||||
<!-- Titles -->
|
||||
<title>{title}</title>
|
||||
<meta property="og:title" content={title} />
|
||||
<meta name="twitter:title" content={title} />
|
||||
<!-- Description -->
|
||||
<meta name="description" content={description} />
|
||||
<meta property="og:description" content={description} />
|
||||
<meta name="twitter:description" content={description} />
|
||||
<!-- Image -->
|
||||
<meta property="og:image" content={ogImage} />
|
||||
<meta property="og:image:width" content="1200" />
|
||||
<meta property="og:image:height" content="630" />
|
||||
<meta name="twitter:image" content={ogImage} />
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
</svelte:head>
|
||||
|
||||
<Main>
|
||||
<div
|
||||
class="aw-big-padding-section-level-1 u-position-relative u-overflow-hidden"
|
||||
style="margin-block-start: -10rem; padding-block-start: 10rem; border-block-end: 1px solid hsl(var(--aw-color-smooth));"
|
||||
>
|
||||
<div
|
||||
class="u-position-absolute"
|
||||
style="pointer-events: none; inset-inline-start: -700px; inset-block-start: 0px;"
|
||||
>
|
||||
<enhanced:img src="./(assets)/bg-red.svg" alt="" />
|
||||
</div>
|
||||
<div
|
||||
class="u-position-absolute"
|
||||
style="pointer-events: none; inset-inline-end: -700px; inset-block-start: -400px;"
|
||||
>
|
||||
<enhanced:img src="./(assets)/bg-green.svg" alt="" />
|
||||
</div>
|
||||
<div class="aw-big-padding-section-level-2 u-position-relative aw-u-margin-block-80">
|
||||
<div class="aw-container">
|
||||
<h1 class="aw-display aw-u-color-text-primary">Threads</h1>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="aw-container" style="padding-block-end: 5rem">
|
||||
<div class="u-flex u-flex-wrap u-cross-center u-gap-32">
|
||||
<ul class="u-flex u-flex-wrap u-gap-8">
|
||||
{#each tags as tag}
|
||||
<li style="display: flex; align-items: center;">
|
||||
<button
|
||||
class="aw-btn-tag"
|
||||
class:is-selected={selectedTags?.includes(tag)}
|
||||
on:click={() => toggleTag(tag)}
|
||||
>
|
||||
{tag}
|
||||
</button>
|
||||
</li>
|
||||
{/each}
|
||||
<li>
|
||||
<TagsDropdown tags={moreTags} selectedTags={selectedTags ?? []} {toggleTag} />
|
||||
</li>
|
||||
</ul>
|
||||
<div
|
||||
class="aw-input-text-search-wrapper u-width-full-line u-max-width-350 aw-u-max-inline-size-none-mobile u-margin-inline-start-auto"
|
||||
>
|
||||
<span
|
||||
class="aw-icon-search u-z-index-5"
|
||||
aria-hidden="true"
|
||||
style="inset-block-start:0.9rem"
|
||||
/>
|
||||
<input
|
||||
class="aw-input-button -u-padding-block-0 u-position-relative u-z-index-1"
|
||||
type="text"
|
||||
id="search"
|
||||
placeholder="Search for threads"
|
||||
data-hit="-1"
|
||||
use:search
|
||||
bind:value={query}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{#if threads.length}
|
||||
<h2 class="u-margin-block-start-16 aw-u-color-text-primary" aria-live="polite">
|
||||
Found {query.length ? threads.length : '600+'} results.
|
||||
</h2>
|
||||
{/if}
|
||||
|
||||
<div class="u-flex-vertical u-gap-16 u-margin-block-start-16">
|
||||
{#each threads as thread (thread.$id)}
|
||||
<ThreadCard {thread} {query} />
|
||||
{:else}
|
||||
<div class="aw-card is-normal has-border-gradient empty-card">
|
||||
<enhanced:img class="img" src="./(assets)/empty-state.png" alt="" />
|
||||
<span class="aw-main-body-500">No support threads found</span>
|
||||
<button
|
||||
class="aw-button"
|
||||
on:click={() => {
|
||||
query = '';
|
||||
handleSearch('');
|
||||
}}>Clear search</button
|
||||
>
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
</div>
|
||||
<PreFooter />
|
||||
<div class="aw-container" style="margin-block-start: -7.75rem;">
|
||||
<FooterNav />
|
||||
<MainFooter />
|
||||
</div>
|
||||
</Main>
|
||||
|
||||
<style lang="scss">
|
||||
.empty-card {
|
||||
padding: 1.25rem;
|
||||
|
||||
.img {
|
||||
display: block;
|
||||
width: 13.75rem;
|
||||
height: auto;
|
||||
margin-inline: auto;
|
||||
}
|
||||
|
||||
span {
|
||||
display: block;
|
||||
color: hsl(var(--aw-color-primary));
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
button {
|
||||
margin-block-start: 1.5rem;
|
||||
margin-inline: auto;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
13
src/routes/threads/+page.ts
Normal file
@@ -0,0 +1,13 @@
|
||||
import { getThreads } from './helpers.js';
|
||||
|
||||
export async function load({ url }) {
|
||||
const tagsParam = url.searchParams.get('tags');
|
||||
|
||||
return {
|
||||
threads: await getThreads({
|
||||
q: url.searchParams.get('q'),
|
||||
tags: tagsParam ? tagsParam.split(',') : undefined,
|
||||
allTags: true
|
||||
})
|
||||
};
|
||||
}
|
||||
72
src/routes/threads/PreFooter.svelte
Normal file
@@ -0,0 +1,72 @@
|
||||
<div class="wrapper">
|
||||
<img src="/images/bgs/pre-footer.png" alt="" class="aw-pre-footer-bg" style="z-index:-1" />
|
||||
<div class="aw-container">
|
||||
<h2 class="aw-display aw-u-color-text-primary">Need support?</h2>
|
||||
<div class="cards">
|
||||
<div class="cardy">
|
||||
<h3 class="aw-label aw-u-color-text-primary">Join our Discord</h3>
|
||||
<p class="aw-main-body-400 u-margin-block-start-16 aw-u-color-text-primary">
|
||||
Get community support by joining our Discord server
|
||||
</p>
|
||||
<a class="aw-button u-margin-block-start-24" href="https://appwrite.io/discord">
|
||||
<span class="aw-icon-discord" />
|
||||
<span class="text">Join Discord</span>
|
||||
</a>
|
||||
</div>
|
||||
<div class="cardy">
|
||||
<h3 class="aw-label aw-u-color-text-primary">Get premium support</h3>
|
||||
<p class="aw-main-body-400 u-margin-block-start-16 aw-u-color-text-primary">
|
||||
Become a pro user and get email support from our team
|
||||
</p>
|
||||
<a class="aw-button u-margin-block-start-24" href="https://appwrite.io/pricing">
|
||||
<span class="text">Learn more</span>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.wrapper {
|
||||
padding-block: 7.5rem;
|
||||
overflow: hidden;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
h2 {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.cards {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fit, minmax(400px, 1fr));
|
||||
justify-content: center;
|
||||
gap: 2.25rem;
|
||||
margin-block-start: 5rem;
|
||||
}
|
||||
|
||||
.cardy {
|
||||
@include border-gradient;
|
||||
--m-border-gradient-before: linear-gradient(
|
||||
180deg,
|
||||
rgba(255, 255, 255, 0.16) 0%,
|
||||
rgba(255, 255, 255, 0) 100%
|
||||
);
|
||||
--m-border-radius: 1rem;
|
||||
|
||||
background: rgba(255, 255, 255, 0.04);
|
||||
backdrop-filter: blur(7.5px);
|
||||
padding: 1.5rem;
|
||||
}
|
||||
|
||||
.aw-pre-footer-bg {
|
||||
position: absolute;
|
||||
top: clamp(300px, 50vw, 50%);
|
||||
left: clamp(300px, 50vw, 50%);
|
||||
transform: translate(-58%, -72%);
|
||||
width: clamp(1200px, 200vw, 3000px);
|
||||
height: auto;
|
||||
max-inline-size: unset;
|
||||
max-block-size: unset;
|
||||
}
|
||||
</style>
|
||||
113
src/routes/threads/TagsDropdown.svelte
Normal file
@@ -0,0 +1,113 @@
|
||||
<script lang="ts">
|
||||
import DropdownCheckboxItem from '$lib/components/DropdownMenu/DropdownCheckboxItem.svelte';
|
||||
import DropdownMenu from '$lib/components/DropdownMenu/DropdownMenu.svelte';
|
||||
import { melt } from '@melt-ui/svelte';
|
||||
import { fly } from 'svelte/transition';
|
||||
|
||||
export let tags: string[];
|
||||
export let selectedTags: string[];
|
||||
export let toggleTag: (tag: string) => void;
|
||||
</script>
|
||||
|
||||
<DropdownMenu let:open let:menu let:trigger>
|
||||
<button class="aw-btn-tag" use:melt={trigger}>
|
||||
<span class="text">More</span>
|
||||
<span class="aw-icon-chevron-down" style="font-size: 1rem" />
|
||||
</button>
|
||||
|
||||
{#if open}
|
||||
<div
|
||||
class="menu-wrapper aw-card is-normal menu has-border-gradient"
|
||||
style:z-index="1"
|
||||
use:melt={menu}
|
||||
transition:fly={{ y: 8, duration: 250 }}
|
||||
>
|
||||
<ul
|
||||
>
|
||||
{#each tags as tag}
|
||||
{@const checked = selectedTags?.includes(tag)}
|
||||
<DropdownCheckboxItem let:checkboxItem {checked}>
|
||||
<li
|
||||
use:melt={checkboxItem}
|
||||
on:m-click={(e) => {
|
||||
e.preventDefault();
|
||||
toggleTag(tag);
|
||||
}}
|
||||
>
|
||||
<div class="checkbox">
|
||||
{#if checked}
|
||||
<span class="aw-icon-check" />
|
||||
{/if}
|
||||
</div>
|
||||
{tag}
|
||||
</li>
|
||||
</DropdownCheckboxItem>
|
||||
{/each}
|
||||
</ul>
|
||||
</div>
|
||||
{/if}
|
||||
</DropdownMenu>
|
||||
|
||||
<style lang="scss">
|
||||
.menu-wrapper {
|
||||
--p-card-border-radius: 0.5rem;
|
||||
padding: 0.75rem;
|
||||
backdrop-filter: blur(2px);
|
||||
--webkit-backdrop-filter: blur(2px);
|
||||
}
|
||||
ul {
|
||||
min-width: 14.375rem;
|
||||
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 0.5rem;
|
||||
height: 12rem;
|
||||
overflow-y: auto;
|
||||
|
||||
&:focus {
|
||||
outline: none;
|
||||
box-shadow: none;
|
||||
}
|
||||
}
|
||||
|
||||
li {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.5rem;
|
||||
|
||||
border-radius: 0.5rem;
|
||||
padding: 0.5rem 0.75rem;
|
||||
|
||||
&:hover {
|
||||
cursor: pointer;
|
||||
background-color: hsl(var(--aw-color-offset));
|
||||
}
|
||||
}
|
||||
|
||||
.checkbox {
|
||||
--p-checkbox-size: 1.4rem;
|
||||
width: var(--p-checkbox-size);
|
||||
height: var(--p-checkbox-size);
|
||||
|
||||
background-color: #19191c;
|
||||
border: 1px solid #56565c;
|
||||
border-radius: 0.25rem;
|
||||
|
||||
position: relative;
|
||||
|
||||
[class*='icon'] {
|
||||
position: absolute;
|
||||
inset: 0;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 1rem;
|
||||
color: black;
|
||||
}
|
||||
|
||||
:global([data-state='checked']) & {
|
||||
background-color: hsl(var(--aw-color-primary));
|
||||
border-color: hsl(var(--aw-color-primary));
|
||||
}
|
||||
}
|
||||
</style>
|
||||
68
src/routes/threads/ThreadCard.svelte
Normal file
@@ -0,0 +1,68 @@
|
||||
<script lang="ts">
|
||||
import { highlight } from '$lib/actions/highlight';
|
||||
import type { DiscordThread } from './types';
|
||||
|
||||
export let thread: DiscordThread;
|
||||
export let query: string;
|
||||
|
||||
$: highlightTerms = query?.split(' ') ?? [];
|
||||
</script>
|
||||
|
||||
{#key highlightTerms}
|
||||
<a
|
||||
href="/threads/{thread.discord_id}"
|
||||
class="aw-card is-normal has-border-gradient thread"
|
||||
>
|
||||
<div class="u-flex u-gap-8">
|
||||
<h3 class="aw-main-body-500 aw-u-color-text-primary" use:highlight={highlightTerms}>
|
||||
{thread.title}
|
||||
</h3>
|
||||
<!-- <time class="aw-caption-400 u-margin-inline-start-auto">12 Jan, 2023</time> -->
|
||||
</div>
|
||||
|
||||
<p class="aw-main-body-500 u-margin-block-start-4" use:highlight={highlightTerms}>
|
||||
{thread.content.length > 200 ? thread.content.slice(0, 200) + '...' : thread.content}
|
||||
</p>
|
||||
|
||||
<div class="u-flex u-main-space-between u-gap-16 u-margin-block-start-16">
|
||||
<ul class="u-flex u-gap-8">
|
||||
{#each thread.tags ?? [] as tag}
|
||||
<li>
|
||||
<div class="aw-tag">{tag}</div>
|
||||
</li>
|
||||
{/each}
|
||||
</ul>
|
||||
|
||||
<div
|
||||
class="aw-icon-button is-more-content"
|
||||
aria-label="Replies"
|
||||
style:pointer-events="none"
|
||||
>
|
||||
<span class="aw-icon-message" aria-hidden="true" style="font-size:1rem" />
|
||||
<span class="aw-caption-400 aw-u-line-height-1-2">{thread.message_count}</span>
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
{/key}
|
||||
|
||||
<style lang="scss">
|
||||
.aw-card {
|
||||
padding: 1.25rem;
|
||||
}
|
||||
|
||||
.thread {
|
||||
position: relative;
|
||||
|
||||
p: {
|
||||
overflow-wrap: break-word;
|
||||
}
|
||||
}
|
||||
|
||||
.thread :global(mark) {
|
||||
background-color: hsl(var(--aw-color-pink-500) / 0.5);
|
||||
}
|
||||
|
||||
h3 {
|
||||
margin-block-end: 0.25rem;
|
||||
}
|
||||
</style>
|
||||
22
src/routes/threads/[id]/+page.server.ts
Normal file
@@ -0,0 +1,22 @@
|
||||
import { error } from '@sveltejs/kit';
|
||||
import { getRelatedThreads, getThread, getThreadMessages } from '../helpers.js';
|
||||
|
||||
export const prerender = false;
|
||||
|
||||
export const load = async ({ params }) => {
|
||||
const id = params.id;
|
||||
|
||||
try {
|
||||
const thread = await getThread(id);
|
||||
const related = await getRelatedThreads(thread);
|
||||
const messages = await getThreadMessages(id);
|
||||
|
||||
return {
|
||||
...thread,
|
||||
related,
|
||||
messages,
|
||||
};
|
||||
} catch (e) {
|
||||
throw error(404, 'Thread not found');
|
||||
}
|
||||
};
|
||||
254
src/routes/threads/[id]/+page.svelte
Normal file
@@ -0,0 +1,254 @@
|
||||
<script lang="ts">
|
||||
import { Main } from '$lib/layouts';
|
||||
import { DEFAULT_DESCRIPTION } from '$lib/utils/metadata';
|
||||
import { TITLE_SUFFIX } from '$routes/titles';
|
||||
|
||||
import FooterNav from '$lib/components/FooterNav.svelte';
|
||||
import MainFooter from '$lib/components/MainFooter.svelte';
|
||||
import SeoOgImage from '$lib/components/SeoOgImage.svelte';
|
||||
import PreFooter from '../PreFooter.svelte';
|
||||
import MessageCard from './MessageCard.svelte';
|
||||
|
||||
export let data;
|
||||
|
||||
const title = data.title + ' - Threads' + TITLE_SUFFIX;
|
||||
const description = DEFAULT_DESCRIPTION;
|
||||
const discordLink = `https://discord.com/channels/564160730845151244/${data.discord_id}`;
|
||||
|
||||
function shorten(str: string, len: number) {
|
||||
return str.length > len ? str.slice(0, len) + '...' : str;
|
||||
}
|
||||
</script>
|
||||
|
||||
<svelte:head>
|
||||
<!-- Titles -->
|
||||
<title>{title}</title>
|
||||
<meta property="og:title" content={title} />
|
||||
<meta name="twitter:title" content={title} />
|
||||
<!-- Desscription -->
|
||||
<meta name="description" content={data.seo_description ?? description} />
|
||||
<meta property="og:description" content={data.seo_description ?? description} />
|
||||
<meta name="twitter:description" content={data.seo_description ?? description} />
|
||||
<SeoOgImage
|
||||
title={shorten(data.title, 32)}
|
||||
description={shorten(data.seo_description ?? DEFAULT_DESCRIPTION, 64)}
|
||||
/>
|
||||
</svelte:head>
|
||||
|
||||
<Main>
|
||||
<div class="aw-container" style="padding-block-end: 0;">
|
||||
<div class="header">
|
||||
<div>
|
||||
<a class="aw-link is-secondary u-cross-baseline" href="/threads">
|
||||
<span class="aw-icon-chevron-left" aria-hidden="true" />
|
||||
<span>Back</span>
|
||||
</a>
|
||||
<h1 class="aw-title aw-u-color-text-primary">{data.title}</h1>
|
||||
<ul class="tags">
|
||||
<li class="aw-tag">
|
||||
<span class="aw-icon-arrow-up" />
|
||||
<span class="text">{data.vote_count}</span>
|
||||
</li>
|
||||
{#each data.tags ?? [] as tag}
|
||||
<li class="aw-tag">
|
||||
<span class="text">{tag}</span>
|
||||
</li>
|
||||
{/each}
|
||||
</ul>
|
||||
</div>
|
||||
<div class="buttons">
|
||||
<a
|
||||
class="aw-button"
|
||||
href={discordLink}
|
||||
>
|
||||
<span class="aw-icon-discord" />
|
||||
<span class="text">View on Discord</span>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="thread-grid">
|
||||
<div class="messages">
|
||||
{#each data.messages ?? [] as message, i}
|
||||
{@const isFirst = i === 0}
|
||||
<MessageCard {message}>
|
||||
{#if isFirst}
|
||||
<div class="aw-inline-info" style:margin-block-start="1.5rem">
|
||||
<span
|
||||
class="aw-sub-body-500 aw-u-color-text-primary"
|
||||
style:display="block"
|
||||
>
|
||||
TL;DR
|
||||
</span>
|
||||
{data.tldr}
|
||||
</div>
|
||||
{/if}
|
||||
</MessageCard>
|
||||
{/each}
|
||||
<div class="aw-card is-normal has-border-gradient">
|
||||
<span class="aw-sub-body-500 aw-u-color-text-primary">Reply</span>
|
||||
<p class="aw-sub-body-500 u-margin-block-start-16">
|
||||
Reply to this thread by joining our Discord
|
||||
</p>
|
||||
<a
|
||||
class="aw-button u-margin-block-start-24"
|
||||
href={discordLink}
|
||||
>
|
||||
<span class="aw-icon-discord" />
|
||||
<span class="text">Reply on Discord</span>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="related">
|
||||
{#if data.related.length}
|
||||
<h2 class="aw-eyebrow aw-u-color-text-primary">Recommended threads</h2>
|
||||
{/if}
|
||||
<ul>
|
||||
{#each data.related as thread}
|
||||
<li>
|
||||
<a href="/threads/{thread.$id}" data-sveltekit-reload>
|
||||
<div class="u-flex u-cross-center">
|
||||
<span class="aw-sub-body-500 aw-u-color-text-primary">
|
||||
{thread.title.length > 40
|
||||
? thread.title.slice(0, 40) + '...'
|
||||
: thread.title}
|
||||
</span>
|
||||
</div>
|
||||
<p class="aw-sub-body-400 u-margin-block-start-8">
|
||||
{thread.content.length > 160
|
||||
? thread.content.slice(0, 160) + '...'
|
||||
: thread.content}
|
||||
</p>
|
||||
</a>
|
||||
</li>
|
||||
{/each}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<PreFooter />
|
||||
<div class="aw-container" style="margin-block-start: -7.75rem;">
|
||||
<FooterNav />
|
||||
<MainFooter />
|
||||
</div>
|
||||
</Main>
|
||||
|
||||
<style lang="scss">
|
||||
.header {
|
||||
display: grid;
|
||||
grid-template-columns: 1fr auto;
|
||||
gap: 4rem;
|
||||
align-items: center;
|
||||
|
||||
margin-block-start: 2.5rem;
|
||||
}
|
||||
|
||||
h1 {
|
||||
margin-block-start: 1rem;
|
||||
}
|
||||
|
||||
.tags {
|
||||
display: flex;
|
||||
gap: 0.5rem;
|
||||
margin-block-start: 1rem;
|
||||
}
|
||||
|
||||
.aw-tag {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.25rem;
|
||||
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.thread-grid {
|
||||
display: grid;
|
||||
grid-template-columns: 2fr 1fr;
|
||||
gap: 3rem;
|
||||
|
||||
margin-block-start: 2rem;
|
||||
border-block-start: 1px solid hsl(var(--aw-color-border));
|
||||
padding-block-end: 5rem;
|
||||
}
|
||||
|
||||
.messages {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 1rem;
|
||||
|
||||
overflow: hidden;
|
||||
|
||||
padding-block-start: 2rem;
|
||||
|
||||
:global(.aw-card) {
|
||||
padding: 1.25rem;
|
||||
}
|
||||
}
|
||||
|
||||
.related {
|
||||
height: 100%;
|
||||
|
||||
position: relative;
|
||||
padding-block-start: 2.25rem;
|
||||
|
||||
overflow: hidden;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: -20px;
|
||||
width: 1px;
|
||||
height: calc(100% + 5rem);
|
||||
background-color: hsl(var(--aw-color-border));
|
||||
}
|
||||
|
||||
ul {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 1rem;
|
||||
|
||||
margin-block-start: 1.5rem;
|
||||
|
||||
li {
|
||||
padding-block-end: 1rem;
|
||||
|
||||
&:not(:last-child) {
|
||||
border-block-end: 1px solid hsl(var(--aw-color-smooth));
|
||||
}
|
||||
|
||||
&:hover {
|
||||
opacity: 0.75;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@keyframes dot {
|
||||
0% {
|
||||
translate: 0 0;
|
||||
}
|
||||
37% {
|
||||
translate: 0 -0.25rem;
|
||||
}
|
||||
75% {
|
||||
translate: 0 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media #{$break1} {
|
||||
.header {
|
||||
gap: 2rem;
|
||||
grid-template-columns: 1fr;
|
||||
}
|
||||
|
||||
.thread-grid {
|
||||
grid-template-columns: 1fr;
|
||||
}
|
||||
|
||||
.related::before {
|
||||
background-color: transparent;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
120
src/routes/threads/[id]/CodeRenderer.svelte
Normal file
@@ -0,0 +1,120 @@
|
||||
<script lang="ts">
|
||||
import '$scss/hljs.css';
|
||||
import { getCodeHtml, type Language } from '$lib/utils/code';
|
||||
import { getContext, hasContext } from 'svelte';
|
||||
import { platformMap } from '$lib/utils/references';
|
||||
import { Tooltip } from '$lib/components';
|
||||
import { copy } from '$lib/utils/copy';
|
||||
|
||||
import { melt } from '@melt-ui/svelte';
|
||||
import type { CodeContext } from '$markdoc/tags/MultiCode.svelte';
|
||||
|
||||
export let text: string;
|
||||
export let language: Language = 'typescript';
|
||||
export let process = true;
|
||||
export let withLineNumbers = true;
|
||||
|
||||
const insideMultiCode = hasContext('multi-code');
|
||||
const selected = insideMultiCode ? getContext<CodeContext>('multi-code').selected : null;
|
||||
|
||||
enum CopyStatus {
|
||||
Copy = 'Copy',
|
||||
Copied = 'Copied!'
|
||||
}
|
||||
let copyText = CopyStatus.Copy;
|
||||
async function handleCopy() {
|
||||
await copy(text);
|
||||
|
||||
copyText = CopyStatus.Copied;
|
||||
setTimeout(() => {
|
||||
copyText = CopyStatus.Copy;
|
||||
}, 1000);
|
||||
}
|
||||
|
||||
if (insideMultiCode) {
|
||||
const ctx = getContext<CodeContext>('multi-code');
|
||||
|
||||
ctx.snippets.update((n) => {
|
||||
n.add(language);
|
||||
|
||||
return n;
|
||||
});
|
||||
|
||||
ctx.selected.subscribe((n) => {
|
||||
if (n === language) {
|
||||
ctx.content.set(text);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
$: result = process
|
||||
? getCodeHtml({ content: text, language: language ?? 'sh', withLineNumbers })
|
||||
: text;
|
||||
</script>
|
||||
|
||||
{#if insideMultiCode}
|
||||
{#if $selected === language}
|
||||
<!-- eslint-disable-next-line svelte/no-at-html-tags -->
|
||||
{@html result}
|
||||
{/if}
|
||||
{:else}
|
||||
<section class="theme-dark aw-code-snippet" aria-label="code-snippet panel">
|
||||
<header class="aw-code-snippet-header">
|
||||
<div class="aw-code-snippet-header-start">
|
||||
{#if platformMap[language]}
|
||||
<div class="u-flex u-gap-16">
|
||||
<div class="aw-tag"><span class="text">{platformMap[language]}</span></div>
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
<div class="aw-code-snippet-header-end">
|
||||
<ul class="buttons-list u-flex u-gap-8">
|
||||
<li class="buttons-list-item aw-u-padding-inline-start-20">
|
||||
<Tooltip>
|
||||
<button
|
||||
slot="asChild"
|
||||
let:trigger
|
||||
use:melt={trigger}
|
||||
on:click={handleCopy}
|
||||
class="aw-icon-button"
|
||||
aria-label="copy code from code-snippet"
|
||||
>
|
||||
<span class="aw-icon-copy" aria-hidden="true" />
|
||||
</button>
|
||||
<svelte:fragment slot="tooltip">
|
||||
{copyText}
|
||||
</svelte:fragment>
|
||||
</Tooltip>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</header>
|
||||
<div class="aw-code-snippet-content">
|
||||
<!-- eslint-disable-next-line svelte/no-at-html-tags -->
|
||||
{@html result}
|
||||
</div>
|
||||
</section>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
button {
|
||||
position: relative;
|
||||
|
||||
.aw-icon-copy {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
transform: translate(-50%, -50%);
|
||||
}
|
||||
}
|
||||
|
||||
.aw-code-snippet {
|
||||
margin-block-end: 1rem;
|
||||
margin-top: 1rem;
|
||||
}
|
||||
|
||||
.aw-code-snippet-content {
|
||||
max-height: 600px;
|
||||
overflow-y: auto;
|
||||
}
|
||||
</style>
|
||||
11
src/routes/threads/[id]/LinkRenderer.svelte
Normal file
@@ -0,0 +1,11 @@
|
||||
<script lang="ts">
|
||||
export let href: string;
|
||||
export let title: string;
|
||||
export let text: string;
|
||||
|
||||
const isExternal = ['http://', 'https://'].some((prefix) => href.startsWith(prefix));
|
||||
const target = isExternal ? '_blank' : undefined;
|
||||
const rel = isExternal ? 'noopener nofollow' : undefined;
|
||||
</script>
|
||||
|
||||
<a class="aw-link is-inline" {href} {title} {target} {rel}>{text}</a>
|
||||
87
src/routes/threads/[id]/MessageCard.svelte
Normal file
@@ -0,0 +1,87 @@
|
||||
<script lang="ts">
|
||||
import SvelteMarkdown from 'svelte-markdown';
|
||||
import type { DiscordMessage } from '../types';
|
||||
import CodeRenderer from './CodeRenderer.svelte';
|
||||
import LinkRenderer from './LinkRenderer.svelte';
|
||||
|
||||
export let message: DiscordMessage;
|
||||
|
||||
const formatTimestamp = (date: string): string => {
|
||||
const dt = new Date(date);
|
||||
|
||||
// format like: 12 Jan, 2023, 13:10
|
||||
const day = dt.getDate();
|
||||
const month = dt.toLocaleString('default', { month: 'short' });
|
||||
const year = dt.getFullYear();
|
||||
const hours = dt.getHours();
|
||||
const minutes = dt.getMinutes();
|
||||
const paddedMinutes = minutes < 10 ? `0${minutes}` : minutes;
|
||||
const paddedHours = hours < 10 ? `0${hours}` : hours;
|
||||
|
||||
return `${day} ${month}, ${year}, ${paddedHours}:${paddedMinutes}`;
|
||||
};
|
||||
</script>
|
||||
|
||||
<div class="aw-card is-normal has-border-gradient message">
|
||||
<div class="header">
|
||||
<div class="author">
|
||||
<div class="author-img">
|
||||
<img src={message.author_avatar} alt="" class="h-full w-full rounded-[inherit]" />
|
||||
</div>
|
||||
<span class="aw-sub-body-500 aw-u-color-text-primary">{message.author}</span>
|
||||
</div>
|
||||
<span class="timestamp aw-caption-400">
|
||||
{formatTimestamp(message.timestamp)}
|
||||
</span>
|
||||
</div>
|
||||
<div class="aw-sub-body-500" style=" margin-block-start: 1rem;">
|
||||
<SvelteMarkdown
|
||||
source={message.message}
|
||||
renderers={{
|
||||
code: CodeRenderer,
|
||||
link: LinkRenderer
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
<slot />
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.aw-card {
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.aw-sub-body-500 {
|
||||
font-size: 1rem !important;
|
||||
}
|
||||
|
||||
.header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.author {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.5rem;
|
||||
}
|
||||
|
||||
.author-img {
|
||||
--p-size: 1.5rem; // 24px
|
||||
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
border-radius: 100%;
|
||||
|
||||
width: var(--p-size);
|
||||
height: var(--p-size);
|
||||
|
||||
img {
|
||||
border-radius: 100%;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
115
src/routes/threads/helpers.ts
Normal file
@@ -0,0 +1,115 @@
|
||||
import {
|
||||
PUBLIC_APPWRITE_COL_MESSAGES_ID,
|
||||
PUBLIC_APPWRITE_COL_THREADS_ID,
|
||||
PUBLIC_APPWRITE_DB_MAIN_ID,
|
||||
PUBLIC_APPWRITE_FN_TLDR_ID
|
||||
} from '$env/static/public';
|
||||
import { databases, functions } from '$lib/appwrite';
|
||||
import { Query } from 'appwrite';
|
||||
import type { DiscordMessage, DiscordThread } from './types';
|
||||
|
||||
type Ranked<T> = {
|
||||
data: T;
|
||||
rank: number; // Percentage of query words found, from 0 to 1
|
||||
};
|
||||
|
||||
type FilterThreadsArgs = {
|
||||
threads: DiscordThread[];
|
||||
q?: string | null;
|
||||
tags?: string[];
|
||||
allTags?: boolean;
|
||||
};
|
||||
|
||||
export function filterThreads({ q, threads: threadDocs, tags, allTags }: FilterThreadsArgs) {
|
||||
const threads = tags
|
||||
? threadDocs.filter((thread) => {
|
||||
const lowercaseTags = thread.tags?.map((tag) => tag.toLowerCase());
|
||||
if (allTags) {
|
||||
return tags?.every((tag) => lowercaseTags?.includes(tag.toLowerCase()));
|
||||
} else {
|
||||
return tags?.some((tag) => lowercaseTags?.includes(tag.toLowerCase()));
|
||||
}
|
||||
})
|
||||
: threadDocs;
|
||||
|
||||
if (!q) return threads;
|
||||
|
||||
const queryWords = q.toLowerCase().split(/\s+/);
|
||||
const rankPerWord = 1 / queryWords.length;
|
||||
const res: Ranked<DiscordThread>[] = [];
|
||||
|
||||
threads.forEach((item) => {
|
||||
const foundWords = new Set<string>();
|
||||
|
||||
Object.values(item).forEach((value) => {
|
||||
const stringified = JSON.stringify(value).toLowerCase();
|
||||
|
||||
queryWords.forEach((word) => {
|
||||
if (stringified.includes(word)) {
|
||||
foundWords.add(word);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
const rank = foundWords.size * rankPerWord;
|
||||
|
||||
if (rank > 0) {
|
||||
res.push({
|
||||
data: item,
|
||||
rank
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
return res.sort((a, b) => b.rank - a.rank).map(({ data }) => data);
|
||||
}
|
||||
|
||||
type GetThreadsArgs = Omit<FilterThreadsArgs, 'threads'>;
|
||||
|
||||
export async function getThreads({ q, tags, allTags }: GetThreadsArgs) {
|
||||
let query = [
|
||||
q ? Query.search('search_meta', q) : undefined
|
||||
];
|
||||
|
||||
tags = tags?.filter(Boolean).map((tag) => tag.toLowerCase()) ?? [];
|
||||
|
||||
if (tags.length > 0) {
|
||||
query = [...query, Query.search('tags', tags.join(','))];
|
||||
}
|
||||
|
||||
const data = await databases.listDocuments(
|
||||
PUBLIC_APPWRITE_DB_MAIN_ID,
|
||||
PUBLIC_APPWRITE_COL_THREADS_ID,
|
||||
query.filter(Boolean) as string[]
|
||||
);
|
||||
|
||||
const threadDocs = data.documents as unknown as DiscordThread[];
|
||||
return filterThreads({ threads: threadDocs, q, tags, allTags });
|
||||
}
|
||||
|
||||
export async function getThread($id: string) {
|
||||
return (await databases.getDocument(
|
||||
PUBLIC_APPWRITE_DB_MAIN_ID,
|
||||
PUBLIC_APPWRITE_COL_THREADS_ID,
|
||||
$id
|
||||
)) as unknown as DiscordThread;
|
||||
}
|
||||
|
||||
export async function getRelatedThreads(thread: DiscordThread, limit: number = 3) {
|
||||
const tags = thread.tags?.filter(Boolean) ?? [];
|
||||
const relatedThreads = await getThreads({ q: null, tags, allTags: false });
|
||||
|
||||
return relatedThreads.filter(({ $id }) => $id !== thread.$id).slice(0, limit);
|
||||
}
|
||||
|
||||
export async function getThreadMessages(threadId: string) {
|
||||
const data = await databases.listDocuments(
|
||||
PUBLIC_APPWRITE_DB_MAIN_ID,
|
||||
PUBLIC_APPWRITE_COL_MESSAGES_ID,
|
||||
[Query.equal('threadId', threadId)].filter(Boolean) as string[]
|
||||
);
|
||||
|
||||
return (data.documents as unknown as DiscordMessage[]).sort(
|
||||
(a, b) => new Date(a.timestamp).getTime() - new Date(b.timestamp).getTime()
|
||||
);
|
||||
}
|
||||
38
src/routes/threads/types.ts
Normal file
@@ -0,0 +1,38 @@
|
||||
import type { Models } from 'appwrite';
|
||||
|
||||
export type MockThread = {
|
||||
id: string;
|
||||
username?: string;
|
||||
title: string;
|
||||
text: string;
|
||||
replies: MockMessage[];
|
||||
};
|
||||
|
||||
export interface DiscordMessage extends Pick<Models.Document, '$id'> {
|
||||
threadId: string;
|
||||
author: string;
|
||||
author_avatar: string;
|
||||
message: string;
|
||||
role?: string;
|
||||
/* `UTC` timestamp */
|
||||
timestamp: string;
|
||||
}
|
||||
|
||||
export interface DiscordThread extends Pick<Models.Document, '$id'> {
|
||||
discord_id: string;
|
||||
author: string;
|
||||
tags?: string[];
|
||||
author_avatar: string;
|
||||
seo_description?: string;
|
||||
content: string;
|
||||
title: string;
|
||||
search_meta?: string;
|
||||
tldr: string;
|
||||
vote_count: number;
|
||||
message_count: number;
|
||||
}
|
||||
|
||||
export type MockMessage = {
|
||||
username?: string;
|
||||
text: string;
|
||||
};
|
||||
38
src/scss/6-elements/_btn-tag.scss
Normal file
@@ -0,0 +1,38 @@
|
||||
@use '../abstract' as *;
|
||||
|
||||
.#{$p}-btn-tag {
|
||||
--p-tag-text-color: var(--aw-color-primary);
|
||||
--p-tag-bg-color: var(--aw-color-greyscale-100);
|
||||
--p-tag-border-color: var(--p-tag-bg-color);
|
||||
|
||||
|
||||
color: hsl(var(--p-tag-text-color));
|
||||
background-color: hsl(var(--p-tag-bg-color));
|
||||
border: 1px solid hsl(var(--p-tag-border-color));
|
||||
|
||||
padding-block: pxToRem(4);
|
||||
padding-inline: pxToRem(8);
|
||||
border-radius: pxToRem(12);
|
||||
font-size: var(--aw-font-size-micro);
|
||||
line-height: var(--aw-line-height-tiny);
|
||||
|
||||
#{$theme-dark} & {
|
||||
--p-tag-bg-color: var(--aw-color-greyscale-750);
|
||||
|
||||
&:where(:hover) {
|
||||
--p-tag-bg-color: var(--aw-color-greyscale-700);
|
||||
}
|
||||
|
||||
&:where(:active) {
|
||||
--p-tag-bg-color: var(--aw-color-greyscale-800);
|
||||
}
|
||||
|
||||
&:where(.is-selected) {
|
||||
--p-tag-border-color: var(--aw-color-white);
|
||||
}
|
||||
|
||||
&:where(:disabled) {
|
||||
--p-tag-bg-color: var(--aw-color-greyscale-800);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -9,6 +9,7 @@
|
||||
@media #{$break1} { padding-inline: pxToRem(20); }
|
||||
}
|
||||
|
||||
|
||||
.#{$p}-main-section {
|
||||
> * { padding-block:pxToRem(24); }
|
||||
>:first-child { padding-block-start:0; }
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
@use '../abstract' as *;
|
||||
|
||||
.#{$p}-icon-button {
|
||||
display: block;
|
||||
display: flex;
|
||||
gap: pxToRem(4);
|
||||
position: relative;
|
||||
block-size:pxToRem(28);
|
||||
inline-size:pxToRem(28);
|
||||
@@ -10,10 +11,17 @@
|
||||
border-radius: pxToRem(8);
|
||||
|
||||
> [class*='icon'] {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
transform: translate(-50%, -50%);
|
||||
position: relative;
|
||||
&::before {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
transform: translate(-50%, -50%);
|
||||
}
|
||||
}
|
||||
&.is-more-content {
|
||||
inline-size:fit-content; padding:pxToRem(4); line-height:pxToRem(18);
|
||||
> [class*='icon'] { inline-size:pxToRem(16); }
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
@forward "badges";
|
||||
@forward "numeric-badge";
|
||||
@forward "tag";
|
||||
@forward "btn-tag";
|
||||
@forward "inline-tag";
|
||||
@forward "card";
|
||||
@forward "lists";
|
||||
|
||||
@@ -31,5 +31,9 @@
|
||||
&.is-inline {
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
&.is-secondary {
|
||||
--p-link-color-text-default: var(--aw-color-secondary);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -47,6 +47,7 @@
|
||||
.#{$p}-u-margin-inline-32-negative { margin-inline:pxToRem(-32); }
|
||||
|
||||
.#{$p}-u-margin-block-0 { margin-block:0; }
|
||||
.#{$p}-u-margin-block-80 { margin-block:pxToRem(80); }
|
||||
.#{$p}-u-margin-block-start-40 { margin-block-start:pxToRem(40); }
|
||||
.#{$p}-u-margin-block-start-40-mobile { @media #{$break1} {margin-block-start:pxToRem(40);} }
|
||||
|
||||
|
||||
@@ -59,4 +59,4 @@ const config = {
|
||||
}
|
||||
}
|
||||
};
|
||||
export default config;
|
||||
export default config;
|
||||
BIN
teams-labels.png
|
Before Width: | Height: | Size: 1.4 MiB |