UNPKG

@daiso-tech/core

Version:

The library offers flexible, framework-agnostic solutions for modern web applications, built on adaptable components that integrate seamlessly with popular frameworks like Next Js.

80 lines 3.51 kB
/** * @module RateLimiter */ import {} from "../../../../backoff-policies/contracts/_module.js"; import { exponentialBackoff } from "../../../../backoff-policies/implementations/_module.js"; import {} from "../../../../execution-context/contracts/_module.js"; import {} from "../../../../rate-limiter/contracts/_module.js"; import { InternalRateLimiterPolicy, } from "../../../../rate-limiter/implementations/adapters/database-rate-limiter-adapter/internal-rate-limiter-policy.js"; import { RateLimiterStateManager } from "../../../../rate-limiter/implementations/adapters/database-rate-limiter-adapter/rate-limiter-state-manager.js"; import { RateLimiterStorage } from "../../../../rate-limiter/implementations/adapters/database-rate-limiter-adapter/rate-limiter-storage.js"; import { FixedWindowLimiter } from "../../../../rate-limiter/implementations/policies/_module.js"; import { TimeSpan } from "../../../../time-span/implementations/_module.js"; /** * IMPORT_PATH: `"@daiso-tech/core/rate-limiter/database-rate-limiter-adapter"` * @group Adapters */ export class DatabaseRateLimiterAdapter { rateLimiterStorage; rateLimiterStateManager; /** * @example * ```ts * import { DatabaseRateLimiterAdapter } from "@daiso-tech/core/rate-limiter/database-rate-limiter-adapter"; * import { MemoryRateLimiterStorageAdapter } from "@daiso-tech/core/rate-limiter/memory-rate-limiter-storage-adapter"; * * const rateLimiterStorageAdapter = new MemoryRateLimiterStorageAdapter(); * const rateLimiterAdapter = new DatabaseRateLimiterAdapter({ * adapter: rateLimiterStorageAdapter * }); * ``` */ constructor(settings) { const { adapter, backoffPolicy = exponentialBackoff(), rateLimiterPolicy = new FixedWindowLimiter(), } = settings; const internalRateLimiterPolicy = new InternalRateLimiterPolicy(rateLimiterPolicy); this.rateLimiterStorage = new RateLimiterStorage({ adapter: adapter, rateLimiterPolicy: internalRateLimiterPolicy, backoffPolicy, }); this.rateLimiterStateManager = new RateLimiterStateManager(internalRateLimiterPolicy, backoffPolicy); } async getState(context, key) { const state = await this.rateLimiterStorage.find(context, key); if (state === null) { return null; } return { success: state.success, attempt: state.attempt, resetTime: TimeSpan.fromDateRange({ end: state.resetTime, }), }; } async updateState(context, key, limit) { const currentDate = new Date(); const track = this.rateLimiterStateManager.track(currentDate); const updateState = this.rateLimiterStateManager.updateState(limit, currentDate); const state = await this.rateLimiterStorage.atomicUpdate({ context, key, update: (prevState) => { const newState1 = track(prevState); const newState2 = updateState(newState1); return newState2; }, }); return { success: state.success, attempt: state.attempt, resetTime: TimeSpan.fromDateRange({ end: state.resetTime, }), }; } async reset(context, key) { await this.rateLimiterStorage.remove(context, key); } } //# sourceMappingURL=database-rate-limiter-adapter.js.map