refactor: LOW+MEDIUM cleanups — CQRS DiaryQuery/GoalCommand+GoalQuery,

test-helpers out of production, decompose get_user_profile_html,
dedup secure_flag, remove vestigial social_query, drop
PersistedImportSession, LoginCommand rename, DeleteAccountDeps,
PersonId macro, ReviewSortBy rename, TUI Command for fs::read,
generic PaginatedResponse<T>, noop ports for production fallbacks
This commit is contained in:
2026-07-10 05:29:02 +02:00
parent 5e0dde656c
commit 6a9b4e5c00
52 changed files with 405 additions and 298 deletions

View File

@@ -5,7 +5,7 @@ use domain::{
errors::DomainError,
events::DomainEvent,
ports::{
GoalRepository, LocalApContentQuery, MovieQuery, ReviewRepository, StatsRepository,
GoalQuery, LocalApContentQuery, MovieQuery, ReviewRepository, StatsRepository,
UserFederationSettingsQuery,
},
value_objects::{MovieId, ReviewId, UserId},
@@ -22,7 +22,7 @@ pub struct ActivityPubEventHandler {
content_query: Arc<dyn LocalApContentQuery>,
review_repo: Arc<dyn ReviewRepository>,
movie_repo: Arc<dyn MovieQuery>,
goal_repo: Arc<dyn GoalRepository>,
goal_repo: Arc<dyn GoalQuery>,
stats_repo: Arc<dyn StatsRepository>,
federation_settings: Arc<dyn UserFederationSettingsQuery>,
base_url: String,
@@ -35,7 +35,7 @@ impl ActivityPubEventHandler {
content_query: Arc<dyn LocalApContentQuery>,
review_repo: Arc<dyn ReviewRepository>,
movie_repo: Arc<dyn MovieQuery>,
goal_repo: Arc<dyn GoalRepository>,
goal_repo: Arc<dyn GoalQuery>,
stats_repo: Arc<dyn StatsRepository>,
federation_settings: Arc<dyn UserFederationSettingsQuery>,
base_url: String,

View File

@@ -4,7 +4,7 @@ use async_trait::async_trait;
use chrono::DateTime;
use domain::{
models::RemoteGoalEntry,
ports::{GoalRepository, RemoteGoalRepository},
ports::{GoalQuery, RemoteGoalRepository},
value_objects::UserId,
};
use k_ap::{ApContentReader, ApObjectHandler};
@@ -15,7 +15,7 @@ use crate::urls::{actor_url, goal_url};
pub struct GoalObjectHandler {
pub remote_goal_repo: Arc<dyn RemoteGoalRepository>,
pub goal_repo: Arc<dyn GoalRepository>,
pub goal_repo: Arc<dyn GoalQuery>,
pub base_url: String,
}

View File

@@ -53,8 +53,8 @@ pub struct ActivityPubDeps {
pub local_ap_content: std::sync::Arc<dyn domain::ports::LocalApContentQuery>,
pub movie_repo: std::sync::Arc<dyn domain::ports::MovieQuery>,
pub review_repo: std::sync::Arc<dyn domain::ports::ReviewRepository>,
pub diary_repo: std::sync::Arc<dyn domain::ports::DiaryRepository>,
pub goal_repo: std::sync::Arc<dyn domain::ports::GoalRepository>,
pub diary_repo: std::sync::Arc<dyn domain::ports::DiaryQuery>,
pub goal_repo: std::sync::Arc<dyn domain::ports::GoalQuery>,
pub stats_repo: std::sync::Arc<dyn domain::ports::StatsRepository>,
pub user_repo: std::sync::Arc<dyn domain::ports::UserRepository>,
pub federation_settings: std::sync::Arc<dyn domain::ports::UserFederationSettingsQuery>,

View File

@@ -4,7 +4,7 @@ use async_trait::async_trait;
use domain::{
events::DomainEvent,
models::ReviewSource,
ports::{DiaryRepository, EventPublisher, LocalApContentQuery, MovieQuery},
ports::{DiaryQuery, EventPublisher, LocalApContentQuery, MovieQuery},
value_objects::{Comment, ExternalMetadataId, MovieId, Rating, ReviewId, UserId},
};
use k_ap::{ApContentReader, ApObjectHandler};
@@ -17,7 +17,7 @@ use crate::urls::{actor_url, review_url};
pub struct ReviewObjectHandler {
pub content_query: Arc<dyn LocalApContentQuery>,
pub movie_repo: Arc<dyn MovieQuery>,
pub diary_repo: Arc<dyn DiaryRepository>,
pub diary_repo: Arc<dyn DiaryQuery>,
pub review_store: Arc<dyn RemoteReviewRepository>,
pub event_publisher: Arc<dyn EventPublisher>,
pub base_url: String,

View File

@@ -5,7 +5,7 @@ use domain::{
DiaryEntry, DiaryFilter, FeedEntry, MovieStats, ReviewHistory, ReviewSortBy,
collections::{PageParams, Paginated},
},
ports::DiaryRepository,
ports::DiaryQuery,
value_objects::{MovieId, UserId},
};
use futures::stream::BoxStream;
@@ -202,7 +202,7 @@ impl PostgresDiaryRepository {
}
#[async_trait]
impl DiaryRepository for PostgresDiaryRepository {
impl DiaryQuery for PostgresDiaryRepository {
async fn query_diary(
&self,
filter: &DiaryFilter,

View File

@@ -2,7 +2,7 @@ use async_trait::async_trait;
use domain::{
errors::DomainError,
models::{Goal, GoalType},
ports::GoalRepository,
ports::{GoalCommand, GoalQuery},
value_objects::{GoalId, UserId},
};
use sqlx::{PgPool, Row};
@@ -25,7 +25,7 @@ impl PostgresGoalRepository {
}
#[async_trait]
impl GoalRepository for PostgresGoalRepository {
impl GoalCommand for PostgresGoalRepository {
async fn save(&self, goal: &Goal) -> Result<(), DomainError> {
let id = goal.id().value().to_string();
let user_id = goal.user_id().value().to_string();
@@ -84,7 +84,10 @@ impl GoalRepository for PostgresGoalRepository {
}
Ok(())
}
}
#[async_trait]
impl GoalQuery for PostgresGoalRepository {
async fn find_by_user_and_year(
&self,
user_id: &UserId,

View File

@@ -82,7 +82,7 @@ pub struct PostgresWireOutput {
pub movie_command: std::sync::Arc<dyn domain::ports::MovieCommand>,
pub movie_query: std::sync::Arc<dyn domain::ports::MovieQuery>,
pub review: std::sync::Arc<dyn domain::ports::ReviewRepository>,
pub diary: std::sync::Arc<dyn domain::ports::DiaryRepository>,
pub diary: std::sync::Arc<dyn domain::ports::DiaryQuery>,
pub stats: std::sync::Arc<dyn domain::ports::StatsRepository>,
pub user: std::sync::Arc<dyn domain::ports::UserRepository>,
pub import_session: std::sync::Arc<dyn domain::ports::ImportSessionRepository>,
@@ -92,7 +92,8 @@ pub struct PostgresWireOutput {
pub ap_content: std::sync::Arc<dyn domain::ports::LocalApContentQuery>,
pub wrapup_repo: std::sync::Arc<dyn domain::ports::WrapUpRepository>,
pub wrapup_stats: std::sync::Arc<dyn domain::ports::WrapUpStatsQuery>,
pub goal: std::sync::Arc<dyn domain::ports::GoalRepository>,
pub goal_command: std::sync::Arc<dyn domain::ports::GoalCommand>,
pub goal_query: std::sync::Arc<dyn domain::ports::GoalQuery>,
pub user_settings: std::sync::Arc<dyn domain::ports::UserSettingsRepository>,
pub federation_settings: std::sync::Arc<dyn domain::ports::UserFederationSettingsQuery>,
pub remote_goal: std::sync::Arc<dyn domain::ports::RemoteGoalRepository>,
@@ -134,7 +135,8 @@ pub async fn wire(database_url: &str) -> anyhow::Result<PostgresWireOutput> {
ap_content: std::sync::Arc::new(PostgresApContentQuery::new(pool.clone())) as _,
wrapup_repo: std::sync::Arc::new(PostgresWrapUpRepository::new(pool.clone())) as _,
wrapup_stats: std::sync::Arc::new(PostgresWrapUpStatsQuery::new(pool.clone())) as _,
goal: std::sync::Arc::new(goals::PostgresGoalRepository::new(pool.clone())) as _,
goal_command: std::sync::Arc::new(goals::PostgresGoalRepository::new(pool.clone())) as _,
goal_query: std::sync::Arc::new(goals::PostgresGoalRepository::new(pool.clone())) as _,
user_settings: std::sync::Arc::clone(&user_settings_repo) as _,
federation_settings: user_settings_repo as _,
remote_goal: std::sync::Arc::new(postgres_federation::PostgresRemoteGoalRepository::new(

View File

@@ -5,7 +5,7 @@ use domain::{
DiaryEntry, DiaryFilter, FeedEntry, MovieStats, ReviewHistory, ReviewSortBy,
collections::{PageParams, Paginated},
},
ports::DiaryRepository,
ports::DiaryQuery,
value_objects::{MovieId, UserId},
};
use futures::stream::BoxStream;
@@ -181,7 +181,7 @@ impl SqliteDiaryRepository {
}
#[async_trait]
impl DiaryRepository for SqliteDiaryRepository {
impl DiaryQuery for SqliteDiaryRepository {
async fn query_diary(
&self,
filter: &DiaryFilter,

View File

@@ -2,7 +2,7 @@ use async_trait::async_trait;
use domain::{
errors::DomainError,
models::{Goal, GoalType},
ports::GoalRepository,
ports::{GoalCommand, GoalQuery},
value_objects::{GoalId, UserId},
};
use sqlx::{Row, SqlitePool};
@@ -23,7 +23,7 @@ impl SqliteGoalRepository {
}
#[async_trait]
impl GoalRepository for SqliteGoalRepository {
impl GoalCommand for SqliteGoalRepository {
async fn save(&self, goal: &Goal) -> Result<(), DomainError> {
let id = goal.id().value().to_string();
let user_id = goal.user_id().value().to_string();
@@ -82,7 +82,10 @@ impl GoalRepository for SqliteGoalRepository {
}
Ok(())
}
}
#[async_trait]
impl GoalQuery for SqliteGoalRepository {
async fn find_by_user_and_year(
&self,
user_id: &UserId,

View File

@@ -78,7 +78,7 @@ pub struct SqliteWireOutput {
pub movie_command: std::sync::Arc<dyn domain::ports::MovieCommand>,
pub movie_query: std::sync::Arc<dyn domain::ports::MovieQuery>,
pub review: std::sync::Arc<dyn domain::ports::ReviewRepository>,
pub diary: std::sync::Arc<dyn domain::ports::DiaryRepository>,
pub diary: std::sync::Arc<dyn domain::ports::DiaryQuery>,
pub stats: std::sync::Arc<dyn domain::ports::StatsRepository>,
pub user: std::sync::Arc<dyn domain::ports::UserRepository>,
pub import_session: std::sync::Arc<dyn domain::ports::ImportSessionRepository>,
@@ -88,7 +88,8 @@ pub struct SqliteWireOutput {
pub ap_content: std::sync::Arc<dyn domain::ports::LocalApContentQuery>,
pub wrapup_repo: std::sync::Arc<dyn domain::ports::WrapUpRepository>,
pub wrapup_stats: std::sync::Arc<dyn domain::ports::WrapUpStatsQuery>,
pub goal: std::sync::Arc<dyn domain::ports::GoalRepository>,
pub goal_command: std::sync::Arc<dyn domain::ports::GoalCommand>,
pub goal_query: std::sync::Arc<dyn domain::ports::GoalQuery>,
pub user_settings: std::sync::Arc<dyn domain::ports::UserSettingsRepository>,
pub federation_settings: std::sync::Arc<dyn domain::ports::UserFederationSettingsQuery>,
pub remote_goal: std::sync::Arc<dyn domain::ports::RemoteGoalRepository>,
@@ -137,7 +138,8 @@ pub async fn wire(database_url: &str) -> anyhow::Result<SqliteWireOutput> {
ap_content: std::sync::Arc::new(SqliteApContentQuery::new(pool.clone())) as _,
wrapup_repo: std::sync::Arc::new(SqliteWrapUpRepository::new(pool.clone())) as _,
wrapup_stats: std::sync::Arc::new(SqliteWrapUpStatsQuery::new(pool.clone())) as _,
goal: std::sync::Arc::new(goals::SqliteGoalRepository::new(pool.clone())) as _,
goal_command: std::sync::Arc::new(goals::SqliteGoalRepository::new(pool.clone())) as _,
goal_query: std::sync::Arc::new(goals::SqliteGoalRepository::new(pool.clone())) as _,
user_settings: std::sync::Arc::clone(&user_settings_repo) as _,
federation_settings: user_settings_repo as _,
remote_goal: std::sync::Arc::new(sqlite_federation::SqliteRemoteGoalRepository::new(

View File

@@ -2,7 +2,7 @@ use super::*;
use domain::{
models::collections::PageParams,
models::{FeedSortBy, FollowingFilter},
ports::DiaryRepository,
ports::DiaryQuery,
};
use sqlx::SqlitePool;