mirror of
https://github.com/catlog22/Claude-Code-Workflow.git
synced 2026-02-10 02:24:35 +08:00
- Implemented share token creation and revocation for CLI sessions. - Added a new page for viewing shared CLI sessions with SSE support. - Introduced hooks for fetching and managing CLI session shares. - Enhanced the IssueTerminalTab component to handle share tokens and display active shares. - Updated API routes to support fetching and revoking share tokens. - Added unit tests for the CLI session share manager and rate limiter. - Updated localization files to include new strings for sharing functionality.
72 lines
2.1 KiB
JavaScript
72 lines
2.1 KiB
JavaScript
/**
|
|
* Unit tests for RateLimiter
|
|
*/
|
|
|
|
import { describe, it } from 'node:test';
|
|
import assert from 'node:assert/strict';
|
|
|
|
const limiterUrl = new URL('../dist/core/services/rate-limiter.js', import.meta.url).href;
|
|
|
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
let mod;
|
|
|
|
describe('RateLimiter', async () => {
|
|
mod = await import(limiterUrl);
|
|
|
|
it('enforces limits within a window', () => {
|
|
const limiter = new mod.RateLimiter({ limit: 3, windowMs: 60_000 });
|
|
|
|
const r1 = limiter.consume('k');
|
|
const r2 = limiter.consume('k');
|
|
const r3 = limiter.consume('k');
|
|
const r4 = limiter.consume('k');
|
|
|
|
assert.equal(r1.ok, true);
|
|
assert.equal(r1.remaining, 2);
|
|
assert.equal(typeof r1.resetAt, 'number');
|
|
|
|
assert.equal(r2.ok, true);
|
|
assert.equal(r2.remaining, 1);
|
|
assert.equal(r2.resetAt, r1.resetAt);
|
|
|
|
assert.equal(r3.ok, true);
|
|
assert.equal(r3.remaining, 0);
|
|
assert.equal(r3.resetAt, r1.resetAt);
|
|
|
|
assert.equal(r4.ok, false);
|
|
assert.equal(r4.remaining, 0);
|
|
assert.equal(r4.resetAt, r1.resetAt);
|
|
});
|
|
|
|
it('handles costs and does not penalize impossible costs', () => {
|
|
const limiter = new mod.RateLimiter({ limit: 3, windowMs: 60_000 });
|
|
|
|
// Cost is floored; negative cost becomes 0
|
|
assert.equal(limiter.consume('k2', -5).ok, true);
|
|
assert.equal(limiter.consume('k2').remaining, 2);
|
|
|
|
// Cost larger than limit returns not ok but bucket remains full.
|
|
const tooMuch = limiter.consume('k3', 10);
|
|
assert.equal(tooMuch.ok, false);
|
|
assert.equal(tooMuch.remaining, 0);
|
|
assert.equal(limiter.consume('k3').remaining, 2);
|
|
});
|
|
|
|
it('resets after the window expires', async () => {
|
|
const limiter = new mod.RateLimiter({ limit: 1, windowMs: 50 });
|
|
|
|
assert.equal(limiter.consume('k').ok, true);
|
|
assert.equal(limiter.consume('k').ok, false);
|
|
|
|
await new Promise((resolve) => setTimeout(resolve, 70));
|
|
|
|
assert.equal(limiter.consume('k').ok, true);
|
|
});
|
|
|
|
it('supports a limit of 0', () => {
|
|
const limiter = new mod.RateLimiter({ limit: 0, windowMs: 1_000 });
|
|
assert.equal(limiter.consume('k').ok, false);
|
|
assert.equal(limiter.consume('k', 0).ok, true);
|
|
});
|
|
});
|