mirror of
https://relay.ngit.dev/npub15qydau2hjma6ngxkl2cyar74wzyjshvl65za5k5rl69264ar2exs5cyejr/ngit-grasp.git
synced 2026-10-06 07:28:23 +00:00
refactor(grasp-audit): split ValidRepo into Sent/Served, add tolerant purgatory
- Rename ValidRepo to ValidRepoSent (announcement sent, may be in purgatory) - Add ValidRepoServed (announcement queryable after git data pushed) - Add send_event_and_note_purgatory() for tolerant purgatory detection - Update fixtures to use tolerant method instead of strict assertion - Update event_acceptance_policy tests to use ValidRepoServed This enables tests to pass regardless of purgatory implementation status while still having explicit purgatory tests that verify the behavior.
This commit is contained in:
@@ -245,7 +245,7 @@ pub async fn test_something(client: &AuditClient) -> TestResult {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// 2. Prerequisites (cached per-TestContext)
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepo).await?;
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepoSent).await?;
|
||||
|
||||
// 3. Test-specific event
|
||||
let my_event = client.create_issue(&repo, "Title", "Content", vec![])?;
|
||||
|
||||
@@ -209,6 +209,36 @@ impl AuditClient {
|
||||
Ok(event_id)
|
||||
}
|
||||
|
||||
/// Send event and note whether it entered purgatory (not served) or was served immediately.
|
||||
///
|
||||
/// This is a tolerant version of `send_event_expect_purgatory_not_served` that doesn't
|
||||
/// fail if purgatory is not observed. It returns whether purgatory was observed so
|
||||
/// fixtures can proceed regardless of relay implementation status.
|
||||
///
|
||||
/// Returns (EventId, bool) where bool = true if event was NOT served (purgatory observed).
|
||||
pub async fn send_event_and_note_purgatory(&self, event: Event) -> Result<(EventId, bool)> {
|
||||
if self.config.read_only {
|
||||
return Err(anyhow!("Client is in read-only mode"));
|
||||
}
|
||||
|
||||
let output = self.client.send_event(&event).await?;
|
||||
let event_id = *output.id();
|
||||
|
||||
// Check if any relay rejected the event and return the error message
|
||||
if !output.failed.is_empty() {
|
||||
let (relay_url, error) = output.failed.iter().next().unwrap();
|
||||
return Err(anyhow!("Relay {} rejected event: {}", relay_url, error));
|
||||
}
|
||||
|
||||
// Wait a bit for event to propagate
|
||||
tokio::time::sleep(Duration::from_millis(300)).await;
|
||||
|
||||
// Check if event is served (not in purgatory) or not served (in purgatory)
|
||||
let in_purgatory = !self.is_event_on_relay(event.id).await?;
|
||||
|
||||
Ok((event_id, in_purgatory))
|
||||
}
|
||||
|
||||
/// check if an event is on the relay
|
||||
pub async fn is_event_on_relay(&self, id: EventId) -> Result<bool> {
|
||||
Ok(!self
|
||||
|
||||
+81
-58
@@ -47,7 +47,7 @@
|
||||
//! let ctx = TestContext::new(&client);
|
||||
//!
|
||||
//! // Request a fixture - behavior depends on mode
|
||||
//! let repo = ctx.get_fixture(FixtureKind::ValidRepo).await?;
|
||||
//! let repo = ctx.get_fixture(FixtureKind::ValidRepoSent).await?;
|
||||
//! # Ok(())
|
||||
//! # }
|
||||
//! ```
|
||||
@@ -109,11 +109,11 @@ pub const PR_TEST_COMMIT_HASH: &str = "5d40fb1555a0c28bf4d650515a73aaa54d4d9bfb"
|
||||
///
|
||||
/// ## Fixture Dependencies
|
||||
///
|
||||
/// Several fixtures depend on `ValidRepo` - they all use the SAME repo_id
|
||||
/// Several fixtures depend on `ValidRepoSent` - they all use the SAME repo_id
|
||||
/// within a single TestContext instance to ensure proper fixture relationships:
|
||||
/// - `RepoState` → uses ValidRepo's repo_id
|
||||
/// - `MaintainerAnnouncement` + `MaintainerState` → uses ValidRepo's repo_id
|
||||
/// - `RecursiveMaintainerRepoAndState` → uses ValidRepo's repo_id
|
||||
/// - `RepoState` → uses ValidRepoSent's repo_id
|
||||
/// - `MaintainerAnnouncement` + `MaintainerState` → uses ValidRepoSent's repo_id
|
||||
/// - `RecursiveMaintainerRepoAndState` → uses ValidRepoSent's repo_id
|
||||
///
|
||||
/// This enables testing recursive maintainer authorization chains where multiple
|
||||
/// parties publish announcements and state events for the same repository.
|
||||
@@ -122,10 +122,16 @@ pub enum FixtureKind {
|
||||
/// Basic repository announcement (kind 30617)
|
||||
/// - Signed by owner keys (`client.keys()`)
|
||||
/// - Lists `client.maintainer_pubkey_hex()` in maintainers tag
|
||||
ValidRepo,
|
||||
ValidRepoSent,
|
||||
|
||||
/// Repository announcement that is queryable from the relay (served, not in purgatory)
|
||||
/// - Depends on OwnerStateDataPushed (git data pushed, announcement promoted)
|
||||
/// - Returns the same event as ValidRepoSent (now queryable)
|
||||
/// - Use this for tests that need to query the announcement back from the relay
|
||||
ValidRepoServed,
|
||||
|
||||
/// Repository with one issue (kind 1621)
|
||||
/// - Requires ValidRepo (reuses same repo_id)
|
||||
/// - Requires ValidRepoSent (reuses same repo_id)
|
||||
RepoWithIssue,
|
||||
|
||||
/// Repository with issue and comment (kind 1111)
|
||||
@@ -133,14 +139,14 @@ pub enum FixtureKind {
|
||||
RepoWithComment,
|
||||
|
||||
/// Repository state announcement (kind 30618) for owner
|
||||
/// - Requires ValidRepo (uses same repo_id)
|
||||
/// - Requires ValidRepoSent (uses same repo_id)
|
||||
/// - Signed by owner keys (`client.keys()`)
|
||||
/// - Points to DETERMINISTIC_COMMIT_HASH
|
||||
/// - Timestamp: 10 seconds in the past
|
||||
RepoState,
|
||||
|
||||
/// PR (Pull Request) event for the SAME repo_id as ValidRepo
|
||||
/// - Requires ValidRepo (uses same repo_id)
|
||||
/// PR (Pull Request) event for the SAME repo_id as ValidRepoSent
|
||||
/// - Requires ValidRepoSent (uses same repo_id)
|
||||
/// - Signed by `client.pr_author_keys()`
|
||||
/// - Kind 1618 (NIP-34 PR)
|
||||
/// - Includes `a` tag referencing the repo
|
||||
@@ -153,7 +159,7 @@ pub enum FixtureKind {
|
||||
/// This is a "Generated" stage fixture - the event is created but not published.
|
||||
/// Useful for tests that need the PR event ID before the event exists on the relay.
|
||||
///
|
||||
/// - Requires ValidRepo (uses same repo_id)
|
||||
/// - Requires ValidRepoSent (uses same repo_id)
|
||||
/// - Signed by `client.pr_author_keys()`
|
||||
/// - Kind 1618 (NIP-34 PR)
|
||||
/// - Includes `c` tag pointing to PR_TEST_COMMIT_HASH
|
||||
@@ -187,7 +193,7 @@ pub enum FixtureKind {
|
||||
/// (the "wrong" commit), but no PR event exists yet on the relay.
|
||||
///
|
||||
/// Server state after this fixture:
|
||||
/// - ValidRepo announcement on relay
|
||||
/// - ValidRepoSent announcement on relay
|
||||
/// - refs/nostr/<pr-event-id> exists on git server with wrong commit
|
||||
/// - PR event is NOT on relay (but returned for tests to publish later)
|
||||
///
|
||||
@@ -203,7 +209,7 @@ pub enum FixtureKind {
|
||||
/// then the PR event was published (which may trigger cleanup).
|
||||
///
|
||||
/// Server state after this fixture:
|
||||
/// - ValidRepo announcement on relay
|
||||
/// - ValidRepoSent announcement on relay
|
||||
/// - PR event is on relay
|
||||
/// - refs/nostr/<pr-event-id> may have been cleaned up (that's what tests verify)
|
||||
///
|
||||
@@ -221,7 +227,7 @@ pub enum FixtureKind {
|
||||
/// 4. **DataPushed**: Clones repo, creates deterministic commit, pushes to relay
|
||||
/// 5. **Verified**: Confirms event is served by relay
|
||||
///
|
||||
/// - Requires ValidRepo (uses same repo_id)
|
||||
/// - Requires ValidRepoSent (uses same repo_id)
|
||||
/// - State event signed by owner keys (`client.keys()`)
|
||||
/// - Points to DETERMINISTIC_COMMIT_HASH
|
||||
/// - Git push verified to succeed (state matches pushed commit)
|
||||
@@ -252,7 +258,7 @@ pub enum FixtureKind {
|
||||
/// not the owner's announcement, so this tests the recursive maintainer traversal.
|
||||
///
|
||||
/// This fixture represents the complete flow for testing recursive maintainer push authorization:
|
||||
/// 1. **Generated**: (MaintainerStateDataPushed dependency includes ValidRepo + OwnerStateDataPushed)
|
||||
/// 1. **Generated**: (MaintainerStateDataPushed dependency includes ValidRepoSent + OwnerStateDataPushed)
|
||||
/// Creates MaintainerAnnouncement + RecursiveMaintainerState
|
||||
/// 2. **Sent**: Sends events to relay (returns OK, accepted but 'purgatory:...' message)
|
||||
/// 3. **Verify Not Served**: Confirms event is not served by relays
|
||||
@@ -276,16 +282,19 @@ impl FixtureKind {
|
||||
pub fn dependencies(&self) -> Vec<FixtureKind> {
|
||||
match self {
|
||||
// Base fixtures - no dependencies
|
||||
Self::ValidRepo => vec![],
|
||||
Self::ValidRepoSent => vec![],
|
||||
|
||||
// Fixtures that depend on ValidRepo
|
||||
Self::RepoWithIssue => vec![Self::ValidRepo],
|
||||
Self::RepoState => vec![Self::ValidRepo],
|
||||
Self::PREvent => vec![Self::ValidRepo],
|
||||
Self::PREventGenerated => vec![Self::ValidRepo],
|
||||
// ValidRepoServed depends on OwnerStateDataPushed (announcement promoted after git push)
|
||||
Self::ValidRepoServed => vec![Self::OwnerStateDataPushed],
|
||||
|
||||
// Fixtures that depend on ValidRepoServed (need queryable announcement)
|
||||
Self::RepoWithIssue => vec![Self::ValidRepoServed],
|
||||
Self::RepoState => vec![Self::ValidRepoSent],
|
||||
Self::PREvent => vec![Self::ValidRepoSent],
|
||||
Self::PREventGenerated => vec![Self::ValidRepoSent],
|
||||
Self::PRWrongCommitPushedBeforeEvent => vec![Self::PREventGenerated],
|
||||
Self::PREventSentAfterWrongPush => vec![Self::PRWrongCommitPushedBeforeEvent],
|
||||
Self::OwnerStateDataPushed => vec![Self::ValidRepo],
|
||||
Self::OwnerStateDataPushed => vec![Self::ValidRepoSent],
|
||||
|
||||
// Fixtures that depend on RepoWithIssue
|
||||
Self::RepoWithComment => vec![Self::RepoWithIssue],
|
||||
@@ -323,6 +332,8 @@ impl FixtureKind {
|
||||
Self::PREventSentAfterWrongPush => true,
|
||||
// HeadSetToDevelopBranch sends its state event internally
|
||||
Self::HeadSetToDevelopBranch => true,
|
||||
// ValidRepoServed doesn't send anything itself, just returns cached event
|
||||
Self::ValidRepoServed => true,
|
||||
// All other fixtures return a single event for the caller to send
|
||||
_ => false,
|
||||
}
|
||||
@@ -373,7 +384,7 @@ impl From<AuditMode> for ContextMode {
|
||||
/// let ctx = TestContext::new(&client);
|
||||
///
|
||||
/// // Get a repository fixture - will be reused by subsequent TestContexts
|
||||
/// let repo = ctx.get_fixture(FixtureKind::ValidRepo).await?;
|
||||
/// let repo = ctx.get_fixture(FixtureKind::ValidRepoSent).await?;
|
||||
///
|
||||
/// // For cargo test (isolated fixtures)
|
||||
/// let config = AuditConfig::isolated();
|
||||
@@ -381,7 +392,7 @@ impl From<AuditMode> for ContextMode {
|
||||
/// let ctx = TestContext::new(&client);
|
||||
///
|
||||
/// // Get a repository fixture - fresh for this TestContext only
|
||||
/// let repo = ctx.get_fixture(FixtureKind::ValidRepo).await?;
|
||||
/// let repo = ctx.get_fixture(FixtureKind::ValidRepoSent).await?;
|
||||
/// # Ok(())
|
||||
/// # }
|
||||
/// ```
|
||||
@@ -436,7 +447,7 @@ impl<'a> TestContext<'a> {
|
||||
/// ```no_run
|
||||
/// # use grasp_audit::*;
|
||||
/// # async fn example(ctx: &TestContext<'_>) -> anyhow::Result<()> {
|
||||
/// let repo = ctx.get_fixture(FixtureKind::ValidRepo).await?;
|
||||
/// let repo = ctx.get_fixture(FixtureKind::ValidRepoSent).await?;
|
||||
/// # Ok(())
|
||||
/// # }
|
||||
/// ```
|
||||
@@ -517,7 +528,7 @@ impl<'a> TestContext<'a> {
|
||||
/// ```no_run
|
||||
/// # use grasp_audit::*;
|
||||
/// # async fn example(ctx: &TestContext<'_>) -> anyhow::Result<()> {
|
||||
/// // This ensures ValidRepo exists first, then creates RepoState
|
||||
/// // This ensures ValidRepoSent exists first, then creates RepoState
|
||||
/// let state = ctx.ensure_fixture(FixtureKind::RepoState).await?;
|
||||
/// # Ok(())
|
||||
/// # }
|
||||
@@ -625,10 +636,10 @@ impl<'a> TestContext<'a> {
|
||||
/// already-cached dependencies.
|
||||
async fn build_fixture_inner(&self, kind: FixtureKind) -> Result<Event> {
|
||||
match kind {
|
||||
FixtureKind::ValidRepo => {
|
||||
// ValidRepo has no dependencies - create a new repo announcement
|
||||
FixtureKind::ValidRepoSent => {
|
||||
// ValidRepoSent has no dependencies - create a new repo announcement
|
||||
let test_name = format!(
|
||||
"fixture-ValidRepo-{}",
|
||||
"fixture-ValidRepoSent-{}",
|
||||
&uuid::Uuid::new_v4().to_string()[..8]
|
||||
);
|
||||
|
||||
@@ -638,9 +649,15 @@ impl<'a> TestContext<'a> {
|
||||
.with_context(|| format!("create_repo_announcement failed for {}", test_name))
|
||||
}
|
||||
|
||||
FixtureKind::ValidRepoServed => {
|
||||
// OwnerStateDataPushed is already ensured as a dependency.
|
||||
// The announcement is now promoted (served). Return the cached ValidRepoSent event.
|
||||
self.get_cached_dependency(FixtureKind::ValidRepoSent)
|
||||
}
|
||||
|
||||
FixtureKind::RepoWithIssue => {
|
||||
// ValidRepo is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
// ValidRepoServed is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoServed)?;
|
||||
|
||||
// Build issue referencing it - caller will send it
|
||||
self.client
|
||||
@@ -658,8 +675,8 @@ impl<'a> TestContext<'a> {
|
||||
FixtureKind::RepoState => {
|
||||
use nostr_sdk::prelude::*;
|
||||
|
||||
// ValidRepo is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
// ValidRepoSent is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoSent)?;
|
||||
|
||||
// Extract repo_id from repo announcement
|
||||
let repo_id = repo
|
||||
@@ -695,15 +712,15 @@ impl<'a> TestContext<'a> {
|
||||
FixtureKind::PREvent => {
|
||||
use nostr_sdk::prelude::*;
|
||||
|
||||
// ValidRepo is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
// ValidRepoSent is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoSent)?;
|
||||
|
||||
let repo_id = repo
|
||||
.tags
|
||||
.iter()
|
||||
.find(|t| t.kind() == TagKind::d())
|
||||
.and_then(|t| t.content())
|
||||
.ok_or_else(|| anyhow::anyhow!("Missing repo_id in ValidRepo fixture"))?
|
||||
.ok_or_else(|| anyhow::anyhow!("Missing repo_id in ValidRepoSent fixture"))?
|
||||
.to_string();
|
||||
|
||||
// Create PR event 1 second in the past
|
||||
@@ -738,15 +755,15 @@ impl<'a> TestContext<'a> {
|
||||
// This fixture is for "Generated" stage only
|
||||
use nostr_sdk::prelude::*;
|
||||
|
||||
// ValidRepo is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
// ValidRepoSent is ensured by ensure_fixture before this is called
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoSent)?;
|
||||
|
||||
let repo_id = repo
|
||||
.tags
|
||||
.iter()
|
||||
.find(|t| t.kind() == TagKind::d())
|
||||
.and_then(|t| t.content())
|
||||
.ok_or_else(|| anyhow::anyhow!("Missing repo_id in ValidRepo fixture"))?
|
||||
.ok_or_else(|| anyhow::anyhow!("Missing repo_id in ValidRepoSent fixture"))?
|
||||
.to_string();
|
||||
|
||||
// Create PR event 1 second in the past
|
||||
@@ -873,9 +890,9 @@ impl<'a> TestContext<'a> {
|
||||
use nostr_sdk::prelude::*;
|
||||
|
||||
// ============================================================
|
||||
// Stage 1: ValidRepo is ensured by ensure_fixture before this is called
|
||||
// Stage 1: ValidRepoSent is ensured by ensure_fixture before this is called
|
||||
// ============================================================
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoSent)?;
|
||||
let repo_id = self.extract_repo_id(&repo)?;
|
||||
|
||||
// Build state event
|
||||
@@ -901,9 +918,11 @@ impl<'a> TestContext<'a> {
|
||||
// ============================================================
|
||||
// Stage 2 & 3: Send to Relay, get Accepted response and Verify its Not Served
|
||||
// ============================================================
|
||||
self.client
|
||||
.send_event_expect_purgatory_not_served(state_event.clone())
|
||||
let (_, _in_purgatory) = self
|
||||
.client
|
||||
.send_event_and_note_purgatory(state_event.clone())
|
||||
.await?;
|
||||
// Note: We don't fail if purgatory wasn't observed - the fixture proceeds regardless
|
||||
|
||||
// ============================================================
|
||||
// Stage 4: DataPushed - Clone repo, create commit, push
|
||||
@@ -1048,8 +1067,8 @@ impl<'a> TestContext<'a> {
|
||||
// Extract repo_id from owner's state event (same d-tag structure)
|
||||
let repo_id = self.extract_repo_id(&owner_state)?;
|
||||
|
||||
// Get the repo (ValidRepo, also cached) for the owner's npub
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
// Get the repo (ValidRepoSent, also cached) for the owner's npub
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoSent)?;
|
||||
|
||||
// Build maintainer's state event (state event ONLY - no announcement)
|
||||
let base_time = Timestamp::now().as_secs();
|
||||
@@ -1074,9 +1093,11 @@ impl<'a> TestContext<'a> {
|
||||
// ============================================================
|
||||
// Stage 2 & 3: Send to Relay, get Accepted response and Verify its Not Served
|
||||
// ============================================================
|
||||
self.client
|
||||
.send_event_expect_purgatory_not_served(maintainer_state_event.clone())
|
||||
let (_, _in_purgatory) = self
|
||||
.client
|
||||
.send_event_and_note_purgatory(maintainer_state_event.clone())
|
||||
.await?;
|
||||
// Note: We don't fail if purgatory wasn't observed - the fixture proceeds regardless
|
||||
|
||||
// ============================================================
|
||||
// Stage 4: DataPushed - Clone repo, create maintainer commit, push
|
||||
@@ -1194,7 +1215,7 @@ impl<'a> TestContext<'a> {
|
||||
/// recursive maintainer force-pushes their commit on top.
|
||||
///
|
||||
/// This handles all stages of the fixture:
|
||||
/// 1. **Generated**: (MaintainerStateDataPushed dependency includes ValidRepo + OwnerStateDataPushed)
|
||||
/// 1. **Generated**: (MaintainerStateDataPushed dependency includes ValidRepoSent + OwnerStateDataPushed)
|
||||
/// Creates MaintainerAnnouncement + RecursiveMaintainerState
|
||||
/// 2. **Sent**: Sends events to relay (returns OK, accepted but 'purgatory:...' message)
|
||||
/// 3. **Verify Not Served**: Confirms event is not served by relays
|
||||
@@ -1215,8 +1236,8 @@ impl<'a> TestContext<'a> {
|
||||
// Extract repo_id from maintainer's state event (same d-tag structure)
|
||||
let repo_id = self.extract_repo_id(&maintainer_state)?;
|
||||
|
||||
// Get the repo (ValidRepo, also cached) for the owner's npub
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
// Get the repo (ValidRepoSent, also cached) for the owner's npub
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoSent)?;
|
||||
|
||||
// ============================================================
|
||||
// Stage 1 (continued): Generate MaintainerAnnouncement and RecursiveMaintainerState
|
||||
@@ -1249,9 +1270,11 @@ impl<'a> TestContext<'a> {
|
||||
// ============================================================
|
||||
// Stage 2 & 3: Send to Relay, get Accepted response and Verify its Not Served
|
||||
// ============================================================
|
||||
self.client
|
||||
.send_event_expect_purgatory_not_served(recursive_maintainer_state_event.clone())
|
||||
let (_, _in_purgatory) = self
|
||||
.client
|
||||
.send_event_and_note_purgatory(recursive_maintainer_state_event.clone())
|
||||
.await?;
|
||||
// Note: We don't fail if purgatory wasn't observed - the fixture proceeds regardless
|
||||
|
||||
// ============================================================
|
||||
// Stage 4: DataPushed - Clone repo, create recursive maintainer commit, push
|
||||
@@ -1428,7 +1451,7 @@ impl<'a> TestContext<'a> {
|
||||
/// 3. A wrong commit is pushed to refs/nostr/<pr-event-id>
|
||||
///
|
||||
/// Server state after:
|
||||
/// - ValidRepo announcement on relay
|
||||
/// - ValidRepoSent announcement on relay
|
||||
/// - refs/nostr/<pr-event-id> on git server pointing to DETERMINISTIC_COMMIT_HASH (wrong)
|
||||
/// - NO PR event on relay
|
||||
///
|
||||
@@ -1440,8 +1463,8 @@ impl<'a> TestContext<'a> {
|
||||
let pr_event = self.get_cached_dependency(FixtureKind::PREventGenerated)?;
|
||||
let pr_event_id = pr_event.id.to_hex();
|
||||
|
||||
// Get the ValidRepo to extract repo info
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepo)?;
|
||||
// Get the ValidRepoSent to extract repo info
|
||||
let repo = self.get_cached_dependency(FixtureKind::ValidRepoSent)?;
|
||||
let repo_id = self.extract_repo_id(&repo)?;
|
||||
|
||||
// Get relay domain for cloning
|
||||
@@ -1520,7 +1543,7 @@ impl<'a> TestContext<'a> {
|
||||
///
|
||||
/// This fixture builds on PRWrongCommitPushedBeforeEvent by sending the PR event.
|
||||
/// After this fixture, the relay has:
|
||||
/// - ValidRepo announcement
|
||||
/// - ValidRepoSent announcement
|
||||
/// - PR event
|
||||
/// - refs/nostr/<pr-event-id> may have been cleaned up (that's what tests verify)
|
||||
///
|
||||
@@ -2040,10 +2063,10 @@ mod tests {
|
||||
use std::collections::HashSet;
|
||||
|
||||
let mut set = HashSet::new();
|
||||
set.insert(FixtureKind::ValidRepo);
|
||||
set.insert(FixtureKind::ValidRepoSent);
|
||||
set.insert(FixtureKind::RepoWithIssue);
|
||||
|
||||
assert!(set.contains(&FixtureKind::ValidRepo));
|
||||
assert!(set.contains(&FixtureKind::ValidRepoSent));
|
||||
assert!(!set.contains(&FixtureKind::RepoWithComment));
|
||||
}
|
||||
|
||||
|
||||
@@ -246,7 +246,7 @@ impl CorsTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository announcement to get a real repo path
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
|
||||
@@ -157,12 +157,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Request repository fixture - behavior depends on mode
|
||||
let event = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let event = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// Get relay URL for validation
|
||||
let relay_url = client
|
||||
@@ -602,12 +605,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// NEW: Get repository fixture (mode-aware)
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let repo = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// 2. Create issue that references the repo
|
||||
let issue = Self::create_issue_for_repo(client, &repo, "Test Issue 1")?;
|
||||
@@ -637,12 +643,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Get repository fixture (mode-aware)
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let repo = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// Extract repo_id and create `A` tag manually
|
||||
let repo_id =
|
||||
@@ -690,12 +699,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Get repository fixture (mode-aware)
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let repo = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// Extract repo_id and create `q` tag
|
||||
let repo_id =
|
||||
@@ -825,12 +837,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Get repository fixture (mode-aware)
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let repo = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// Create Kind 1 A that quotes the repo (makes it accepted)
|
||||
let repo_id = Self::extract_d_tag(&repo).ok_or("Failed to extract repo_id")?;
|
||||
@@ -881,12 +896,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Get repository fixture (mode-aware)
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let repo = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// Verify repo is queryable (ensures it's fully indexed before we reference it)
|
||||
let repo_id = Self::extract_d_tag(&repo).ok_or("Failed to extract repo_id")?;
|
||||
@@ -1034,12 +1052,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Get repository fixture (mode-aware)
|
||||
let repo = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let repo = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// Create Kind 1 A locally but DON'T send it yet
|
||||
let kind1_a = client
|
||||
@@ -1148,12 +1169,15 @@ impl EventAcceptancePolicyTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Get accepted repo A fixture (mode-aware)
|
||||
let _repo_a = ctx.get_fixture(FixtureKind::ValidRepo).await.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
let _repo_a = ctx
|
||||
.get_fixture(FixtureKind::ValidRepoServed)
|
||||
.await
|
||||
.map_err(|e| {
|
||||
format!(
|
||||
"Test setup failed: could not get valid repository fixture: {}",
|
||||
e
|
||||
)
|
||||
})?;
|
||||
|
||||
// Create Repo B but DON'T send it (unaccepted)
|
||||
let repo_b = Self::create_test_repo(client, "unaccepted-repo-b").await?;
|
||||
|
||||
@@ -49,7 +49,7 @@ impl GitCloneTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -171,7 +171,7 @@ impl GitCloneTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -274,7 +274,7 @@ impl GitCloneTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
|
||||
@@ -62,7 +62,7 @@ impl GitFilterTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -185,7 +185,7 @@ impl GitFilterTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -296,7 +296,7 @@ impl GitFilterTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
|
||||
@@ -69,7 +69,7 @@ impl Nip01SmokeTests {
|
||||
// Step 1: GENERATE - Create TestContext and get ValidRepo fixture
|
||||
let ctx = TestContext::new(client);
|
||||
let event = ctx
|
||||
.get_fixture(FixtureKind::ValidRepo)
|
||||
.get_fixture(FixtureKind::ValidRepoSent)
|
||||
.await
|
||||
.map_err(|e| format!("Failed to create ValidRepo fixture: {}", e))?;
|
||||
|
||||
@@ -135,7 +135,7 @@ impl Nip01SmokeTests {
|
||||
// Step 1: GENERATE - Create TestContext and get ValidRepo fixture
|
||||
let ctx = TestContext::new(client);
|
||||
let _event = ctx
|
||||
.get_fixture(FixtureKind::ValidRepo)
|
||||
.get_fixture(FixtureKind::ValidRepoSent)
|
||||
.await
|
||||
.map_err(|e| format!("Failed to create ValidRepo fixture: {}", e))?;
|
||||
|
||||
|
||||
@@ -208,7 +208,7 @@ async fn setup_pr_test_repo(
|
||||
) -> Result<(PathBuf, String, String, String), String> {
|
||||
// Get fixtures
|
||||
let repo_event = ctx
|
||||
.get_fixture(FixtureKind::ValidRepo)
|
||||
.get_fixture(FixtureKind::ValidRepoSent)
|
||||
.await
|
||||
.map_err(|e| format!("Failed to get repo announcement: {}", e))?;
|
||||
|
||||
@@ -407,7 +407,7 @@ impl PushAuthorizationTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create repository (no state event)
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -956,7 +956,7 @@ impl PushAuthorizationTests {
|
||||
// ============================================================
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -1110,7 +1110,7 @@ impl PushAuthorizationTests {
|
||||
let pr_event_id = pr_event.id.to_hex();
|
||||
|
||||
// Get repo info for cloning (fresh clone for verification)
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(test_name, SpecRef::GitAcceptRefsNostrEventId, desc)
|
||||
@@ -1198,7 +1198,7 @@ impl PushAuthorizationTests {
|
||||
let pr_event_id = pr_event.id.to_hex();
|
||||
|
||||
// Get repo info for cloning (fresh clone for this test)
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(test_name, SpecRef::GitAcceptRefsNostrEventId, desc)
|
||||
@@ -1289,7 +1289,7 @@ impl PushAuthorizationTests {
|
||||
let pr_event_id = pr_event.id.to_hex();
|
||||
|
||||
// Get repo info for cloning (fresh clone for this test)
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(test_name, SpecRef::GitAcceptRefsNostrEventId, desc)
|
||||
@@ -1425,7 +1425,7 @@ impl PushAuthorizationTests {
|
||||
// ============================================================
|
||||
// Step 2: Extract repo_id and owner npub from ValidRepo (cached by fixture)
|
||||
// ============================================================
|
||||
let valid_repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let valid_repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(e) => e,
|
||||
Err(e) => {
|
||||
return TestResult::new(test_name, SpecRef::GitSetHeadOnReceive, desc)
|
||||
@@ -1528,7 +1528,7 @@ impl PushAuthorizationTests {
|
||||
// ============================================================
|
||||
// Step 2: Extract repo_id and owner npub from ValidRepo (cached by fixture)
|
||||
// ============================================================
|
||||
let valid_repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let valid_repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(e) => e,
|
||||
Err(e) => {
|
||||
return TestResult::new(test_name, SpecRef::GitSetHeadOnReceive, desc)
|
||||
|
||||
@@ -51,7 +51,7 @@ impl RepositoryCreationTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Use TestContext to create and send repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -131,7 +131,7 @@ impl RepositoryCreationTests {
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
// Create a repository announcement
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
@@ -210,7 +210,7 @@ impl RepositoryCreationTests {
|
||||
|
||||
let ctx = TestContext::new(client);
|
||||
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepo).await {
|
||||
let repo = match ctx.get_fixture(FixtureKind::ValidRepoSent).await {
|
||||
Ok(r) => r,
|
||||
Err(e) => {
|
||||
return TestResult::new(
|
||||
|
||||
Reference in New Issue
Block a user