cache images locally

This commit is contained in:
Nikita Galaiko 2023-02-24 13:27:18 +01:00
parent e8a77b7d50
commit e549e99c05
4 changed files with 83 additions and 4 deletions

15
src-tauri/Cargo.lock generated
View File

@ -1003,7 +1003,9 @@ dependencies = [
"filetime",
"git2",
"log",
"md5",
"notify",
"reqwest",
"sentry",
"sentry-tauri",
"serde",
@ -1014,6 +1016,7 @@ dependencies = [
"tauri-plugin-log",
"tauri-plugin-window-state",
"tempfile",
"urlencoding",
"uuid 1.3.0",
"walkdir",
]
@ -1756,6 +1759,12 @@ version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2532096657941c2fea9c289d370a250971c689d4f143798ff67113ec042024a5"
[[package]]
name = "md5"
version = "0.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "490cc448043f947bae3cbee9c203358d62dbee0db12107a74be5c30ccfd09771"
[[package]]
name = "memchr"
version = "2.5.0"
@ -3830,6 +3839,12 @@ dependencies = [
"serde",
]
[[package]]
name = "urlencoding"
version = "2.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e8db7427f936968176eaa7cdf81b7f98b980b18495ec28f1b5791ac3bfe3eea9"
[[package]]
name = "utf-8"
version = "0.7.6"

View File

@ -15,7 +15,7 @@ tauri-build = { version = "1.2", features = [] }
[dependencies]
serde = { version = "1.0", features = ["derive"] }
tauri = { version = "1.2", features = ["dialog-open", "path-all", "shell-open", "system-tray", "window-start-dragging"] }
tauri = { version = "1.2", features = ["dialog-open", "path-all", "protocol-asset", "shell-open", "system-tray", "window-start-dragging"] }
tauri-plugin-window-state = { git = "https://github.com/tauri-apps/plugins-workspace", branch = "dev" }
tauri-plugin-log = { git = "https://github.com/tauri-apps/plugins-workspace", branch = "dev", features = ["colored"] }
log = "0.4.17"
@ -31,6 +31,9 @@ sentry = "0.27"
walkdir = "2.3.2"
anyhow = "1.0.69"
tempfile = "3.3.0"
reqwest = "0.11.14"
md5 = "0.7.0"
urlencoding = "2.1.2"
[features]
# by default Tauri runs in production mode

View File

@ -35,6 +35,42 @@ fn app_title() -> String {
}
}
fn build_asset_url(path: &str) -> String {
format!("asset://localhost/{}", urlencoding::encode(path))
}
fn proxy_image(handle: tauri::AppHandle, src: &str) -> Result<String> {
if src.starts_with("asset://") {
return Ok(src.to_string());
}
let images_dir = handle
.path_resolver()
.app_cache_dir()
.unwrap()
.join("images");
let hash = md5::compute(src);
let ext = src.split('.').last().unwrap_or("jpg");
let save_to = images_dir.join(format!("{:X}.{}", hash, ext));
if save_to.exists() {
return Ok(build_asset_url(&save_to.display().to_string()));
}
let resp = reqwest::blocking::get(src)?;
if !resp.status().is_success() {
log::error!("Failed to download picture {}", src);
return Ok(src.to_string());
}
let bytes = resp.bytes()?;
std::fs::create_dir_all(&images_dir)?;
std::fs::write(&save_to, bytes)?;
Ok(build_asset_url(&save_to.display().to_string()))
}
#[tauri::command]
fn list_sessions(
handle: tauri::AppHandle,
@ -69,12 +105,30 @@ fn get_user(handle: tauri::AppHandle) -> Result<Option<users::User>, Error> {
let storage = storage::Storage::from_path_resolver(&path_resolver);
let users_storage = users::Storage::new(storage);
users_storage.get().map_err(|e| {
match users_storage.get().map_err(|e| {
log::error!("{:#}", e);
Error {
message: "Failed to get user".to_string(),
}
})
})? {
Some(user) => {
let local_picture = match proxy_image(handle, &user.picture) {
Ok(picture) => picture,
Err(e) => {
log::error!("{:#}", e);
user.picture
}
};
let user = users::User {
picture: local_picture.to_string(),
..user
};
Ok(Some(user))
}
None => Ok(None),
}
}
#[tauri::command]

View File

@ -20,6 +20,13 @@
"all": false,
"open": true
},
"protocol": {
"all": false,
"asset": true,
"assetScope": [
"$APPCACHE/images/*"
]
},
"window": {
"all": false,
"startDragging": true
@ -43,7 +50,7 @@
"targets": ["dmg", "updater"]
},
"security": {
"csp": null
"csp": "default-src 'self'; img-src 'self' asset: https://asset.localhost"
},
"systemTray": {
"iconPath": "icons/tray.png",