2024-03-24 14:18:58 +01:00
|
|
|
import {LRUCache} from 'lru-cache';
|
|
|
|
import {Adapter, AdapterPayload} from "oidc-provider";
|
2024-03-23 07:38:23 +01:00
|
|
|
|
2024-03-24 14:18:58 +01:00
|
|
|
|
|
|
|
const options = {
|
|
|
|
max: 500,
|
|
|
|
|
|
|
|
// for use with tracking overall storage size
|
|
|
|
maxSize: 5000,
|
|
|
|
|
|
|
|
// how long to live in ms
|
|
|
|
ttl: 1000 * 60 * 5,
|
|
|
|
|
|
|
|
// return stale items before removing from cache?
|
|
|
|
allowStale: false,
|
|
|
|
|
|
|
|
updateAgeOnGet: false,
|
|
|
|
updateAgeOnHas: false,
|
|
|
|
}
|
|
|
|
|
|
|
|
const epochTime = (date = Date.now()) => Math.floor(date / 1000);
|
|
|
|
|
|
|
|
const storage = new LRUCache<string,AdapterPayload|string[]|string>(options);
|
|
|
|
|
|
|
|
function grantKeyFor(id: string) {
|
|
|
|
return `grant:${id}`;
|
|
|
|
}
|
|
|
|
|
|
|
|
function userCodeKeyFor(userCode:string) {
|
|
|
|
return `userCode:${userCode}`;
|
|
|
|
}
|
|
|
|
|
|
|
|
class MemoryAdapter implements Adapter{
|
|
|
|
private readonly name: string;
|
|
|
|
constructor(name:string) {
|
|
|
|
this.name = name;
|
2024-03-23 07:38:23 +01:00
|
|
|
}
|
|
|
|
|
2024-03-24 14:18:58 +01:00
|
|
|
key(id:string) {
|
|
|
|
return `${this.name}:${id}`;
|
|
|
|
}
|
|
|
|
|
|
|
|
destroy(id:string) {
|
|
|
|
const key = this.key(id);
|
|
|
|
|
|
|
|
const found = storage.get(key) as AdapterPayload;
|
|
|
|
const grantId = found && found.grantId;
|
|
|
|
|
|
|
|
storage.delete(key);
|
|
|
|
|
|
|
|
if (grantId) {
|
|
|
|
const grantKey = grantKeyFor(grantId);
|
|
|
|
(storage.get(grantKey) as string[])!.forEach(token => storage.delete(token));
|
|
|
|
storage.delete(grantKey);
|
|
|
|
}
|
|
|
|
|
|
|
|
return Promise.resolve();
|
|
|
|
}
|
|
|
|
|
|
|
|
consume(id: string) {
|
|
|
|
(storage.get(this.key(id)) as AdapterPayload)!.consumed = epochTime();
|
|
|
|
return Promise.resolve();
|
2024-03-23 07:38:23 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
find(id: string): Promise<AdapterPayload | void | undefined> {
|
2024-03-24 14:18:58 +01:00
|
|
|
return Promise.resolve<AdapterPayload>(storage.get(this.key(id)) as AdapterPayload);
|
2024-03-23 07:38:23 +01:00
|
|
|
}
|
|
|
|
|
2024-03-24 14:18:58 +01:00
|
|
|
findByUserCode(userCode: string) {
|
|
|
|
const id = storage.get(userCodeKeyFor(userCode)) as string;
|
|
|
|
return this.find(id);
|
2024-03-23 07:38:23 +01:00
|
|
|
}
|
|
|
|
|
2024-03-24 14:18:58 +01:00
|
|
|
upsert(id: string, payload: any, expiresIn: number) {
|
|
|
|
console.log('upsert');
|
|
|
|
const key = this.key(id);
|
|
|
|
|
|
|
|
const { grantId, userCode } = payload;
|
|
|
|
if (grantId) {
|
|
|
|
const grantKey = grantKeyFor(grantId);
|
|
|
|
const grant = storage.get(grantKey) as unknown as string[];
|
|
|
|
if (!grant) {
|
|
|
|
storage.set(grantKey, [key]);
|
|
|
|
} else {
|
|
|
|
grant.push(key);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (userCode) {
|
|
|
|
storage.set(userCodeKeyFor(userCode), id, {ttl:expiresIn * 1000});
|
|
|
|
}
|
|
|
|
|
|
|
|
storage.set(key, payload, {ttl: expiresIn * 1000});
|
|
|
|
|
|
|
|
return Promise.resolve();
|
2024-03-23 07:38:23 +01:00
|
|
|
}
|
|
|
|
|
2024-03-24 14:18:58 +01:00
|
|
|
findByUid(uid: string): Promise<AdapterPayload | void | undefined> {
|
|
|
|
console.log('findByUid', uid);
|
2024-03-23 07:38:23 +01:00
|
|
|
return Promise.resolve(undefined);
|
|
|
|
}
|
|
|
|
|
2024-03-24 14:18:58 +01:00
|
|
|
revokeByGrantId(grantId: string): Promise<void | undefined> {
|
|
|
|
console.log('findByUid', grantId);
|
2024-03-23 07:38:23 +01:00
|
|
|
return Promise.resolve(undefined);
|
|
|
|
}
|
|
|
|
}
|
2024-03-24 14:18:58 +01:00
|
|
|
|
|
|
|
export default MemoryAdapter
|