<?php
if (isset($_GET['action'])) $action = addslashes(trim(strip_tags(stripslashes(rawurldecode($_GET['action'])))));
else $action = false;

if (isset($_POST['submit'])) {
  if ($_POST['submit'] == 'reload') $update = 0;
}


$fields = array();

$encrypt_modules = array();
$modules_folder = array_diff(scandir('modules'), array('.', '..'));
foreach ($modules_folder as $module_folder){
  if (is_dir('modules/'.$module_folder) && is_file('modules/'.$module_folder.'/encrypt_config.php')){
    $encrypt_modules[$module_folder] = include('modules/'.$module_folder.'/encrypt_config.php');
  }
}

$module_name = NULL;

if (isset($encrypt_modules) && is_array($encrypt_modules)){
	foreach ($encrypt_modules AS $module_key => $module_value){
		foreach ($module_value AS $table_key => $table_value){
			if ($table_key == $id){
				$module_name = $module_key;
				foreach ($table_value AS $field => $field_data){
          $has_hash = check_column($table_key, $field.'_hash');
          $has_plain = check_column($table_key, $field.'_plain');

          $fields[$field]['c_hash'] = $has_hash ? 1 : NULL;
          $fields[$field]['c_hash_original'] = $has_hash ? 1 : 0;

          if (isset($field_data['plain']) && $field_data['plain'] === true){
            $fields[$field]['plain'] = 1;
            $fields[$field]['c_plain'] = $has_plain ? 1 : NULL;
            $fields[$field]['c_plain_original'] = $has_plain ? 1 : 0;
          }
										
				}
			}
		}
	}
}

	
if (isset($_POST['fields'])) {
  foreach ($fields as $key => $field) {
    $fields[$key]['c_hash'] = isset($_POST['fields'][$key]['c_hash']) ? 1 : 0;
    $fields[$key]['c_plain'] = isset($_POST['fields'][$key]['c_plain']) ? 1 : 0;
  }
}

if (isset($_POST['c_encrypt']) && $_POST['c_encrypt']) {
  foreach ($fields as $key => $value){
    $fields[$key]['c_hash'] = 1;
  }
}

foreach ($fields as $key => $value){
  if (empty($fields[$key]['c_hash'])) {
    $fields[$key]['c_plain'] = 0;
  }
}

if ($update) {
	if (isset($_POST['c_decrypt']) && $_POST['c_decrypt']) $encrypt_action = 'decrypt';
	if (isset($_POST['c_rotate']) && $_POST['c_rotate']) $encrypt_action = 'rotate';
	if (!isset($encrypt_action)) $encrypt_action = 'encrypt';
	
	$sql_check = "SELECT * FROM encrypt_log WHERE table_name = :table_name AND status = 'pending'";
  $result_check = $conn->prepare($sql_check);
  $result_check->bindValue(':table_name', $id, PDO::PARAM_STR);
  $result_check->execute();

  if ($result_check->rowCount() > 0) {
    $error = LABEL_ERROR_PROCESS_RUNNING;
  }

  $has_changes = false;
	foreach ($fields as $key => $value){
	  $old_hash = (int) ($value['c_hash_original'] ?? 0);
	  $new_hash = (int) ($value['c_hash'] ?? 0);
	
	  if ($old_hash !== $new_hash) {
	    $has_changes = true;
	    break;
	  }
	
	  if (isset($value['plain'])) {
	    $old_plain = (int) ($value['c_plain_original'] ?? 0);
	    $new_plain = (int) ($value['c_plain'] ?? 0);
	    if ($old_plain !== $new_plain) {
	      $has_changes = true;
	      break;
	    }
	  }
	  
	}

  if (!$has_changes && $encrypt_action == 'encrypt') {
    $error = LABEL_ERROR_NO_CHANGES;
  }
    
	if (!$fields OR !$module_name){
		$error = LABEL_ERROR_MANDATORY;
	}
    
	if (!isset($error) && $update == 1){
  	if ($encrypt_action == 'decrypt') {
      foreach ($fields as $key => $value) {
        $sql = "INSERT INTO encrypt_log SET
        				datetime = :datetime,
        				module = :module,
        				table_name = :table_name,
        				field_name = :field_name,
        				action = 'decrypt',
        				c_plain = '0',
        				status = 'pending'";
        $result = $conn->prepare($sql);
        $result->bindValue(':datetime', time(), PDO::PARAM_INT);
        $result->bindValue(':module', $module_name, PDO::PARAM_STR);
        $result->bindValue(':table_name', $id, PDO::PARAM_STR);
        $result->bindValue(':field_name', $key, PDO::PARAM_STR);
        $result->execute();
      }
    } else {
      foreach ($fields as $key => $value) {
        $old_hash = (int) ($value['c_hash_original'] ?? 0);
        $new_hash = (int) ($value['c_hash'] ?? 0);

        $old_plain = (int) ($value['c_plain_original'] ?? 0);
        $new_plain = (int) ($value['c_plain'] ?? 0);
        
        if ($old_hash === $new_hash && $old_plain === $new_plain) continue;

        if ($new_hash) {
	        $sql = "INSERT INTO encrypt_log SET
	        				datetime = :datetime,
	        				module = :module,
	        				table_name = :table_name,
	        				field_name = :field_name,
	        				action = 'encrypt',
	        				c_plain = :c_plain,
	        				status = 'pending'";
          $result = $conn->prepare($sql);
	        $result->bindValue(':datetime', time(), PDO::PARAM_INT);
	        $result->bindValue(':module', $module_name, PDO::PARAM_STR);
	        $result->bindValue(':table_name', $id, PDO::PARAM_STR);
	        $result->bindValue(':field_name', $key, PDO::PARAM_STR);
          if (isset($value['c_plain']) && $value['c_plain']) $result->bindValue(':c_plain', '1', PDO::PARAM_STR);
          else $result->bindValue(':c_plain', '0', PDO::PARAM_STR);
          $result->execute();
        } else {
	        $sql = "INSERT INTO encrypt_log SET
	        				datetime = :datetime,
	        				module = :module,
	        				table_name = :table_name,
	        				field_name = :field_name,
	        				action = 'decrypt',
	        				c_plain = '0',
        					status = 'pending'";
          $result = $conn->prepare($sql);
	        $result->bindValue(':datetime', time(), PDO::PARAM_INT);
	        $result->bindValue(':module', $module_name, PDO::PARAM_STR);
	        $result->bindValue(':table_name', $id, PDO::PARAM_STR);
	        $result->bindValue(':field_name', $key, PDO::PARAM_STR);
          $result->execute();
        }
      }

      if ($encrypt_action === 'rotate') {
        $sql = "INSERT INTO encrypt_log SET
        				datetime = :datetime,
        				module = :module,
        				table_name = :table_name,
        				field_name = '',
        				action = 'rotate',
        				c_plain = '0',
      					status = 'pending'";
        $result = $conn->prepare($sql);
        $result->bindValue(':datetime', time(), PDO::PARAM_INT);
        $result->bindValue(':module', $module_name, PDO::PARAM_STR);
        $result->bindValue(':table_name', $id, PDO::PARAM_STR);
        $result->execute();
      }
    }
  }
}

