Live video on the AT Protocol
79
fork

Configure Feed

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

at v0.7.32 122 lines 3.5 kB view raw
1import fs from "node:fs/promises"; 2import os from "node:os"; 3import path from "node:path"; 4 5import { Secp256k1Keypair, randomStr } from "@atproto/crypto"; 6import * as pds from "@atproto/pds"; 7 8import getPort from "get-port"; 9import * as ui8 from "uint8arrays"; 10 11import { ADMIN_PASSWORD, JWT_SECRET } from "./constants.js"; 12 13export interface PdsServerOptions extends Partial<pds.ServerEnvironment> { 14 didPlcUrl: string; 15} 16 17export interface AdditionalPdsContext { 18 dataDirectory: string; 19 blobstoreLoc: string; 20} 21 22export class TestPdsServer { 23 constructor( 24 public readonly server: pds.PDS, 25 public readonly url: string, 26 public readonly port: number, 27 public readonly additional: AdditionalPdsContext, 28 ) {} 29 30 static async create(config: PdsServerOptions): Promise<TestPdsServer> { 31 const plcRotationKey = await Secp256k1Keypair.create({ exportable: true }); 32 const plcRotationPriv = ui8.toString(await plcRotationKey.export(), "hex"); 33 const recoveryKey = (await Secp256k1Keypair.create()).did(); 34 35 const port = config.port || (await getPort()); 36 const url = `http://localhost:${port}`; 37 38 const blobstoreLoc = path.join(os.tmpdir(), randomStr(8, "base32")); 39 const dataDirectory = path.join(os.tmpdir(), randomStr(8, "base32")); 40 41 await fs.mkdir(dataDirectory, { recursive: true }); 42 43 const env: pds.ServerEnvironment = { 44 devMode: true, 45 port, 46 dataDirectory: dataDirectory, 47 blobstoreDiskLocation: blobstoreLoc, 48 recoveryDidKey: recoveryKey, 49 adminPassword: ADMIN_PASSWORD, 50 jwtSecret: JWT_SECRET, 51 serviceHandleDomains: [".test"], 52 bskyAppViewUrl: "https://appview.invalid", 53 bskyAppViewDid: "did:example:invalid", 54 bskyAppViewCdnUrlPattern: "http://cdn.appview.com/%s/%s/%s", 55 modServiceUrl: "https://moderator.invalid", 56 modServiceDid: "did:example:invalid", 57 plcRotationKeyK256PrivateKeyHex: plcRotationPriv, 58 inviteRequired: false, 59 disableSsrfProtection: true, 60 serviceName: "Development PDS", 61 // brandColor: "#ffcb1e", 62 errorColor: undefined, 63 logoUrl: 64 "https://uxwing.com/wp-content/themes/uxwing/download/animals-and-birds/bee-icon.png", 65 homeUrl: "https://bsky.social/", 66 termsOfServiceUrl: "https://bsky.social/about/support/tos", 67 privacyPolicyUrl: "https://bsky.social/about/support/privacy-policy", 68 supportUrl: "https://blueskyweb.zendesk.com/hc/en-us", 69 ...config, 70 }; 71 72 const cfg = pds.envToCfg(env); 73 const secrets = pds.envToSecrets(env); 74 75 const server = await pds.PDS.create(cfg, secrets); 76 77 await server.start(); 78 79 return new TestPdsServer(server, url, port, { 80 dataDirectory: dataDirectory, 81 blobstoreLoc: blobstoreLoc, 82 }); 83 } 84 85 get ctx(): pds.AppContext { 86 return this.server.ctx; 87 } 88 89 adminAuth(): string { 90 return ( 91 "Basic " + 92 ui8.toString( 93 ui8.fromString(`admin:${ADMIN_PASSWORD}`, "utf8"), 94 "base64pad", 95 ) 96 ); 97 } 98 99 adminAuthHeaders() { 100 return { 101 authorization: this.adminAuth(), 102 }; 103 } 104 105 jwtSecretKey() { 106 return pds.createSecretKeyObject(JWT_SECRET); 107 } 108 109 async processAll() { 110 await this.ctx.backgroundQueue.processAll(); 111 } 112 113 async close() { 114 await this.server.destroy(); 115 116 await fs.rm(this.additional.dataDirectory, { 117 recursive: true, 118 force: true, 119 }); 120 await fs.rm(this.additional.blobstoreLoc, { force: true }); 121 } 122}