verae-edge-billing/tests/api-tokens.test.ts

94 lines
3.2 KiB
TypeScript

import request from 'supertest';
import { buildApp, DEFAULT_CUSTOMERS } from '../src/app';
import { InMemoryApiTokenRepo } from '../src/db/api-token-repo';
import { InMemoryCustomerRepo } from '../src/auth';
import { InMemorySessionRepo } from '../src/accounts';
describe('xVerae- long-lived API tokens', () => {
const prevAllowMock = process.env.ALLOW_MOCK_CERTS;
const prevUpstream = process.env.ZAPPIER_UPSTREAM;
beforeAll(() => {
delete process.env.ZAPPIER_UPSTREAM;
process.env.ALLOW_MOCK_CERTS = 'true';
});
afterAll(() => {
if (prevAllowMock === undefined) delete process.env.ALLOW_MOCK_CERTS;
else process.env.ALLOW_MOCK_CERTS = prevAllowMock;
if (prevUpstream === undefined) delete process.env.ZAPPIER_UPSTREAM;
else process.env.ZAPPIER_UPSTREAM = prevUpstream;
});
it('portal creates token once; stamp auth accepts xVerae- and Bearer', async () => {
const customers = new InMemoryCustomerRepo(
DEFAULT_CUSTOMERS.map((c) =>
c.id === 'cust_1'
? {
...c,
email: 'ada@example.com',
passwordHash:
// hashPassword('password12') — use signup instead
undefined,
}
: c,
),
);
const apiTokens = new InMemoryApiTokenRepo();
const sessions = new InMemorySessionRepo();
const { app } = buildApp({ customers, apiTokens, sessions });
const signup = await request(app).post('/portal/api/signup').send({
name: 'Ada Token',
email: 'ada-token@example.com',
password: 'password12',
});
expect(signup.status).toBe(201);
const portalToken = signup.body.token as string;
const created = await request(app)
.post('/portal/api/tokens')
.set('authorization', `Bearer ${portalToken}`)
.send({ name: 'ci' });
expect(created.status).toBe(201);
expect(created.body.token).toMatch(/^xVerae-/);
const secret = created.body.token as string;
const listed = await request(app)
.get('/portal/api/tokens')
.set('authorization', `Bearer ${portalToken}`);
expect(listed.status).toBe(200);
expect(listed.body.tokens).toHaveLength(1);
expect(listed.body.tokens[0].token).toBeUndefined();
const viaHeader = await request(app)
.post('/v1/timestamp')
.set('x-api-key', secret)
.send({ sha256: 'a'.repeat(64) });
expect([200, 202]).toContain(viaHeader.status);
const viaBearer = await request(app)
.post('/v1/timestamp')
.set('authorization', `Bearer ${secret}`)
.send({ sha256: 'b'.repeat(64) });
expect([200, 202]).toContain(viaBearer.status);
const revoke = await request(app)
.delete(`/portal/api/tokens/${created.body.id}`)
.set('authorization', `Bearer ${portalToken}`);
expect(revoke.status).toBe(200);
const denied = await request(app)
.post('/v1/timestamp')
.set('x-api-key', secret)
.send({ sha256: 'c'.repeat(64) });
expect(denied.status).toBe(401);
});
it('legacy key-ada still works', async () => {
const { app } = buildApp();
const res = await request(app)
.post('/v1/timestamp')
.set('x-api-key', 'key-ada')
.send({ sha256: 'd'.repeat(64) });
expect([200, 202]).toContain(res.status);
});
});