Port strfry policies to @nostrify/policies
Use packages from JSR and adapt code for new policy APIs
This commit is contained in:
@@ -1,8 +1,8 @@
|
||||
import type { IterablePubkeys, Policy } from 'https://gitlab.com/soapbox-pub/strfry-policies/-/raw/develop/mod.ts';
|
||||
import { NostrEvent, NostrRelayInfo, NostrRelayOK, NPolicy } from 'jsr:@nostrify/types@^0.35.0';
|
||||
import { nip57 } from 'jsr:@nostr/tools';
|
||||
import { Client } from 'npm:ldapts';
|
||||
import { nip57 } from '@nostr/tools';
|
||||
|
||||
interface LdapConfig {
|
||||
export interface LdapConfig {
|
||||
url: string;
|
||||
bindDN: string;
|
||||
password: string;
|
||||
@@ -10,68 +10,73 @@ interface LdapConfig {
|
||||
whitelistPubkeys?: IterablePubkeys;
|
||||
}
|
||||
|
||||
const ldapPolicy: Policy<LdapConfig> = async (msg, opts) => {
|
||||
const client = new Client({ url: opts.url });
|
||||
const { kind, tags } = msg.event;
|
||||
let { pubkey } = msg.event;
|
||||
let out = { id: msg.event.id }
|
||||
export class LdapPolicy implements NPolicy {
|
||||
constructor(private opts: LdapConfig) {}
|
||||
|
||||
if (opts.whitelistPubkeys.includes(pubkey)) {
|
||||
out['action'] = 'accept';
|
||||
out['msg'] = '';
|
||||
return out;
|
||||
}
|
||||
// deno-lint-ignore require-await
|
||||
async call(event: NostrEvent): Promise<NostrRelayOK> {
|
||||
const client = new Client({ url: this.opts.url });
|
||||
const { id, kind, tags } = event;
|
||||
let { pubkey } = event;
|
||||
|
||||
// Zap receipt
|
||||
if (kind === 9735) {
|
||||
const descriptionTag = tags.find(([t, v]) => t === 'description' && v);
|
||||
const invalidZapRequestMsg = 'Zap receipts must contain a valid zap request from a relay member';
|
||||
|
||||
if (typeof descriptionTag === 'undefined') {
|
||||
out['action'] = 'reject';
|
||||
out['msg'] = invalidZapRequestMsg;
|
||||
return out;
|
||||
if (this.opts.whitelistPubkeys.includes(pubkey)) {
|
||||
return ['OK', id, true, ''];
|
||||
}
|
||||
|
||||
const zapRequestJSON = descriptionTag[1];
|
||||
const validationResult = nip57.validateZapRequest(zapRequestJSON);
|
||||
// Zap receipt
|
||||
if (kind === 9735) {
|
||||
const descriptionTag = tags.find(([t, v]) => t === 'description' && v);
|
||||
const invalidZapRequestMsg = 'Zap receipts must contain a valid zap request from a relay member';
|
||||
|
||||
// TODO
|
||||
// The zap receipt event's pubkey MUST be the same as the recipient's lnurl provider's nostrPubkey (retrieved in step 1 of the protocol flow).
|
||||
// The invoiceAmount contained in the bolt11 tag of the zap receipt MUST equal the amount tag of the zap request (if present).
|
||||
if (typeof descriptionTag === 'undefined') {
|
||||
return ['OK', id, false, invalidZapRequestMsg];
|
||||
}
|
||||
|
||||
if (validationResult === null) {
|
||||
pubkey = JSON.parse(zapRequestJSON).pubkey;
|
||||
} else {
|
||||
out['action'] = 'reject';
|
||||
out['msg'] = invalidZapRequestMsg;
|
||||
return out;
|
||||
const zapRequestJSON = descriptionTag[1];
|
||||
const validationResult = nip57.validateZapRequest(zapRequestJSON);
|
||||
|
||||
// TODO
|
||||
// The zap receipt event's pubkey MUST be the same as the recipient's lnurl provider's nostrPubkey (retrieved in step 1 of the protocol flow).
|
||||
// The invoiceAmount contained in the bolt11 tag of the zap receipt MUST equal the amount tag of the zap request (if present).
|
||||
|
||||
if (validationResult === null) {
|
||||
pubkey = JSON.parse(zapRequestJSON).pubkey;
|
||||
} else {
|
||||
return ['OK', id, false, invalidZapRequestMsg];
|
||||
}
|
||||
}
|
||||
|
||||
const out = { accept: true, msg: ''};
|
||||
|
||||
try {
|
||||
await client.bind(this.opts.bindDN, this.opts.password);
|
||||
|
||||
const { searchEntries } = await client.search(this.opts.searchDN, {
|
||||
filter: `(nostrKey=${pubkey})`,
|
||||
attributes: ['nostrKey']
|
||||
});
|
||||
const memberKey = searchEntries[0]?.nostrKey;
|
||||
|
||||
if (memberKey === pubkey) {
|
||||
out['accept'] = true;
|
||||
} else {
|
||||
out['accept'] = false;
|
||||
out['msg'] = 'Only members can publish notes on this relay';
|
||||
}
|
||||
} catch (ex) {
|
||||
out['accept'] = false;
|
||||
out['msg'] = 'Auth service temporarily unavailable';
|
||||
} finally {
|
||||
await client.unbind();
|
||||
return ['OK', id, out['accept'], out['msg']];
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
await client.bind(opts.bindDN, opts.password);
|
||||
|
||||
const { searchEntries } = await client.search(opts.searchDN, {
|
||||
filter: `(nostrKey=${pubkey})`,
|
||||
attributes: ['nostrKey']
|
||||
});
|
||||
const memberKey = searchEntries[0]?.nostrKey;
|
||||
|
||||
if (memberKey === pubkey) {
|
||||
out['action'] = 'accept';
|
||||
out['msg'] = '';
|
||||
} else {
|
||||
out['action'] = 'reject';
|
||||
out['msg'] = 'Only members can publish notes on this relay';
|
||||
}
|
||||
} catch (ex) {
|
||||
out['action'] = 'reject';
|
||||
out['msg'] = 'Auth service temporarily unavailable';
|
||||
} finally {
|
||||
await client.unbind();
|
||||
return out;
|
||||
get info(): NostrRelayInfo {
|
||||
return {
|
||||
limitation: {
|
||||
restricted_writes: true,
|
||||
},
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
export default ldapPolicy;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user