mirror of
https://relay.ngit.dev/npub15qydau2hjma6ngxkl2cyar74wzyjshvl65za5k5rl69264ar2exs5cyejr/ngit-grasp.git
synced 2026-10-05 23:18:24 +00:00
rename: fetch_repository_data -> fetch_repository_data_{excluding,with}_purgatory
The old name was ambiguous - it wasn't clear whether purgatory was included or not. The two variants are now explicitly named: - fetch_repository_data_excluding_purgatory: DB only - fetch_repository_data_with_purgatory: DB + purgatory overlay SyncContext trait method also renamed to fetch_repository_data_with_purgatory to match the free function it delegates to.
This commit is contained in:
@@ -234,7 +234,7 @@ pub struct RepositoryData {
|
||||
///
|
||||
/// This performs a single database query to fetch both announcement and state events,
|
||||
/// which is more efficient than separate queries.
|
||||
pub async fn fetch_repository_data(
|
||||
pub async fn fetch_repository_data_excluding_purgatory(
|
||||
database: &SharedDatabase,
|
||||
identifier: &str,
|
||||
) -> Result<RepositoryData> {
|
||||
@@ -298,7 +298,7 @@ pub async fn fetch_repository_data_with_purgatory(
|
||||
identifier: &str,
|
||||
) -> Result<RepositoryData> {
|
||||
// First, fetch from database
|
||||
let mut repo_data = fetch_repository_data(database, identifier).await?;
|
||||
let mut repo_data = fetch_repository_data_excluding_purgatory(database, identifier).await?;
|
||||
|
||||
// Then, add announcements from purgatory
|
||||
let purgatory_announcements = purgatory.get_announcements_by_identifier(identifier);
|
||||
@@ -511,7 +511,7 @@ pub async fn get_authorization_from_db(
|
||||
identifier: &str,
|
||||
) -> Result<AuthorizationResult> {
|
||||
// Fetch all repository data with a single query
|
||||
let repo_data = fetch_repository_data(database, identifier).await?;
|
||||
let repo_data = fetch_repository_data_excluding_purgatory(database, identifier).await?;
|
||||
|
||||
if repo_data.announcements.is_empty() {
|
||||
return Ok(AuthorizationResult::denied(
|
||||
|
||||
+23
-22
@@ -38,8 +38,8 @@ use tracing::{debug, info, warn};
|
||||
use nostr_sdk::Event;
|
||||
|
||||
use crate::git::authorization::{
|
||||
collect_authorized_maintainers, fetch_repository_data, fetch_repository_data_with_purgatory,
|
||||
RepositoryData,
|
||||
collect_authorized_maintainers, fetch_repository_data_excluding_purgatory,
|
||||
fetch_repository_data_with_purgatory, RepositoryData,
|
||||
};
|
||||
use crate::git::{self, oid_exists};
|
||||
use crate::nostr::builder::{Nip34WritePolicy, SharedDatabase};
|
||||
@@ -933,20 +933,21 @@ async fn process_purgatory_state_events(
|
||||
// IMPORTANT: Use fetch_repository_data_with_purgatory to include announcements
|
||||
// that may still be in purgatory (not yet promoted). This ensures authorization
|
||||
// works correctly even if the announcement promotion happens in the same batch.
|
||||
let mut db_repo_data = match fetch_repository_data_with_purgatory(database, purgatory, identifier).await {
|
||||
Ok(data) => data,
|
||||
Err(e) => {
|
||||
warn!(
|
||||
identifier = %identifier,
|
||||
error = %e,
|
||||
"Failed to fetch repository data for purgatory state events"
|
||||
);
|
||||
result
|
||||
.errors
|
||||
.push(format!("Failed to fetch repo data: {}", e));
|
||||
return result;
|
||||
}
|
||||
};
|
||||
let mut db_repo_data =
|
||||
match fetch_repository_data_with_purgatory(database, purgatory, identifier).await {
|
||||
Ok(data) => data,
|
||||
Err(e) => {
|
||||
warn!(
|
||||
identifier = %identifier,
|
||||
error = %e,
|
||||
"Failed to fetch repository data for purgatory state events"
|
||||
);
|
||||
result
|
||||
.errors
|
||||
.push(format!("Failed to fetch repo data: {}", e));
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
// Process each state event in chronological order
|
||||
for entry in &purgatory_states {
|
||||
@@ -1231,7 +1232,7 @@ async fn process_purgatory_pr_events(
|
||||
// NOTE: Only fetch from database, NOT purgatory. PR events should only be
|
||||
// released from purgatory when the announcement has been promoted (validated).
|
||||
// This ensures we don't accept PR events for announcements that fail validation.
|
||||
let db_repo_data = match fetch_repository_data(database, identifier).await {
|
||||
let db_repo_data = match fetch_repository_data_excluding_purgatory(database, identifier).await {
|
||||
Ok(data) => data,
|
||||
Err(e) => {
|
||||
warn!(
|
||||
@@ -1372,7 +1373,9 @@ async fn process_purgatory_announcements(
|
||||
error = %e,
|
||||
"Failed to parse owner pubkey"
|
||||
);
|
||||
result.errors.push(format!("Failed to parse owner pubkey: {}", e));
|
||||
result
|
||||
.errors
|
||||
.push(format!("Failed to parse owner pubkey: {}", e));
|
||||
return result;
|
||||
}
|
||||
};
|
||||
@@ -1450,10 +1453,8 @@ async fn process_purgatory_announcements(
|
||||
}
|
||||
|
||||
// Re-process events from hot cache
|
||||
let dummy_addr = SocketAddr::new(
|
||||
IpAddr::V4(Ipv4Addr::LOCALHOST),
|
||||
0,
|
||||
);
|
||||
let dummy_addr =
|
||||
SocketAddr::new(IpAddr::V4(Ipv4Addr::LOCALHOST), 0);
|
||||
for hot_event in hot_events {
|
||||
info!(
|
||||
event_id = %hot_event.id,
|
||||
|
||||
@@ -7,7 +7,7 @@ use nostr_relay_builder::prelude::Event;
|
||||
|
||||
use super::PolicyContext;
|
||||
use crate::git;
|
||||
use crate::git::authorization::{collect_authorized_maintainers, fetch_repository_data};
|
||||
use crate::git::authorization::{collect_authorized_maintainers, fetch_repository_data_excluding_purgatory};
|
||||
|
||||
/// Policy for validating PR and PR Update events
|
||||
#[derive(Clone)]
|
||||
@@ -131,7 +131,7 @@ impl PrEventPolicy {
|
||||
// only be accepted for announcements that have been promoted (validated).
|
||||
// If the announcement is still in purgatory, the PR event should also go
|
||||
// to purgatory and wait for the announcement to be promoted.
|
||||
let db_repo_data = fetch_repository_data(&self.ctx.database, &identifier).await?;
|
||||
let db_repo_data = fetch_repository_data_excluding_purgatory(&self.ctx.database, &identifier).await?;
|
||||
|
||||
// Extract owner pubkey from source repo path
|
||||
let owner_pubkey = crate::git::sync::extract_owner_from_repo_path(
|
||||
@@ -211,7 +211,7 @@ impl PrEventPolicy {
|
||||
// only be accepted for announcements that have been promoted (validated).
|
||||
// If the announcement is still in purgatory, the PR event should also go
|
||||
// to purgatory and wait for the announcement to be promoted.
|
||||
let db_repo_data = fetch_repository_data(&self.ctx.database, identifier).await?;
|
||||
let db_repo_data = fetch_repository_data_excluding_purgatory(&self.ctx.database, identifier).await?;
|
||||
|
||||
// 3. Extract list of maintainers from "a 30617:<maintainer>:<identifier>" tags
|
||||
let mut maintainer_pubkeys = std::collections::HashSet::new();
|
||||
|
||||
@@ -87,7 +87,10 @@ pub trait SyncContext: Send + Sync {
|
||||
///
|
||||
/// # Returns
|
||||
/// Repository data including announcements and state events
|
||||
async fn fetch_repository_data(&self, identifier: &str) -> Result<RepositoryData>;
|
||||
async fn fetch_repository_data_with_purgatory(
|
||||
&self,
|
||||
identifier: &str,
|
||||
) -> Result<RepositoryData>;
|
||||
|
||||
/// Get all OIDs needed for purgatory events with this identifier.
|
||||
///
|
||||
@@ -283,7 +286,10 @@ impl SyncContext for RealSyncContext {
|
||||
urls
|
||||
}
|
||||
|
||||
async fn fetch_repository_data(&self, identifier: &str) -> Result<RepositoryData> {
|
||||
async fn fetch_repository_data_with_purgatory(
|
||||
&self,
|
||||
identifier: &str,
|
||||
) -> Result<RepositoryData> {
|
||||
// Use the purgatory-aware variant so that clone URLs from announcements still
|
||||
// in purgatory (not yet promoted) are available. Without this, the sync loop
|
||||
// would find no URLs to fetch from and the announcement could never be promoted
|
||||
@@ -585,7 +591,7 @@ pub mod mock {
|
||||
/// assert_eq!(mock.fetch_log(), vec!["https://github.com/foo/bar.git"]);
|
||||
/// ```
|
||||
pub struct MockSyncContext {
|
||||
/// Repository data to return from fetch_repository_data
|
||||
/// Repository data to return from fetch_repository_data_with_purgatory
|
||||
repo_data: RwLock<Option<RepositoryData>>,
|
||||
|
||||
/// Clone URLs available for the repository (from announcements)
|
||||
@@ -732,7 +738,10 @@ pub mod mock {
|
||||
self.pr_clone_urls.clone()
|
||||
}
|
||||
|
||||
async fn fetch_repository_data(&self, _identifier: &str) -> Result<RepositoryData> {
|
||||
async fn fetch_repository_data_with_purgatory(
|
||||
&self,
|
||||
_identifier: &str,
|
||||
) -> Result<RepositoryData> {
|
||||
// Return stored repo_data or create a minimal one with clone URLs
|
||||
if let Some(data) = self.repo_data.read().unwrap().as_ref() {
|
||||
// Clone the data - this is a test mock so efficiency isn't critical
|
||||
|
||||
@@ -104,7 +104,7 @@ pub async fn sync_identifier_next_url<C: SyncContext + ?Sized>(
|
||||
}
|
||||
|
||||
// 3. Get repository data
|
||||
let repo_data = match ctx.fetch_repository_data(identifier).await {
|
||||
let repo_data = match ctx.fetch_repository_data_with_purgatory(identifier).await {
|
||||
Ok(data) => data,
|
||||
Err(e) => {
|
||||
debug!(
|
||||
@@ -228,7 +228,7 @@ pub async fn get_throttled_domains_with_untried_urls<C: SyncContext + ?Sized>(
|
||||
throttle_manager: &ThrottleManager,
|
||||
git_naughty_list: &NaughtyListTracker,
|
||||
) -> Vec<ThrottledDomainInfo> {
|
||||
let repo_data = match ctx.fetch_repository_data(identifier).await {
|
||||
let repo_data = match ctx.fetch_repository_data_with_purgatory(identifier).await {
|
||||
Ok(data) => data,
|
||||
Err(_) => return vec![],
|
||||
};
|
||||
@@ -333,7 +333,7 @@ pub async fn sync_identifier_from_url<C: SyncContext + ?Sized>(
|
||||
};
|
||||
|
||||
// Get repository data for target repo path
|
||||
let repo_data = match ctx.fetch_repository_data(identifier).await {
|
||||
let repo_data = match ctx.fetch_repository_data_with_purgatory(identifier).await {
|
||||
Ok(data) => data,
|
||||
Err(e) => {
|
||||
debug!(
|
||||
|
||||
Reference in New Issue
Block a user