feat: support nip-36

This commit is contained in:
2024-04-16 07:49:44 +07:00
parent 09b143cb08
commit 94d400cab2
16 changed files with 253 additions and 150 deletions

View File

@@ -23,9 +23,11 @@ enum NSTORE_KEYS {
export class Ark {
public windows: WebviewWindow[];
public settings: Settings;
constructor() {
this.windows = [];
this.settings = undefined;
}
public async get_all_accounts() {
@@ -144,7 +146,6 @@ export class Ark {
if (asOf && asOf > 0) until = asOf.toString();
const dedup = true;
const seenIds = new Set<string>();
const dedupQueue = new Set<string>();
@@ -155,31 +156,37 @@ export class Ark {
global: isGlobal,
});
if (dedup) {
for (const event of nostrEvents) {
const tags = event.tags
.filter((el) => el[0] === "e")
?.map((item) => item[1]);
for (const event of nostrEvents) {
const tags = event.tags
.filter((el) => el[0] === "e")
?.map((item) => item[1]);
if (tags.length) {
for (const tag of tags) {
if (seenIds.has(tag)) {
dedupQueue.add(event.id);
break;
}
seenIds.add(tag);
if (tags.length) {
for (const tag of tags) {
if (seenIds.has(tag)) {
dedupQueue.add(event.id);
break;
}
seenIds.add(tag);
}
}
return nostrEvents
.filter((event) => !dedupQueue.has(event.id))
.sort((a, b) => b.created_at - a.created_at);
}
return nostrEvents;
const events = nostrEvents
.filter((event) => !dedupQueue.has(event.id))
.sort((a, b) => b.created_at - a.created_at);
if (this.settings?.nsfw) {
return events.filter(
(event) =>
event.tags.filter((event) => event[0] === "content-warning")
.length > 0,
);
}
return events;
} catch (e) {
console.error(String(e));
console.info(String(e));
return [];
}
}
@@ -229,7 +236,12 @@ export class Ark {
return nostrEvents.sort((a, b) => b.created_at - a.created_at);
}
public async publish(content: string, reply_to?: string, quote?: boolean) {
public async publish(
content: string,
reply_to?: string,
quote?: boolean,
nsfw?: boolean,
) {
try {
const g = await generateContentTags(content);
@@ -238,26 +250,34 @@ export class Ark {
if (reply_to) {
const replyEvent = await this.get_event(reply_to);
const relayHint =
replyEvent.tags.find((ev) => ev[0] === "e")?.[0][2] ?? "";
if (quote) {
eventTags.push([
"e",
replyEvent.id,
replyEvent.relay || "",
"mention",
]);
eventTags.push(["e", replyEvent.id, relayHint, "mention"]);
} else {
const rootEvent = replyEvent.tags.find((ev) => ev[3] === "root");
if (rootEvent) {
eventTags.push(["e", rootEvent[1], rootEvent[2] || "", "root"]);
eventTags.push([
"e",
rootEvent[1],
rootEvent[2] || relayHint,
"root",
]);
}
eventTags.push(["e", replyEvent.id, replyEvent.relay || "", "reply"]);
eventTags.push(["e", replyEvent.id, relayHint, "reply"]);
eventTags.push(["p", replyEvent.pubkey]);
}
}
if (nsfw) {
eventTags.push(["L", "content-warning"]);
eventTags.push(["l", "reason", "content-warning"]);
eventTags.push(["content-warning", "nsfw"]);
}
const cmd: string = await invoke("publish", {
content: eventContent,
tags: eventTags,
@@ -605,6 +625,7 @@ export class Ark {
key: NSTORE_KEYS.settings,
});
const settings: Settings = cmd ? JSON.parse(cmd) : null;
this.settings = settings;
return settings;
} catch {
const defaultSettings: Settings = {
@@ -612,7 +633,9 @@ export class Ark {
enhancedPrivacy: false,
notification: false,
zap: false,
nsfw: false,
};
this.settings = defaultSettings;
return defaultSettings;
}
}

View File

@@ -123,3 +123,4 @@ export * from "./src/laurel";
export * from "./src/quote";
export * from "./src/key";
export * from "./src/remote";
export * from "./src/nsfw";

View File

@@ -1,20 +1,13 @@
export function AddMediaIcon(props: JSX.IntrinsicElements["svg"]) {
return (
<svg
xmlns="http://www.w3.org/2000/svg"
width="24"
height="24"
fill="none"
viewBox="0 0 24 24"
{...props}
>
<path
stroke="currentColor"
strokeLinecap="round"
strokeLinejoin="round"
strokeWidth="2"
d="M19 22v-3m0 0v-3m0 3h-3m3 0h3m0-5.648V11l-.001-1m-9.464 11H10c-.756 0-1.41 0-1.983-.01M22 10H21c-1.393 0-2.09 0-2.676.06A11.5 11.5 0 008.06 20.324c-.02.2-.034.415-.043.665M22 10c-.008-2.15-.068-3.336-.544-4.27a5 5 0 00-2.185-2.185C18.2 3 16.8 3 14 3h-4c-2.8 0-4.2 0-5.27.545A5 5 0 002.545 5.73C2 6.8 2 8.2 2 11v2c0 2.8 0 4.2.545 5.27a5 5 0 002.185 2.185c.78.398 1.738.505 3.287.534M7.5 9.5a1 1 0 110-2 1 1 0 010 2z"
/>
</svg>
);
return (
<svg width="24" height="24" fill="none" viewBox="0 0 24 24" {...props}>
<path
stroke="currentColor"
strokeLinecap="round"
strokeLinejoin="round"
strokeWidth="1.5"
d="M15.25 8.75v-4a2 2 0 0 0-2-2h-8.5a2 2 0 0 0-2 2v8.5a2 2 0 0 0 2 2h4M3.1 11.9l1.794-1.176a2 2 0 0 1 2.206.01l1.279.852M6 6.25h.5m8 8.75h.5M6.75 6.25a.5.5 0 1 1-1 0 .5.5 0 0 1 1 0Zm7 6.95v3.6l2.8-1.8-2.8-1.8Zm5.5 8.05h-8.5a2 2 0 0 1-2-2v-8.5a2 2 0 0 1 2-2h8.5a2 2 0 0 1 2 2v8.5a2 2 0 0 1-2 2Z"
/>
</svg>
);
}

View File

@@ -0,0 +1,13 @@
export function NsfwIcon(props: JSX.IntrinsicElements["svg"]) {
return (
<svg width="24" height="24" fill="none" viewBox="0 0 24 24" {...props}>
<path
stroke="currentColor"
strokeLinecap="round"
strokeLinejoin="round"
strokeWidth="1.5"
d="M4.75 18.75v1.5a1 1 0 0 0 1 1h12.5a1 1 0 0 0 1-1v-1.5a2 2 0 0 0-2-2H6.75a2 2 0 0 0-2 2Zm2-2V12a5.25 5.25 0 0 1 10.5 0v4.75M12 1.75v1.025M21.225 12h1.025M2.775 12H1.75m16.773-6.523.725-.725m-13.771.725-.725-.725M12 16.75v-3"
/>
</svg>
);
}

View File

@@ -3,6 +3,8 @@ export interface Settings {
enhancedPrivacy: boolean;
autoUpdate: boolean;
zap: boolean;
nsfw: boolean;
[key: string]: string | number | boolean;
}
export interface Keys {

View File

@@ -20,7 +20,6 @@ export const Note = {
Pin: NotePin,
Content: NoteContent,
Zap: NoteZap,
Pin: NotePin,
Child: NoteChild,
Thread: NoteThread,
};