add policy routes and publish default policy on startup

This commit is contained in:
Siddharth Singh 2025-03-30 13:31:51 +05:30
parent dc9e45f133
commit 7cb643d1e4
No known key found for this signature in database
3 changed files with 68 additions and 1 deletions

View file

@ -151,6 +151,9 @@ import dittoNamesRoute from '@/routes/dittoNamesRoute.ts';
import pleromaAdminPermissionGroupsRoute from '@/routes/pleromaAdminPermissionGroupsRoute.ts'; import pleromaAdminPermissionGroupsRoute from '@/routes/pleromaAdminPermissionGroupsRoute.ts';
import pleromaStatusesRoute from '@/routes/pleromaStatusesRoute.ts'; import pleromaStatusesRoute from '@/routes/pleromaStatusesRoute.ts';
import { DittoRelayStore } from '@/storages/DittoRelayStore.ts'; import { DittoRelayStore } from '@/storages/DittoRelayStore.ts';
import { PolicyRegistry } from '@nostrify/policies';
import { adminListPoliciesController, adminCurrentPolicyController } from '@/controllers/api/policies.ts';
import { createPolicyEvent, DEFAULT_POLICIES } from '@/utils/policies.ts';
export interface AppEnv extends DittoEnv { export interface AppEnv extends DittoEnv {
Variables: DittoEnv['Variables'] & { Variables: DittoEnv['Variables'] & {
@ -197,6 +200,12 @@ const pgstore = new DittoPgStore({
const pool = new DittoPool({ conf, relay: pgstore }); const pool = new DittoPool({ conf, relay: pgstore });
const relay = new DittoRelayStore({ db, conf, pool, relay: pgstore }); const relay = new DittoRelayStore({ db, conf, pool, relay: pgstore });
const policyRegistry = new PolicyRegistry({ antiDuplicationPolicyStore: await Deno.openKv(), store: relay });
const havePolicy = await relay.count([{ kinds: [11984], authors: [await conf.signer.getPublicKey()] }]);
if (!havePolicy) {
relay.event(await createPolicyEvent(conf, DEFAULT_POLICIES));
}
await seedZapSplits({ conf, relay }); await seedZapSplits({ conf, relay });
@ -496,6 +505,9 @@ app.delete('/api/v1/pleroma/admin/users/tag', userMiddleware({ role: 'admin' }),
app.patch('/api/v1/pleroma/admin/users/suggest', userMiddleware({ role: 'admin' }), pleromaAdminSuggestController); app.patch('/api/v1/pleroma/admin/users/suggest', userMiddleware({ role: 'admin' }), pleromaAdminSuggestController);
app.patch('/api/v1/pleroma/admin/users/unsuggest', userMiddleware({ role: 'admin' }), pleromaAdminUnsuggestController); app.patch('/api/v1/pleroma/admin/users/unsuggest', userMiddleware({ role: 'admin' }), pleromaAdminUnsuggestController);
app.get('/api/v1/admin/policies', userMiddleware({ role: 'admin' }), adminListPoliciesController);
app.get('/api/v1/admin/policies/current', userMiddleware({ role: 'admin' }), adminCurrentPolicyController);
app.route('/api/v1/custom_emojis', customEmojisRoute); app.route('/api/v1/custom_emojis', customEmojisRoute);
// Not (yet) implemented. // Not (yet) implemented.
@ -558,5 +570,5 @@ app.get('*', publicFiles, staticFiles, ratelimit, frontendController);
app.onError(errorHandler); app.onError(errorHandler);
export default app; export default app;
export { policyRegistry };
export type { AppContext, AppController, AppMiddleware }; export type { AppContext, AppController, AppMiddleware };

View file

@ -0,0 +1,26 @@
import { policyRegistry, type AppController } from '@/app.ts';
import { DEFAULT_POLICIES } from "@/utils/policies.ts";
export const adminListPoliciesController: AppController = (c) => {
return c.json(Object.entries(policyRegistry.policies)
.map(([internalName, item]) => {
return {
internalName,
...item,
instantiate: undefined,
}
}))
};
export const adminCurrentPolicyController: AppController = async (c) => {
const { relay, conf } = c.var;
const pubkey = await conf.signer.getPublicKey();
const current = await relay.query([{
authors: [pubkey],
kinds: [11984]
}]).then(events => events[0]);
if (current) return c.json({ mode: conf.policyMode, policies: current });
return c.json({ mode: conf.policyMode, policies: DEFAULT_POLICIES });
}

View file

@ -0,0 +1,29 @@
import { policyRegistry } from '@/app.ts';
import { nostrNow } from '@/utils.ts';
import type { DittoConf } from "@ditto/conf";
type ParamValue = string | number | boolean;
interface PolicySpec {
name: keyof typeof policyRegistry.policies;
params?: Record<string, ParamValue | ParamValue[]>;
}
export const DEFAULT_POLICIES: PolicySpec[] = [
{ "name": "AntiDuplicationPolicy" },
{ "name": "AuthorPolicy" },
{ "name": "DomainPolicy" },
{ "name": "HellthreadPolicy" },
{ "name": "ReplyBotPolicy" },
{ "name": "SizePolicy" },
{ "name": "HashtagPolicy", "params": { "hashtags": ["NSFW", "explicit", "violence", "cp", "porn"] } },
];
export const createPolicyEvent = async (conf: DittoConf, policies: PolicySpec[]) => {
return await conf.signer.signEvent({
kind: 11984,
content: JSON.stringify({ policies }),
created_at: nostrNow(),
tags: []
})
}