an attempt to make a lightweight, easily self-hostable, scoped bluesky appview

quick fix and readme

rimar1337 efe3c430 ead18ca3

Changed files
+62 -5
utils
+6 -1
deno.lock
··· 10 10 "jsr:@std/fmt@1": "1.0.8", 11 11 "jsr:@std/fs@1": "1.0.19", 12 12 "jsr:@std/internal@^1.0.9": "1.0.10", 13 + "jsr:@std/jsonc@*": "1.0.2", 13 14 "jsr:@std/path@0.217": "0.217.0", 14 15 "jsr:@std/path@1": "1.1.1", 15 16 "jsr:@std/path@^1.1.1": "1.1.1", ··· 31 32 "npm:multiformats@*": "13.4.0", 32 33 "npm:quick-lru@*": "7.0.1", 33 34 "npm:vite@*": "7.1.3_@types+node@22.15.15_picomatch@4.0.3", 34 - "npm:web-did-resolver@*": "2.0.30" 35 + "npm:web-did-resolver@*": "2.0.30", 36 + "npm:zod@*": "3.25.46" 35 37 }, 36 38 "jsr": { 37 39 "@db/sqlite@0.11.1": { ··· 74 76 }, 75 77 "@std/internal@1.0.10": { 76 78 "integrity": "e3be62ce42cab0e177c27698e5d9800122f67b766a0bea6ca4867886cbde8cf7" 79 + }, 80 + "@std/jsonc@1.0.2": { 81 + "integrity": "909605dae3af22bd75b1cbda8d64a32cf1fd2cf6efa3f9e224aba6d22c0f44c7" 77 82 }, 78 83 "@std/path@0.217.0": { 79 84 "integrity": "1217cc25534bca9a2f672d7fe7c6f356e4027df400c0e85c0ef3e4343bc67d11",
+52 -2
readme.md
··· 48 48 49 49 example configuration is in the `config.jsonc.example` file 50 50 51 - expose your localhost to the web using a tunnel or something and use that url as the custom appview url 51 + ### Index Server 52 + start it by running 53 + ```sh 54 + deno task index 55 + ``` 56 + it should just work actually 57 + implemented xrpc routes for `#skylite_index` are: 58 + ```ts 59 + const indexServerRoutes = new Set([ 60 + "/xrpc/app.bsky.actor.getProfile", 61 + "/xrpc/app.bsky.actor.getProfiles", 62 + "/xrpc/app.bsky.feed.getActorFeeds", 63 + "/xrpc/app.bsky.feed.getFeedGenerator", 64 + "/xrpc/app.bsky.feed.getFeedGenerators", 65 + "/xrpc/app.bsky.feed.getPosts", 66 + "/xrpc/party.whey.app.bsky.feed.getActorLikesPartial", 67 + "/xrpc/party.whey.app.bsky.feed.getAuthorFeedPartial", 68 + "/xrpc/party.whey.app.bsky.feed.getLikesPartial", 69 + "/xrpc/party.whey.app.bsky.feed.getPostThreadPartial", 70 + "/xrpc/party.whey.app.bsky.feed.getQuotesPartial", 71 + "/xrpc/party.whey.app.bsky.feed.getRepostedByPartial", 72 + // i havent implemented these three yet 73 + /* 74 + app.bsky.graph.getLists // doesnt need to because theres no items[], and its self ProfileViewBasic 75 + app.bsky.graph.getList // needs to be Partial-ed (items[] union with ProfileViewRef) 76 + app.bsky.graph.getActorStarterPacks // maybe doesnt need to be Partial-ed because its self ProfileViewBasic 77 + */ 52 78 53 - this should work on any bluesky client that supports changing the appview URL (im using an unreleased custom fork for development) 79 + // and the last one is a stub because its pretty hard to do 80 + "/xrpc/party.whey.app.bsky.feed.getListFeedPartial", 81 + ]); 82 + ``` 54 83 55 84 there is no way to register users to be indexed by the server yet (either Index nor View servers) so you can just manually add your account to the `system.db` file for now 85 + 86 + ### View Server 87 + start it by running 88 + ```sh 89 + deno task view 90 + ``` 91 + expose your localhost to the web using a tunnel or something and use that url as the custom appview url 92 + 93 + this should work on any bluesky client that supports changing the appview URL (im using an unreleased custom fork for development) as the view server implements the `#bsky_appview` routes for compatibility with existing clients 94 + 95 + the view server has extra configurations that you need to understand. 96 + the view server hydrates content by calling other servers (either an `#skylite_index` or `#bsky_appview`) and so you need to write the order of which servers are prioritized first for resolving the hydration endpoints 97 + ```js 98 + // In order of which skylite index servers or bsky appviews to use first 99 + "indexPriority": [ 100 + "user#skylite_index", // user resolved skylite index server 101 + "did:web:backupindexserver.your.site#skylite_index", // a specific skylite index server 102 + "user#bsky_appview", // user resolved bsky appview 103 + "did:web:api.bsky.app#bsky_appview" // a specific bsky appview 104 + ] 105 + ``` 56 106 57 107 id say this project is like uhh ~20% done so not a lot of things you can do with this right now
+4 -2
utils/sharders.ts
··· 1 + import { config } from "../config.ts"; 2 + 1 3 function getShardId(params: URLSearchParams): string { 2 4 params.sort(); 3 5 return params.toString(); ··· 245 247 export class JetstreamManager extends ShardedConnectionManager<JetstreamParams> { 246 248 constructor(onMessage: (msg: any) => void) { 247 249 super( 248 - `${Deno.env.get("JETSTREAM_URL")}/subscribe`, 250 + `${config.jetstream}/subscribe`, 249 251 { wantedDids: 10000, wantedCollections: 100 }, 250 252 onMessage 251 253 ); ··· 255 257 export class SpacedustManager extends ShardedConnectionManager<SpacedustParams> { 256 258 constructor(onMessage: (msg: any) => void) { 257 259 super( 258 - `${Deno.env.get("SPACEDUST_URL")}/subscribe`, 260 + `${config.spacedust}/subscribe`, 259 261 { wantedSubjects: 100, wantedSubjectDids: 100, wantedSources: 100 }, 260 262 onMessage 261 263 );