GHSA-fc26-m9pf-v56q: PraisonAI LinearBot: webhook auth bypass enables agent exec

GHSA-fc26-m9pf-v56q HIGH
Published June 18, 2026
CISO Take

PraisonAI's LinearBot fails open when LINEAR_WEBHOOK_SECRET is absent — the webhook listener binds to 0.0.0.0 and accepts unsigned HTTP requests from any network caller without authentication, allowing an attacker to forge Linear AgentSession events and invoke the configured AI agent entirely unauthenticated. With CVSS 8.6 (AV:N/AC:L/PR:N/UI:N) and a trivially simple HTTP POST as the full exploit, this is a zero-barrier attack for any host that can reach the webhook port — a common scenario in cloud deployments where 0.0.0.0 binding exposes the service externally. Blast radius includes unauthorized LLM inference consuming paid model quota, fabricated responses posted to Linear under the bot identity, and — depending on configured agent tools — chained execution against file systems, external APIs, or other capabilities granted to the agent. Upgrade to praisonai 4.6.59 immediately; if patching is delayed, enforce LINEAR_WEBHOOK_SECRET and restrict network access to the webhook port to Linear's published IP ranges.

Sources: GitHub Advisory ATLAS

What is the risk?

CVSS 8.6 High (AV:N/AC:L/PR:N/UI:N/S:U/C:L/I:H/A:L). Exploitation requires only network reachability to the webhook port — no credentials, AI/ML knowledge, or tooling beyond a basic HTTP client. The fail-open default means any misconfigured deployment that omits LINEAR_WEBHOOK_SECRET is instantly exploitable; the CLI actively advertises the unauthenticated public endpoint at startup without blocking launch. Risk is highest in cloud and container deployments where webhook ports are externally reachable. Not in CISA KEV and no confirmed public exploit code, but the attack surface is trivially deterministic and a local proof-of-concept with 100% reproducibility is documented in the advisory. The package carries 106 prior CVEs, suggesting a pattern of security debt in this component.

How does the attack unfold?

Reconnaissance
Attacker identifies an exposed PraisonAI LinearBot webhook endpoint on 0.0.0.0 via port scan or leaked configuration, then confirms absent signature verification by sending an unsigned probe that returns HTTP 200.
AML.T0006
Auth Bypass Exploitation
Attacker forges a POST to /webhook with the Linear-Event: AgentSession header; the absent LINEAR_WEBHOOK_SECRET causes _handle_webhook() to skip all HMAC verification and accept the request unconditionally.
AML.T0049
Unauthorized Agent Invocation
Forged webhook body is dispatched to BotSessionManager.chat() with attacker-controlled issue title and description as agent input, triggering unauthorized LLM inference and enabling prompt injection into the agent's reasoning.
AML.T0053
Impact
Agent posts fabricated responses to Linear under the bot's identity, consumes paid model quota, and may execute any tools configured for the agent — including file-system, code-execution, or external-API capabilities — proportional to the agent's permission surface.
AML.T0034.002

What systems are affected?

Package Ecosystem Vulnerable Range Patched
PraisonAI pip >= 4.6.56, <= 4.6.58 4.6.59
1 dependents 68% patched ~14d to patch Full package profile →

Do you use PraisonAI? You're affected.

How severe is it?

CVSS 3.1
8.6 / 10
EPSS
N/A
Exploitation Status
No known exploitation
Sophistication
Trivial

What is the attack surface?

AV AC PR UI S C I A
AV Network
AC Low
PR None
UI None
S Unchanged
C Low
I High
A Low

What should I do?

6 steps
  1. Patch: upgrade to praisonai >= 4.6.59 immediately.

  2. Workaround if immediate patching is not possible: configure LINEAR_WEBHOOK_SECRET to a cryptographically strong random secret — this enforces HMAC-SHA256 verification and rejects all unsigned requests.

  3. Network control: restrict firewall or security group rules to allow webhook port traffic only from Linear's published webhook source IP ranges.

  4. Prefer loopback binding: if a public endpoint is not required, restrict the listener to 127.0.0.1 behind a reverse proxy with its own authentication layer.

  5. Detection: alert on webhook endpoint hits with missing or invalid Linear-Signature headers; monitor for unexpected spikes in agent session invocations or LLM token consumption.

  6. Audit: scan all deployment environments for absent LINEAR_WEBHOOK_SECRET in environment configuration before the next deployment cycle.

How is it classified?

Which compliance frameworks are affected?

This CVE is relevant to:

EU AI Act
Article 15 - Accuracy, robustness and cybersecurity
ISO 42001
A.9.2 - AI system access control
NIST AI RMF
GOVERN 6.1 - Policies, processes, procedures, and practices across the organization MANAGE 2.2 - Mechanisms exist to respond to AI risks
OWASP LLM Top 10
LLM08 - Excessive Agency

Frequently Asked Questions

What is GHSA-fc26-m9pf-v56q?

PraisonAI's LinearBot fails open when LINEAR_WEBHOOK_SECRET is absent — the webhook listener binds to 0.0.0.0 and accepts unsigned HTTP requests from any network caller without authentication, allowing an attacker to forge Linear AgentSession events and invoke the configured AI agent entirely unauthenticated. With CVSS 8.6 (AV:N/AC:L/PR:N/UI:N) and a trivially simple HTTP POST as the full exploit, this is a zero-barrier attack for any host that can reach the webhook port — a common scenario in cloud deployments where 0.0.0.0 binding exposes the service externally. Blast radius includes unauthorized LLM inference consuming paid model quota, fabricated responses posted to Linear under the bot identity, and — depending on configured agent tools — chained execution against file systems, external APIs, or other capabilities granted to the agent. Upgrade to praisonai 4.6.59 immediately; if patching is delayed, enforce LINEAR_WEBHOOK_SECRET and restrict network access to the webhook port to Linear's published IP ranges.

Is GHSA-fc26-m9pf-v56q actively exploited?

No confirmed active exploitation of GHSA-fc26-m9pf-v56q has been reported, but organizations should still patch proactively.

How to fix GHSA-fc26-m9pf-v56q?

1. Patch: upgrade to praisonai >= 4.6.59 immediately. 2. Workaround if immediate patching is not possible: configure LINEAR_WEBHOOK_SECRET to a cryptographically strong random secret — this enforces HMAC-SHA256 verification and rejects all unsigned requests. 3. Network control: restrict firewall or security group rules to allow webhook port traffic only from Linear's published webhook source IP ranges. 4. Prefer loopback binding: if a public endpoint is not required, restrict the listener to 127.0.0.1 behind a reverse proxy with its own authentication layer. 5. Detection: alert on webhook endpoint hits with missing or invalid Linear-Signature headers; monitor for unexpected spikes in agent session invocations or LLM token consumption. 6. Audit: scan all deployment environments for absent LINEAR_WEBHOOK_SECRET in environment configuration before the next deployment cycle.

What systems are affected by GHSA-fc26-m9pf-v56q?

This vulnerability affects the following AI/ML architecture patterns: agent frameworks, agentic pipelines, webhook integrations, CI/CD-integrated AI agents.

What is the CVSS score for GHSA-fc26-m9pf-v56q?

GHSA-fc26-m9pf-v56q has a CVSS v3.1 base score of 8.6 (HIGH).

What is the AI security impact?

Affected AI Architectures

agent frameworksagentic pipelineswebhook integrationsCI/CD-integrated AI agents

MITRE ATLAS Techniques

AML.T0034.002 Agentic Resource Consumption
AML.T0048.000 Financial Harm
AML.T0049 Exploit Public-Facing Application
AML.T0051.002 Triggered
AML.T0053 AI Agent Tool Invocation

Compliance Controls Affected

EU AI Act: Article 15
ISO 42001: A.9.2
NIST AI RMF: GOVERN 6.1, MANAGE 2.2
OWASP LLM Top 10: LLM08

What are the technical details?

Original Advisory

# PraisonAI LinearBot processes unsigned webhooks when `LINEAR_WEBHOOK_SECRET` is missing ## Summary PraisonAI's LinearBot starts a public webhook listener on `0.0.0.0` and treats `LINEAR_WEBHOOK_SECRET` as optional. When the secret is absent, startup only logs a warning and `_handle_webhook()` skips `Linear-Signature` verification entirely. An unauthenticated network caller who can reach the webhook endpoint can submit a forged `Linear-Event: AgentSession` request. The forged request is parsed, scheduled for background processing, dispatched to `_handle_agent_session()`, and passed into `BotSessionManager.chat()`. The bot then attempts to post the agent response back to Linear under the configured bot token. The local PoV is offline and deterministic. It does not contact Linear. It calls the webhook handler directly, monkey-patches the outbound Linear comment path, and proves both sides of the boundary: - no secret configured: unsigned forged webhook returns `200`, invokes the agent session path once, and attempts one Linear comment; - secret configured: missing and bad signatures both return `401` and do not invoke the agent; - secret configured with valid HMAC: request returns `200` and invokes the agent, proving the control path still works. ## Affected Product - Repository: `MervinPraison/PraisonAI` - Package: `praisonai` - Components: - `src/praisonai/praisonai/bots/linear.py` - `src/praisonai/praisonai/cli/features/bots_cli.py` Validated affected: - live `main` / latest observed release `v4.6.58`: `1ad58ca02975ff1398efeda694ea2ab78f20cf3e` - previous local current checkout: `2f9677abb2ea68eab864ee8b6a828fd0141612e1` - `v4.6.57` - `v4.6.56` - `v4.5.50` Sampled tags where the LinearBot component was not present: - `v4.5.49` - `v4.5.51` - `v4.6.9` - `v4.6.10` Suggested affected range: LinearBot-bearing releases with the fail-open signature behavior, at least `4.5.50` and `>= 4.6.56, <= 4.6.58`. The component appears non-contiguously in sampled tags, so maintainers should confirm the exact packaged version history before publishing a final range. ## Root Cause `LinearBot.__init__()` accepts an empty signing secret and falls back to an empty environment value: ```python self._signing_secret = signing_secret or os.environ.get("LINEAR_WEBHOOK_SECRET", "") ``` `start()` treats the missing secret as a warning instead of refusing to expose the webhook listener: ```python if not self._signing_secret: logger.warning("LINEAR_WEBHOOK_SECRET not set - webhook signatures will not be verified") self._site = web.TCPSite(self._runner, "0.0.0.0", self._webhook_port) ``` `_handle_webhook()` only verifies the request if the secret is truthy: ```python if self._signing_secret: signature = request.headers.get("Linear-Signature", "") if not self._verify_signature(raw_body, signature): return web.Response(status=401, text="Invalid signature") ``` With no secret configured, the code continues to JSON parsing, accepts a caller supplied `webhookTimestamp`, reads the caller supplied `Linear-Event` header, and schedules processing: ```python event_type = request.headers.get("Linear-Event", "") task = asyncio.create_task(self._process_webhook(event_type, body)) return web.Response(status=200, text="OK") ``` For `AgentSession`, the forged body is routed to the agent: ```python if event_type == "AgentSession": await self._handle_agent_session(body) ... response = await self._session_mgr.chat(self._agent, user_id, message.content) await self._send_comment(...) ``` The CLI has the same fail-open posture: `start_linear()` loads `LINEAR_WEBHOOK_SECRET`, prints a warning when it is missing, then reports a public `http://0.0.0.0:<port>/webhook` endpoint with verification disabled. ## Why This Is Not Intended Behavior PraisonAI's Linear Bot documentation tells operators to set `LINEAR_WEBHOOK_SECRET`, pass it to `praisonai bot linear`, copy the Linear webhook signing secret, and use it for HMAC-SHA256 verification. The same page says missing secrets disable signature verification, while its best-practices section says webhook secrets ensure authenticity. Linear's webhook documentation says receivers should ensure requests were sent by Linear by verifying the `Linear-Signature` HMAC over the raw body, then checking that `webhookTimestamp` is recent. The timestamp check alone is not an authentication boundary because an attacker can supply a current timestamp in a forged body. The implementation itself also confirms the intended boundary: when a secret is configured, missing and bad signatures are rejected before agent dispatch. The bug is the missing-secret fail-open mode on a public webhook server, not the signature algorithm. ## Local PoV Run against the latest observed release checkout: ```bash python3 submission-bundle/praisonai-prai-cand-013-linear-webhook-signature-fail-open/poc/pov_prai_cand_013_linear_webhook_signature_fail_open.py --repo artifacts/repos/praisonai-v4.6.58 ``` Expected output includes: ```json { "candidate": "PRAI-CAND-013", "ok": true, "cases": { "no_secret_unsigned_forged_webhook": { "http_status": 200, "signing_secret_configured": false, "session_calls": [ { "user_id": "linear-system", "content": "Issue: Forged Linear AgentSession event\n\nPRAI-CAND-013 local forged webhook payload" } ], "sent_comments": [ { "issue_id": "issue-prai-cand-013", "comment": "agent response", "session_id": "prai-cand-013-session" } ] }, "secret_missing_signature_control": { "http_status": 401, "session_calls": [] }, "secret_bad_signature_control": { "http_status": 401, "session_calls": [] }, "secret_valid_signature_control": { "http_status": 200, "session_calls": [ { "user_id": "linear-system" } ] } } } ``` Stored evidence: - `evidence/pov-v4.6.58.json` - `evidence/pov-live-main-v4.6.58.json` - `evidence/pov-current-head.json` - `evidence/version-sweep.tsv` ## Impact If a PraisonAI operator starts LinearBot with a Linear token but omits `LINEAR_WEBHOOK_SECRET`, any network caller that can reach the webhook endpoint can spoof Linear webhook events and invoke the configured agent through the Linear integration. For the `AgentSession` event path, this lets the attacker supply issue title and description content that becomes the agent input. Depending on the configured agent and tools, this can cause unauthorized LLM/tool execution, consume paid model quota, create or update Linear comments under the bot identity, and drive the bot into workflows intended only for authenticated Linear events. This report does not claim arbitrary code execution by default. The concrete boundary crossed is unauthenticated remote agent invocation through a forged Linear webhook. ## Suggested Fix Fail closed for public webhook listeners: 1. Refuse to start LinearBot when `LINEAR_WEBHOOK_SECRET` is missing, unless an explicit development-only option such as `--insecure-skip-webhook-signature-verification` is provided. 2. In `_handle_webhook()`, reject requests when no signing secret is configured instead of silently skipping verification. 3. Preserve raw-body HMAC verification and constant-time comparison for the configured-secret path. 4. Treat timestamp freshness as replay protection after signature validation, not as a replacement for authentication. 5. Prefer loopback binding by default, or require an explicit host flag for public binding. 6. Add regression tests: - no signing secret rejects startup or rejects webhook requests; - missing signature with a configured secret returns `401`; - invalid signature with a configured secret returns `401`; - valid HMAC with a configured secret returns success; - stale timestamp after valid HMAC returns `401`; - the CLI does not advertise a public unauthenticated webhook by default.

Exploitation Scenario

An attacker discovers a PraisonAI LinearBot instance via port scan or leaked CI/CD configuration and confirms the webhook is unauthenticated by sending a probe POST that returns 200. The attacker crafts a malicious POST to /webhook with the Linear-Event: AgentSession header and a JSON body containing a forged issue title and description embedding prompt injection instructions — for example, directing the agent to enumerate configuration files, exfiltrate environment variables, or invoke a code-execution tool. The handler, lacking a signing secret, skips all signature validation, parses the body, and dispatches it to BotSessionManager.chat() with the attacker-controlled content as the agent's user message. The agent executes the injected prompt, posts its response to a Linear issue under the bot token, and — if configured with file-system or external-API tools — may chain the injection into broader system-level actions, all without any authentication step.

Weaknesses (CWE)

CWE-287 — Improper Authentication: When an actor claims to have a given identity, the product does not prove or insufficiently proves that the claim is correct.

  • [Architecture and Design] Use an authentication framework or library such as the OWASP ESAPI Authentication feature.

Source: MITRE CWE corpus.

CVSS Vector

CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:L/I:H/A:L

Timeline

Published
June 18, 2026
Last Modified
June 18, 2026
First Seen
June 18, 2026

Related Vulnerabilities