added additional plugins
This commit is contained in:
parent
c85895d306
commit
00e60ec1b7
132 changed files with 27514 additions and 0 deletions
|
|
@ -0,0 +1,324 @@
|
|||
<?php
|
||||
/**
|
||||
* Token Manager Class
|
||||
* Handles secure token storage with encryption
|
||||
*/
|
||||
|
||||
// Prevent direct access
|
||||
if (!defined('WPINC')) {
|
||||
die('Direct access not permitted.');
|
||||
}
|
||||
|
||||
if (!defined('ABSPATH')) {
|
||||
exit;
|
||||
}
|
||||
|
||||
class MCB_Token_Manager {
|
||||
|
||||
/**
|
||||
* Check if encryption is available
|
||||
*/
|
||||
public static function encryption_available() {
|
||||
return function_exists('openssl_encrypt') && function_exists('openssl_decrypt');
|
||||
}
|
||||
|
||||
/**
|
||||
* Encrypt token for secure storage
|
||||
*/
|
||||
public static function encrypt_token($token) {
|
||||
if (empty($token)) {
|
||||
return '';
|
||||
}
|
||||
|
||||
// Use WordPress salts for encryption
|
||||
if (self::encryption_available()) {
|
||||
$key = substr(hash('sha256', wp_salt('auth')), 0, 32);
|
||||
$iv = substr(hash('sha256', wp_salt('secure')), 0, 16);
|
||||
|
||||
$encrypted = openssl_encrypt($token, 'AES-256-CBC', $key, 0, $iv);
|
||||
if ($encrypted !== false) {
|
||||
return base64_encode($encrypted);
|
||||
}
|
||||
}
|
||||
|
||||
// Fallback to base64 if encryption not available
|
||||
return base64_encode($token);
|
||||
}
|
||||
|
||||
/**
|
||||
* Decrypt token for use
|
||||
*/
|
||||
public static function decrypt_token($encrypted_token) {
|
||||
if (empty($encrypted_token)) {
|
||||
return '';
|
||||
}
|
||||
|
||||
// Use WordPress salts for decryption
|
||||
if (self::encryption_available()) {
|
||||
$key = substr(hash('sha256', wp_salt('auth')), 0, 32);
|
||||
$iv = substr(hash('sha256', wp_salt('secure')), 0, 16);
|
||||
|
||||
$decoded = base64_decode($encrypted_token);
|
||||
if ($decoded !== false) {
|
||||
$decrypted = openssl_decrypt($decoded, 'AES-256-CBC', $key, 0, $iv);
|
||||
if ($decrypted !== false) {
|
||||
return $decrypted;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Fallback to base64 if encryption not available
|
||||
return base64_decode($encrypted_token);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store encrypted token
|
||||
*/
|
||||
public static function store_token($platform, $token) {
|
||||
if (empty($token)) {
|
||||
delete_option('mcb_' . $platform . '_token_encrypted');
|
||||
return true;
|
||||
}
|
||||
|
||||
$encrypted = self::encrypt_token($token);
|
||||
return update_option('mcb_' . $platform . '_token_encrypted', $encrypted);
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve and decrypt token
|
||||
*/
|
||||
public static function get_token($platform) {
|
||||
$encrypted = get_option('mcb_' . $platform . '_token_encrypted', '');
|
||||
if (empty($encrypted)) {
|
||||
// Check for legacy unencrypted token
|
||||
$legacy = get_option('mcb_' . $platform . '_token', '');
|
||||
if (!empty($legacy)) {
|
||||
// Migrate to encrypted storage
|
||||
self::store_token($platform, $legacy);
|
||||
delete_option('mcb_' . $platform . '_token');
|
||||
return $legacy;
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
return self::decrypt_token($encrypted);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove all tokens (for privacy/GDPR)
|
||||
*/
|
||||
public static function remove_all_tokens() {
|
||||
$platforms = array('github', 'gitlab', 'bitbucket', 'codeberg');
|
||||
foreach ($platforms as $platform) {
|
||||
delete_option('mcb_' . $platform . '_token');
|
||||
delete_option('mcb_' . $platform . '_token_encrypted');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Privacy Manager Class
|
||||
* Handles GDPR compliance and privacy features
|
||||
*/
|
||||
class MCB_Privacy_Manager {
|
||||
|
||||
/**
|
||||
* Initialize privacy features
|
||||
*/
|
||||
public static function init() {
|
||||
// WordPress privacy policy content
|
||||
add_action('admin_init', array(__CLASS__, 'privacy_policy_content'));
|
||||
|
||||
// Data exporter for GDPR
|
||||
add_filter('wp_privacy_personal_data_exporters', array(__CLASS__, 'register_data_exporter'));
|
||||
|
||||
// Data eraser for GDPR
|
||||
add_filter('wp_privacy_personal_data_erasers', array(__CLASS__, 'register_data_eraser'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if privacy mode is enabled
|
||||
*/
|
||||
public static function is_privacy_mode() {
|
||||
return get_option('mcb_privacy_mode', false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Add suggested privacy policy content
|
||||
*/
|
||||
public static function privacy_policy_content() {
|
||||
if (!function_exists('wp_add_privacy_policy_content')) {
|
||||
return;
|
||||
}
|
||||
|
||||
$content = '
|
||||
<h3>Git Code Viewer Plugin</h3>
|
||||
<p>When you visit pages that display code repositories using the Git Code Viewer plugin:</p>
|
||||
<ul>
|
||||
<li>We temporarily store an anonymized version of your IP address (for 60 seconds) to prevent abuse through rate limiting.</li>
|
||||
<li>If security events occur, we may log your browser user agent (for 7 days) for security monitoring.</li>
|
||||
<li>We do not use cookies or tracking technologies.</li>
|
||||
<li>We only access publicly available repository data from GitHub, GitLab, Bitbucket, and Codeberg.</li>
|
||||
<li>No personal information is shared with third parties.</li>
|
||||
<li>All data is automatically deleted after the retention period.</li>
|
||||
</ul>
|
||||
<p>If Privacy Mode is enabled, no IP addresses or user agents are collected.</p>
|
||||
';
|
||||
|
||||
wp_add_privacy_policy_content(
|
||||
'Git Code Viewer',
|
||||
wp_kses_post($content)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register data exporter for GDPR requests
|
||||
*/
|
||||
public static function register_data_exporter($exporters) {
|
||||
$exporters['git-code-viewer'] = array(
|
||||
'exporter_friendly_name' => __('Git Code Viewer Plugin'),
|
||||
'callback' => array(__CLASS__, 'data_exporter')
|
||||
);
|
||||
return $exporters;
|
||||
}
|
||||
|
||||
/**
|
||||
* Export user data for GDPR requests
|
||||
*/
|
||||
public static function data_exporter($email_address, $page = 1) {
|
||||
$export_items = array();
|
||||
|
||||
// Get security logs that might contain this user's data
|
||||
$logs = get_transient('mcb_security_logs');
|
||||
|
||||
if (is_array($logs)) {
|
||||
$user_data = array();
|
||||
|
||||
// Note: We don't store email addresses, so we can't directly match
|
||||
// This is actually good for privacy!
|
||||
$user_data[] = array(
|
||||
'name' => 'Security Logs Notice',
|
||||
'value' => 'The Git Code Viewer plugin does not store email addresses. Any security logs contain only anonymized IP addresses and user agents.'
|
||||
);
|
||||
|
||||
$export_items[] = array(
|
||||
'group_id' => 'git-code-viewer',
|
||||
'group_label' => 'Git Code Viewer Data',
|
||||
'item_id' => 'gcv-notice',
|
||||
'data' => $user_data
|
||||
);
|
||||
}
|
||||
|
||||
return array(
|
||||
'data' => $export_items,
|
||||
'done' => true
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register data eraser for GDPR requests
|
||||
*/
|
||||
public static function register_data_eraser($erasers) {
|
||||
$erasers['git-code-viewer'] = array(
|
||||
'eraser_friendly_name' => __('Git Code Viewer Plugin'),
|
||||
'callback' => array(__CLASS__, 'data_eraser')
|
||||
);
|
||||
return $erasers;
|
||||
}
|
||||
|
||||
/**
|
||||
* Erase user data for GDPR requests
|
||||
*/
|
||||
public static function data_eraser($email_address, $page = 1) {
|
||||
// Since we don't store email addresses or persistent user data,
|
||||
// we can only clear all transient data if requested
|
||||
|
||||
if ($page === 1) {
|
||||
// Clear all security logs
|
||||
delete_transient('mcb_security_logs');
|
||||
|
||||
// Clear all rate limit transients (they expire in 60 seconds anyway)
|
||||
global $wpdb;
|
||||
$wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '_transient_mcb_rate_%'");
|
||||
$wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '_transient_timeout_mcb_rate_%'");
|
||||
}
|
||||
|
||||
return array(
|
||||
'items_removed' => true,
|
||||
'items_retained' => false,
|
||||
'messages' => array('All temporary Git Code Viewer data has been removed.'),
|
||||
'done' => true
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get anonymized IP for privacy compliance
|
||||
*/
|
||||
public static function get_anonymized_ip($ip) {
|
||||
if (self::is_privacy_mode()) {
|
||||
return 'privacy-mode';
|
||||
}
|
||||
|
||||
// Anonymize IP by removing last octet for IPv4 or last 80 bits for IPv6
|
||||
if (filter_var($ip, FILTER_VALIDATE_IP, FILTER_FLAG_IPV4)) {
|
||||
$parts = explode('.', $ip);
|
||||
$parts[3] = '0';
|
||||
return implode('.', $parts);
|
||||
} elseif (filter_var($ip, FILTER_VALIDATE_IP, FILTER_FLAG_IPV6)) {
|
||||
// Zero out last 80 bits
|
||||
return substr($ip, 0, strrpos($ip, ':')) . ':0:0:0:0:0';
|
||||
}
|
||||
|
||||
return 'unknown';
|
||||
}
|
||||
|
||||
/**
|
||||
* Clean up old data automatically
|
||||
*/
|
||||
public static function cleanup_old_data() {
|
||||
// This is called on a daily schedule
|
||||
global $wpdb;
|
||||
|
||||
// Remove expired rate limit transients
|
||||
$wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '_transient_timeout_mcb_%' AND option_value < UNIX_TIMESTAMP()");
|
||||
|
||||
// Remove orphaned transients (fixed MySQL compatibility issue)
|
||||
// First get all valid transient names
|
||||
$valid_transients = $wpdb->get_col(
|
||||
"SELECT CONCAT('_transient_', SUBSTRING(option_name, 20))
|
||||
FROM {$wpdb->options}
|
||||
WHERE option_name LIKE '_transient_timeout_mcb_%'"
|
||||
);
|
||||
|
||||
if (!empty($valid_transients)) {
|
||||
// Build a safe IN clause
|
||||
$placeholders = array_fill(0, count($valid_transients), '%s');
|
||||
$in_clause = implode(',', $placeholders);
|
||||
|
||||
// Delete orphaned transients
|
||||
$wpdb->query(
|
||||
$wpdb->prepare(
|
||||
"DELETE FROM {$wpdb->options}
|
||||
WHERE option_name LIKE '_transient_mcb_%'
|
||||
AND option_name NOT IN ($in_clause)",
|
||||
$valid_transients
|
||||
)
|
||||
);
|
||||
} else {
|
||||
// No valid transients with timeouts, remove all MCB transients
|
||||
$wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '_transient_mcb_%'");
|
||||
}
|
||||
|
||||
// Also clean up expired timeout options
|
||||
$wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '_transient_timeout_mcb_%' AND option_value < UNIX_TIMESTAMP()");
|
||||
}
|
||||
}
|
||||
|
||||
// Initialize privacy features
|
||||
MCB_Privacy_Manager::init();
|
||||
|
||||
// Schedule cleanup (weekly is sufficient for transient cleanup)
|
||||
if (!wp_next_scheduled('mcb_privacy_cleanup')) {
|
||||
wp_schedule_event(time(), 'weekly', 'mcb_privacy_cleanup');
|
||||
}
|
||||
add_action('mcb_privacy_cleanup', array('MCB_Privacy_Manager', 'cleanup_old_data'));
|
||||
Loading…
Add table
Add a link
Reference in a new issue