diff --git a/mediarepo-ui/README.md b/mediarepo-ui/README.md
index c04b2ee..b66efa2 100644
--- a/mediarepo-ui/README.md
+++ b/mediarepo-ui/README.md
@@ -1,27 +1,26 @@
-# MediarepoUi
+
+mediarepo-ui
+
+This repository is a work in progress
-This project was generated with [Angular CLI](https://github.com/angular/angular-cli) version 12.2.9.
+- - -
-## Development server
+This repository contains a frontend client to connect to the [mediarepo-daemon](https://github.com/Trivernis/mediarepo-daemon).
+It is written in tauri (yay).
-Run `ng serve` for a dev server. Navigate to `http://localhost:4200/`. The app will automatically reload if you change any of the source files.
+## Usage
-## Code scaffolding
+Refer to [the tauri documentation](https://tauri.studio/en/docs/getting-started) for information about setting up your environment to build this project.
+With the `cargo-tauri` tooling installed you can run
+```
+cargo tauri dev
+```
+to start the application in development mode or
+```
+cargo tauri build
+```
+to bundle the application.
-Run `ng generate component component-name` to generate a new component. You can also use `ng generate directive|pipe|service|class|guard|interface|enum|module`.
+## License
-## Build
-
-Run `ng build` to build the project. The build artifacts will be stored in the `dist/` directory.
-
-## Running unit tests
-
-Run `ng test` to execute the unit tests via [Karma](https://karma-runner.github.io).
-
-## Running end-to-end tests
-
-Run `ng e2e` to execute the end-to-end tests via a platform of your choice. To use this command, you need to first add a package that implements end-to-end testing capabilities.
-
-## Further help
-
-To get more help on the Angular CLI use `ng help` or go check out the [Angular CLI Overview and Command Reference](https://angular.io/cli) page.
+GPL-3
diff --git a/mediarepo-ui/src-tauri/src/commands/files.rs b/mediarepo-ui/src-tauri/src/commands/files.rs
index 8d908bd..877ff10 100644
--- a/mediarepo-ui/src-tauri/src/commands/files.rs
+++ b/mediarepo-ui/src-tauri/src/commands/files.rs
@@ -1,13 +1,13 @@
-use crate::commands::get_ipc;
+use crate::commands::{add_once_buffer, get_ipc};
use mediarepo::requests::{FindFilesByTagsRequest, GetFileThumbnailsRequest, ReadFileRequest};
use mediarepo::responses::{FileResponse, ThumbnailResponse};
use crate::context::Context;
-use crate::error::{AppError, AppResult};
+use crate::error::AppResult;
#[tauri::command]
pub async fn get_all_files(context: tauri::State<'_, Context>) -> AppResult> {
- let ipc = get_ipc(context).await?;
+ let ipc = get_ipc(&context).await?;
let response = ipc
.emitter
.emit_to("files", "all_files", ())
@@ -23,7 +23,7 @@ pub async fn find_files(
tags: Vec,
context: tauri::State<'_, Context>,
) -> AppResult> {
- let ipc = get_ipc(context).await?;
+ let ipc = get_ipc(&context).await?;
let response = ipc
.emitter
.emit_to("files", "find_files", FindFilesByTagsRequest { tags })
@@ -36,17 +36,20 @@ pub async fn find_files(
#[tauri::command]
pub async fn read_file_by_hash(
hash: String,
+ mime: String,
context: tauri::State<'_, Context>,
-) -> AppResult> {
- let ipc = get_ipc(context).await?;
+) -> AppResult {
+ let ipc = get_ipc(&context).await?;
let response = ipc
.emitter
- .emit_to("files", "read_file", ReadFileRequest::Hash(hash))
+ .emit_to("files", "read_file", ReadFileRequest::Hash(hash.clone()))
.await?
.await_reply(&ipc)
.await?;
+ let raw_data = response.data_raw().to_vec();
+ let uri = add_once_buffer(&context, hash, mime, raw_data);
- Ok(response.data_raw().to_vec())
+ Ok(uri)
}
#[tauri::command]
@@ -54,7 +57,7 @@ pub async fn get_thumbnails(
hash: String,
context: tauri::State<'_, Context>,
) -> AppResult> {
- let ipc = get_ipc(context).await?;
+ let ipc = get_ipc(&context).await?;
let response = ipc
.emitter
.emit_to(
@@ -72,19 +75,18 @@ pub async fn get_thumbnails(
#[tauri::command]
pub async fn read_thumbnail(
hash: String,
+ mime: String,
context: tauri::State<'_, Context>,
-) -> AppResult> {
- let ipc = context.ipc.read().await;
- if let Some(ipc) = &*ipc {
- let response = ipc
- .emitter
- .emit_to("files", "read_thumbnail", hash)
- .await?
- .await_reply(&ipc)
- .await?;
+) -> AppResult {
+ let ipc = get_ipc(&context).await?;
+ let response = ipc
+ .emitter
+ .emit_to("files", "read_thumbnail", hash.clone())
+ .await?
+ .await_reply(&ipc)
+ .await?;
+ let raw_data = response.data_raw().to_vec();
+ let uri = add_once_buffer(&context, hash, mime, raw_data);
- Ok(response.data_raw().to_vec())
- } else {
- Err(AppError::new("No ipc connection."))
- }
+ Ok(uri)
}
diff --git a/mediarepo-ui/src-tauri/src/commands/mod.rs b/mediarepo-ui/src-tauri/src/commands/mod.rs
index 594b24c..91aa347 100644
--- a/mediarepo-ui/src-tauri/src/commands/mod.rs
+++ b/mediarepo-ui/src-tauri/src/commands/mod.rs
@@ -1,6 +1,6 @@
use rmp_ipc::ipc::context::Context as IPCContext;
-use crate::context::Context;
+use crate::context::{Context, OnceBuffer};
use crate::error::{AppError, AppResult};
pub mod files;
@@ -20,7 +20,22 @@ pub async fn emit_info(context: tauri::State<'_, Context>) -> AppResult<()> {
Ok(())
}
-pub async fn get_ipc(context: tauri::State<'_, Context>) -> AppResult {
+pub async fn get_ipc(context: &tauri::State<'_, Context>) -> AppResult {
let ipc = context.ipc.read().await;
(ipc.clone()).ok_or(AppError::new("No ipc connection."))
}
+
+/// Adds a once-buffer to the buffer store
+pub fn add_once_buffer(
+ context: &tauri::State<'_, Context>,
+ key: String,
+ mime: String,
+ buf: Vec,
+) -> String {
+ let uri = format!("once://{}", key);
+ let once_buffer = OnceBuffer { mime, buf };
+ let mut once_buffers = context.once_buffers.lock().unwrap();
+ once_buffers.insert(key, once_buffer);
+
+ uri
+}
diff --git a/mediarepo-ui/src-tauri/src/commands/tags.rs b/mediarepo-ui/src-tauri/src/commands/tags.rs
index 1770e30..8d696ba 100644
--- a/mediarepo-ui/src-tauri/src/commands/tags.rs
+++ b/mediarepo-ui/src-tauri/src/commands/tags.rs
@@ -9,7 +9,7 @@ pub async fn get_tags_for_file(
hash: String,
context: tauri::State<'_, Context>,
) -> AppResult> {
- let ipc = get_ipc(context).await?;
+ let ipc = get_ipc(&context).await?;
let response = ipc
.emitter
.emit_to("tags", "tags_for_file", FileIdentifier::Hash(hash))
diff --git a/mediarepo-ui/src-tauri/src/context.rs b/mediarepo-ui/src-tauri/src/context.rs
index 8e04277..34ef383 100644
--- a/mediarepo-ui/src-tauri/src/context.rs
+++ b/mediarepo-ui/src-tauri/src/context.rs
@@ -1,14 +1,22 @@
use crate::commands::repo::Repository;
use crate::settings::Settings;
use rmp_ipc::ipc::context::Context as IPCContext;
+use std::collections::HashMap;
use std::sync::Arc;
+use std::sync::Mutex as StdMutex;
use tokio::sync::RwLock;
+pub struct OnceBuffer {
+ pub mime: String,
+ pub buf: Vec,
+}
+
#[derive(Clone)]
pub struct Context {
pub active_repository: Arc>>,
pub ipc: Arc>>,
pub settings: Arc>,
+ pub once_buffers: Arc>>,
}
impl Context {
@@ -17,6 +25,7 @@ impl Context {
ipc: Arc::new(RwLock::new(None)),
active_repository: Arc::new(RwLock::new(None)),
settings: Arc::new(RwLock::new(settings)),
+ once_buffers: Arc::new(StdMutex::new(HashMap::new())),
}
}
}
diff --git a/mediarepo-ui/src-tauri/src/main.rs b/mediarepo-ui/src-tauri/src/main.rs
index 189a6de..9ec99f2 100644
--- a/mediarepo-ui/src-tauri/src/main.rs
+++ b/mediarepo-ui/src-tauri/src/main.rs
@@ -11,6 +11,8 @@ use crate::commands::repo::{
use crate::commands::tags::*;
use crate::context::Context;
use crate::settings::load_settings;
+use tauri::http::ResponseBuilder;
+use tauri::Manager;
mod commands;
pub mod context;
@@ -24,6 +26,25 @@ fn main() {
tauri::Builder::default()
.manage(context)
+ .register_uri_scheme_protocol("once", |app, request| {
+ let context = app.state::();
+ let resource_key = request.uri().trim_start_matches("once://");
+ let buffer = {
+ let mut buffers = context.once_buffers.lock().unwrap();
+ buffers.remove(resource_key)
+ };
+ if let Some(buffer) = buffer {
+ ResponseBuilder::new()
+ .mimetype(&buffer.mime)
+ .status(200)
+ .body(buffer.buf)
+ } else {
+ ResponseBuilder::new()
+ .mimetype("text/plain")
+ .status(404)
+ .body("Resource not found".as_bytes().to_vec())
+ }
+ })
.invoke_handler(tauri::generate_handler![
get_repositories,
add_repository,
diff --git a/mediarepo-ui/src/app/services/file/file.service.ts b/mediarepo-ui/src/app/services/file/file.service.ts
index b01cb3b..dd4d4a7 100644
--- a/mediarepo-ui/src/app/services/file/file.service.ts
+++ b/mediarepo-ui/src/app/services/file/file.service.ts
@@ -26,18 +26,14 @@ export class FileService {
this.displayedFiles.next(files);
}
- public async readFile(hash: string, mime_type: string): Promise {
- const data = await invoke("read_file_by_hash", {hash});
- const blob = new Blob([new Uint8Array(data)], {type: mime_type});
-
- return this.createSafeObjectUrl(blob);
+ public async readFile(hash: string, mime: string): Promise {
+ const once_uri = await invoke("read_file_by_hash", {hash, mime});
+ return this.sanitizer.bypassSecurityTrustResourceUrl(once_uri);
}
public async readThumbnail(thumbnail: Thumbnail): Promise {
- let data = await invoke("read_thumbnail", {hash: thumbnail.hash});
- const blob = new Blob([new Uint8Array(data)], {type: thumbnail.mime});
-
- return this.createSafeObjectUrl(blob);
+ let once_uri = await invoke("read_thumbnail", {hash: thumbnail.hash, mime: thumbnail.mime});
+ return this.sanitizer.bypassSecurityTrustResourceUrl(once_uri);
}
public async getThumbnails(hash: string): Promise {