diff --git a/src/policies/whitelist-policy.test.ts b/src/policies/whitelist-policy.test.ts new file mode 100644 index 0000000..e6afe32 --- /dev/null +++ b/src/policies/whitelist-policy.test.ts @@ -0,0 +1,15 @@ +import { assert } from '../deps.ts'; +import { buildEvent, buildInputMessage } from '../test.ts'; + +import whitelistPolicy from './whitelist-policy.ts'; + +Deno.test('allows only whitelisted pubkeys', async () => { + const msgA = buildInputMessage({ event: buildEvent({ pubkey: 'A' }) }); + const msgB = buildInputMessage({ event: buildEvent({ pubkey: 'B' }) }); + const msgC = buildInputMessage({ event: buildEvent({ pubkey: 'C' }) }); + + assert((await whitelistPolicy(msgA, [])).action === 'reject'); + assert((await whitelistPolicy(msgA, ['A'])).action === 'accept'); + assert((await whitelistPolicy(msgC, ['B', 'A'])).action === 'reject'); + assert((await whitelistPolicy(msgB, ['B', 'A'])).action === 'accept'); +}); diff --git a/src/policies/whitelist-policy.ts b/src/policies/whitelist-policy.ts new file mode 100644 index 0000000..da9f2f4 --- /dev/null +++ b/src/policies/whitelist-policy.ts @@ -0,0 +1,32 @@ +import type { Policy } from '../types.ts'; + +/** + * Allows only the listed pubkeys to post to the relay. All other events are rejected. + * Pass an array of pubkeys or an iterable, making it efficient to load pubkeys from a large file. + */ +const whitelistPolicy: Policy> = ({ event: { id, pubkey } }, pubkeys = []) => { + let isMatch = false; + + for (const p of pubkeys) { + if (p === pubkey) { + isMatch = true; + break; + } + } + + if (isMatch) { + return { + id, + action: 'accept', + msg: '', + }; + } + + return { + id, + action: 'reject', + msg: 'Only certain pubkeys are allowed.', + }; +}; + +export default whitelistPolicy;