CVE-2025-59397
Description
Open Web Analytics (OWA) before 1.8.1 allows owa_db.php v[value] SQL injection.
AI Insight
LLM-synthesized narrative grounded in this CVE's description and references.
Open Web Analytics (OWA) before 1.8.1 contains a SQL injection vulnerability in owa_db.php via unsanitized v[value] parameter.
Vulnerability
Overview
Open Web Analytics (OWA) versions prior to 1.8.1 are vulnerable to SQL injection in the owa_db.php file. The flaw resides in the _makeConstraintClause function, specifically in the handling of the v[value] parameter when using the =@ and !@ operators for query constraints. The vulnerable code directly concatenates user-supplied input into SQL statements via sprintf("LOCATE('%s', %s) > 0", $v['value'], ...), without proper sanitization [1][2].
Exploitation
Details
An attacker with a low-privileged account can craft a malicious v[value] parameter, which is not sanitized before being inserted into the SQL query. The vulnerability is exploitable through the query builder functionality that processes these operators. No special network position is required beyond authenticated access to the OWA application [2][3]. The attack surface is the web interface that accepts the vulnerable parameters.
Impact
Successful exploitation allows an attacker to execute arbitrary SQL queries against the underlying database. This could lead to unauthorized read access to sensitive analytics data, including potentially user information. The CVSS v3.1 score is 5.0 (Medium), with vector AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:N/A:N indicating high confidentiality impact but no integrity or availability impact [1][2].
Mitigation
The vulnerability is fixed in OWA version 1.8.1. The patch (commit 1e5531522acb8f145627c9feb0175cf8a66561ba) adds sanitization for the v[value] parameter by applying the prepare() method to user-controlled values in the affected code paths [4]. Users are strongly advised to upgrade to OWA 1.8.1 or later to mitigate the risk.
AI Insight generated on May 19, 2026. Synthesized from this CVE's description and the cited reference URLs; citations are validated against the source bundle.
Affected packages
Versions sourced from the GitHub Security Advisory.
| Package | Affected versions | Patched versions |
|---|---|---|
open-web-analytics/open-web-analyticsPackagist | < 1.8.1 | 1.8.1 |
Affected products
1- Range: <1.8.1
Patches
28c5943a27496Updating version string.
2 files changed · +2 −2
owa_env.php+1 −1 modified@@ -42,7 +42,7 @@ define('OWA_PLUGIN_DIR', OWA_DIR.'plugins/'); define('OWA_CONF_DIR', OWA_DIR.'conf/'); define('OWA_THEMES_DIR', OWA_DIR.'themes/'); -define('OWA_VERSION', 'master'); +define('OWA_VERSION', '1.8.1'); define('OWA_VENDOR_DIR', OWA_DIR.'vendor/'); if ( file_exists( OWA_VENDOR_DIR . 'autoload.php' ) ) {
package.json+1 −1 modified@@ -1,6 +1,6 @@ { "name": "owa", - "version": "1.0.0", + "version": "1.8.1", "description": "Open Web Analytics is an open source alternative to commercial web analytics tools such as Google Analytics. This software allows you to stay in control of the data you collect about the user of your websites or applications.", "main": "index.js", "scripts": {
1e5531522acbadding sanitization
3 files changed · +54 −16
modules/base/classes/sanitize.php+40 −2 modified@@ -90,6 +90,43 @@ public static function escapeForDisplay($string, $encoding = 'UTF-8', $quotes = } } + /** + * Strip SQL keywords and punctuation to prevent SQL injection. + * + * @param string $input String to sanitize + * @return string Sanitized string + * @access public + * @static + */ + public static function stripSql( $input = '' ) { + + if ( ! $input ) { + return $input; + } + + // Decode any encoded characters to reveal obfuscated SQL keywords. + $decoded = urldecode( $input ); + $decoded = html_entity_decode( $decoded, ENT_QUOTES | ENT_HTML5, 'UTF-8' ); + + // Remove common SQL command keywords. + $sql_keywords = array( + 'select', 'insert', 'update', 'delete', 'drop', 'union', 'create', + 'alter', 'truncate', 'replace', 'merge', 'call', 'exec' + ); + $pattern = '/\\b(' . implode( '|', $sql_keywords ) . ')\\b/i'; + $decoded = preg_replace( $pattern, '', $decoded ); + + // Remove commas and parentheses except for our allowed values. + $allowed_values = ['(not set)', '(unknown)']; + if ( ! in_array( $input, $allowed_values ) ) { + $decoded = str_replace( array( ',', '(', ')' ), '', $decoded ); + } + + // Remove any encoded commas or parentheses that may remain. + $decoded = preg_replace( '/%2C|%28|%29|(|)|,/i', '', $decoded ); + + return $decoded; + } /** * Strip Whitespace @@ -327,8 +364,9 @@ public static function cleanUrl( $url ) { 'backslash' => false ) ); - - return trim(str_replace('&', '&', $url)); + if ( $url ){ + return trim(str_replace('&', '&', $url)); + } } public static function cleanUserId ( $user_id ) {
owa_db.php+13 −13 modified@@ -17,7 +17,7 @@ // require_once(OWA_BASE_DIR.'/owa_base.php'); - +require_once(OWA_BASE_CLASS_DIR.'sanitize.php'); /** * Database Connection Class * @@ -443,7 +443,7 @@ function generateSelectQuerySql() { // Add as if (!empty($v['as'])): - $cols .= ' as '.$v['as']; + $cols .= ' as '.$this->prepare( $v['as']); endif; @@ -503,7 +503,7 @@ function _updateQuery() { endif; - $set .= $v['name'] .' = \'' . $this->prepare($v['value']) . '\''; + $set .= $this->prepare( $v['name'] ) .' = \'' . $this->prepare($v['value']) . '\''; $i++; } @@ -574,35 +574,35 @@ function _makeConstraintClause( $type, $params ) { $constraint = $type.' '; foreach ($params as $k => $v) { - + owa_coreAPI::debug($v); switch (strtolower($v['operator'])) { - + case '==': - $constraint .= sprintf("%s = '%s'",$v['name'], $this->prepare( $v['value'] ) ); + $constraint .= sprintf("%s = '%s'", $this->prepare( $v['name'] ), $this->prepare( $v['value'] ) ); break; case 'between': - $constraint .= sprintf("%s BETWEEN '%s' AND '%s'", $v['name'], $this->prepare( $v['value']['start'] ), $this->prepare( $v['value']['end'] ) ); + $constraint .= sprintf("%s BETWEEN '%s' AND '%s'", $this->prepare( $v['name'] ), $this->prepare( $v['value']['start'] ), $this->prepare( $v['value']['end'] ) ); break; case '=~': - $constraint .= sprintf("%s %s '%s'",$v['name'], OWA_SQL_REGEXP, $this->prepare( $v['value'] ) ); + $constraint .= sprintf("%s %s '%s'", $this->prepare( $v['name'] ), OWA_SQL_REGEXP, $this->prepare( $v['value'] ) ); break; case '!~': - $constraint .= sprintf("%s %s '%s'",$v['name'], OWA_SQL_NOTREGEXP, $this->prepare( $v['value'] ) ); + $constraint .= sprintf("%s %s '%s'",$this->prepare( $v['name'] ), OWA_SQL_NOTREGEXP, $this->prepare( $v['value'] ) ); break; case '=@': - $constraint .= sprintf("LOCATE('%s', %s) > 0",$v['value'], $this->prepare( $v['name'] ) ); + $constraint .= sprintf("LOCATE('%s', %s) > 0",$this->prepare( $v['value'] ), $this->prepare( $v['name'] ) ); break; case '!@': - $constraint .= sprintf("LOCATE('%s', %s) = 0",$v['value'], $this->prepare( $v['name'] ) ); + $constraint .= sprintf("LOCATE('%s', %s) = 0",$this->prepare( $v['value'] ), $this->prepare( $v['name'] ) ); break; default: - $constraint .= sprintf("%s %s '%s'",$v['name'], $v['operator'], $this->prepare( $v['value'] ) ); + $constraint .= sprintf("%s %s '%s'",$this->prepare( $v['name'] ), $v['operator'], $this->prepare( $v['value'] ) ); break; } @@ -641,7 +641,7 @@ function join($type, $table, $as, $foreign_key, $primary_key = '') { function prepare ( $string ) { - return $string; + return owa_sanitize::stripSql( $string ); } function _makeJoinClause() {
plugins/db/owa_db_mysql.php+1 −1 modified@@ -297,7 +297,7 @@ function prepare( $string ) { if(is_null($string)){ return $string; } - + $string = owa_sanitize::stripSql( $string ); if ($this->connection_status == false) { $this->connect(); }
Vulnerability mechanics
Generated on May 9, 2026. Inputs: CWE entries + fix-commit diffs from this CVE's patches. Citations validated against bundle.
References
9- github.com/advisories/GHSA-6w8r-xgqq-qg6gghsaADVISORY
- nvd.nist.gov/vuln/detail/CVE-2025-59397ghsaADVISORY
- github.com/Open-Web-Analytics/Open-Web-Analytics/commit/1e5531522acb8f145627c9feb0175cf8a66561banvdWEB
- github.com/Open-Web-Analytics/Open-Web-Analytics/compare/1.8.0...1.8.1nvdWEB
- github.com/Open-Web-Analytics/Open-Web-Analytics/releases/tag/1.8.1nvdWEB
- seclists.org/fulldisclosure/2025/Oct/5nvdWEB
- www.openwebanalytics.comnvdWEB
- www.seralys.com/research/CVE-2025-59397.txtnvdWEB
- seclists.org/fulldisclosure/2025/Oct/5nvd
News mentions
0No linked articles in our index yet.