testRefreshesNameTheirAccount

tcmts.atproto.test.testRefreshesNameTheirAccount · #gcln2u55 · term

A refreshed token is taken only if the answer names the account it's for.

import { refreshSession } from "#codebase/tcmts/atproto";
import type { OAuthSession } from "#codebase/tcmts/atproto";
import assert from "node:assert/strict";
import crypto from "node:crypto";
import fs from "node:fs";
import http from "node:http";
import os from "node:os";
import path from "node:path";

export const testRefreshesNameTheirAccount = async () => {
  let sub: string | undefined;
  const server = http.createServer((_req, res) => {
    res.writeHead(200, { "content-type": "application/json" });
    res.end(
      JSON.stringify({
        access_token: "new",
        token_type: "DPoP",
        expires_in: 60,
        ...(sub ? { sub } : {}),
      }),
    );
  });
  await new Promise<void>((r) => server.listen(0, "127.0.0.1", r));
  const was = process.env.XDG_CONFIG_HOME;
  process.env.XDG_CONFIG_HOME = fs.mkdtempSync(path.join(os.tmpdir(), "refresh "));
  try {
    const s: OAuthSession = {
      did: "did:plc:me",
      pds: "https://pds.example",
      issuer: "https://pds.example",
      tokenEndpoint: `http://127.0.0.1:${(server.address() as { port: number }).port}/token`,
      clientId: "http://localhost",
      dpopKey: crypto
        .generateKeyPairSync("ec", { namedCurve: "P-256" })
        .privateKey.export({ format: "jwk" }),
      accessToken: "old",
      refreshToken: "r",
      expiresAt: 0,
      scope: "atproto",
    };
    assert.equal(await refreshSession({ ...s }), false, "an answer naming no one");
    sub = "did:plc:someone-else";
    assert.equal(await refreshSession({ ...s }), false, "an answer naming someone else");
    sub = "did:plc:me";
    assert.equal(await refreshSession(s), true);
    assert.equal(s.accessToken, "new");
  } finally {
    server.close();
    if (was === undefined) delete process.env.XDG_CONFIG_HOME;
    else process.env.XDG_CONFIG_HOME = was;
  }
}

uses