Skip to content

Unauthenticated POST /api/v1/sync/trigger drives outbound fan-out and queue flooding #82

Description

@beardthelion

POST /api/v1/sync/trigger is reachable unauthenticated in the default configuration and drives the node to fan out HTTP requests to every known peer and enqueue per-repo sync work, with no caller identity check or effective rate limit.

Where

  • require_signed_peer_writes defaults to false (crates/gitlawb-node/src/config.rs:48).
  • With the flag false, the route is gated only by auth::optional_signature (server.rs:248), which passes unsigned requests through (auth/mod.rs:239).
  • trigger_sync (crates/gitlawb-node/src/api/peers.rs:184) takes no auth extractor and no body, loops over all peers issuing outbound GETs to {peer}/api/v1/repos, and enqueues a sync row per returned repo.
  • The route is publicly merged (server.rs:248). The per-DID rate limiter (rate_limit.rs) keys on the authenticated DID and early-returns when none is present, so it does nothing for an unauthenticated caller.

Impact

An anonymous caller can repeatedly force outbound fan-out and flood the sync queue (amplification/abuse). Combined with the outbound-redirect behavior and any poisoned peer row, it also becomes an unauthenticated trigger for the SSRF path.

Suggested fix

Require a valid signature on sync/trigger even when require_signed_peer_writes is false. (A "known-peer" check doesn't fit here: the request carries no peer identity and pulls from all peers.) Rate-limiting only helps once auth is enforced, since the limiter keys on the authenticated DID, so the two changes are coupled rather than independent. The sole caller, gl sync trigger, already signs when an identity is present, so requiring a signature is low-collateral. notify_sync is acceptable as-is since it gates on a known-peer DID.

Metadata

Metadata

Assignees

No one assigned

    Labels

    crate:nodegitlawb-node — the serving node and REST APIkind:securityVulnerability fix or hardeningsev:mediumDegraded but workaround existssubsystem:apiNode REST API request/response surfacesubsystem:peersPeer announce, discovery, and registry

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions