- Fix production debug exposure in Zoho admin interface (WP_DEBUG conditional) - Implement secure credential storage with AES-256-CBC encryption - Add file upload size limits (5MB profiles, 2MB logos) with enhanced validation - Fix privilege escalation via PHP Reflection bypass with public method alternative - Add comprehensive input validation and security headers - Update plugin version to 1.0.7 with security hardening Security improvements: ✅ Debug information exposure eliminated in production ✅ API credentials now encrypted in database storage ✅ File upload security enhanced with size/type validation ✅ AJAX endpoints secured with proper capability checks ✅ SQL injection protection verified via parameterized queries ✅ CSRF protection maintained with nonce verification 🤖 Generated with Claude Code Co-Authored-By: Claude <noreply@anthropic.com>
583 lines
No EOL
22 KiB
PHP
583 lines
No EOL
22 KiB
PHP
<?php
|
|
/**
|
|
* HVAC Astra Theme Integration
|
|
*
|
|
* Properly integrates HVAC plugin with Astra theme using theme-specific hooks and filters
|
|
*
|
|
* @package HVAC_Community_Events
|
|
* @since 1.0.0
|
|
*/
|
|
|
|
// Exit if accessed directly
|
|
if (!defined('ABSPATH')) {
|
|
exit;
|
|
}
|
|
|
|
/**
|
|
* HVAC Astra Integration Class
|
|
*/
|
|
class HVAC_Astra_Integration {
|
|
|
|
/**
|
|
* Instance
|
|
*
|
|
* @var HVAC_Astra_Integration
|
|
*/
|
|
private static $instance = null;
|
|
|
|
/**
|
|
* Get instance
|
|
*/
|
|
public static function instance() {
|
|
if (null === self::$instance) {
|
|
self::$instance = new self();
|
|
}
|
|
return self::$instance;
|
|
}
|
|
|
|
/**
|
|
* Constructor
|
|
*/
|
|
private function __construct() {
|
|
// Only run if Astra theme is active
|
|
if (!defined('ASTRA_THEME_VERSION')) {
|
|
return;
|
|
}
|
|
|
|
$this->init_hooks();
|
|
}
|
|
|
|
/**
|
|
* Initialize hooks
|
|
*/
|
|
private function init_hooks() {
|
|
// Early init to catch template redirects
|
|
add_action('template_redirect', [$this, 'ensure_correct_template'], 1);
|
|
|
|
// Layout filters - use higher priority to ensure they run after Astra's defaults
|
|
add_filter('astra_page_layout', [$this, 'force_hvac_page_layout'], 999);
|
|
add_filter('astra_get_content_layout', [$this, 'force_hvac_content_layout'], 999);
|
|
add_filter('astra_site_layout', [$this, 'force_hvac_site_layout'], 999);
|
|
|
|
// Container filters
|
|
add_filter('astra_container_class', [$this, 'modify_container_class'], 999, 2);
|
|
add_filter('astra_get_container_class', [$this, 'get_hvac_container_class'], 999);
|
|
|
|
// Body classes
|
|
add_filter('body_class', [$this, 'add_hvac_body_classes'], 999);
|
|
|
|
// Content width
|
|
add_action('wp', [$this, 'setup_hvac_content_width'], 999);
|
|
|
|
// Dynamic CSS
|
|
add_filter('astra_dynamic_theme_css', [$this, 'add_hvac_dynamic_css'], 999);
|
|
|
|
// Disable sidebar for HVAC pages
|
|
add_action('wp', [$this, 'disable_sidebar_for_hvac_pages'], 1);
|
|
|
|
// Force template usage
|
|
add_filter('template_include', [$this, 'force_hvac_template'], 999);
|
|
|
|
// Disable Astra breadcrumbs for HVAC pages
|
|
add_filter('astra_breadcrumb_enabled', [$this, 'disable_astra_breadcrumbs'], 999);
|
|
add_filter('astra_get_option_ast-breadcrumbs-content', [$this, 'disable_breadcrumb_option'], 999);
|
|
add_filter('astra_get_option_breadcrumb-position', [$this, 'disable_breadcrumb_position'], 999);
|
|
|
|
// Header transparency control for HVAC pages
|
|
add_filter('astra_get_option_theme-transparent-header-meta', [$this, 'disable_transparent_header'], 999);
|
|
add_filter('astra_transparent_header_meta', [$this, 'force_header_transparency_setting'], 999);
|
|
add_filter('astra_get_option_transparent-header-enable', [$this, 'disable_transparent_header_option'], 999);
|
|
|
|
// Layout control filters for Find a Trainer
|
|
add_filter('astra_get_option_site-content-layout', [$this, 'set_find_trainer_layout'], 999);
|
|
add_filter('astra_get_option_ast-site-content-layout', [$this, 'set_find_trainer_layout'], 999);
|
|
}
|
|
|
|
/**
|
|
* Force page layout for HVAC pages
|
|
*/
|
|
public function force_hvac_page_layout($layout) {
|
|
if ($this->is_hvac_page()) {
|
|
return 'no-sidebar';
|
|
}
|
|
return $layout;
|
|
}
|
|
|
|
/**
|
|
* Force content layout for HVAC pages
|
|
*/
|
|
public function force_hvac_content_layout($layout) {
|
|
if ($this->is_find_trainer_page()) {
|
|
return 'boxed-container';
|
|
} elseif ($this->is_hvac_page()) {
|
|
return 'plain-container';
|
|
}
|
|
return $layout;
|
|
}
|
|
|
|
/**
|
|
* Force site layout for HVAC pages
|
|
*/
|
|
public function force_hvac_site_layout($layout) {
|
|
if ($this->is_find_trainer_page()) {
|
|
return 'ast-boxed-layout';
|
|
} elseif ($this->is_hvac_page()) {
|
|
return 'ast-full-width-layout';
|
|
}
|
|
return $layout;
|
|
}
|
|
|
|
/**
|
|
* Modify container class for HVAC pages
|
|
*/
|
|
public function modify_container_class($classes, $layout) {
|
|
if ($this->is_find_trainer_page()) {
|
|
// Ensure Find a Trainer uses proper boxed container
|
|
$classes = str_replace('ast-full-width-container', 'ast-container', $classes);
|
|
} elseif ($this->is_hvac_page()) {
|
|
// Remove any constrained container classes for other HVAC pages
|
|
$classes = str_replace('ast-container', 'ast-full-width-container', $classes);
|
|
}
|
|
return $classes;
|
|
}
|
|
|
|
/**
|
|
* Get HVAC-specific container class
|
|
*/
|
|
public function get_hvac_container_class($class) {
|
|
if ($this->is_find_trainer_page()) {
|
|
return 'ast-container';
|
|
} elseif ($this->is_hvac_page()) {
|
|
return 'ast-full-width-container';
|
|
}
|
|
return $class;
|
|
}
|
|
|
|
/**
|
|
* Add HVAC-specific body classes
|
|
*/
|
|
public function add_hvac_body_classes($classes) {
|
|
if ($this->is_find_trainer_page()) {
|
|
// Add Astra-specific classes for boxed layout with Find a Trainer
|
|
$classes[] = 'ast-no-sidebar';
|
|
$classes[] = 'ast-separate-container';
|
|
$classes[] = 'ast-boxed-layout';
|
|
$classes[] = 'ast-boxed-container';
|
|
$classes[] = 'hvac-find-trainer-page';
|
|
$classes[] = 'hvac-astra-integrated';
|
|
|
|
// Remove conflicting classes
|
|
$remove_classes = ['ast-right-sidebar', 'ast-left-sidebar', 'ast-page-builder-template', 'ast-full-width-layout', 'ast-plain-container'];
|
|
$classes = array_diff($classes, $remove_classes);
|
|
} elseif ($this->is_hvac_page()) {
|
|
// Add Astra-specific classes for full-width layout
|
|
$classes[] = 'ast-no-sidebar';
|
|
$classes[] = 'ast-separate-container';
|
|
$classes[] = 'ast-full-width-layout';
|
|
$classes[] = 'ast-plain-container';
|
|
$classes[] = 'hvac-astra-integrated';
|
|
|
|
// Remove conflicting classes
|
|
$remove_classes = ['ast-right-sidebar', 'ast-left-sidebar', 'ast-page-builder-template'];
|
|
$classes = array_diff($classes, $remove_classes);
|
|
}
|
|
|
|
return $classes;
|
|
}
|
|
|
|
/**
|
|
* Setup content width for HVAC pages
|
|
*/
|
|
public function setup_hvac_content_width() {
|
|
if ($this->is_hvac_page() && !$this->is_find_trainer_page()) {
|
|
// Set global content width for dashboard pages only
|
|
global $content_width;
|
|
$content_width = 1920; // Full HD width
|
|
|
|
// Update Astra's content width
|
|
add_filter('astra_get_content_width', function() {
|
|
return 1920;
|
|
}, 999);
|
|
} elseif ($this->is_find_trainer_page()) {
|
|
// Set standard content width for Find A Trainer page
|
|
global $content_width;
|
|
$content_width = 1200; // Standard boxed width
|
|
|
|
add_filter('astra_get_content_width', function() {
|
|
return 1200;
|
|
}, 999);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Add dynamic CSS for HVAC pages
|
|
*/
|
|
public function add_hvac_dynamic_css($css) {
|
|
if ($this->is_hvac_page()) {
|
|
if ($this->is_find_trainer_page()) {
|
|
// Find A Trainer page - boxed layout with 1200px max-width
|
|
$hvac_css = '
|
|
/* Find A Trainer - FORCE boxed layout with highest specificity */
|
|
body.hvac-find-trainer-page #page,
|
|
body.hvac-find-trainer-page .site,
|
|
body.hvac-find-trainer-page .ast-container,
|
|
body.hvac-find-trainer-page .site-content > .ast-container,
|
|
body.hvac-find-trainer-page .entry-content > .ast-container,
|
|
body.hvac-find-trainer-page .site-content,
|
|
body.hvac-find-trainer-page #primary,
|
|
body.hvac-find-trainer-page .content-area {
|
|
max-width: 1200px !important;
|
|
width: 100% !important;
|
|
padding-left: 20px !important;
|
|
padding-right: 20px !important;
|
|
margin: 0 auto !important;
|
|
box-sizing: border-box !important;
|
|
}
|
|
|
|
/* Override ALL Astra layout classes */
|
|
body.hvac-find-trainer-page.ast-full-width-layout .site,
|
|
body.hvac-find-trainer-page.ast-full-width-layout .ast-container,
|
|
body.hvac-find-trainer-page .ast-full-width-container,
|
|
body.hvac-find-trainer-page.ast-boxed-layout .site,
|
|
body.hvac-find-trainer-page.ast-boxed-layout .ast-container {
|
|
max-width: 1200px !important;
|
|
margin: 0 auto !important;
|
|
background: #fff !important;
|
|
padding-left: 20px !important;
|
|
padding-right: 20px !important;
|
|
}
|
|
|
|
/* Remove sidebar completely */
|
|
.hvac-find-trainer-page .widget-area,
|
|
.hvac-find-trainer-page .ast-sidebar,
|
|
.hvac-find-trainer-page #secondary,
|
|
.hvac-find-trainer-page aside.widget-area,
|
|
.hvac-find-trainer-page .sidebar-main {
|
|
display: none !important;
|
|
}
|
|
|
|
/* Single column content */
|
|
.hvac-find-trainer-page #primary,
|
|
.hvac-find-trainer-page .site-main,
|
|
.hvac-find-trainer-page .content-area {
|
|
width: 100% !important;
|
|
max-width: 100% !important;
|
|
margin: 0 !important;
|
|
float: none !important;
|
|
}
|
|
|
|
/* Map container constraints within boxed layout */
|
|
.hvac-find-trainer-page .hvac-map-section {
|
|
max-width: 1160px !important; /* 1200px minus padding */
|
|
margin: 0 auto !important;
|
|
overflow: hidden !important;
|
|
}
|
|
|
|
/* MapGeo plugin specific overrides for boxed layout compliance */
|
|
.hvac-find-trainer-page .hvac-map-section .map_wrapper,
|
|
.hvac-find-trainer-page .hvac-map-section .map_box,
|
|
.hvac-find-trainer-page .hvac-map-section .map_container,
|
|
.hvac-find-trainer-page .igm-map-wrapper,
|
|
.hvac-find-trainer-page .igm-container,
|
|
.hvac-find-trainer-page .igm-map-container,
|
|
.hvac-find-trainer-page .interactive-geo-map,
|
|
.hvac-find-trainer-page [id*="igmMap"] {
|
|
max-width: 100% !important;
|
|
width: 100% !important;
|
|
overflow: hidden !important;
|
|
box-sizing: border-box !important;
|
|
}
|
|
|
|
/* Force MapGeo to respect parent container width */
|
|
.hvac-find-trainer-page .hvac-map-filters-container {
|
|
max-width: 1200px !important;
|
|
margin: 0 auto !important;
|
|
padding: 0 20px !important;
|
|
box-sizing: border-box !important;
|
|
overflow: hidden !important;
|
|
}
|
|
|
|
/* Ensure entire page content stays within 1200px */
|
|
.hvac-find-trainer-page > .ast-container > * {
|
|
max-width: 100% !important;
|
|
overflow-x: hidden !important;
|
|
}
|
|
|
|
/* FORCE opaque header with highest specificity */
|
|
body.hvac-find-trainer-page .main-header-bar,
|
|
body.hvac-find-trainer-page .ast-primary-header-bar,
|
|
body.hvac-find-trainer-page .site-header,
|
|
body.hvac-find-trainer-page header,
|
|
body.hvac-find-trainer-page .ast-header-wrapper {
|
|
background: rgba(255, 255, 255, 1) !important;
|
|
background-color: rgba(255, 255, 255, 1) !important;
|
|
backdrop-filter: none !important;
|
|
opacity: 1 !important;
|
|
}
|
|
';
|
|
} else {
|
|
// Other HVAC pages - full-width layout
|
|
$hvac_css = '
|
|
/* HVAC Full-width overrides for Astra */
|
|
.hvac-astra-integrated .ast-container {
|
|
max-width: 100% !important;
|
|
width: 100% !important;
|
|
padding-left: 40px !important;
|
|
padding-right: 40px !important;
|
|
}
|
|
|
|
.hvac-astra-integrated .site-content .ast-container {
|
|
max-width: 100% !important;
|
|
}
|
|
|
|
.hvac-astra-integrated .hvac-page-wrapper {
|
|
max-width: 1920px;
|
|
margin: 0 auto;
|
|
}
|
|
|
|
/* Remove sidebar completely */
|
|
.hvac-astra-integrated .widget-area,
|
|
.hvac-astra-integrated .ast-sidebar,
|
|
.hvac-astra-integrated #secondary,
|
|
.hvac-astra-integrated aside.widget-area,
|
|
.hvac-astra-integrated .sidebar-main {
|
|
display: none !important;
|
|
width: 0 !important;
|
|
height: 0 !important;
|
|
visibility: hidden !important;
|
|
position: absolute !important;
|
|
left: -9999px !important;
|
|
}
|
|
|
|
/* Full-width content area */
|
|
.hvac-astra-integrated #primary,
|
|
.hvac-astra-integrated .site-main,
|
|
.hvac-astra-integrated .content-area {
|
|
width: 100% !important;
|
|
max-width: 100% !important;
|
|
margin: 0 !important;
|
|
float: none !important;
|
|
display: block !important;
|
|
}
|
|
|
|
/* Force single column layout */
|
|
.hvac-astra-integrated .ast-container > .ast-row {
|
|
display: block !important;
|
|
}
|
|
|
|
.hvac-astra-integrated .ast-col-md-8,
|
|
.hvac-astra-integrated .ast-col-lg-8 {
|
|
width: 100% !important;
|
|
max-width: 100% !important;
|
|
}
|
|
|
|
/* Ensure content takes full width */
|
|
.hvac-astra-integrated .entry-content {
|
|
width: 100% !important;
|
|
max-width: 100% !important;
|
|
}
|
|
';
|
|
}
|
|
|
|
$css .= $hvac_css;
|
|
}
|
|
|
|
return $css;
|
|
}
|
|
|
|
/**
|
|
* Disable sidebar for HVAC pages
|
|
*/
|
|
public function disable_sidebar_for_hvac_pages() {
|
|
if ($this->is_hvac_page()) {
|
|
// Remove ALL sidebar actions from Astra
|
|
remove_action('astra_sidebars', 'astra_get_sidebar');
|
|
remove_action('astra_sidebar', 'astra_get_sidebar');
|
|
remove_action('astra_primary_content_bottom', 'astra_primary_content_bottom');
|
|
|
|
// Force sidebar removal via filters
|
|
add_filter('astra_display_sidebar', '__return_false', 999);
|
|
add_filter('is_active_sidebar', [$this, 'disable_sidebar'], 999, 2);
|
|
|
|
// Update post meta to ensure proper layout and header settings
|
|
global $post;
|
|
if ($post) {
|
|
// Common settings for all HVAC pages
|
|
update_post_meta($post->ID, 'site-sidebar-layout', 'no-sidebar');
|
|
update_post_meta($post->ID, 'ast-site-sidebar-layout', 'no-sidebar');
|
|
update_post_meta($post->ID, 'ast-featured-img', 'disabled');
|
|
update_post_meta($post->ID, 'ast-breadcrumbs-content', 'disabled');
|
|
update_post_meta($post->ID, 'theme-transparent-header-meta', 'disabled');
|
|
|
|
// Specific settings for Find a Trainer
|
|
if ($this->is_find_trainer_page()) {
|
|
update_post_meta($post->ID, 'site-content-layout', 'boxed-container');
|
|
update_post_meta($post->ID, 'ast-site-content-layout', 'boxed-container');
|
|
update_post_meta($post->ID, 'site-post-title', 'disabled');
|
|
} else {
|
|
// Other HVAC pages use plain container
|
|
update_post_meta($post->ID, 'site-content-layout', 'plain-container');
|
|
update_post_meta($post->ID, 'ast-site-content-layout', 'page-builder');
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Disable sidebar check for HVAC pages
|
|
*/
|
|
public function disable_sidebar($is_active, $index) {
|
|
if ($this->is_hvac_page()) {
|
|
return false;
|
|
}
|
|
return $is_active;
|
|
}
|
|
|
|
/**
|
|
* Check if current page is an HVAC page
|
|
*/
|
|
private function is_hvac_page() {
|
|
// Check by template
|
|
if (is_page_template()) {
|
|
$template = get_page_template_slug();
|
|
if (strpos($template, 'page-trainer') !== false ||
|
|
strpos($template, 'page-master') !== false ||
|
|
strpos($template, 'page-certificate') !== false ||
|
|
strpos($template, 'page-generate') !== false) {
|
|
return true;
|
|
}
|
|
}
|
|
|
|
// Check by URL
|
|
$current_url = $_SERVER['REQUEST_URI'];
|
|
$hvac_paths = ['trainer/', 'master-trainer/', 'certificate', 'generate-certificates', 'find-a-trainer'];
|
|
|
|
foreach ($hvac_paths as $path) {
|
|
if (strpos($current_url, $path) !== false) {
|
|
return true;
|
|
}
|
|
}
|
|
|
|
// Check by page slug
|
|
if (is_page()) {
|
|
global $post;
|
|
if ($post) {
|
|
$slug = $post->post_name;
|
|
$hvac_slugs = ['trainer', 'dashboard', 'profile', 'certificate', 'venue', 'organizer', 'find-a-trainer'];
|
|
foreach ($hvac_slugs as $hvac_slug) {
|
|
if (strpos($slug, $hvac_slug) !== false) {
|
|
return true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
/**
|
|
* Check if current page is Find A Trainer page
|
|
*/
|
|
private function is_find_trainer_page() {
|
|
if (is_page()) {
|
|
global $post;
|
|
if ($post && $post->post_name === 'find-a-trainer') {
|
|
return true;
|
|
}
|
|
}
|
|
|
|
$current_url = $_SERVER['REQUEST_URI'];
|
|
return strpos($current_url, 'find-a-trainer') !== false;
|
|
}
|
|
|
|
/**
|
|
* Ensure correct template is loaded
|
|
*/
|
|
public function ensure_correct_template() {
|
|
if ($this->is_hvac_page() && is_page()) {
|
|
global $post;
|
|
if ($post && $post->post_name === 'profile') {
|
|
// Force the profile template
|
|
$template = get_post_meta($post->ID, '_wp_page_template', true);
|
|
if (empty($template) || $template === 'default') {
|
|
update_post_meta($post->ID, '_wp_page_template', 'templates/page-trainer-profile.php');
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Force HVAC template loading
|
|
*/
|
|
public function force_hvac_template($template) {
|
|
// Temporarily disabled to avoid errors
|
|
return $template;
|
|
}
|
|
|
|
/**
|
|
* Disable Astra breadcrumbs for HVAC pages
|
|
*/
|
|
public function disable_astra_breadcrumbs($enabled) {
|
|
if ($this->is_hvac_page()) {
|
|
return false;
|
|
}
|
|
return $enabled;
|
|
}
|
|
|
|
/**
|
|
* Disable breadcrumb option for HVAC pages
|
|
*/
|
|
public function disable_breadcrumb_option($option) {
|
|
if ($this->is_hvac_page()) {
|
|
return 'disabled';
|
|
}
|
|
return $option;
|
|
}
|
|
|
|
/**
|
|
* Disable breadcrumb position for HVAC pages
|
|
*/
|
|
public function disable_breadcrumb_position($position) {
|
|
if ($this->is_hvac_page()) {
|
|
return '';
|
|
}
|
|
return $position;
|
|
}
|
|
|
|
/**
|
|
* Disable transparent header for ALL pages (not just HVAC)
|
|
*/
|
|
public function disable_transparent_header($option) {
|
|
// Force opaque header on all pages
|
|
return 'disabled';
|
|
}
|
|
|
|
/**
|
|
* Force header transparency setting to disabled
|
|
*/
|
|
public function force_header_transparency_setting($meta) {
|
|
// Always return disabled to force opaque header
|
|
return 'disabled';
|
|
}
|
|
|
|
/**
|
|
* Disable transparent header option globally
|
|
*/
|
|
public function disable_transparent_header_option($option) {
|
|
// Disable transparent header globally
|
|
return false;
|
|
}
|
|
|
|
/**
|
|
* Set Find a Trainer page layout to boxed container
|
|
*/
|
|
public function set_find_trainer_layout($layout) {
|
|
if ($this->is_find_trainer_page()) {
|
|
return 'boxed-container';
|
|
}
|
|
return $layout;
|
|
}
|
|
}
|
|
|
|
// Initialize
|
|
HVAC_Astra_Integration::instance(); |