Bluesky app fork with some witchin' additions 💫
0
fork

Configure Feed

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

fix: replicate legacy login agent for oauth

fixes embeds not getting thumbnails and such!

xan.lol 1791592e 343ad297

+115 -5
+81
src/state/session/__tests__/oauth-agent-test.ts
··· 1 + import {type OAuthSession} from '@atproto/oauth-client-browser' 2 + import {describe, expect, it, jest} from '@jest/globals' 3 + 4 + jest.mock('../agent', () => ({ 5 + sessionAccountToSession(account: {did: string; handle: string}) { 6 + return { 7 + accessJwt: '', 8 + did: account.did, 9 + emailAuthFactor: false, 10 + emailConfirmed: false, 11 + handle: account.handle, 12 + refreshJwt: '', 13 + active: true, 14 + } 15 + }, 16 + })) 17 + 18 + jest.mock('../moderation', () => ({ 19 + configureModerationForAccount() { 20 + return Promise.resolve() 21 + }, 22 + })) 23 + 24 + jest.mock('../oauth-web-client', () => ({ 25 + getWebOAuthClient() { 26 + throw new Error('not used in this test') 27 + }, 28 + })) 29 + 30 + import {OauthBskyAppAgent} from '../oauth-agent' 31 + 32 + function createOAuthSession(): OAuthSession { 33 + return { 34 + did: 'did:plc:alice', 35 + serverMetadata: { 36 + issuer: 'https://bsky.social', 37 + }, 38 + fetchHandler() { 39 + throw new Error('not implemented in test') 40 + }, 41 + } as unknown as OAuthSession 42 + } 43 + 44 + describe('OauthBskyAppAgent', () => { 45 + it('preserves service and dispatch urls when cloned and proxied', async () => { 46 + const agent = new OauthBskyAppAgent(createOAuthSession()) 47 + 48 + expect(agent.serviceUrl.toString()).toBe('https://bsky.social/') 49 + expect(agent.dispatchUrl.toString()).toBe('https://bsky.social/') 50 + 51 + await agent.prepare( 52 + { 53 + service: 'https://bsky.social', 54 + did: 'did:plc:alice', 55 + handle: 'alice.test', 56 + active: true, 57 + emailConfirmed: false, 58 + emailAuthFactor: false, 59 + pdsUrl: 'https://alice.pds.example', 60 + isSelfHosted: false, 61 + isOauthSession: true, 62 + }, 63 + Promise.resolve(), 64 + Promise.resolve(), 65 + ) 66 + 67 + expect(agent.serviceUrl.toString()).toBe('https://bsky.social/') 68 + expect(agent.pdsUrl?.toString()).toBe('https://alice.pds.example/') 69 + expect(agent.dispatchUrl.toString()).toBe('https://alice.pds.example/') 70 + 71 + const proxied = agent.withProxy('bsky_fg', 'did:plc:feed') 72 + expect(proxied).toBeInstanceOf(OauthBskyAppAgent) 73 + expect(proxied.serviceUrl.toString()).toBe('https://bsky.social/') 74 + expect(proxied.dispatchUrl.toString()).toBe('https://alice.pds.example/') 75 + 76 + const pdsAgent = agent.cloneWithoutProxy() 77 + expect(pdsAgent.proxy).toBeUndefined() 78 + expect(pdsAgent.serviceUrl.toString()).toBe('https://bsky.social/') 79 + expect(pdsAgent.dispatchUrl.toString()).toBe('https://alice.pds.example/') 80 + }) 81 + })
+33 -4
src/state/session/oauth-agent.ts
··· 108 108 } 109 109 110 110 export class OauthBskyAppAgent extends Agent { 111 + readonly sessionManager: OAuthSession 111 112 session?: AtpSessionData 112 - dispatchUrl?: string 113 + private _serviceUrl: URL 114 + private _pdsUrl?: URL 113 115 114 116 constructor(session: OAuthSession) { 115 117 super(session) 118 + this.sessionManager = session 119 + this._serviceUrl = new URL(session.serverMetadata.issuer) 120 + } 121 + 122 + clone(): this { 123 + const cloned = this.copyInto(new OauthBskyAppAgent(this.sessionManager)) 124 + cloned.session = this.session 125 + cloned._serviceUrl = this._serviceUrl 126 + cloned._pdsUrl = this._pdsUrl 127 + return cloned as this 128 + } 129 + 130 + get serviceUrl() { 131 + return this._serviceUrl 132 + } 133 + 134 + get pdsUrl() { 135 + return this._pdsUrl 136 + } 137 + 138 + get dispatchUrl() { 139 + return this.pdsUrl || this.serviceUrl 140 + } 141 + 142 + /** @deprecated use {@link serviceUrl} instead */ 143 + get service() { 144 + return this.serviceUrl 116 145 } 117 146 118 147 async prepare( ··· 121 150 moderation: Promise<void>, 122 151 ) { 123 152 this.session = sessionAccountToSession(account) 124 - this.dispatchUrl = account.pdsUrl 153 + this._serviceUrl = new URL(account.service) 154 + this._pdsUrl = account.pdsUrl ? new URL(account.pdsUrl) : undefined 125 155 this.configureProxy(BLUESKY_PROXY_HEADER.get()) 126 156 127 157 await Promise.all([gates, moderation]) ··· 132 162 dispose() {} 133 163 134 164 cloneWithoutProxy(): OauthBskyAppAgent { 135 - const cloned = new OauthBskyAppAgent(this.sessionManager as OAuthSession) 136 - cloned.session = this.session 165 + const cloned = this.clone() 137 166 cloned.configureProxy(null) 138 167 return cloned 139 168 }