Merge FS and DB library raw items.

This commit is contained in:
Florian THIERRY
2026-07-17 11:54:22 +02:00
parent 4abd7dc5b9
commit ad44b181cb
5 changed files with 32 additions and 16 deletions
+13 -3
View File
@@ -20,11 +20,21 @@ impl VideoService {
pub fn list_root_folder(&self) -> Result<Vec<LibraryItem>, VideoError> { pub fn list_root_folder(&self) -> Result<Vec<LibraryItem>, VideoError> {
let read_items_with_possibly_no_id = self.video_port.list_root_folder()?; let read_items_with_possibly_no_id = self.video_port.list_root_folder()?;
let items_with_id = read_items_with_possibly_no_id.iter()
let new_items = read_items_with_possibly_no_id.iter()
.filter(|item| item.id.is_none())
.map(LibraryRawItem::map_to_library_item) .map(LibraryRawItem::map_to_library_item)
.collect(); .collect();
self.video_port.save_all(&items_with_id)?;
Ok(items_with_id) let already_existing_items = read_items_with_possibly_no_id.iter()
.filter(|item| item.id.is_some())
.map(LibraryRawItem::map_to_library_item)
.collect::<Vec<LibraryItem>>();
self.video_port.save_all(&new_items)?;
let all_items = already_existing_items.into_iter().chain(new_items).collect();
Ok(all_items)
} }
} }
+10 -6
View File
@@ -6,6 +6,7 @@ use uuid::Uuid;
use std::env; use std::env;
use std::fs; use std::fs;
use std::fs::DirEntry; use std::fs::DirEntry;
use std::io::{Error, ErrorKind};
use lumiere_domain::video::model::video::VideoFormat::{AVI, MKV, MP4, WEBM}; use lumiere_domain::video::model::video::VideoFormat::{AVI, MKV, MP4, WEBM};
use crate::video::model::LibraryItemEntity; use crate::video::model::LibraryItemEntity;
use crate::video::repository::LibraryItemSqliteRepository; use crate::video::repository::LibraryItemSqliteRepository;
@@ -54,15 +55,17 @@ impl LibraryItemAdapter {
Ok(library_raw_item) Ok(library_raw_item)
} }
fn get_all_library_items_from_db(&self) -> Result<Vec<LibraryItem>, VideoError> { fn get_all_library_items_from_db(&self) -> Result<Vec<LibraryRawItem>, Error> {
self.repository.get_all_of_root_folder().map_err(|error| VideoError::FolderBrowsingTechnicalIssue) self.repository.get_all_of_root_folder().map_err(|error| Error::new(ErrorKind::Other, "Unable to retrieve the library items of root folder from database."))
.map(LibraryItemEntity::to_library_item) .and_then(|entities| entities.into_iter()
.map(LibraryItemEntity::to_library_raw_item)
.collect::<Result<Vec<LibraryRawItem>, _>>())
} }
fn merge_item_lists(file_system_items: Vec<LibraryRawItem>, db_items: Vec<LibraryRawItem>) -> Vec<LibraryRawItem> { fn merge_item_lists(file_system_items: Vec<LibraryRawItem>, db_items: Vec<LibraryRawItem>) -> Vec<LibraryRawItem> {
let file_system_items_which_are_not_in_database: Vec<LibraryRawItem> = file_system_items.into_iter() let file_system_items_which_are_not_in_database = file_system_items.into_iter()
.filter(|file_system_item| !Self::does_item_belong_to_db_items(&db_items, &file_system_item)) .filter(|file_system_item| !Self::does_item_belong_to_db_items(&db_items, &file_system_item))
.collect(); .collect::<Vec<LibraryRawItem>>();
db_items.into_iter().chain(file_system_items_which_are_not_in_database).collect() db_items.into_iter().chain(file_system_items_which_are_not_in_database).collect()
} }
@@ -76,7 +79,8 @@ impl LibraryItemAdapter {
impl VideoPort for LibraryItemAdapter { impl VideoPort for LibraryItemAdapter {
fn list_root_folder(&self) -> Result<Vec<LibraryRawItem>, VideoError> { fn list_root_folder(&self) -> Result<Vec<LibraryRawItem>, VideoError> {
let file_system_items = self.get_root_folder_read_library_items()?; let file_system_items = self.get_root_folder_read_library_items()?;
let db_items = self.get_all_library_items_from_db()?; let db_items = self.get_all_library_items_from_db()
.map_err(|_| VideoError::FileReadingTechnicalIssue)?;
let merged = Self::merge_item_lists(file_system_items, db_items); let merged = Self::merge_item_lists(file_system_items, db_items);
+1 -1
View File
@@ -1,4 +1,4 @@
pub mod adapter; pub mod adapter;
pub mod model; pub mod model;
pub mod video_format_detector; pub mod video_format_detector;
mod repository; pub mod repository;
+4 -4
View File
@@ -1,7 +1,7 @@
use std::fs::File; use std::fs::File;
use std::io::{Error, ErrorKind}; use std::io::{Error, ErrorKind};
use uuid::Uuid; use uuid::Uuid;
use lumiere_domain::video::model::library_item::{LibraryItem, LibraryItemType}; use lumiere_domain::video::model::library_item::{LibraryItem, LibraryItemType, LibraryRawItem};
pub struct TokioVideoFile { pub struct TokioVideoFile {
pub file: File pub file: File
@@ -50,9 +50,9 @@ impl LibraryItemEntity {
} }
} }
pub(crate) fn to_library_item(&self) -> Result<LibraryItem, Error> { pub(crate) fn to_library_raw_item(self) -> Result<LibraryRawItem, Error> {
let library_item = LibraryItem { let library_item = LibraryRawItem {
id: self.id.clone(), id: Some(self.id.clone()),
name: self.name.clone(), name: self.name.clone(),
r#type: Self::map_type_from_i8(self.r#type)? r#type: Self::map_type_from_i8(self.r#type)?
}; };
+3 -1
View File
@@ -13,6 +13,7 @@ use lumiere_infrastructure::video::adapter::LibraryItemAdapter;
use rusqlite::Connection; use rusqlite::Connection;
use std::io::{Error, ErrorKind}; use std::io::{Error, ErrorKind};
use std::sync::{Arc, Mutex}; use std::sync::{Arc, Mutex};
use lumiere_infrastructure::video::repository::LibraryItemSqliteRepository;
pub struct ApplicationContext { pub struct ApplicationContext {
pub database_connection: Arc<Mutex<Connection>>, pub database_connection: Arc<Mutex<Connection>>,
@@ -55,7 +56,8 @@ impl ApplicationContext {
// let user_adapter = Box::new(UserSqliteAdapter::new(user_repository.clone())); // let user_adapter = Box::new(UserSqliteAdapter::new(user_repository.clone()));
let user_service = UserService::new(configuration_service.clone(), user_adapter.clone()); let user_service = UserService::new(configuration_service.clone(), user_adapter.clone());
let video_adapter = Box::new(LibraryItemAdapter::new()); let library_item_repository = LibraryItemSqliteRepository::new(arc_mutex_connection.clone());
let video_adapter = Box::new(LibraryItemAdapter::new(library_item_repository));
let video_service = VideoService::new(video_adapter.clone()); let video_service = VideoService::new(video_adapter.clone());
Self { Self {