chore: bump gpui-pre to 0.3.8 and clean up unused code
This commit is contained in:
@@ -17,7 +17,6 @@ gpui.workspace = true
|
||||
instant.workspace = true
|
||||
flume.workspace = true
|
||||
futures.workspace = true
|
||||
log.workspace = true
|
||||
anyhow.workspace = true
|
||||
webbrowser.workspace = true
|
||||
serde_json.workspace = true
|
||||
|
||||
@@ -1,14 +1,11 @@
|
||||
/// Client name (Application name)
|
||||
pub const CLIENT_NAME: &str = "Coop";
|
||||
|
||||
/// COOP's public key
|
||||
pub const COOP_PUBKEY: &str = "npub1j3rz3ndl902lya6ywxvy5c983lxs8mpukqnx4pa4lt5wrykwl5ys7wpw3x";
|
||||
|
||||
/// App ID
|
||||
pub const APP_ID: &str = "su.reya.coop";
|
||||
|
||||
/// Keyring name
|
||||
pub const MASTER_KEYRING: &str = "Coop Master Key";
|
||||
pub(crate) const MASTER_KEYRING: &str = "Coop Master Key";
|
||||
pub const USER_KEYRING: &str = "Coop User Credential";
|
||||
|
||||
/// Default timeout for subscription
|
||||
@@ -26,20 +23,12 @@ pub const DEVICE_GIFTWRAP: &str = "device-gift-wraps";
|
||||
/// Default subscription id for user gift wrap events
|
||||
pub const USER_GIFTWRAP: &str = "user-gift-wraps";
|
||||
|
||||
/// Default timeout for Nostr Connect
|
||||
pub const NOSTR_CONNECT_TIMEOUT: u64 = 60;
|
||||
|
||||
/// Default Nostr Connect relay
|
||||
pub const NOSTR_CONNECT_RELAY: &str = "wss://relay.nip46.com";
|
||||
|
||||
/// Default vertex relays
|
||||
pub const WOT_RELAYS: [&str; 1] = ["wss://relay.vertexlab.io"];
|
||||
/// Default search relays
|
||||
pub(crate) const INDEXER_RELAYS: [&str; 2] =
|
||||
["wss://indexer.coracle.social", "wss://user.kindpag.es"];
|
||||
|
||||
/// Default search relays
|
||||
pub const INDEXER_RELAYS: [&str; 2] = ["wss://indexer.coracle.social", "wss://user.kindpag.es"];
|
||||
|
||||
/// Default search relays
|
||||
pub const SEARCH_RELAYS: [&str; 2] = ["wss://antiprimal.net", "wss://search.nos.today"];
|
||||
pub(crate) const SEARCH_RELAYS: [&str; 2] = ["wss://antiprimal.net", "wss://search.nos.today"];
|
||||
|
||||
/// Default bootstrap relays
|
||||
pub const BOOTSTRAP_RELAYS: [&str; 4] = [
|
||||
|
||||
@@ -15,9 +15,9 @@ use nostr::nips::nip94::Sha256Hash;
|
||||
use nostr_sdk::prelude::*;
|
||||
use sha2::{Digest, Sha256};
|
||||
|
||||
pub const ALGORITHM: &str = "aes-gcm";
|
||||
pub(crate) const ALGORITHM: &str = "aes-gcm";
|
||||
|
||||
pub const MAX_FILE_SIZE: usize = 25 * 1024 * 1024;
|
||||
pub(crate) const MAX_FILE_SIZE: usize = 25 * 1024 * 1024;
|
||||
|
||||
const TAG_SHA256: &str = "x";
|
||||
const TAG_ORIGINAL_SHA256: &str = "ox";
|
||||
@@ -30,7 +30,7 @@ const TAG_DIM: &str = "dim";
|
||||
const TAG_ALT: &str = "alt";
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub struct EncryptedFile {
|
||||
pub(crate) struct EncryptedFile {
|
||||
pub data: Vec<u8>,
|
||||
pub key: String,
|
||||
pub nonce: String,
|
||||
@@ -115,7 +115,7 @@ impl FileAttachment {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn encrypt(data: &[u8]) -> Result<EncryptedFile, Error> {
|
||||
pub(crate) fn encrypt(data: &[u8]) -> Result<EncryptedFile, Error> {
|
||||
let key = Aes256Gcm::generate_key(OsRng);
|
||||
let nonce = AesGcm::<Aes256, U16>::generate_nonce(OsRng);
|
||||
let cipher = AesGcm::<Aes256, U16>::new(&key);
|
||||
@@ -131,7 +131,7 @@ pub fn encrypt(data: &[u8]) -> Result<EncryptedFile, Error> {
|
||||
})
|
||||
}
|
||||
|
||||
pub fn decrypt(data: &[u8], key: &str, nonce: &str) -> Result<Vec<u8>, Error> {
|
||||
pub(crate) fn decrypt(data: &[u8], key: &str, nonce: &str) -> Result<Vec<u8>, Error> {
|
||||
let key = decode(key, "decryption key")?;
|
||||
let nonce = decode(nonce, "decryption nonce")?;
|
||||
|
||||
@@ -159,7 +159,7 @@ pub fn decrypt(data: &[u8], key: &str, nonce: &str) -> Result<Vec<u8>, Error> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn sha256_hex(data: &[u8]) -> String {
|
||||
pub(crate) fn sha256_hex(data: &[u8]) -> String {
|
||||
let hash: [u8; 32] = Sha256::digest(data).into();
|
||||
|
||||
Sha256Hash::from_byte_array(hash).to_hex()
|
||||
@@ -227,7 +227,7 @@ pub async fn upload_encrypted(
|
||||
Err(anyhow!("File upload not supported on web"))
|
||||
}
|
||||
|
||||
pub async fn download_and_decrypt(
|
||||
pub(crate) async fn download_and_decrypt(
|
||||
url: &Url,
|
||||
key: &str,
|
||||
nonce: &str,
|
||||
@@ -318,63 +318,6 @@ pub async fn download_and_decrypt_to_file(
|
||||
Err(anyhow!("File download not supported on web"))
|
||||
}
|
||||
|
||||
/// The cache file a decrypted blob for `plaintext_sha256` is written to.
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
fn blob_cache_path(plaintext_sha256: &str) -> PathBuf {
|
||||
std::env::temp_dir()
|
||||
.join("coop-blobs")
|
||||
.join(plaintext_sha256)
|
||||
}
|
||||
|
||||
/// Download an encrypted blob whose pointer carries the *plaintext* hash
|
||||
/// and write the decrypted bytes to a content-addressed cache file,
|
||||
/// so later renders skip the network.
|
||||
///
|
||||
/// The cache file carries no extension: `img` sniffs the format from the bytes.
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
pub async fn download_and_decrypt_to_cache(
|
||||
url: &Url,
|
||||
key: &str,
|
||||
nonce: &str,
|
||||
plaintext_sha256: &str,
|
||||
cx: &AsyncApp,
|
||||
) -> Result<PathBuf, Error> {
|
||||
let path = blob_cache_path(plaintext_sha256);
|
||||
|
||||
if smol::fs::metadata(&path).await.is_ok() {
|
||||
return Ok(path);
|
||||
}
|
||||
|
||||
let data = download_and_decrypt(url, key, nonce, None, cx).await?;
|
||||
|
||||
if !sha256_hex(&data).eq_ignore_ascii_case(plaintext_sha256) {
|
||||
bail!("Blob hash mismatch");
|
||||
}
|
||||
|
||||
let Some(parent) = path.parent() else {
|
||||
bail!("Invalid blob cache path");
|
||||
};
|
||||
smol::fs::create_dir_all(parent).await?;
|
||||
|
||||
// Write under a temporary name first, so an interrupted download is never reused
|
||||
let partial = path.with_extension("download");
|
||||
smol::fs::write(&partial, data).await?;
|
||||
smol::fs::rename(&partial, &path).await?;
|
||||
|
||||
Ok(path)
|
||||
}
|
||||
|
||||
#[cfg(target_arch = "wasm32")]
|
||||
pub async fn download_and_decrypt_to_cache(
|
||||
_url: &Url,
|
||||
_key: &str,
|
||||
_nonce: &str,
|
||||
_plaintext_sha256: &str,
|
||||
_cx: &AsyncApp,
|
||||
) -> Result<PathBuf, Error> {
|
||||
Err(anyhow!("Blob download not supported on web"))
|
||||
}
|
||||
|
||||
fn tag_value<'a>(tags: &'a Tags, name: &str) -> Option<&'a str> {
|
||||
tags.iter()
|
||||
.find(|tag| tag.kind() == name)
|
||||
|
||||
+1
-72
@@ -52,8 +52,6 @@ impl Global for GlobalNostrRegistry {}
|
||||
/// Signer event.
|
||||
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord)]
|
||||
pub enum StateEvent {
|
||||
/// The state is busy
|
||||
Busy,
|
||||
/// User has no signer
|
||||
NoSigner,
|
||||
/// The signer has changed
|
||||
@@ -67,7 +65,7 @@ impl StateEvent {
|
||||
matches!(self, StateEvent::SignerChanged)
|
||||
}
|
||||
|
||||
pub fn error<T>(error: T) -> Self
|
||||
pub(crate) fn error<T>(error: T) -> Self
|
||||
where
|
||||
T: Into<String>,
|
||||
{
|
||||
@@ -180,11 +178,6 @@ impl NostrRegistry {
|
||||
self.current_user
|
||||
}
|
||||
|
||||
/// Whether the initial credential check has concluded
|
||||
pub fn ready(&self) -> bool {
|
||||
self.ready
|
||||
}
|
||||
|
||||
fn mark_ready(&mut self, cx: &mut Context<Self>) {
|
||||
if self.ready {
|
||||
return;
|
||||
@@ -525,68 +518,4 @@ impl NostrRegistry {
|
||||
Ok(results)
|
||||
})
|
||||
}
|
||||
|
||||
/// Perform a WoT (via Vertex) search for a given query.
|
||||
pub fn wot_search(&self, query: &str, cx: &App) -> Task<Result<Vec<PublicKey>, Error>> {
|
||||
let client = self.client();
|
||||
let query = query.to_string();
|
||||
let signer = self.signer.clone();
|
||||
|
||||
cx.background_spawn(async move {
|
||||
// Construct a vertex request event
|
||||
let event = EventBuilder::new(Kind::Custom(5315), "")
|
||||
.tags(vec![
|
||||
Tag::custom("param", vec!["search", &query]),
|
||||
Tag::custom("param", vec!["limit", "10"]),
|
||||
])
|
||||
.finalize_async(&signer)
|
||||
.await?;
|
||||
|
||||
// Send the event to vertex relays
|
||||
let output = client.send_event(&event).to(WOT_RELAYS).await?;
|
||||
|
||||
// Construct a filter to get the response or error from vertex
|
||||
let filter = Filter::new()
|
||||
.kinds(vec![Kind::Custom(6315), Kind::Custom(7000)])
|
||||
.event(output.id().to_owned());
|
||||
|
||||
// Construct target for subscription
|
||||
let target: HashMap<&str, Vec<Filter>> = WOT_RELAYS
|
||||
.into_iter()
|
||||
.map(|relay| (relay, vec![filter.clone()]))
|
||||
.collect();
|
||||
|
||||
// Stream events from the wot relays
|
||||
let mut stream = client
|
||||
.stream_events(target)
|
||||
.timeout(Duration::from_secs(TIMEOUT))
|
||||
.await?;
|
||||
|
||||
while let Some((_url, res)) = stream.next().await {
|
||||
if let Ok(event) = res {
|
||||
match event.kind {
|
||||
Kind::Custom(6315) => {
|
||||
let content: serde_json::Value = serde_json::from_str(&event.content)?;
|
||||
let pubkeys: Vec<PublicKey> = content
|
||||
.as_array()
|
||||
.into_iter()
|
||||
.flatten()
|
||||
.filter_map(|item| item.as_object())
|
||||
.filter_map(|obj| obj.get("pubkey").and_then(|v| v.as_str()))
|
||||
.filter_map(|pubkey_str| PublicKey::parse(pubkey_str).ok())
|
||||
.collect();
|
||||
|
||||
return Ok(pubkeys);
|
||||
}
|
||||
Kind::Custom(7000) => {
|
||||
return Err(anyhow!("Search error"));
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Err(anyhow!("No results for query: {query}"))
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,9 +8,6 @@ pub struct Announcement {
|
||||
}
|
||||
|
||||
impl Announcement {
|
||||
/// Parse an announcement from an event, returning `None` when the `n`
|
||||
/// tag is missing or malformed so callers never mistake the author's
|
||||
/// identity key for an encryption key.
|
||||
pub fn from_event(event: &Event) -> Option<Self> {
|
||||
let public_key = event
|
||||
.tags
|
||||
@@ -22,10 +19,6 @@ impl Announcement {
|
||||
Some(Self { public_key })
|
||||
}
|
||||
|
||||
pub fn new(public_key: PublicKey) -> Self {
|
||||
Self { public_key }
|
||||
}
|
||||
|
||||
/// Returns the public key of the device that created this announcement.
|
||||
pub fn public_key(&self) -> PublicKey {
|
||||
self.public_key
|
||||
|
||||
@@ -50,7 +50,7 @@ impl UniversalSigner {
|
||||
}
|
||||
|
||||
/// Swap the inner signer in-place. All clones see the new signer.
|
||||
pub fn swap_inner<T>(&self, new_signer: T)
|
||||
pub(crate) fn swap_inner<T>(&self, new_signer: T)
|
||||
where
|
||||
T: AsyncGetPublicKey + AsyncSignEvent + AsyncNip44 + 'static,
|
||||
<T as AsyncGetPublicKey>::Error: Error + Send + Sync + 'static,
|
||||
@@ -137,14 +137,6 @@ where
|
||||
}
|
||||
}
|
||||
|
||||
impl UniversalSigner {
|
||||
#[allow(dead_code)]
|
||||
fn with_inner<R>(&self, f: impl FnOnce(&dyn InnerSigner) -> R) -> R {
|
||||
let guard = self.inner.read().expect("RwLock poisoned");
|
||||
f(&**guard)
|
||||
}
|
||||
}
|
||||
|
||||
impl AsyncGetPublicKey for UniversalSigner {
|
||||
type Error = UniversalSignerError;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user