1
0
forked from Kieran/snort

feat: custom nip96 server

This commit is contained in:
kieran 2024-05-13 14:19:28 +01:00
parent ecd3876287
commit b5ca5327db
Signed by: Kieran
GPG Key ID: DE71CEB3925BE941
7 changed files with 87 additions and 6 deletions

View File

@ -469,6 +469,9 @@ const PreferencesPage = () => {
fileUploader: e.target.value, fileUploader: e.target.value,
} as UserPreferences) } as UserPreferences)
}> }>
<option value="nip96">
<FormattedMessage defaultMessage="NIP-96" />
</option>
<option value="void.cat"> <option value="void.cat">
void.cat <FormattedMessage {...messages.Default} /> void.cat <FormattedMessage {...messages.Default} />
</option> </option>
@ -477,6 +480,19 @@ const PreferencesPage = () => {
<option value="nostrimg.com">nostrimg.com</option> <option value="nostrimg.com">nostrimg.com</option>
<option value="nostrcheck.me">nostrcheck.me (NIP-96)</option> <option value="nostrcheck.me">nostrcheck.me (NIP-96)</option>
</select> </select>
{pref.fileUploader === "nip96" && (
<>
<small>
<FormattedMessage defaultMessage="Custom server URL" />
</small>
<input
type="text"
value={pref.nip96Server}
onChange={e => setPref({ ...pref, nip96Server: e.target.value })}
placeholder="https://my-nip96-server.com/"
/>
</>
)}
</div> </div>
<div className="flex justify-between"> <div className="flex justify-between">
<div className="flex flex-col g8"> <div className="flex flex-col g8">

View File

@ -46,7 +46,12 @@ export interface UserPreferences {
/** /**
* File uploading service to upload attachments to * File uploading service to upload attachments to
*/ */
fileUploader: "void.cat" | "nostr.build" | "nostrimg.com" | "void.cat-NIP96" | "nostrcheck.me"; fileUploader: "void.cat" | "nostr.build" | "nostrimg.com" | "void.cat-NIP96" | "nostrcheck.me" | "nip96";
/**
* Custom file server to upload files to
*/
nip96Server?: string;
/** /**
* Use imgproxy to optimize images * Use imgproxy to optimize images

View File

@ -8,7 +8,9 @@ export class Nip96Uploader implements Uploader {
constructor( constructor(
readonly url: string, readonly url: string,
readonly publisher: EventPublisher, readonly publisher: EventPublisher,
) {} ) {
this.url = new URL(this.url).toString();
}
get progress() { get progress() {
return []; return [];
@ -62,16 +64,27 @@ export class Nip96Uploader implements Uploader {
metadata: { metadata: {
width: dim?.at(0) ? Number(dim[0]) : undefined, width: dim?.at(0) ? Number(dim[0]) : undefined,
height: dim?.at(1) ? Number(dim[1]) : undefined, height: dim?.at(1) ? Number(dim[1]) : undefined,
blurhash: data.nip94_event.tags.find(a => a[0] === "blurhash")?.at(1),
hash: data.nip94_event.tags.find(a => a[0] === "x")?.at(1),
}, },
}; };
} }
return { return {
error: data.message, error: data.message,
}; };
} else {
const text = await rsp.text();
try {
const obj = JSON.parse(text) as Nip96Result;
return {
error: obj.message,
};
} catch {
return {
error: `Upload failed: ${text}`,
};
}
} }
return {
error: "Upload failed",
};
} }
} }

View File

@ -0,0 +1 @@
export class BlossomClient {}

View File

@ -65,7 +65,10 @@ export interface UploadProgress {
export type UploadStage = "starting" | "hashing" | "uploading" | "done" | undefined; export type UploadStage = "starting" | "hashing" | "uploading" | "done" | undefined;
export default function useFileUpload(): Uploader { export default function useFileUpload(): Uploader {
const fileUploader = usePreferences(s => s.fileUploader); const { fileUploader, nip96Server } = usePreferences(s => ({
fileUploader: s.fileUploader,
nip96Server: s.nip96Server,
}));
const { publisher } = useEventPublisher(); const { publisher } = useEventPublisher();
const [progress, setProgress] = useState<Array<UploadProgress>>([]); const [progress, setProgress] = useState<Array<UploadProgress>>([]);
const [stage, setStage] = useState<UploadStage>(); const [stage, setStage] = useState<UploadStage>();
@ -77,6 +80,9 @@ export default function useFileUpload(): Uploader {
progress: [], progress: [],
} as Uploader; } as Uploader;
} }
case "nip96": {
return new Nip96Uploader(unwrap(nip96Server), unwrap(publisher));
}
case "void.cat-NIP96": { case "void.cat-NIP96": {
return new Nip96Uploader("https://void.cat/nostr", unwrap(publisher)); return new Nip96Uploader("https://void.cat/nostr", unwrap(publisher));
} }

View File

@ -62,6 +62,9 @@
"01iNut": { "01iNut": {
"defaultMessage": "Nostr address does not belong to you" "defaultMessage": "Nostr address does not belong to you"
}, },
"08zn6O": {
"defaultMessage": "Export Keys"
},
"0Azlrb": { "0Azlrb": {
"defaultMessage": "Manage" "defaultMessage": "Manage"
}, },
@ -177,6 +180,9 @@
"3tVy+Z": { "3tVy+Z": {
"defaultMessage": "{n} Followers" "defaultMessage": "{n} Followers"
}, },
"3yk8fB": {
"defaultMessage": "Wallet"
},
"450Fty": { "450Fty": {
"defaultMessage": "None" "defaultMessage": "None"
}, },
@ -508,6 +514,9 @@
"FmXUJg": { "FmXUJg": {
"defaultMessage": "follows you" "defaultMessage": "follows you"
}, },
"FvanT6": {
"defaultMessage": "Accounts"
},
"G/yZLu": { "G/yZLu": {
"defaultMessage": "Remove" "defaultMessage": "Remove"
}, },
@ -572,6 +581,9 @@
"HhcAVH": { "HhcAVH": {
"defaultMessage": "You don't follow this person, click here to load media from <i>{link}</i>, or update <a><i>your preferences</i></a> to always load media from everybody." "defaultMessage": "You don't follow this person, click here to load media from <i>{link}</i>, or update <a><i>your preferences</i></a> to always load media from everybody."
}, },
"HqRNN8": {
"defaultMessage": "Support"
},
"I1AoOu": { "I1AoOu": {
"defaultMessage": "Last post {time}" "defaultMessage": "Last post {time}"
}, },
@ -635,6 +647,9 @@
"JSx7y9": { "JSx7y9": {
"defaultMessage": "Subscribe to {site_name} {plan} for {price} and receive the following rewards" "defaultMessage": "Subscribe to {site_name} {plan} for {price} and receive the following rewards"
}, },
"JTht/T": {
"defaultMessage": "NIP-96"
},
"JeoS4y": { "JeoS4y": {
"defaultMessage": "Repost" "defaultMessage": "Repost"
}, },
@ -819,6 +834,9 @@
"Qxv0B2": { "Qxv0B2": {
"defaultMessage": "You currently have {number} sats in your zap pool." "defaultMessage": "You currently have {number} sats in your zap pool."
}, },
"R/6nsx": {
"defaultMessage": "Subscription"
},
"R81upa": { "R81upa": {
"defaultMessage": "People you follow" "defaultMessage": "People you follow"
}, },
@ -907,6 +925,9 @@
"TvKqBp": { "TvKqBp": {
"defaultMessage": "liked" "defaultMessage": "liked"
}, },
"TwyMau": {
"defaultMessage": "Account"
},
"U1aPPi": { "U1aPPi": {
"defaultMessage": "Stop listening" "defaultMessage": "Stop listening"
}, },
@ -1286,9 +1307,15 @@
"hY4lzx": { "hY4lzx": {
"defaultMessage": "Supports" "defaultMessage": "Supports"
}, },
"hYOE+U": {
"defaultMessage": "Invite"
},
"ha8JKG": { "ha8JKG": {
"defaultMessage": "Show graph" "defaultMessage": "Show graph"
}, },
"hf6g/W": {
"defaultMessage": "Custom server URL"
},
"hicxcO": { "hicxcO": {
"defaultMessage": "Show replies" "defaultMessage": "Show replies"
}, },
@ -1298,6 +1325,9 @@
"hniz8Z": { "hniz8Z": {
"defaultMessage": "here" "defaultMessage": "here"
}, },
"hvFRBo": {
"defaultMessage": "Interaction"
},
"i/dBAR": { "i/dBAR": {
"defaultMessage": "Zap Pool" "defaultMessage": "Zap Pool"
}, },

View File

@ -20,6 +20,7 @@
"/n5KSF": "{n} ms", "/n5KSF": "{n} ms",
"00LcfG": "Load more", "00LcfG": "Load more",
"01iNut": "Nostr address does not belong to you", "01iNut": "Nostr address does not belong to you",
"08zn6O": "Export Keys",
"0Azlrb": "Manage", "0Azlrb": "Manage",
"0BUTMv": "Search...", "0BUTMv": "Search...",
"0HFX0T": "Use Exact Location", "0HFX0T": "Use Exact Location",
@ -58,6 +59,7 @@
"3qnJlS": "You are voting with {amount} sats", "3qnJlS": "You are voting with {amount} sats",
"3t3kok": "{n,plural,=1{{n} new note} other{{n} new notes}}", "3t3kok": "{n,plural,=1{{n} new note} other{{n} new notes}}",
"3tVy+Z": "{n} Followers", "3tVy+Z": "{n} Followers",
"3yk8fB": "Wallet",
"450Fty": "None", "450Fty": "None",
"47FYwb": "Cancel", "47FYwb": "Cancel",
"4IPzdn": "Primary Developers", "4IPzdn": "Primary Developers",
@ -168,6 +170,7 @@
"FdhSU2": "Claim Now", "FdhSU2": "Claim Now",
"FfYsOb": "An error has occured!", "FfYsOb": "An error has occured!",
"FmXUJg": "follows you", "FmXUJg": "follows you",
"FvanT6": "Accounts",
"G/yZLu": "Remove", "G/yZLu": "Remove",
"G1BGCg": "Select Wallet", "G1BGCg": "Select Wallet",
"G3A56c": "Subscribed to Push", "G3A56c": "Subscribed to Push",
@ -189,6 +192,7 @@
"HWbkEK": "Clear cache and reload", "HWbkEK": "Clear cache and reload",
"HbefNb": "Open Wallet", "HbefNb": "Open Wallet",
"HhcAVH": "You don't follow this person, click here to load media from <i>{link}</i>, or update <a><i>your preferences</i></a> to always load media from everybody.", "HhcAVH": "You don't follow this person, click here to load media from <i>{link}</i>, or update <a><i>your preferences</i></a> to always load media from everybody.",
"HqRNN8": "Support",
"I1AoOu": "Last post {time}", "I1AoOu": "Last post {time}",
"IEwZvs": "Are you sure you want to unpin this note?", "IEwZvs": "Are you sure you want to unpin this note?",
"IIOul1": "Account Data", "IIOul1": "Account Data",
@ -210,6 +214,7 @@
"JIVWWA": "Sport", "JIVWWA": "Sport",
"JPFYIM": "No lightning address", "JPFYIM": "No lightning address",
"JSx7y9": "Subscribe to {site_name} {plan} for {price} and receive the following rewards", "JSx7y9": "Subscribe to {site_name} {plan} for {price} and receive the following rewards",
"JTht/T": "NIP-96",
"JeoS4y": "Repost", "JeoS4y": "Repost",
"JjGgXI": "Search users", "JjGgXI": "Search users",
"JkLHGw": "Website", "JkLHGw": "Website",
@ -271,6 +276,7 @@
"QJfhKt": "The private key is like a password, but it cannot be reset. Guard it carefully and never show it to anyone. Once someone has your private key, they will have access to your account forever.", "QJfhKt": "The private key is like a password, but it cannot be reset. Guard it carefully and never show it to anyone. Once someone has your private key, they will have access to your account forever.",
"QWhotP": "Zap Pool only works if you use one of the supported wallet connections (WebLN, LNC, LNDHub or Nostr Wallet Connect)", "QWhotP": "Zap Pool only works if you use one of the supported wallet connections (WebLN, LNC, LNDHub or Nostr Wallet Connect)",
"Qxv0B2": "You currently have {number} sats in your zap pool.", "Qxv0B2": "You currently have {number} sats in your zap pool.",
"R/6nsx": "Subscription",
"R81upa": "People you follow", "R81upa": "People you follow",
"RDha9y": "Service Worker Not Running", "RDha9y": "Service Worker Not Running",
"RSr2uB": "Username must only contain lowercase letters and numbers", "RSr2uB": "Username must only contain lowercase letters and numbers",
@ -300,6 +306,7 @@
"TpgeGw": "Hex Salt..", "TpgeGw": "Hex Salt..",
"Tpy00S": "People", "Tpy00S": "People",
"TvKqBp": "liked", "TvKqBp": "liked",
"TwyMau": "Account",
"U1aPPi": "Stop listening", "U1aPPi": "Stop listening",
"UDYlxu": "Pending Subscriptions", "UDYlxu": "Pending Subscriptions",
"UJTWqI": "Remove from my relays", "UJTWqI": "Remove from my relays",
@ -426,10 +433,13 @@
"hMzcSq": "Messages", "hMzcSq": "Messages",
"hRTfTR": "PRO", "hRTfTR": "PRO",
"hY4lzx": "Supports", "hY4lzx": "Supports",
"hYOE+U": "Invite",
"ha8JKG": "Show graph", "ha8JKG": "Show graph",
"hf6g/W": "Custom server URL",
"hicxcO": "Show replies", "hicxcO": "Show replies",
"hmZ3Bz": "Media", "hmZ3Bz": "Media",
"hniz8Z": "here", "hniz8Z": "here",
"hvFRBo": "Interaction",
"i/dBAR": "Zap Pool", "i/dBAR": "Zap Pool",
"i5gBFz": "Your sent and received payments will show up here.", "i5gBFz": "Your sent and received payments will show up here.",
"iCqGww": "Reactions ({n})", "iCqGww": "Reactions ({n})",