Oct 8, 2026·6 min read·4 visits
A check-after-use path traversal vulnerability in PraisonAI's ContextGatherer allows unauthorized reading of sensitive local host files.
PraisonAI is vulnerable to an arbitrary local file read vulnerability prior to version 4.6.78. The flaw is in the ContextGatherer component, where validation checks are executed only after files are parsed and appended to the context bundle, bypassing security constraints.
PraisonAI is an open-source framework designed to orchestrate multi-agent artificial intelligence systems and streamline the assembly of codebases for LLM context windows. In versions prior to 4.6.78, the platform exposes an arbitrary local file read vulnerability via its context gathering subsystem. This component is designed to scan directories and bundle codebase files to populate large language model context windows.
The vulnerability is categorized as CWE-22 (Improper Limitation of a Pathname to a Restricted Directory / 'Path Traversal') and CWE-200 (Exposure of Sensitive Information to an Unauthorized Actor). It resides in the ContextGatherer component within src/praisonai/praisonai/ui/context.py. When parsing configuration files such as .praisoncontext or .praisoninclude, the application fails to restrict paths to the designated workspace root.
An attacker can exploit this flaw by submitting malicious configuration files with absolute paths or directory traversal sequences. When the context compilation routine is triggered, these external files are parsed and appended to the context output bundle. This occurs because the safety boundaries are verified only after the files have been successfully read into memory.
The root cause of CVE-2026-61431 lies in a check-after-use logic flaw within the file collection routine of the ContextGatherer class. When compiling context, the class processes user-specified inclusion lists from configuration files like .praisoncontext. The application relies on Python's os.path.join() function to combine the workspace root directory with user-supplied paths.
In Python, if one of the arguments to os.path.join() is an absolute path, all previous components are discarded, and the absolute path is returned. For example, joining /app with /etc/passwd returns /etc/passwd directly. This behavior allows attackers to completely bypass the intended workspace directory structure.
The helper function add_file_content() executes an immediate read operation using open(file_path, 'r') on the resolved path. Once read, the content is immediately appended to the local context accumulation list. The boundary safety check is only executed after this append operation, via the Path(file_path).relative_to(self.directory) call.
If the path lies outside the root directory, relative_to() throws a ValueError exception. However, because this validation check is wrapped in a broad try-except block designed to catch general reading errors, the resulting exception is caught and logged as a simple warning. The execution flow continues without removing the unauthorized file content that was already appended to the context list, culminating in information disclosure.
The vulnerability resides in src/praisonai/praisonai/ui/context.py before version 4.6.78. The vulnerable path resolution and inclusion logic allowed unrestricted file reads.
# Vulnerable Code Structure (Prior to v4.6.78)
def add_file_content(file_path):
"""Helper function to add file content to context."""
try:
# Step 1: The file is opened and read immediately
with open(file_path, 'r', encoding='utf-8') as f:
content = f.read()
# Step 2: Content is appended to the context list
context.append(
f"File: {file_path}\n\n{content}\n\n{'=' * 50}\n"
)
# Step 3: Validation occurs AFTER the read and append
# If file_path is not relative to self.directory, ValueError is raised
self.included_files.append(
Path(file_path).relative_to(self.directory)
)
except Exception as e:
# Step 4: The ValueError is caught here, but the appended content is not removed
logger.error(f"Error reading {file_path}: {e}")To correct this flaw, the maintainers implemented a safe path resolution helper _resolve_include_path() in commit 393de394087e3badc79acfec490323bcc99638bd. This helper ensures that all target paths are properly sanitized and verified to reside within the designated workspace directory prior to any reading operations.
# Patched Code Structure (v4.6.78)
def _resolve_include_path(self, include_path: str) -> Optional[str]:
"""Resolve an include path and keep it within the project directory."""
if os.path.isabs(include_path):
candidate = os.path.expanduser(include_path)
else:
candidate = os.path.join(self.directory, include_path)
base = os.path.realpath(self.directory)
resolved = os.path.realpath(os.path.normpath(candidate))
try:
# Validate that the resolved path starts with the base path
if os.path.commonpath([resolved, base]) != base:
logger.warning("Skipping include outside project root: %s", include_path)
return None
except ValueError:
logger.warning("Skipping include outside project root: %s", include_path)
return None
return resolvedExploitation of CVE-2026-61431 relies on local or repository-level vectors where an attacker can introduce a malicious configuration file. The primary prerequisite is that the victim must execute the PraisonAI context gathering mechanism on a workspace containing these configuration files.
The attack sequence begins with the placement of a .praisoncontext or .praisoninclude file within the root of a target project directory. Within this configuration file, the attacker defines absolute paths such as /etc/passwd or relative directory traversal sequences such as ../../../../etc/shadow.
When a user runs the context generation tool using commands like praisonai context or triggers UI-based context consolidation, the application processes the configuration. It reads the files specified, appends their content, and generates a final context.txt file or feeds the context directly to an LLM provider. Although error messages will appear in the output console, the resulting file contains the fully exfiltrated contents of the requested local files.
The security impact of CVE-2026-61431 is classified as High for Confidentiality. Because the context gathering component executes with the privileges of the running PraisonAI process, any file readable by that system user can be accessed and compiled into the LLM context.
This vulnerability can lead to the disclosure of sensitive host files, including environment variables, API tokens, database credentials, ssh keys, and system files. If PraisonAI is deployed in cloud or containerized environments, exposure of container service tokens or configurations could lead to subsequent privilege escalation or infrastructure compromise.
The CVSS v3.1 vector is rated as 5.5 (Medium): CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:H/I:N/A:N. Under CVSS v4.0, the vulnerability scores 6.8 (Medium): CVSS:4.0/AV:L/AC:L/AT:N/PR:N/UI:P/VC:H/VI:N/VA:N/SC:N/SI:N/SA:N. The requirement for user interaction (loading and compiling a malicious repository) keeps the severity score moderate, though the impact of successful exploitation remains high.
The primary remediation strategy for CVE-2026-61431 is upgrading the praisonai and praisonaiagents packages to version 4.6.78 or later. The update introduces robust input validation and path isolation checks that prevent arbitrary file inclusion.
# Upgrade packages using pip
pip install --upgrade praisonai praisonaiagentsFor environments where an immediate upgrade is not feasible, administrators and developers must enforce strict workspace hygiene. Avoid running PraisonAI utilities within repositories or directories obtained from untrusted sources, and manually inspect .praisoncontext and .praisoninclude files for unexpected paths prior to execution.
Additionally, running the PraisonAI runtime environment inside a minimally privileged container containerized or sandbox environment is highly recommended. Restricting the container's file system access ensures that even if a path traversal occurs, the impact is isolated from the host operating system.
CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:H/I:N/A:N| Product | Affected Versions | Fixed Version |
|---|---|---|
praisonai MervinPraison | < 4.6.78 | 4.6.78 |
praisonaiagents MervinPraison | < 4.6.78 | 4.6.78 |
| Attribute | Detail |
|---|---|
| CWE ID | CWE-22 / CWE-200 |
| Attack Vector | Local |
| CVSS Score | 6.8 |
| Exploit Status | Proof-of-Concept |
| CISA KEV Status | No |
| Impact | Information Disclosure |
The product uses external input to construct a pathname that is intended to identify a file or directory that is located under a restricted parent directory, but the product does not properly neutralize special elements within the pathname that can cause the pathname to resolve to a location that is outside of the restricted directory.
A path traversal vulnerability in datamodel-code-generator allows remote attackers to write or overwrite arbitrary files on the local host filesystem via a manipulated Protobuf schema containing malicious weak import paths.
An algorithmic complexity vulnerability (CWE-770) in the Excelize library allows remote attackers to cause resource exhaustion (100% CPU usage) via a crafted Microsoft Excel spreadsheet. This occurs because the look-ahead row index parsing in Rows.Columns() fails to enforce upper boundary limits, enabling an out-of-bounds row index to trigger an infinite seek loop inside the Rows iterator.
An unauthenticated Server-Side Request Forgery (SSRF) vulnerability exists in Ghost CMS from version 6.54.1 to 6.65.0. The vulnerability stems from a validation bypass in the favicon resolution logic within the bookmark-fetching subsystem, which allows remote, unauthenticated attackers to trigger arbitrary HTTP requests to the local host and internal networks. This bypass circumvents the custom DNS-level IP blocklist controls configured globally in the application.
A resource allocation vulnerability (CWE-770) in lz4-java before version 1.11.4 allows an unauthenticated remote attacker to trigger CPU exhaustion and high garbage collection overhead by streaming empty concatenated LZ4 frames.
A Denial of Service (DoS) vulnerability exists in the yawkat fork of lz4-java prior to version 1.11.4. Under specific non-default configurations (stopOnEmptyBlock = false), parsing crafted streams with a large sequence of contiguous empty LZ4 blocks triggers uncontrolled recursion inside the LZ4BlockInputStream.refill() method, causing stack exhaustion and thread termination.
CVE-2026-76485 is a critical stack-based buffer overflow vulnerability in the VXLAN OAM (NGOAM) parsing component of Cisco NX-OS Software. The flaw enables an unauthenticated, remote attacker to execute arbitrary code with root privileges or trigger a denial of service on affected Nexus switches. This vulnerability is triggered through crafted packets sent to an IP interface. No workarounds are currently available to mitigate the vulnerability while preserving the NGOAM functionality. Cisco has published software patches to address this flaw.