PluginProbe
MainWP Dashboard: Self-hosted WordPress Management for Agencies / 5.2.2
MainWP Dashboard: Self-hosted WordPress Management for Agencies v5.2.2
6.2 6.1.8 6.1.7 6.1.6 6.1.5 6.1.4 6.1.3 6.1.2 6.1.1 6.1 6.0.12 6.0.11 4.6.0.1 5.0 5.0.1 5.0.2 5.0.3 5.0.3.1 5.0.3.2 5.1 5.1.1 5.2 5.2.1 5.2.2 5.3 All 153 releases
mainwp / modules / logs / classes / class-log-admin.php

class-log-admin.php in MainWP Dashboard: Self-hosted WordPress Management for Agencies 5.2.2, at modules/logs/classes/class-log-admin.php

391 lines 14.3 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Centralized manager for WordPress backend functionality.
4 *
5 * @package MainWP\Dashboard
6 * @version 4.5.1
7 */
8
9 namespace MainWP\Dashboard\Module\Log;
10
11 use MainWP\Dashboard\MainWP_Logger;
12 use MainWP\Dashboard\MainWP_Post_Handler;
13
14
15 defined( 'ABSPATH' ) || exit;
16
17 use DateTime;
18 use DateTimeZone;
19 use DateInterval;
20 use WP_CLI;
21
22 /**
23 * Class - Log_Admin
24 */
25 class Log_Admin {
26
27 /**
28 * Holds Instance of manager object
29 *
30 * @var Log_manager
31 */
32 public $manager;
33
34
35 /**
36 * Menu page screen id
37 *
38 * @var string
39 */
40 public $screen_id = array();
41
42 /**
43 * List table object
44 *
45 * @var List_Table
46 */
47 public $list_table = null;
48
49 /**
50 * Parent page of the records and settings pages
51 *
52 * @var string
53 */
54 public $admin_parent_page = 'admin.php';
55
56 /**
57 * Class constructor.
58 *
59 * @param Log_Manager $manager Instance of manager object.
60 */
61 public function __construct( $manager ) {
62 $this->manager = $manager;
63 add_action( 'init', array( &$this, 'init' ) );
64 add_filter( 'mainwp_getsubpages_settings', array( $this, 'add_subpage_menu_logs' ) );
65 // Load admin scripts and styles.
66 add_action(
67 'admin_enqueue_scripts',
68 array(
69 $this,
70 'admin_enqueue_scripts',
71 ),
72 9
73 );
74
75 // Auto purge setup.
76 add_action( 'wp_loaded', array( $this, 'hook_purge_scheduled_action' ) );
77 add_action( 'admin_init', array( $this, 'admin_init' ) );
78 }
79
80 /**
81 * Initiate Hooks
82 *
83 * Initiates hooks for the Dashboard insights module.
84 */
85 public function init() {
86 add_action( 'mainwp_help_sidebar_content', array( $this, 'mainwp_help_content' ) );
87 }
88
89 /**
90 * Handle admin_init action.
91 */
92 public function admin_init() {
93 MainWP_Post_Handler::instance()->add_action( 'mainwp_module_log_display_rows', array( $this, 'ajax_display_rows' ) );
94 MainWP_Post_Handler::instance()->add_action( 'mainwp_module_log_delete_records', array( $this, 'ajax_delete_records' ) );
95 MainWP_Post_Handler::instance()->add_action( 'mainwp_module_log_compact_records', array( $this, 'ajax_compact_records' ) );
96 MainWP_Post_Handler::instance()->add_action( 'mainwp_module_log_events_display_rows', array( Log_Insights_Page::instance(), 'ajax_events_display_rows' ) );
97 Log_Events_Filter_Segment::get_instance()->admin_init();
98 }
99
100
101 /**
102 * Init sub menu logs.
103 *
104 * @param array $subpages sub pages.
105 *
106 * @action init
107 */
108 public function add_subpage_menu_logs( $subpages = array() ) {
109 $subpages[] = array(
110 'title' => esc_html__( 'Dashboard Insights', 'mainwp' ),
111 'slug' => 'DashboardInsights',
112 'callback' => array( $this, 'render_list_table' ),
113 'class' => 'mainwp-logs-menu',
114 );
115 return $subpages;
116 }
117
118 /**
119 * Render main page
120 */
121 public function render_list_table() {
122 $this->list_table = new Log_List_Table( $this->manager );
123 /** This action is documented in ../pages/page-mainwp-manage-sites.php */
124 do_action( 'mainwp_pageheader_settings', 'DashboardInsights' );
125 ?>
126 <div id="mainwp-manage-sites-content" class="ui segment">
127 <div class="ui form">
128 <h3 class="ui dividing header"><?php esc_html_e( 'Dashboard Insights', 'mainwp' ); ?></h3>
129 <h4 class="ui header"><?php printf( esc_html__( 'Total logs size: %1$s (MB)', 'mainwp' ), esc_html( $this->get_db_size() ) ); ?></h4>
130 <div id="mainwp-message-zone" style="display:none;" class="ui message"></div>
131 <form method="post" class="mainwp-table-container">
132 <?php
133 wp_nonce_field( 'mainwp-admin-nonce' );
134 $this->list_table->display();
135 ?>
136 </form>
137 </div>
138 </div>
139 <?php
140 /** This action is documented in ../pages/page-mainwp-manage-sites.php */
141 do_action( 'mainwp_pagefooter_settings', 'DashboardInsights' );
142 }
143
144 /**
145 * Enqueue scripts/styles for admin screen
146 *
147 * @action admin_enqueue_scripts
148 *
149 * @param string $hook Current hook.
150 *
151 * @return void
152 */
153 public function admin_enqueue_scripts( $hook ) {
154 $script_screens = array( 'mainwp_page_InsightsOverview', 'mainwp_page_SettingsDashboardInsights', 'mainwp_page_SettingsInsights' );
155 wp_enqueue_style( 'mainwp-module-log-admin', $this->manager->locations['url'] . 'ui/css/admin.css', array(), $this->manager->get_version() );
156
157 if ( in_array( $hook, $script_screens, true ) ) {
158 wp_enqueue_script(
159 'mainwp-module-log-admin',
160 $this->manager->locations['url'] . 'ui/js/admin.js',
161 array(
162 'jquery',
163 'mainwp',
164 ),
165 $this->manager->get_version(),
166 false
167 );
168
169 if ( in_array( $hook, array( 'mainwp_page_InsightsOverview' ), true ) ) {
170 add_filter(
171 'mainwp_admin_enqueue_scripts',
172 function ( $scripts ) {
173 if ( is_array( $scripts ) ) {
174 $scripts['apexcharts'] = true;
175 }
176 return $scripts;
177 }
178 );
179 }
180
181 wp_localize_script(
182 'mainwp-module-log-admin',
183 'mainwpModuleLog',
184 array(
185 'i18n' => array(),
186 'gmt_offset' => get_option( 'gmt_offset' ),
187 )
188 );
189 }
190 }
191
192
193 /**
194 * Method ajax_display_rows()
195 *
196 * Display table rows, optimize for shared hosting or big networks.
197 */
198 public function ajax_display_rows() {
199 MainWP_Post_Handler::instance()->check_security( 'mainwp_module_log_display_rows' );
200 $this->load_list_table();
201 $this->list_table->prepare_items();
202 $output = $this->list_table->ajax_get_datatable_rows();
203 MainWP_Logger::instance()->log_execution_time( 'ajax_display_rows()' );
204 wp_send_json( $output );
205 }
206
207 /**
208 * Handle ajax delete logs records.
209 */
210 public function ajax_delete_records() {
211 MainWP_Post_Handler::instance()->check_security( 'mainwp_module_log_delete_records' );
212
213 $start_date = isset( $_POST['startdate'] ) ? sanitize_text_field( wp_unslash( $_POST['startdate'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification,WordPress.Security.ValidatedSanitizedInput.InputNotSanitized
214 $end_date = isset( $_POST['enddate'] ) ? sanitize_text_field( wp_unslash( $_POST['enddate'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification,WordPress.Security.ValidatedSanitizedInput.InputNotSanitized
215
216 $start_time = ! empty( $start_date ) ? strtotime( $start_date . ' 00:00:00' ) : '';
217 $end_time = ! empty( $end_date ) ? strtotime( $end_date . ' 23:59:59' ) : '';
218
219 if ( ! is_numeric( $start_time ) || ! is_numeric( $end_time ) || $start_time > $end_time ) {
220 die( wp_json_encode( array( 'error' => esc_html__( 'Invalid Start date or end date. Please try again.' ) ) ) );
221 }
222
223 $this->manager->db->create_compact_and_erase_records( $start_time, $end_time );
224
225 wp_send_json( array( 'result' => 'SUCCESS' ) );
226 }
227
228
229 /**
230 * Handle ajax compact logs records.
231 */
232 public function ajax_compact_records() {
233 MainWP_Post_Handler::instance()->check_security( 'mainwp_module_log_compact_records' );
234
235 $year = isset( $_POST['year'] ) ? intval( $_POST['year'] ) : 0; // phpcs:ignore WordPress.Security.NonceVerification,WordPress.Security.ValidatedSanitizedInput.InputNotSanitized
236
237 if ( $year < 2022 ) {
238 die( wp_json_encode( array( 'error' => esc_html__( 'Invalid selected year. Please try again.' ) ) ) );
239 }
240
241 $aday = $year . '-12-15'; // a day in last month.
242
243 $start_time = strtotime( $year . '-1-1 00:00:00' );
244 $end_time = strtotime( gmdate( 'Y-m-t', strtotime( $aday ) ) . ' 23:59:59' );
245
246 $this->manager->db->create_compact_and_erase_records( $start_time, $end_time );
247
248 wp_send_json( array( 'result' => 'SUCCESS' ) );
249 }
250
251 /**
252 * Method load_sites_table()
253 *
254 * Load sites table.
255 */
256 public function load_list_table() {
257 $this->list_table = new Log_List_Table( $this->manager );
258 }
259
260
261 /**
262 * Schedules a purge of records.
263 *
264 * @return void
265 */
266 public function hook_purge_scheduled_action() { //phpcs:ignore -- NOSONAR - complex.
267 $enable_schedule = is_array( $this->manager->settings->options ) && ! empty( $this->manager->settings->options['enabled'] ) && ! empty( $this->manager->settings->options['auto_purge'] ) ? true : false;
268 if ( $enable_schedule ) {
269 $last_purge = get_option( 'mainwp_module_log_last_time_auto_purge_logs' );
270 $next_purge = get_option( 'mainwp_module_log_next_time_auto_purge_logs' );
271 $days = false;
272 if ( is_array( $this->manager->settings->options ) && isset( $this->manager->settings->options['records_ttl'] ) ) {
273 $days = intval( $this->manager->settings->options['records_ttl'] );
274 } else {
275 $days = 100;
276 }
277
278 if ( defined( 'MAINWP_MODULE_LOG_KEEP_RECORDS_TTL' ) && is_numeric( MAINWP_MODULE_LOG_KEEP_RECORDS_TTL ) && MAINWP_MODULE_LOG_KEEP_RECORDS_TTL > 0 ) {
279 $days = MAINWP_MODULE_LOG_KEEP_RECORDS_TTL;
280 }
281
282 if ( $days ) {
283 $time = time();
284 $next_time_purge = false;
285 if ( false === $last_purge && false === $next_purge ) {
286 $next_time_purge = $time + $days * DAY_IN_SECONDS;
287 } elseif ( ! empty( $next_purge ) && $time > (int) $next_purge ) {
288 do_action( 'mainwp_log_action', 'module log :: purge logs schedule start.', MainWP_Logger::LOGS_AUTO_PURGE_LOG_PRIORITY );
289 $end_time = $time - $days * DAY_IN_SECONDS;
290 $start_time = ! empty( $last_purge ) ? $last_purge : $end_time - $days * DAY_IN_SECONDS;
291 $this->manager->db->create_compact_and_erase_records( $start_time, $end_time );
292 update_option( 'mainwp_module_log_last_time_auto_purge_logs', $time );
293 $next_time_purge = $time + $days * DAY_IN_SECONDS;
294 }
295 if ( $next_time_purge ) {
296 update_option( 'mainwp_module_log_next_time_auto_purge_logs', $next_time_purge );
297 }
298 }
299 }
300 }
301
302
303 /**
304 * Get db size.
305 *
306 * @return string Return current db size.
307 */
308 public function get_db_size() {
309 $size = get_transient( 'mainwp_module_log_transient_db_logs_size' );
310 if ( false !== $size ) {
311 return $size;
312 }
313
314 global $wpdb;
315 $sql = $wpdb->prepare(
316 'SELECT
317 ROUND(SUM(DATA_LENGTH + INDEX_LENGTH) / 1024 / 1024, 2)
318 FROM INFORMATION_SCHEMA.TABLES
319 WHERE
320 TABLE_SCHEMA = %s
321 AND table_name = %s
322 OR table_name = %s',
323 $wpdb->dbname,
324 $wpdb->mainwp_tbl_logs,
325 $wpdb->mainwp_tbl_logs_meta
326 );
327
328 $dbsize_mb = $wpdb->get_var( $sql ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared,WordPress.DB.DirectDatabaseQuery.DirectQuery -- prepared SQL.
329
330 set_transient( 'mainwp_module_log_transient_db_logs_size', $dbsize_mb, 15 * MINUTE_IN_SECONDS );
331
332 return $dbsize_mb;
333 }
334
335 /**
336 * Get WP users.
337 *
338 * @return array Array of users.
339 */
340 public function get_all_users() {
341 $list_users = array();
342 $all_users = get_users();
343 if ( is_array( $all_users ) ) {
344 foreach ( $all_users as $user ) {
345 if ( empty( $user->ID ) ) {
346 continue;
347 }
348 $fields = array();
349 $fields['id'] = $user->ID;
350 $fields['login'] = $user->user_login;
351 $fields['nicename'] = $user->user_nicename;
352 $list_users[] = $fields;
353 }
354 }
355 return $list_users;
356 }
357
358 /**
359 * Method mainwp_help_content()
360 *
361 * Creates the MainWP Help Documentation List for the help component in the sidebar.
362 */
363 public static function mainwp_help_content() {
364 $allow_pages = array( 'InsightsOverview' );
365 if ( isset( $_GET['page'] ) && in_array( $_GET['page'], $allow_pages, true ) ) { //phpcs:ignore WordPress.Security.NonceVerification.Recommended
366 ?>
367 <p><?php esc_html_e( 'If you need help with the Dashboard Insights module, please review following help documents', 'mainwp' ); ?></p>
368 <div class="ui list">
369 <div class="item"><i class="external alternate icon"></i> <a href="https://kb.mainwp.com/docs/dashboard-insights/" target="_blank">Dashboard Insights</a></div> <?php // NOSONAR -- compatible with help. ?>
370 <div class="item"><i class="external alternate icon"></i> <a href="https://kb.mainwp.com/docs/dashboard-insights/#comprehensive-filtering-options" target="_blank">Filtering Options</a></div> <?php // NOSONAR -- compatible with help. ?>
371 <div class="item"><i class="external alternate icon"></i> <a href="https://kb.mainwp.com/docs/dashboard-insights/#export-the-data-and-charts-from-an-individual-widget" target="_blank">Export Insights Data</a></div> <?php // NOSONAR -- compatible with help. ?>
372 <?php
373 /**
374 * Action: mainwp_module_dashboard_insights_help_item
375 *
376 * Fires at the bottom of the help articles list in the Help sidebar on the Insights page.
377 *
378 * Suggested HTML markup:
379 *
380 * <div class="item"><a href="Your custom URL">Your custom text</a></div>
381 *
382 * @since 5.2
383 */
384 do_action( 'mainwp_module_dashboard_insights_help_item' );
385 ?>
386 </div>
387 <?php
388 }
389 }
390 }
391