Skip to content

CallbackService.run()/arun() should support a configurable timeout #15

Description

@daviddavis

CallbackService.run() and arun() invoke a user-supplied script via
subprocess.run(...) / asyncio.create_subprocess_exec(...) with no timeout,
so a hung callback (e.g. a script that makes an HTTP call without its own
client-side timeout) will pin a Pulp worker indefinitely until the worker is
restarted or the process is killed externally.

Mitigations already in place:

  • Callbacks are dispatched as their own Pulp tasks
    (pulp_workflow.app.tasks.run_callback), so a hung callback ties up a worker
    slot but does not stall the originating workflow's state machine.
  • Only admins (callbackservice_admin) can register callback scripts, so this
    is a self-inflicted-foot-gun rather than an unauthenticated DoS surface.

Notes:

  • This mirrors pulpcore.app.models.SigningService.sign() / asign() exactly,
    which also have no timeout. Adding a timeout knob here without doing the
    same for SigningService upstream would diverge from the established
    pattern.
  • Suggested shape if/when this is addressed: a WORKFLOW_CALLBACK_TIMEOUT
    setting (default e.g. 300s), passed to subprocess.run(..., timeout=...) in
    run() and wrapped with asyncio.wait_for(process.communicate(), ...) plus
    process.kill() on TimeoutError in arun(). Ideally pushed upstream into
    SigningService as well so both inherit the same behavior.

Originally raised by the Copilot reviewer on #11.

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions