feat: v2 rewrite — hexagonal arch, ActivityPub federation, NATS, deployment-ready #1

Merged
GKaszewski merged 334 commits from v2 into master 2026-05-16 09:42:43 +00:00
2 changed files with 42 additions and 0 deletions
Showing only changes of commit fce819be7f - Show all commits

View File

@@ -1330,6 +1330,42 @@ impl domain::ports::OutboundFederationPort for ActivityPubService {
} }
} }
#[async_trait::async_trait]
impl domain::ports::FederationActionPort for ActivityPubService {
async fn lookup_actor(
&self,
handle: &str,
) -> Result<domain::models::remote_actor::RemoteActor, domain::errors::DomainError> {
let data = self.federation_config.to_request_data();
let actor: crate::actors::DbActor =
webfinger_resolve_actor(handle, &data)
.await
.map_err(|e: crate::error::Error| {
domain::errors::DomainError::ExternalService(e.to_string())
})?;
Ok(domain::models::remote_actor::RemoteActor {
url: actor.ap_id.to_string(),
handle: actor.username.clone(),
display_name: actor.bio.clone(),
inbox_url: actor.inbox_url.to_string(),
shared_inbox_url: None,
public_key: actor.public_key_pem.clone(),
avatar_url: actor.avatar_url.as_ref().map(|u| u.to_string()),
last_fetched_at: actor.last_refreshed_at,
})
}
async fn follow_remote(
&self,
local_user_id: &domain::value_objects::UserId,
handle: &str,
) -> Result<(), domain::errors::DomainError> {
self.follow(local_user_id.as_uuid(), handle)
.await
.map_err(|e| domain::errors::DomainError::ExternalService(e.to_string()))
}
}
#[cfg(test)] #[cfg(test)]
#[path = "tests/service.rs"] #[path = "tests/service.rs"]
mod tests; mod tests;

View File

@@ -1,3 +1,9 @@
fn _assert_impl_federation_action_port()
where
crate::service::ActivityPubService: domain::ports::FederationActionPort,
{
}
use super::*; use super::*;
use crate::repository::{Follower, FollowerStatus, RemoteActor}; use crate::repository::{Follower, FollowerStatus, RemoteActor};