your personal website on atproto - mirror
0
fork

Configure Feed

Select the types of activity you want to include in your feed.

refactor pt4

Florian b00c3c38 48dcbf6f

+194 -119
+3 -2
package.json
··· 41 41 "dependencies": { 42 42 "@atcute/atproto": "^3.1.10", 43 43 "@atcute/bluesky": "^3.2.15", 44 + "@atcute/bluesky-richtext-parser": "^2.1.0", 45 + "@atcute/bluesky-richtext-segmenter": "^3.0.0", 44 46 "@atcute/client": "^4.2.1", 45 47 "@atcute/identity-resolver": "^1.2.2", 46 48 "@atcute/lexicons": "^1.2.6", 47 49 "@atcute/oauth-browser-client": "^2.0.3", 48 - "@atproto/api": "^0.18.16", 49 - "@atproto/common-web": "^0.4.12", 50 + "@atcute/tid": "^1.1.1", 50 51 "@cloudflare/workers-types": "^4.20260123.0", 51 52 "@ethercorps/sveltekit-og": "^4.2.1", 52 53 "@foxui/colors": "^0.4.7",
+100 -53
pnpm-lock.yaml
··· 14 14 '@atcute/bluesky': 15 15 specifier: ^3.2.15 16 16 version: 3.2.15 17 + '@atcute/bluesky-richtext-parser': 18 + specifier: ^2.1.0 19 + version: 2.1.0 20 + '@atcute/bluesky-richtext-segmenter': 21 + specifier: ^3.0.0 22 + version: 3.0.0 17 23 '@atcute/client': 18 24 specifier: ^4.2.1 19 25 version: 4.2.1 ··· 26 32 '@atcute/oauth-browser-client': 27 33 specifier: ^2.0.3 28 34 version: 2.0.3(@atcute/identity@1.1.3) 29 - '@atproto/api': 30 - specifier: ^0.18.16 31 - version: 0.18.16 32 - '@atproto/common-web': 33 - specifier: ^0.4.12 34 - version: 0.4.12 35 + '@atcute/tid': 36 + specifier: ^1.1.1 37 + version: 1.1.1 35 38 '@cloudflare/workers-types': 36 39 specifier: ^4.20260123.0 37 40 version: 4.20260123.0 38 41 '@ethercorps/sveltekit-og': 39 42 specifier: ^4.2.1 40 - version: 4.2.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2))) 43 + version: 4.2.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2))) 41 44 '@foxui/colors': 42 45 specifier: ^0.4.7 43 46 version: 0.4.7(svelte@5.48.0)(tailwindcss@4.1.18) ··· 82 85 version: 3.16.0 83 86 bits-ui: 84 87 specifier: ^2.15.4 85 - version: 2.15.4(@internationalized/date@3.10.1)(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 88 + version: 2.15.4(@internationalized/date@3.10.1)(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 86 89 clsx: 87 90 specifier: ^2.1.1 88 91 version: 2.1.1 ··· 131 134 version: 9.39.2 132 135 '@sveltejs/adapter-cloudflare': 133 136 specifier: ^7.2.6 134 - version: 7.2.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(wrangler@4.60.0(@cloudflare/workers-types@4.20260123.0)) 137 + version: 7.2.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(wrangler@4.60.0(@cloudflare/workers-types@4.20260123.0)) 135 138 '@sveltejs/kit': 136 139 specifier: ^2.50.1 137 - version: 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 140 + version: 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 138 141 '@sveltejs/vite-plugin-svelte': 139 142 specifier: ^6.2.4 140 - version: 6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 143 + version: 6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 141 144 '@tailwindcss/forms': 142 145 specifier: ^0.5.11 143 146 version: 0.5.11(tailwindcss@4.1.18) 144 147 '@tailwindcss/vite': 145 148 specifier: ^4.1.18 146 - version: 4.1.18(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 149 + version: 4.1.18(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 147 150 '@types/turndown': 148 151 specifier: ^5.0.6 149 152 version: 5.0.6 ··· 185 188 version: 8.53.1(eslint@9.39.2(jiti@2.6.1))(typescript@5.9.3) 186 189 vite: 187 190 specifier: ^7.3.1 188 - version: 7.3.1(jiti@2.6.1)(lightningcss@1.30.2) 191 + version: 7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2) 189 192 190 193 packages: 191 194 192 195 '@atcute/atproto@3.1.10': 193 196 resolution: {integrity: sha512-+GKZpOc0PJcdWMQEkTfg/rSNDAAHxmAUGBl60g2az15etqJn5WaUPNGFE2sB7hKpwi5Ue2h/L0OacINcE/JDDQ==, tarball: https://registry.npmjs.org/@atcute/atproto/-/atproto-3.1.10.tgz} 194 197 198 + '@atcute/bluesky-richtext-parser@2.1.0': 199 + resolution: {integrity: sha512-DLye+apLkTM9OjjxQXImXhA3VbvE24Vnlvwc+nMQfpTxhS/VIXP5WRVJ67j/Br/TL6FeSSWLBnv1LuqUSVgUyQ==, tarball: https://registry.npmjs.org/@atcute/bluesky-richtext-parser/-/bluesky-richtext-parser-2.1.0.tgz} 200 + 201 + '@atcute/bluesky-richtext-segmenter@3.0.0': 202 + resolution: {integrity: sha512-NhZTUKtFpeBBbILwAcxj5u4RobIoHOmGw3CAaaEFNebKYSvmTecrXJ7XufHw5DFOUdr8SiKXQVRQxGAxulMNWg==, tarball: https://registry.npmjs.org/@atcute/bluesky-richtext-segmenter/-/bluesky-richtext-segmenter-3.0.0.tgz} 203 + 195 204 '@atcute/bluesky@3.2.15': 196 205 resolution: {integrity: sha512-H4RW3WffjfdKvOZ9issEUQnuSR4KfuAwwJnYu0fclA9VDa99JTJ+pa8tTl9lFeBV9DINtWJAx7rdIbICoVCstQ==, tarball: https://registry.npmjs.org/@atcute/bluesky/-/bluesky-3.2.15.tgz} 197 206 ··· 215 224 '@atcute/oauth-browser-client@2.0.3': 216 225 resolution: {integrity: sha512-rzUjwhjE4LRRKdQnCFQag/zXRZMEAB1hhBoLfnoQuHwWbmDUCL7fzwC3jRhDPp3om8XaYNDj8a/iqRip0wRqoQ==, tarball: https://registry.npmjs.org/@atcute/oauth-browser-client/-/oauth-browser-client-2.0.3.tgz} 217 226 227 + '@atcute/tid@1.1.1': 228 + resolution: {integrity: sha512-djJ8UGhLkTU5V51yCnBEruMg35qETjWzWy5sJG/2gEOl2Gd7rQWHSaf+yrO6vMS5EFA38U2xOWE3EDUPzvc2ZQ==, tarball: https://registry.npmjs.org/@atcute/tid/-/tid-1.1.1.tgz} 229 + 230 + '@atcute/time-ms@1.2.0': 231 + resolution: {integrity: sha512-dtNKebVIbr1+yu3a6vgtL4sfkNgxkL3aA+ohHsjtW83WWMjjGvX8GVTVmYCJ2dYSxIoxK0q1yWs11PmlqzmQ/A==, tarball: https://registry.npmjs.org/@atcute/time-ms/-/time-ms-1.2.0.tgz} 232 + 218 233 '@atcute/uint8array@1.0.6': 219 234 resolution: {integrity: sha512-ucfRBQc7BFT8n9eCyGOzDHEMKF/nZwhS2pPao4Xtab1ML3HdFYcX2DM1tadCzas85QTGxHe5urnUAAcNKGRi9A==, tarball: https://registry.npmjs.org/@atcute/uint8array/-/uint8array-1.0.6.tgz} 220 235 ··· 226 241 227 242 '@atproto/api@0.15.27': 228 243 resolution: {integrity: sha512-ok/WGafh1nz4t8pEQGtAF/32x2E2VDWU4af6BajkO5Gky2jp2q6cv6aB2A5yuvNNcc3XkYMYipsqVHVwLPMF9g==, tarball: https://registry.npmjs.org/@atproto/api/-/api-0.15.27.tgz} 229 - 230 - '@atproto/api@0.18.16': 231 - resolution: {integrity: sha512-tRGKSWr83pP5CQpSboePU21pE+GqLDYy1XHae4HH4hjaT0pr5V8wNgu70kbKB0B02GVUumeDRpJnlHKD+eMzLg==, tarball: https://registry.npmjs.org/@atproto/api/-/api-0.18.16.tgz} 232 244 233 245 '@atproto/common-web@0.4.12': 234 246 resolution: {integrity: sha512-3aCJemqM/fkHQrVPbTCHCdiVstKFI+2LkFLvUhO6XZP0EqUZa/rg/CIZBKTFUWu9I5iYiaEiXL9VwcDRpEevSw==, tarball: https://registry.npmjs.org/@atproto/common-web/-/common-web-0.4.12.tgz} ··· 1402 1414 '@tiptap/starter-kit@3.16.0': 1403 1415 resolution: {integrity: sha512-eWi+77SgKyhSx91Hmn32ER+gPN6FfInGtod4A+XxSG+LqS/sn6kpUEdowYrnqiZzhUXZCSTSJvC+UcMUZHOkxQ==, tarball: https://registry.npmjs.org/@tiptap/starter-kit/-/starter-kit-3.16.0.tgz} 1404 1416 1417 + '@types/bun@1.3.6': 1418 + resolution: {integrity: sha512-uWCv6FO/8LcpREhenN1d1b6fcspAB+cefwD7uti8C8VffIv0Um08TKMn98FynpTiU38+y2dUO55T11NgDt8VAA==, tarball: https://registry.npmjs.org/@types/bun/-/bun-1.3.6.tgz} 1419 + 1405 1420 '@types/cookie@0.6.0': 1406 1421 resolution: {integrity: sha512-4Kh9a6B2bQciAhf7FSuMRRkUWecJgJu9nPnx3yzpsfXX/c50REIqpHY4C82bXP90qrLtXtkDxTZosYO3UpOwlA==, tarball: https://registry.npmjs.org/@types/cookie/-/cookie-0.6.0.tgz} 1407 1422 ··· 1420 1435 '@types/mdurl@2.0.0': 1421 1436 resolution: {integrity: sha512-RGdgjQUZba5p6QEFAVx2OGb8rQDL/cPRG7GiedRzMcJ1tYnUANBncjbSB1NRGwbvjcPeikRABz2nshyPk1bhWg==, tarball: https://registry.npmjs.org/@types/mdurl/-/mdurl-2.0.0.tgz} 1422 1437 1438 + '@types/node@25.0.10': 1439 + resolution: {integrity: sha512-zWW5KPngR/yvakJgGOmZ5vTBemDoSqF3AcV/LrO5u5wTWyEAVVh+IT39G4gtyAkh3CtTZs8aX/yRM82OfzHJRg==, tarball: https://registry.npmjs.org/@types/node/-/node-25.0.10.tgz} 1440 + 1423 1441 '@types/turndown@5.0.6': 1424 1442 resolution: {integrity: sha512-ru00MoyeeouE5BX4gRL+6m/BsDfbRayOskWqUvh7CLGW+UXxHQItqALa38kKnOiZPqJrtzJUgAC2+F0rL1S4Pg==, tarball: https://registry.npmjs.org/@types/turndown/-/turndown-5.0.6.tgz} 1425 1443 ··· 1550 1568 1551 1569 brace-expansion@2.0.2: 1552 1570 resolution: {integrity: sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ==, tarball: https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.2.tgz} 1571 + 1572 + bun-types@1.3.6: 1573 + resolution: {integrity: sha512-OlFwHcnNV99r//9v5IIOgQ9Uk37gZqrNMCcqEaExdkVq3Avwqok1bJFmvGMCkCE0FqzdY8VMOZpfpR3lwI+CsQ==, tarball: https://registry.npmjs.org/bun-types/-/bun-types-1.3.6.tgz} 1553 1574 1554 1575 callsites@3.1.0: 1555 1576 resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==, tarball: https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz} ··· 2131 2152 natural-compare@1.4.0: 2132 2153 resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==, tarball: https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz} 2133 2154 2155 + node-gyp-build@4.8.4: 2156 + resolution: {integrity: sha512-LA4ZjwlnUblHVgq0oBF3Jl/6h/Nvs5fzBLwdEF4nuxnFdsfajde4WfxtJr3CaiH+F6ewcIB/q4jQ4UzPyid+CQ==, tarball: https://registry.npmjs.org/node-gyp-build/-/node-gyp-build-4.8.4.tgz} 2157 + hasBin: true 2158 + 2134 2159 nth-check@2.1.1: 2135 2160 resolution: {integrity: sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==, tarball: https://registry.npmjs.org/nth-check/-/nth-check-2.1.1.tgz} 2136 2161 ··· 2623 2648 ultrahtml@1.6.0: 2624 2649 resolution: {integrity: sha512-R9fBn90VTJrqqLDwyMph+HGne8eqY1iPfYhPzZrvKpIfwkWZbcYlfpsb8B9dTvBfpy1/hqAD7Wi8EKfP9e8zdw==, tarball: https://registry.npmjs.org/ultrahtml/-/ultrahtml-1.6.0.tgz} 2625 2650 2651 + undici-types@7.16.0: 2652 + resolution: {integrity: sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==, tarball: https://registry.npmjs.org/undici-types/-/undici-types-7.16.0.tgz} 2653 + 2626 2654 undici@7.18.2: 2627 2655 resolution: {integrity: sha512-y+8YjDFzWdQlSE9N5nzKMT3g4a5UBX1HKowfdXh0uvAnTaqqwqB92Jt4UXBAeKekDs5IaDKyJFR4X1gYVCgXcw==, tarball: https://registry.npmjs.org/undici/-/undici-7.18.2.tgz} 2628 2656 engines: {node: '>=20.18.1'} ··· 2781 2809 dependencies: 2782 2810 '@atcute/lexicons': 1.2.6 2783 2811 2812 + '@atcute/bluesky-richtext-parser@2.1.0': {} 2813 + 2814 + '@atcute/bluesky-richtext-segmenter@3.0.0': {} 2815 + 2784 2816 '@atcute/bluesky@3.2.15': 2785 2817 dependencies: 2786 2818 '@atcute/atproto': 3.1.10 ··· 2825 2857 transitivePeerDependencies: 2826 2858 - '@atcute/identity' 2827 2859 2860 + '@atcute/tid@1.1.1': 2861 + dependencies: 2862 + '@atcute/time-ms': 1.2.0 2863 + 2864 + '@atcute/time-ms@1.2.0': 2865 + dependencies: 2866 + '@types/bun': 1.3.6 2867 + node-gyp-build: 4.8.4 2868 + 2828 2869 '@atcute/uint8array@1.0.6': {} 2829 2870 2830 2871 '@atcute/util-fetch@1.0.5': ··· 2846 2887 tlds: 1.261.0 2847 2888 zod: 3.25.76 2848 2889 2849 - '@atproto/api@0.18.16': 2850 - dependencies: 2851 - '@atproto/common-web': 0.4.12 2852 - '@atproto/lexicon': 0.6.0 2853 - '@atproto/syntax': 0.4.2 2854 - '@atproto/xrpc': 0.7.7 2855 - await-lock: 2.2.2 2856 - multiformats: 9.9.0 2857 - tlds: 1.261.0 2858 - zod: 3.25.76 2859 - 2860 2890 '@atproto/common-web@0.4.12': 2861 2891 dependencies: 2862 2892 '@atproto/lex-data': 0.0.8 ··· 3147 3177 '@eslint/core': 0.17.0 3148 3178 levn: 0.4.1 3149 3179 3150 - '@ethercorps/sveltekit-og@4.2.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))': 3180 + '@ethercorps/sveltekit-og@4.2.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))': 3151 3181 dependencies: 3152 3182 '@resvg/resvg-wasm': 2.6.2 3153 - '@sveltejs/kit': 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 3183 + '@sveltejs/kit': 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 3154 3184 '@takumi-rs/helpers': 0.55.4 3155 3185 '@takumi-rs/image-response': 0.55.4 3156 3186 '@takumi-rs/wasm': 0.55.4 ··· 3474 3504 dependencies: 3475 3505 acorn: 8.15.0 3476 3506 3477 - '@sveltejs/adapter-cloudflare@7.2.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(wrangler@4.60.0(@cloudflare/workers-types@4.20260123.0))': 3507 + '@sveltejs/adapter-cloudflare@7.2.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(wrangler@4.60.0(@cloudflare/workers-types@4.20260123.0))': 3478 3508 dependencies: 3479 3509 '@cloudflare/workers-types': 4.20260123.0 3480 - '@sveltejs/kit': 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 3510 + '@sveltejs/kit': 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 3481 3511 worktop: 0.8.0-next.18 3482 3512 wrangler: 4.60.0(@cloudflare/workers-types@4.20260123.0) 3483 3513 3484 - '@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2))': 3514 + '@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2))': 3485 3515 dependencies: 3486 3516 '@standard-schema/spec': 1.1.0 3487 3517 '@sveltejs/acorn-typescript': 1.0.8(acorn@8.15.0) 3488 - '@sveltejs/vite-plugin-svelte': 6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 3518 + '@sveltejs/vite-plugin-svelte': 6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 3489 3519 '@types/cookie': 0.6.0 3490 3520 acorn: 8.15.0 3491 3521 cookie: 0.6.0 ··· 3498 3528 set-cookie-parser: 2.7.2 3499 3529 sirv: 3.0.2 3500 3530 svelte: 5.48.0 3501 - vite: 7.3.1(jiti@2.6.1)(lightningcss@1.30.2) 3531 + vite: 7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2) 3502 3532 optionalDependencies: 3503 3533 typescript: 5.9.3 3504 3534 3505 - '@sveltejs/vite-plugin-svelte-inspector@5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2))': 3535 + '@sveltejs/vite-plugin-svelte-inspector@5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2))': 3506 3536 dependencies: 3507 - '@sveltejs/vite-plugin-svelte': 6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 3537 + '@sveltejs/vite-plugin-svelte': 6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 3508 3538 obug: 2.1.1 3509 3539 svelte: 5.48.0 3510 - vite: 7.3.1(jiti@2.6.1)(lightningcss@1.30.2) 3540 + vite: 7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2) 3511 3541 3512 - '@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2))': 3542 + '@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2))': 3513 3543 dependencies: 3514 - '@sveltejs/vite-plugin-svelte-inspector': 5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 3544 + '@sveltejs/vite-plugin-svelte-inspector': 5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 3515 3545 deepmerge: 4.3.1 3516 3546 magic-string: 0.30.21 3517 3547 obug: 2.1.1 3518 3548 svelte: 5.48.0 3519 - vite: 7.3.1(jiti@2.6.1)(lightningcss@1.30.2) 3520 - vitefu: 1.1.1(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 3549 + vite: 7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2) 3550 + vitefu: 1.1.1(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 3521 3551 3522 3552 '@swc/helpers@0.5.18': 3523 3553 dependencies: ··· 3594 3624 postcss-selector-parser: 6.0.10 3595 3625 tailwindcss: 4.1.18 3596 3626 3597 - '@tailwindcss/vite@4.1.18(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2))': 3627 + '@tailwindcss/vite@4.1.18(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2))': 3598 3628 dependencies: 3599 3629 '@tailwindcss/node': 4.1.18 3600 3630 '@tailwindcss/oxide': 4.1.18 3601 3631 tailwindcss: 4.1.18 3602 - vite: 7.3.1(jiti@2.6.1)(lightningcss@1.30.2) 3632 + vite: 7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2) 3603 3633 3604 3634 '@takumi-rs/core-darwin-arm64@0.55.4': 3605 3635 optional: true ··· 3802 3832 '@tiptap/extensions': 3.16.0(@tiptap/core@3.16.0(@tiptap/pm@3.16.0))(@tiptap/pm@3.16.0) 3803 3833 '@tiptap/pm': 3.16.0 3804 3834 3835 + '@types/bun@1.3.6': 3836 + dependencies: 3837 + bun-types: 1.3.6 3838 + 3805 3839 '@types/cookie@0.6.0': {} 3806 3840 3807 3841 '@types/estree@1.0.8': {} ··· 3816 3850 '@types/mdurl': 2.0.0 3817 3851 3818 3852 '@types/mdurl@2.0.0': {} 3853 + 3854 + '@types/node@25.0.10': 3855 + dependencies: 3856 + undici-types: 7.16.0 3819 3857 3820 3858 '@types/turndown@5.0.6': {} 3821 3859 ··· 3957 3995 svelte-toolbelt: 0.7.1(svelte@5.48.0) 3958 3996 tabbable: 6.4.0 3959 3997 3960 - bits-ui@2.15.4(@internationalized/date@3.10.1)(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0): 3998 + bits-ui@2.15.4(@internationalized/date@3.10.1)(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0): 3961 3999 dependencies: 3962 4000 '@floating-ui/core': 1.7.3 3963 4001 '@floating-ui/dom': 1.7.4 3964 4002 '@internationalized/date': 3.10.1 3965 4003 esm-env: 1.2.2 3966 - runed: 0.35.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 4004 + runed: 0.35.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 3967 4005 svelte: 5.48.0 3968 - svelte-toolbelt: 0.10.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 4006 + svelte-toolbelt: 0.10.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 3969 4007 tabbable: 6.4.0 3970 4008 transitivePeerDependencies: 3971 4009 - '@sveltejs/kit' ··· 3982 4020 brace-expansion@2.0.2: 3983 4021 dependencies: 3984 4022 balanced-match: 1.0.2 4023 + 4024 + bun-types@1.3.6: 4025 + dependencies: 4026 + '@types/node': 25.0.10 3985 4027 3986 4028 callsites@3.1.0: {} 3987 4029 ··· 4574 4616 4575 4617 natural-compare@1.4.0: {} 4576 4618 4619 + node-gyp-build@4.8.4: {} 4620 + 4577 4621 nth-check@2.1.1: 4578 4622 dependencies: 4579 4623 boolbase: 1.0.0 ··· 4870 4914 esm-env: 1.2.2 4871 4915 svelte: 5.48.0 4872 4916 4873 - runed@0.35.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0): 4917 + runed@0.35.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0): 4874 4918 dependencies: 4875 4919 dequal: 2.0.3 4876 4920 esm-env: 1.2.2 4877 4921 lz-string: 1.5.0 4878 4922 svelte: 5.48.0 4879 4923 optionalDependencies: 4880 - '@sveltejs/kit': 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)) 4924 + '@sveltejs/kit': 2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)) 4881 4925 4882 4926 sade@1.8.1: 4883 4927 dependencies: ··· 5001 5045 runed: 0.28.0(svelte@5.48.0) 5002 5046 svelte: 5.48.0 5003 5047 5004 - svelte-toolbelt@0.10.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0): 5048 + svelte-toolbelt@0.10.6(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0): 5005 5049 dependencies: 5006 5050 clsx: 2.1.1 5007 - runed: 0.35.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 5051 + runed: 0.35.1(@sveltejs/kit@2.50.1(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.48.0)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0)(typescript@5.9.3)(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)))(svelte@5.48.0) 5008 5052 style-to-object: 1.0.14 5009 5053 svelte: 5.48.0 5010 5054 transitivePeerDependencies: ··· 5104 5148 5105 5149 ultrahtml@1.6.0: {} 5106 5150 5151 + undici-types@7.16.0: {} 5152 + 5107 5153 undici@7.18.2: {} 5108 5154 5109 5155 undici@7.19.0: {} ··· 5136 5182 5137 5183 util-deprecate@1.0.2: {} 5138 5184 5139 - vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2): 5185 + vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2): 5140 5186 dependencies: 5141 5187 esbuild: 0.27.2 5142 5188 fdir: 6.5.0(picomatch@4.0.3) ··· 5145 5191 rollup: 4.56.0 5146 5192 tinyglobby: 0.2.15 5147 5193 optionalDependencies: 5194 + '@types/node': 25.0.10 5148 5195 fsevents: 2.3.3 5149 5196 jiti: 2.6.1 5150 5197 lightningcss: 1.30.2 5151 5198 5152 - vitefu@1.1.1(vite@7.3.1(jiti@2.6.1)(lightningcss@1.30.2)): 5199 + vitefu@1.1.1(vite@7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2)): 5153 5200 optionalDependencies: 5154 - vite: 7.3.1(jiti@2.6.1)(lightningcss@1.30.2) 5201 + vite: 7.3.1(@types/node@25.0.10)(jiti@2.6.1)(lightningcss@1.30.2) 5155 5202 5156 5203 w3c-keyname@2.2.8: {} 5157 5204
+24
src/lib/atproto/methods.ts
··· 70 70 return response.data; 71 71 } 72 72 73 + export async function getAuthorFeed(data?: { 74 + did?: Did; 75 + client?: Client; 76 + filter?: string; 77 + limit?: number; 78 + }) { 79 + data ??= {}; 80 + data.did ??= user.did; 81 + 82 + if (!data.did) throw new Error('Error getting detailed profile: no did'); 83 + 84 + data.client ??= new Client({ 85 + handler: simpleFetchHandler({ service: 'https://public.api.bsky.app' }) 86 + }); 87 + 88 + const response = await data.client.get('app.bsky.feed.getAuthorFeed', { 89 + params: { actor: data.did, filter: data.filter ?? 'posts_with_media', limit: data.limit || 100 } 90 + }); 91 + 92 + if (!response.ok) return; 93 + 94 + return response.data; 95 + } 96 + 73 97 export async function getClient({ did }: { did: Did }) { 74 98 const pds = await getPDS(did); 75 99 if (!pds) throw new Error('PDS not found');
+4 -9
src/lib/cards/BlueskyMediaCard/CreateBlueskyMediaCardModal.svelte
··· 2 2 import { Button, Input, Label, Modal, Subheading } from '@foxui/core'; 3 3 import type { CreationModalComponentProps } from '../types'; 4 4 import { onMount } from 'svelte'; 5 - import { AtpBaseClient } from '@atproto/api'; 6 5 import { getDidContext } from '$lib/website/context'; 6 + import { getAuthorFeed } from '$lib/atproto/methods'; 7 7 8 8 let { item = $bindable(), oncreate, oncancel }: CreationModalComponentProps = $props(); 9 9 ··· 14 14 let isLoading = $state(true); 15 15 16 16 onMount(async () => { 17 - const agent = new AtpBaseClient({ service: 'https://api.bsky.app' }); 18 - const authorFeed = await agent.app.bsky.feed.getAuthorFeed({ 19 - actor: did, 20 - filter: 'posts_with_media', 21 - limit: 100 22 - }); 23 - 24 - for (let post of authorFeed.data.feed) { 17 + const authorFeed = await getAuthorFeed({did}) 18 + 19 + for (let post of authorFeed?.feed ?? []) { 25 20 for (let image of post.post.embed?.images ?? []) { 26 21 mediaList.push(image); 27 22 }
+4 -8
src/lib/cards/BlueskyPostCard/index.ts
··· 1 - import { AtpBaseClient } from '@atproto/api'; 2 1 import type { CardDefinition } from '../types'; 3 2 import BlueskyPostCard from './BlueskyPostCard.svelte'; 4 3 import SidebarItemBlueskyPostCard from './SidebarItemBlueskyPostCard.svelte'; 4 + import { getAuthorFeed } from '$lib/atproto/methods'; 5 5 6 6 export const BlueskyPostCardDefinition = { 7 7 type: 'latestPost', ··· 15 15 }, 16 16 sidebarComponent: SidebarItemBlueskyPostCard, 17 17 loadData: async (items, { did }) => { 18 - const agent = new AtpBaseClient({ service: 'https://api.bsky.app' }); 19 - const authorFeed = await agent.app.bsky.feed.getAuthorFeed({ 20 - actor: did, 21 - filter: 'posts_no_replies', 22 - limit: 2 23 - }); 24 - return JSON.parse(JSON.stringify(authorFeed.data)); 18 + const authorFeed = await getAuthorFeed({ did, filter: 'posts_no_replies', limit: 2 }); 19 + 20 + return JSON.parse(JSON.stringify(authorFeed)); 25 21 }, 26 22 minW: 4 27 23 } as CardDefinition & { type: 'latestPost' };
+2 -3
src/lib/cards/PhotoGalleryCard/index.ts
··· 1 1 import type { CardDefinition } from '../types'; 2 2 import { getRecord, listRecords, parseUri } from '$lib/atproto'; 3 3 import PhotoGalleryCard from './PhotoGalleryCard.svelte'; 4 - import type { Record as ListRecord } from '@atproto/api/dist/client/types/com/atproto/repo/listRecords'; 5 4 6 5 export const PhotoGalleryCardDefinition = { 7 6 type: 'photoGallery', ··· 17 16 card.mobileH = 6; 18 17 }, 19 18 loadData: async (items) => { 20 - const itemsData: Record<string, ListRecord[]> = {}; 19 + const itemsData: Record<string, unknown[]> = {}; 21 20 22 - const galleryItems: Record<string, ListRecord[] | undefined> = { 21 + const galleryItems: Record<string, unknown[] | undefined> = { 23 22 'social.grain.gallery.item': undefined 24 23 }; 25 24
+3 -3
src/lib/cards/SpecialCards/UpdatedBlentos/UpdatedBlentosCard.svelte
··· 1 1 <script lang="ts"> 2 2 import type { ContentComponentProps } from '$lib/cards/types'; 3 3 import { getAdditionalUserData } from '$lib/website/context'; 4 - import type { ProfileViewDetailed } from '@atproto/api/dist/client/types/app/bsky/actor/defs'; 4 + import type { AppBskyActorDefs } from '@atcute/bluesky'; 5 5 6 6 let { item }: ContentComponentProps = $props(); 7 7 8 8 const data = getAdditionalUserData(); 9 9 // svelte-ignore state_referenced_locally 10 - const profiles = data[item.cardType] as ProfileViewDetailed[]; 10 + const profiles = data[item.cardType] as AppBskyActorDefs.ProfileViewDetailed[]; 11 11 12 12 $inspect(profiles); 13 13 </script> ··· 27 27 alt="" 28 28 loading="lazy" 29 29 /> 30 - <div class="text-md line-clamp-1 text-center font-bold max-w-full"> 30 + <div class="text-md line-clamp-1 max-w-full text-center font-bold"> 31 31 {profile.displayName || profile.handle} 32 32 </div> 33 33 </a>
+2 -2
src/lib/cards/StatusphereCard/index.ts
··· 4 4 import type { CardDefinition } from '../types'; 5 5 import { listRecords, putRecord } from '$lib/atproto'; 6 6 import StatusphereCard from './StatusphereCard.svelte'; 7 - import { TID } from '@atproto/common-web'; 8 7 import EditStatusphereCard from './EditStatusphereCard.svelte'; 9 8 import icons from './icons.json'; 9 + import * as TID from '@atcute/tid'; 10 10 11 11 export const StatusphereCardDefinition = { 12 12 type: 'statusphere', ··· 28 28 upload: async (item) => { 29 29 if (item.cardData.hasUpdate) { 30 30 await putRecord({ 31 - rkey: TID.nextStr(), 31 + rkey: TID.now(), 32 32 collection: 'xyz.statusphere.status', 33 33 record: { 34 34 status: item.cardData.emoji,
+2 -2
src/lib/components/bluesky-post/BlueskyPost.svelte
··· 1 1 <script lang="ts"> 2 - import type { FeedViewPost } from '@atproto/api/dist/client/types/app/bsky/feed/defs'; 3 2 import { Post } from '../post'; 4 3 import { blueskyPostToPostData } from '.'; 5 4 import type { Snippet } from 'svelte'; 5 + import type { PostView } from '@atcute/bluesky/types/app/feed/defs'; 6 6 7 7 let { 8 8 feedViewPost, 9 9 children, 10 10 showLogo = false, 11 11 ...restProps 12 - }: { feedViewPost?: FeedViewPost; children?: Snippet; showLogo?: boolean } = $props(); 12 + }: { feedViewPost?: PostView; children?: Snippet; showLogo?: boolean } = $props(); 13 13 14 14 const postData = $derived(feedViewPost ? blueskyPostToPostData(feedViewPost) : undefined); 15 15 </script>
+35 -22
src/lib/components/bluesky-post/index.ts
··· 1 - import { RichText } from '@atproto/api'; 2 1 import type { PostData, PostEmbed } from '../post'; 3 - import type { PostView } from '@atproto/api/dist/client/types/app/bsky/feed/defs'; 2 + import type { PostView } from '@atcute/bluesky/types/app/feed/defs'; 3 + import { segmentize, type Facet, type RichtextSegment } from '@atcute/bluesky-richtext-segmenter'; 4 4 5 5 function blueskyEmbedTypeToEmbedType(type: string) { 6 6 switch (type) { ··· 48 48 // } 49 49 // : undefined, 50 50 author: { 51 - displayName: post.author.displayName, 51 + displayName: post.author.displayName || '', 52 52 handle: post.author.handle, 53 53 avatar: post.author.avatar, 54 54 href: `${baseUrl}/profile/${post.author.did}` ··· 56 56 replyCount: post.replyCount ?? 0, 57 57 repostCount: post.repostCount ?? 0, 58 58 likeCount: post.likeCount ?? 0, 59 - createdAt: post.record.createdAt ?? 0, 59 + createdAt: post.record.createdAt as string, 60 60 61 61 embed: post.embed 62 62 ? ({ ··· 91 91 }; 92 92 } 93 93 94 - // eslint-disable-next-line @typescript-eslint/no-explicit-any 95 - export function blueskyPostToHTML(post: any, baseUrl: string = 'https://bsky.app') { 96 - if (!post?.record) { 97 - return ''; 94 + const renderSegment = (segment: RichtextSegment, baseUrl: string) => { 95 + const { text, features } = segment; 96 + 97 + if (!features) { 98 + return `<span>${text}</span>`; 98 99 } 99 - const rt = new RichText(post.record); 100 - let html = ''; 100 + 101 + // segments can have multiple features, use the first one 102 + const feature = features[0]; 101 103 102 104 const createLink = (href: string, text: string) => { 103 - return `<a target="_blank" rel="noopener noreferrer nofollow" href="${encodeURI(href)}">${encodeURI(text)}</a>`; 105 + return `<a target="_blank" rel="noopener noreferrer nofollow" href="${encodeURI(href)}">${text}</a>`; 104 106 }; 105 107 106 - for (const segment of rt.segments()) { 107 - if (!segment) continue; 108 - if (segment.isLink() && segment.link?.uri) { 109 - html += createLink(segment.link?.uri, segment.text); 110 - } else if (segment.isMention() && segment.mention?.did) { 111 - html += createLink(`${baseUrl}/profile/${segment.mention?.did}`, segment.text); 112 - } else if (segment.isTag() && segment.tag?.tag) { 113 - html += createLink(`${baseUrl}/hashtag/${segment.tag?.tag}`, segment.text); 114 - } else { 115 - html += segment.text; 116 - } 108 + switch (feature.$type) { 109 + case 'app.bsky.richtext.facet#mention': 110 + return createLink(`${baseUrl}/profile/${segment.handle}`, segment.text); 111 + case 'app.bsky.richtext.facet#link': 112 + return createLink(feature.uri, segment.text); 113 + case 'app.bsky.richtext.facet#tag': 114 + return createLink(`${baseUrl}/hashtag/${segment.tag}`, segment.text); 115 + default: 116 + return `<span>${text}</span>`; 117 117 } 118 + };; 119 + 120 + const RichText = ({ text, facets }: { text: string; facets?: Facet[] }, baseUrl: string) => { 121 + const segments = segmentize(text, facets); 122 + return segments.map((v) => renderSegment(v, baseUrl)).join(''); 123 + }; 124 + 125 + export function blueskyPostToHTML(post: PostView, baseUrl: string = 'https://bsky.app') { 126 + if (!post?.record) { 127 + return ''; 128 + } 129 + 130 + const html = RichText({ text: post.record.text, facets: post.record.facets }, baseUrl); 118 131 119 132 return html.replace(/\n/g, '<br>'); 120 133 }
+2 -2
src/lib/helper.ts
··· 3 3 import { CardDefinitionsByType } from './cards'; 4 4 import { deleteRecord, putRecord } from '$lib/atproto'; 5 5 import { toast } from '@foxui/core'; 6 - import { TID } from '@atproto/common-web'; 6 + import * as TID from '@atcute/tid'; 7 7 8 8 export function clamp(value: number, min: number, max: number): number { 9 9 return Math.min(Math.max(value, min), max); ··· 498 498 499 499 export function createEmptyCard(page: string) { 500 500 return { 501 - id: TID.nextStr(), 501 + id: TID.now(), 502 502 x: 0, 503 503 y: 0, 504 504 w: 2,
+5 -4
src/lib/types.ts
··· 1 - import type { At } from '@atcute/client/lexicons'; 2 - import type { ProfileViewDetailed } from '@atproto/api/dist/client/types/app/bsky/actor/defs'; 1 + import type { Blob } from '@atcute/lexicons'; 2 + import type { AppBskyActorDefs } from '@atcute/bluesky'; 3 3 4 4 export type Item = { 5 5 id: string; ··· 39 39 url?: string; 40 40 name?: string; 41 41 description?: string; 42 - icon?: At.Blob; 42 + icon?: Blob; 43 43 preferences?: { 44 44 /** 45 45 * @deprecated ··· 47 47 * use hideProfileSection instead 48 48 */ 49 49 hideProfile?: boolean; 50 + 50 51 // use this instead 51 52 hideProfileSection?: boolean; 52 53 }; 53 54 } 54 55 | undefined; 55 - profile: ProfileViewDetailed; 56 + profile: AppBskyActorDefs.ProfileViewDetailed; 56 57 57 58 additionalData: Record<string, unknown>; 58 59 updatedAt: number;
+6 -7
src/lib/website/load.ts
··· 1 1 import { getDetailedProfile, listRecords, resolveHandle, parseUri } from '$lib/atproto'; 2 - import type { Record as ListRecord } from '@atproto/api/dist/client/types/com/atproto/repo/listRecords'; 3 2 import { CardDefinitionsByType } from '$lib/cards'; 4 3 import type { Item, UserCache, WebsiteData } from '$lib/types'; 5 4 import { compactItems, fixAllCollisions } from '$lib/helper'; ··· 31 30 32 31 result.page = 'blento.' + page; 33 32 34 - result.publication = (result.publications as ListRecord[]).find( 33 + result.publication = (result.publications as Awaited<ReturnType<typeof listRecords>>).find( 35 34 (v) => parseUri(v.uri).rkey === result.page 36 35 )?.value; 37 36 ··· 65 64 66 65 const cards = await listRecords({ did, collection: 'app.blento.card' }).catch(() => { 67 66 console.error('error getting records for collection app.blento.card'); 68 - return [] as ListRecord[]; 67 + return [] as Awaited<ReturnType<typeof listRecords>>; 69 68 }); 70 69 71 70 const publications = await listRecords({ did, collection: 'site.standard.publication' }).catch( 72 71 () => { 73 72 console.error('error getting records for collection site.standard.publication'); 74 - return [] as ListRecord[]; 73 + return [] as Awaited<ReturnType<typeof listRecords>>; 75 74 } 76 75 ); 77 76 ··· 128 127 await cache?.put?.(handle, stringifiedResult); 129 128 130 129 const parsedResult = JSON.parse(stringifiedResult); 131 - parsedResult.publication = (parsedResult.publications as ListRecord[]).find( 132 - (v) => parseUri(v.uri).rkey === parsedResult.page 133 - )?.value; 130 + parsedResult.publication = ( 131 + parsedResult.publications as Awaited<ReturnType<typeof listRecords>> 132 + ).find((v) => parseUri(v.uri).rkey === parsedResult.page)?.value; 134 133 135 134 delete parsedResult['publications']; 136 135
+2 -2
src/routes/all/+page.server.ts
··· 2 2 import type { UserCache, WebsiteData } from '$lib/types.js'; 3 3 import { loadData } from '$lib/website/load'; 4 4 import type { Handle } from '@atcute/lexicons'; 5 - import type { ProfileViewDetailed } from '@atproto/api/dist/client/types/app/bsky/actor/defs.js'; 5 + import type { AppBskyActorDefs } from '@atcute/bluesky'; 6 6 7 7 export async function load({ platform }) { 8 8 const cache = platform?.env?.USER_DATA_CACHE; 9 9 10 10 const list = await cache?.list(); 11 11 12 - const profiles: ProfileViewDetailed[] = []; 12 + const profiles: AppBskyActorDefs.ProfileViewDetailed[] = []; 13 13 for (const value of list?.keys ?? []) { 14 14 // check if at least one card 15 15 const result = await cache?.get(value.name);