Version Description
(2017-07-18) =
-
New Audit Trail Alerts
- Alert 1007 for when an administrator terminate's a logged in session using the Users Sessions Management Add-On
- Alert 6023 to log 404 HTTP errors (requests to non-existing pages) by website visitors (non WordPress users)
-
Improvements
- Seggregated the logging of 404 HTTP Errors by who generates them. Alert 6007 for logged in users, 6023 for anonymous website visitors.
- Improved the logging of Alert 4014 so it is not reported every time a user's profile page is reloaded with a refresh or when a change is applied.
- Removed the wsal_wp_session cookie, which was used to store the selected database when archiving of audit trail alerts is enabled. Using LocalStorage instead.
- Replaced mcrypt (deprecated in PHP 7) with OpenSSL. Mcrypt still used temporarily to convert configured password. Will be removed completely in future updates. Support Ticket
Download this release
Release Info
Developer | WPWhiteSecurity |
Plugin | WP Security Audit Log |
Version | 2.6.5 |
Comparing to | |
See all releases |
Code changes from version 2.6.4 to 2.6.5
- classes/AbstractLogger.php +27 -12
- classes/AbstractSandboxTask.php +77 -66
- classes/AbstractSensor.php +9 -3
- classes/AbstractView.php +56 -28
- classes/Adapters/ActiveRecordInterface.php +17 -13
- classes/Adapters/MetaInterface.php +14 -10
- classes/Adapters/MySQL/ActiveRecordAdapter.php +64 -28
- classes/Adapters/MySQL/MetaAdapter.php +35 -5
- classes/Adapters/MySQL/OccurrenceAdapter.php +60 -18
- classes/Adapters/MySQL/OptionAdapter.php +41 -4
- classes/Adapters/MySQL/QueryAdapter.php +46 -7
- classes/Adapters/MySQL/TmpUserAdapter.php +13 -2
- classes/Adapters/OccurrenceInterface.php +5 -1
- classes/Adapters/QueryInterface.php +8 -4
- classes/Alert.php +30 -16
- classes/AlertManager.php +80 -61
- classes/AuditLogListView.php +10 -6
- classes/Autoloader.php +22 -15
- classes/Connector/AbstractConnector.php +6 -1
- classes/Connector/ConnectorFactory.php +31 -3
- classes/Connector/ConnectorInterface.php +5 -1
- classes/Connector/MySQLDB.php +205 -31
- classes/Connector/wp-db-custom.php +12 -4
- classes/ConstantManager.php +95 -88
- classes/EDD_SL_Plugin_Updater.php +49 -46
- classes/Helpers/DataHelper.php +11 -6
- classes/Lib/class-recursive-arrayaccess.php +0 -139
- classes/Lib/class-wp-session-utils.php +0 -139
- classes/Lib/class-wp-session.php +0 -322
- classes/Lib/wp-session.php +0 -182
- classes/LicenseManager.php +51 -31
- classes/Loggers/Database.php +50 -7
- classes/Models/ActiveRecord.php +103 -39
- classes/Models/Meta.php +26 -10
- classes/Models/Occurrence.php +52 -4
- classes/Models/OccurrenceQuery.php +15 -2
- classes/Models/Option.php +52 -4
- classes/Models/Query.php +95 -11
- classes/Models/TmpUser.php +11 -7
- classes/Nicer.php +294 -284
- classes/SensorManager.php +19 -9
- classes/Sensors/BBPress.php +96 -4
- classes/Sensors/Comments.php +56 -2
- classes/Sensors/Content.php +282 -13
- classes/Sensors/Database.php +35 -1
- classes/Sensors/Files.php +83 -51
- classes/Sensors/LogInOut.php +68 -6
- classes/Sensors/Menus.php +74 -2
- classes/Sensors/MetaData.php +60 -11
- classes/Sensors/Multisite.php +196 -126
- classes/Sensors/PhpErrors.php +137 -102
- classes/Sensors/PluginsThemes.php +74 -16
- classes/Sensors/Request.php +19 -3
- classes/Sensors/System.php +387 -149
- classes/Sensors/UserProfile.php +41 -19
- classes/Sensors/Widgets.php +90 -61
- classes/Sensors/WooCommerce.php +57 -1
- classes/Settings.php +344 -130
- classes/SimpleProfiler.php +51 -41
- classes/ViewManager.php +98 -67
- classes/Views/About.php +93 -85
- classes/Views/AuditLog.php +43 -22
- classes/Views/EmailNotifications.php +10 -3
- classes/Views/Extensions.php +16 -7
- classes/Views/ExternalDB.php +10 -3
- classes/Views/Help.php +20 -10
- classes/Views/Licensing.php +98 -86
- classes/Views/LogInUsers.php +10 -4
- classes/Views/Reports.php +10 -4
- classes/Views/Search.php +10 -4
- classes/Views/Settings.php +53 -49
- classes/Views/ToggleAlerts.php +108 -26
- classes/WidgetManager.php +5 -1
- defaults.php +2 -0
- readme.txt +14 -1
- wp-security-audit-log.php +269 -150
classes/AbstractLogger.php
CHANGED
@@ -1,14 +1,29 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
|
|
|
|
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Abstract class used in the Logger.
|
6 |
+
* @see Loggers/Database.php
|
7 |
+
*/
|
8 |
+
abstract class WSAL_AbstractLogger
|
9 |
+
{
|
10 |
+
/**
|
11 |
+
* @var WpSecurityAuditLog
|
12 |
+
*/
|
13 |
+
protected $plugin;
|
14 |
|
15 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
16 |
+
{
|
17 |
+
$this->plugin = $plugin;
|
18 |
+
}
|
19 |
+
|
20 |
+
/**
|
21 |
+
* Log alert abstract.
|
22 |
+
* @param integer $type alert code
|
23 |
+
* @param array $data Metadata
|
24 |
+
* @param integer $date (Optional) created_on
|
25 |
+
* @param integer $siteid (Optional) site_id
|
26 |
+
* @param bool $migrated (Optional) is_migrated
|
27 |
+
*/
|
28 |
+
public abstract function Log($type, $data = array(), $date = null, $siteid = null, $migrated = false);
|
29 |
+
}
|
classes/AbstractSandboxTask.php
CHANGED
@@ -1,68 +1,79 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
68 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*/
|
5 |
+
abstract class WSAL_AbstractSandboxTask
|
6 |
+
{
|
7 |
+
public function __construct()
|
8 |
+
{
|
9 |
+
// remove time limit and clear output buffers
|
10 |
+
set_time_limit(0);
|
11 |
+
ob_implicit_flush(true);
|
12 |
+
while (ob_get_level()) {
|
13 |
+
ob_end_flush();
|
14 |
+
}
|
15 |
+
|
16 |
+
// set up shutdown handler
|
17 |
+
register_shutdown_function(array($this, 'Shutdown'));
|
18 |
+
|
19 |
+
// run event sequence
|
20 |
+
$this->Header();
|
21 |
+
try {
|
22 |
+
$this->Execute();
|
23 |
+
} catch (Exception $ex) {
|
24 |
+
$this->Message(get_class($ex) . ' [' . basename($ex->getFile()) . ':' . $ex->getLine() . ']: ' . $ex->getMessage());
|
25 |
+
$this->Message($ex->getTraceAsString(), true);
|
26 |
+
}
|
27 |
+
$this->Footer();
|
28 |
+
|
29 |
+
// shutdown
|
30 |
+
die();
|
31 |
+
}
|
32 |
+
|
33 |
+
protected function Header()
|
34 |
+
{
|
35 |
+
echo '<!DOCTYPE html><html><body style="margin: 0; padding: 8px; font: 12px Arial; color: #333;">';
|
36 |
+
echo '<div style="position: fixed; top: 0; left: 0; right: 0; padding: 8px; background: #F0F0F0;">';
|
37 |
+
echo ' <div id="bar" style=" border-top: 2px solid #0AE; top: 20px; height: 0; width: 0%;"> </div>';
|
38 |
+
echo ' <span id="msg"></span> <span id="prg"></span>';
|
39 |
+
echo '</div>';
|
40 |
+
echo '<div id="msgs" style="font-family: Consolas; margin-top: 30px; white-space: pre;"></div>';
|
41 |
+
echo '<script>';
|
42 |
+
echo ' var bar = document.getElementById("bar");';
|
43 |
+
echo ' var msg = document.getElementById("msg");';
|
44 |
+
echo ' var prg = document.getElementById("prg");';
|
45 |
+
echo ' var msgs = document.getElementById("msgs");';
|
46 |
+
echo '</script>';
|
47 |
+
flush();
|
48 |
+
}
|
49 |
+
|
50 |
+
protected function Footer()
|
51 |
+
{
|
52 |
+
echo '<div style="display: none;">';
|
53 |
+
flush();
|
54 |
+
}
|
55 |
+
|
56 |
+
protected abstract function Execute();
|
57 |
+
|
58 |
+
public function Shutdown()
|
59 |
+
{
|
60 |
+
echo '</div></body></html>';
|
61 |
+
flush();
|
62 |
+
}
|
63 |
+
|
64 |
+
protected function Progress($percent)
|
65 |
+
{
|
66 |
+
echo '<script>bar.style.width=prg.innerHTML="' . number_format($percent, 2) . '%";</script>';
|
67 |
+
flush();
|
68 |
+
}
|
69 |
+
|
70 |
+
protected function Message($message, $sticky = false)
|
71 |
+
{
|
72 |
+
if ($sticky) {
|
73 |
+
echo '<script>msgs.appendChild(document.createTextNode(' . json_encode($message . PHP_EOL) . ')); window.scroll(0, document.body.scrollHeight);</script>';
|
74 |
+
} else {
|
75 |
+
echo '<script>msg.innerHTML=' . json_encode($message) . ';</script>';
|
76 |
+
}
|
77 |
+
flush();
|
78 |
+
}
|
79 |
}
|
classes/AbstractSensor.php
CHANGED
@@ -1,5 +1,10 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
3 |
abstract class WSAL_AbstractSensor
|
4 |
{
|
5 |
/**
|
@@ -7,7 +12,8 @@ abstract class WSAL_AbstractSensor
|
|
7 |
*/
|
8 |
protected $plugin;
|
9 |
|
10 |
-
public function __construct(WpSecurityAuditLog $plugin)
|
|
|
11 |
$this->plugin = $plugin;
|
12 |
}
|
13 |
|
@@ -48,7 +54,7 @@ abstract class WSAL_AbstractSensor
|
|
48 |
/**
|
49 |
* Check to see whether or not the specified directory is accessible
|
50 |
* @param string $dirPath
|
51 |
-
* @return
|
52 |
*/
|
53 |
protected function CheckDirectory($dirPath)
|
54 |
{
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Abstract class used in all the sensors.
|
6 |
+
* @see Sensors/*.php
|
7 |
+
*/
|
8 |
abstract class WSAL_AbstractSensor
|
9 |
{
|
10 |
/**
|
12 |
*/
|
13 |
protected $plugin;
|
14 |
|
15 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
16 |
+
{
|
17 |
$this->plugin = $plugin;
|
18 |
}
|
19 |
|
54 |
/**
|
55 |
* Check to see whether or not the specified directory is accessible
|
56 |
* @param string $dirPath
|
57 |
+
* @return boolean
|
58 |
*/
|
59 |
protected function CheckDirectory($dirPath)
|
60 |
{
|
classes/AbstractView.php
CHANGED
@@ -1,9 +1,14 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
/**
|
6 |
-
* @var WpSecurityAuditLog
|
7 |
*/
|
8 |
protected $_plugin;
|
9 |
|
@@ -20,35 +25,40 @@ abstract class WSAL_AbstractView {
|
|
20 |
* @var boolean
|
21 |
*/
|
22 |
public $is_active = false;
|
|
|
|
|
23 |
|
24 |
/**
|
25 |
* @param WpSecurityAuditLog $plugin
|
26 |
*/
|
27 |
-
public function __construct(WpSecurityAuditLog $plugin)
|
|
|
28 |
$this->_plugin = $plugin;
|
29 |
|
30 |
// get and store wordpress version
|
31 |
global $wp_version;
|
32 |
-
if(!isset($wp_version))
|
33 |
$wp_version = get_bloginfo('version');
|
|
|
34 |
$this->_wpversion = floatval($wp_version);
|
35 |
|
36 |
// handle admin notices
|
37 |
add_action('wp_ajax_AjaxDismissNotice', array($this, 'AjaxDismissNotice'));
|
38 |
}
|
39 |
|
40 |
-
public static $AllowedNoticeNames = array();
|
41 |
-
|
42 |
/**
|
43 |
* Dismiss an admin notice through ajax.
|
44 |
* @internal
|
45 |
*/
|
46 |
-
public function AjaxDismissNotice()
|
47 |
-
|
|
|
48 |
die('Access Denied.');
|
|
|
49 |
|
50 |
-
if(!isset($_REQUEST['notice']))
|
51 |
die('Notice name expected as "notice" parameter.');
|
|
|
52 |
|
53 |
$this->DismissNotice($_REQUEST['notice']);
|
54 |
}
|
@@ -57,7 +67,8 @@ abstract class WSAL_AbstractView {
|
|
57 |
* @param string $name Name of notice.
|
58 |
* @return boolean Whether notice got dismissed or not.
|
59 |
*/
|
60 |
-
public function IsNoticeDismissed($name)
|
|
|
61 |
$user_id = get_current_user_id();
|
62 |
$meta_key = 'wsal-notice-' . $name;
|
63 |
self::$AllowedNoticeNames[] = $name;
|
@@ -67,18 +78,21 @@ abstract class WSAL_AbstractView {
|
|
67 |
/**
|
68 |
* @param string $name Name of notice to dismiss.
|
69 |
*/
|
70 |
-
public function DismissNotice($name)
|
|
|
71 |
$user_id = get_current_user_id();
|
72 |
$meta_key = 'wsal-notice-' . $name;
|
73 |
$old_value = get_user_meta($user_id, $meta_key, true);
|
74 |
-
if (in_array($name, self::$AllowedNoticeNames) || $old_value === false)
|
75 |
update_user_meta($user_id, $meta_key, '1');
|
|
|
76 |
}
|
77 |
|
78 |
/**
|
79 |
* @param string $name Makes this notice available.
|
80 |
*/
|
81 |
-
public function RegisterNotice($name)
|
|
|
82 |
self::$AllowedNoticeNames[] = $name;
|
83 |
}
|
84 |
|
@@ -110,48 +124,60 @@ abstract class WSAL_AbstractView {
|
|
110 |
/**
|
111 |
* Renders the view icon (this has been deprecated in newwer WP versions).
|
112 |
*/
|
113 |
-
public function RenderIcon()
|
|
|
114 |
?><div id="icon-plugins" class="icon32"><br></div><?php
|
115 |
}
|
116 |
|
117 |
/**
|
118 |
* Renders the view title.
|
119 |
*/
|
120 |
-
public function RenderTitle()
|
|
|
121 |
?><h2><?php echo esc_html($this->GetTitle()); ?></h2><?php
|
122 |
}
|
123 |
|
124 |
/**
|
125 |
* @link self::Render()
|
126 |
*/
|
127 |
-
public function RenderContent()
|
|
|
128 |
$this->Render();
|
129 |
}
|
130 |
|
131 |
/**
|
132 |
* @return boolean Whether page should appear in menu or not.
|
133 |
*/
|
134 |
-
public function IsVisible()
|
|
|
|
|
|
|
135 |
|
136 |
/**
|
137 |
* @return boolean Whether page should be accessible or not.
|
138 |
*/
|
139 |
-
public function IsAccessible()
|
|
|
|
|
|
|
140 |
|
141 |
/**
|
142 |
* Used for rendering stuff into head tag.
|
143 |
*/
|
144 |
-
public function Header()
|
|
|
145 |
|
146 |
/**
|
147 |
* Used for rendering stuff in page fotoer.
|
148 |
*/
|
149 |
-
public function Footer()
|
|
|
150 |
|
151 |
/**
|
152 |
* @return string Safe view menu name.
|
153 |
*/
|
154 |
-
public function GetSafeViewName()
|
|
|
155 |
return 'wsal-' . preg_replace('/[^A-Za-z0-9\-]/', '-', $this->GetViewName());
|
156 |
}
|
157 |
|
@@ -159,14 +185,16 @@ abstract class WSAL_AbstractView {
|
|
159 |
* Override this and make it return true to create a shortcut link in plugin page to the view.
|
160 |
* @return boolean
|
161 |
*/
|
162 |
-
public function HasPluginShortcutLink()
|
|
|
163 |
return false;
|
164 |
}
|
165 |
|
166 |
/**
|
167 |
* @return string URL to backend page for displaying view.
|
168 |
*/
|
169 |
-
public function GetUrl()
|
|
|
170 |
$fn = function_exists('network_admin_url') ? 'network_admin_url' : 'admin_url';
|
171 |
return $fn('admin.php?page=' . $this->GetSafeViewName());
|
172 |
}
|
@@ -174,8 +202,8 @@ abstract class WSAL_AbstractView {
|
|
174 |
/**
|
175 |
* @return string Generates view name out of class name.
|
176 |
*/
|
177 |
-
public function GetViewName()
|
|
|
178 |
return strtolower(str_replace(array('WSAL_Views_', 'WSAL_'), '', get_class($this)));
|
179 |
}
|
180 |
-
|
181 |
-
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Abstract class used in all the views.
|
6 |
+
* @see Views/*.php
|
7 |
+
*/
|
8 |
+
abstract class WSAL_AbstractView
|
9 |
+
{
|
10 |
/**
|
11 |
+
* @var WpSecurityAuditLog
|
12 |
*/
|
13 |
protected $_plugin;
|
14 |
|
25 |
* @var boolean
|
26 |
*/
|
27 |
public $is_active = false;
|
28 |
+
|
29 |
+
public static $AllowedNoticeNames = array();
|
30 |
|
31 |
/**
|
32 |
* @param WpSecurityAuditLog $plugin
|
33 |
*/
|
34 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
35 |
+
{
|
36 |
$this->_plugin = $plugin;
|
37 |
|
38 |
// get and store wordpress version
|
39 |
global $wp_version;
|
40 |
+
if (!isset($wp_version)) {
|
41 |
$wp_version = get_bloginfo('version');
|
42 |
+
}
|
43 |
$this->_wpversion = floatval($wp_version);
|
44 |
|
45 |
// handle admin notices
|
46 |
add_action('wp_ajax_AjaxDismissNotice', array($this, 'AjaxDismissNotice'));
|
47 |
}
|
48 |
|
|
|
|
|
49 |
/**
|
50 |
* Dismiss an admin notice through ajax.
|
51 |
* @internal
|
52 |
*/
|
53 |
+
public function AjaxDismissNotice()
|
54 |
+
{
|
55 |
+
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
56 |
die('Access Denied.');
|
57 |
+
}
|
58 |
|
59 |
+
if (!isset($_REQUEST['notice'])) {
|
60 |
die('Notice name expected as "notice" parameter.');
|
61 |
+
}
|
62 |
|
63 |
$this->DismissNotice($_REQUEST['notice']);
|
64 |
}
|
67 |
* @param string $name Name of notice.
|
68 |
* @return boolean Whether notice got dismissed or not.
|
69 |
*/
|
70 |
+
public function IsNoticeDismissed($name)
|
71 |
+
{
|
72 |
$user_id = get_current_user_id();
|
73 |
$meta_key = 'wsal-notice-' . $name;
|
74 |
self::$AllowedNoticeNames[] = $name;
|
78 |
/**
|
79 |
* @param string $name Name of notice to dismiss.
|
80 |
*/
|
81 |
+
public function DismissNotice($name)
|
82 |
+
{
|
83 |
$user_id = get_current_user_id();
|
84 |
$meta_key = 'wsal-notice-' . $name;
|
85 |
$old_value = get_user_meta($user_id, $meta_key, true);
|
86 |
+
if (in_array($name, self::$AllowedNoticeNames) || $old_value === false) {
|
87 |
update_user_meta($user_id, $meta_key, '1');
|
88 |
+
}
|
89 |
}
|
90 |
|
91 |
/**
|
92 |
* @param string $name Makes this notice available.
|
93 |
*/
|
94 |
+
public function RegisterNotice($name)
|
95 |
+
{
|
96 |
self::$AllowedNoticeNames[] = $name;
|
97 |
}
|
98 |
|
124 |
/**
|
125 |
* Renders the view icon (this has been deprecated in newwer WP versions).
|
126 |
*/
|
127 |
+
public function RenderIcon()
|
128 |
+
{
|
129 |
?><div id="icon-plugins" class="icon32"><br></div><?php
|
130 |
}
|
131 |
|
132 |
/**
|
133 |
* Renders the view title.
|
134 |
*/
|
135 |
+
public function RenderTitle()
|
136 |
+
{
|
137 |
?><h2><?php echo esc_html($this->GetTitle()); ?></h2><?php
|
138 |
}
|
139 |
|
140 |
/**
|
141 |
* @link self::Render()
|
142 |
*/
|
143 |
+
public function RenderContent()
|
144 |
+
{
|
145 |
$this->Render();
|
146 |
}
|
147 |
|
148 |
/**
|
149 |
* @return boolean Whether page should appear in menu or not.
|
150 |
*/
|
151 |
+
public function IsVisible()
|
152 |
+
{
|
153 |
+
return true;
|
154 |
+
}
|
155 |
|
156 |
/**
|
157 |
* @return boolean Whether page should be accessible or not.
|
158 |
*/
|
159 |
+
public function IsAccessible()
|
160 |
+
{
|
161 |
+
return true;
|
162 |
+
}
|
163 |
|
164 |
/**
|
165 |
* Used for rendering stuff into head tag.
|
166 |
*/
|
167 |
+
public function Header()
|
168 |
+
{}
|
169 |
|
170 |
/**
|
171 |
* Used for rendering stuff in page fotoer.
|
172 |
*/
|
173 |
+
public function Footer()
|
174 |
+
{}
|
175 |
|
176 |
/**
|
177 |
* @return string Safe view menu name.
|
178 |
*/
|
179 |
+
public function GetSafeViewName()
|
180 |
+
{
|
181 |
return 'wsal-' . preg_replace('/[^A-Za-z0-9\-]/', '-', $this->GetViewName());
|
182 |
}
|
183 |
|
185 |
* Override this and make it return true to create a shortcut link in plugin page to the view.
|
186 |
* @return boolean
|
187 |
*/
|
188 |
+
public function HasPluginShortcutLink()
|
189 |
+
{
|
190 |
return false;
|
191 |
}
|
192 |
|
193 |
/**
|
194 |
* @return string URL to backend page for displaying view.
|
195 |
*/
|
196 |
+
public function GetUrl()
|
197 |
+
{
|
198 |
$fn = function_exists('network_admin_url') ? 'network_admin_url' : 'admin_url';
|
199 |
return $fn('admin.php?page=' . $this->GetSafeViewName());
|
200 |
}
|
202 |
/**
|
203 |
* @return string Generates view name out of class name.
|
204 |
*/
|
205 |
+
public function GetViewName()
|
206 |
+
{
|
207 |
return strtolower(str_replace(array('WSAL_Views_', 'WSAL_'), '', get_class($this)));
|
208 |
}
|
209 |
+
}
|
|
classes/Adapters/ActiveRecordInterface.php
CHANGED
@@ -1,15 +1,19 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
|
|
|
|
|
|
|
|
15 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Interface used by the ActiveRecord.
|
6 |
+
*/
|
7 |
+
interface WSAL_Adapters_ActiveRecordInterface
|
8 |
+
{
|
9 |
+
public function IsInstalled();
|
10 |
+
public function Install();
|
11 |
+
public function Uninstall();
|
12 |
+
public function Load($cond = '%d', $args = array(1));
|
13 |
+
public function Save($activeRecord);
|
14 |
+
public function Delete($activeRecord);
|
15 |
+
public function LoadMulti($cond, $args = array());
|
16 |
+
public function LoadAndCallForEach($callback, $cond = '%d', $args = array(1));
|
17 |
+
public function Count($cond = '%d', $args = array(1));
|
18 |
+
public function LoadMultiQuery($query, $args = array());
|
19 |
}
|
classes/Adapters/MetaInterface.php
CHANGED
@@ -1,13 +1,17 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
/**
|
5 |
-
* Create a meta object
|
6 |
-
* @param $metaData Array of meta data
|
7 |
-
* @return int ID of the new meta data
|
8 |
-
*/
|
9 |
-
public function deleteByOccurenceIds($occurenceIds);
|
10 |
-
|
11 |
-
public function loadByNameAndOccurenceId($metaName, $occurenceId);
|
12 |
-
|
13 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Interface used by the Metadata.
|
6 |
+
*/
|
7 |
+
interface WSAL_Adapters_MetaInterface
|
8 |
+
{
|
9 |
+
/**
|
10 |
+
* Create a meta object
|
11 |
+
* @param $metaData Array of meta data
|
12 |
+
* @return int ID of the new meta data
|
13 |
+
*/
|
14 |
+
public function deleteByOccurenceIds($occurenceIds);
|
15 |
|
16 |
+
public function loadByNameAndOccurenceId($metaName, $occurenceId);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
17 |
}
|
classes/Adapters/MySQL/ActiveRecordAdapter.php
CHANGED
@@ -1,5 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInterface
|
4 |
{
|
5 |
protected $connection;
|
@@ -21,6 +28,9 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
21 |
$this->connection = $conn;
|
22 |
}
|
23 |
|
|
|
|
|
|
|
24 |
public function GetModel()
|
25 |
{
|
26 |
return new WSAL_Models_ActiveRecord();
|
@@ -62,9 +72,11 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
62 |
|
63 |
if (!isset($this->_column_cache)) {
|
64 |
$this->_column_cache = array();
|
65 |
-
foreach (array_keys(get_object_vars($model)) as $col)
|
66 |
-
if (trim($col) && $col[0] != '_')
|
67 |
$this->_column_cache[] = $col;
|
|
|
|
|
68 |
}
|
69 |
return $this->_column_cache;
|
70 |
}
|
@@ -73,8 +85,8 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
73 |
* @deprecated
|
74 |
* @return boolean Returns whether table structure is installed or not.
|
75 |
*/
|
76 |
-
public function IsInstalled()
|
77 |
-
|
78 |
$_wpdb = $this->connection;
|
79 |
$sql = 'SHOW TABLES LIKE "' . $this->GetTable() . '"';
|
80 |
return strtolower($_wpdb->get_var($sql)) == strtolower($this->GetTable());
|
@@ -83,36 +95,36 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
83 |
/**
|
84 |
* Install this ActiveRecord structure into DB.
|
85 |
*/
|
86 |
-
public function Install()
|
|
|
87 |
$_wpdb = $this->connection;
|
88 |
$_wpdb->query($this->_GetInstallQuery());
|
89 |
}
|
90 |
|
91 |
-
|
92 |
* Install this ActiveRecord structure into DB WordPress.
|
93 |
*/
|
94 |
-
public function InstallOriginal()
|
|
|
95 |
global $wpdb;
|
96 |
$wpdb->query($this->_GetInstallQuery(true));
|
97 |
}
|
98 |
|
99 |
/**
|
100 |
-
* Remove this ActiveRecord structure
|
101 |
*/
|
102 |
public function Uninstall()
|
103 |
{
|
104 |
-
//global $wpdb;
|
105 |
$_wpdb = $this->connection;
|
106 |
$_wpdb->query($this->_GetUninstallQuery());
|
107 |
}
|
108 |
|
109 |
/**
|
110 |
-
* Save an active record
|
111 |
* @return integer|boolean Either the number of modified/inserted rows or false on failure.
|
112 |
*/
|
113 |
public function Save($activeRecord)
|
114 |
{
|
115 |
-
//global $wpdb;
|
116 |
$_wpdb = $this->connection;
|
117 |
$copy = $activeRecord;
|
118 |
$data = array();
|
@@ -155,13 +167,12 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
155 |
}
|
156 |
|
157 |
/**
|
158 |
-
* Load record from DB.
|
159 |
* @param string $cond (Optional) Load condition.
|
160 |
* @param array $args (Optional) Load condition arguments.
|
161 |
*/
|
162 |
public function Load($cond = '%d', $args = array(1))
|
163 |
{
|
164 |
-
//global $wpdb;
|
165 |
$_wpdb = $this->connection;
|
166 |
|
167 |
$sql = $_wpdb->prepare('SELECT * FROM '.$this->GetTable().' WHERE '. $cond, $args);
|
@@ -170,9 +181,13 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
170 |
return $data;
|
171 |
}
|
172 |
|
|
|
|
|
|
|
|
|
|
|
173 |
public function LoadArray($cond, $args = array())
|
174 |
{
|
175 |
-
//global $wpdb;
|
176 |
$_wpdb = $this->connection;
|
177 |
$result = array();
|
178 |
$sql = $_wpdb->prepare('SELECT * FROM '.$this->GetTable().' WHERE '. $cond, $args);
|
@@ -188,7 +203,6 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
188 |
*/
|
189 |
public function Delete($activeRecord)
|
190 |
{
|
191 |
-
//global $wpdb;
|
192 |
$_wpdb = $this->connection;
|
193 |
$result = $_wpdb->delete(
|
194 |
$this->GetTable(),
|
@@ -218,7 +232,6 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
218 |
*/
|
219 |
public function LoadMulti($cond, $args = array())
|
220 |
{
|
221 |
-
//global $wpdb;
|
222 |
$_wpdb = $this->connection;
|
223 |
$result = array();
|
224 |
$sql = (!is_array($args) || !count($args)) // do we really need to prepare() or not?
|
@@ -240,7 +253,6 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
240 |
*/
|
241 |
public function LoadAndCallForEach($callback, $cond = '%d', $args = array(1))
|
242 |
{
|
243 |
-
//global $wpdb;
|
244 |
$_wpdb = $this->connection;
|
245 |
$class = get_called_class();
|
246 |
$sql = $_wpdb->prepare('SELECT * FROM ' . $this->GetTable() . ' WHERE '.$cond, $args);
|
@@ -258,7 +270,6 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
258 |
*/
|
259 |
public function Count($cond = '%d', $args = array(1))
|
260 |
{
|
261 |
-
//global $wpdb;
|
262 |
$_wpdb = $this->connection;
|
263 |
$class = get_called_class();
|
264 |
$sql = $_wpdb->prepare('SELECT COUNT(*) FROM ' . $this->GetTable() . ' WHERE ' . $cond, $args);
|
@@ -273,7 +284,6 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
273 |
*/
|
274 |
public function CountQuery($query, $args = array())
|
275 |
{
|
276 |
-
//global $wpdb;
|
277 |
$_wpdb = $this->connection;
|
278 |
$sql = count($args) ? $_wpdb->prepare($query, $args) : $query;
|
279 |
return (int)$_wpdb->get_var($sql);
|
@@ -287,7 +297,6 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
287 |
*/
|
288 |
public function LoadMultiQuery($query, $args = array())
|
289 |
{
|
290 |
-
//global $wpdb;
|
291 |
$_wpdb = $this->connection;
|
292 |
$class = get_called_class();
|
293 |
$result = array();
|
@@ -299,6 +308,7 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
299 |
}
|
300 |
|
301 |
/**
|
|
|
302 |
* @return string Must return SQL for creating table.
|
303 |
*/
|
304 |
protected function _GetInstallQuery($prefix = false)
|
@@ -349,7 +359,6 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
349 |
}
|
350 |
|
351 |
return $sql;
|
352 |
-
|
353 |
}
|
354 |
|
355 |
/**
|
@@ -360,6 +369,11 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
360 |
return 'DROP TABLE ' . $this->GetTable();
|
361 |
}
|
362 |
|
|
|
|
|
|
|
|
|
|
|
363 |
private function GetUserNames($_userId)
|
364 |
{
|
365 |
global $wpdb;
|
@@ -379,7 +393,16 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
379 |
}
|
380 |
|
381 |
/**
|
382 |
-
* Function used in WSAL reporting extension
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
383 |
*/
|
384 |
public function GetReporting($_siteId, $_userId, $_roleName, $_alertCode, $_startTimestamp, $_endTimestamp, $_nextDate = null, $_limit = 0)
|
385 |
{
|
@@ -456,8 +479,10 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
456 |
}
|
457 |
|
458 |
/**
|
459 |
-
* Function used in WSAL reporting extension
|
460 |
-
* Check if criteria are matching in the DB
|
|
|
|
|
461 |
*/
|
462 |
public function CheckMatchReportCriteria($criteria)
|
463 |
{
|
@@ -509,7 +534,17 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
509 |
}
|
510 |
|
511 |
/**
|
512 |
-
*
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
513 |
*/
|
514 |
public function GetReportGrouped($_siteId, $_startTimestamp, $_endTimestamp, $_userId = 'null', $_roleName = 'null', $_ipAddress = 'null', $_alertCode = 'null', $_limit = 0)
|
515 |
{
|
@@ -623,8 +658,9 @@ class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInte
|
|
623 |
}
|
624 |
|
625 |
/**
|
626 |
-
*
|
627 |
-
* It is used in the query of the above function
|
|
|
628 |
*/
|
629 |
private function TempUsers($tableUsers)
|
630 |
{
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* MySQL database ActiveRecord class.
|
5 |
+
*
|
6 |
+
* MySQL generic table used for Save, Read, Create or Delete
|
7 |
+
* elements in the Database.
|
8 |
+
* There are also the functions used in the Report Add-On to get the reports.
|
9 |
+
*/
|
10 |
class WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_ActiveRecordInterface
|
11 |
{
|
12 |
protected $connection;
|
28 |
$this->connection = $conn;
|
29 |
}
|
30 |
|
31 |
+
/**
|
32 |
+
* @return WSAL_Models_ActiveRecord
|
33 |
+
*/
|
34 |
public function GetModel()
|
35 |
{
|
36 |
return new WSAL_Models_ActiveRecord();
|
72 |
|
73 |
if (!isset($this->_column_cache)) {
|
74 |
$this->_column_cache = array();
|
75 |
+
foreach (array_keys(get_object_vars($model)) as $col) {
|
76 |
+
if (trim($col) && $col[0] != '_') {
|
77 |
$this->_column_cache[] = $col;
|
78 |
+
}
|
79 |
+
}
|
80 |
}
|
81 |
return $this->_column_cache;
|
82 |
}
|
85 |
* @deprecated
|
86 |
* @return boolean Returns whether table structure is installed or not.
|
87 |
*/
|
88 |
+
public function IsInstalled()
|
89 |
+
{
|
90 |
$_wpdb = $this->connection;
|
91 |
$sql = 'SHOW TABLES LIKE "' . $this->GetTable() . '"';
|
92 |
return strtolower($_wpdb->get_var($sql)) == strtolower($this->GetTable());
|
95 |
/**
|
96 |
* Install this ActiveRecord structure into DB.
|
97 |
*/
|
98 |
+
public function Install()
|
99 |
+
{
|
100 |
$_wpdb = $this->connection;
|
101 |
$_wpdb->query($this->_GetInstallQuery());
|
102 |
}
|
103 |
|
104 |
+
/**
|
105 |
* Install this ActiveRecord structure into DB WordPress.
|
106 |
*/
|
107 |
+
public function InstallOriginal()
|
108 |
+
{
|
109 |
global $wpdb;
|
110 |
$wpdb->query($this->_GetInstallQuery(true));
|
111 |
}
|
112 |
|
113 |
/**
|
114 |
+
* Remove this ActiveRecord structure from DB.
|
115 |
*/
|
116 |
public function Uninstall()
|
117 |
{
|
|
|
118 |
$_wpdb = $this->connection;
|
119 |
$_wpdb->query($this->_GetUninstallQuery());
|
120 |
}
|
121 |
|
122 |
/**
|
123 |
+
* Save an active record into DB.
|
124 |
* @return integer|boolean Either the number of modified/inserted rows or false on failure.
|
125 |
*/
|
126 |
public function Save($activeRecord)
|
127 |
{
|
|
|
128 |
$_wpdb = $this->connection;
|
129 |
$copy = $activeRecord;
|
130 |
$data = array();
|
167 |
}
|
168 |
|
169 |
/**
|
170 |
+
* Load record from DB (Single row).
|
171 |
* @param string $cond (Optional) Load condition.
|
172 |
* @param array $args (Optional) Load condition arguments.
|
173 |
*/
|
174 |
public function Load($cond = '%d', $args = array(1))
|
175 |
{
|
|
|
176 |
$_wpdb = $this->connection;
|
177 |
|
178 |
$sql = $_wpdb->prepare('SELECT * FROM '.$this->GetTable().' WHERE '. $cond, $args);
|
181 |
return $data;
|
182 |
}
|
183 |
|
184 |
+
/**
|
185 |
+
* Load records from DB (Multi rows).
|
186 |
+
* @param string $cond Load condition.
|
187 |
+
* @param array $args (Optional) Load condition arguments.
|
188 |
+
*/
|
189 |
public function LoadArray($cond, $args = array())
|
190 |
{
|
|
|
191 |
$_wpdb = $this->connection;
|
192 |
$result = array();
|
193 |
$sql = $_wpdb->prepare('SELECT * FROM '.$this->GetTable().' WHERE '. $cond, $args);
|
203 |
*/
|
204 |
public function Delete($activeRecord)
|
205 |
{
|
|
|
206 |
$_wpdb = $this->connection;
|
207 |
$result = $_wpdb->delete(
|
208 |
$this->GetTable(),
|
232 |
*/
|
233 |
public function LoadMulti($cond, $args = array())
|
234 |
{
|
|
|
235 |
$_wpdb = $this->connection;
|
236 |
$result = array();
|
237 |
$sql = (!is_array($args) || !count($args)) // do we really need to prepare() or not?
|
253 |
*/
|
254 |
public function LoadAndCallForEach($callback, $cond = '%d', $args = array(1))
|
255 |
{
|
|
|
256 |
$_wpdb = $this->connection;
|
257 |
$class = get_called_class();
|
258 |
$sql = $_wpdb->prepare('SELECT * FROM ' . $this->GetTable() . ' WHERE '.$cond, $args);
|
270 |
*/
|
271 |
public function Count($cond = '%d', $args = array(1))
|
272 |
{
|
|
|
273 |
$_wpdb = $this->connection;
|
274 |
$class = get_called_class();
|
275 |
$sql = $_wpdb->prepare('SELECT COUNT(*) FROM ' . $this->GetTable() . ' WHERE ' . $cond, $args);
|
284 |
*/
|
285 |
public function CountQuery($query, $args = array())
|
286 |
{
|
|
|
287 |
$_wpdb = $this->connection;
|
288 |
$sql = count($args) ? $_wpdb->prepare($query, $args) : $query;
|
289 |
return (int)$_wpdb->get_var($sql);
|
297 |
*/
|
298 |
public function LoadMultiQuery($query, $args = array())
|
299 |
{
|
|
|
300 |
$_wpdb = $this->connection;
|
301 |
$class = get_called_class();
|
302 |
$result = array();
|
308 |
}
|
309 |
|
310 |
/**
|
311 |
+
* @param string $prefix (Optional) table prefix
|
312 |
* @return string Must return SQL for creating table.
|
313 |
*/
|
314 |
protected function _GetInstallQuery($prefix = false)
|
359 |
}
|
360 |
|
361 |
return $sql;
|
|
|
362 |
}
|
363 |
|
364 |
/**
|
369 |
return 'DROP TABLE ' . $this->GetTable();
|
370 |
}
|
371 |
|
372 |
+
/**
|
373 |
+
* Get Users user_login.
|
374 |
+
* @param int $_userId user ID
|
375 |
+
* @return string comma separated users login
|
376 |
+
*/
|
377 |
private function GetUserNames($_userId)
|
378 |
{
|
379 |
global $wpdb;
|
393 |
}
|
394 |
|
395 |
/**
|
396 |
+
* Function used in WSAL reporting extension.
|
397 |
+
* @param int $_siteId site ID
|
398 |
+
* @param int $_userId user ID
|
399 |
+
* @param string $_roleName user role
|
400 |
+
* @param int $_alertCode alert code
|
401 |
+
* @param timestamp $_startTimestamp from created_on
|
402 |
+
* @param timestamp $_endTimestamp to created_on
|
403 |
+
* @param timestamp $_nextDate (Optional) created_on >
|
404 |
+
* @param int $_limit (Optional) limit
|
405 |
+
* @return array Report results
|
406 |
*/
|
407 |
public function GetReporting($_siteId, $_userId, $_roleName, $_alertCode, $_startTimestamp, $_endTimestamp, $_nextDate = null, $_limit = 0)
|
408 |
{
|
479 |
}
|
480 |
|
481 |
/**
|
482 |
+
* Function used in WSAL reporting extension.
|
483 |
+
* Check if criteria are matching in the DB.
|
484 |
+
* @param mixed $criteria query conditions
|
485 |
+
* @return int count of distinct values
|
486 |
*/
|
487 |
public function CheckMatchReportCriteria($criteria)
|
488 |
{
|
534 |
}
|
535 |
|
536 |
/**
|
537 |
+
* Function used in WSAL reporting extension.
|
538 |
+
* List of unique IP addresses used by the same user.
|
539 |
+
* @param int $_siteId site ID
|
540 |
+
* @param timestamp $_startTimestamp from created_on
|
541 |
+
* @param timestamp $_endTimestamp to created_on
|
542 |
+
* @param int $_userId (Optional) user ID
|
543 |
+
* @param string $_roleName (Optional) user role
|
544 |
+
* @param string $_ipAddress (Optional) IP address
|
545 |
+
* @param int $_alertCode (Optional) alert code
|
546 |
+
* @param int $_limit (Optional) limit
|
547 |
+
* @return array Report results grouped by IP and Username
|
548 |
*/
|
549 |
public function GetReportGrouped($_siteId, $_startTimestamp, $_endTimestamp, $_userId = 'null', $_roleName = 'null', $_ipAddress = 'null', $_alertCode = 'null', $_limit = 0)
|
550 |
{
|
658 |
}
|
659 |
|
660 |
/**
|
661 |
+
* DELETE from table `tmp_users` and populate with users.
|
662 |
+
* It is used in the query of the above function.
|
663 |
+
* @param string $tableUsers table name
|
664 |
*/
|
665 |
private function TempUsers($tableUsers)
|
666 |
{
|
classes/Adapters/MySQL/MetaAdapter.php
CHANGED
@@ -1,7 +1,13 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
5 |
protected $_table = 'wsal_metadata';
|
6 |
protected $_idkey = 'id';
|
7 |
|
@@ -11,6 +17,9 @@ class WSAL_Adapters_MySQL_Meta extends WSAL_Adapters_MySQL_ActiveRecord implemen
|
|
11 |
public static $name_maxlength = 100;
|
12 |
public $value = array(); // force mixed type
|
13 |
|
|
|
|
|
|
|
14 |
public function GetModel()
|
15 |
{
|
16 |
return new WSAL_Models_Meta();
|
@@ -21,11 +30,19 @@ class WSAL_Adapters_MySQL_Meta extends WSAL_Adapters_MySQL_ActiveRecord implemen
|
|
21 |
parent::__construct($conn);
|
22 |
}
|
23 |
|
24 |
-
|
|
|
|
|
|
|
|
|
25 |
return parent::GetTableOptions() . ',' . PHP_EOL
|
26 |
. ' KEY occurrence_name (occurrence_id,name)';
|
27 |
}
|
28 |
|
|
|
|
|
|
|
|
|
29 |
public function DeleteByOccurenceIds($occurenceIds)
|
30 |
{
|
31 |
if (!empty($occurenceIds)) {
|
@@ -35,16 +52,29 @@ class WSAL_Adapters_MySQL_Meta extends WSAL_Adapters_MySQL_ActiveRecord implemen
|
|
35 |
}
|
36 |
}
|
37 |
|
|
|
|
|
|
|
|
|
|
|
|
|
38 |
public function LoadByNameAndOccurenceId($metaName, $occurenceId)
|
39 |
{
|
40 |
return $this->Load('occurrence_id = %d AND name = %s', array($occurenceId, $metaName));
|
41 |
}
|
42 |
|
|
|
|
|
|
|
|
|
|
|
43 |
public function GetMatchingIPs($limit = null)
|
44 |
{
|
45 |
$_wpdb = $this->connection;
|
46 |
$sql = "SELECT DISTINCT value FROM {$this->GetTable()} WHERE name = \"ClientIP\"";
|
47 |
-
if (!is_null($limit))
|
|
|
|
|
48 |
$ips = $_wpdb->get_col($sql);
|
49 |
foreach ($ips as $key => $ip) {
|
50 |
$ips[$key] = str_replace('"', '', $ip);
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* MySQL database Metadata class.
|
5 |
+
*
|
6 |
+
* MySQL wsal_metadata table used for to store the alert meta data:
|
7 |
+
* username, user_roles, client_ip, user_agent, post_id, post_title, etc.
|
8 |
+
*/
|
9 |
+
class WSAL_Adapters_MySQL_Meta extends WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_MetaInterface
|
10 |
+
{
|
11 |
protected $_table = 'wsal_metadata';
|
12 |
protected $_idkey = 'id';
|
13 |
|
17 |
public static $name_maxlength = 100;
|
18 |
public $value = array(); // force mixed type
|
19 |
|
20 |
+
/**
|
21 |
+
* @return WSAL_Models_Meta
|
22 |
+
*/
|
23 |
public function GetModel()
|
24 |
{
|
25 |
return new WSAL_Models_Meta();
|
30 |
parent::__construct($conn);
|
31 |
}
|
32 |
|
33 |
+
/**
|
34 |
+
* @return string SQL table options (constraints, foreign keys, indexes etc).
|
35 |
+
*/
|
36 |
+
protected function GetTableOptions()
|
37 |
+
{
|
38 |
return parent::GetTableOptions() . ',' . PHP_EOL
|
39 |
. ' KEY occurrence_name (occurrence_id,name)';
|
40 |
}
|
41 |
|
42 |
+
/**
|
43 |
+
* Delete metadata by occurrence_id.
|
44 |
+
* @param array $occurenceIds list of occurrence IDs
|
45 |
+
*/
|
46 |
public function DeleteByOccurenceIds($occurenceIds)
|
47 |
{
|
48 |
if (!empty($occurenceIds)) {
|
52 |
}
|
53 |
}
|
54 |
|
55 |
+
/**
|
56 |
+
* Load metadata by name and occurrence_id.
|
57 |
+
* @param string $metaName metadata name
|
58 |
+
* @param string $occurenceId metadata occurrence_id
|
59 |
+
* @return WSAL_Meta[]
|
60 |
+
*/
|
61 |
public function LoadByNameAndOccurenceId($metaName, $occurenceId)
|
62 |
{
|
63 |
return $this->Load('occurrence_id = %d AND name = %s', array($occurenceId, $metaName));
|
64 |
}
|
65 |
|
66 |
+
/**
|
67 |
+
* Get distinct values of IPs.
|
68 |
+
* @param int $limit (Optional) limit
|
69 |
+
* @return array distinct values of IPs
|
70 |
+
*/
|
71 |
public function GetMatchingIPs($limit = null)
|
72 |
{
|
73 |
$_wpdb = $this->connection;
|
74 |
$sql = "SELECT DISTINCT value FROM {$this->GetTable()} WHERE name = \"ClientIP\"";
|
75 |
+
if (!is_null($limit)) {
|
76 |
+
$sql .= ' LIMIT ' . $limit;
|
77 |
+
}
|
78 |
$ips = $_wpdb->get_col($sql);
|
79 |
foreach ($ips as $key => $ip) {
|
80 |
$ips[$key] = str_replace('"', '', $ip);
|
classes/Adapters/MySQL/OccurrenceAdapter.php
CHANGED
@@ -1,7 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
protected $_table = 'wsal_occurrences';
|
6 |
protected $_idkey = 'id';
|
7 |
protected $_meta;
|
@@ -13,33 +18,50 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
13 |
public $is_read = false;
|
14 |
public $is_migrated = false;
|
15 |
|
16 |
-
public function __construct($conn)
|
|
|
17 |
parent::__construct($conn);
|
18 |
}
|
19 |
|
20 |
-
|
|
|
|
|
|
|
|
|
21 |
return parent::GetTableOptions() . ',' . PHP_EOL
|
22 |
. ' KEY site_alert_created (site_id,alert_id,created_on)';
|
23 |
}
|
24 |
|
|
|
|
|
|
|
25 |
public function GetModel()
|
26 |
{
|
27 |
return new WSAL_Models_Occurrence();
|
28 |
}
|
|
|
29 |
/**
|
30 |
-
* Returns
|
31 |
-
* @
|
|
|
32 |
*/
|
33 |
-
public function GetMeta($occurence)
|
34 |
-
|
|
|
35 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
36 |
$this->_meta = $meta->Load('occurrence_id = %d', array($occurence->id));
|
37 |
}
|
38 |
return $this->_meta;
|
39 |
}
|
40 |
|
41 |
-
|
42 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
43 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
44 |
$this->_meta = $meta->LoadArray('occurrence_id = %d', array($occurence->id));
|
45 |
}
|
@@ -48,10 +70,12 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
48 |
|
49 |
/**
|
50 |
* Loads a meta item given its name.
|
|
|
51 |
* @param string $name Meta name.
|
52 |
* @return WSAL_Meta The meta item, be sure to checked if it was loaded successfully.
|
53 |
*/
|
54 |
-
public function GetNamedMeta($occurence, $name)
|
|
|
55 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
56 |
$this->_meta = $meta->Load('occurrence_id = %d AND name = %s', array($occurence->id, $name));
|
57 |
|
@@ -63,7 +87,8 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
63 |
* @param array $names List of meta names.
|
64 |
* @return WSAL_Meta The first meta item that exists.
|
65 |
*/
|
66 |
-
public function GetFirstNamedMeta($occurence, $names)
|
|
|
67 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
68 |
$query = '(' . str_repeat('name = %s OR ', count($names)).'0)';
|
69 |
$query = 'occurrence_id = %d AND ' . $query . ' ORDER BY name DESC LIMIT 1';
|
@@ -81,7 +106,8 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
81 |
* @param integer $limit Maximum limit.
|
82 |
* @return WSAL_Occurrence[]
|
83 |
*/
|
84 |
-
public static function GetNewestUnique($limit = PHP_INT_MAX)
|
|
|
85 |
$temp = new self();
|
86 |
return self::LoadMultiQuery('
|
87 |
SELECT *, COUNT(alert_id) as count
|
@@ -96,13 +122,14 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
96 |
}
|
97 |
|
98 |
/**
|
99 |
-
* Gets occurences of the same type by IP and Username within specified time frame
|
100 |
* @param string $ipAddress
|
101 |
* @param string $username
|
102 |
* @param int $alertId Alert type we are lookign for
|
103 |
* @param int $siteId
|
104 |
* @param $startTime mktime
|
105 |
* @param $endTime mktime
|
|
|
106 |
*/
|
107 |
public function CheckKnownUsers($args = array())
|
108 |
{
|
@@ -122,6 +149,15 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
122 |
);
|
123 |
}
|
124 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
125 |
public function CheckUnKnownUsers($args = array())
|
126 |
{
|
127 |
$tt2 = new WSAL_Adapters_MySQL_Meta($this->connection);
|
@@ -136,6 +172,10 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
136 |
);
|
137 |
}
|
138 |
|
|
|
|
|
|
|
|
|
139 |
protected function prepareOccurrenceQuery($query)
|
140 |
{
|
141 |
$searchQueryParameters = array();
|
@@ -167,8 +207,9 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
167 |
}
|
168 |
|
169 |
/**
|
170 |
-
* Gets occurrence by Post_id
|
171 |
* @param int $post_id
|
|
|
172 |
*/
|
173 |
public function GetByPostID($post_id)
|
174 |
{
|
@@ -185,15 +226,16 @@ class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord im
|
|
185 |
}
|
186 |
|
187 |
/**
|
188 |
-
* Gets occurences of the same type by IP within specified time frame
|
189 |
* @param string $ipAddress
|
190 |
* @param string $username
|
191 |
* @param int $alertId Alert type we are lookign for
|
192 |
* @param int $siteId
|
193 |
* @param $startTime mktime
|
194 |
* @param $endTime mktime
|
|
|
195 |
*/
|
196 |
-
public function CheckAlert404($args = array())
|
197 |
{
|
198 |
$tt2 = new WSAL_Adapters_MySQL_Meta($this->connection);
|
199 |
return self::LoadMultiQuery(
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* MySQL database Occurrence class.
|
5 |
+
*
|
6 |
+
* MySQL wsal_occurrences table used for to store the alerts.
|
7 |
+
*/
|
8 |
+
class WSAL_Adapters_MySQL_Occurrence extends WSAL_Adapters_MySQL_ActiveRecord implements WSAL_Adapters_OccurrenceInterface
|
9 |
+
{
|
10 |
protected $_table = 'wsal_occurrences';
|
11 |
protected $_idkey = 'id';
|
12 |
protected $_meta;
|
18 |
public $is_read = false;
|
19 |
public $is_migrated = false;
|
20 |
|
21 |
+
public function __construct($conn)
|
22 |
+
{
|
23 |
parent::__construct($conn);
|
24 |
}
|
25 |
|
26 |
+
/**
|
27 |
+
* @return string SQL table options (constraints, foreign keys, indexes etc).
|
28 |
+
*/
|
29 |
+
protected function GetTableOptions()
|
30 |
+
{
|
31 |
return parent::GetTableOptions() . ',' . PHP_EOL
|
32 |
. ' KEY site_alert_created (site_id,alert_id,created_on)';
|
33 |
}
|
34 |
|
35 |
+
/**
|
36 |
+
* @return WSAL_Models_Occurrence
|
37 |
+
*/
|
38 |
public function GetModel()
|
39 |
{
|
40 |
return new WSAL_Models_Occurrence();
|
41 |
}
|
42 |
+
|
43 |
/**
|
44 |
+
* Returns metadata related to this event.
|
45 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Load()
|
46 |
+
* @return WSAL_Meta
|
47 |
*/
|
48 |
+
public function GetMeta($occurence)
|
49 |
+
{
|
50 |
+
if (!isset($this->_meta)) {
|
51 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
52 |
$this->_meta = $meta->Load('occurrence_id = %d', array($occurence->id));
|
53 |
}
|
54 |
return $this->_meta;
|
55 |
}
|
56 |
|
57 |
+
/**
|
58 |
+
* Returns allmeta data related to this event.
|
59 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::LoadArray()
|
60 |
+
* @return WSAL_Meta[]
|
61 |
+
*/
|
62 |
+
public function GetMultiMeta($occurence)
|
63 |
+
{
|
64 |
+
if (!isset($this->_meta)) {
|
65 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
66 |
$this->_meta = $meta->LoadArray('occurrence_id = %d', array($occurence->id));
|
67 |
}
|
70 |
|
71 |
/**
|
72 |
* Loads a meta item given its name.
|
73 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Load()
|
74 |
* @param string $name Meta name.
|
75 |
* @return WSAL_Meta The meta item, be sure to checked if it was loaded successfully.
|
76 |
*/
|
77 |
+
public function GetNamedMeta($occurence, $name)
|
78 |
+
{
|
79 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
80 |
$this->_meta = $meta->Load('occurrence_id = %d AND name = %s', array($occurence->id, $name));
|
81 |
|
87 |
* @param array $names List of meta names.
|
88 |
* @return WSAL_Meta The first meta item that exists.
|
89 |
*/
|
90 |
+
public function GetFirstNamedMeta($occurence, $names)
|
91 |
+
{
|
92 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
93 |
$query = '(' . str_repeat('name = %s OR ', count($names)).'0)';
|
94 |
$query = 'occurrence_id = %d AND ' . $query . ' ORDER BY name DESC LIMIT 1';
|
106 |
* @param integer $limit Maximum limit.
|
107 |
* @return WSAL_Occurrence[]
|
108 |
*/
|
109 |
+
public static function GetNewestUnique($limit = PHP_INT_MAX)
|
110 |
+
{
|
111 |
$temp = new self();
|
112 |
return self::LoadMultiQuery('
|
113 |
SELECT *, COUNT(alert_id) as count
|
122 |
}
|
123 |
|
124 |
/**
|
125 |
+
* Gets occurences of the same type by IP and Username within specified time frame.
|
126 |
* @param string $ipAddress
|
127 |
* @param string $username
|
128 |
* @param int $alertId Alert type we are lookign for
|
129 |
* @param int $siteId
|
130 |
* @param $startTime mktime
|
131 |
* @param $endTime mktime
|
132 |
+
* @return WSAL_Occurrence[]
|
133 |
*/
|
134 |
public function CheckKnownUsers($args = array())
|
135 |
{
|
149 |
);
|
150 |
}
|
151 |
|
152 |
+
/**
|
153 |
+
* Gets occurences of the same type by IP within specified time frame.
|
154 |
+
* @param string $ipAddress
|
155 |
+
* @param int $alertId Alert type we are lookign for
|
156 |
+
* @param int $siteId
|
157 |
+
* @param $startTime mktime
|
158 |
+
* @param $endTime mktime
|
159 |
+
* @return WSAL_Occurrence[]
|
160 |
+
*/
|
161 |
public function CheckUnKnownUsers($args = array())
|
162 |
{
|
163 |
$tt2 = new WSAL_Adapters_MySQL_Meta($this->connection);
|
172 |
);
|
173 |
}
|
174 |
|
175 |
+
/**
|
176 |
+
* Add conditions to the Query
|
177 |
+
* @param string $query
|
178 |
+
*/
|
179 |
protected function prepareOccurrenceQuery($query)
|
180 |
{
|
181 |
$searchQueryParameters = array();
|
207 |
}
|
208 |
|
209 |
/**
|
210 |
+
* Gets occurrence by Post_id.
|
211 |
* @param int $post_id
|
212 |
+
* @return WSAL_Occurrence[]
|
213 |
*/
|
214 |
public function GetByPostID($post_id)
|
215 |
{
|
226 |
}
|
227 |
|
228 |
/**
|
229 |
+
* Gets occurences of the same type by IP within specified time frame.
|
230 |
* @param string $ipAddress
|
231 |
* @param string $username
|
232 |
* @param int $alertId Alert type we are lookign for
|
233 |
* @param int $siteId
|
234 |
* @param $startTime mktime
|
235 |
* @param $endTime mktime
|
236 |
+
* @return WSAL_Occurrence[]
|
237 |
*/
|
238 |
+
public function CheckAlert404($args = array())
|
239 |
{
|
240 |
$tt2 = new WSAL_Adapters_MySQL_Meta($this->connection);
|
241 |
return self::LoadMultiQuery(
|
classes/Adapters/MySQL/OptionAdapter.php
CHANGED
@@ -1,8 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Adapters_MySQL_Option extends WSAL_Adapters_MySQL_ActiveRecord
|
4 |
{
|
5 |
-
|
6 |
protected $_table = 'wsal_options';
|
7 |
protected $_idkey = 'id';
|
8 |
|
@@ -16,19 +20,33 @@ class WSAL_Adapters_MySQL_Option extends WSAL_Adapters_MySQL_ActiveRecord
|
|
16 |
parent::__construct($conn);
|
17 |
}
|
18 |
|
|
|
|
|
|
|
19 |
public function GetModel()
|
20 |
{
|
21 |
return new WSAL_Models_Option();
|
22 |
}
|
23 |
|
|
|
|
|
|
|
|
|
|
|
24 |
public function GetNamedOption($name)
|
25 |
-
{
|
|
|
26 |
return $this->Load('option_name = %s', array($name));
|
27 |
} else {
|
28 |
return null;
|
29 |
}
|
30 |
}
|
31 |
|
|
|
|
|
|
|
|
|
|
|
32 |
public function GetNotificationsSetting($opt_prefix)
|
33 |
{
|
34 |
if ($this->IsInstalled()) {
|
@@ -38,6 +56,11 @@ class WSAL_Adapters_MySQL_Option extends WSAL_Adapters_MySQL_ActiveRecord
|
|
38 |
}
|
39 |
}
|
40 |
|
|
|
|
|
|
|
|
|
|
|
41 |
public function GetNotification($id)
|
42 |
{
|
43 |
if ($this->IsInstalled()) {
|
@@ -47,6 +70,11 @@ class WSAL_Adapters_MySQL_Option extends WSAL_Adapters_MySQL_ActiveRecord
|
|
47 |
}
|
48 |
}
|
49 |
|
|
|
|
|
|
|
|
|
|
|
50 |
public function DeleteByName($name)
|
51 |
{
|
52 |
if (!empty($name)) {
|
@@ -58,6 +86,11 @@ class WSAL_Adapters_MySQL_Option extends WSAL_Adapters_MySQL_ActiveRecord
|
|
58 |
}
|
59 |
}
|
60 |
|
|
|
|
|
|
|
|
|
|
|
61 |
public function DeleteByPrefix($opt_prefix)
|
62 |
{
|
63 |
if (!empty($opt_prefix)) {
|
@@ -69,11 +102,15 @@ class WSAL_Adapters_MySQL_Option extends WSAL_Adapters_MySQL_ActiveRecord
|
|
69 |
}
|
70 |
}
|
71 |
|
|
|
|
|
|
|
|
|
|
|
72 |
public function CountNotifications($opt_prefix)
|
73 |
{
|
74 |
$_wpdb = $this->connection;
|
75 |
$sql = "SELECT COUNT(id) FROM " . $this->GetTable() . " WHERE option_name LIKE '". $opt_prefix ."%'";
|
76 |
return (int)$_wpdb->get_var($sql);
|
77 |
}
|
78 |
-
|
79 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* MySQL database Option class.
|
5 |
+
*
|
6 |
+
* MySQL wsal_options table used for to store the plugin settings and Add-Ons settings.
|
7 |
+
*/
|
8 |
class WSAL_Adapters_MySQL_Option extends WSAL_Adapters_MySQL_ActiveRecord
|
9 |
{
|
|
|
10 |
protected $_table = 'wsal_options';
|
11 |
protected $_idkey = 'id';
|
12 |
|
20 |
parent::__construct($conn);
|
21 |
}
|
22 |
|
23 |
+
/**
|
24 |
+
* @return WSAL_Models_Option
|
25 |
+
*/
|
26 |
public function GetModel()
|
27 |
{
|
28 |
return new WSAL_Models_Option();
|
29 |
}
|
30 |
|
31 |
+
/**
|
32 |
+
* Get option by name.
|
33 |
+
* @param string $name option_name
|
34 |
+
* @return string|null option value
|
35 |
+
*/
|
36 |
public function GetNamedOption($name)
|
37 |
+
{
|
38 |
+
if ($this->IsInstalled()) {
|
39 |
return $this->Load('option_name = %s', array($name));
|
40 |
} else {
|
41 |
return null;
|
42 |
}
|
43 |
}
|
44 |
|
45 |
+
/**
|
46 |
+
* Get options by prefix (notifications stored in json format).
|
47 |
+
* @param string $opt_prefix prefix
|
48 |
+
* @return array|null options
|
49 |
+
*/
|
50 |
public function GetNotificationsSetting($opt_prefix)
|
51 |
{
|
52 |
if ($this->IsInstalled()) {
|
56 |
}
|
57 |
}
|
58 |
|
59 |
+
/**
|
60 |
+
* Get option by id (notifications stored in json format).
|
61 |
+
* @param int $id option ID
|
62 |
+
* @return string|null option
|
63 |
+
*/
|
64 |
public function GetNotification($id)
|
65 |
{
|
66 |
if ($this->IsInstalled()) {
|
70 |
}
|
71 |
}
|
72 |
|
73 |
+
/**
|
74 |
+
* Delete option by name.
|
75 |
+
* @param string $name option_name
|
76 |
+
* @return boolean.
|
77 |
+
*/
|
78 |
public function DeleteByName($name)
|
79 |
{
|
80 |
if (!empty($name)) {
|
86 |
}
|
87 |
}
|
88 |
|
89 |
+
/**
|
90 |
+
* Delete options start with prefix.
|
91 |
+
* @param string $opt_prefix prefix
|
92 |
+
* @return boolean.
|
93 |
+
*/
|
94 |
public function DeleteByPrefix($opt_prefix)
|
95 |
{
|
96 |
if (!empty($opt_prefix)) {
|
102 |
}
|
103 |
}
|
104 |
|
105 |
+
/**
|
106 |
+
* Number of options start with prefix.
|
107 |
+
* @param string $opt_prefix prefix
|
108 |
+
* @return integer Indicates the number of items.
|
109 |
+
*/
|
110 |
public function CountNotifications($opt_prefix)
|
111 |
{
|
112 |
$_wpdb = $this->connection;
|
113 |
$sql = "SELECT COUNT(id) FROM " . $this->GetTable() . " WHERE option_name LIKE '". $opt_prefix ."%'";
|
114 |
return (int)$_wpdb->get_var($sql);
|
115 |
}
|
|
|
116 |
}
|
classes/Adapters/MySQL/QueryAdapter.php
CHANGED
@@ -1,5 +1,11 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
4 |
{
|
5 |
protected $connection;
|
@@ -10,6 +16,9 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
10 |
}
|
11 |
|
12 |
/**
|
|
|
|
|
|
|
13 |
* @return string Generated sql.
|
14 |
*/
|
15 |
protected function GetSql($query, &$args = array())
|
@@ -85,13 +94,19 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
85 |
return $sql;
|
86 |
}
|
87 |
|
|
|
|
|
|
|
|
|
88 |
protected function getActiveRecordAdapter()
|
89 |
{
|
90 |
return new WSAL_Adapters_MySQL_ActiveRecord($this->connection);
|
91 |
}
|
92 |
|
93 |
/**
|
94 |
-
*
|
|
|
|
|
95 |
*/
|
96 |
public function Execute($query)
|
97 |
{
|
@@ -108,7 +123,9 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
108 |
}
|
109 |
|
110 |
/**
|
111 |
-
*
|
|
|
|
|
112 |
*/
|
113 |
public function Count($query)
|
114 |
{
|
@@ -126,6 +143,11 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
126 |
return $this->getActiveRecordAdapter()->CountQuery($sql, $args);
|
127 |
}
|
128 |
|
|
|
|
|
|
|
|
|
|
|
129 |
public function CountDelete($query)
|
130 |
{
|
131 |
$result = $this->GetSqlDelete($query, true);
|
@@ -134,7 +156,8 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
134 |
}
|
135 |
|
136 |
/**
|
137 |
-
*
|
|
|
138 |
*/
|
139 |
public function Delete($query)
|
140 |
{
|
@@ -143,6 +166,11 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
143 |
return $this->getActiveRecordAdapter()->DeleteQuery($result['sql'], $result['args']);
|
144 |
}
|
145 |
|
|
|
|
|
|
|
|
|
|
|
146 |
public function DeleteMetas($query, $args)
|
147 |
{
|
148 |
// back up columns, use COUNT as default column and generate sql
|
@@ -163,6 +191,12 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
163 |
$meta->DeleteByOccurenceIds($occ_ids);
|
164 |
}
|
165 |
|
|
|
|
|
|
|
|
|
|
|
|
|
166 |
public function GetSqlDelete($query, $getCount = false)
|
167 |
{
|
168 |
$result = array();
|
@@ -201,16 +235,22 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
201 |
. (!empty($orderBys) ? (' ORDER BY ' . implode(', ', array_keys($orderBys)) . ' ' . implode(', ', array_values($orderBys))) : '')
|
202 |
. $sLimitClause;
|
203 |
$result['args'] = $args;
|
204 |
-
//restore columns
|
205 |
$query->setColumns($cols);
|
206 |
|
207 |
return $result;
|
208 |
}
|
209 |
|
|
|
|
|
|
|
|
|
210 |
public function SearchCondition($query)
|
211 |
{
|
212 |
$condition = $query->getSearchCondition();
|
213 |
-
if (empty($condition))
|
|
|
|
|
214 |
$searchConditions = array();
|
215 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
216 |
$occurrence = new WSAL_Adapters_MySQL_Occurrence($this->connection);
|
@@ -226,5 +266,4 @@ class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
|
226 |
$searchConditions['args'] = "%". $condition. "%";
|
227 |
return $searchConditions;
|
228 |
}
|
229 |
-
|
230 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* MySQL database Query class.
|
5 |
+
*
|
6 |
+
* The SQL query is created in this class, here the SQL is filled with
|
7 |
+
* the arguments.
|
8 |
+
*/
|
9 |
class WSAL_Adapters_MySQL_Query implements WSAL_Adapters_QueryInterface
|
10 |
{
|
11 |
protected $connection;
|
16 |
}
|
17 |
|
18 |
/**
|
19 |
+
* Get the SQL filled with the args.
|
20 |
+
* @param object $query query object
|
21 |
+
* @param array $args args of the query
|
22 |
* @return string Generated sql.
|
23 |
*/
|
24 |
protected function GetSql($query, &$args = array())
|
94 |
return $sql;
|
95 |
}
|
96 |
|
97 |
+
/**
|
98 |
+
* Get an instance of the ActiveRecord Adapter.
|
99 |
+
* @return WSAL_Adapters_MySQL_ActiveRecord
|
100 |
+
*/
|
101 |
protected function getActiveRecordAdapter()
|
102 |
{
|
103 |
return new WSAL_Adapters_MySQL_ActiveRecord($this->connection);
|
104 |
}
|
105 |
|
106 |
/**
|
107 |
+
* Execute query and return data as $ar_cls objects.
|
108 |
+
* @param object $query query object
|
109 |
+
* @return WSAL_Models_ActiveRecord[]
|
110 |
*/
|
111 |
public function Execute($query)
|
112 |
{
|
123 |
}
|
124 |
|
125 |
/**
|
126 |
+
* Count query
|
127 |
+
* @param object $query query object
|
128 |
+
* @return integer counting records.
|
129 |
*/
|
130 |
public function Count($query)
|
131 |
{
|
143 |
return $this->getActiveRecordAdapter()->CountQuery($sql, $args);
|
144 |
}
|
145 |
|
146 |
+
/**
|
147 |
+
* Count DELETE query
|
148 |
+
* @param object $query query object
|
149 |
+
* @return integer counting records.
|
150 |
+
*/
|
151 |
public function CountDelete($query)
|
152 |
{
|
153 |
$result = $this->GetSqlDelete($query, true);
|
156 |
}
|
157 |
|
158 |
/**
|
159 |
+
* Query for deleting records
|
160 |
+
* @param object $query query object.
|
161 |
*/
|
162 |
public function Delete($query)
|
163 |
{
|
166 |
return $this->getActiveRecordAdapter()->DeleteQuery($result['sql'], $result['args']);
|
167 |
}
|
168 |
|
169 |
+
/**
|
170 |
+
* Load occurrence IDs then delete Metadata by occurrence_id
|
171 |
+
* @param object $query query object
|
172 |
+
* @param array $args args of the query
|
173 |
+
*/
|
174 |
public function DeleteMetas($query, $args)
|
175 |
{
|
176 |
// back up columns, use COUNT as default column and generate sql
|
191 |
$meta->DeleteByOccurenceIds($occ_ids);
|
192 |
}
|
193 |
|
194 |
+
/**
|
195 |
+
* Get the DELETE query SQL filled with the args.
|
196 |
+
* @param object $query query object
|
197 |
+
* @param array $args args of the query
|
198 |
+
* @return string Generated sql.
|
199 |
+
*/
|
200 |
public function GetSqlDelete($query, $getCount = false)
|
201 |
{
|
202 |
$result = array();
|
235 |
. (!empty($orderBys) ? (' ORDER BY ' . implode(', ', array_keys($orderBys)) . ' ' . implode(', ', array_values($orderBys))) : '')
|
236 |
. $sLimitClause;
|
237 |
$result['args'] = $args;
|
238 |
+
// restore columns
|
239 |
$query->setColumns($cols);
|
240 |
|
241 |
return $result;
|
242 |
}
|
243 |
|
244 |
+
/**
|
245 |
+
* Search by alert code OR by Metadata value.
|
246 |
+
* @param object $query query object
|
247 |
+
*/
|
248 |
public function SearchCondition($query)
|
249 |
{
|
250 |
$condition = $query->getSearchCondition();
|
251 |
+
if (empty($condition)) {
|
252 |
+
return null;
|
253 |
+
}
|
254 |
$searchConditions = array();
|
255 |
$meta = new WSAL_Adapters_MySQL_Meta($this->connection);
|
256 |
$occurrence = new WSAL_Adapters_MySQL_Occurrence($this->connection);
|
266 |
$searchConditions['args'] = "%". $condition. "%";
|
267 |
return $searchConditions;
|
268 |
}
|
|
|
269 |
}
|
classes/Adapters/MySQL/TmpUserAdapter.php
CHANGED
@@ -1,12 +1,23 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Adapters_MySQL_TmpUser extends WSAL_Adapters_MySQL_ActiveRecord {
|
4 |
|
5 |
protected $_table = 'wsal_tmp_users';
|
6 |
|
|
|
|
|
|
|
7 |
public function GetModel()
|
8 |
{
|
9 |
-
return new
|
10 |
}
|
11 |
|
12 |
public function __construct($conn)
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* MySQL database TmpUser class.
|
5 |
+
*
|
6 |
+
* This class is used for create a temporary table to store the WP users
|
7 |
+
* when the External DB Add-On is activated and the Alerts are stored on an external DB
|
8 |
+
* because the query between plugin tables and the internal wp_uses table is not possible.
|
9 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord->GetReportGrouped()
|
10 |
+
*/
|
11 |
class WSAL_Adapters_MySQL_TmpUser extends WSAL_Adapters_MySQL_ActiveRecord {
|
12 |
|
13 |
protected $_table = 'wsal_tmp_users';
|
14 |
|
15 |
+
/**
|
16 |
+
* @return WSAL_Models_TmpUser
|
17 |
+
*/
|
18 |
public function GetModel()
|
19 |
{
|
20 |
+
return new WSAL_Models_TmpUser();
|
21 |
}
|
22 |
|
23 |
public function __construct($conn)
|
classes/Adapters/OccurrenceInterface.php
CHANGED
@@ -1,5 +1,9 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
interface WSAL_Adapters_OccurrenceInterface
|
4 |
{
|
5 |
public function GetMeta($occurence);
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Interface used by the Occurrence.
|
6 |
+
*/
|
7 |
interface WSAL_Adapters_OccurrenceInterface
|
8 |
{
|
9 |
public function GetMeta($occurence);
|
classes/Adapters/QueryInterface.php
CHANGED
@@ -1,8 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
interface WSAL_Adapters_QueryInterface
|
4 |
{
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Interface used by the Query.
|
6 |
+
*/
|
7 |
interface WSAL_Adapters_QueryInterface
|
8 |
{
|
9 |
+
public function Execute($query);
|
10 |
+
public function Count($query);
|
11 |
+
public function Delete($query);
|
12 |
}
|
classes/Alert.php
CHANGED
@@ -1,7 +1,11 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
5 |
/**
|
6 |
* Alert type (used when triggering an alert etc).
|
7 |
* @var integer
|
@@ -38,7 +42,8 @@ final class WSAL_Alert {
|
|
38 |
*/
|
39 |
public $mesg = '';
|
40 |
|
41 |
-
public function __construct($type = 0, $code = 0, $catg = '', $subcatg = '', $desc = '', $mesg = '')
|
|
|
42 |
$this->type = $type;
|
43 |
$this->code = $code;
|
44 |
$this->catg = $catg;
|
@@ -53,13 +58,16 @@ final class WSAL_Alert {
|
|
53 |
* @param array $metaData (Optional) Meta data relevant to expression.
|
54 |
* @return mixed The value nearest to the expression.
|
55 |
*/
|
56 |
-
protected function GetMetaExprValue($expr, $metaData = array())
|
|
|
57 |
// TODO Handle function calls (and methods?)
|
58 |
$expr = explode('->', $expr);
|
59 |
$meta = array_shift($expr);
|
60 |
$meta = isset($metaData[$meta]) ? $metaData[$meta] : null;
|
61 |
-
foreach($expr as $part){
|
62 |
-
if(is_scalar($meta) || is_null($meta))
|
|
|
|
|
63 |
$meta = is_array($meta) ? $meta[$part] : $meta->$part;
|
64 |
}
|
65 |
return is_scalar($meta) ? (string)$meta : var_export($meta, true);
|
@@ -73,20 +81,24 @@ final class WSAL_Alert {
|
|
73 |
* @param string $afterMeta (Optional) Some text to put after meta values.
|
74 |
* @return string The expanded message.
|
75 |
*/
|
76 |
-
protected function GetFormattedMesg($origMesg, $metaData = array(), $metaFormatter = null)
|
|
|
77 |
// tokenize message with regex
|
78 |
$mesg = preg_split('/(%.*?%)/', (string)$origMesg, -1, PREG_SPLIT_DELIM_CAPTURE);
|
79 |
-
if(!is_array($mesg))
|
|
|
|
|
80 |
// handle tokenized message
|
81 |
-
foreach($mesg as $i => $token){
|
82 |
// handle escaped percent sign
|
83 |
-
if($token == '%%'){
|
84 |
$mesg[$i] = '%';
|
85 |
-
}else
|
86 |
-
|
87 |
-
if(substr($token, 0, 1) == '%' && substr($token, -1, 1) == '%'){
|
88 |
$mesg[$i] = $this->GetMetaExprValue(substr($token, 1, -1), $metaData);
|
89 |
-
if($metaFormatter)
|
|
|
|
|
90 |
}
|
91 |
}
|
92 |
// compact message and return
|
@@ -94,12 +106,14 @@ final class WSAL_Alert {
|
|
94 |
}
|
95 |
|
96 |
/**
|
|
|
97 |
* @param array $metaData (Optional) Meta data relevant to message.
|
98 |
* @param callable|null $metaFormatter (Optional) Meta formatter callback.
|
99 |
* @param string|null $mesg (Optional) Override message template to use.
|
100 |
* @return string Fully formatted message.
|
101 |
*/
|
102 |
-
public function GetMessage($metaData = array(), $metaFormatter = null, $mesg = null)
|
|
|
103 |
return $this->GetFormattedMesg(is_null($mesg) ? $this->mesg : $mesg, $metaData, $metaFormatter);
|
104 |
}
|
105 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* WSAL_Alert Object class.
|
6 |
+
*/
|
7 |
+
final class WSAL_Alert
|
8 |
+
{
|
9 |
/**
|
10 |
* Alert type (used when triggering an alert etc).
|
11 |
* @var integer
|
42 |
*/
|
43 |
public $mesg = '';
|
44 |
|
45 |
+
public function __construct($type = 0, $code = 0, $catg = '', $subcatg = '', $desc = '', $mesg = '')
|
46 |
+
{
|
47 |
$this->type = $type;
|
48 |
$this->code = $code;
|
49 |
$this->catg = $catg;
|
58 |
* @param array $metaData (Optional) Meta data relevant to expression.
|
59 |
* @return mixed The value nearest to the expression.
|
60 |
*/
|
61 |
+
protected function GetMetaExprValue($expr, $metaData = array())
|
62 |
+
{
|
63 |
// TODO Handle function calls (and methods?)
|
64 |
$expr = explode('->', $expr);
|
65 |
$meta = array_shift($expr);
|
66 |
$meta = isset($metaData[$meta]) ? $metaData[$meta] : null;
|
67 |
+
foreach ($expr as $part) {
|
68 |
+
if (is_scalar($meta) || is_null($meta)) {
|
69 |
+
return $meta; // this isn't 100% correct
|
70 |
+
}
|
71 |
$meta = is_array($meta) ? $meta[$part] : $meta->$part;
|
72 |
}
|
73 |
return is_scalar($meta) ? (string)$meta : var_export($meta, true);
|
81 |
* @param string $afterMeta (Optional) Some text to put after meta values.
|
82 |
* @return string The expanded message.
|
83 |
*/
|
84 |
+
protected function GetFormattedMesg($origMesg, $metaData = array(), $metaFormatter = null)
|
85 |
+
{
|
86 |
// tokenize message with regex
|
87 |
$mesg = preg_split('/(%.*?%)/', (string)$origMesg, -1, PREG_SPLIT_DELIM_CAPTURE);
|
88 |
+
if (!is_array($mesg)) {
|
89 |
+
return (string)$origMesg;
|
90 |
+
}
|
91 |
// handle tokenized message
|
92 |
+
foreach ($mesg as $i => $token) {
|
93 |
// handle escaped percent sign
|
94 |
+
if ($token == '%%') {
|
95 |
$mesg[$i] = '%';
|
96 |
+
} else if (substr($token, 0, 1) == '%' && substr($token, -1, 1) == '%') {
|
97 |
+
// handle complex expressions
|
|
|
98 |
$mesg[$i] = $this->GetMetaExprValue(substr($token, 1, -1), $metaData);
|
99 |
+
if ($metaFormatter) {
|
100 |
+
$mesg[$i] = call_user_func($metaFormatter, $token, $mesg[$i]);
|
101 |
+
}
|
102 |
}
|
103 |
}
|
104 |
// compact message and return
|
106 |
}
|
107 |
|
108 |
/**
|
109 |
+
* Gets alert message.
|
110 |
* @param array $metaData (Optional) Meta data relevant to message.
|
111 |
* @param callable|null $metaFormatter (Optional) Meta formatter callback.
|
112 |
* @param string|null $mesg (Optional) Override message template to use.
|
113 |
* @return string Fully formatted message.
|
114 |
*/
|
115 |
+
public function GetMessage($metaData = array(), $metaFormatter = null, $mesg = null)
|
116 |
+
{
|
117 |
return $this->GetFormattedMesg(is_null($mesg) ? $this->mesg : $mesg, $metaData, $metaFormatter);
|
118 |
}
|
119 |
}
|
classes/AlertManager.php
CHANGED
@@ -1,32 +1,50 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
/**
|
6 |
* @var WSAL_Alert[]
|
7 |
*/
|
8 |
protected $_alerts = array();
|
9 |
-
|
10 |
/**
|
11 |
* @var WSAL_AbstractLogger[]
|
12 |
*/
|
13 |
protected $_loggers = array();
|
14 |
-
|
15 |
/**
|
16 |
* @var WpSecurityAuditLog
|
17 |
*/
|
18 |
protected $plugin;
|
19 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
20 |
/**
|
21 |
* Create new AlertManager instance.
|
22 |
* @param WpSecurityAuditLog $plugin
|
23 |
*/
|
24 |
-
public function __construct(WpSecurityAuditLog $plugin)
|
|
|
25 |
$this->plugin = $plugin;
|
26 |
foreach (glob(dirname(__FILE__) . '/Loggers/*.php') as $file) {
|
27 |
$this->AddFromFile($file);
|
28 |
}
|
29 |
-
|
30 |
add_action('shutdown', array($this, '_CommitPipeline'));
|
31 |
}
|
32 |
|
@@ -34,26 +52,29 @@ final class WSAL_AlertManager {
|
|
34 |
* Add new logger from file inside autoloader path.
|
35 |
* @param string $file Path to file.
|
36 |
*/
|
37 |
-
public function AddFromFile($file)
|
|
|
38 |
$this->AddFromClass($this->plugin->GetClassFileClassName($file));
|
39 |
}
|
40 |
-
|
41 |
/**
|
42 |
* Add new logger given class name.
|
43 |
* @param string $class Class name.
|
44 |
*/
|
45 |
-
public function AddFromClass($class)
|
|
|
46 |
$this->AddInstance(new $class($this->plugin));
|
47 |
}
|
48 |
-
|
49 |
/**
|
50 |
* Add newly created logger to list.
|
51 |
* @param WSAL_AbstractLogger $logger The new logger.
|
52 |
*/
|
53 |
-
public function AddInstance(WSAL_AbstractLogger $logger)
|
|
|
54 |
$this->_loggers[] = $logger;
|
55 |
}
|
56 |
-
|
57 |
/**
|
58 |
* Remove logger by class name.
|
59 |
* @param string $class The class name.
|
@@ -66,25 +87,14 @@ final class WSAL_AlertManager {
|
|
66 |
}
|
67 |
}
|
68 |
}
|
69 |
-
|
70 |
-
/**
|
71 |
-
* Contains a list of alerts to trigger.
|
72 |
-
* @var array
|
73 |
-
*/
|
74 |
-
protected $_pipeline = array();
|
75 |
-
|
76 |
-
/**
|
77 |
-
* Contains an array of alerts that have been triggered for this request.
|
78 |
-
* @var int[]
|
79 |
-
*/
|
80 |
-
protected $_triggered_types = array();
|
81 |
-
|
82 |
/**
|
83 |
* Trigger an alert.
|
84 |
* @param integer $type Alert type.
|
85 |
* @param array $data Alert data.
|
86 |
*/
|
87 |
-
public function Trigger($type, $data = array(), $delayed = false)
|
|
|
88 |
$username = wp_get_current_user()->user_login;
|
89 |
if (empty($username) && !empty($data["Username"])) {
|
90 |
$username = $data['Username'];
|
@@ -111,7 +121,8 @@ final class WSAL_AlertManager {
|
|
111 |
* @param array roles
|
112 |
* @return boolean True if enable false otherwise.
|
113 |
*/
|
114 |
-
public function CheckEnableUserRoles($user, $roles)
|
|
|
115 |
$is_enable = true;
|
116 |
if ($user != "" && $this->IsDisabledUser($user)) {
|
117 |
$is_enable = false;
|
@@ -121,17 +132,18 @@ final class WSAL_AlertManager {
|
|
121 |
}
|
122 |
return $is_enable;
|
123 |
}
|
124 |
-
|
125 |
/**
|
126 |
* Trigger only if a condition is met at the end of request.
|
127 |
* @param integer $type Alert type ID.
|
128 |
* @param array $data Alert data.
|
129 |
* @param callable $cond A future condition callback (receives an object of type WSAL_AlertManager as parameter).
|
130 |
*/
|
131 |
-
public function TriggerIf($type, $data, $cond = null)
|
|
|
132 |
$username = wp_get_current_user()->user_login;
|
133 |
$roles = $this->plugin->settings->GetCurrentUserRoles();
|
134 |
-
|
135 |
if ($this->CheckEnableUserRoles($username, $roles)) {
|
136 |
$this->_pipeline[] = array(
|
137 |
'type' => $type,
|
@@ -140,7 +152,7 @@ final class WSAL_AlertManager {
|
|
140 |
);
|
141 |
}
|
142 |
}
|
143 |
-
|
144 |
/**
|
145 |
* @internal Commit an alert now.
|
146 |
*/
|
@@ -163,16 +175,17 @@ final class WSAL_AlertManager {
|
|
163 |
}
|
164 |
}
|
165 |
}
|
166 |
-
|
167 |
/**
|
168 |
* @internal Runs over triggered alerts in pipeline and passes them to loggers.
|
169 |
*/
|
170 |
-
public function _CommitPipeline()
|
|
|
171 |
foreach ($this->_pipeline as $item) {
|
172 |
$this->_CommitItem($item['type'], $item['data'], $item['cond']);
|
173 |
}
|
174 |
}
|
175 |
-
|
176 |
/**
|
177 |
* @param integer $type Alert type ID.
|
178 |
* @return boolean True if at the end of request an alert of this type will be triggered.
|
@@ -186,16 +199,17 @@ final class WSAL_AlertManager {
|
|
186 |
}
|
187 |
return false;
|
188 |
}
|
189 |
-
|
190 |
/**
|
191 |
* @param int $type Alert type ID.
|
192 |
* @return boolean True if an alert has been or will be triggered in this request, false otherwise.
|
193 |
*/
|
194 |
-
public function WillOrHasTriggered($type)
|
|
|
195 |
return in_array($type, $this->_triggered_types)
|
196 |
|| $this->WillTrigger($type);
|
197 |
}
|
198 |
-
|
199 |
/**
|
200 |
* Register an alert type.
|
201 |
* @param array $info Array of [type, code, category, description, message] respectively.
|
@@ -216,7 +230,7 @@ final class WSAL_AlertManager {
|
|
216 |
}
|
217 |
}
|
218 |
}
|
219 |
-
|
220 |
/**
|
221 |
* Register a whole group of items.
|
222 |
* @param array $groups An array with group name as the index and an array of group items as the value.
|
@@ -233,38 +247,42 @@ final class WSAL_AlertManager {
|
|
233 |
}
|
234 |
}
|
235 |
}
|
236 |
-
|
237 |
/**
|
238 |
* Returns whether alert of type $type is enabled or not.
|
239 |
* @param integer $type Alert type.
|
240 |
* @return boolean True if enabled, false otherwise.
|
241 |
*/
|
242 |
-
public function IsEnabled($type)
|
|
|
243 |
return !in_array($type, $this->GetDisabledAlerts());
|
244 |
}
|
245 |
-
|
246 |
/**
|
247 |
* Disables a set of alerts by type.
|
248 |
* @param int[] $types Alert type codes to be disabled.
|
249 |
*/
|
250 |
-
public function SetDisabledAlerts($types)
|
|
|
251 |
$this->plugin->settings->SetDisabledAlerts($types);
|
252 |
}
|
253 |
-
|
254 |
/**
|
255 |
* @return int[] Returns an array of disabled alerts' type code.
|
256 |
*/
|
257 |
-
public function GetDisabledAlerts()
|
|
|
258 |
return $this->plugin->settings->GetDisabledAlerts();
|
259 |
}
|
260 |
-
|
261 |
/**
|
262 |
* @return WSAL_AbstractLogger[] Returns an array of loaded loggers.
|
263 |
*/
|
264 |
-
public function GetLoggers()
|
|
|
265 |
return $this->_loggers;
|
266 |
}
|
267 |
-
|
268 |
/**
|
269 |
* Converts an Alert into a Log entry (by invoking loggers).
|
270 |
* You should not call this method directly.
|
@@ -302,24 +320,24 @@ final class WSAL_AlertManager {
|
|
302 |
}
|
303 |
}
|
304 |
// Check if the user management plugin is loaded and adds the SessionID
|
305 |
-
if (class_exists('WSAL_User_Management_Plugin')) {
|
306 |
-
if (function_exists('get_current_user_id')) {
|
307 |
-
$session_tokens = get_user_meta(get_current_user_id(), 'session_tokens', true);
|
308 |
-
if (!empty($session_tokens)) {
|
309 |
-
end($session_tokens);
|
310 |
-
$data['SessionID'] = key($session_tokens);
|
311 |
}
|
312 |
}
|
313 |
}
|
314 |
//if(isset($_SERVER['REMOTE_HOST']) && $_SERVER['REMOTE_HOST'] != $data['ClientIP'])
|
315 |
// $data['ClientHost'] = $_SERVER['REMOTE_HOST'];
|
316 |
//$data['OtherIPs'] = $_SERVER['REMOTE_HOST'];
|
317 |
-
|
318 |
foreach ($this->_loggers as $logger) {
|
319 |
$logger->Log($type, $data);
|
320 |
}
|
321 |
}
|
322 |
-
|
323 |
/**
|
324 |
* Return alert given alert type.
|
325 |
* @param integer $type Alert type.
|
@@ -335,15 +353,16 @@ final class WSAL_AlertManager {
|
|
335 |
}
|
336 |
return $default;
|
337 |
}
|
338 |
-
|
339 |
/**
|
340 |
* Returns all supported alerts.
|
341 |
* @return WSAL_Alert[]
|
342 |
*/
|
343 |
-
public function GetAlerts()
|
|
|
344 |
return $this->_alerts;
|
345 |
}
|
346 |
-
|
347 |
/**
|
348 |
* Returns all supported alerts.
|
349 |
* @return array
|
@@ -373,7 +392,7 @@ final class WSAL_AlertManager {
|
|
373 |
{
|
374 |
return (in_array($user, $this->GetDisabledUsers())) ? true : false;
|
375 |
}
|
376 |
-
|
377 |
/**
|
378 |
* @return Returns an array of disabled users.
|
379 |
*/
|
@@ -397,7 +416,7 @@ final class WSAL_AlertManager {
|
|
397 |
}
|
398 |
return $is_disabled;
|
399 |
}
|
400 |
-
|
401 |
/**
|
402 |
* @return Returns an array of disabled users.
|
403 |
*/
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* WSAL_AlertManager class.
|
6 |
+
* It is the actual trigger for the alerts.
|
7 |
+
*/
|
8 |
+
final class WSAL_AlertManager
|
9 |
+
{
|
10 |
/**
|
11 |
* @var WSAL_Alert[]
|
12 |
*/
|
13 |
protected $_alerts = array();
|
14 |
+
|
15 |
/**
|
16 |
* @var WSAL_AbstractLogger[]
|
17 |
*/
|
18 |
protected $_loggers = array();
|
19 |
+
|
20 |
/**
|
21 |
* @var WpSecurityAuditLog
|
22 |
*/
|
23 |
protected $plugin;
|
24 |
|
25 |
+
/**
|
26 |
+
* Contains a list of alerts to trigger.
|
27 |
+
* @var array
|
28 |
+
*/
|
29 |
+
protected $_pipeline = array();
|
30 |
+
|
31 |
+
/**
|
32 |
+
* Contains an array of alerts that have been triggered for this request.
|
33 |
+
* @var int[]
|
34 |
+
*/
|
35 |
+
protected $_triggered_types = array();
|
36 |
+
|
37 |
/**
|
38 |
* Create new AlertManager instance.
|
39 |
* @param WpSecurityAuditLog $plugin
|
40 |
*/
|
41 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
42 |
+
{
|
43 |
$this->plugin = $plugin;
|
44 |
foreach (glob(dirname(__FILE__) . '/Loggers/*.php') as $file) {
|
45 |
$this->AddFromFile($file);
|
46 |
}
|
47 |
+
|
48 |
add_action('shutdown', array($this, '_CommitPipeline'));
|
49 |
}
|
50 |
|
52 |
* Add new logger from file inside autoloader path.
|
53 |
* @param string $file Path to file.
|
54 |
*/
|
55 |
+
public function AddFromFile($file)
|
56 |
+
{
|
57 |
$this->AddFromClass($this->plugin->GetClassFileClassName($file));
|
58 |
}
|
59 |
+
|
60 |
/**
|
61 |
* Add new logger given class name.
|
62 |
* @param string $class Class name.
|
63 |
*/
|
64 |
+
public function AddFromClass($class)
|
65 |
+
{
|
66 |
$this->AddInstance(new $class($this->plugin));
|
67 |
}
|
68 |
+
|
69 |
/**
|
70 |
* Add newly created logger to list.
|
71 |
* @param WSAL_AbstractLogger $logger The new logger.
|
72 |
*/
|
73 |
+
public function AddInstance(WSAL_AbstractLogger $logger)
|
74 |
+
{
|
75 |
$this->_loggers[] = $logger;
|
76 |
}
|
77 |
+
|
78 |
/**
|
79 |
* Remove logger by class name.
|
80 |
* @param string $class The class name.
|
87 |
}
|
88 |
}
|
89 |
}
|
90 |
+
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
91 |
/**
|
92 |
* Trigger an alert.
|
93 |
* @param integer $type Alert type.
|
94 |
* @param array $data Alert data.
|
95 |
*/
|
96 |
+
public function Trigger($type, $data = array(), $delayed = false)
|
97 |
+
{
|
98 |
$username = wp_get_current_user()->user_login;
|
99 |
if (empty($username) && !empty($data["Username"])) {
|
100 |
$username = $data['Username'];
|
121 |
* @param array roles
|
122 |
* @return boolean True if enable false otherwise.
|
123 |
*/
|
124 |
+
public function CheckEnableUserRoles($user, $roles)
|
125 |
+
{
|
126 |
$is_enable = true;
|
127 |
if ($user != "" && $this->IsDisabledUser($user)) {
|
128 |
$is_enable = false;
|
132 |
}
|
133 |
return $is_enable;
|
134 |
}
|
135 |
+
|
136 |
/**
|
137 |
* Trigger only if a condition is met at the end of request.
|
138 |
* @param integer $type Alert type ID.
|
139 |
* @param array $data Alert data.
|
140 |
* @param callable $cond A future condition callback (receives an object of type WSAL_AlertManager as parameter).
|
141 |
*/
|
142 |
+
public function TriggerIf($type, $data, $cond = null)
|
143 |
+
{
|
144 |
$username = wp_get_current_user()->user_login;
|
145 |
$roles = $this->plugin->settings->GetCurrentUserRoles();
|
146 |
+
|
147 |
if ($this->CheckEnableUserRoles($username, $roles)) {
|
148 |
$this->_pipeline[] = array(
|
149 |
'type' => $type,
|
152 |
);
|
153 |
}
|
154 |
}
|
155 |
+
|
156 |
/**
|
157 |
* @internal Commit an alert now.
|
158 |
*/
|
175 |
}
|
176 |
}
|
177 |
}
|
178 |
+
|
179 |
/**
|
180 |
* @internal Runs over triggered alerts in pipeline and passes them to loggers.
|
181 |
*/
|
182 |
+
public function _CommitPipeline()
|
183 |
+
{
|
184 |
foreach ($this->_pipeline as $item) {
|
185 |
$this->_CommitItem($item['type'], $item['data'], $item['cond']);
|
186 |
}
|
187 |
}
|
188 |
+
|
189 |
/**
|
190 |
* @param integer $type Alert type ID.
|
191 |
* @return boolean True if at the end of request an alert of this type will be triggered.
|
199 |
}
|
200 |
return false;
|
201 |
}
|
202 |
+
|
203 |
/**
|
204 |
* @param int $type Alert type ID.
|
205 |
* @return boolean True if an alert has been or will be triggered in this request, false otherwise.
|
206 |
*/
|
207 |
+
public function WillOrHasTriggered($type)
|
208 |
+
{
|
209 |
return in_array($type, $this->_triggered_types)
|
210 |
|| $this->WillTrigger($type);
|
211 |
}
|
212 |
+
|
213 |
/**
|
214 |
* Register an alert type.
|
215 |
* @param array $info Array of [type, code, category, description, message] respectively.
|
230 |
}
|
231 |
}
|
232 |
}
|
233 |
+
|
234 |
/**
|
235 |
* Register a whole group of items.
|
236 |
* @param array $groups An array with group name as the index and an array of group items as the value.
|
247 |
}
|
248 |
}
|
249 |
}
|
250 |
+
|
251 |
/**
|
252 |
* Returns whether alert of type $type is enabled or not.
|
253 |
* @param integer $type Alert type.
|
254 |
* @return boolean True if enabled, false otherwise.
|
255 |
*/
|
256 |
+
public function IsEnabled($type)
|
257 |
+
{
|
258 |
return !in_array($type, $this->GetDisabledAlerts());
|
259 |
}
|
260 |
+
|
261 |
/**
|
262 |
* Disables a set of alerts by type.
|
263 |
* @param int[] $types Alert type codes to be disabled.
|
264 |
*/
|
265 |
+
public function SetDisabledAlerts($types)
|
266 |
+
{
|
267 |
$this->plugin->settings->SetDisabledAlerts($types);
|
268 |
}
|
269 |
+
|
270 |
/**
|
271 |
* @return int[] Returns an array of disabled alerts' type code.
|
272 |
*/
|
273 |
+
public function GetDisabledAlerts()
|
274 |
+
{
|
275 |
return $this->plugin->settings->GetDisabledAlerts();
|
276 |
}
|
277 |
+
|
278 |
/**
|
279 |
* @return WSAL_AbstractLogger[] Returns an array of loaded loggers.
|
280 |
*/
|
281 |
+
public function GetLoggers()
|
282 |
+
{
|
283 |
return $this->_loggers;
|
284 |
}
|
285 |
+
|
286 |
/**
|
287 |
* Converts an Alert into a Log entry (by invoking loggers).
|
288 |
* You should not call this method directly.
|
320 |
}
|
321 |
}
|
322 |
// Check if the user management plugin is loaded and adds the SessionID
|
323 |
+
if ( class_exists( 'WSAL_User_Management_Plugin' ) ) {
|
324 |
+
if ( function_exists( 'get_current_user_id' ) ) {
|
325 |
+
$session_tokens = get_user_meta( get_current_user_id(), 'session_tokens', true );
|
326 |
+
if ( ! empty( $session_tokens ) ) {
|
327 |
+
end( $session_tokens );
|
328 |
+
$data['SessionID'] = key( $session_tokens );
|
329 |
}
|
330 |
}
|
331 |
}
|
332 |
//if(isset($_SERVER['REMOTE_HOST']) && $_SERVER['REMOTE_HOST'] != $data['ClientIP'])
|
333 |
// $data['ClientHost'] = $_SERVER['REMOTE_HOST'];
|
334 |
//$data['OtherIPs'] = $_SERVER['REMOTE_HOST'];
|
335 |
+
|
336 |
foreach ($this->_loggers as $logger) {
|
337 |
$logger->Log($type, $data);
|
338 |
}
|
339 |
}
|
340 |
+
|
341 |
/**
|
342 |
* Return alert given alert type.
|
343 |
* @param integer $type Alert type.
|
353 |
}
|
354 |
return $default;
|
355 |
}
|
356 |
+
|
357 |
/**
|
358 |
* Returns all supported alerts.
|
359 |
* @return WSAL_Alert[]
|
360 |
*/
|
361 |
+
public function GetAlerts()
|
362 |
+
{
|
363 |
return $this->_alerts;
|
364 |
}
|
365 |
+
|
366 |
/**
|
367 |
* Returns all supported alerts.
|
368 |
* @return array
|
392 |
{
|
393 |
return (in_array($user, $this->GetDisabledUsers())) ? true : false;
|
394 |
}
|
395 |
+
|
396 |
/**
|
397 |
* @return Returns an array of disabled users.
|
398 |
*/
|
416 |
}
|
417 |
return $is_disabled;
|
418 |
}
|
419 |
+
|
420 |
/**
|
421 |
* @return Returns an array of disabled users.
|
422 |
*/
|
classes/AuditLogListView.php
CHANGED
@@ -2,10 +2,14 @@
|
|
2 |
|
3 |
require_once(ABSPATH . 'wp-admin/includes/admin.php');
|
4 |
require_once(ABSPATH . 'wp-admin/includes/class-wp-list-table.php');
|
5 |
-
|
|
|
|
|
|
|
|
|
|
|
6 |
class WSAL_AuditLogListView extends WP_List_Table
|
7 |
{
|
8 |
-
|
9 |
/**
|
10 |
* @var WpSecurityAuditLog
|
11 |
*/
|
@@ -84,8 +88,8 @@ class WSAL_AuditLogListView extends WP_List_Table
|
|
84 |
// switch to live or archive DB
|
85 |
if ($this->_plugin->settings->IsArchivingEnabled()) {
|
86 |
$selected = 'live';
|
87 |
-
$
|
88 |
-
if (
|
89 |
$selected = 'archive';
|
90 |
}
|
91 |
?><div class="wsal-ssa wsal-db">
|
@@ -418,8 +422,8 @@ class WSAL_AuditLogListView extends WP_List_Table
|
|
418 |
{
|
419 |
if ($this->_plugin->settings->IsArchivingEnabled()) {
|
420 |
// Switch to Archive DB
|
421 |
-
$
|
422 |
-
if (
|
423 |
$this->_plugin->settings->SwitchToArchiveDB();
|
424 |
}
|
425 |
}
|
2 |
|
3 |
require_once(ABSPATH . 'wp-admin/includes/admin.php');
|
4 |
require_once(ABSPATH . 'wp-admin/includes/class-wp-list-table.php');
|
5 |
+
/**
|
6 |
+
* @package Wsal
|
7 |
+
*
|
8 |
+
* This view is included in Audit Log Viewer Page.
|
9 |
+
* @see Views/AuditLog.php
|
10 |
+
*/
|
11 |
class WSAL_AuditLogListView extends WP_List_Table
|
12 |
{
|
|
|
13 |
/**
|
14 |
* @var WpSecurityAuditLog
|
15 |
*/
|
88 |
// switch to live or archive DB
|
89 |
if ($this->_plugin->settings->IsArchivingEnabled()) {
|
90 |
$selected = 'live';
|
91 |
+
$selected_db = get_transient('wsal_wp_selected_db');
|
92 |
+
if ($selected_db && $selected_db == 'archive') {
|
93 |
$selected = 'archive';
|
94 |
}
|
95 |
?><div class="wsal-ssa wsal-db">
|
422 |
{
|
423 |
if ($this->_plugin->settings->IsArchivingEnabled()) {
|
424 |
// Switch to Archive DB
|
425 |
+
$selected_db = get_transient('wsal_wp_selected_db');
|
426 |
+
if ($selected_db && $selected_db == 'archive') {
|
427 |
$this->_plugin->settings->SwitchToArchiveDB();
|
428 |
}
|
429 |
}
|
classes/Autoloader.php
CHANGED
@@ -1,5 +1,9 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Autoloader {
|
4 |
/**
|
5 |
* @var WpSecurityAuditLog
|
@@ -8,16 +12,19 @@ class WSAL_Autoloader {
|
|
8 |
|
9 |
protected $paths = array();
|
10 |
|
11 |
-
public function __construct(WpSecurityAuditLog $plugin)
|
|
|
12 |
$this->plugin = $plugin;
|
13 |
|
14 |
// register autoloader
|
15 |
spl_autoload_register(array($this, 'LoadClass'));
|
16 |
}
|
17 |
|
18 |
-
public function Register($prefix, $path)
|
19 |
-
|
|
|
20 |
$this->paths[$prefix] = array();
|
|
|
21 |
$this->paths[$prefix][] = rtrim(str_replace('\\', '/', $path), '/') . '/';
|
22 |
}
|
23 |
|
@@ -26,12 +33,13 @@ class WSAL_Autoloader {
|
|
26 |
* @param string $class Class name.
|
27 |
* @return boolean True if class is found and loaded, false otherwise.
|
28 |
*/
|
29 |
-
public function LoadClass($class)
|
30 |
-
|
31 |
-
|
32 |
-
|
|
|
33 |
$file = $path . str_replace('_', DIRECTORY_SEPARATOR, substr($class, strlen($prefix))) . '.php';
|
34 |
-
if(file_exists($file)){
|
35 |
$s = $this->plugin->profiler->Start('Autoload ' . basename($file));
|
36 |
require_once($file);
|
37 |
$s->Stop();
|
@@ -40,7 +48,6 @@ class WSAL_Autoloader {
|
|
40 |
}
|
41 |
}
|
42 |
}
|
43 |
-
|
44 |
return false;
|
45 |
}
|
46 |
|
@@ -49,12 +56,13 @@ class WSAL_Autoloader {
|
|
49 |
* @param string $file File name.
|
50 |
* @return string|false Class name or false on error.
|
51 |
*/
|
52 |
-
public function GetClassFileClassName($file)
|
|
|
53 |
$file = str_replace('\\', '/', $file); // win/dos hotfix
|
54 |
|
55 |
-
foreach($this->paths as $prefix => $paths){
|
56 |
-
foreach($paths as $path){
|
57 |
-
if(strstr($file, $path) !== false){
|
58 |
return str_replace(
|
59 |
array($path, '/'),
|
60 |
array($prefix, '_'),
|
@@ -63,7 +71,6 @@ class WSAL_Autoloader {
|
|
63 |
}
|
64 |
}
|
65 |
}
|
66 |
-
|
67 |
return false;
|
68 |
}
|
69 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Classes Auto Loader.
|
6 |
+
*/
|
7 |
class WSAL_Autoloader {
|
8 |
/**
|
9 |
* @var WpSecurityAuditLog
|
12 |
|
13 |
protected $paths = array();
|
14 |
|
15 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
16 |
+
{
|
17 |
$this->plugin = $plugin;
|
18 |
|
19 |
// register autoloader
|
20 |
spl_autoload_register(array($this, 'LoadClass'));
|
21 |
}
|
22 |
|
23 |
+
public function Register($prefix, $path)
|
24 |
+
{
|
25 |
+
if (!isset($this->paths[$prefix])) {
|
26 |
$this->paths[$prefix] = array();
|
27 |
+
}
|
28 |
$this->paths[$prefix][] = rtrim(str_replace('\\', '/', $path), '/') . '/';
|
29 |
}
|
30 |
|
33 |
* @param string $class Class name.
|
34 |
* @return boolean True if class is found and loaded, false otherwise.
|
35 |
*/
|
36 |
+
public function LoadClass($class)
|
37 |
+
{
|
38 |
+
foreach ($this->paths as $prefix => $paths) {
|
39 |
+
foreach ($paths as $path) {
|
40 |
+
if (strstr($class, $prefix) !== false) {
|
41 |
$file = $path . str_replace('_', DIRECTORY_SEPARATOR, substr($class, strlen($prefix))) . '.php';
|
42 |
+
if (file_exists($file)) {
|
43 |
$s = $this->plugin->profiler->Start('Autoload ' . basename($file));
|
44 |
require_once($file);
|
45 |
$s->Stop();
|
48 |
}
|
49 |
}
|
50 |
}
|
|
|
51 |
return false;
|
52 |
}
|
53 |
|
56 |
* @param string $file File name.
|
57 |
* @return string|false Class name or false on error.
|
58 |
*/
|
59 |
+
public function GetClassFileClassName($file)
|
60 |
+
{
|
61 |
$file = str_replace('\\', '/', $file); // win/dos hotfix
|
62 |
|
63 |
+
foreach ($this->paths as $prefix => $paths) {
|
64 |
+
foreach ($paths as $path) {
|
65 |
+
if (strstr($file, $path) !== false) {
|
66 |
return str_replace(
|
67 |
array($path, '/'),
|
68 |
array($prefix, '_'),
|
71 |
}
|
72 |
}
|
73 |
}
|
|
|
74 |
return false;
|
75 |
}
|
76 |
}
|
classes/Connector/AbstractConnector.php
CHANGED
@@ -1,7 +1,12 @@
|
|
1 |
<?php
|
2 |
//require_once('ConnectorInterface.php');
|
3 |
require_once('wp-db-custom.php');
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
abstract class WSAL_Connector_AbstractConnector
|
6 |
{
|
7 |
protected $connection = null;
|
1 |
<?php
|
2 |
//require_once('ConnectorInterface.php');
|
3 |
require_once('wp-db-custom.php');
|
4 |
+
/**
|
5 |
+
* @package Wsal
|
6 |
+
* Adapter Classes loader class.
|
7 |
+
*
|
8 |
+
* Abstract class used as a class loader.
|
9 |
+
*/
|
10 |
abstract class WSAL_Connector_AbstractConnector
|
11 |
{
|
12 |
protected $connection = null;
|
classes/Connector/ConnectorFactory.php
CHANGED
@@ -1,7 +1,11 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
5 |
abstract class WSAL_Connector_ConnectorFactory
|
6 |
{
|
7 |
public static $connector;
|
@@ -41,6 +45,10 @@ abstract class WSAL_Connector_ConnectorFactory
|
|
41 |
return self::$connector;
|
42 |
}
|
43 |
|
|
|
|
|
|
|
|
|
44 |
public static function GetConfig()
|
45 |
{
|
46 |
$conf = new WSAL_Settings(WpSecurityAuditLog::GetInstance());
|
@@ -59,6 +67,16 @@ abstract class WSAL_Connector_ConnectorFactory
|
|
59 |
}
|
60 |
}
|
61 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
62 |
public static function CheckConfig($type, $user, $password, $name, $hostname, $base_prefix)
|
63 |
{
|
64 |
$result = false;
|
@@ -73,6 +91,16 @@ abstract class WSAL_Connector_ConnectorFactory
|
|
73 |
return $result;
|
74 |
}
|
75 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
76 |
public static function GetConfigArray($type, $user, $password, $name, $hostname, $base_prefix)
|
77 |
{
|
78 |
return array(
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* Class WSAL_Connector_ConnectorFactory.
|
5 |
+
*
|
6 |
+
* Abstract class used for create the connector, only MySQL is implemented.
|
7 |
+
* @todo add other adapters.
|
8 |
+
*/
|
9 |
abstract class WSAL_Connector_ConnectorFactory
|
10 |
{
|
11 |
public static $connector;
|
45 |
return self::$connector;
|
46 |
}
|
47 |
|
48 |
+
/**
|
49 |
+
* Get the adapter config stored in the DB
|
50 |
+
* @return array|null adapter config
|
51 |
+
*/
|
52 |
public static function GetConfig()
|
53 |
{
|
54 |
$conf = new WSAL_Settings(WpSecurityAuditLog::GetInstance());
|
67 |
}
|
68 |
}
|
69 |
|
70 |
+
/**
|
71 |
+
* Check the adapter config with a test connection.
|
72 |
+
* @param string $type adapter type
|
73 |
+
* @param string $user adapter user
|
74 |
+
* @param string $password adapter password
|
75 |
+
* @param string $name adapter name
|
76 |
+
* @param string $hostname adapter hostname
|
77 |
+
* @param string $base_prefix adapter base_prefix
|
78 |
+
* @return boolean true|false
|
79 |
+
*/
|
80 |
public static function CheckConfig($type, $user, $password, $name, $hostname, $base_prefix)
|
81 |
{
|
82 |
$result = false;
|
91 |
return $result;
|
92 |
}
|
93 |
|
94 |
+
/**
|
95 |
+
* Create array config.
|
96 |
+
* @param string $type adapter type
|
97 |
+
* @param string $user adapter user
|
98 |
+
* @param string $password adapter password
|
99 |
+
* @param string $name adapter name
|
100 |
+
* @param string $hostname adapter hostname
|
101 |
+
* @param string $base_prefix adapter base_prefix
|
102 |
+
* @return array config
|
103 |
+
*/
|
104 |
public static function GetConfigArray($type, $user, $password, $name, $hostname, $base_prefix)
|
105 |
{
|
106 |
return array(
|
classes/Connector/ConnectorInterface.php
CHANGED
@@ -1,5 +1,9 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
interface WSAL_Connector_ConnectorInterface
|
4 |
{
|
5 |
public function getAdapter($class_name);
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Interface used by the WSAL_Connector.
|
6 |
+
*/
|
7 |
interface WSAL_Connector_ConnectorInterface
|
8 |
{
|
9 |
public function getAdapter($class_name);
|
classes/Connector/MySQLDB.php
CHANGED
@@ -1,9 +1,19 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements WSAL_Connector_ConnectorInterface
|
4 |
{
|
5 |
protected $connectionConfig = null;
|
6 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
7 |
public function __construct($connectionConfig = null)
|
8 |
{
|
9 |
$this->connectionConfig = $connectionConfig;
|
@@ -11,6 +21,10 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
11 |
require_once($this->getAdaptersDirectory() . '/OptionAdapter.php');
|
12 |
}
|
13 |
|
|
|
|
|
|
|
|
|
14 |
public function TestConnection()
|
15 |
{
|
16 |
error_reporting(E_ALL ^ (E_NOTICE | E_WARNING | E_DEPRECATED));
|
@@ -43,6 +57,7 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
43 |
|
44 |
/**
|
45 |
* Returns a wpdb instance
|
|
|
46 |
*/
|
47 |
public function getConnection()
|
48 |
{
|
@@ -65,7 +80,8 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
65 |
}
|
66 |
|
67 |
/**
|
68 |
-
* Gets an adapter for the specified model
|
|
|
69 |
*/
|
70 |
public function getAdapter($class_name)
|
71 |
{
|
@@ -80,6 +96,7 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
80 |
|
81 |
/**
|
82 |
* Checks if the necessary tables are available
|
|
|
83 |
*/
|
84 |
public function isInstalled()
|
85 |
{
|
@@ -90,6 +107,7 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
90 |
|
91 |
/**
|
92 |
* Checks if old version tables are available
|
|
|
93 |
*/
|
94 |
public function canMigrate()
|
95 |
{
|
@@ -109,22 +127,23 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
109 |
$filePath = explode(DIRECTORY_SEPARATOR, $file);
|
110 |
$fileName = $filePath[count($filePath) - 1];
|
111 |
$className = $this->getAdapterClassName(str_replace("Adapter.php", "", $fileName));
|
112 |
-
|
113 |
$class = new $className($this->getConnection());
|
114 |
if ($excludeOptions && $class instanceof WSAL_Adapters_MySQL_Option) {
|
115 |
continue;
|
116 |
}
|
|
|
117 |
// exclude the tmp_users table
|
118 |
if (!$excludeOptions && $class instanceof WSAL_Adapters_MySQL_TmpUser) {
|
119 |
continue;
|
120 |
}
|
121 |
-
|
122 |
if (is_subclass_of($class, "WSAL_Adapters_MySQL_ActiveRecord")) {
|
123 |
$class->Install();
|
124 |
}
|
125 |
}
|
126 |
}
|
127 |
-
|
128 |
/**
|
129 |
* Uninstall all DB tables.
|
130 |
*/
|
@@ -144,6 +163,10 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
144 |
}
|
145 |
}
|
146 |
|
|
|
|
|
|
|
|
|
147 |
private function GetIncreaseOccurrence()
|
148 |
{
|
149 |
$_wpdb = $this->getConnection();
|
@@ -152,6 +175,11 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
152 |
return (int)$_wpdb->get_var($sql);
|
153 |
}
|
154 |
|
|
|
|
|
|
|
|
|
|
|
155 |
public function MigrateMeta($index, $limit)
|
156 |
{
|
157 |
$result = null;
|
@@ -192,6 +220,11 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
192 |
return $result;
|
193 |
}
|
194 |
|
|
|
|
|
|
|
|
|
|
|
195 |
public function MigrateOccurrence($index, $limit)
|
196 |
{
|
197 |
$result = null;
|
@@ -229,6 +262,11 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
229 |
return $result;
|
230 |
}
|
231 |
|
|
|
|
|
|
|
|
|
|
|
232 |
public function MigrateBackOccurrence($index, $limit)
|
233 |
{
|
234 |
$result = null;
|
@@ -265,13 +303,18 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
265 |
return $result;
|
266 |
}
|
267 |
|
|
|
|
|
|
|
|
|
|
|
268 |
public function MigrateBackMeta($index, $limit)
|
269 |
{
|
270 |
$result = null;
|
271 |
$offset = ($index * $limit);
|
272 |
global $wpdb;
|
273 |
$_wpdb = $this->getConnection();
|
274 |
-
|
275 |
// Load data Meta from External DB
|
276 |
$meta = new WSAL_Adapters_MySQL_Meta($_wpdb);
|
277 |
if (!$meta->IsInstalled()) {
|
@@ -284,7 +327,7 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
284 |
// Insert data to WP
|
285 |
if (!empty($metadata)) {
|
286 |
$metaWP = new WSAL_Adapters_MySQL_Meta($wpdb);
|
287 |
-
|
288 |
$index++;
|
289 |
$sql = 'INSERT INTO ' . $metaWP->GetWPTable() . ' (occurrence_id, name, value) VALUES ' ;
|
290 |
foreach ($metadata as $entry) {
|
@@ -301,6 +344,10 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
301 |
return $result;
|
302 |
}
|
303 |
|
|
|
|
|
|
|
|
|
304 |
private function DeleteAfterMigrate($record)
|
305 |
{
|
306 |
global $wpdb;
|
@@ -308,31 +355,122 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
308 |
$wpdb->query($sql);
|
309 |
}
|
310 |
|
311 |
-
|
312 |
-
|
313 |
-
|
314 |
-
|
315 |
-
|
316 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
317 |
$ciphertext = $iv . $ciphertext;
|
318 |
-
$ciphertext_base64 = base64_encode($ciphertext);
|
319 |
-
|
320 |
return $ciphertext_base64;
|
|
|
321 |
}
|
322 |
-
|
323 |
-
|
324 |
-
|
325 |
-
|
326 |
-
|
327 |
-
|
328 |
-
|
329 |
-
|
330 |
-
|
331 |
-
|
332 |
-
|
333 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
334 |
}
|
335 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
336 |
public function MirroringAlertsToDB($args)
|
337 |
{
|
338 |
$last_created_on = null;
|
@@ -388,6 +526,11 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
388 |
return $last_created_on;
|
389 |
}
|
390 |
|
|
|
|
|
|
|
|
|
|
|
391 |
public function ArchiveOccurrence($args)
|
392 |
{
|
393 |
$_wpdb = $this->getConnection();
|
@@ -403,8 +546,8 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
403 |
}
|
404 |
|
405 |
if (!empty($args['by_limit'])) {
|
406 |
-
$sql = 'SELECT occ.* FROM ' . $occurrence->GetTable() . ' occ
|
407 |
-
LEFT JOIN (SELECT id FROM ' . $occurrence->GetTable() . ' order by created_on DESC limit ' . $args['by_limit'] . ') as ids
|
408 |
on ids.id = occ.id
|
409 |
WHERE ids.id IS NULL';
|
410 |
}
|
@@ -438,6 +581,11 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
438 |
}
|
439 |
}
|
440 |
|
|
|
|
|
|
|
|
|
|
|
441 |
public function ArchiveMeta($args)
|
442 |
{
|
443 |
$_wpdb = $this->getConnection();
|
@@ -468,13 +616,17 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
468 |
}
|
469 |
}
|
470 |
|
|
|
|
|
|
|
|
|
471 |
public function DeleteAfterArchive($args)
|
472 |
{
|
473 |
$_wpdb = $this->getConnection();
|
474 |
$archive_db = $args['archive_db'];
|
475 |
|
476 |
$sOccurenceIds = implode(", ", $args["occurence_ids"]);
|
477 |
-
|
478 |
$occurrence = new WSAL_Adapters_MySQL_Occurrence($_wpdb);
|
479 |
$sql = 'DELETE FROM ' . $occurrence->GetTable() . ' WHERE id IN (' . $sOccurenceIds . ')';
|
480 |
$_wpdb->query($sql);
|
@@ -484,6 +636,11 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
484 |
$_wpdb->query($sql);
|
485 |
}
|
486 |
|
|
|
|
|
|
|
|
|
|
|
487 |
private function truncateKey()
|
488 |
{
|
489 |
if (!defined('AUTH_KEY')) {
|
@@ -496,4 +653,21 @@ class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements
|
|
496 |
return AUTH_KEY;
|
497 |
}
|
498 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
499 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* MySQL Connector Class
|
5 |
+
* It uses wpdb WordPress DB Class
|
6 |
+
*/
|
7 |
class WSAL_Connector_MySQLDB extends WSAL_Connector_AbstractConnector implements WSAL_Connector_ConnectorInterface
|
8 |
{
|
9 |
protected $connectionConfig = null;
|
10 |
+
|
11 |
+
/**
|
12 |
+
* @param string $dbuser MySQL database user
|
13 |
+
* @param string $dbpassword MySQL database password
|
14 |
+
* @param string $dbname MySQL database name
|
15 |
+
* @param string $dbhost MySQL database host
|
16 |
+
*/
|
17 |
public function __construct($connectionConfig = null)
|
18 |
{
|
19 |
$this->connectionConfig = $connectionConfig;
|
21 |
require_once($this->getAdaptersDirectory() . '/OptionAdapter.php');
|
22 |
}
|
23 |
|
24 |
+
/**
|
25 |
+
* Test the connection.
|
26 |
+
* @throws Exception Connection failed
|
27 |
+
*/
|
28 |
public function TestConnection()
|
29 |
{
|
30 |
error_reporting(E_ALL ^ (E_NOTICE | E_WARNING | E_DEPRECATED));
|
57 |
|
58 |
/**
|
59 |
* Returns a wpdb instance
|
60 |
+
* @return wpdb
|
61 |
*/
|
62 |
public function getConnection()
|
63 |
{
|
80 |
}
|
81 |
|
82 |
/**
|
83 |
+
* Gets an adapter for the specified model.
|
84 |
+
* @return WSAL_Adapters_MySQL_{class_name}
|
85 |
*/
|
86 |
public function getAdapter($class_name)
|
87 |
{
|
96 |
|
97 |
/**
|
98 |
* Checks if the necessary tables are available
|
99 |
+
* @return bool true|false
|
100 |
*/
|
101 |
public function isInstalled()
|
102 |
{
|
107 |
|
108 |
/**
|
109 |
* Checks if old version tables are available
|
110 |
+
* @return bool true|false
|
111 |
*/
|
112 |
public function canMigrate()
|
113 |
{
|
127 |
$filePath = explode(DIRECTORY_SEPARATOR, $file);
|
128 |
$fileName = $filePath[count($filePath) - 1];
|
129 |
$className = $this->getAdapterClassName(str_replace("Adapter.php", "", $fileName));
|
130 |
+
|
131 |
$class = new $className($this->getConnection());
|
132 |
if ($excludeOptions && $class instanceof WSAL_Adapters_MySQL_Option) {
|
133 |
continue;
|
134 |
}
|
135 |
+
|
136 |
// exclude the tmp_users table
|
137 |
if (!$excludeOptions && $class instanceof WSAL_Adapters_MySQL_TmpUser) {
|
138 |
continue;
|
139 |
}
|
140 |
+
|
141 |
if (is_subclass_of($class, "WSAL_Adapters_MySQL_ActiveRecord")) {
|
142 |
$class->Install();
|
143 |
}
|
144 |
}
|
145 |
}
|
146 |
+
|
147 |
/**
|
148 |
* Uninstall all DB tables.
|
149 |
*/
|
163 |
}
|
164 |
}
|
165 |
|
166 |
+
/**
|
167 |
+
* Increase occurrence ID
|
168 |
+
* @return integer MAX(id)
|
169 |
+
*/
|
170 |
private function GetIncreaseOccurrence()
|
171 |
{
|
172 |
$_wpdb = $this->getConnection();
|
175 |
return (int)$_wpdb->get_var($sql);
|
176 |
}
|
177 |
|
178 |
+
/**
|
179 |
+
* Migrate Metadata from WP DB to External DB.
|
180 |
+
* @param integer $index
|
181 |
+
* @param integer $limit limit
|
182 |
+
*/
|
183 |
public function MigrateMeta($index, $limit)
|
184 |
{
|
185 |
$result = null;
|
220 |
return $result;
|
221 |
}
|
222 |
|
223 |
+
/**
|
224 |
+
* Migrate Occurrences from WP DB to External DB.
|
225 |
+
* @param integer $index
|
226 |
+
* @param integer $limit limit
|
227 |
+
*/
|
228 |
public function MigrateOccurrence($index, $limit)
|
229 |
{
|
230 |
$result = null;
|
262 |
return $result;
|
263 |
}
|
264 |
|
265 |
+
/**
|
266 |
+
* Migrate Back Occurrences from External DB to WP DB.
|
267 |
+
* @param integer $index
|
268 |
+
* @param integer $limit limit
|
269 |
+
*/
|
270 |
public function MigrateBackOccurrence($index, $limit)
|
271 |
{
|
272 |
$result = null;
|
303 |
return $result;
|
304 |
}
|
305 |
|
306 |
+
/**
|
307 |
+
* Migrate Back Metadata from External DB to WP DB.
|
308 |
+
* @param integer $index
|
309 |
+
* @param integer $limit limit
|
310 |
+
*/
|
311 |
public function MigrateBackMeta($index, $limit)
|
312 |
{
|
313 |
$result = null;
|
314 |
$offset = ($index * $limit);
|
315 |
global $wpdb;
|
316 |
$_wpdb = $this->getConnection();
|
317 |
+
|
318 |
// Load data Meta from External DB
|
319 |
$meta = new WSAL_Adapters_MySQL_Meta($_wpdb);
|
320 |
if (!$meta->IsInstalled()) {
|
327 |
// Insert data to WP
|
328 |
if (!empty($metadata)) {
|
329 |
$metaWP = new WSAL_Adapters_MySQL_Meta($wpdb);
|
330 |
+
|
331 |
$index++;
|
332 |
$sql = 'INSERT INTO ' . $metaWP->GetWPTable() . ' (occurrence_id, name, value) VALUES ' ;
|
333 |
foreach ($metadata as $entry) {
|
344 |
return $result;
|
345 |
}
|
346 |
|
347 |
+
/**
|
348 |
+
* Delete after Migrate alerts.
|
349 |
+
* @param object $record type of record
|
350 |
+
*/
|
351 |
private function DeleteAfterMigrate($record)
|
352 |
{
|
353 |
global $wpdb;
|
355 |
$wpdb->query($sql);
|
356 |
}
|
357 |
|
358 |
+
/**
|
359 |
+
* Encrypt plain text.
|
360 |
+
* Encrypt string, before saves it to the DB.
|
361 |
+
*
|
362 |
+
* @param string $plaintext - Plain text that is going to be encrypted.
|
363 |
+
* @return string
|
364 |
+
* @since 2.6.3
|
365 |
+
*/
|
366 |
+
public function encryptString( $plaintext ) {
|
367 |
+
|
368 |
+
// Check for previous version.
|
369 |
+
$plugin = WpSecurityAuditLog::GetInstance();
|
370 |
+
$version = $plugin->GetGlobalOption( 'version', '0.0.0' );
|
371 |
+
|
372 |
+
if ( -1 === version_compare( $version, '2.6.2' ) ) {
|
373 |
+
return $this->encryptString_fallback( $plaintext );
|
374 |
+
}
|
375 |
+
|
376 |
+
$ciphertext = false;
|
377 |
+
|
378 |
+
$encrypt_method = 'AES-256-CBC';
|
379 |
+
$secret_key = $this->truncateKey();
|
380 |
+
$secret_iv = $this->get_openssl_iv();
|
381 |
+
|
382 |
+
// Hash the key.
|
383 |
+
$key = hash( 'sha256', $secret_key );
|
384 |
+
|
385 |
+
// iv - encrypt method AES-256-CBC expects 16 bytes - else you will get a warning.
|
386 |
+
$iv = substr( hash( 'sha256', $secret_iv ), 0, 16 );
|
387 |
+
|
388 |
+
$ciphertext = openssl_encrypt( $plaintext, $encrypt_method, $key, 0, $iv );
|
389 |
+
$ciphertext = base64_encode( $ciphertext );
|
390 |
+
|
391 |
+
return $ciphertext;
|
392 |
+
|
393 |
+
}
|
394 |
+
|
395 |
+
/**
|
396 |
+
* Encrypt plain text - Fallback.
|
397 |
+
*
|
398 |
+
* @param string $plaintext - Plain text that is going to be encrypted.
|
399 |
+
* @return string
|
400 |
+
* @since 2.6.3
|
401 |
+
*/
|
402 |
+
public function encryptString_fallback( $plaintext ) {
|
403 |
+
|
404 |
+
$iv_size = mcrypt_get_iv_size( MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC );
|
405 |
+
$iv = mcrypt_create_iv( $iv_size, MCRYPT_RAND );
|
406 |
+
$key = $this->truncateKey();
|
407 |
+
$ciphertext = mcrypt_encrypt( MCRYPT_RIJNDAEL_128, $key, $plaintext, MCRYPT_MODE_CBC, $iv );
|
408 |
$ciphertext = $iv . $ciphertext;
|
409 |
+
$ciphertext_base64 = base64_encode( $ciphertext );
|
|
|
410 |
return $ciphertext_base64;
|
411 |
+
|
412 |
}
|
413 |
+
|
414 |
+
/**
|
415 |
+
* Decrypt the encrypted string.
|
416 |
+
* Decrypt string, after reads it from the DB.
|
417 |
+
*
|
418 |
+
* @param string $ciphertext_base64 - encrypted string.
|
419 |
+
* @return string
|
420 |
+
* @since 2.6.3
|
421 |
+
*/
|
422 |
+
public function decryptString( $ciphertext_base64 ) {
|
423 |
+
|
424 |
+
// Check for previous version.
|
425 |
+
$plugin = WpSecurityAuditLog::GetInstance();
|
426 |
+
$version = $plugin->GetGlobalOption( 'version', '0.0.0' );
|
427 |
+
|
428 |
+
if ( -1 === version_compare( $version, '2.6.2' ) ) {
|
429 |
+
return $this->decryptString_fallback( $ciphertext_base64 );
|
430 |
+
}
|
431 |
+
|
432 |
+
$plaintext = false;
|
433 |
+
|
434 |
+
$encrypt_method = 'AES-256-CBC';
|
435 |
+
$secret_key = $this->truncateKey();
|
436 |
+
$secret_iv = $this->get_openssl_iv();
|
437 |
+
|
438 |
+
// Hash the key.
|
439 |
+
$key = hash( 'sha256', $secret_key );
|
440 |
+
|
441 |
+
// iv - encrypt method AES-256-CBC expects 16 bytes - else you will get a warning.
|
442 |
+
$iv = substr( hash( 'sha256', $secret_iv ), 0, 16 );
|
443 |
+
|
444 |
+
$plaintext = openssl_decrypt( base64_decode( $ciphertext_base64 ), $encrypt_method, $key, 0, $iv );
|
445 |
+
|
446 |
+
return $plaintext;
|
447 |
+
|
448 |
}
|
449 |
|
450 |
+
/**
|
451 |
+
* Decrypt the encrypted string - Fallback.
|
452 |
+
*
|
453 |
+
* @param string $ciphertext_base64 - encrypted string.
|
454 |
+
* @return string
|
455 |
+
* @since 2.6.3
|
456 |
+
*/
|
457 |
+
public function decryptString_fallback( $ciphertext_base64 ) {
|
458 |
+
|
459 |
+
$ciphertext_dec = base64_decode( $ciphertext_base64 );
|
460 |
+
$iv_size = mcrypt_get_iv_size( MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC );
|
461 |
+
$iv_dec = substr( $ciphertext_dec, 0, $iv_size );
|
462 |
+
$ciphertext_dec = substr( $ciphertext_dec, $iv_size );
|
463 |
+
$key = $this->truncateKey();
|
464 |
+
$plaintext_dec = mcrypt_decrypt( MCRYPT_RIJNDAEL_128, $key, $ciphertext_dec, MCRYPT_MODE_CBC, $iv_dec );
|
465 |
+
return rtrim( $plaintext_dec, "\0" );
|
466 |
+
|
467 |
+
}
|
468 |
+
|
469 |
+
/**
|
470 |
+
* Mirroring Occurrences and Metadata Tables.
|
471 |
+
* Read from current DB and copy into Mirroring DB.
|
472 |
+
* @param array $args archive Database and limit by date
|
473 |
+
*/
|
474 |
public function MirroringAlertsToDB($args)
|
475 |
{
|
476 |
$last_created_on = null;
|
526 |
return $last_created_on;
|
527 |
}
|
528 |
|
529 |
+
/**
|
530 |
+
* Archiving Occurrences Table.
|
531 |
+
* Read from current DB and copy into Archive DB.
|
532 |
+
* @param array $args archive Database and limit by count OR by date
|
533 |
+
*/
|
534 |
public function ArchiveOccurrence($args)
|
535 |
{
|
536 |
$_wpdb = $this->getConnection();
|
546 |
}
|
547 |
|
548 |
if (!empty($args['by_limit'])) {
|
549 |
+
$sql = 'SELECT occ.* FROM ' . $occurrence->GetTable() . ' occ
|
550 |
+
LEFT JOIN (SELECT id FROM ' . $occurrence->GetTable() . ' order by created_on DESC limit ' . $args['by_limit'] . ') as ids
|
551 |
on ids.id = occ.id
|
552 |
WHERE ids.id IS NULL';
|
553 |
}
|
581 |
}
|
582 |
}
|
583 |
|
584 |
+
/**
|
585 |
+
* Archiving Metadata Table.
|
586 |
+
* Read from current DB and copy into Archive DB.
|
587 |
+
* @param array $args archive Database and occurrences IDs
|
588 |
+
*/
|
589 |
public function ArchiveMeta($args)
|
590 |
{
|
591 |
$_wpdb = $this->getConnection();
|
616 |
}
|
617 |
}
|
618 |
|
619 |
+
/**
|
620 |
+
* Delete Occurrences and Metadata after archiving.
|
621 |
+
* @param array $args archive Database and occurrences IDs
|
622 |
+
*/
|
623 |
public function DeleteAfterArchive($args)
|
624 |
{
|
625 |
$_wpdb = $this->getConnection();
|
626 |
$archive_db = $args['archive_db'];
|
627 |
|
628 |
$sOccurenceIds = implode(", ", $args["occurence_ids"]);
|
629 |
+
|
630 |
$occurrence = new WSAL_Adapters_MySQL_Occurrence($_wpdb);
|
631 |
$sql = 'DELETE FROM ' . $occurrence->GetTable() . ' WHERE id IN (' . $sOccurenceIds . ')';
|
632 |
$_wpdb->query($sql);
|
636 |
$_wpdb->query($sql);
|
637 |
}
|
638 |
|
639 |
+
/**
|
640 |
+
* Truncate string longer than 32 characters.
|
641 |
+
* Authentication Unique Key @see wp-config.php
|
642 |
+
* @return string AUTH_KEY
|
643 |
+
*/
|
644 |
private function truncateKey()
|
645 |
{
|
646 |
if (!defined('AUTH_KEY')) {
|
653 |
return AUTH_KEY;
|
654 |
}
|
655 |
}
|
656 |
+
|
657 |
+
/**
|
658 |
+
* Get OpenSSL IV for DB.
|
659 |
+
*
|
660 |
+
* @since 2.6.3
|
661 |
+
*/
|
662 |
+
private function get_openssl_iv() {
|
663 |
+
|
664 |
+
$secret_openssl_iv = 'і-(аэ┤#≥и┴зейН';
|
665 |
+
$key_size = strlen( $secret_openssl_iv );
|
666 |
+
if ( $key_size > 32 ) {
|
667 |
+
return substr( $secret_openssl_iv, 0, 32 );
|
668 |
+
} else {
|
669 |
+
return $secret_openssl_iv;
|
670 |
+
}
|
671 |
+
|
672 |
+
}
|
673 |
}
|
classes/Connector/wp-db-custom.php
CHANGED
@@ -1,10 +1,19 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
class wpdbCustom extends wpdb
|
4 |
{
|
5 |
-
|
6 |
-
*
|
7 |
* and hide the print of the error
|
|
|
|
|
|
|
|
|
|
|
8 |
*/
|
9 |
public function __construct($dbuser, $dbpassword, $dbname, $dbhost)
|
10 |
{
|
@@ -32,5 +41,4 @@ class wpdbCustom extends wpdb
|
|
32 |
|
33 |
$this->db_connect(false);
|
34 |
}
|
35 |
-
|
36 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* Test the DB connection.
|
5 |
+
* It uses wpdb WordPress DB Class.
|
6 |
+
*/
|
7 |
class wpdbCustom extends wpdb
|
8 |
{
|
9 |
+
/**
|
10 |
+
* Overwrite wpdb class for set $allow_bail to false
|
11 |
* and hide the print of the error
|
12 |
+
* @global string $wp_version
|
13 |
+
* @param string $dbuser MySQL database user
|
14 |
+
* @param string $dbpassword MySQL database password
|
15 |
+
* @param string $dbname MySQL database name
|
16 |
+
* @param string $dbhost MySQL database host
|
17 |
*/
|
18 |
public function __construct($dbuser, $dbpassword, $dbname, $dbhost)
|
19 |
{
|
41 |
|
42 |
$this->db_connect(false);
|
43 |
}
|
|
|
44 |
}
|
classes/ConstantManager.php
CHANGED
@@ -1,89 +1,96 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
69 |
-
|
70 |
-
|
71 |
-
|
72 |
-
|
73 |
-
|
74 |
-
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
|
79 |
-
|
80 |
-
|
81 |
-
|
82 |
-
|
83 |
-
|
84 |
-
|
85 |
-
|
86 |
-
|
87 |
-
|
88 |
-
|
89 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Class used for Constants,
|
6 |
+
* E_NOTICE, E_WARNING, E_CRITICAL, etc.
|
7 |
+
*/
|
8 |
+
class WSAL_ConstantManager
|
9 |
+
{
|
10 |
+
protected $_constants = array();
|
11 |
+
|
12 |
+
/**
|
13 |
+
* Use an existing PHP constant.
|
14 |
+
* @param string $name Constant name.
|
15 |
+
* @param string $description Constant description.
|
16 |
+
*/
|
17 |
+
public function UseConstant($name, $description = '')
|
18 |
+
{
|
19 |
+
$this->_constants[] = (object)array(
|
20 |
+
'name' => $name,
|
21 |
+
'value' => constant($name),
|
22 |
+
'description' => $description,
|
23 |
+
);
|
24 |
+
}
|
25 |
+
|
26 |
+
/**
|
27 |
+
* Add new PHP constant.
|
28 |
+
* @param string $name Constant name.
|
29 |
+
* @param integer|string $value Constant value.
|
30 |
+
* @param string $description Constant description.
|
31 |
+
*/
|
32 |
+
public function AddConstant($name, $value, $description = '')
|
33 |
+
{
|
34 |
+
// check for constant conflict and define new one if required
|
35 |
+
if (defined($name) && constant($name) !== $value) {
|
36 |
+
throw new Exception('Constant already defined with a different value.');
|
37 |
+
} else {
|
38 |
+
define($name, $value);
|
39 |
+
}
|
40 |
+
// add constant to da list.
|
41 |
+
$this->UseConstant($name, $description);
|
42 |
+
}
|
43 |
+
|
44 |
+
/**
|
45 |
+
* Add multiple constants in one go.
|
46 |
+
* @param array $items Array of arrays with name, value, description pairs.
|
47 |
+
*/
|
48 |
+
public function AddConstants($items)
|
49 |
+
{
|
50 |
+
foreach ($items as $item) {
|
51 |
+
$this->AddConstant(
|
52 |
+
$item['name'],
|
53 |
+
$item['value'],
|
54 |
+
$item['description']
|
55 |
+
);
|
56 |
+
}
|
57 |
+
}
|
58 |
+
|
59 |
+
/**
|
60 |
+
* Use multiple constants in one go.
|
61 |
+
* @param array $items Array of arrays with name, description pairs.
|
62 |
+
*/
|
63 |
+
public function UseConstants($items)
|
64 |
+
{
|
65 |
+
foreach ($items as $item) {
|
66 |
+
$this->UseConstant(
|
67 |
+
$item['name'],
|
68 |
+
$item['description']
|
69 |
+
);
|
70 |
+
}
|
71 |
+
}
|
72 |
+
|
73 |
+
/**
|
74 |
+
* Get constant details by a particular detail.
|
75 |
+
* @param string $what The type of detail: 'name', 'value'
|
76 |
+
* @param mixed $value The detail expected value.
|
77 |
+
* @return mixed Either constant details (props: name, value, description) or $default if not found.
|
78 |
+
*/
|
79 |
+
public function GetConstantBy($what, $value, $default = null)
|
80 |
+
{
|
81 |
+
// make sure we do have some constants...
|
82 |
+
if (count($this->_constants)) {
|
83 |
+
// make sure that constants do have a $what property
|
84 |
+
if (!isset($this->_constants[0]->$what)) {
|
85 |
+
throw new Exception('Unexpected detail type "' . $what . '".');
|
86 |
+
}
|
87 |
+
// return constant match the property value
|
88 |
+
foreach ($this->_constants as $constant) {
|
89 |
+
if ($constant->$what == $value) {
|
90 |
+
return $constant;
|
91 |
+
}
|
92 |
+
}
|
93 |
+
}
|
94 |
+
return $default;
|
95 |
+
}
|
96 |
+
}
|
classes/EDD_SL_Plugin_Updater.php
CHANGED
@@ -1,15 +1,16 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
// uncomment this line for testing
|
4 |
//set_site_transient( 'update_plugins', null );
|
5 |
|
6 |
/**
|
|
|
7 |
* Allows plugins to use their own update API.
|
8 |
*
|
9 |
* @author Pippin Williamson
|
10 |
* @version 1.2
|
11 |
*/
|
12 |
-
class EDD_SL_Plugin_Updater
|
|
|
13 |
private $api_url = '';
|
14 |
private $api_data = array();
|
15 |
private $name = '';
|
@@ -27,11 +28,12 @@ class EDD_SL_Plugin_Updater {
|
|
27 |
* @param array $_api_data Optional data to send with API calls.
|
28 |
* @return void
|
29 |
*/
|
30 |
-
function __construct(
|
31 |
-
|
32 |
-
$this->
|
33 |
-
$this->
|
34 |
-
$this->
|
|
|
35 |
$this->version = $_api_data['version'];
|
36 |
|
37 |
// Set up hooks.
|
@@ -42,13 +44,13 @@ class EDD_SL_Plugin_Updater {
|
|
42 |
* Set up WordPress filters to hook into WP's update process.
|
43 |
*
|
44 |
* @uses add_filter()
|
45 |
-
*
|
46 |
* @return void
|
47 |
*/
|
48 |
-
private function hook()
|
49 |
-
|
50 |
-
add_filter(
|
51 |
-
add_filter(
|
|
|
52 |
}
|
53 |
|
54 |
/**
|
@@ -64,30 +66,25 @@ class EDD_SL_Plugin_Updater {
|
|
64 |
* @param array $_transient_data Update array build by WordPress.
|
65 |
* @return array Modified update array with custom plugin data.
|
66 |
*/
|
67 |
-
function pre_set_site_transient_update_plugins_filter(
|
68 |
-
|
69 |
-
if(
|
70 |
-
|
71 |
// This ensures that the custom API request only runs on the second time that WP fires the update check
|
72 |
$this->do_check = true;
|
73 |
-
|
74 |
return $_transient_data;
|
75 |
}
|
76 |
|
77 |
-
$to_send = array(
|
|
|
78 |
|
79 |
-
$api_response
|
80 |
-
|
81 |
-
if( false !== $api_response && is_object( $api_response ) && isset( $api_response->new_version ) ) {
|
82 |
-
|
83 |
-
if( version_compare( $this->version, $api_response->new_version, '<' ) ) {
|
84 |
$_transient_data->response[$this->name] = $api_response;
|
85 |
}
|
86 |
}
|
87 |
return $_transient_data;
|
88 |
}
|
89 |
|
90 |
-
|
91 |
/**
|
92 |
* Updates information on the "View version x.x details" page with custom data.
|
93 |
*
|
@@ -98,18 +95,21 @@ class EDD_SL_Plugin_Updater {
|
|
98 |
* @param object $_args
|
99 |
* @return object $_data
|
100 |
*/
|
101 |
-
function plugins_api_filter(
|
102 |
-
|
103 |
-
|
104 |
-
|
|
|
|
|
105 |
|
106 |
-
$api_response = $this->api_request(
|
107 |
-
if (
|
|
|
|
|
108 |
|
109 |
return $_data;
|
110 |
}
|
111 |
|
112 |
-
|
113 |
/**
|
114 |
* Disable SSL verification in order to prevent download update failures
|
115 |
*
|
@@ -117,9 +117,10 @@ class EDD_SL_Plugin_Updater {
|
|
117 |
* @param string $url
|
118 |
* @return object $array
|
119 |
*/
|
120 |
-
function http_request_args(
|
|
|
121 |
// If it is an https request and we are performing a package download, disable ssl verification
|
122 |
-
if(
|
123 |
$args['sslverify'] = false;
|
124 |
}
|
125 |
return $args;
|
@@ -136,17 +137,18 @@ class EDD_SL_Plugin_Updater {
|
|
136 |
* @param array $_data Parameters for the API action.
|
137 |
* @return false||object
|
138 |
*/
|
139 |
-
private function api_request(
|
140 |
-
|
141 |
global $wp_version;
|
|
|
142 |
|
143 |
-
$data
|
144 |
-
|
145 |
-
if( $data['slug'] != $this->slug )
|
146 |
return;
|
|
|
147 |
|
148 |
-
if(
|
149 |
return;
|
|
|
150 |
|
151 |
$api_params = array(
|
152 |
'edd_action' => 'get_version',
|
@@ -156,15 +158,16 @@ class EDD_SL_Plugin_Updater {
|
|
156 |
'author' => $data['author'],
|
157 |
'url' => home_url()
|
158 |
);
|
159 |
-
$request = wp_remote_post(
|
160 |
|
161 |
-
if (
|
162 |
-
$request = json_decode(
|
163 |
-
if(
|
164 |
-
$request->sections = maybe_unserialize(
|
|
|
165 |
return $request;
|
166 |
-
else
|
167 |
return false;
|
168 |
-
|
169 |
}
|
170 |
}
|
1 |
<?php
|
|
|
2 |
// uncomment this line for testing
|
3 |
//set_site_transient( 'update_plugins', null );
|
4 |
|
5 |
/**
|
6 |
+
* @package Wsal
|
7 |
* Allows plugins to use their own update API.
|
8 |
*
|
9 |
* @author Pippin Williamson
|
10 |
* @version 1.2
|
11 |
*/
|
12 |
+
class EDD_SL_Plugin_Updater
|
13 |
+
{
|
14 |
private $api_url = '';
|
15 |
private $api_data = array();
|
16 |
private $name = '';
|
28 |
* @param array $_api_data Optional data to send with API calls.
|
29 |
* @return void
|
30 |
*/
|
31 |
+
public function __construct($_api_url, $_plugin_file, $_api_data = null)
|
32 |
+
{
|
33 |
+
$this->api_url = trailingslashit($_api_url);
|
34 |
+
$this->api_data = urlencode_deep($_api_data);
|
35 |
+
$this->name = plugin_basename($_plugin_file);
|
36 |
+
$this->slug = basename($_plugin_file, '.php');
|
37 |
$this->version = $_api_data['version'];
|
38 |
|
39 |
// Set up hooks.
|
44 |
* Set up WordPress filters to hook into WP's update process.
|
45 |
*
|
46 |
* @uses add_filter()
|
|
|
47 |
* @return void
|
48 |
*/
|
49 |
+
private function hook()
|
50 |
+
{
|
51 |
+
add_filter('pre_set_site_transient_update_plugins', array( $this, 'pre_set_site_transient_update_plugins_filter'));
|
52 |
+
add_filter('plugins_api', array( $this, 'plugins_api_filter' ), 10, 3);
|
53 |
+
add_filter('http_request_args', array( $this, 'http_request_args' ), 10, 2);
|
54 |
}
|
55 |
|
56 |
/**
|
66 |
* @param array $_transient_data Update array build by WordPress.
|
67 |
* @return array Modified update array with custom plugin data.
|
68 |
*/
|
69 |
+
public function pre_set_site_transient_update_plugins_filter($_transient_data)
|
70 |
+
{
|
71 |
+
if (empty($_transient_data) || !$this->do_check) {
|
|
|
72 |
// This ensures that the custom API request only runs on the second time that WP fires the update check
|
73 |
$this->do_check = true;
|
|
|
74 |
return $_transient_data;
|
75 |
}
|
76 |
|
77 |
+
$to_send = array('slug' => $this->slug);
|
78 |
+
$api_response = $this->api_request('plugin_latest_version', $to_send);
|
79 |
|
80 |
+
if (false !== $api_response && is_object($api_response) && isset($api_response->new_version)) {
|
81 |
+
if (version_compare($this->version, $api_response->new_version, '<')) {
|
|
|
|
|
|
|
82 |
$_transient_data->response[$this->name] = $api_response;
|
83 |
}
|
84 |
}
|
85 |
return $_transient_data;
|
86 |
}
|
87 |
|
|
|
88 |
/**
|
89 |
* Updates information on the "View version x.x details" page with custom data.
|
90 |
*
|
95 |
* @param object $_args
|
96 |
* @return object $_data
|
97 |
*/
|
98 |
+
public function plugins_api_filter($_data, $_action = '', $_args = null)
|
99 |
+
{
|
100 |
+
if (($_action != 'plugin_information') || !isset($_args->slug) || ($_args->slug != $this->slug)) {
|
101 |
+
return $_data;
|
102 |
+
}
|
103 |
+
$to_send = array('slug' => $this->slug);
|
104 |
|
105 |
+
$api_response = $this->api_request('plugin_information', $to_send);
|
106 |
+
if (false !== $api_response) {
|
107 |
+
$_data = $api_response;
|
108 |
+
}
|
109 |
|
110 |
return $_data;
|
111 |
}
|
112 |
|
|
|
113 |
/**
|
114 |
* Disable SSL verification in order to prevent download update failures
|
115 |
*
|
117 |
* @param string $url
|
118 |
* @return object $array
|
119 |
*/
|
120 |
+
public function http_request_args($args, $url)
|
121 |
+
{
|
122 |
// If it is an https request and we are performing a package download, disable ssl verification
|
123 |
+
if (strpos($url, 'https://') !== false && strpos($url, 'edd_action=package_download')) {
|
124 |
$args['sslverify'] = false;
|
125 |
}
|
126 |
return $args;
|
137 |
* @param array $_data Parameters for the API action.
|
138 |
* @return false||object
|
139 |
*/
|
140 |
+
private function api_request($_action, $_data)
|
141 |
+
{
|
142 |
global $wp_version;
|
143 |
+
$data = array_merge($this->api_data, $_data);
|
144 |
|
145 |
+
if ($data['slug'] != $this->slug) {
|
|
|
|
|
146 |
return;
|
147 |
+
}
|
148 |
|
149 |
+
if (empty($data['license'])) {
|
150 |
return;
|
151 |
+
}
|
152 |
|
153 |
$api_params = array(
|
154 |
'edd_action' => 'get_version',
|
158 |
'author' => $data['author'],
|
159 |
'url' => home_url()
|
160 |
);
|
161 |
+
$request = wp_remote_post($this->api_url, array('timeout' => 15, 'sslverify' => false, 'body' => $api_params));
|
162 |
|
163 |
+
if (!is_wp_error($request)) {
|
164 |
+
$request = json_decode(wp_remote_retrieve_body($request));
|
165 |
+
if ($request && isset($request->sections)) {
|
166 |
+
$request->sections = maybe_unserialize($request->sections);
|
167 |
+
}
|
168 |
return $request;
|
169 |
+
} else {
|
170 |
return false;
|
171 |
+
}
|
172 |
}
|
173 |
}
|
classes/Helpers/DataHelper.php
CHANGED
@@ -1,14 +1,18 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Helpers_DataHelper
|
4 |
{
|
5 |
-
|
6 |
-
/**
|
7 |
* A wrapper for JSON encoding that fixes potential issues.
|
8 |
* @param mixed $data The data to encode.
|
9 |
* @return string JSON string.
|
10 |
*/
|
11 |
-
public static function JsonEncode($data)
|
|
|
12 |
return @json_encode($data);
|
13 |
}
|
14 |
|
@@ -17,7 +21,8 @@ class WSAL_Helpers_DataHelper
|
|
17 |
* @param string $data The JSON string to decode.
|
18 |
* @return mixed Decoded data.
|
19 |
*/
|
20 |
-
public static function JsonDecode($data)
|
|
|
21 |
return @json_decode($data);
|
22 |
}
|
23 |
-
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Helper class used for encode/decode json data.
|
6 |
+
*/
|
7 |
class WSAL_Helpers_DataHelper
|
8 |
{
|
9 |
+
/**
|
|
|
10 |
* A wrapper for JSON encoding that fixes potential issues.
|
11 |
* @param mixed $data The data to encode.
|
12 |
* @return string JSON string.
|
13 |
*/
|
14 |
+
public static function JsonEncode($data)
|
15 |
+
{
|
16 |
return @json_encode($data);
|
17 |
}
|
18 |
|
21 |
* @param string $data The JSON string to decode.
|
22 |
* @return mixed Decoded data.
|
23 |
*/
|
24 |
+
public static function JsonDecode($data)
|
25 |
+
{
|
26 |
return @json_decode($data);
|
27 |
}
|
28 |
+
}
|
classes/Lib/class-recursive-arrayaccess.php
DELETED
@@ -1,139 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
/**
|
3 |
-
* Multidimensional ArrayAccess
|
4 |
-
*
|
5 |
-
* Allows ArrayAccess-like functionality with multidimensional arrays. Fully supports
|
6 |
-
* both sets and unsets.
|
7 |
-
*
|
8 |
-
* @package WordPress
|
9 |
-
* @subpackage Session
|
10 |
-
* @since 3.6.0
|
11 |
-
*/
|
12 |
-
|
13 |
-
// Exit if accessed directly
|
14 |
-
if ( ! defined( 'ABSPATH' ) ) exit;
|
15 |
-
|
16 |
-
/**
|
17 |
-
* Recursive array class to allow multidimensional array access.
|
18 |
-
*
|
19 |
-
* @package WordPress
|
20 |
-
* @since 3.6.0
|
21 |
-
*/
|
22 |
-
class Recursive_ArrayAccess implements ArrayAccess {
|
23 |
-
/**
|
24 |
-
* Internal data collection.
|
25 |
-
*
|
26 |
-
* @var array
|
27 |
-
*/
|
28 |
-
protected $container = array();
|
29 |
-
|
30 |
-
/**
|
31 |
-
* Flag whether or not the internal collection has been changed.
|
32 |
-
*
|
33 |
-
* @var bool
|
34 |
-
*/
|
35 |
-
protected $dirty = false;
|
36 |
-
|
37 |
-
/**
|
38 |
-
* Default object constructor.
|
39 |
-
*
|
40 |
-
* @param array $data
|
41 |
-
*/
|
42 |
-
protected function __construct( $data = array() ) {
|
43 |
-
foreach ( $data as $key => $value ) {
|
44 |
-
$this[ $key ] = $value;
|
45 |
-
}
|
46 |
-
}
|
47 |
-
|
48 |
-
/**
|
49 |
-
* Allow deep copies of objects
|
50 |
-
*/
|
51 |
-
public function __clone() {
|
52 |
-
foreach ( $this->container as $key => $value ) {
|
53 |
-
if ( $value instanceof self ) {
|
54 |
-
$this[ $key ] = clone $value;
|
55 |
-
}
|
56 |
-
}
|
57 |
-
}
|
58 |
-
|
59 |
-
/**
|
60 |
-
* Output the data container as a multidimensional array.
|
61 |
-
*
|
62 |
-
* @return array
|
63 |
-
*/
|
64 |
-
public function toArray() {
|
65 |
-
$data = $this->container;
|
66 |
-
foreach ( $data as $key => $value ) {
|
67 |
-
if ( $value instanceof self ) {
|
68 |
-
$data[ $key ] = $value->toArray();
|
69 |
-
}
|
70 |
-
}
|
71 |
-
return $data;
|
72 |
-
}
|
73 |
-
|
74 |
-
/**
|
75 |
-
* ArrayAccess Implementation
|
76 |
-
**/
|
77 |
-
|
78 |
-
/**
|
79 |
-
* Whether a offset exists
|
80 |
-
*
|
81 |
-
* @link http://php.net/manual/en/arrayaccess.offsetexists.php
|
82 |
-
*
|
83 |
-
* @param mixed $offset An offset to check for.
|
84 |
-
*
|
85 |
-
* @return boolean true on success or false on failure.
|
86 |
-
*/
|
87 |
-
public function offsetExists( $offset ) {
|
88 |
-
return isset( $this->container[ $offset ]) ;
|
89 |
-
}
|
90 |
-
|
91 |
-
/**
|
92 |
-
* Offset to retrieve
|
93 |
-
*
|
94 |
-
* @link http://php.net/manual/en/arrayaccess.offsetget.php
|
95 |
-
*
|
96 |
-
* @param mixed $offset The offset to retrieve.
|
97 |
-
*
|
98 |
-
* @return mixed Can return all value types.
|
99 |
-
*/
|
100 |
-
public function offsetGet( $offset ) {
|
101 |
-
return isset( $this->container[ $offset ] ) ? $this->container[ $offset ] : null;
|
102 |
-
}
|
103 |
-
|
104 |
-
/**
|
105 |
-
* Offset to set
|
106 |
-
*
|
107 |
-
* @link http://php.net/manual/en/arrayaccess.offsetset.php
|
108 |
-
*
|
109 |
-
* @param mixed $offset The offset to assign the value to.
|
110 |
-
* @param mixed $value The value to set.
|
111 |
-
*
|
112 |
-
* @return void
|
113 |
-
*/
|
114 |
-
public function offsetSet( $offset, $data ) {
|
115 |
-
if ( is_array( $data ) ) {
|
116 |
-
$data = new self( $data );
|
117 |
-
}
|
118 |
-
if ( $offset === null ) { // don't forget this!
|
119 |
-
$this->container[] = $data;
|
120 |
-
} else {
|
121 |
-
$this->container[ $offset ] = $data;
|
122 |
-
}
|
123 |
-
|
124 |
-
$this->dirty = true;
|
125 |
-
}
|
126 |
-
|
127 |
-
/**
|
128 |
-
* Offset to unset
|
129 |
-
*
|
130 |
-
* @link http://php.net/manual/en/arrayaccess.offsetunset.php
|
131 |
-
*
|
132 |
-
* @param mixed $offset The offset to unset.
|
133 |
-
*
|
134 |
-
* @return void
|
135 |
-
*/
|
136 |
-
public function offsetUnset( $offset ) {
|
137 |
-
unset( $this->container[ $offset ] );
|
138 |
-
}
|
139 |
-
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/Lib/class-wp-session-utils.php
DELETED
@@ -1,139 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
/**
|
4 |
-
* Utility class for sesion utilities
|
5 |
-
*
|
6 |
-
* THIS CLASS SHOULD NEVER BE INSTANTIATED
|
7 |
-
*/
|
8 |
-
class WP_Session_Utils {
|
9 |
-
/**
|
10 |
-
* Count the total sessions in the database.
|
11 |
-
*
|
12 |
-
* @global wpdb $wpdb
|
13 |
-
*
|
14 |
-
* @return int
|
15 |
-
*/
|
16 |
-
public static function count_sessions() {
|
17 |
-
global $wpdb;
|
18 |
-
|
19 |
-
$query = "SELECT COUNT(*) FROM $wpdb->options WHERE option_name LIKE '_wp_session_expires_%'";
|
20 |
-
|
21 |
-
/**
|
22 |
-
* Filter the query in case tables are non-standard.
|
23 |
-
*
|
24 |
-
* @param string $query Database count query
|
25 |
-
*/
|
26 |
-
$query = apply_filters( 'wp_session_count_query', $query );
|
27 |
-
|
28 |
-
$sessions = $wpdb->get_var( $query );
|
29 |
-
|
30 |
-
return absint( $sessions );
|
31 |
-
}
|
32 |
-
|
33 |
-
/**
|
34 |
-
* Create a new, random session in the database.
|
35 |
-
*
|
36 |
-
* @param null|string $date
|
37 |
-
*/
|
38 |
-
public static function create_dummy_session( $date = null ) {
|
39 |
-
// Generate our date
|
40 |
-
if ( null !== $date ) {
|
41 |
-
$time = strtotime( $date );
|
42 |
-
|
43 |
-
if ( false === $time ) {
|
44 |
-
$date = null;
|
45 |
-
} else {
|
46 |
-
$expires = date( 'U', strtotime( $date ) );
|
47 |
-
}
|
48 |
-
}
|
49 |
-
|
50 |
-
// If null was passed, or if the string parsing failed, fall back on a default
|
51 |
-
if ( null === $date ) {
|
52 |
-
/**
|
53 |
-
* Filter the expiration of the session in the database
|
54 |
-
*
|
55 |
-
* @param int
|
56 |
-
*/
|
57 |
-
$expires = time() + (int) apply_filters( 'wp_session_expiration', 30 * 60 );
|
58 |
-
}
|
59 |
-
|
60 |
-
$session_id = self::generate_id();
|
61 |
-
|
62 |
-
// Store the session
|
63 |
-
add_option( "_wp_session_{$session_id}", array(), '', 'no' );
|
64 |
-
add_option( "_wp_session_expires_{$session_id}", $expires, '', 'no' );
|
65 |
-
}
|
66 |
-
|
67 |
-
/**
|
68 |
-
* Delete old sessions from the database.
|
69 |
-
*
|
70 |
-
* @param int $limit Maximum number of sessions to delete.
|
71 |
-
*
|
72 |
-
* @global wpdb $wpdb
|
73 |
-
*
|
74 |
-
* @return int Sessions deleted.
|
75 |
-
*/
|
76 |
-
public static function delete_old_sessions( $limit = 1000 ) {
|
77 |
-
global $wpdb;
|
78 |
-
|
79 |
-
$limit = absint( $limit );
|
80 |
-
$keys = $wpdb->get_results( "SELECT option_name, option_value FROM $wpdb->options WHERE option_name LIKE '_wp_session_expires_%' ORDER BY option_value ASC LIMIT 0, {$limit}" );
|
81 |
-
|
82 |
-
$now = time();
|
83 |
-
$expired = array();
|
84 |
-
$count = 0;
|
85 |
-
|
86 |
-
foreach( $keys as $expiration ) {
|
87 |
-
$key = $expiration->option_name;
|
88 |
-
$expires = $expiration->option_value;
|
89 |
-
|
90 |
-
if ( $now > $expires ) {
|
91 |
-
$session_id = preg_replace("/[^A-Za-z0-9_]/", '', substr( $key, 20 ) );
|
92 |
-
|
93 |
-
$expired[] = $key;
|
94 |
-
$expired[] = "_wp_session_{$session_id}";
|
95 |
-
|
96 |
-
$count += 1;
|
97 |
-
}
|
98 |
-
}
|
99 |
-
|
100 |
-
// Delete expired sessions
|
101 |
-
if ( ! empty( $expired ) ) {
|
102 |
-
$placeholders = array_fill( 0, count( $expired ), '%s' );
|
103 |
-
$format = implode( ', ', $placeholders );
|
104 |
-
$query = "DELETE FROM $wpdb->options WHERE option_name IN ($format)";
|
105 |
-
|
106 |
-
$prepared = $wpdb->prepare( $query, $expired );
|
107 |
-
$wpdb->query( $prepared );
|
108 |
-
}
|
109 |
-
|
110 |
-
return $count;
|
111 |
-
}
|
112 |
-
|
113 |
-
/**
|
114 |
-
* Remove all sessions from the database, regardless of expiration.
|
115 |
-
*
|
116 |
-
* @global wpdb $wpdb
|
117 |
-
*
|
118 |
-
* @return int Sessions deleted
|
119 |
-
*/
|
120 |
-
public static function delete_all_sessions() {
|
121 |
-
global $wpdb;
|
122 |
-
|
123 |
-
$count = $wpdb->query( "DELETE FROM $wpdb->options WHERE option_name LIKE '_wp_session_%'" );
|
124 |
-
|
125 |
-
return (int) ( $count / 2 );
|
126 |
-
}
|
127 |
-
|
128 |
-
/**
|
129 |
-
* Generate a new, random session ID.
|
130 |
-
*
|
131 |
-
* @return string
|
132 |
-
*/
|
133 |
-
public static function generate_id() {
|
134 |
-
require_once( ABSPATH . 'wp-includes/class-phpass.php' );
|
135 |
-
$hash = new PasswordHash( 8, false );
|
136 |
-
|
137 |
-
return md5( $hash->get_random_bytes( 32 ) );
|
138 |
-
}
|
139 |
-
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/Lib/class-wp-session.php
DELETED
@@ -1,322 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
/**
|
3 |
-
* WordPress session managment.
|
4 |
-
*
|
5 |
-
* Standardizes WordPress session data using database-backed options for storage.
|
6 |
-
* for storing user session information.
|
7 |
-
*
|
8 |
-
* @package WordPress
|
9 |
-
* @subpackage Session
|
10 |
-
* @since 3.7.0
|
11 |
-
*/
|
12 |
-
|
13 |
-
// Exit if accessed directly
|
14 |
-
if ( ! defined( 'ABSPATH' ) ) exit;
|
15 |
-
|
16 |
-
/**
|
17 |
-
* WordPress Session class for managing user session data.
|
18 |
-
*
|
19 |
-
* @package WordPress
|
20 |
-
* @since 3.7.0
|
21 |
-
*/
|
22 |
-
final class WP_Session extends Recursive_ArrayAccess implements Iterator, Countable {
|
23 |
-
/**
|
24 |
-
* ID of the current session.
|
25 |
-
*
|
26 |
-
* @var string
|
27 |
-
*/
|
28 |
-
public $session_id;
|
29 |
-
|
30 |
-
/**
|
31 |
-
* Unix timestamp when session expires.
|
32 |
-
*
|
33 |
-
* @var int
|
34 |
-
*/
|
35 |
-
protected $expires;
|
36 |
-
|
37 |
-
/**
|
38 |
-
* Unix timestamp indicating when the expiration time needs to be reset.
|
39 |
-
*
|
40 |
-
* @var int
|
41 |
-
*/
|
42 |
-
protected $exp_variant;
|
43 |
-
|
44 |
-
/**
|
45 |
-
* Singleton instance.
|
46 |
-
*
|
47 |
-
* @var bool|WP_Session
|
48 |
-
*/
|
49 |
-
private static $instance = false;
|
50 |
-
|
51 |
-
/**
|
52 |
-
* Retrieve the current session instance.
|
53 |
-
*
|
54 |
-
* @param bool $session_id Session ID from which to populate data.
|
55 |
-
*
|
56 |
-
* @return bool|WP_Session
|
57 |
-
*/
|
58 |
-
public static function get_instance() {
|
59 |
-
if (!self::$instance) {
|
60 |
-
self::$instance = new self();
|
61 |
-
}
|
62 |
-
|
63 |
-
return self::$instance;
|
64 |
-
}
|
65 |
-
|
66 |
-
/**
|
67 |
-
* Default constructor.
|
68 |
-
* Will rebuild the session collection from the given session ID if it exists. Otherwise, will
|
69 |
-
* create a new session with that ID.
|
70 |
-
*
|
71 |
-
* @param $session_id
|
72 |
-
* @uses apply_filters Calls `wp_session_expiration` to determine how long until sessions expire.
|
73 |
-
*/
|
74 |
-
protected function __construct() {
|
75 |
-
if ( isset( $_COOKIE[WP_SESSION_COOKIE] ) ) {
|
76 |
-
$cookie = stripslashes( $_COOKIE[WP_SESSION_COOKIE] );
|
77 |
-
$cookie_crumbs = explode( '||', $cookie );
|
78 |
-
|
79 |
-
$this->session_id = $cookie_crumbs[0];
|
80 |
-
$this->expires = $cookie_crumbs[1];
|
81 |
-
$this->exp_variant = $cookie_crumbs[2];
|
82 |
-
|
83 |
-
// Update the session expiration if we're past the variant time
|
84 |
-
if ( time() > $this->exp_variant ) {
|
85 |
-
$this->set_expiration();
|
86 |
-
delete_option( "_wp_session_expires_{$this->session_id}" );
|
87 |
-
add_option( "_wp_session_expires_{$this->session_id}", $this->expires, '', 'no' );
|
88 |
-
}
|
89 |
-
} else {
|
90 |
-
$this->session_id = WP_Session_Utils::generate_id();
|
91 |
-
$this->set_expiration();
|
92 |
-
}
|
93 |
-
|
94 |
-
$this->read_data();
|
95 |
-
|
96 |
-
$this->set_cookie();
|
97 |
-
}
|
98 |
-
|
99 |
-
/**
|
100 |
-
* Set both the expiration time and the expiration variant.
|
101 |
-
*
|
102 |
-
* If the current time is below the variant, we don't update the session's expiration time. If it's
|
103 |
-
* greater than the variant, then we update the expiration time in the database. This prevents
|
104 |
-
* writing to the database on every page load for active sessions and only updates the expiration
|
105 |
-
* time if we're nearing when the session actually expires.
|
106 |
-
*
|
107 |
-
* By default, the expiration time is set to 30 minutes.
|
108 |
-
* By default, the expiration variant is set to 24 minutes.
|
109 |
-
*
|
110 |
-
* As a result, the session expiration time - at a maximum - will only be written to the database once
|
111 |
-
* every 24 minutes. After 30 minutes, the session will have been expired. No cookie will be sent by
|
112 |
-
* the browser, and the old session will be queued for deletion by the garbage collector.
|
113 |
-
*
|
114 |
-
* @uses apply_filters Calls `wp_session_expiration_variant` to get the max update window for session data.
|
115 |
-
* @uses apply_filters Calls `wp_session_expiration` to get the standard expiration time for sessions.
|
116 |
-
*/
|
117 |
-
protected function set_expiration() {
|
118 |
-
$this->exp_variant = time() + (int) apply_filters('wp_session_expiration_variant', 24 * 60);
|
119 |
-
$this->expires = time() + (int) apply_filters('wp_session_expiration', 30 * 60);
|
120 |
-
}
|
121 |
-
|
122 |
-
/**
|
123 |
-
* Set the session cookie
|
124 |
-
*/
|
125 |
-
protected function set_cookie() {
|
126 |
-
@setcookie(WP_SESSION_COOKIE, $this->session_id . '||' . $this->expires . '||' . $this->exp_variant, $this->expires, COOKIEPATH, COOKIE_DOMAIN);
|
127 |
-
}
|
128 |
-
|
129 |
-
/**
|
130 |
-
* Generate a cryptographically strong unique ID for the session token.
|
131 |
-
*
|
132 |
-
* @return string
|
133 |
-
*/
|
134 |
-
protected function generate_id() {
|
135 |
-
require_once(ABSPATH . 'wp-includes/class-phpass.php');
|
136 |
-
$hasher = new PasswordHash(8, false);
|
137 |
-
|
138 |
-
return md5($hasher->get_random_bytes(32));
|
139 |
-
}
|
140 |
-
|
141 |
-
/**
|
142 |
-
* Checks if is valid md5 string
|
143 |
-
*
|
144 |
-
* @param string $md5
|
145 |
-
* @return int
|
146 |
-
*/
|
147 |
-
protected function is_valid_md5($md5 = '') {
|
148 |
-
return preg_match('/^[a-f0-9]{32}$/', $md5);
|
149 |
-
}
|
150 |
-
|
151 |
-
/**
|
152 |
-
* Read data from a transient for the current session.
|
153 |
-
*
|
154 |
-
* Automatically resets the expiration time for the session transient to some time in the future.
|
155 |
-
*
|
156 |
-
* @return array
|
157 |
-
*/
|
158 |
-
protected function read_data() {
|
159 |
-
$this->container = get_option("_wp_session_{$this->session_id}", array());
|
160 |
-
|
161 |
-
return $this->container;
|
162 |
-
}
|
163 |
-
|
164 |
-
/**
|
165 |
-
* Write the data from the current session to the data storage system.
|
166 |
-
*/
|
167 |
-
public function write_data() {
|
168 |
-
$option_key = "_wp_session_{$this->session_id}";
|
169 |
-
|
170 |
-
// Only write the collection to the DB if it's changed.
|
171 |
-
if ($this->dirty) {
|
172 |
-
if (false === get_option($option_key)) {
|
173 |
-
add_option("_wp_session_{$this->session_id}", $this->container, '', 'no');
|
174 |
-
add_option("_wp_session_expires_{$this->session_id}", $this->expires, '', 'no');
|
175 |
-
} else {
|
176 |
-
delete_option("_wp_session_{$this->session_id}");
|
177 |
-
add_option("_wp_session_{$this->session_id}", $this->container, '', 'no');
|
178 |
-
}
|
179 |
-
}
|
180 |
-
}
|
181 |
-
|
182 |
-
/**
|
183 |
-
* Output the current container contents as a JSON-encoded string.
|
184 |
-
*
|
185 |
-
* @return string
|
186 |
-
*/
|
187 |
-
public function json_out() {
|
188 |
-
return json_encode($this->container);
|
189 |
-
}
|
190 |
-
|
191 |
-
/**
|
192 |
-
* Decodes a JSON string and, if the object is an array, overwrites the session container with its contents.
|
193 |
-
*
|
194 |
-
* @param string $data
|
195 |
-
*
|
196 |
-
* @return bool
|
197 |
-
*/
|
198 |
-
public function json_in($data) {
|
199 |
-
$array = json_decode($data);
|
200 |
-
|
201 |
-
if (is_array($array)) {
|
202 |
-
$this->container = $array;
|
203 |
-
return true;
|
204 |
-
}
|
205 |
-
|
206 |
-
return false;
|
207 |
-
}
|
208 |
-
|
209 |
-
/**
|
210 |
-
* Regenerate the current session's ID.
|
211 |
-
*
|
212 |
-
* @param bool $delete_old Flag whether or not to delete the old session data from the server.
|
213 |
-
*/
|
214 |
-
public function regenerate_id($delete_old = false) {
|
215 |
-
if ($delete_old) {
|
216 |
-
delete_option("_wp_session_{$this->session_id}");
|
217 |
-
}
|
218 |
-
|
219 |
-
$this->session_id = $this->generate_id();
|
220 |
-
|
221 |
-
$this->set_cookie();
|
222 |
-
}
|
223 |
-
|
224 |
-
/**
|
225 |
-
* Check if a session has been initialized.
|
226 |
-
*
|
227 |
-
* @return bool
|
228 |
-
*/
|
229 |
-
public function session_started() {
|
230 |
-
return !!self::$instance;
|
231 |
-
}
|
232 |
-
|
233 |
-
/**
|
234 |
-
* Return the read-only cache expiration value.
|
235 |
-
*
|
236 |
-
* @return int
|
237 |
-
*/
|
238 |
-
public function cache_expiration() {
|
239 |
-
return $this->expires;
|
240 |
-
}
|
241 |
-
|
242 |
-
/**
|
243 |
-
* Flushes all session variables.
|
244 |
-
*/
|
245 |
-
public function reset() {
|
246 |
-
$this->container = array();
|
247 |
-
}
|
248 |
-
|
249 |
-
/*****************************************************************/
|
250 |
-
/* Iterator Implementation */
|
251 |
-
/*****************************************************************/
|
252 |
-
|
253 |
-
/**
|
254 |
-
* Current position of the array.
|
255 |
-
*
|
256 |
-
* @link http://php.net/manual/en/iterator.current.php
|
257 |
-
*
|
258 |
-
* @return mixed
|
259 |
-
*/
|
260 |
-
public function current() {
|
261 |
-
return current($this->container);
|
262 |
-
}
|
263 |
-
|
264 |
-
/**
|
265 |
-
* Key of the current element.
|
266 |
-
*
|
267 |
-
* @link http://php.net/manual/en/iterator.key.php
|
268 |
-
*
|
269 |
-
* @return mixed
|
270 |
-
*/
|
271 |
-
public function key() {
|
272 |
-
return key($this->container);
|
273 |
-
}
|
274 |
-
|
275 |
-
/**
|
276 |
-
* Move the internal point of the container array to the next item
|
277 |
-
*
|
278 |
-
* @link http://php.net/manual/en/iterator.next.php
|
279 |
-
*
|
280 |
-
* @return void
|
281 |
-
*/
|
282 |
-
public function next() {
|
283 |
-
next($this->container);
|
284 |
-
}
|
285 |
-
|
286 |
-
/**
|
287 |
-
* Rewind the internal point of the container array.
|
288 |
-
*
|
289 |
-
* @link http://php.net/manual/en/iterator.rewind.php
|
290 |
-
*
|
291 |
-
* @return void
|
292 |
-
*/
|
293 |
-
public function rewind() {
|
294 |
-
reset($this->container);
|
295 |
-
}
|
296 |
-
|
297 |
-
/**
|
298 |
-
* Is the current key valid?
|
299 |
-
*
|
300 |
-
* @link http://php.net/manual/en/iterator.rewind.php
|
301 |
-
*
|
302 |
-
* @return bool
|
303 |
-
*/
|
304 |
-
public function valid() {
|
305 |
-
return $this->offsetExists($this->key());
|
306 |
-
}
|
307 |
-
|
308 |
-
/*****************************************************************/
|
309 |
-
/* Countable Implementation */
|
310 |
-
/*****************************************************************/
|
311 |
-
|
312 |
-
/**
|
313 |
-
* Get the count of elements in the container array.
|
314 |
-
*
|
315 |
-
* @link http://php.net/manual/en/countable.count.php
|
316 |
-
*
|
317 |
-
* @return int
|
318 |
-
*/
|
319 |
-
public function count() {
|
320 |
-
return count($this->container);
|
321 |
-
}
|
322 |
-
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/Lib/wp-session.php
DELETED
@@ -1,182 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
/**
|
3 |
-
* WordPress session managment.
|
4 |
-
*
|
5 |
-
* Standardizes WordPress session data and uses either database transients or in-memory caching
|
6 |
-
* for storing user session information.
|
7 |
-
*
|
8 |
-
* @package WordPress
|
9 |
-
* @subpackage Session
|
10 |
-
* @since 3.7.0
|
11 |
-
*/
|
12 |
-
|
13 |
-
// Exit if accessed directly
|
14 |
-
if (!defined('ABSPATH')) exit;
|
15 |
-
|
16 |
-
/**
|
17 |
-
* Return the current cache expire setting.
|
18 |
-
*
|
19 |
-
* @return int
|
20 |
-
*/
|
21 |
-
function wp_session_cache_expire() {
|
22 |
-
$wp_session = WP_Session::get_instance();
|
23 |
-
|
24 |
-
return $wp_session->cache_expiration();
|
25 |
-
}
|
26 |
-
|
27 |
-
/**
|
28 |
-
* Alias of wp_session_write_close()
|
29 |
-
*/
|
30 |
-
function wp_session_commit() {
|
31 |
-
wp_session_write_close();
|
32 |
-
}
|
33 |
-
|
34 |
-
/**
|
35 |
-
* Load a JSON-encoded string into the current session.
|
36 |
-
*
|
37 |
-
* @param string $data
|
38 |
-
*/
|
39 |
-
function wp_session_decode($data) {
|
40 |
-
$wp_session = WP_Session::get_instance();
|
41 |
-
|
42 |
-
return $wp_session->json_in($data);
|
43 |
-
}
|
44 |
-
|
45 |
-
/**
|
46 |
-
* Encode the current session's data as a JSON string.
|
47 |
-
*
|
48 |
-
* @return string
|
49 |
-
*/
|
50 |
-
function wp_session_encode() {
|
51 |
-
$wp_session = WP_Session::get_instance();
|
52 |
-
|
53 |
-
return $wp_session->json_out();
|
54 |
-
}
|
55 |
-
|
56 |
-
/**
|
57 |
-
* Regenerate the session ID.
|
58 |
-
*
|
59 |
-
* @param bool $delete_old_session
|
60 |
-
*
|
61 |
-
* @return bool
|
62 |
-
*/
|
63 |
-
function wp_session_regenerate_id($delete_old_session = false) {
|
64 |
-
$wp_session = WP_Session::get_instance();
|
65 |
-
|
66 |
-
$wp_session->regenerate_id($delete_old_session);
|
67 |
-
|
68 |
-
return true;
|
69 |
-
}
|
70 |
-
|
71 |
-
/**
|
72 |
-
* Start new or resume existing session.
|
73 |
-
*
|
74 |
-
* Resumes an existing session based on a value sent by the _wp_session cookie.
|
75 |
-
*
|
76 |
-
* @return bool
|
77 |
-
*/
|
78 |
-
function wp_session_start() {
|
79 |
-
$wp_session = WP_Session::get_instance();
|
80 |
-
do_action('wp_session_start');
|
81 |
-
|
82 |
-
return $wp_session->session_started();
|
83 |
-
}
|
84 |
-
// Removed
|
85 |
-
//add_action( 'plugins_loaded', 'wp_session_start' );
|
86 |
-
|
87 |
-
/**
|
88 |
-
* Return the current session status.
|
89 |
-
*
|
90 |
-
* @return int
|
91 |
-
*/
|
92 |
-
function wp_session_status() {
|
93 |
-
$wp_session = WP_Session::get_instance();
|
94 |
-
|
95 |
-
if ($wp_session->session_started()) {
|
96 |
-
return PHP_SESSION_ACTIVE;
|
97 |
-
}
|
98 |
-
|
99 |
-
return PHP_SESSION_NONE;
|
100 |
-
}
|
101 |
-
|
102 |
-
/**
|
103 |
-
* Unset all session variables.
|
104 |
-
*/
|
105 |
-
function wp_session_unset() {
|
106 |
-
$wp_session = WP_Session::get_instance();
|
107 |
-
|
108 |
-
$wp_session->reset();
|
109 |
-
}
|
110 |
-
|
111 |
-
/**
|
112 |
-
* Write session data and end session
|
113 |
-
*/
|
114 |
-
function wp_session_write_close() {
|
115 |
-
$wp_session = WP_Session::get_instance();
|
116 |
-
|
117 |
-
$wp_session->write_data();
|
118 |
-
do_action('wp_session_commit');
|
119 |
-
}
|
120 |
-
add_action('shutdown', 'wp_session_write_close');
|
121 |
-
add_action('wp_logout', 'wp_session_unset');
|
122 |
-
|
123 |
-
/**
|
124 |
-
* Clean up expired sessions by removing data and their expiration entries from
|
125 |
-
* the WordPress options table.
|
126 |
-
*
|
127 |
-
* This method should never be called directly and should instead be triggered as part
|
128 |
-
* of a scheduled task or cron job.
|
129 |
-
*/
|
130 |
-
if (!function_exists('wp_session_cleanup')) {
|
131 |
-
function wp_session_cleanup()
|
132 |
-
{
|
133 |
-
global $wpdb;
|
134 |
-
|
135 |
-
if (defined('WP_SETUP_CONFIG')) {
|
136 |
-
return;
|
137 |
-
}
|
138 |
-
|
139 |
-
if (!defined('WP_INSTALLING')) {
|
140 |
-
$expiration_keys = $wpdb->get_results("SELECT option_name, option_value FROM $wpdb->options WHERE option_name LIKE '_wp_session_expires_%'");
|
141 |
-
|
142 |
-
$now = current_time('timestamp');
|
143 |
-
$expired_sessions = array();
|
144 |
-
|
145 |
-
foreach ($expiration_keys as $expiration) {
|
146 |
-
// If the session has expired
|
147 |
-
if ($now > intval($expiration->option_value)) {
|
148 |
-
// Get the session ID by parsing the option_name
|
149 |
-
$session_id = substr($expiration->option_name, 20);
|
150 |
-
|
151 |
-
if ((int) -1 === (int) $session_id || !preg_match('/^[a-f0-9]{32}$/', $session_id)) {
|
152 |
-
continue;
|
153 |
-
}
|
154 |
-
$expired_sessions[] = $expiration->option_name;
|
155 |
-
$expired_sessions[] = esc_sql("_wp_session_$session_id");
|
156 |
-
}
|
157 |
-
}
|
158 |
-
// Delete all expired sessions in a single query
|
159 |
-
if (!empty($expired_sessions)) {
|
160 |
-
$option_names = implode("','", $expired_sessions);
|
161 |
-
$wpdb->query("DELETE FROM $wpdb->options WHERE option_name IN ('$option_names')");
|
162 |
-
}
|
163 |
-
}
|
164 |
-
|
165 |
-
// Allow other plugins to hook in to the garbage collection process.
|
166 |
-
do_action('wp_session_cleanup');
|
167 |
-
}
|
168 |
-
}
|
169 |
-
add_action('wp_session_garbage_collection', 'wp_session_cleanup');
|
170 |
-
|
171 |
-
/**
|
172 |
-
* Register the garbage collector as a twice daily event.
|
173 |
-
*/
|
174 |
-
if (!function_exists('wp_session_register_garbage_collection')) {
|
175 |
-
function wp_session_register_garbage_collection()
|
176 |
-
{
|
177 |
-
if (!wp_next_scheduled('wp_session_garbage_collection')) {
|
178 |
-
wp_schedule_event(current_time('timestamp'), 'twicedaily', 'wp_session_garbage_collection');
|
179 |
-
}
|
180 |
-
}
|
181 |
-
}
|
182 |
-
add_action('wp', 'wp_session_register_garbage_collection');
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/LicenseManager.php
CHANGED
@@ -4,8 +4,13 @@
|
|
4 |
if(!class_exists('EDD_SL_Plugin_Updater')){
|
5 |
require_once('EDD_SL_Plugin_Updater.php');
|
6 |
}
|
7 |
-
|
8 |
-
|
|
|
|
|
|
|
|
|
|
|
9 |
/**
|
10 |
* @var WpSecurityAuditLog
|
11 |
*/
|
@@ -13,30 +18,36 @@ class WSAL_LicenseManager {
|
|
13 |
|
14 |
protected $plugins = array();
|
15 |
|
16 |
-
public function __construct(WpSecurityAuditLog $plugin)
|
|
|
17 |
$this->plugin = $plugin;
|
18 |
add_action('plugins_loaded', array($this, 'LoadPlugins'));
|
19 |
}
|
20 |
|
21 |
-
protected function GetStoreUrl()
|
|
|
22 |
return 'https://www.wpsecurityauditlog.com/';
|
23 |
}
|
24 |
|
25 |
-
public function CountPlugins()
|
|
|
26 |
return count($this->plugins);
|
27 |
}
|
28 |
|
29 |
-
public function Plugins()
|
|
|
30 |
return $this->plugins;
|
31 |
}
|
32 |
|
33 |
-
public function LoadPlugins()
|
34 |
-
|
|
|
35 |
$this->AddPremiumPlugin($pluginFile);
|
36 |
}
|
37 |
}
|
38 |
|
39 |
-
protected function GetPluginData($pluginFile, $license)
|
|
|
40 |
// A hack since get_plugin_data() is not available now
|
41 |
$pluginData = get_file_data($pluginFile, array(
|
42 |
'Name' => 'Plugin Name',
|
@@ -46,11 +57,11 @@ class WSAL_LicenseManager {
|
|
46 |
'Author' => 'Author',
|
47 |
'TextDomain' => 'Text Domain',
|
48 |
'DomainPath' => 'Domain Path',
|
49 |
-
), 'plugin'
|
50 |
|
51 |
$pluginUpdater = is_null($license)
|
52 |
-
|
53 |
-
|
54 |
$this->GetStoreUrl(),
|
55 |
$pluginFile,
|
56 |
array(
|
@@ -67,7 +78,8 @@ class WSAL_LicenseManager {
|
|
67 |
);
|
68 |
}
|
69 |
|
70 |
-
public function AddPremiumPlugin($pluginFile)
|
|
|
71 |
if (isset($pluginFile)) {
|
72 |
$name = sanitize_key(basename($pluginFile));
|
73 |
$license = $this->plugin->settings->GetLicenseKey($name);
|
@@ -75,20 +87,23 @@ class WSAL_LicenseManager {
|
|
75 |
}
|
76 |
}
|
77 |
|
78 |
-
public function AddPlugin($pluginFile)
|
|
|
79 |
if (isset($pluginFile)) {
|
80 |
$name = sanitize_key(basename($pluginFile));
|
81 |
$this->plugins[$name] = $this->GetPluginData($pluginFile, null);
|
82 |
}
|
83 |
}
|
84 |
|
85 |
-
protected function GetBlogIds()
|
|
|
86 |
global $wpdb;
|
87 |
$sql = 'SELECT blog_id FROM ' . $wpdb->blogs;
|
88 |
return $wpdb->get_col($sql);
|
89 |
}
|
90 |
|
91 |
-
public function ActivateLicense($name, $license)
|
|
|
92 |
$this->plugin->settings->SetLicenseKey($name, $license);
|
93 |
|
94 |
$plugins = $this->Plugins();
|
@@ -101,10 +116,10 @@ class WSAL_LicenseManager {
|
|
101 |
|
102 |
$blog_ids = $this->plugin->IsMultisite() ? $this->GetBlogIds() : array(1);
|
103 |
|
104 |
-
foreach($blog_ids as $blog_id){
|
105 |
-
|
106 |
-
if($this->plugin->IsMultisite())
|
107 |
$api_params['url'] = urlencode(get_home_url($blog_id));
|
|
|
108 |
|
109 |
$response = wp_remote_get(
|
110 |
esc_url_raw(add_query_arg($api_params, $this->GetStoreUrl())),
|
@@ -119,16 +134,18 @@ class WSAL_LicenseManager {
|
|
119 |
|
120 |
$license_data = json_decode(wp_remote_retrieve_body($response));
|
121 |
|
122 |
-
if(is_object($license_data)){
|
123 |
$this->plugin->settings->SetLicenseStatus($name, $license_data->license);
|
124 |
-
if($license_data->license !== 'valid'){
|
125 |
$error = 'License Not Valid';
|
126 |
-
if (isset($license_data->error))
|
|
|
|
|
127 |
$this->plugin->settings->SetLicenseErrors($name, $error);
|
128 |
$this->DeactivateLicense($name, $license);
|
129 |
return false;
|
130 |
}
|
131 |
-
}else{
|
132 |
$this->plugin->settings->SetLicenseErrors($name, 'Unexpected Licensing Server Response');
|
133 |
$this->DeactivateLicense($name, $license);
|
134 |
return false;
|
@@ -138,15 +155,16 @@ class WSAL_LicenseManager {
|
|
138 |
return true;
|
139 |
}
|
140 |
|
141 |
-
public function IsLicenseValid($name)
|
|
|
142 |
return trim(strtolower($this->plugin->settings->GetLicenseStatus($name))) === 'valid';
|
143 |
}
|
144 |
|
145 |
-
public function DeactivateLicense($name, $license = null)
|
|
|
146 |
$this->plugin->settings->SetLicenseStatus($name, '');
|
147 |
-
|
148 |
// deactivate it on the server (if license was given)
|
149 |
-
if(!is_null($license)){
|
150 |
$plugins = $this->Plugins();
|
151 |
$api_params = array(
|
152 |
'edd_action'=> 'deactivate_license',
|
@@ -157,17 +175,19 @@ class WSAL_LicenseManager {
|
|
157 |
|
158 |
$blog_ids = $this->plugin->IsMultisite() ? $this->GetBlogIds() : array(1);
|
159 |
|
160 |
-
foreach($blog_ids as $blog_id){
|
161 |
-
|
162 |
-
if($this->plugin->IsMultisite())
|
163 |
$api_params['url'] = urlencode(get_home_url($blog_id));
|
|
|
164 |
|
165 |
$response = wp_remote_get(
|
166 |
esc_url_raw(add_query_arg($api_params, $this->GetStoreUrl())),
|
167 |
array('timeout' => 15, 'sslverify' => false)
|
168 |
);
|
169 |
|
170 |
-
if (is_wp_error($response))
|
|
|
|
|
171 |
|
172 |
wp_remote_retrieve_body($response);
|
173 |
}
|
4 |
if(!class_exists('EDD_SL_Plugin_Updater')){
|
5 |
require_once('EDD_SL_Plugin_Updater.php');
|
6 |
}
|
7 |
+
/**
|
8 |
+
* @package Wsal
|
9 |
+
*
|
10 |
+
* License Manager used in all the Add-Ons licenses.
|
11 |
+
*/
|
12 |
+
class WSAL_LicenseManager
|
13 |
+
{
|
14 |
/**
|
15 |
* @var WpSecurityAuditLog
|
16 |
*/
|
18 |
|
19 |
protected $plugins = array();
|
20 |
|
21 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
22 |
+
{
|
23 |
$this->plugin = $plugin;
|
24 |
add_action('plugins_loaded', array($this, 'LoadPlugins'));
|
25 |
}
|
26 |
|
27 |
+
protected function GetStoreUrl()
|
28 |
+
{
|
29 |
return 'https://www.wpsecurityauditlog.com/';
|
30 |
}
|
31 |
|
32 |
+
public function CountPlugins()
|
33 |
+
{
|
34 |
return count($this->plugins);
|
35 |
}
|
36 |
|
37 |
+
public function Plugins()
|
38 |
+
{
|
39 |
return $this->plugins;
|
40 |
}
|
41 |
|
42 |
+
public function LoadPlugins()
|
43 |
+
{
|
44 |
+
foreach (apply_filters('wsal_register', array()) as $pluginFile) {
|
45 |
$this->AddPremiumPlugin($pluginFile);
|
46 |
}
|
47 |
}
|
48 |
|
49 |
+
protected function GetPluginData($pluginFile, $license)
|
50 |
+
{
|
51 |
// A hack since get_plugin_data() is not available now
|
52 |
$pluginData = get_file_data($pluginFile, array(
|
53 |
'Name' => 'Plugin Name',
|
57 |
'Author' => 'Author',
|
58 |
'TextDomain' => 'Text Domain',
|
59 |
'DomainPath' => 'Domain Path',
|
60 |
+
), 'plugin');
|
61 |
|
62 |
$pluginUpdater = is_null($license)
|
63 |
+
? null
|
64 |
+
: new EDD_SL_Plugin_Updater(
|
65 |
$this->GetStoreUrl(),
|
66 |
$pluginFile,
|
67 |
array(
|
78 |
);
|
79 |
}
|
80 |
|
81 |
+
public function AddPremiumPlugin($pluginFile)
|
82 |
+
{
|
83 |
if (isset($pluginFile)) {
|
84 |
$name = sanitize_key(basename($pluginFile));
|
85 |
$license = $this->plugin->settings->GetLicenseKey($name);
|
87 |
}
|
88 |
}
|
89 |
|
90 |
+
public function AddPlugin($pluginFile)
|
91 |
+
{
|
92 |
if (isset($pluginFile)) {
|
93 |
$name = sanitize_key(basename($pluginFile));
|
94 |
$this->plugins[$name] = $this->GetPluginData($pluginFile, null);
|
95 |
}
|
96 |
}
|
97 |
|
98 |
+
protected function GetBlogIds()
|
99 |
+
{
|
100 |
global $wpdb;
|
101 |
$sql = 'SELECT blog_id FROM ' . $wpdb->blogs;
|
102 |
return $wpdb->get_col($sql);
|
103 |
}
|
104 |
|
105 |
+
public function ActivateLicense($name, $license)
|
106 |
+
{
|
107 |
$this->plugin->settings->SetLicenseKey($name, $license);
|
108 |
|
109 |
$plugins = $this->Plugins();
|
116 |
|
117 |
$blog_ids = $this->plugin->IsMultisite() ? $this->GetBlogIds() : array(1);
|
118 |
|
119 |
+
foreach ($blog_ids as $blog_id) {
|
120 |
+
if ($this->plugin->IsMultisite()) {
|
|
|
121 |
$api_params['url'] = urlencode(get_home_url($blog_id));
|
122 |
+
}
|
123 |
|
124 |
$response = wp_remote_get(
|
125 |
esc_url_raw(add_query_arg($api_params, $this->GetStoreUrl())),
|
134 |
|
135 |
$license_data = json_decode(wp_remote_retrieve_body($response));
|
136 |
|
137 |
+
if (is_object($license_data)) {
|
138 |
$this->plugin->settings->SetLicenseStatus($name, $license_data->license);
|
139 |
+
if ($license_data->license !== 'valid') {
|
140 |
$error = 'License Not Valid';
|
141 |
+
if (isset($license_data->error)) {
|
142 |
+
$error .= ': ' . ucfirst(str_replace('_', ' ', $license_data->error));
|
143 |
+
}
|
144 |
$this->plugin->settings->SetLicenseErrors($name, $error);
|
145 |
$this->DeactivateLicense($name, $license);
|
146 |
return false;
|
147 |
}
|
148 |
+
} else {
|
149 |
$this->plugin->settings->SetLicenseErrors($name, 'Unexpected Licensing Server Response');
|
150 |
$this->DeactivateLicense($name, $license);
|
151 |
return false;
|
155 |
return true;
|
156 |
}
|
157 |
|
158 |
+
public function IsLicenseValid($name)
|
159 |
+
{
|
160 |
return trim(strtolower($this->plugin->settings->GetLicenseStatus($name))) === 'valid';
|
161 |
}
|
162 |
|
163 |
+
public function DeactivateLicense($name, $license = null)
|
164 |
+
{
|
165 |
$this->plugin->settings->SetLicenseStatus($name, '');
|
|
|
166 |
// deactivate it on the server (if license was given)
|
167 |
+
if (!is_null($license)) {
|
168 |
$plugins = $this->Plugins();
|
169 |
$api_params = array(
|
170 |
'edd_action'=> 'deactivate_license',
|
175 |
|
176 |
$blog_ids = $this->plugin->IsMultisite() ? $this->GetBlogIds() : array(1);
|
177 |
|
178 |
+
foreach ($blog_ids as $blog_id) {
|
179 |
+
if ($this->plugin->IsMultisite()) {
|
|
|
180 |
$api_params['url'] = urlencode(get_home_url($blog_id));
|
181 |
+
}
|
182 |
|
183 |
$response = wp_remote_get(
|
184 |
esc_url_raw(add_query_arg($api_params, $this->GetStoreUrl())),
|
185 |
array('timeout' => 15, 'sslverify' => false)
|
186 |
);
|
187 |
|
188 |
+
if (is_wp_error($response)) {
|
189 |
+
return false;
|
190 |
+
}
|
191 |
|
192 |
wp_remote_retrieve_body($response);
|
193 |
}
|
classes/Loggers/Database.php
CHANGED
@@ -1,18 +1,33 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
4 |
{
|
5 |
-
|
6 |
public function __construct(WpSecurityAuditLog $plugin)
|
7 |
{
|
8 |
parent::__construct($plugin);
|
9 |
$plugin->AddCleanupHook(array($this, 'CleanUp'));
|
10 |
}
|
11 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
12 |
public function Log($type, $data = array(), $date = null, $siteid = null, $migrated = false)
|
13 |
{
|
14 |
// is this a php alert, and if so, are we logging such alerts?
|
15 |
-
if ($type < 0010 && !$this->plugin->settings->IsPhpErrorLoggingEnabled())
|
|
|
|
|
16 |
|
17 |
// create new occurrence
|
18 |
$occ = new WSAL_Models_Occurrence();
|
@@ -32,6 +47,9 @@ class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
|
32 |
}
|
33 |
}
|
34 |
|
|
|
|
|
|
|
35 |
public function CleanUp()
|
36 |
{
|
37 |
$now = current_time('timestamp');
|
@@ -57,15 +75,23 @@ class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
|
57 |
$query = new WSAL_Models_OccurrenceQuery();
|
58 |
$query->addOrderBy("created_on", false);
|
59 |
// TO DO Fixing data
|
60 |
-
if ($is_date_e)
|
61 |
-
|
|
|
|
|
|
|
|
|
62 |
|
63 |
-
if (($max_items-1) == 0)
|
|
|
|
|
64 |
|
65 |
$result = $query->getAdapter()->GetSqlDelete($query);
|
66 |
$deletedCount = $query->getAdapter()->Delete($query);
|
67 |
|
68 |
-
if ($deletedCount == 0)
|
|
|
|
|
69 |
// keep track of what we're doing
|
70 |
$this->plugin->alerts->Trigger(0003, array(
|
71 |
'Message' => 'Running system cleanup.',
|
@@ -77,6 +103,10 @@ class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
|
77 |
do_action('wsal_prune', $deletedCount, vsprintf($result['sql'], $result['args']));
|
78 |
}
|
79 |
|
|
|
|
|
|
|
|
|
80 |
private function AlertInject($occurrence)
|
81 |
{
|
82 |
$count = $this->CheckPromoToShow();
|
@@ -96,6 +126,11 @@ class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
|
96 |
}
|
97 |
}
|
98 |
|
|
|
|
|
|
|
|
|
|
|
99 |
private function GetPromoAlert()
|
100 |
{
|
101 |
$lastPromoSentId = $this->plugin->GetGlobalOption('promo-send-id');
|
@@ -115,6 +150,10 @@ class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
|
115 |
return $promoToSend;
|
116 |
}
|
117 |
|
|
|
|
|
|
|
|
|
118 |
private function GetActivePromoText()
|
119 |
{
|
120 |
$aPromoAlerts = array();
|
@@ -136,6 +175,10 @@ class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
|
136 |
return $aPromoAlerts;
|
137 |
}
|
138 |
|
|
|
|
|
|
|
|
|
139 |
private function CheckPromoToShow()
|
140 |
{
|
141 |
$promoToShow = null;
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* Loggers Class.
|
5 |
+
*
|
6 |
+
* This class store the logs in the Database and adds the promo
|
7 |
+
* alerts, there is also the function to clean up alerts.
|
8 |
+
*/
|
9 |
class WSAL_Loggers_Database extends WSAL_AbstractLogger
|
10 |
{
|
|
|
11 |
public function __construct(WpSecurityAuditLog $plugin)
|
12 |
{
|
13 |
parent::__construct($plugin);
|
14 |
$plugin->AddCleanupHook(array($this, 'CleanUp'));
|
15 |
}
|
16 |
|
17 |
+
/**
|
18 |
+
* Log alert.
|
19 |
+
* @param integer $type alert code
|
20 |
+
* @param array $data Metadata
|
21 |
+
* @param integer $date (Optional) created_on
|
22 |
+
* @param integer $siteid (Optional) site_id
|
23 |
+
* @param bool $migrated (Optional) is_migrated
|
24 |
+
*/
|
25 |
public function Log($type, $data = array(), $date = null, $siteid = null, $migrated = false)
|
26 |
{
|
27 |
// is this a php alert, and if so, are we logging such alerts?
|
28 |
+
if ($type < 0010 && !$this->plugin->settings->IsPhpErrorLoggingEnabled()) {
|
29 |
+
return;
|
30 |
+
}
|
31 |
|
32 |
// create new occurrence
|
33 |
$occ = new WSAL_Models_Occurrence();
|
47 |
}
|
48 |
}
|
49 |
|
50 |
+
/**
|
51 |
+
* Clean Up alerts by date OR by max number.
|
52 |
+
*/
|
53 |
public function CleanUp()
|
54 |
{
|
55 |
$now = current_time('timestamp');
|
75 |
$query = new WSAL_Models_OccurrenceQuery();
|
76 |
$query->addOrderBy("created_on", false);
|
77 |
// TO DO Fixing data
|
78 |
+
if ($is_date_e) {
|
79 |
+
$query->addCondition('created_on <= %s', intval($max_stamp));
|
80 |
+
}
|
81 |
+
if ($is_limt_e) {
|
82 |
+
$query->setLimit($max_items);
|
83 |
+
}
|
84 |
|
85 |
+
if (($max_items-1) == 0) {
|
86 |
+
return; // nothing to delete
|
87 |
+
}
|
88 |
|
89 |
$result = $query->getAdapter()->GetSqlDelete($query);
|
90 |
$deletedCount = $query->getAdapter()->Delete($query);
|
91 |
|
92 |
+
if ($deletedCount == 0) {
|
93 |
+
return; // nothing to delete
|
94 |
+
}
|
95 |
// keep track of what we're doing
|
96 |
$this->plugin->alerts->Trigger(0003, array(
|
97 |
'Message' => 'Running system cleanup.',
|
103 |
do_action('wsal_prune', $deletedCount, vsprintf($result['sql'], $result['args']));
|
104 |
}
|
105 |
|
106 |
+
/**
|
107 |
+
* Inject Promo alert every $count alerts if no Add-ons are activated.
|
108 |
+
* @param WSAL_Models_Occurrence $occurrence occurrence
|
109 |
+
*/
|
110 |
private function AlertInject($occurrence)
|
111 |
{
|
112 |
$count = $this->CheckPromoToShow();
|
126 |
}
|
127 |
}
|
128 |
|
129 |
+
/**
|
130 |
+
* Get the promo id, to send each time a different promo,
|
131 |
+
* keeping the last id saved in the DB.
|
132 |
+
* @return integer $promoToSend the array index
|
133 |
+
*/
|
134 |
private function GetPromoAlert()
|
135 |
{
|
136 |
$lastPromoSentId = $this->plugin->GetGlobalOption('promo-send-id');
|
150 |
return $promoToSend;
|
151 |
}
|
152 |
|
153 |
+
/**
|
154 |
+
* Array of promo.
|
155 |
+
* @return array $aPromoAlerts the array of promo
|
156 |
+
*/
|
157 |
private function GetActivePromoText()
|
158 |
{
|
159 |
$aPromoAlerts = array();
|
175 |
return $aPromoAlerts;
|
176 |
}
|
177 |
|
178 |
+
/**
|
179 |
+
* Check condition to show promo.
|
180 |
+
* @return integer|null counter alert
|
181 |
+
*/
|
182 |
private function CheckPromoToShow()
|
183 |
{
|
184 |
$promoToShow = null;
|
classes/Models/ActiveRecord.php
CHANGED
@@ -1,11 +1,20 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
|
|
|
|
|
|
|
|
4 |
abstract class WSAL_Models_ActiveRecord
|
5 |
{
|
|
|
|
|
|
|
|
|
|
|
6 |
|
7 |
/**
|
8 |
-
* @
|
9 |
*/
|
10 |
protected $connector;
|
11 |
|
@@ -14,39 +23,48 @@ abstract class WSAL_Models_ActiveRecord
|
|
14 |
protected $adapterName = null;
|
15 |
|
16 |
protected $useDefaultAdapter = false;
|
|
|
|
|
|
|
|
|
17 |
|
18 |
/**
|
19 |
* @return array Returns this records' fields.
|
20 |
*/
|
21 |
public function GetFields()
|
22 |
{
|
23 |
-
if(!isset($this->_column_cache)){
|
24 |
$this->_column_cache = array();
|
25 |
-
foreach(array_keys(get_object_vars($this)) as $col)
|
26 |
-
if(trim($col) && $col[0] != '_')
|
27 |
$this->_column_cache[] = $col;
|
|
|
|
|
28 |
}
|
29 |
return $this->_column_cache;
|
30 |
}
|
31 |
|
|
|
|
|
|
|
|
|
32 |
public function setId($id)
|
33 |
{
|
34 |
$this->id = $id;
|
35 |
}
|
36 |
|
|
|
|
|
|
|
|
|
37 |
public function getId()
|
38 |
{
|
39 |
return $this->id;
|
40 |
}
|
41 |
-
|
42 |
-
const STATE_UNKNOWN = 'unknown';
|
43 |
-
const STATE_CREATED = 'created';
|
44 |
-
const STATE_UPDATED = 'updated';
|
45 |
-
const STATE_DELETED = 'deleted';
|
46 |
-
const STATE_LOADED = 'loaded';
|
47 |
-
|
48 |
-
protected $_state = self::STATE_UNKNOWN;
|
49 |
|
|
|
|
|
|
|
50 |
public function __construct($data = null)
|
51 |
{
|
52 |
if (!$this->adapterName) {
|
@@ -58,6 +76,10 @@ abstract class WSAL_Models_ActiveRecord
|
|
58 |
}
|
59 |
}
|
60 |
|
|
|
|
|
|
|
|
|
61 |
protected function getConnector()
|
62 |
{
|
63 |
if (!empty($this->connector)) {
|
@@ -71,22 +93,28 @@ abstract class WSAL_Models_ActiveRecord
|
|
71 |
return $this->connector;
|
72 |
}
|
73 |
|
|
|
|
|
|
|
|
|
|
|
74 |
public function getAdapter()
|
75 |
{
|
76 |
return $this->getConnector()->getAdapter($this->adapterName);
|
77 |
}
|
78 |
|
79 |
-
|
80 |
/**
|
81 |
* Load record from DB.
|
|
|
82 |
* @param string $cond (Optional) Load condition.
|
83 |
* @param array $args (Optional) Load condition arguments.
|
84 |
*/
|
85 |
-
public function Load($cond = '%d', $args = array(1))
|
|
|
86 |
$this->_state = self::STATE_UNKNOWN;
|
87 |
|
88 |
$data = $this->getAdapter()->Load($cond, $args);
|
89 |
-
if(!is_null($data)){
|
90 |
$this->LoadData($data);
|
91 |
$this->_state = self::STATE_LOADED;
|
92 |
}
|
@@ -96,7 +124,8 @@ abstract class WSAL_Models_ActiveRecord
|
|
96 |
* Load object data from variable.
|
97 |
* @param array|object $data Data array or object.
|
98 |
*/
|
99 |
-
public function LoadData($data)
|
|
|
100 |
$copy = get_class($this);
|
101 |
$copy = new $copy;
|
102 |
foreach ((array)$data as $key => $val) {
|
@@ -132,6 +161,7 @@ abstract class WSAL_Models_ActiveRecord
|
|
132 |
|
133 |
/**
|
134 |
* Save this active record
|
|
|
135 |
* @return integer|boolean Either the number of modified/inserted rows or false on failure.
|
136 |
*/
|
137 |
public function Save()
|
@@ -152,47 +182,63 @@ abstract class WSAL_Models_ActiveRecord
|
|
152 |
}
|
153 |
|
154 |
/**
|
155 |
-
* Deletes this active record
|
|
|
|
|
156 |
*/
|
157 |
public function Delete()
|
158 |
{
|
159 |
$this->_state = self::STATE_UNKNOWN;
|
160 |
$result = $this->getAdapter()->Delete($this);
|
161 |
-
if($result !== false)
|
162 |
$this->_state = self::STATE_DELETED;
|
|
|
163 |
|
164 |
return $result;
|
165 |
}
|
166 |
|
167 |
-
|
168 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
169 |
return $result;
|
170 |
}
|
171 |
|
172 |
/**
|
173 |
-
*
|
|
|
174 |
*/
|
175 |
-
public function IsLoaded()
|
|
|
176 |
return $this->_state == self::STATE_LOADED;
|
177 |
}
|
178 |
|
179 |
/**
|
180 |
-
*
|
|
|
181 |
*/
|
182 |
-
public function IsSaved()
|
|
|
183 |
return $this->_state == self::STATE_CREATED
|
184 |
|| $this->_state == self::STATE_UPDATED;
|
185 |
}
|
186 |
|
187 |
/**
|
188 |
-
*
|
|
|
189 |
*/
|
190 |
-
public function IsCreated()
|
|
|
191 |
return $this->_state == self::STATE_CREATED;
|
192 |
}
|
193 |
|
194 |
/**
|
195 |
-
*
|
|
|
196 |
*/
|
197 |
public function IsUpdated()
|
198 |
{
|
@@ -200,28 +246,33 @@ abstract class WSAL_Models_ActiveRecord
|
|
200 |
}
|
201 |
|
202 |
/**
|
203 |
-
*
|
|
|
|
|
204 |
*/
|
205 |
public function IsInstalled()
|
206 |
{
|
207 |
return $this->getAdapter()->IsInstalled();
|
208 |
}
|
209 |
|
|
|
|
|
|
|
|
|
210 |
public function Install()
|
211 |
{
|
212 |
return $this->getAdapter()->Install();
|
213 |
}
|
214 |
|
215 |
/**
|
216 |
-
*
|
|
|
217 |
*/
|
218 |
public function IsDeleted()
|
219 |
{
|
220 |
return $this->_state == self::STATE_DELETED;
|
221 |
}
|
222 |
|
223 |
-
protected static $_cache = array();
|
224 |
-
|
225 |
/**
|
226 |
* Load ActiveRecord from DB or cache.
|
227 |
* @param string $target ActiveRecord class name.
|
@@ -229,9 +280,10 @@ abstract class WSAL_Models_ActiveRecord
|
|
229 |
* @param array $args Arguments used in condition.
|
230 |
* @return WSAL_Models_ActiveRecord
|
231 |
*/
|
232 |
-
protected static function CacheLoad($target, $query, $args)
|
|
|
233 |
$index = $target . '::' . vsprintf($query, $args);
|
234 |
-
if(!isset(self::$_cache[$index])){
|
235 |
self::$_cache[$index] = new $target();
|
236 |
self::$_cache[$index]->Load($query, $args);
|
237 |
}
|
@@ -244,9 +296,10 @@ abstract class WSAL_Models_ActiveRecord
|
|
244 |
* @param string $query Load condition.
|
245 |
* @param array $args Arguments used in condition.
|
246 |
*/
|
247 |
-
protected static function CacheRemove($target, $query, $args)
|
|
|
248 |
$index = $target . '::' . sprintf($query, $args);
|
249 |
-
if(!isset(self::$_cache[$index])){
|
250 |
unset(self::$_cache[$index]);
|
251 |
}
|
252 |
}
|
@@ -260,7 +313,15 @@ abstract class WSAL_Models_ActiveRecord
|
|
260 |
}
|
261 |
|
262 |
/**
|
263 |
-
* Function used in WSAL reporting extension
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
264 |
*/
|
265 |
public function GetReporting($_siteId, $_userId, $_roleName, $_alertCode, $_startTimestamp, $_endTimestamp)
|
266 |
{
|
@@ -268,7 +329,10 @@ abstract class WSAL_Models_ActiveRecord
|
|
268 |
}
|
269 |
|
270 |
/**
|
271 |
-
* Check if the float is IPv4 instead
|
|
|
|
|
|
|
272 |
*/
|
273 |
private function is_ip_address($ip_address)
|
274 |
{
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Abstract ActiveRecord model is the generic model for any kind
|
6 |
+
* of adapter.
|
7 |
+
*/
|
8 |
abstract class WSAL_Models_ActiveRecord
|
9 |
{
|
10 |
+
const STATE_UNKNOWN = 'unknown';
|
11 |
+
const STATE_CREATED = 'created';
|
12 |
+
const STATE_UPDATED = 'updated';
|
13 |
+
const STATE_DELETED = 'deleted';
|
14 |
+
const STATE_LOADED = 'loaded';
|
15 |
|
16 |
/**
|
17 |
+
* @var $connector Data connector;
|
18 |
*/
|
19 |
protected $connector;
|
20 |
|
23 |
protected $adapterName = null;
|
24 |
|
25 |
protected $useDefaultAdapter = false;
|
26 |
+
|
27 |
+
protected $_state = self::STATE_UNKNOWN;
|
28 |
+
|
29 |
+
protected static $_cache = array();
|
30 |
|
31 |
/**
|
32 |
* @return array Returns this records' fields.
|
33 |
*/
|
34 |
public function GetFields()
|
35 |
{
|
36 |
+
if (!isset($this->_column_cache)) {
|
37 |
$this->_column_cache = array();
|
38 |
+
foreach (array_keys(get_object_vars($this)) as $col) {
|
39 |
+
if (trim($col) && $col[0] != '_') {
|
40 |
$this->_column_cache[] = $col;
|
41 |
+
}
|
42 |
+
}
|
43 |
}
|
44 |
return $this->_column_cache;
|
45 |
}
|
46 |
|
47 |
+
/**
|
48 |
+
* Sets the id.
|
49 |
+
* @param integer $id
|
50 |
+
*/
|
51 |
public function setId($id)
|
52 |
{
|
53 |
$this->id = $id;
|
54 |
}
|
55 |
|
56 |
+
/**
|
57 |
+
* Gets the id.
|
58 |
+
* @return integer $id.
|
59 |
+
*/
|
60 |
public function getId()
|
61 |
{
|
62 |
return $this->id;
|
63 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
64 |
|
65 |
+
/**
|
66 |
+
* @throws Exception requires adapterName
|
67 |
+
*/
|
68 |
public function __construct($data = null)
|
69 |
{
|
70 |
if (!$this->adapterName) {
|
76 |
}
|
77 |
}
|
78 |
|
79 |
+
/**
|
80 |
+
* Gets the connector.
|
81 |
+
* @return WSAL_Connector_ConnectorInterface
|
82 |
+
*/
|
83 |
protected function getConnector()
|
84 |
{
|
85 |
if (!empty($this->connector)) {
|
93 |
return $this->connector;
|
94 |
}
|
95 |
|
96 |
+
/**
|
97 |
+
* Gets an adapter for the specified model
|
98 |
+
* based on the adapter name.
|
99 |
+
* @see WSAL_Connector_ConnectorInterface::getAdapter()
|
100 |
+
*/
|
101 |
public function getAdapter()
|
102 |
{
|
103 |
return $this->getConnector()->getAdapter($this->adapterName);
|
104 |
}
|
105 |
|
|
|
106 |
/**
|
107 |
* Load record from DB.
|
108 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Load()
|
109 |
* @param string $cond (Optional) Load condition.
|
110 |
* @param array $args (Optional) Load condition arguments.
|
111 |
*/
|
112 |
+
public function Load($cond = '%d', $args = array(1))
|
113 |
+
{
|
114 |
$this->_state = self::STATE_UNKNOWN;
|
115 |
|
116 |
$data = $this->getAdapter()->Load($cond, $args);
|
117 |
+
if (!is_null($data)) {
|
118 |
$this->LoadData($data);
|
119 |
$this->_state = self::STATE_LOADED;
|
120 |
}
|
124 |
* Load object data from variable.
|
125 |
* @param array|object $data Data array or object.
|
126 |
*/
|
127 |
+
public function LoadData($data)
|
128 |
+
{
|
129 |
$copy = get_class($this);
|
130 |
$copy = new $copy;
|
131 |
foreach ((array)$data as $key => $val) {
|
161 |
|
162 |
/**
|
163 |
* Save this active record
|
164 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Save()
|
165 |
* @return integer|boolean Either the number of modified/inserted rows or false on failure.
|
166 |
*/
|
167 |
public function Save()
|
182 |
}
|
183 |
|
184 |
/**
|
185 |
+
* Deletes this active record.
|
186 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Delete()
|
187 |
+
* @return int|boolean Either the amount of deleted rows or False on error.
|
188 |
*/
|
189 |
public function Delete()
|
190 |
{
|
191 |
$this->_state = self::STATE_UNKNOWN;
|
192 |
$result = $this->getAdapter()->Delete($this);
|
193 |
+
if ($result !== false) {
|
194 |
$this->_state = self::STATE_DELETED;
|
195 |
+
}
|
196 |
|
197 |
return $result;
|
198 |
}
|
199 |
|
200 |
+
/**
|
201 |
+
* Count records that matching a condition.
|
202 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Count()
|
203 |
+
* @return int count
|
204 |
+
*/
|
205 |
+
public function Count($cond = '%d', $args = array(1))
|
206 |
+
{
|
207 |
+
$result = $this->getAdapter()->Count($cond, $args);
|
208 |
return $result;
|
209 |
}
|
210 |
|
211 |
/**
|
212 |
+
* Check state loaded.
|
213 |
+
* @return bool
|
214 |
*/
|
215 |
+
public function IsLoaded()
|
216 |
+
{
|
217 |
return $this->_state == self::STATE_LOADED;
|
218 |
}
|
219 |
|
220 |
/**
|
221 |
+
* Check state saved.
|
222 |
+
* @return bool
|
223 |
*/
|
224 |
+
public function IsSaved()
|
225 |
+
{
|
226 |
return $this->_state == self::STATE_CREATED
|
227 |
|| $this->_state == self::STATE_UPDATED;
|
228 |
}
|
229 |
|
230 |
/**
|
231 |
+
* Check state created.
|
232 |
+
* @return bool
|
233 |
*/
|
234 |
+
public function IsCreated()
|
235 |
+
{
|
236 |
return $this->_state == self::STATE_CREATED;
|
237 |
}
|
238 |
|
239 |
/**
|
240 |
+
* Check state updated.
|
241 |
+
* @return bool
|
242 |
*/
|
243 |
public function IsUpdated()
|
244 |
{
|
246 |
}
|
247 |
|
248 |
/**
|
249 |
+
* Check if the Record structure is created.
|
250 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::IsInstalled()
|
251 |
+
* @return bool
|
252 |
*/
|
253 |
public function IsInstalled()
|
254 |
{
|
255 |
return $this->getAdapter()->IsInstalled();
|
256 |
}
|
257 |
|
258 |
+
/**
|
259 |
+
* Install the Record structure.
|
260 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Install()
|
261 |
+
*/
|
262 |
public function Install()
|
263 |
{
|
264 |
return $this->getAdapter()->Install();
|
265 |
}
|
266 |
|
267 |
/**
|
268 |
+
* Check state deleted.
|
269 |
+
* @return bool
|
270 |
*/
|
271 |
public function IsDeleted()
|
272 |
{
|
273 |
return $this->_state == self::STATE_DELETED;
|
274 |
}
|
275 |
|
|
|
|
|
276 |
/**
|
277 |
* Load ActiveRecord from DB or cache.
|
278 |
* @param string $target ActiveRecord class name.
|
280 |
* @param array $args Arguments used in condition.
|
281 |
* @return WSAL_Models_ActiveRecord
|
282 |
*/
|
283 |
+
protected static function CacheLoad($target, $query, $args)
|
284 |
+
{
|
285 |
$index = $target . '::' . vsprintf($query, $args);
|
286 |
+
if (!isset(self::$_cache[$index])) {
|
287 |
self::$_cache[$index] = new $target();
|
288 |
self::$_cache[$index]->Load($query, $args);
|
289 |
}
|
296 |
* @param string $query Load condition.
|
297 |
* @param array $args Arguments used in condition.
|
298 |
*/
|
299 |
+
protected static function CacheRemove($target, $query, $args)
|
300 |
+
{
|
301 |
$index = $target . '::' . sprintf($query, $args);
|
302 |
+
if (!isset(self::$_cache[$index])) {
|
303 |
unset(self::$_cache[$index]);
|
304 |
}
|
305 |
}
|
313 |
}
|
314 |
|
315 |
/**
|
316 |
+
* Function used in WSAL reporting extension.
|
317 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::GetReporting()
|
318 |
+
* @param int $_siteId site ID
|
319 |
+
* @param int $_userId user ID
|
320 |
+
* @param string $_roleName user role
|
321 |
+
* @param int $_alertCode alert code
|
322 |
+
* @param timestamp $_startTimestamp from created_on
|
323 |
+
* @param timestamp $_endTimestamp to created_on
|
324 |
+
* @return array Report results
|
325 |
*/
|
326 |
public function GetReporting($_siteId, $_userId, $_roleName, $_alertCode, $_startTimestamp, $_endTimestamp)
|
327 |
{
|
329 |
}
|
330 |
|
331 |
/**
|
332 |
+
* Check if the float is IPv4 instead.
|
333 |
+
* @see WSAL_Models_ActiveRecord::LoadData()
|
334 |
+
* @param float $ip_address number to check
|
335 |
+
* @return bool result validation
|
336 |
*/
|
337 |
private function is_ip_address($ip_address)
|
338 |
{
|
classes/Models/Meta.php
CHANGED
@@ -1,15 +1,24 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
public $name = '';
|
10 |
-
public $value = array(); // force mixed type
|
11 |
-
|
12 |
-
public function SaveMeta()
|
13 |
{
|
14 |
$this->_state = self::STATE_UNKNOWN;
|
15 |
$updateId = $this->getId();
|
@@ -21,6 +30,13 @@ class WSAL_Models_Meta extends WSAL_Models_ActiveRecord {
|
|
21 |
return $result;
|
22 |
}
|
23 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
24 |
public function UpdateByNameAndOccurenceId($name, $value, $occurrenceId)
|
25 |
{
|
26 |
$meta = $this->getAdapter()->LoadByNameAndOccurenceId($name, $occurrenceId);
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Metadata model is the model for the Metadata adapter,
|
6 |
+
* used for save and update the metadata.
|
7 |
+
*/
|
8 |
+
class WSAL_Models_Meta extends WSAL_Models_ActiveRecord
|
9 |
+
{
|
10 |
+
public $id = 0;
|
11 |
+
public $occurrence_id = 0;
|
12 |
+
public $name = '';
|
13 |
+
public $value = array(); // force mixed type
|
14 |
+
protected $adapterName = "Meta";
|
15 |
|
16 |
+
/**
|
17 |
+
* Save Metadata into Adapter.
|
18 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Save()
|
19 |
+
* @return integer|boolean Either the number of modified/inserted rows or false on failure.
|
20 |
+
*/
|
21 |
+
public function SaveMeta()
|
|
|
|
|
|
|
|
|
22 |
{
|
23 |
$this->_state = self::STATE_UNKNOWN;
|
24 |
$updateId = $this->getId();
|
30 |
return $result;
|
31 |
}
|
32 |
|
33 |
+
/**
|
34 |
+
* Update Metadata by name and occurrence_id.
|
35 |
+
* @see WSAL_Adapters_MySQL_Meta::LoadByNameAndOccurenceId()
|
36 |
+
* @param string $name meta name
|
37 |
+
* @param mixed $value meta value
|
38 |
+
* @param integer $occurrenceId occurrence_id
|
39 |
+
*/
|
40 |
public function UpdateByNameAndOccurenceId($name, $value, $occurrenceId)
|
41 |
{
|
42 |
$meta = $this->getAdapter()->LoadByNameAndOccurenceId($name, $occurrenceId);
|
classes/Models/Occurrence.php
CHANGED
@@ -1,5 +1,10 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
4 |
{
|
5 |
public $id = 0;
|
@@ -12,6 +17,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
12 |
|
13 |
/**
|
14 |
* Returns the alert related to this occurrence.
|
|
|
15 |
* @return WSAL_Alert
|
16 |
*/
|
17 |
public function GetAlert()
|
@@ -21,6 +27,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
21 |
|
22 |
/**
|
23 |
* Returns the value of a meta item.
|
|
|
24 |
* @param string $name Name of meta item.
|
25 |
* @param mixed $default Default value returned when meta does not exist.
|
26 |
* @return mixed The value, if meta item does not exist $default returned.
|
@@ -28,7 +35,6 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
28 |
public function GetMetaValue($name, $default = array())
|
29 |
{
|
30 |
//get meta adapter
|
31 |
-
//call the function ($name, $this->getId())
|
32 |
$meta = $this->getAdapter()->GetNamedMeta($this, $name);
|
33 |
return maybe_unserialize($meta['value']);
|
34 |
|
@@ -37,7 +43,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
37 |
}
|
38 |
|
39 |
/**
|
40 |
-
*
|
41 |
* @param string $name Meta name.
|
42 |
* @param mixed $value Meta value.
|
43 |
*/
|
@@ -53,6 +59,12 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
53 |
}
|
54 |
}
|
55 |
|
|
|
|
|
|
|
|
|
|
|
|
|
56 |
public function UpdateMetaValue($name, $value)
|
57 |
{
|
58 |
$model = new WSAL_Models_Meta();
|
@@ -61,6 +73,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
61 |
|
62 |
/**
|
63 |
* Returns a key-value pair of meta data.
|
|
|
64 |
* @return array
|
65 |
*/
|
66 |
public function GetMetaArray()
|
@@ -85,6 +98,8 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
85 |
}
|
86 |
|
87 |
/**
|
|
|
|
|
88 |
* @param callable|null $metaFormatter (Optional) Meta formatter callback.
|
89 |
* @return string Full-formatted message.
|
90 |
*/
|
@@ -106,6 +121,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
106 |
|
107 |
/**
|
108 |
* Delete occurrence as well as associated meta data.
|
|
|
109 |
* @return boolean True on success, false on failure.
|
110 |
*/
|
111 |
public function Delete()
|
@@ -117,6 +133,8 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
117 |
}
|
118 |
|
119 |
/**
|
|
|
|
|
120 |
* @return string User's username.
|
121 |
*/
|
122 |
public function GetUsername()
|
@@ -134,6 +152,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
134 |
}
|
135 |
|
136 |
/**
|
|
|
137 |
* @return string IP address of request.
|
138 |
*/
|
139 |
public function GetSourceIP()
|
@@ -142,6 +161,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
142 |
}
|
143 |
|
144 |
/**
|
|
|
145 |
* @return string IP address of request (from proxies etc).
|
146 |
*/
|
147 |
public function GetOtherIPs()
|
@@ -157,6 +177,7 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
157 |
}
|
158 |
|
159 |
/**
|
|
|
160 |
* @return array Array of user roles.
|
161 |
*/
|
162 |
public function GetUserRoles()
|
@@ -174,29 +195,56 @@ class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
|
174 |
}
|
175 |
|
176 |
/**
|
177 |
-
* Finds occurences of the same type by IP and Username within specified time frame
|
178 |
* @param string $ipAddress
|
179 |
* @param string $username
|
180 |
* @param int $alertId Alert type we are lookign for
|
181 |
* @param int $siteId
|
182 |
* @param $startTime mktime
|
183 |
* @param $endTime mktime
|
|
|
184 |
*/
|
185 |
public function CheckKnownUsers($args = array())
|
186 |
{
|
187 |
return $this->getAdapter()->CheckKnownUsers($args);
|
188 |
}
|
189 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
190 |
public function CheckUnKnownUsers($args = array())
|
191 |
{
|
192 |
return $this->getAdapter()->CheckUnKnownUsers($args);
|
193 |
}
|
194 |
|
|
|
|
|
|
|
|
|
|
|
|
|
195 |
public function GetByPostID($post_id)
|
196 |
{
|
197 |
return $this->getAdapter()->GetByPostID($post_id);
|
198 |
}
|
199 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
200 |
public function CheckAlert404($args = array())
|
201 |
{
|
202 |
return $this->getAdapter()->CheckAlert404($args);
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Occurrence model is the model for the Occurrence adapter,
|
6 |
+
* used for get the alert, set the meta fields, etc.
|
7 |
+
*/
|
8 |
class WSAL_Models_Occurrence extends WSAL_Models_ActiveRecord
|
9 |
{
|
10 |
public $id = 0;
|
17 |
|
18 |
/**
|
19 |
* Returns the alert related to this occurrence.
|
20 |
+
* @see WSAL_AlertManager::GetAlert()
|
21 |
* @return WSAL_Alert
|
22 |
*/
|
23 |
public function GetAlert()
|
27 |
|
28 |
/**
|
29 |
* Returns the value of a meta item.
|
30 |
+
* @see WSAL_Adapters_MySQL_Occurrence::GetNamedMeta()
|
31 |
* @param string $name Name of meta item.
|
32 |
* @param mixed $default Default value returned when meta does not exist.
|
33 |
* @return mixed The value, if meta item does not exist $default returned.
|
35 |
public function GetMetaValue($name, $default = array())
|
36 |
{
|
37 |
//get meta adapter
|
|
|
38 |
$meta = $this->getAdapter()->GetNamedMeta($this, $name);
|
39 |
return maybe_unserialize($meta['value']);
|
40 |
|
43 |
}
|
44 |
|
45 |
/**
|
46 |
+
* Sets the value of a meta item (creates or updates meta item).
|
47 |
* @param string $name Meta name.
|
48 |
* @param mixed $value Meta value.
|
49 |
*/
|
59 |
}
|
60 |
}
|
61 |
|
62 |
+
/**
|
63 |
+
* Update Metadata of this occurrence by name.
|
64 |
+
* @see WSAL_Models_Meta::UpdateByNameAndOccurenceId()
|
65 |
+
* @param string $name meta name
|
66 |
+
* @param mixed $value meta value
|
67 |
+
*/
|
68 |
public function UpdateMetaValue($name, $value)
|
69 |
{
|
70 |
$model = new WSAL_Models_Meta();
|
73 |
|
74 |
/**
|
75 |
* Returns a key-value pair of meta data.
|
76 |
+
* @see WSAL_Adapters_MySQL_Occurrence::GetMultiMeta()
|
77 |
* @return array
|
78 |
*/
|
79 |
public function GetMetaArray()
|
98 |
}
|
99 |
|
100 |
/**
|
101 |
+
* Gets alert message.
|
102 |
+
* @see WSAL_Alert::GetMessage()
|
103 |
* @param callable|null $metaFormatter (Optional) Meta formatter callback.
|
104 |
* @return string Full-formatted message.
|
105 |
*/
|
121 |
|
122 |
/**
|
123 |
* Delete occurrence as well as associated meta data.
|
124 |
+
* @see WSAL_Adapters_ActiveRecordInterface::Delete()
|
125 |
* @return boolean True on success, false on failure.
|
126 |
*/
|
127 |
public function Delete()
|
133 |
}
|
134 |
|
135 |
/**
|
136 |
+
* Gets the username.
|
137 |
+
* @see WSAL_Adapters_MySQL_Occurrence::GetFirstNamedMeta()
|
138 |
* @return string User's username.
|
139 |
*/
|
140 |
public function GetUsername()
|
152 |
}
|
153 |
|
154 |
/**
|
155 |
+
* Gets the Client IP.
|
156 |
* @return string IP address of request.
|
157 |
*/
|
158 |
public function GetSourceIP()
|
161 |
}
|
162 |
|
163 |
/**
|
164 |
+
* Gets if there are other IPs.
|
165 |
* @return string IP address of request (from proxies etc).
|
166 |
*/
|
167 |
public function GetOtherIPs()
|
177 |
}
|
178 |
|
179 |
/**
|
180 |
+
* Gets user roles.
|
181 |
* @return array Array of user roles.
|
182 |
*/
|
183 |
public function GetUserRoles()
|
195 |
}
|
196 |
|
197 |
/**
|
198 |
+
* Finds occurences of the same type by IP and Username within specified time frame.
|
199 |
* @param string $ipAddress
|
200 |
* @param string $username
|
201 |
* @param int $alertId Alert type we are lookign for
|
202 |
* @param int $siteId
|
203 |
* @param $startTime mktime
|
204 |
* @param $endTime mktime
|
205 |
+
* @return WSAL_Occurrence[]
|
206 |
*/
|
207 |
public function CheckKnownUsers($args = array())
|
208 |
{
|
209 |
return $this->getAdapter()->CheckKnownUsers($args);
|
210 |
}
|
211 |
|
212 |
+
/**
|
213 |
+
* Finds occurences of the same type by IP within specified time frame.
|
214 |
+
* @param string $ipAddress
|
215 |
+
* @param int $alertId Alert type we are lookign for
|
216 |
+
* @param int $siteId
|
217 |
+
* @param $startTime mktime
|
218 |
+
* @param $endTime mktime
|
219 |
+
* @return WSAL_Occurrence[]
|
220 |
+
*/
|
221 |
public function CheckUnKnownUsers($args = array())
|
222 |
{
|
223 |
return $this->getAdapter()->CheckUnKnownUsers($args);
|
224 |
}
|
225 |
|
226 |
+
/**
|
227 |
+
* Gets occurrence by Post_id
|
228 |
+
* @see WSAL_Adapters_MySQL_Occurrence::GetByPostID()
|
229 |
+
* @param integer $post_id
|
230 |
+
* @return WSAL_Occurrence[]
|
231 |
+
*/
|
232 |
public function GetByPostID($post_id)
|
233 |
{
|
234 |
return $this->getAdapter()->GetByPostID($post_id);
|
235 |
}
|
236 |
|
237 |
+
/**
|
238 |
+
* Gets occurences of the same type by IP within specified time frame.
|
239 |
+
* @see WSAL_Adapters_MySQL_Occurrence::CheckAlert404()
|
240 |
+
* @param string $ipAddress
|
241 |
+
* @param string $username
|
242 |
+
* @param int $alertId Alert type we are lookign for
|
243 |
+
* @param int $siteId
|
244 |
+
* @param $startTime mktime
|
245 |
+
* @param $endTime mktime
|
246 |
+
* @return WSAL_Occurrence[]
|
247 |
+
*/
|
248 |
public function CheckAlert404($args = array())
|
249 |
{
|
250 |
return $this->getAdapter()->CheckAlert404($args);
|
classes/Models/OccurrenceQuery.php
CHANGED
@@ -1,15 +1,29 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Models_OccurrenceQuery extends WSAL_Models_Query
|
4 |
{
|
5 |
protected $arguments = array();
|
6 |
|
|
|
|
|
|
|
|
|
|
|
|
|
7 |
public function addArgument($field, $value)
|
8 |
{
|
9 |
$this->arguments[$field] = $value;
|
10 |
return $this;
|
11 |
}
|
12 |
|
|
|
|
|
|
|
|
|
13 |
public function clearArguments()
|
14 |
{
|
15 |
$this->arguments = array();
|
@@ -25,5 +39,4 @@ class WSAL_Models_OccurrenceQuery extends WSAL_Models_Query
|
|
25 |
$this->getConnector()->getAdapter("Occurrence")->GetTable()
|
26 |
);
|
27 |
}
|
28 |
-
|
29 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* OccurrenceQuery model adds or clears arguments in the Query model.
|
6 |
+
*/
|
7 |
class WSAL_Models_OccurrenceQuery extends WSAL_Models_Query
|
8 |
{
|
9 |
protected $arguments = array();
|
10 |
|
11 |
+
/**
|
12 |
+
* Sets arguments.
|
13 |
+
* @param string $field name field
|
14 |
+
* @param mixed $value value
|
15 |
+
* @return self
|
16 |
+
*/
|
17 |
public function addArgument($field, $value)
|
18 |
{
|
19 |
$this->arguments[$field] = $value;
|
20 |
return $this;
|
21 |
}
|
22 |
|
23 |
+
/**
|
24 |
+
* Resets arguments.
|
25 |
+
* @return self
|
26 |
+
*/
|
27 |
public function clearArguments()
|
28 |
{
|
29 |
$this->arguments = array();
|
39 |
$this->getConnector()->getAdapter("Occurrence")->GetTable()
|
40 |
);
|
41 |
}
|
|
|
42 |
}
|
classes/Models/Option.php
CHANGED
@@ -1,20 +1,27 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
/**
|
|
|
4 |
* Wordpress options are always loaded from the default wordpress database.
|
|
|
|
|
5 |
*/
|
6 |
class WSAL_Models_Option extends WSAL_Models_ActiveRecord
|
7 |
{
|
8 |
-
|
9 |
-
protected $adapterName = "Option";
|
10 |
public $id = '';
|
11 |
public $option_name = '';
|
12 |
public $option_value = '';
|
|
|
|
|
13 |
/**
|
14 |
* Options are always stored in WPDB. This setting ensures that
|
15 |
*/
|
16 |
protected $useDefaultAdapter = true;
|
17 |
|
|
|
|
|
|
|
|
|
|
|
18 |
public function SetOptionValue($name, $value)
|
19 |
{
|
20 |
$option = $this->getAdapter()->GetNamedOption($name);
|
@@ -26,9 +33,15 @@ class WSAL_Models_Option extends WSAL_Models_ActiveRecord
|
|
26 |
return $this->Save();
|
27 |
}
|
28 |
|
|
|
|
|
|
|
|
|
|
|
|
|
29 |
public function GetOptionValue($name, $default = array())
|
30 |
{
|
31 |
-
$option = $this->getAdapter()->GetNamedOption($name);
|
32 |
$this->option_value = (!empty($option)) ? $option['option_value'] : null;
|
33 |
if (!empty($this->option_value)) {
|
34 |
$this->_state = self::STATE_LOADED;
|
@@ -38,6 +51,11 @@ class WSAL_Models_Option extends WSAL_Models_ActiveRecord
|
|
38 |
return $this->IsLoaded() ? $this->option_value : $default;
|
39 |
}
|
40 |
|
|
|
|
|
|
|
|
|
|
|
41 |
public function Save()
|
42 |
{
|
43 |
$this->_state = self::STATE_UNKNOWN;
|
@@ -51,11 +69,23 @@ class WSAL_Models_Option extends WSAL_Models_ActiveRecord
|
|
51 |
return $result;
|
52 |
}
|
53 |
|
|
|
|
|
|
|
|
|
|
|
|
|
54 |
public function GetNotificationsSetting($opt_prefix)
|
55 |
{
|
56 |
return $this->getAdapter()->GetNotificationsSetting($opt_prefix);
|
57 |
}
|
58 |
|
|
|
|
|
|
|
|
|
|
|
|
|
59 |
public function GetNotification($id)
|
60 |
{
|
61 |
return $this->LoadData(
|
@@ -63,16 +93,34 @@ class WSAL_Models_Option extends WSAL_Models_ActiveRecord
|
|
63 |
);
|
64 |
}
|
65 |
|
|
|
|
|
|
|
|
|
|
|
|
|
66 |
public function DeleteByName($name)
|
67 |
{
|
68 |
return $this->getAdapter()->DeleteByName($name);
|
69 |
}
|
70 |
|
|
|
|
|
|
|
|
|
|
|
|
|
71 |
public function DeleteByPrefix($opt_prefix)
|
72 |
{
|
73 |
return $this->getAdapter()->DeleteByPrefix($opt_prefix);
|
74 |
}
|
75 |
|
|
|
|
|
|
|
|
|
|
|
|
|
76 |
public function CountNotifications($opt_prefix)
|
77 |
{
|
78 |
return $this->getAdapter()->CountNotifications($opt_prefix);
|
1 |
<?php
|
|
|
2 |
/**
|
3 |
+
* @package Wsal
|
4 |
* Wordpress options are always loaded from the default wordpress database.
|
5 |
+
*
|
6 |
+
* Option Model gets and sets the options of the wsal_options table in the database.
|
7 |
*/
|
8 |
class WSAL_Models_Option extends WSAL_Models_ActiveRecord
|
9 |
{
|
|
|
|
|
10 |
public $id = '';
|
11 |
public $option_name = '';
|
12 |
public $option_value = '';
|
13 |
+
protected $adapterName = "Option";
|
14 |
+
|
15 |
/**
|
16 |
* Options are always stored in WPDB. This setting ensures that
|
17 |
*/
|
18 |
protected $useDefaultAdapter = true;
|
19 |
|
20 |
+
/**
|
21 |
+
* Sets Option record.
|
22 |
+
* @param string $name option name
|
23 |
+
* @param mixed $value option value
|
24 |
+
*/
|
25 |
public function SetOptionValue($name, $value)
|
26 |
{
|
27 |
$option = $this->getAdapter()->GetNamedOption($name);
|
33 |
return $this->Save();
|
34 |
}
|
35 |
|
36 |
+
/**
|
37 |
+
* Gets Option record.
|
38 |
+
* @param string $name option name
|
39 |
+
* @param mixed $default (Optional) default value
|
40 |
+
* @return mixed option value
|
41 |
+
*/
|
42 |
public function GetOptionValue($name, $default = array())
|
43 |
{
|
44 |
+
$option = $this->getAdapter()->GetNamedOption($name);
|
45 |
$this->option_value = (!empty($option)) ? $option['option_value'] : null;
|
46 |
if (!empty($this->option_value)) {
|
47 |
$this->_state = self::STATE_LOADED;
|
51 |
return $this->IsLoaded() ? $this->option_value : $default;
|
52 |
}
|
53 |
|
54 |
+
/**
|
55 |
+
* Save Option record.
|
56 |
+
* @see WSAL_Adapters_MySQL_ActiveRecord::Save()
|
57 |
+
* @return integer|boolean Either the number of modified/inserted rows or false on failure.
|
58 |
+
*/
|
59 |
public function Save()
|
60 |
{
|
61 |
$this->_state = self::STATE_UNKNOWN;
|
69 |
return $result;
|
70 |
}
|
71 |
|
72 |
+
/**
|
73 |
+
* Get options by prefix (notifications stored in json format).
|
74 |
+
* @see WSAL_Adapters_MySQL_Option::GetNotificationsSetting()
|
75 |
+
* @param string $opt_prefix prefix
|
76 |
+
* @return array|null options
|
77 |
+
*/
|
78 |
public function GetNotificationsSetting($opt_prefix)
|
79 |
{
|
80 |
return $this->getAdapter()->GetNotificationsSetting($opt_prefix);
|
81 |
}
|
82 |
|
83 |
+
/**
|
84 |
+
* Get option by id (notifications stored in json format).
|
85 |
+
* @see WSAL_Adapters_MySQL_Option::GetNotification()
|
86 |
+
* @param int $id option ID
|
87 |
+
* @return string|null option
|
88 |
+
*/
|
89 |
public function GetNotification($id)
|
90 |
{
|
91 |
return $this->LoadData(
|
93 |
);
|
94 |
}
|
95 |
|
96 |
+
/**
|
97 |
+
* Delete option by name.
|
98 |
+
* @see WSAL_Adapters_MySQL_Option::DeleteByName()
|
99 |
+
* @param string $name option_name
|
100 |
+
* @return boolean
|
101 |
+
*/
|
102 |
public function DeleteByName($name)
|
103 |
{
|
104 |
return $this->getAdapter()->DeleteByName($name);
|
105 |
}
|
106 |
|
107 |
+
/**
|
108 |
+
* Delete options start with prefix.
|
109 |
+
* @see WSAL_Adapters_MySQL_Option::DeleteByPrefix()
|
110 |
+
* @param string $opt_prefix prefix
|
111 |
+
* @return boolean
|
112 |
+
*/
|
113 |
public function DeleteByPrefix($opt_prefix)
|
114 |
{
|
115 |
return $this->getAdapter()->DeleteByPrefix($opt_prefix);
|
116 |
}
|
117 |
|
118 |
+
/**
|
119 |
+
* Number of options start with prefix.
|
120 |
+
* @see WSAL_Adapters_MySQL_Option::CountNotifications()
|
121 |
+
* @param string $opt_prefix prefix
|
122 |
+
* @return integer Indicates the number of items.
|
123 |
+
*/
|
124 |
public function CountNotifications($opt_prefix)
|
125 |
{
|
126 |
return $this->getAdapter()->CountNotifications($opt_prefix);
|
classes/Models/Query.php
CHANGED
@@ -1,5 +1,10 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Models_Query
|
4 |
{
|
5 |
protected $columns = array();
|
@@ -10,13 +15,16 @@ class WSAL_Models_Query
|
|
10 |
protected $from = array();
|
11 |
protected $meta_join = false;
|
12 |
protected $searchCondition = null;
|
13 |
-
|
14 |
|
15 |
public function __construct()
|
16 |
{
|
17 |
-
|
18 |
}
|
19 |
|
|
|
|
|
|
|
|
|
20 |
public function getConnector()
|
21 |
{
|
22 |
if (!empty($this->connector)) {
|
@@ -30,56 +38,102 @@ class WSAL_Models_Query
|
|
30 |
return $this->connector;
|
31 |
}
|
32 |
|
|
|
|
|
|
|
|
|
33 |
public function getAdapter()
|
34 |
{
|
35 |
return $this->getConnector()->getAdapter('Query');
|
36 |
}
|
37 |
|
|
|
|
|
|
|
|
|
|
|
38 |
public function addColumn($column)
|
39 |
{
|
40 |
$this->columns[] = $column;
|
41 |
return $this;
|
42 |
}
|
43 |
|
|
|
|
|
|
|
|
|
44 |
public function clearColumns()
|
45 |
{
|
46 |
$this->columns = array();
|
47 |
return $this;
|
48 |
}
|
49 |
|
|
|
|
|
|
|
|
|
50 |
public function getColumns()
|
51 |
{
|
52 |
return $this->columns;
|
53 |
}
|
54 |
|
|
|
|
|
|
|
|
|
|
|
55 |
public function setColumns($columns)
|
56 |
{
|
57 |
$this->columns = $columns;
|
58 |
return $this;
|
59 |
}
|
60 |
|
|
|
|
|
|
|
|
|
|
|
|
|
61 |
public function addCondition($field, $value)
|
62 |
{
|
63 |
$this->conditions[$field] = $value;
|
64 |
return $this;
|
65 |
}
|
66 |
|
|
|
|
|
|
|
|
|
67 |
public function addORCondition($aConditions)
|
68 |
{
|
69 |
$this->conditions[] = $aConditions;
|
70 |
}
|
71 |
|
|
|
|
|
|
|
|
|
72 |
public function clearConditions()
|
73 |
{
|
74 |
$this->conditions = array();
|
75 |
return $this;
|
76 |
}
|
77 |
|
|
|
|
|
|
|
|
|
78 |
public function getConditions()
|
79 |
{
|
80 |
return $this->conditions;
|
81 |
}
|
82 |
|
|
|
|
|
|
|
|
|
|
|
|
|
83 |
public function addOrderBy($field, $isDescending = false)
|
84 |
{
|
85 |
$order = ($isDescending) ? 'DESC' : 'ASC';
|
@@ -87,29 +141,50 @@ class WSAL_Models_Query
|
|
87 |
return $this;
|
88 |
}
|
89 |
|
|
|
|
|
|
|
|
|
90 |
public function clearOrderBy()
|
91 |
{
|
92 |
$this->orderBy = array();
|
93 |
return $this;
|
94 |
}
|
95 |
|
|
|
|
|
|
|
|
|
96 |
public function getOrderBy()
|
97 |
{
|
98 |
return $this->orderBy;
|
99 |
}
|
100 |
|
|
|
|
|
|
|
|
|
|
|
101 |
public function addFrom($fromDataSet)
|
102 |
{
|
103 |
$this->from[] = $fromDataSet;
|
104 |
return $this;
|
105 |
}
|
106 |
|
|
|
|
|
|
|
|
|
107 |
public function clearFrom()
|
108 |
{
|
109 |
$this->from = array();
|
110 |
return $this;
|
111 |
}
|
112 |
|
|
|
|
|
|
|
|
|
113 |
public function getFrom()
|
114 |
{
|
115 |
return $this->from;
|
@@ -117,7 +192,6 @@ class WSAL_Models_Query
|
|
117 |
|
118 |
/**
|
119 |
* Gets the value of limit.
|
120 |
-
*
|
121 |
* @return mixed
|
122 |
*/
|
123 |
public function getLimit()
|
@@ -127,21 +201,17 @@ class WSAL_Models_Query
|
|
127 |
|
128 |
/**
|
129 |
* Sets the value of limit.
|
130 |
-
*
|
131 |
* @param mixed $limit the limit
|
132 |
-
*
|
133 |
* @return self
|
134 |
*/
|
135 |
public function setLimit($limit)
|
136 |
{
|
137 |
$this->limit = $limit;
|
138 |
-
|
139 |
return $this;
|
140 |
}
|
141 |
|
142 |
/**
|
143 |
* Gets the value of offset.
|
144 |
-
*
|
145 |
* @return mixed
|
146 |
*/
|
147 |
public function getOffset()
|
@@ -151,34 +221,48 @@ class WSAL_Models_Query
|
|
151 |
|
152 |
/**
|
153 |
* Sets the value of offset.
|
154 |
-
*
|
155 |
* @param mixed $offset the offset
|
156 |
-
*
|
157 |
* @return self
|
158 |
*/
|
159 |
public function setOffset($offset)
|
160 |
{
|
161 |
$this->offset = $offset;
|
162 |
-
|
163 |
return $this;
|
164 |
}
|
165 |
|
|
|
|
|
|
|
|
|
|
|
166 |
public function addSearchCondition($value)
|
167 |
{
|
168 |
$this->searchCondition = $value;
|
169 |
return $this;
|
170 |
}
|
171 |
|
|
|
|
|
|
|
|
|
172 |
public function getSearchCondition()
|
173 |
{
|
174 |
return $this->searchCondition;
|
175 |
}
|
176 |
|
|
|
|
|
|
|
|
|
177 |
public function hasMetaJoin()
|
178 |
{
|
179 |
return $this->meta_join;
|
180 |
}
|
181 |
|
|
|
|
|
|
|
|
|
182 |
public function addMetaJoin()
|
183 |
{
|
184 |
$this->meta_join = true;
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* Query Class.
|
5 |
+
*
|
6 |
+
* Query model is the class for all the query conditions.
|
7 |
+
*/
|
8 |
class WSAL_Models_Query
|
9 |
{
|
10 |
protected $columns = array();
|
15 |
protected $from = array();
|
16 |
protected $meta_join = false;
|
17 |
protected $searchCondition = null;
|
18 |
+
protected $useDefaultAdapter = false;
|
19 |
|
20 |
public function __construct()
|
21 |
{
|
|
|
22 |
}
|
23 |
|
24 |
+
/**
|
25 |
+
* Initialize a connector singleton.
|
26 |
+
* @return WSAL_Connector_ConnectorInterface
|
27 |
+
*/
|
28 |
public function getConnector()
|
29 |
{
|
30 |
if (!empty($this->connector)) {
|
38 |
return $this->connector;
|
39 |
}
|
40 |
|
41 |
+
/**
|
42 |
+
* Gets the adapter.
|
43 |
+
* @return WSAL_Adapters_MySQL_Query
|
44 |
+
*/
|
45 |
public function getAdapter()
|
46 |
{
|
47 |
return $this->getConnector()->getAdapter('Query');
|
48 |
}
|
49 |
|
50 |
+
/**
|
51 |
+
* Add a column.
|
52 |
+
* @param mixed $column column value
|
53 |
+
* @return self
|
54 |
+
*/
|
55 |
public function addColumn($column)
|
56 |
{
|
57 |
$this->columns[] = $column;
|
58 |
return $this;
|
59 |
}
|
60 |
|
61 |
+
/**
|
62 |
+
* Clear all columns.
|
63 |
+
* @return self
|
64 |
+
*/
|
65 |
public function clearColumns()
|
66 |
{
|
67 |
$this->columns = array();
|
68 |
return $this;
|
69 |
}
|
70 |
|
71 |
+
/**
|
72 |
+
* Get columns.
|
73 |
+
* @return array $columns
|
74 |
+
*/
|
75 |
public function getColumns()
|
76 |
{
|
77 |
return $this->columns;
|
78 |
}
|
79 |
|
80 |
+
/**
|
81 |
+
* Set all columns.
|
82 |
+
* @param array $columns columns values
|
83 |
+
* @return self
|
84 |
+
*/
|
85 |
public function setColumns($columns)
|
86 |
{
|
87 |
$this->columns = $columns;
|
88 |
return $this;
|
89 |
}
|
90 |
|
91 |
+
/**
|
92 |
+
* Add conditions.
|
93 |
+
* @param string $field condition field
|
94 |
+
* @param mixed $value condition value
|
95 |
+
* @return self
|
96 |
+
*/
|
97 |
public function addCondition($field, $value)
|
98 |
{
|
99 |
$this->conditions[$field] = $value;
|
100 |
return $this;
|
101 |
}
|
102 |
|
103 |
+
/**
|
104 |
+
* Add OR condition.
|
105 |
+
* @param array $aConditions multi conditions
|
106 |
+
*/
|
107 |
public function addORCondition($aConditions)
|
108 |
{
|
109 |
$this->conditions[] = $aConditions;
|
110 |
}
|
111 |
|
112 |
+
/**
|
113 |
+
* Clear all conditions.
|
114 |
+
* @return self
|
115 |
+
*/
|
116 |
public function clearConditions()
|
117 |
{
|
118 |
$this->conditions = array();
|
119 |
return $this;
|
120 |
}
|
121 |
|
122 |
+
/**
|
123 |
+
* Get all conditions.
|
124 |
+
* @return array $conditions
|
125 |
+
*/
|
126 |
public function getConditions()
|
127 |
{
|
128 |
return $this->conditions;
|
129 |
}
|
130 |
|
131 |
+
/**
|
132 |
+
* Add order by.
|
133 |
+
* @param string $field field name
|
134 |
+
* @param boolean $isDescending (Optional) ascending/descending
|
135 |
+
* @return self
|
136 |
+
*/
|
137 |
public function addOrderBy($field, $isDescending = false)
|
138 |
{
|
139 |
$order = ($isDescending) ? 'DESC' : 'ASC';
|
141 |
return $this;
|
142 |
}
|
143 |
|
144 |
+
/**
|
145 |
+
* Clear order by.
|
146 |
+
* @return self
|
147 |
+
*/
|
148 |
public function clearOrderBy()
|
149 |
{
|
150 |
$this->orderBy = array();
|
151 |
return $this;
|
152 |
}
|
153 |
|
154 |
+
/**
|
155 |
+
* Get order by.
|
156 |
+
* @return array $orderBy
|
157 |
+
*/
|
158 |
public function getOrderBy()
|
159 |
{
|
160 |
return $this->orderBy;
|
161 |
}
|
162 |
|
163 |
+
/**
|
164 |
+
* Add from.
|
165 |
+
* @param string $fromDataSet data set
|
166 |
+
* @return self
|
167 |
+
*/
|
168 |
public function addFrom($fromDataSet)
|
169 |
{
|
170 |
$this->from[] = $fromDataSet;
|
171 |
return $this;
|
172 |
}
|
173 |
|
174 |
+
/**
|
175 |
+
* Reset from.
|
176 |
+
* @return self
|
177 |
+
*/
|
178 |
public function clearFrom()
|
179 |
{
|
180 |
$this->from = array();
|
181 |
return $this;
|
182 |
}
|
183 |
|
184 |
+
/**
|
185 |
+
* Get from.
|
186 |
+
* @return string $from data set
|
187 |
+
*/
|
188 |
public function getFrom()
|
189 |
{
|
190 |
return $this->from;
|
192 |
|
193 |
/**
|
194 |
* Gets the value of limit.
|
|
|
195 |
* @return mixed
|
196 |
*/
|
197 |
public function getLimit()
|
201 |
|
202 |
/**
|
203 |
* Sets the value of limit.
|
|
|
204 |
* @param mixed $limit the limit
|
|
|
205 |
* @return self
|
206 |
*/
|
207 |
public function setLimit($limit)
|
208 |
{
|
209 |
$this->limit = $limit;
|
|
|
210 |
return $this;
|
211 |
}
|
212 |
|
213 |
/**
|
214 |
* Gets the value of offset.
|
|
|
215 |
* @return mixed
|
216 |
*/
|
217 |
public function getOffset()
|
221 |
|
222 |
/**
|
223 |
* Sets the value of offset.
|
|
|
224 |
* @param mixed $offset the offset
|
|
|
225 |
* @return self
|
226 |
*/
|
227 |
public function setOffset($offset)
|
228 |
{
|
229 |
$this->offset = $offset;
|
|
|
230 |
return $this;
|
231 |
}
|
232 |
|
233 |
+
/**
|
234 |
+
* Adds condition.
|
235 |
+
* @param mixed $value condition
|
236 |
+
* @return self
|
237 |
+
*/
|
238 |
public function addSearchCondition($value)
|
239 |
{
|
240 |
$this->searchCondition = $value;
|
241 |
return $this;
|
242 |
}
|
243 |
|
244 |
+
/**
|
245 |
+
* Gets condition.
|
246 |
+
* @return self
|
247 |
+
*/
|
248 |
public function getSearchCondition()
|
249 |
{
|
250 |
return $this->searchCondition;
|
251 |
}
|
252 |
|
253 |
+
/**
|
254 |
+
* Check meta join.
|
255 |
+
* @return boolean
|
256 |
+
*/
|
257 |
public function hasMetaJoin()
|
258 |
{
|
259 |
return $this->meta_join;
|
260 |
}
|
261 |
|
262 |
+
/**
|
263 |
+
* Adds meta join.
|
264 |
+
* @return self
|
265 |
+
*/
|
266 |
public function addMetaJoin()
|
267 |
{
|
268 |
$this->meta_join = true;
|
classes/Models/TmpUser.php
CHANGED
@@ -1,9 +1,13 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
|
|
|
|
|
|
|
|
9 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* Model tmp_users
|
5 |
+
*
|
6 |
+
* Model used for the Temporary WP_users table.
|
7 |
+
*/
|
8 |
+
class WSAL_Models_TmpUser extends WSAL_Models_ActiveRecord
|
9 |
+
{
|
10 |
+
public $id = 0;
|
11 |
+
public $user_login = '';
|
12 |
+
protected $adapterName = "TmpUser";
|
13 |
}
|
classes/Nicer.php
CHANGED
@@ -1,289 +1,299 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
protected $_has_reflection = null;
|
46 |
-
|
47 |
-
/**
|
48 |
-
* Constructs new renderer instance.
|
49 |
-
* @param mixed $value The value to inspect and render.
|
50 |
-
* @param boolean $inspectMethods Whether to inspect and output methods for objects or not.
|
51 |
-
*/
|
52 |
-
public function __construct($value, $inspectMethods = false){
|
53 |
-
$this->value = $value;
|
54 |
-
$this->inspect_methods = $inspectMethods;
|
55 |
-
|
56 |
-
if(is_null($this->_has_reflection))
|
57 |
-
$this->_has_reflection = class_exists('ReflectionClass');
|
58 |
-
}
|
59 |
-
|
60 |
-
/**
|
61 |
-
* Generates the inspector HTML and returns it as a string.
|
62 |
-
* @return string Generated HTML.
|
63 |
-
*/
|
64 |
-
public function generate(){
|
65 |
-
return $this->_generate_value($this->value, $this->css_class);
|
66 |
-
}
|
67 |
-
|
68 |
-
/**
|
69 |
-
* Renders the inspector HTML directly to the browser.
|
70 |
-
*/
|
71 |
-
public function render(){
|
72 |
-
echo $this->generate();
|
73 |
-
}
|
74 |
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
|
79 |
-
|
80 |
-
|
81 |
-
|
82 |
-
|
83 |
-
|
84 |
-
|
85 |
-
|
86 |
-
|
87 |
-
|
88 |
-
|
89 |
-
|
90 |
-
|
91 |
-
|
92 |
-
|
93 |
-
|
94 |
-
|
95 |
-
|
96 |
-
|
97 |
-
|
98 |
-
|
99 |
-
|
100 |
-
|
101 |
-
|
102 |
-
|
103 |
-
|
104 |
-
|
105 |
-
|
106 |
-
|
107 |
-
|
108 |
-
|
109 |
-
|
110 |
-
|
111 |
-
|
112 |
-
|
113 |
|
114 |
-
|
115 |
-
|
116 |
-
|
117 |
-
|
118 |
-
|
119 |
-
|
120 |
-
|
121 |
-
|
122 |
-
|
123 |
-
|
124 |
-
$html .= '<span class="'.$this->css_class.'_ni">No Methods</span>';
|
125 |
-
}
|
126 |
-
}
|
127 |
-
}
|
128 |
-
|
129 |
-
/**
|
130 |
-
* Render a single particular value.
|
131 |
-
* @param mixed $var The value to render
|
132 |
-
* @param string $class Parent CSS class.
|
133 |
-
* @param string $id Item HTML id.
|
134 |
-
*/
|
135 |
-
protected function _generate_value($var, $class = '', $id = ''){
|
136 |
-
$BEENTHERE = self::$BEEN_THERE;
|
137 |
-
$class .= ' '.$this->css_class.'_t_'.gettype($var);
|
138 |
-
|
139 |
-
$html = '<div id="'.$id.'" class="'.$class.'">';
|
140 |
-
|
141 |
-
switch(true){
|
142 |
|
143 |
-
|
144 |
-
|
145 |
-
|
146 |
-
|
147 |
-
|
148 |
-
|
149 |
-
|
150 |
-
|
151 |
-
|
152 |
-
|
153 |
-
|
154 |
-
|
155 |
-
|
156 |
-
|
157 |
-
|
158 |
-
|
159 |
-
|
160 |
-
|
161 |
-
|
162 |
-
|
163 |
-
|
164 |
-
|
165 |
-
|
166 |
-
|
167 |
-
|
168 |
-
|
169 |
-
|
170 |
-
|
171 |
-
|
172 |
-
|
173 |
-
|
174 |
-
|
175 |
-
|
176 |
-
|
177 |
-
|
178 |
-
|
179 |
-
|
180 |
-
|
181 |
-
|
182 |
-
|
183 |
-
|
184 |
-
|
185 |
-
|
186 |
-
|
187 |
-
|
188 |
-
|
189 |
-
|
190 |
-
|
191 |
-
|
192 |
-
|
193 |
-
|
194 |
-
|
195 |
-
|
196 |
-
|
197 |
-
|
198 |
-
|
199 |
-
|
200 |
-
|
201 |
-
|
202 |
-
|
203 |
-
|
204 |
-
|
205 |
-
|
206 |
-
|
207 |
-
|
208 |
-
|
209 |
-
|
210 |
-
|
211 |
-
|
212 |
-
|
213 |
-
|
214 |
-
|
215 |
-
|
216 |
-
|
217 |
-
|
218 |
-
|
219 |
-
|
220 |
-
|
221 |
-
|
222 |
-
|
223 |
-
|
224 |
-
|
225 |
-
|
226 |
-
|
227 |
-
|
228 |
-
|
229 |
-
|
230 |
-
|
231 |
-
|
232 |
-
|
233 |
-
|
234 |
-
|
235 |
-
|
236 |
-
|
237 |
-
|
238 |
-
|
239 |
-
|
240 |
-
|
241 |
-
|
242 |
-
|
243 |
-
|
244 |
-
|
245 |
-
|
246 |
-
|
247 |
-
|
248 |
-
|
249 |
-
|
250 |
-
|
251 |
-
|
252 |
-
|
253 |
-
|
254 |
-
|
255 |
-
|
256 |
-
|
257 |
-
|
258 |
-
|
259 |
-
|
260 |
-
|
261 |
-
|
262 |
-
|
263 |
-
|
264 |
-
|
265 |
-
|
266 |
-
|
267 |
-
|
268 |
-
|
269 |
-
|
270 |
-
|
271 |
-
$doc = null;
|
272 |
-
$prms = array('???');
|
273 |
-
}
|
274 |
-
|
275 |
-
$xcls = !$doc ? $cls.'_ad' : '';
|
276 |
-
$html = '<a class="'.$cls.'_c" '.($doc?'href="javascript:;"':'').' onclick="'.$this->js_func.'(\''.$this->html_id.'\',\''.$id.'\');">';
|
277 |
-
$html .= ' <span class="'.$cls.'_a '.$xcls.'">►</span>';
|
278 |
-
$html .= ' <span class="'.$cls.'_k">'.$this->_esc_html($name).'<span class="'.$cls.'_ma">(<span>'.implode(', ', $prms).'</span>)</span></span>';
|
279 |
-
$html .= '</a>';
|
280 |
-
|
281 |
-
if($doc){
|
282 |
-
$html .= '<div id="'.$this->html_id.'_v'.$id.'" class="nice_r_v '.$this->css_class.'_t_comment">';
|
283 |
-
$html .= nl2br(str_replace(' ', ' ', $this->_esc_html($doc)));
|
284 |
-
$html .= '</div>';
|
285 |
-
}
|
286 |
-
|
287 |
-
return $html;
|
288 |
-
}
|
289 |
-
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* Inspects and prints out PHP values as HTML in a nicer way than print_r().
|
5 |
+
* @author Christian Sciberras <christian@sciberras.me>
|
6 |
+
* @copyright (c) 2013, Christian Sciberras
|
7 |
+
* @license https://raw.github.com/uuf6429/nice_r/master/LICENSE MIT License
|
8 |
+
* @link https://github.com/uuf6429/nice_r GitHub Repository
|
9 |
+
* @version 2.0
|
10 |
+
* @since 2.0
|
11 |
+
*/
|
12 |
+
class WSAL_Nicer
|
13 |
+
{
|
14 |
+
protected $value;
|
15 |
+
|
16 |
+
/**
|
17 |
+
* Allows modification of CSS class prefix.
|
18 |
+
* @var string
|
19 |
+
*/
|
20 |
+
public $css_class = 'nice_r';
|
21 |
+
|
22 |
+
/**
|
23 |
+
* Allows modification of HTML id prefix.
|
24 |
+
* @var string
|
25 |
+
*/
|
26 |
+
public $html_id = 'nice_r_v';
|
27 |
+
|
28 |
+
/**
|
29 |
+
* Allows modification of JS function used to toggle sections.
|
30 |
+
* @var string
|
31 |
+
*/
|
32 |
+
public $js_func = 'nice_r_toggle';
|
33 |
+
|
34 |
+
/**
|
35 |
+
* Whether to inspect and output methods for objects or not.
|
36 |
+
* @var boolean
|
37 |
+
*/
|
38 |
+
public $inspect_methods = false;
|
39 |
+
|
40 |
+
/**
|
41 |
+
* Since PHP does not support private constants, we'll have to settle for private static fields.
|
42 |
+
* @var string
|
43 |
+
*/
|
44 |
+
protected static $BEEN_THERE = '__NICE_R_INFINITE_RECURSION_PROTECT__';
|
45 |
+
|
46 |
+
protected $_has_reflection = null;
|
47 |
+
|
48 |
+
/**
|
49 |
+
* Constructs new renderer instance.
|
50 |
+
* @param mixed $value The value to inspect and render.
|
51 |
+
* @param boolean $inspectMethods Whether to inspect and output methods for objects or not.
|
52 |
+
*/
|
53 |
+
public function __construct($value, $inspectMethods = false)
|
54 |
+
{
|
55 |
+
$this->value = $value;
|
56 |
+
$this->inspect_methods = $inspectMethods;
|
57 |
+
|
58 |
+
if (is_null($this->_has_reflection)) {
|
59 |
+
$this->_has_reflection = class_exists('ReflectionClass');
|
60 |
+
}
|
61 |
+
}
|
62 |
+
|
63 |
+
/**
|
64 |
+
* Generates the inspector HTML and returns it as a string.
|
65 |
+
* @return string Generated HTML.
|
66 |
+
*/
|
67 |
+
public function generate()
|
68 |
+
{
|
69 |
+
return $this->_generate_value($this->value, $this->css_class);
|
70 |
+
}
|
71 |
+
|
72 |
+
/**
|
73 |
+
* Renders the inspector HTML directly to the browser.
|
74 |
+
*/
|
75 |
+
public function render()
|
76 |
+
{
|
77 |
+
echo $this->generate();
|
78 |
+
}
|
79 |
|
80 |
+
/**
|
81 |
+
* Converts a string to HTML, encoding any special characters.
|
82 |
+
* @param string $text The original string.
|
83 |
+
* @return string The string as HTML.
|
84 |
+
*/
|
85 |
+
protected function _esc_html($text)
|
86 |
+
{
|
87 |
+
return htmlspecialchars($text, ENT_QUOTES, 'UTF-8');
|
88 |
+
}
|
89 |
+
|
90 |
+
protected function _inspect_array(&$html, &$var)
|
91 |
+
{
|
92 |
+
$has_subitems = false;
|
93 |
+
|
94 |
+
foreach ($var as $k => $v) {
|
95 |
+
if ($k !== self::$BEEN_THERE) {
|
96 |
+
$html .= $this->_generate_keyvalue($k, $v);
|
97 |
+
$has_subitems = true;
|
98 |
+
}
|
99 |
+
}
|
100 |
+
|
101 |
+
if (!$has_subitems) {
|
102 |
+
$html .= '<span class="'.$this->css_class.'_ni">Empty Array</span>';
|
103 |
+
}
|
104 |
+
}
|
105 |
+
|
106 |
+
protected function _inspect_object(&$html, &$var)
|
107 |
+
{
|
108 |
+
// render properties
|
109 |
+
$has_subitems = false;
|
110 |
+
|
111 |
+
foreach ((array)$var as $k => $v) {
|
112 |
+
if ($k !== self::$BEEN_THERE) {
|
113 |
+
$html .= $this->_generate_keyvalue($k, $v);
|
114 |
+
$has_subitems = true;
|
115 |
+
}
|
116 |
+
}
|
117 |
+
|
118 |
+
if (!$has_subitems) {
|
119 |
+
$html .= '<span class="'.$this->css_class.'_ni">No Properties</span>';
|
120 |
+
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
121 |
|
122 |
+
// render methods (if enabled)
|
123 |
+
if ($this->inspect_methods) {
|
124 |
+
$has_subitems = false;
|
125 |
+
|
126 |
+
foreach ((array)get_class_methods($var) as $method) {
|
127 |
+
$html .= $this->_generate_callable($var, $method);
|
128 |
+
$has_subitems = true;
|
129 |
+
}
|
130 |
+
|
131 |
+
if (!$has_subitems) {
|
132 |
+
$html .= '<span class="'.$this->css_class.'_ni">No Methods</span>';
|
133 |
+
}
|
134 |
+
}
|
135 |
+
}
|
136 |
+
|
137 |
+
/**
|
138 |
+
* Render a single particular value.
|
139 |
+
* @param mixed $var The value to render
|
140 |
+
* @param string $class Parent CSS class.
|
141 |
+
* @param string $id Item HTML id.
|
142 |
+
*/
|
143 |
+
protected function _generate_value($var, $class = '', $id = '')
|
144 |
+
{
|
145 |
+
$BEENTHERE = self::$BEEN_THERE;
|
146 |
+
$class .= ' '.$this->css_class.'_t_'.gettype($var);
|
147 |
+
|
148 |
+
$html = '<div id="'.$id.'" class="'.$class.'">';
|
149 |
+
switch (true) {
|
150 |
+
// handle arrays
|
151 |
+
case is_array($var):
|
152 |
+
if (isset($var[$BEENTHERE])) {
|
153 |
+
$html .= '<span class="'.$this->css_class.'_ir">Infinite Recursion Detected!</span>';
|
154 |
+
} else {
|
155 |
+
$var[$BEENTHERE] = true;
|
156 |
+
$this->_inspect_array($html, $var);
|
157 |
+
unset($var[$BEENTHERE]);
|
158 |
+
}
|
159 |
+
break;
|
160 |
|
161 |
+
// handle objects
|
162 |
+
case is_object($var):
|
163 |
+
if (isset($var->$BEENTHERE)) {
|
164 |
+
$html .= '<span class="'.$this->css_class.'_ir">Infinite Recursion Detected!</span>';
|
165 |
+
} else {
|
166 |
+
$var->$BEENTHERE = true;
|
167 |
+
$this->_inspect_object($html, $var);
|
168 |
+
unset($var->$BEENTHERE);
|
169 |
+
}
|
170 |
+
break;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
171 |
|
172 |
+
// handle simple types
|
173 |
+
default:
|
174 |
+
$html .= $this->_generate_keyvalue('', $var);
|
175 |
+
break;
|
176 |
+
}
|
177 |
+
|
178 |
+
return $html . '</div>';
|
179 |
+
}
|
180 |
+
|
181 |
+
/**
|
182 |
+
* Generates a new unique ID for tagging elements.
|
183 |
+
* @staticvar int $id
|
184 |
+
* @return integer An ID unique per request.
|
185 |
+
*/
|
186 |
+
protected function _generate_dropid()
|
187 |
+
{
|
188 |
+
static $id = 0;
|
189 |
+
return ++$id;
|
190 |
+
}
|
191 |
+
|
192 |
+
/**
|
193 |
+
* Render a key-value pair.
|
194 |
+
* @staticvar int $id Specifies element id.
|
195 |
+
* @param string $key Key name.
|
196 |
+
* @param mixed $val Key value.
|
197 |
+
*/
|
198 |
+
protected function _generate_keyvalue($key, $val)
|
199 |
+
{
|
200 |
+
$id = $this->_generate_dropid();
|
201 |
+
$p = ''; // preview
|
202 |
+
$d = ''; // description
|
203 |
+
$t = gettype($val); // get data type
|
204 |
+
$is_hash = ($t=='array') || ($t=='object');
|
205 |
+
|
206 |
+
switch ($t) {
|
207 |
+
case 'boolean':
|
208 |
+
$p = $val ? 'TRUE' : 'FALSE';
|
209 |
+
break;
|
210 |
+
case 'integer':
|
211 |
+
case 'double':
|
212 |
+
$p = (string)$val;
|
213 |
+
break;
|
214 |
+
case 'string':
|
215 |
+
$d .= ', '.strlen($val).' characters';
|
216 |
+
$p = $val;
|
217 |
+
break;
|
218 |
+
case 'resource':
|
219 |
+
$d .= ', '.get_resource_type($val).' type';
|
220 |
+
$p = (string)$val;
|
221 |
+
break;
|
222 |
+
case 'array':
|
223 |
+
$d .= ', '.count($val).' elements';
|
224 |
+
break;
|
225 |
+
case 'object':
|
226 |
+
$d .= ', '.get_class($val).', '.count(get_object_vars($val)).' properties';
|
227 |
+
break;
|
228 |
+
}
|
229 |
+
|
230 |
+
$cls = $this->css_class;
|
231 |
+
$xcls = !$is_hash ? $cls.'_ad' : '';
|
232 |
+
$html = '<a '.($is_hash?'href="javascript:;"':'').' onclick="'.$this->js_func.'(\''.$this->html_id.'\',\''.$id.'\');">';
|
233 |
+
$html .= ' <span class="'.$cls.'_a '.$xcls.'" id="'.$this->html_id.'_a'.$id.'">►</span>';
|
234 |
+
$html .= ' <span class="'.$cls.'_k">'.$this->_esc_html($key).'</span>';
|
235 |
+
$html .= ' <span class="'.$cls.'_d">(<span>'.ucwords($t).'</span>'.$d.')</span>';
|
236 |
+
$html .= ' <span class="'.$cls.'_p '.$cls.'_t_'.$t.'">'.$this->_esc_html($p).'</span>';
|
237 |
+
$html .= '</a>';
|
238 |
+
|
239 |
+
if ($is_hash) {
|
240 |
+
$html .= $this->_generate_value($val, $cls.'_v', $this->html_id.'_v'.$id);
|
241 |
+
}
|
242 |
+
|
243 |
+
return $html;
|
244 |
+
}
|
245 |
+
|
246 |
+
protected function _generate_callable($context, $callback)
|
247 |
+
{
|
248 |
+
$id = $this->_generate_dropid();
|
249 |
+
$ref = null;
|
250 |
+
$name = 'Anonymous';
|
251 |
+
$cls = $this->css_class;
|
252 |
+
|
253 |
+
if ($this->_has_reflection) {
|
254 |
+
if (is_null($context)) {
|
255 |
+
$ref = new ReflectionFunction($callback);
|
256 |
+
} else {
|
257 |
+
$ref = new ReflectionMethod($context, $callback);
|
258 |
+
}
|
259 |
+
$name = $ref->getName();
|
260 |
+
} elseif (is_string($callback)) {
|
261 |
+
$name = $callback;
|
262 |
+
}
|
263 |
+
|
264 |
+
if (!is_null($ref)) {
|
265 |
+
$doc = $ref->getDocComment();
|
266 |
+
$prms = array();
|
267 |
+
foreach ($ref->getParameters() as $p) {
|
268 |
+
$prms[] = '$' . $p->getName() . (
|
269 |
+
$p->isDefaultValueAvailable()
|
270 |
+
? (
|
271 |
+
' = <span class="'.$cls.'_mv">' . (
|
272 |
+
$p->isDefaultValueConstant()
|
273 |
+
? $p->getDefaultValueConstantName()
|
274 |
+
: var_export($p->getDefaultValue(), true)
|
275 |
+
) . '</span>'
|
276 |
+
)
|
277 |
+
: ''
|
278 |
+
);
|
279 |
+
}
|
280 |
+
} else {
|
281 |
+
$doc = null;
|
282 |
+
$prms = array('???');
|
283 |
+
}
|
284 |
+
|
285 |
+
$xcls = !$doc ? $cls.'_ad' : '';
|
286 |
+
$html = '<a class="'.$cls.'_c" '.($doc?'href="javascript:;"':'').' onclick="'.$this->js_func.'(\''.$this->html_id.'\',\''.$id.'\');">';
|
287 |
+
$html .= ' <span class="'.$cls.'_a '.$xcls.'">►</span>';
|
288 |
+
$html .= ' <span class="'.$cls.'_k">'.$this->_esc_html($name).'<span class="'.$cls.'_ma">(<span>'.implode(', ', $prms).'</span>)</span></span>';
|
289 |
+
$html .= '</a>';
|
290 |
+
|
291 |
+
if ($doc) {
|
292 |
+
$html .= '<div id="'.$this->html_id.'_v'.$id.'" class="nice_r_v '.$this->css_class.'_t_comment">';
|
293 |
+
$html .= nl2br(str_replace(' ', ' ', $this->_esc_html($doc)));
|
294 |
+
$html .= '</div>';
|
295 |
+
}
|
296 |
+
|
297 |
+
return $html;
|
298 |
+
}
|
299 |
+
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/SensorManager.php
CHANGED
@@ -1,13 +1,18 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
5 |
/**
|
6 |
* @var WSAL_AbstractSensor[]
|
7 |
*/
|
8 |
protected $sensors = array();
|
9 |
|
10 |
-
public function __construct(WpSecurityAuditLog $plugin)
|
|
|
11 |
parent::__construct($plugin);
|
12 |
|
13 |
foreach (glob(dirname(__FILE__) . '/Sensors/*.php') as $file) {
|
@@ -29,13 +34,15 @@ final class WSAL_SensorManager extends WSAL_AbstractSensor {
|
|
29 |
}
|
30 |
}
|
31 |
|
32 |
-
public function HookEvents()
|
|
|
33 |
foreach ($this->sensors as $sensor) {
|
34 |
$sensor->HookEvents();
|
35 |
}
|
36 |
}
|
37 |
|
38 |
-
public function GetSensors()
|
|
|
39 |
return $this->sensors;
|
40 |
}
|
41 |
|
@@ -43,7 +50,8 @@ final class WSAL_SensorManager extends WSAL_AbstractSensor {
|
|
43 |
* Add new sensor from file inside autoloader path.
|
44 |
* @param string $file Path to file.
|
45 |
*/
|
46 |
-
public function AddFromFile($file)
|
|
|
47 |
$this->AddFromClass($this->plugin->GetClassFileClassName($file));
|
48 |
}
|
49 |
|
@@ -51,7 +59,8 @@ final class WSAL_SensorManager extends WSAL_AbstractSensor {
|
|
51 |
* Add new sensor given class name.
|
52 |
* @param string $class Class name.
|
53 |
*/
|
54 |
-
public function AddFromClass($class)
|
|
|
55 |
$this->AddInstance(new $class($this->plugin));
|
56 |
}
|
57 |
|
@@ -59,7 +68,8 @@ final class WSAL_SensorManager extends WSAL_AbstractSensor {
|
|
59 |
* Add newly created sensor to list.
|
60 |
* @param WSAL_AbstractSensor $sensor The new sensor.
|
61 |
*/
|
62 |
-
public function AddInstance(WSAL_AbstractSensor $sensor)
|
|
|
63 |
$this->sensors[] = $sensor;
|
64 |
}
|
65 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* This Class load all the sensors and initialize them.
|
6 |
+
*/
|
7 |
+
final class WSAL_SensorManager extends WSAL_AbstractSensor
|
8 |
+
{
|
9 |
/**
|
10 |
* @var WSAL_AbstractSensor[]
|
11 |
*/
|
12 |
protected $sensors = array();
|
13 |
|
14 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
15 |
+
{
|
16 |
parent::__construct($plugin);
|
17 |
|
18 |
foreach (glob(dirname(__FILE__) . '/Sensors/*.php') as $file) {
|
34 |
}
|
35 |
}
|
36 |
|
37 |
+
public function HookEvents()
|
38 |
+
{
|
39 |
foreach ($this->sensors as $sensor) {
|
40 |
$sensor->HookEvents();
|
41 |
}
|
42 |
}
|
43 |
|
44 |
+
public function GetSensors()
|
45 |
+
{
|
46 |
return $this->sensors;
|
47 |
}
|
48 |
|
50 |
* Add new sensor from file inside autoloader path.
|
51 |
* @param string $file Path to file.
|
52 |
*/
|
53 |
+
public function AddFromFile($file)
|
54 |
+
{
|
55 |
$this->AddFromClass($this->plugin->GetClassFileClassName($file));
|
56 |
}
|
57 |
|
59 |
* Add new sensor given class name.
|
60 |
* @param string $class Class name.
|
61 |
*/
|
62 |
+
public function AddFromClass($class)
|
63 |
+
{
|
64 |
$this->AddInstance(new $class($this->plugin));
|
65 |
}
|
66 |
|
68 |
* Add newly created sensor to list.
|
69 |
* @param WSAL_AbstractSensor $sensor The new sensor.
|
70 |
*/
|
71 |
+
public function AddInstance(WSAL_AbstractSensor $sensor)
|
72 |
+
{
|
73 |
$this->sensors[] = $sensor;
|
74 |
}
|
75 |
}
|
classes/Sensors/BBPress.php
CHANGED
@@ -1,11 +1,39 @@
|
|
1 |
<?php
|
2 |
/**
|
3 |
-
*
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
4 |
*/
|
5 |
class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
6 |
{
|
|
|
|
|
|
|
7 |
protected $_OldLink = null;
|
8 |
|
|
|
|
|
|
|
9 |
public function HookEvents()
|
10 |
{
|
11 |
if (current_user_can("edit_posts")) {
|
@@ -17,6 +45,9 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
17 |
add_action('untrash_post', array($this, 'EventForumUntrashed'));
|
18 |
}
|
19 |
|
|
|
|
|
|
|
20 |
public function EventAdminInit()
|
21 |
{
|
22 |
// load old data, if applicable
|
@@ -25,6 +56,10 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
25 |
$this->TriggerAjaxChange();
|
26 |
}
|
27 |
|
|
|
|
|
|
|
|
|
28 |
protected function RetrieveOldData()
|
29 |
{
|
30 |
if (isset($_POST) && isset($_POST['post_ID'])
|
@@ -36,6 +71,12 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
36 |
}
|
37 |
}
|
38 |
|
|
|
|
|
|
|
|
|
|
|
|
|
39 |
public function CheckForumChange($post_ID, $newpost, $oldpost)
|
40 |
{
|
41 |
if ($this->CheckBBPress($oldpost)) {
|
@@ -60,7 +101,8 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
60 |
}
|
61 |
|
62 |
/**
|
63 |
-
* Permanently deleted
|
|
|
64 |
*/
|
65 |
public function EventForumDeleted($post_id)
|
66 |
{
|
@@ -78,7 +120,8 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
78 |
}
|
79 |
|
80 |
/**
|
81 |
-
* Moved to Trash
|
|
|
82 |
*/
|
83 |
public function EventForumTrashed($post_id)
|
84 |
{
|
@@ -96,7 +139,8 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
96 |
}
|
97 |
|
98 |
/**
|
99 |
-
* Restored from Trash
|
|
|
100 |
*/
|
101 |
public function EventForumUntrashed($post_id)
|
102 |
{
|
@@ -113,6 +157,11 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
113 |
}
|
114 |
}
|
115 |
|
|
|
|
|
|
|
|
|
|
|
116 |
private function CheckBBPress($post)
|
117 |
{
|
118 |
switch ($post->post_type) {
|
@@ -125,6 +174,12 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
125 |
}
|
126 |
}
|
127 |
|
|
|
|
|
|
|
|
|
|
|
|
|
128 |
private function EventForumCreation($old_post, $new_post)
|
129 |
{
|
130 |
$original = isset($_POST['original_post_status']) ? $_POST['original_post_status'] : '';
|
@@ -153,6 +208,11 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
153 |
return 0;
|
154 |
}
|
155 |
|
|
|
|
|
|
|
|
|
|
|
156 |
private function EventForumChangedVisibility($post)
|
157 |
{
|
158 |
$result = 0;
|
@@ -192,6 +252,11 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
192 |
return $result;
|
193 |
}
|
194 |
|
|
|
|
|
|
|
|
|
|
|
195 |
private function EventForumChangedType($post)
|
196 |
{
|
197 |
$result = 0;
|
@@ -242,6 +307,11 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
242 |
return $result;
|
243 |
}
|
244 |
|
|
|
|
|
|
|
|
|
|
|
245 |
private function EventForumChangedStatus($post)
|
246 |
{
|
247 |
$result = 0;
|
@@ -294,6 +364,12 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
294 |
return $result;
|
295 |
}
|
296 |
|
|
|
|
|
|
|
|
|
|
|
|
|
297 |
private function EventForumChanged($old_post, $new_post)
|
298 |
{
|
299 |
$editorLink = $this->GetEditorLink($new_post);
|
@@ -356,6 +432,11 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
356 |
return 0;
|
357 |
}
|
358 |
|
|
|
|
|
|
|
|
|
|
|
359 |
private function EventForumByCode($post, $event)
|
360 |
{
|
361 |
$editorLink = $this->GetEditorLink($post);
|
@@ -366,6 +447,11 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
366 |
));
|
367 |
}
|
368 |
|
|
|
|
|
|
|
|
|
|
|
369 |
private function EventTopicByCode($post, $event)
|
370 |
{
|
371 |
$editorLink = $this->GetEditorLink($post);
|
@@ -378,6 +464,7 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
378 |
|
379 |
/**
|
380 |
* Trigger of ajax events generated in the Topic Grid
|
|
|
381 |
*/
|
382 |
public function TriggerAjaxChange()
|
383 |
{
|
@@ -432,6 +519,11 @@ class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
|
432 |
}
|
433 |
}
|
434 |
|
|
|
|
|
|
|
|
|
|
|
435 |
private function GetEditorLink($post)
|
436 |
{
|
437 |
$name = 'EditorLink';
|
1 |
<?php
|
2 |
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Support for BBPress Forum Plugin.
|
6 |
+
*
|
7 |
+
* 8000 User created new forum
|
8 |
+
* 8001 User changed status of a forum
|
9 |
+
* 8002 User changed visibility of a forum
|
10 |
+
* 8003 User changed the URL of a forum
|
11 |
+
* 8004 User changed order of a forum
|
12 |
+
* 8005 User moved forum to trash
|
13 |
+
* 8006 User permanently deleted forum
|
14 |
+
* 8007 User restored forum from trash
|
15 |
+
* 8008 User changed the parent of a forum
|
16 |
+
* 8011 User changed type of a forum
|
17 |
+
* 8014 User created new topic
|
18 |
+
* 8015 User changed status of a topic
|
19 |
+
* 8016 User changed type of a topic
|
20 |
+
* 8017 User changed URL of a topic
|
21 |
+
* 8018 User changed the forum of a topic
|
22 |
+
* 8019 User moved topic to trash
|
23 |
+
* 8020 User permanently deleted topic
|
24 |
+
* 8021 User restored topic from trash
|
25 |
+
* 8022 User changed visibility of a topic
|
26 |
*/
|
27 |
class WSAL_Sensors_BBPress extends WSAL_AbstractSensor
|
28 |
{
|
29 |
+
/**
|
30 |
+
* @var string old permalink
|
31 |
+
*/
|
32 |
protected $_OldLink = null;
|
33 |
|
34 |
+
/**
|
35 |
+
* Listening to events using WP hooks.
|
36 |
+
*/
|
37 |
public function HookEvents()
|
38 |
{
|
39 |
if (current_user_can("edit_posts")) {
|
45 |
add_action('untrash_post', array($this, 'EventForumUntrashed'));
|
46 |
}
|
47 |
|
48 |
+
/**
|
49 |
+
* Triggered when a user accesses the admin area.
|
50 |
+
*/
|
51 |
public function EventAdminInit()
|
52 |
{
|
53 |
// load old data, if applicable
|
56 |
$this->TriggerAjaxChange();
|
57 |
}
|
58 |
|
59 |
+
/**
|
60 |
+
* Retrieve Old data.
|
61 |
+
* @global mixed $_POST post data
|
62 |
+
*/
|
63 |
protected function RetrieveOldData()
|
64 |
{
|
65 |
if (isset($_POST) && isset($_POST['post_ID'])
|
71 |
}
|
72 |
}
|
73 |
|
74 |
+
/**
|
75 |
+
* Calls event forum changes.
|
76 |
+
* @param integer $post_ID post ID
|
77 |
+
* @param stdClass $newpost the new post
|
78 |
+
* @param stdClass $oldpost the old post
|
79 |
+
*/
|
80 |
public function CheckForumChange($post_ID, $newpost, $oldpost)
|
81 |
{
|
82 |
if ($this->CheckBBPress($oldpost)) {
|
101 |
}
|
102 |
|
103 |
/**
|
104 |
+
* Permanently deleted.
|
105 |
+
* @param integer $post_id post ID
|
106 |
*/
|
107 |
public function EventForumDeleted($post_id)
|
108 |
{
|
120 |
}
|
121 |
|
122 |
/**
|
123 |
+
* Moved to Trash.
|
124 |
+
* @param integer $post_id post ID
|
125 |
*/
|
126 |
public function EventForumTrashed($post_id)
|
127 |
{
|
139 |
}
|
140 |
|
141 |
/**
|
142 |
+
* Restored from Trash.
|
143 |
+
* @param integer $post_id post ID
|
144 |
*/
|
145 |
public function EventForumUntrashed($post_id)
|
146 |
{
|
157 |
}
|
158 |
}
|
159 |
|
160 |
+
/**
|
161 |
+
* Check post type.
|
162 |
+
* @param stdClass $post post
|
163 |
+
* @return boolean
|
164 |
+
*/
|
165 |
private function CheckBBPress($post)
|
166 |
{
|
167 |
switch ($post->post_type) {
|
174 |
}
|
175 |
}
|
176 |
|
177 |
+
/**
|
178 |
+
* Event post creation.
|
179 |
+
* @param stdClass $old_post the old post
|
180 |
+
* @param stdClass $new_post the new post
|
181 |
+
* @return boolean
|
182 |
+
*/
|
183 |
private function EventForumCreation($old_post, $new_post)
|
184 |
{
|
185 |
$original = isset($_POST['original_post_status']) ? $_POST['original_post_status'] : '';
|
208 |
return 0;
|
209 |
}
|
210 |
|
211 |
+
/**
|
212 |
+
* Event post changed visibility.
|
213 |
+
* @param stdClass $post the post
|
214 |
+
* @return boolean $result
|
215 |
+
*/
|
216 |
private function EventForumChangedVisibility($post)
|
217 |
{
|
218 |
$result = 0;
|
252 |
return $result;
|
253 |
}
|
254 |
|
255 |
+
/**
|
256 |
+
* Event post changed type.
|
257 |
+
* @param stdClass $post the post
|
258 |
+
* @return boolean $result
|
259 |
+
*/
|
260 |
private function EventForumChangedType($post)
|
261 |
{
|
262 |
$result = 0;
|
307 |
return $result;
|
308 |
}
|
309 |
|
310 |
+
/**
|
311 |
+
* Event post changed status.
|
312 |
+
* @param stdClass $post the post
|
313 |
+
* @return boolean $result
|
314 |
+
*/
|
315 |
private function EventForumChangedStatus($post)
|
316 |
{
|
317 |
$result = 0;
|
364 |
return $result;
|
365 |
}
|
366 |
|
367 |
+
/**
|
368 |
+
* Event post changed (order, parent, URL).
|
369 |
+
* @param stdClass $old_post the old post
|
370 |
+
* @param stdClass $new_post the new post
|
371 |
+
* @return boolean $result
|
372 |
+
*/
|
373 |
private function EventForumChanged($old_post, $new_post)
|
374 |
{
|
375 |
$editorLink = $this->GetEditorLink($new_post);
|
432 |
return 0;
|
433 |
}
|
434 |
|
435 |
+
/**
|
436 |
+
* Trigger Event (Forum).
|
437 |
+
* @param stdClass $post the post
|
438 |
+
* @param integer $event event code
|
439 |
+
*/
|
440 |
private function EventForumByCode($post, $event)
|
441 |
{
|
442 |
$editorLink = $this->GetEditorLink($post);
|
447 |
));
|
448 |
}
|
449 |
|
450 |
+
/**
|
451 |
+
* Trigger Event (Topic).
|
452 |
+
* @param stdClass $post the post
|
453 |
+
* @param integer $event event code
|
454 |
+
*/
|
455 |
private function EventTopicByCode($post, $event)
|
456 |
{
|
457 |
$editorLink = $this->GetEditorLink($post);
|
464 |
|
465 |
/**
|
466 |
* Trigger of ajax events generated in the Topic Grid
|
467 |
+
* @global mixed $_GET Get data
|
468 |
*/
|
469 |
public function TriggerAjaxChange()
|
470 |
{
|
519 |
}
|
520 |
}
|
521 |
|
522 |
+
/**
|
523 |
+
* Get editor link.
|
524 |
+
* @param stdClass $post the post
|
525 |
+
* @return array $aLink name and value link
|
526 |
+
*/
|
527 |
private function GetEditorLink($post)
|
528 |
{
|
529 |
$name = 'EditorLink';
|
classes/Sensors/Comments.php
CHANGED
@@ -1,8 +1,25 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_Comments extends WSAL_AbstractSensor
|
4 |
{
|
5 |
-
|
|
|
|
|
6 |
public function HookEvents()
|
7 |
{
|
8 |
add_action('edit_comment', array($this, 'EventCommentEdit'), 10, 1);
|
@@ -15,12 +32,22 @@ class WSAL_Sensors_Comments extends WSAL_AbstractSensor
|
|
15 |
add_action('comment_post', array($this, 'EventComment'), 10, 2);
|
16 |
}
|
17 |
|
|
|
|
|
|
|
|
|
18 |
public function EventCommentEdit($comment_ID)
|
19 |
{
|
20 |
$comment = get_comment($comment_ID);
|
21 |
$this->EventGeneric($comment_ID, 2093);
|
22 |
}
|
23 |
|
|
|
|
|
|
|
|
|
|
|
|
|
24 |
public function EventCommentApprove($new_status, $old_status, $comment)
|
25 |
{
|
26 |
if (!empty($comment) && $old_status != $new_status) {
|
@@ -42,26 +69,46 @@ class WSAL_Sensors_Comments extends WSAL_AbstractSensor
|
|
42 |
}
|
43 |
}
|
44 |
|
|
|
|
|
|
|
|
|
45 |
public function EventCommentSpam($comment_ID)
|
46 |
{
|
47 |
$this->EventGeneric($comment_ID, 2094);
|
48 |
}
|
49 |
|
|
|
|
|
|
|
|
|
50 |
public function EventCommentUnspam($comment_ID)
|
51 |
{
|
52 |
$this->EventGeneric($comment_ID, 2095);
|
53 |
}
|
54 |
|
|
|
|
|
|
|
|
|
55 |
public function EventCommentTrash($comment_ID)
|
56 |
{
|
57 |
$this->EventGeneric($comment_ID, 2096);
|
58 |
}
|
59 |
|
|
|
|
|
|
|
|
|
60 |
public function EventCommentUntrash($comment_ID)
|
61 |
{
|
62 |
$this->EventGeneric($comment_ID, 2097);
|
63 |
}
|
64 |
|
|
|
|
|
|
|
|
|
65 |
public function EventCommentDeleted($comment_ID)
|
66 |
{
|
67 |
$this->EventGeneric($comment_ID, 2098);
|
@@ -100,6 +147,11 @@ class WSAL_Sensors_Comments extends WSAL_AbstractSensor
|
|
100 |
}
|
101 |
}
|
102 |
|
|
|
|
|
|
|
|
|
|
|
103 |
private function EventGeneric($comment_ID, $alert_code)
|
104 |
{
|
105 |
$comment = get_comment($comment_ID);
|
@@ -120,6 +172,8 @@ class WSAL_Sensors_Comments extends WSAL_AbstractSensor
|
|
120 |
/**
|
121 |
* Shows the username if the comment is owned by a user
|
122 |
* and the email if the comment was posted by a non WordPress user
|
|
|
|
|
123 |
*/
|
124 |
private function CheckAuthor($comment)
|
125 |
{
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Wordpress comments.
|
6 |
+
*
|
7 |
+
* 2090 User approved a comment
|
8 |
+
* 2091 User unapproved a comment
|
9 |
+
* 2092 User replied to a comment
|
10 |
+
* 2093 User edited a comment
|
11 |
+
* 2094 User marked a comment as Spam
|
12 |
+
* 2095 User marked a comment as Not Spam
|
13 |
+
* 2096 User moved a comment to trash
|
14 |
+
* 2097 User restored a comment from the trash
|
15 |
+
* 2098 User permanently deleted a comment
|
16 |
+
* 2099 User posted a comment
|
17 |
+
*/
|
18 |
class WSAL_Sensors_Comments extends WSAL_AbstractSensor
|
19 |
{
|
20 |
+
/**
|
21 |
+
* Listening to events using WP hooks.
|
22 |
+
*/
|
23 |
public function HookEvents()
|
24 |
{
|
25 |
add_action('edit_comment', array($this, 'EventCommentEdit'), 10, 1);
|
32 |
add_action('comment_post', array($this, 'EventComment'), 10, 2);
|
33 |
}
|
34 |
|
35 |
+
/**
|
36 |
+
* Trigger comment edit.
|
37 |
+
* @param integer $comment_ID comment ID
|
38 |
+
*/
|
39 |
public function EventCommentEdit($comment_ID)
|
40 |
{
|
41 |
$comment = get_comment($comment_ID);
|
42 |
$this->EventGeneric($comment_ID, 2093);
|
43 |
}
|
44 |
|
45 |
+
/**
|
46 |
+
* Trigger comment status.
|
47 |
+
* @param string $new_status new status
|
48 |
+
* @param string $old_status old status
|
49 |
+
* @param stdClass $comment comment
|
50 |
+
*/
|
51 |
public function EventCommentApprove($new_status, $old_status, $comment)
|
52 |
{
|
53 |
if (!empty($comment) && $old_status != $new_status) {
|
69 |
}
|
70 |
}
|
71 |
|
72 |
+
/**
|
73 |
+
* Trigger comment spam.
|
74 |
+
* @param integer $comment_ID comment ID
|
75 |
+
*/
|
76 |
public function EventCommentSpam($comment_ID)
|
77 |
{
|
78 |
$this->EventGeneric($comment_ID, 2094);
|
79 |
}
|
80 |
|
81 |
+
/**
|
82 |
+
* Trigger comment unspam.
|
83 |
+
* @param integer $comment_ID comment ID
|
84 |
+
*/
|
85 |
public function EventCommentUnspam($comment_ID)
|
86 |
{
|
87 |
$this->EventGeneric($comment_ID, 2095);
|
88 |
}
|
89 |
|
90 |
+
/**
|
91 |
+
* Trigger comment trash.
|
92 |
+
* @param integer $comment_ID comment ID
|
93 |
+
*/
|
94 |
public function EventCommentTrash($comment_ID)
|
95 |
{
|
96 |
$this->EventGeneric($comment_ID, 2096);
|
97 |
}
|
98 |
|
99 |
+
/**
|
100 |
+
* Trigger comment untrash.
|
101 |
+
* @param integer $comment_ID comment ID
|
102 |
+
*/
|
103 |
public function EventCommentUntrash($comment_ID)
|
104 |
{
|
105 |
$this->EventGeneric($comment_ID, 2097);
|
106 |
}
|
107 |
|
108 |
+
/**
|
109 |
+
* Trigger comment deleted.
|
110 |
+
* @param integer $comment_ID comment ID
|
111 |
+
*/
|
112 |
public function EventCommentDeleted($comment_ID)
|
113 |
{
|
114 |
$this->EventGeneric($comment_ID, 2098);
|
147 |
}
|
148 |
}
|
149 |
|
150 |
+
/**
|
151 |
+
* Trigger generic event.
|
152 |
+
* @param integer $comment_ID comment ID
|
153 |
+
* @param integer $alert_code event code
|
154 |
+
*/
|
155 |
private function EventGeneric($comment_ID, $alert_code)
|
156 |
{
|
157 |
$comment = get_comment($comment_ID);
|
172 |
/**
|
173 |
* Shows the username if the comment is owned by a user
|
174 |
* and the email if the comment was posted by a non WordPress user
|
175 |
+
* @param stdClass $comment comment
|
176 |
+
* @return string author username or email
|
177 |
*/
|
178 |
private function CheckAuthor($comment)
|
179 |
{
|
classes/Sensors/Content.php
CHANGED
@@ -1,8 +1,113 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
4 |
{
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
5 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
6 |
public function HookEvents()
|
7 |
{
|
8 |
if (current_user_can("edit_posts")) {
|
@@ -22,6 +127,14 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
22 |
add_filter('post_edit_form_tag', array($this, 'EditingPost'), 10, 1);
|
23 |
}
|
24 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
25 |
protected function GetEventTypeForPostType($post, $typePost, $typePage, $typeCustom)
|
26 |
{
|
27 |
switch ($post->post_type) {
|
@@ -34,12 +147,9 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
34 |
}
|
35 |
}
|
36 |
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
protected $_OldTmpl = null;
|
41 |
-
protected $_OldStky = null;
|
42 |
-
|
43 |
public function EventWordpressInit()
|
44 |
{
|
45 |
// load old data, if applicable
|
@@ -48,6 +158,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
48 |
$this->CheckCategoryDeletion();
|
49 |
}
|
50 |
|
|
|
|
|
|
|
|
|
51 |
protected function RetrieveOldData()
|
52 |
{
|
53 |
if (isset($_POST) && isset($_POST['post_ID'])
|
@@ -63,6 +177,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
63 |
}
|
64 |
}
|
65 |
|
|
|
|
|
|
|
|
|
|
|
66 |
protected function GetPostTemplate($post)
|
67 |
{
|
68 |
$id = $post->ID;
|
@@ -84,11 +203,22 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
84 |
return get_query_template('page', $templates);
|
85 |
}
|
86 |
|
|
|
|
|
|
|
|
|
|
|
87 |
protected function GetPostCategories($post)
|
88 |
{
|
89 |
return wp_get_post_categories($post->ID, array('fields' => 'names'));
|
90 |
}
|
91 |
|
|
|
|
|
|
|
|
|
|
|
|
|
92 |
public function EventPostChanged($newStatus, $oldStatus, $post)
|
93 |
{
|
94 |
// ignorable states
|
@@ -146,6 +276,12 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
146 |
}
|
147 |
}
|
148 |
|
|
|
|
|
|
|
|
|
|
|
|
|
149 |
protected function CheckPostCreation($oldPost, $newPost)
|
150 |
{
|
151 |
$WPActions = array('editpost', 'heartbeat');
|
@@ -191,6 +327,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
191 |
}
|
192 |
}
|
193 |
|
|
|
|
|
|
|
|
|
194 |
public function EventPublishFuture($post_id)
|
195 |
{
|
196 |
$post = get_post($post_id);
|
@@ -208,6 +348,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
208 |
}
|
209 |
}
|
210 |
|
|
|
|
|
|
|
|
|
211 |
public function EventPostDeleted($post_id)
|
212 |
{
|
213 |
$post = get_post($post_id);
|
@@ -234,6 +378,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
234 |
}
|
235 |
}
|
236 |
|
|
|
|
|
|
|
|
|
237 |
public function EventPostTrashed($post_id)
|
238 |
{
|
239 |
$post = get_post($post_id);
|
@@ -251,6 +399,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
251 |
));
|
252 |
}
|
253 |
|
|
|
|
|
|
|
|
|
254 |
public function EventPostUntrashed($post_id)
|
255 |
{
|
256 |
$post = get_post($post_id);
|
@@ -267,6 +419,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
267 |
));
|
268 |
}
|
269 |
|
|
|
|
|
|
|
|
|
|
|
270 |
protected function CheckDateChange($oldpost, $newpost)
|
271 |
{
|
272 |
$from = strtotime($oldpost->post_date);
|
@@ -294,7 +451,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
294 |
return 0;
|
295 |
}
|
296 |
|
297 |
-
|
|
|
|
|
|
|
|
|
298 |
protected function CheckReviewPendingChange($oldpost, $newpost)
|
299 |
{
|
300 |
if ($oldpost->post_status == 'pending') {
|
@@ -310,6 +471,12 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
310 |
return 0;
|
311 |
}
|
312 |
|
|
|
|
|
|
|
|
|
|
|
|
|
313 |
protected function CheckCategoriesChange($oldCats, $newCats, $post)
|
314 |
{
|
315 |
$oldCats = implode(', ', $oldCats);
|
@@ -331,6 +498,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
331 |
}
|
332 |
}
|
333 |
|
|
|
|
|
|
|
|
|
|
|
334 |
protected function CheckAuthorChange($oldpost, $newpost)
|
335 |
{
|
336 |
if ($oldpost->post_author != $newpost->post_author) {
|
@@ -352,6 +524,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
352 |
}
|
353 |
}
|
354 |
|
|
|
|
|
|
|
|
|
|
|
355 |
protected function CheckStatusChange($oldpost, $newpost)
|
356 |
{
|
357 |
if ($oldpost->post_status != $newpost->post_status) {
|
@@ -382,6 +559,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
382 |
}
|
383 |
}
|
384 |
|
|
|
|
|
|
|
|
|
|
|
385 |
protected function CheckParentChange($oldpost, $newpost)
|
386 |
{
|
387 |
if ($oldpost->post_parent != $newpost->post_parent) {
|
@@ -403,6 +585,12 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
403 |
}
|
404 |
}
|
405 |
|
|
|
|
|
|
|
|
|
|
|
|
|
406 |
protected function CheckPermalinkChange($oldLink, $newLink, $post)
|
407 |
{
|
408 |
if ($oldLink != $newLink) {
|
@@ -421,6 +609,13 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
421 |
return 0;
|
422 |
}
|
423 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
424 |
protected function CheckVisibilityChange($oldpost, $newpost, $oldStatus, $newStatus)
|
425 |
{
|
426 |
if ($oldStatus == 'draft' || $newStatus == 'draft') {
|
@@ -461,6 +656,12 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
461 |
}
|
462 |
}
|
463 |
|
|
|
|
|
|
|
|
|
|
|
|
|
464 |
protected function CheckTemplateChange($oldTmpl, $newTmpl, $post)
|
465 |
{
|
466 |
if ($oldTmpl != $newTmpl) {
|
@@ -482,6 +683,12 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
482 |
}
|
483 |
}
|
484 |
|
|
|
|
|
|
|
|
|
|
|
|
|
485 |
protected function CheckStickyChange($oldStky, $newStky, $post)
|
486 |
{
|
487 |
if ($oldStky != $newStky) {
|
@@ -498,6 +705,12 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
498 |
}
|
499 |
}
|
500 |
|
|
|
|
|
|
|
|
|
|
|
|
|
501 |
public function CheckModificationChange($post_ID, $oldpost, $newpost)
|
502 |
{
|
503 |
if ($this->CheckOtherSensors($oldpost)) {
|
@@ -541,6 +754,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
541 |
}
|
542 |
}
|
543 |
|
|
|
|
|
|
|
|
|
544 |
public function EventCategoryCreation($category_id)
|
545 |
{
|
546 |
$category = get_category($category_id);
|
@@ -552,6 +769,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
552 |
));
|
553 |
}
|
554 |
|
|
|
|
|
|
|
|
|
555 |
protected function CheckCategoryDeletion()
|
556 |
{
|
557 |
if (empty($_POST)) {
|
@@ -585,6 +806,10 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
585 |
}
|
586 |
}
|
587 |
|
|
|
|
|
|
|
|
|
588 |
public function EventChangedCategoryParent()
|
589 |
{
|
590 |
if (empty($_POST)) {
|
@@ -615,6 +840,12 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
615 |
}
|
616 |
}
|
617 |
|
|
|
|
|
|
|
|
|
|
|
|
|
618 |
private function CheckAutoDraft($code, $title)
|
619 |
{
|
620 |
if ($code == 2008 && $title == "auto-draft") {
|
@@ -629,6 +860,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
629 |
}
|
630 |
}
|
631 |
|
|
|
|
|
|
|
|
|
|
|
632 |
private function getRevisionLink($revision_id)
|
633 |
{
|
634 |
if (!empty($revision_id)) {
|
@@ -638,6 +874,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
638 |
}
|
639 |
}
|
640 |
|
|
|
|
|
|
|
|
|
|
|
641 |
private function getCategoryLink($category_id)
|
642 |
{
|
643 |
if (!empty($category_id)) {
|
@@ -650,6 +891,7 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
650 |
/**
|
651 |
* Ignore post from BBPress, WooCommerce Plugin
|
652 |
* Triggered on the Sensors
|
|
|
653 |
*/
|
654 |
private function CheckOtherSensors($post)
|
655 |
{
|
@@ -665,7 +907,9 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
665 |
}
|
666 |
|
667 |
/**
|
668 |
-
* Triggered after save post for add revision link
|
|
|
|
|
669 |
*/
|
670 |
public function SetRevisionLink($post_id, $post, $update)
|
671 |
{
|
@@ -686,7 +930,9 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
686 |
}
|
687 |
|
688 |
/**
|
689 |
-
* Alerts for Viewing of Posts, Pages and Custom Posts
|
|
|
|
|
690 |
*/
|
691 |
public function ViewingPost($title, $post = null)
|
692 |
{
|
@@ -698,7 +944,7 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
698 |
$currentPath = $_SERVER["REQUEST_URI"];
|
699 |
if (!empty($_SERVER["HTTP_REFERER"])
|
700 |
&& strpos($_SERVER["HTTP_REFERER"], $currentPath) !== false) {
|
701 |
-
//Ignore this if we were on the same page so we avoid double audit entries
|
702 |
return $title;
|
703 |
}
|
704 |
if (!empty($post->post_title)) {
|
@@ -715,7 +961,8 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
715 |
}
|
716 |
|
717 |
/**
|
718 |
-
* Alerts for Editing of Posts, Pages and Custom Posts
|
|
|
719 |
*/
|
720 |
public function EditingPost($post)
|
721 |
{
|
@@ -747,7 +994,9 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
747 |
}
|
748 |
|
749 |
/**
|
750 |
-
* Check if the alert was triggered
|
|
|
|
|
751 |
*/
|
752 |
private function WasTriggered($alert_id)
|
753 |
{
|
@@ -763,6 +1012,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
763 |
return false;
|
764 |
}
|
765 |
|
|
|
|
|
|
|
|
|
|
|
766 |
private function CheckTitleChange($oldpost, $newpost)
|
767 |
{
|
768 |
if ($oldpost->post_title != $newpost->post_title) {
|
@@ -778,6 +1032,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
778 |
return 0;
|
779 |
}
|
780 |
|
|
|
|
|
|
|
|
|
|
|
781 |
private function CheckCommentsPings($oldpost, $newpost)
|
782 |
{
|
783 |
$result = 0;
|
@@ -818,6 +1077,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
818 |
return $result;
|
819 |
}
|
820 |
|
|
|
|
|
|
|
|
|
|
|
821 |
private function GetCommentsPingsEvent($post, $status)
|
822 |
{
|
823 |
if ($post->post_type == 'post') {
|
@@ -852,6 +1116,11 @@ class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
|
852 |
return $event;
|
853 |
}
|
854 |
|
|
|
|
|
|
|
|
|
|
|
855 |
private function GetEditorLink($post)
|
856 |
{
|
857 |
$name = 'EditorLink';
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Wordpress contents (posts, pages and custom posts).
|
6 |
+
*
|
7 |
+
* 2000 User created a new blog post and saved it as draft
|
8 |
+
* 2001 User published a blog post
|
9 |
+
* 2002 User modified a published blog post
|
10 |
+
* 2003 User modified a draft blog post
|
11 |
+
* 2008 User permanently deleted a blog post from the trash
|
12 |
+
* 2012 User moved a blog post to the trash
|
13 |
+
* 2014 User restored a blog post from trash
|
14 |
+
* 2016 User changed blog post category
|
15 |
+
* 2017 User changed blog post URL
|
16 |
+
* 2019 User changed blog post author
|
17 |
+
* 2021 User changed blog post status
|
18 |
+
* 2023 User created new category
|
19 |
+
* 2024 User deleted category
|
20 |
+
* 2025 User changed the visibility of a blog post
|
21 |
+
* 2027 User changed the date of a blog post
|
22 |
+
* 2049 User set a post as sticky
|
23 |
+
* 2050 User removed post from sticky
|
24 |
+
* 2052 User changed generic tables
|
25 |
+
* 2065 User modified content for a published post
|
26 |
+
* 2068 User modified content for a draft post
|
27 |
+
* 2072 User modified content of a post
|
28 |
+
* 2073 User submitted a post for review
|
29 |
+
* 2074 User scheduled a post
|
30 |
+
* 2086 User changed title of a post
|
31 |
+
* 2100 User opened a post in the editor
|
32 |
+
* 2101 User viewed a post
|
33 |
+
* 2111 User disabled Comments/Trackbacks and Pingbacks on a published post
|
34 |
+
* 2112 User enabled Comments/Trackbacks and Pingbacks on a published post
|
35 |
+
* 2113 User disabled Comments/Trackbacks and Pingbacks on a draft post
|
36 |
+
* 2114 User enabled Comments/Trackbacks and Pingbacks on a draft post
|
37 |
+
* 2004 User created a new WordPress page and saved it as draft
|
38 |
+
* 2005 User published a WordPress page
|
39 |
+
* 2006 User modified a published WordPress page
|
40 |
+
* 2007 User modified a draft WordPress page
|
41 |
+
* 2009 User permanently deleted a page from the trash
|
42 |
+
* 2013 User moved WordPress page to the trash
|
43 |
+
* 2015 User restored a WordPress page from trash
|
44 |
+
* 2018 User changed page URL
|
45 |
+
* 2020 User changed page author
|
46 |
+
* 2022 User changed page status
|
47 |
+
* 2026 User changed the visibility of a page post
|
48 |
+
* 2028 User changed the date of a page post
|
49 |
+
* 2047 User changed the parent of a page
|
50 |
+
* 2048 User changed the template of a page
|
51 |
+
* 2066 User modified content for a published page
|
52 |
+
* 2069 User modified content for a draft page
|
53 |
+
* 2075 User scheduled a page
|
54 |
+
* 2087 User changed title of a page
|
55 |
+
* 2102 User opened a page in the editor
|
56 |
+
* 2103 User viewed a page
|
57 |
+
* 2115 User disabled Comments/Trackbacks and Pingbacks on a published page
|
58 |
+
* 2116 User enabled Comments/Trackbacks and Pingbacks on a published page
|
59 |
+
* 2117 User disabled Comments/Trackbacks and Pingbacks on a draft page
|
60 |
+
* 2118 User enabled Comments/Trackbacks and Pingbacks on a draft page
|
61 |
+
* 2029 User created a new post with custom post type and saved it as draft
|
62 |
+
* 2030 User published a post with custom post type
|
63 |
+
* 2031 User modified a post with custom post type
|
64 |
+
* 2032 User modified a draft post with custom post type
|
65 |
+
* 2033 User permanently deleted post with custom post type
|
66 |
+
* 2034 User moved post with custom post type to trash
|
67 |
+
* 2035 User restored post with custom post type from trash
|
68 |
+
* 2036 User changed the category of a post with custom post type
|
69 |
+
* 2037 User changed the URL of a post with custom post type
|
70 |
+
* 2038 User changed the author or post with custom post type
|
71 |
+
* 2039 User changed the status of post with custom post type
|
72 |
+
* 2040 User changed the visibility of a post with custom post type
|
73 |
+
* 2041 User changed the date of post with custom post type
|
74 |
+
* 2067 User modified content for a published custom post type
|
75 |
+
* 2070 User modified content for a draft custom post type
|
76 |
+
* 2076 User scheduled a custom post type
|
77 |
+
* 2088 User changed title of a custom post type
|
78 |
+
* 2104 User opened a custom post type in the editor
|
79 |
+
* 2105 User viewed a custom post type
|
80 |
+
*/
|
81 |
class WSAL_Sensors_Content extends WSAL_AbstractSensor
|
82 |
{
|
83 |
+
/**
|
84 |
+
* @var stdClass old post
|
85 |
+
*/
|
86 |
+
protected $_OldPost = null;
|
87 |
+
|
88 |
+
/**
|
89 |
+
* @var string old permalink
|
90 |
+
*/
|
91 |
+
protected $_OldLink = null;
|
92 |
+
|
93 |
+
/**
|
94 |
+
* @var array old categories
|
95 |
+
*/
|
96 |
+
protected $_OldCats = null;
|
97 |
|
98 |
+
/**
|
99 |
+
* @var string old path to file
|
100 |
+
*/
|
101 |
+
protected $_OldTmpl = null;
|
102 |
+
|
103 |
+
/**
|
104 |
+
* @var boolean old post is marked as sticky
|
105 |
+
*/
|
106 |
+
protected $_OldStky = null;
|
107 |
+
|
108 |
+
/**
|
109 |
+
* Listening to events using WP hooks.
|
110 |
+
*/
|
111 |
public function HookEvents()
|
112 |
{
|
113 |
if (current_user_can("edit_posts")) {
|
127 |
add_filter('post_edit_form_tag', array($this, 'EditingPost'), 10, 1);
|
128 |
}
|
129 |
|
130 |
+
/**
|
131 |
+
* Gets the alert code based on the type of post.
|
132 |
+
* @param stdClass $post the post
|
133 |
+
* @param integer $typePost alert code type post
|
134 |
+
* @param integer $typePage alert code type page
|
135 |
+
* @param integer $typeCustom alert code type custom
|
136 |
+
* @return integer alert code
|
137 |
+
*/
|
138 |
protected function GetEventTypeForPostType($post, $typePost, $typePage, $typeCustom)
|
139 |
{
|
140 |
switch ($post->post_type) {
|
147 |
}
|
148 |
}
|
149 |
|
150 |
+
/**
|
151 |
+
* Triggered when a user accesses the admin area.
|
152 |
+
*/
|
|
|
|
|
|
|
153 |
public function EventWordpressInit()
|
154 |
{
|
155 |
// load old data, if applicable
|
158 |
$this->CheckCategoryDeletion();
|
159 |
}
|
160 |
|
161 |
+
/**
|
162 |
+
* Retrieve Old data.
|
163 |
+
* @global mixed $_POST post data
|
164 |
+
*/
|
165 |
protected function RetrieveOldData()
|
166 |
{
|
167 |
if (isset($_POST) && isset($_POST['post_ID'])
|
177 |
}
|
178 |
}
|
179 |
|
180 |
+
/**
|
181 |
+
* Get the template path.
|
182 |
+
* @param stdClass $post the post
|
183 |
+
* @return string full path to file
|
184 |
+
*/
|
185 |
protected function GetPostTemplate($post)
|
186 |
{
|
187 |
$id = $post->ID;
|
203 |
return get_query_template('page', $templates);
|
204 |
}
|
205 |
|
206 |
+
/**
|
207 |
+
* Get post categories (array of category names).
|
208 |
+
* @param stdClass $post the post
|
209 |
+
* @return array list of categories
|
210 |
+
*/
|
211 |
protected function GetPostCategories($post)
|
212 |
{
|
213 |
return wp_get_post_categories($post->ID, array('fields' => 'names'));
|
214 |
}
|
215 |
|
216 |
+
/**
|
217 |
+
* Check all the post changes.
|
218 |
+
* @param string $newStatus new status
|
219 |
+
* @param string $oldStatus old status
|
220 |
+
* @param stdClass $post the post
|
221 |
+
*/
|
222 |
public function EventPostChanged($newStatus, $oldStatus, $post)
|
223 |
{
|
224 |
// ignorable states
|
276 |
}
|
277 |
}
|
278 |
|
279 |
+
/**
|
280 |
+
* Check post creation.
|
281 |
+
* @global array $_POST
|
282 |
+
* @param stdClass $oldPost old post
|
283 |
+
* @param stdClass $newPost new post
|
284 |
+
*/
|
285 |
protected function CheckPostCreation($oldPost, $newPost)
|
286 |
{
|
287 |
$WPActions = array('editpost', 'heartbeat');
|
327 |
}
|
328 |
}
|
329 |
|
330 |
+
/**
|
331 |
+
* Post future publishing.
|
332 |
+
* @param integer $post_id post ID
|
333 |
+
*/
|
334 |
public function EventPublishFuture($post_id)
|
335 |
{
|
336 |
$post = get_post($post_id);
|
348 |
}
|
349 |
}
|
350 |
|
351 |
+
/**
|
352 |
+
* Post permanently deleted.
|
353 |
+
* @param integer $post_id post ID
|
354 |
+
*/
|
355 |
public function EventPostDeleted($post_id)
|
356 |
{
|
357 |
$post = get_post($post_id);
|
378 |
}
|
379 |
}
|
380 |
|
381 |
+
/**
|
382 |
+
* Post moved to the trash.
|
383 |
+
* @param integer $post_id post ID
|
384 |
+
*/
|
385 |
public function EventPostTrashed($post_id)
|
386 |
{
|
387 |
$post = get_post($post_id);
|
399 |
));
|
400 |
}
|
401 |
|
402 |
+
/**
|
403 |
+
* Post restored from trash.
|
404 |
+
* @param integer $post_id post ID
|
405 |
+
*/
|
406 |
public function EventPostUntrashed($post_id)
|
407 |
{
|
408 |
$post = get_post($post_id);
|
419 |
));
|
420 |
}
|
421 |
|
422 |
+
/**
|
423 |
+
* Post date changed.
|
424 |
+
* @param stdClass $oldPost old post
|
425 |
+
* @param stdClass $newPost new post
|
426 |
+
*/
|
427 |
protected function CheckDateChange($oldpost, $newpost)
|
428 |
{
|
429 |
$from = strtotime($oldpost->post_date);
|
451 |
return 0;
|
452 |
}
|
453 |
|
454 |
+
/**
|
455 |
+
* Revision used.
|
456 |
+
* @param stdClass $oldPost old post
|
457 |
+
* @param stdClass $newPost new post
|
458 |
+
*/
|
459 |
protected function CheckReviewPendingChange($oldpost, $newpost)
|
460 |
{
|
461 |
if ($oldpost->post_status == 'pending') {
|
471 |
return 0;
|
472 |
}
|
473 |
|
474 |
+
/**
|
475 |
+
* Categories changed.
|
476 |
+
* @param array $oldCats old categories
|
477 |
+
* @param array $newCats new categories
|
478 |
+
* @param stdClass $post the post
|
479 |
+
*/
|
480 |
protected function CheckCategoriesChange($oldCats, $newCats, $post)
|
481 |
{
|
482 |
$oldCats = implode(', ', $oldCats);
|
498 |
}
|
499 |
}
|
500 |
|
501 |
+
/**
|
502 |
+
* Author changed.
|
503 |
+
* @param stdClass $oldPost old post
|
504 |
+
* @param stdClass $newPost new post
|
505 |
+
*/
|
506 |
protected function CheckAuthorChange($oldpost, $newpost)
|
507 |
{
|
508 |
if ($oldpost->post_author != $newpost->post_author) {
|
524 |
}
|
525 |
}
|
526 |
|
527 |
+
/**
|
528 |
+
* Status changed.
|
529 |
+
* @param stdClass $oldPost old post
|
530 |
+
* @param stdClass $newPost new post
|
531 |
+
*/
|
532 |
protected function CheckStatusChange($oldpost, $newpost)
|
533 |
{
|
534 |
if ($oldpost->post_status != $newpost->post_status) {
|
559 |
}
|
560 |
}
|
561 |
|
562 |
+
/**
|
563 |
+
* Post parent changed.
|
564 |
+
* @param stdClass $oldPost old post
|
565 |
+
* @param stdClass $newPost new post
|
566 |
+
*/
|
567 |
protected function CheckParentChange($oldpost, $newpost)
|
568 |
{
|
569 |
if ($oldpost->post_parent != $newpost->post_parent) {
|
585 |
}
|
586 |
}
|
587 |
|
588 |
+
/**
|
589 |
+
* Permalink changed.
|
590 |
+
* @param string $oldLink old permalink
|
591 |
+
* @param string $newLink new permalink
|
592 |
+
* @param stdClass $post the post
|
593 |
+
*/
|
594 |
protected function CheckPermalinkChange($oldLink, $newLink, $post)
|
595 |
{
|
596 |
if ($oldLink != $newLink) {
|
609 |
return 0;
|
610 |
}
|
611 |
|
612 |
+
/**
|
613 |
+
* Post visibility changed.
|
614 |
+
* @param stdClass $oldPost old post
|
615 |
+
* @param stdClass $newPost new post
|
616 |
+
* @param string $oldStatus old status
|
617 |
+
* @param string $newStatus new status
|
618 |
+
*/
|
619 |
protected function CheckVisibilityChange($oldpost, $newpost, $oldStatus, $newStatus)
|
620 |
{
|
621 |
if ($oldStatus == 'draft' || $newStatus == 'draft') {
|
656 |
}
|
657 |
}
|
658 |
|
659 |
+
/**
|
660 |
+
* Post template changed.
|
661 |
+
* @param string $oldTmpl old template path
|
662 |
+
* @param string $newTmpl new template path
|
663 |
+
* @param stdClass $post the post
|
664 |
+
*/
|
665 |
protected function CheckTemplateChange($oldTmpl, $newTmpl, $post)
|
666 |
{
|
667 |
if ($oldTmpl != $newTmpl) {
|
683 |
}
|
684 |
}
|
685 |
|
686 |
+
/**
|
687 |
+
* Post sets as sticky changes.
|
688 |
+
* @param string $oldTmpl old template path
|
689 |
+
* @param string $newTmpl new template path
|
690 |
+
* @param stdClass $post the post
|
691 |
+
*/
|
692 |
protected function CheckStickyChange($oldStky, $newStky, $post)
|
693 |
{
|
694 |
if ($oldStky != $newStky) {
|
705 |
}
|
706 |
}
|
707 |
|
708 |
+
/**
|
709 |
+
* Post modified content.
|
710 |
+
* @param integer $post_ID post ID
|
711 |
+
* @param stdClass $oldPost old post
|
712 |
+
* @param stdClass $newPost new post
|
713 |
+
*/
|
714 |
public function CheckModificationChange($post_ID, $oldpost, $newpost)
|
715 |
{
|
716 |
if ($this->CheckOtherSensors($oldpost)) {
|
754 |
}
|
755 |
}
|
756 |
|
757 |
+
/**
|
758 |
+
* New category created.
|
759 |
+
* @param integer $category_id category ID
|
760 |
+
*/
|
761 |
public function EventCategoryCreation($category_id)
|
762 |
{
|
763 |
$category = get_category($category_id);
|
769 |
));
|
770 |
}
|
771 |
|
772 |
+
/**
|
773 |
+
* Category deleted.
|
774 |
+
* @global array $_POST post data
|
775 |
+
*/
|
776 |
protected function CheckCategoryDeletion()
|
777 |
{
|
778 |
if (empty($_POST)) {
|
806 |
}
|
807 |
}
|
808 |
|
809 |
+
/**
|
810 |
+
* Changed the parent of the category.
|
811 |
+
* @global array $_POST post data
|
812 |
+
*/
|
813 |
public function EventChangedCategoryParent()
|
814 |
{
|
815 |
if (empty($_POST)) {
|
840 |
}
|
841 |
}
|
842 |
|
843 |
+
/**
|
844 |
+
* Check auto draft and the setting: Hide Plugin in Plugins Page
|
845 |
+
* @param integer $code alert code
|
846 |
+
* @param string $title title
|
847 |
+
* @return boolean
|
848 |
+
*/
|
849 |
private function CheckAutoDraft($code, $title)
|
850 |
{
|
851 |
if ($code == 2008 && $title == "auto-draft") {
|
860 |
}
|
861 |
}
|
862 |
|
863 |
+
/**
|
864 |
+
* Builds revision link.
|
865 |
+
* @param integer $revision_id revision ID
|
866 |
+
* @return string|null link
|
867 |
+
*/
|
868 |
private function getRevisionLink($revision_id)
|
869 |
{
|
870 |
if (!empty($revision_id)) {
|
874 |
}
|
875 |
}
|
876 |
|
877 |
+
/**
|
878 |
+
* Builds category link.
|
879 |
+
* @param integer $category_id category ID
|
880 |
+
* @return string|null link
|
881 |
+
*/
|
882 |
private function getCategoryLink($category_id)
|
883 |
{
|
884 |
if (!empty($category_id)) {
|
891 |
/**
|
892 |
* Ignore post from BBPress, WooCommerce Plugin
|
893 |
* Triggered on the Sensors
|
894 |
+
* @param stdClass $post the post
|
895 |
*/
|
896 |
private function CheckOtherSensors($post)
|
897 |
{
|
907 |
}
|
908 |
|
909 |
/**
|
910 |
+
* Triggered after save post for add revision link.
|
911 |
+
* @param integer $post_id post ID
|
912 |
+
* @param stdClass $post post
|
913 |
*/
|
914 |
public function SetRevisionLink($post_id, $post, $update)
|
915 |
{
|
930 |
}
|
931 |
|
932 |
/**
|
933 |
+
* Alerts for Viewing of Posts, Pages and Custom Posts.
|
934 |
+
* @param string $title title
|
935 |
+
* @param stdClass $post (Optional) the post
|
936 |
*/
|
937 |
public function ViewingPost($title, $post = null)
|
938 |
{
|
944 |
$currentPath = $_SERVER["REQUEST_URI"];
|
945 |
if (!empty($_SERVER["HTTP_REFERER"])
|
946 |
&& strpos($_SERVER["HTTP_REFERER"], $currentPath) !== false) {
|
947 |
+
// Ignore this if we were on the same page so we avoid double audit entries
|
948 |
return $title;
|
949 |
}
|
950 |
if (!empty($post->post_title)) {
|
961 |
}
|
962 |
|
963 |
/**
|
964 |
+
* Alerts for Editing of Posts, Pages and Custom Posts.
|
965 |
+
* @param stdClass $post post
|
966 |
*/
|
967 |
public function EditingPost($post)
|
968 |
{
|
994 |
}
|
995 |
|
996 |
/**
|
997 |
+
* Check if the alert was triggered.
|
998 |
+
* @param integer $alert_id alert code
|
999 |
+
* @return boolean
|
1000 |
*/
|
1001 |
private function WasTriggered($alert_id)
|
1002 |
{
|
1012 |
return false;
|
1013 |
}
|
1014 |
|
1015 |
+
/**
|
1016 |
+
* Changed title of a post.
|
1017 |
+
* @param stdClass $oldPost old post
|
1018 |
+
* @param stdClass $newPost new post
|
1019 |
+
*/
|
1020 |
private function CheckTitleChange($oldpost, $newpost)
|
1021 |
{
|
1022 |
if ($oldpost->post_title != $newpost->post_title) {
|
1032 |
return 0;
|
1033 |
}
|
1034 |
|
1035 |
+
/**
|
1036 |
+
* Comments/Trackbacks and Pingbacks check.
|
1037 |
+
* @param stdClass $oldPost old post
|
1038 |
+
* @param stdClass $newPost new post
|
1039 |
+
*/
|
1040 |
private function CheckCommentsPings($oldpost, $newpost)
|
1041 |
{
|
1042 |
$result = 0;
|
1077 |
return $result;
|
1078 |
}
|
1079 |
|
1080 |
+
/**
|
1081 |
+
* Comments/Trackbacks and Pingbacks event code.
|
1082 |
+
* @param stdClass $post the post
|
1083 |
+
* @param string $status the status
|
1084 |
+
*/
|
1085 |
private function GetCommentsPingsEvent($post, $status)
|
1086 |
{
|
1087 |
if ($post->post_type == 'post') {
|
1116 |
return $event;
|
1117 |
}
|
1118 |
|
1119 |
+
/**
|
1120 |
+
* Get editor link.
|
1121 |
+
* @param stdClass $post the post
|
1122 |
+
* @return array $aLink name and value link
|
1123 |
+
*/
|
1124 |
private function GetEditorLink($post)
|
1125 |
{
|
1126 |
$name = 'EditorLink';
|
classes/Sensors/Database.php
CHANGED
@@ -1,13 +1,34 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_Database extends WSAL_AbstractSensor
|
4 |
{
|
|
|
|
|
|
|
5 |
public function HookEvents()
|
6 |
{
|
7 |
add_action('dbdelta_queries', array($this, 'EventDBDeltaQuery'));
|
8 |
add_action('query', array($this, 'EventDropQuery'));
|
9 |
}
|
10 |
|
|
|
|
|
|
|
|
|
11 |
public function EventDropQuery($query)
|
12 |
{
|
13 |
$table_names = array();
|
@@ -31,6 +52,10 @@ class WSAL_Sensors_Database extends WSAL_AbstractSensor
|
|
31 |
return $query;
|
32 |
}
|
33 |
|
|
|
|
|
|
|
|
|
34 |
public function EventDBDeltaQuery($queries)
|
35 |
{
|
36 |
$typeQueries = array(
|
@@ -74,6 +99,11 @@ class WSAL_Sensors_Database extends WSAL_AbstractSensor
|
|
74 |
return $queries;
|
75 |
}
|
76 |
|
|
|
|
|
|
|
|
|
|
|
77 |
protected function GetEventQueryType($type_action, $type_query)
|
78 |
{
|
79 |
switch ($type_action) {
|
@@ -92,6 +122,10 @@ class WSAL_Sensors_Database extends WSAL_AbstractSensor
|
|
92 |
}
|
93 |
}
|
94 |
|
|
|
|
|
|
|
|
|
95 |
protected function GetActionType($actype)
|
96 |
{
|
97 |
$is_themes = $actype == 'themes';
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Database sensor.
|
6 |
+
*
|
7 |
+
* 5010 Plugin created tables
|
8 |
+
* 5011 Plugin modified tables structure
|
9 |
+
* 5012 Plugin deleted tables
|
10 |
+
* 5013 Theme created tables
|
11 |
+
* 5014 Theme modified tables structure
|
12 |
+
* 5015 Theme deleted tables
|
13 |
+
* 5016 Unknown component created tables
|
14 |
+
* 5017 Unknown component modified tables structure
|
15 |
+
* 5018 Unknown component deleted tables
|
16 |
+
*/
|
17 |
class WSAL_Sensors_Database extends WSAL_AbstractSensor
|
18 |
{
|
19 |
+
/**
|
20 |
+
* Listening to events using WP hooks.
|
21 |
+
*/
|
22 |
public function HookEvents()
|
23 |
{
|
24 |
add_action('dbdelta_queries', array($this, 'EventDBDeltaQuery'));
|
25 |
add_action('query', array($this, 'EventDropQuery'));
|
26 |
}
|
27 |
|
28 |
+
/**
|
29 |
+
* Checks for drop query.
|
30 |
+
* @param WP_Query $query query object
|
31 |
+
*/
|
32 |
public function EventDropQuery($query)
|
33 |
{
|
34 |
$table_names = array();
|
52 |
return $query;
|
53 |
}
|
54 |
|
55 |
+
/**
|
56 |
+
* Checks DB Delta queries.
|
57 |
+
* @param array $queries array of query
|
58 |
+
*/
|
59 |
public function EventDBDeltaQuery($queries)
|
60 |
{
|
61 |
$typeQueries = array(
|
99 |
return $queries;
|
100 |
}
|
101 |
|
102 |
+
/**
|
103 |
+
* Get code alert by action and type query.
|
104 |
+
* @param string $type_action (plugins, themes or unknown)
|
105 |
+
* @param string $type_query (create, update or delete)
|
106 |
+
*/
|
107 |
protected function GetEventQueryType($type_action, $type_query)
|
108 |
{
|
109 |
switch ($type_action) {
|
122 |
}
|
123 |
}
|
124 |
|
125 |
+
/**
|
126 |
+
* Get info by action type.
|
127 |
+
* @param string $actype (plugins, themes or unknown)
|
128 |
+
*/
|
129 |
protected function GetActionType($actype)
|
130 |
{
|
131 |
$is_themes = $actype == 'themes';
|
classes/Sensors/Files.php
CHANGED
@@ -1,55 +1,87 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
28 |
$file = get_attached_file($attachmentID);
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
|
|
|
|
|
|
|
|
55 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Files sensor.
|
6 |
+
*
|
7 |
+
* 2010 User uploaded file from Uploads directory
|
8 |
+
* 2011 User deleted file from Uploads directory
|
9 |
+
* 2046 User changed a file using the theme editor
|
10 |
+
* 2051 User changed a file using the plugin editor
|
11 |
+
*/
|
12 |
+
class WSAL_Sensors_Files extends WSAL_AbstractSensor
|
13 |
+
{
|
14 |
+
/**
|
15 |
+
* @var boolean file uploaded
|
16 |
+
*/
|
17 |
+
protected $IsFileUploaded = false;
|
18 |
|
19 |
+
/**
|
20 |
+
* Listening to events using WP hooks.
|
21 |
+
*/
|
22 |
+
public function HookEvents()
|
23 |
+
{
|
24 |
+
add_action('add_attachment', array($this, 'EventFileUploaded'));
|
25 |
+
add_action('delete_attachment', array($this, 'EventFileUploadedDeleted'));
|
26 |
+
add_action('admin_init', array($this, 'EventAdminInit'));
|
27 |
+
}
|
28 |
+
|
29 |
+
/**
|
30 |
+
* File uploaded.
|
31 |
+
* @param integer $attachmentID attachment ID
|
32 |
+
*/
|
33 |
+
public function EventFileUploaded($attachmentID)
|
34 |
+
{
|
35 |
+
$action = isset($_REQUEST['action']) ? $_REQUEST['action'] : '';
|
36 |
+
if ($action != 'upload-theme' && $action != 'upload-plugin') {
|
37 |
+
$file = get_attached_file($attachmentID);
|
38 |
+
$this->plugin->alerts->Trigger(2010, array(
|
39 |
+
'AttachmentID' => $attachmentID,
|
40 |
+
'FileName' => basename($file),
|
41 |
+
'FilePath' => dirname($file),
|
42 |
+
));
|
43 |
+
}
|
44 |
+
$this->IsFileUploaded = true;
|
45 |
+
}
|
46 |
+
|
47 |
+
/**
|
48 |
+
* Deleted file from uploads directory.
|
49 |
+
* @param integer $attachmentID attachment ID
|
50 |
+
*/
|
51 |
+
public function EventFileUploadedDeleted($attachmentID)
|
52 |
+
{
|
53 |
+
if ($this->IsFileUploaded) {
|
54 |
+
return;
|
55 |
+
}
|
56 |
$file = get_attached_file($attachmentID);
|
57 |
+
$this->plugin->alerts->Trigger(2011, array(
|
58 |
+
'AttachmentID' => $attachmentID,
|
59 |
+
'FileName' => basename($file),
|
60 |
+
'FilePath' => dirname($file),
|
61 |
+
));
|
62 |
+
}
|
63 |
+
|
64 |
+
/**
|
65 |
+
* Triggered when a user accesses the admin area.
|
66 |
+
*/
|
67 |
+
public function EventAdminInit()
|
68 |
+
{
|
69 |
+
$action = isset($_REQUEST['action']) ? $_REQUEST['action'] : '';
|
70 |
+
$is_theme_editor = basename($_SERVER['SCRIPT_NAME']) == 'theme-editor.php';
|
71 |
+
$is_plugin_editor = basename($_SERVER['SCRIPT_NAME']) == 'plugin-editor.php';
|
72 |
+
|
73 |
+
if ($is_theme_editor && $action == 'update') {
|
74 |
+
$this->plugin->alerts->Trigger(2046, array(
|
75 |
+
'File' => $_REQUEST['file'],
|
76 |
+
'Theme' => $_REQUEST['theme'],
|
77 |
+
));
|
78 |
+
}
|
79 |
+
|
80 |
+
if ($is_plugin_editor && $action == 'update') {
|
81 |
+
$this->plugin->alerts->Trigger(2051, array(
|
82 |
+
'File' => $_REQUEST['file'],
|
83 |
+
'Plugin' => $_REQUEST['plugin'],
|
84 |
+
));
|
85 |
+
}
|
86 |
+
}
|
87 |
}
|
classes/Sensors/LogInOut.php
CHANGED
@@ -1,8 +1,33 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
4 |
{
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
5 |
|
|
|
|
|
|
|
6 |
public function HookEvents()
|
7 |
{
|
8 |
add_action('wp_login', array($this, 'EventLogin'), 10, 2);
|
@@ -13,13 +38,17 @@ class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
|
13 |
add_filter('wp_login_blocked', array($this, 'EventLoginBlocked'), 10, 1);
|
14 |
}
|
15 |
|
16 |
-
|
17 |
-
|
|
|
18 |
public function GetCurrentUser()
|
19 |
{
|
20 |
$this->_current_user = wp_get_current_user();
|
21 |
}
|
22 |
|
|
|
|
|
|
|
23 |
public function EventLogin($user_login, $user = null)
|
24 |
{
|
25 |
if (empty($user)) {
|
@@ -35,6 +64,9 @@ class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
|
35 |
), true);
|
36 |
}
|
37 |
|
|
|
|
|
|
|
38 |
public function EventLogout()
|
39 |
{
|
40 |
if ($this->_current_user->ID != 0) {
|
@@ -45,19 +77,31 @@ class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
|
45 |
}
|
46 |
}
|
47 |
|
48 |
-
|
49 |
-
|
50 |
-
|
|
|
51 |
protected function GetLoginFailureLogLimit()
|
52 |
{
|
53 |
return 10;
|
54 |
}
|
55 |
|
|
|
|
|
|
|
|
|
56 |
protected function GetLoginFailureExpiration()
|
57 |
{
|
58 |
return 12 * 60 * 60;
|
59 |
}
|
60 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
61 |
protected function IsPastLoginFailureLimit($ip, $site_id, $user)
|
62 |
{
|
63 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
@@ -70,6 +114,12 @@ class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
|
70 |
}
|
71 |
}
|
72 |
|
|
|
|
|
|
|
|
|
|
|
|
|
73 |
protected function IncrementLoginFailure($ip, $site_id, $user)
|
74 |
{
|
75 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
@@ -97,6 +147,10 @@ class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
|
97 |
}
|
98 |
}
|
99 |
|
|
|
|
|
|
|
|
|
100 |
public function EventLoginFailure($username)
|
101 |
{
|
102 |
list($y, $m, $d) = explode('-', date('Y-m-d'));
|
@@ -193,6 +247,10 @@ class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
|
193 |
}
|
194 |
}
|
195 |
|
|
|
|
|
|
|
|
|
196 |
public function EventPasswordReset($user, $new_pass)
|
197 |
{
|
198 |
if (!empty($user)) {
|
@@ -204,6 +262,10 @@ class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
|
204 |
}
|
205 |
}
|
206 |
|
|
|
|
|
|
|
|
|
207 |
public function EventLoginBlocked($username)
|
208 |
{
|
209 |
$user = get_user_by('login', $username);
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Login/Logout sensor.
|
6 |
+
*
|
7 |
+
* 1000 User logged in
|
8 |
+
* 1001 User logged out
|
9 |
+
* 1002 Login failed
|
10 |
+
* 1003 Login failed / non existing user
|
11 |
+
* 1004 Login blocked
|
12 |
+
* 4003 User has changed his or her password
|
13 |
+
*/
|
14 |
class WSAL_Sensors_LogInOut extends WSAL_AbstractSensor
|
15 |
{
|
16 |
+
/**
|
17 |
+
* Transient name.
|
18 |
+
* WordPress will prefix the name with "_transient_" or "_transient_timeout_" in the options table.
|
19 |
+
*/
|
20 |
+
const TRANSIENT_FAILEDLOGINS = 'wsal-failedlogins-known';
|
21 |
+
const TRANSIENT_FAILEDLOGINS_UNKNOWN = 'wsal-failedlogins-unknown';
|
22 |
+
|
23 |
+
/**
|
24 |
+
* @var WP_User current user object
|
25 |
+
*/
|
26 |
+
protected $_current_user = null;
|
27 |
|
28 |
+
/**
|
29 |
+
* Listening to events using WP hooks.
|
30 |
+
*/
|
31 |
public function HookEvents()
|
32 |
{
|
33 |
add_action('wp_login', array($this, 'EventLogin'), 10, 2);
|
38 |
add_filter('wp_login_blocked', array($this, 'EventLoginBlocked'), 10, 1);
|
39 |
}
|
40 |
|
41 |
+
/**
|
42 |
+
* Sets current user.
|
43 |
+
*/
|
44 |
public function GetCurrentUser()
|
45 |
{
|
46 |
$this->_current_user = wp_get_current_user();
|
47 |
}
|
48 |
|
49 |
+
/**
|
50 |
+
* Event Login.
|
51 |
+
*/
|
52 |
public function EventLogin($user_login, $user = null)
|
53 |
{
|
54 |
if (empty($user)) {
|
64 |
), true);
|
65 |
}
|
66 |
|
67 |
+
/**
|
68 |
+
* Event Logout.
|
69 |
+
*/
|
70 |
public function EventLogout()
|
71 |
{
|
72 |
if ($this->_current_user->ID != 0) {
|
77 |
}
|
78 |
}
|
79 |
|
80 |
+
/**
|
81 |
+
* Login failure limit count.
|
82 |
+
* @return integer limit
|
83 |
+
*/
|
84 |
protected function GetLoginFailureLogLimit()
|
85 |
{
|
86 |
return 10;
|
87 |
}
|
88 |
|
89 |
+
/**
|
90 |
+
* Expiration of the transient saved in the WP database.
|
91 |
+
* @return integer Time until expiration in seconds from now
|
92 |
+
*/
|
93 |
protected function GetLoginFailureExpiration()
|
94 |
{
|
95 |
return 12 * 60 * 60;
|
96 |
}
|
97 |
|
98 |
+
/**
|
99 |
+
* Check failure limit.
|
100 |
+
* @param string $ip IP address
|
101 |
+
* @param integer $site_id blog ID
|
102 |
+
* @param WP_User $user user object
|
103 |
+
* @return boolean passed limit true|false
|
104 |
+
*/
|
105 |
protected function IsPastLoginFailureLimit($ip, $site_id, $user)
|
106 |
{
|
107 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
114 |
}
|
115 |
}
|
116 |
|
117 |
+
/**
|
118 |
+
* Increment failure limit.
|
119 |
+
* @param string $ip IP address
|
120 |
+
* @param integer $site_id blog ID
|
121 |
+
* @param WP_User $user user object
|
122 |
+
*/
|
123 |
protected function IncrementLoginFailure($ip, $site_id, $user)
|
124 |
{
|
125 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
147 |
}
|
148 |
}
|
149 |
|
150 |
+
/**
|
151 |
+
* Event Login failure.
|
152 |
+
* @param string $username username
|
153 |
+
*/
|
154 |
public function EventLoginFailure($username)
|
155 |
{
|
156 |
list($y, $m, $d) = explode('-', date('Y-m-d'));
|
247 |
}
|
248 |
}
|
249 |
|
250 |
+
/**
|
251 |
+
* Event changed password.
|
252 |
+
* @param WP_User $user user object
|
253 |
+
*/
|
254 |
public function EventPasswordReset($user, $new_pass)
|
255 |
{
|
256 |
if (!empty($user)) {
|
262 |
}
|
263 |
}
|
264 |
|
265 |
+
/**
|
266 |
+
* Event login blocked.
|
267 |
+
* @param string $username username
|
268 |
+
*/
|
269 |
public function EventLoginBlocked($username)
|
270 |
{
|
271 |
$user = get_user_by('login', $username);
|
classes/Sensors/Menus.php
CHANGED
@@ -1,5 +1,19 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
4 |
{
|
5 |
protected $_OldMenu = null;
|
@@ -7,6 +21,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
7 |
protected $_OldMenuItems = array();
|
8 |
protected $_OldMenuLocations = null;
|
9 |
|
|
|
|
|
|
|
10 |
public function HookEvents()
|
11 |
{
|
12 |
add_action('wp_create_nav_menu', array($this, 'CreateMenu'), 10, 2);
|
@@ -22,6 +39,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
22 |
add_action('customize_save_after', array($this, 'CustomizeSave'));
|
23 |
}
|
24 |
|
|
|
|
|
|
|
25 |
public function UpdateMenuItem($menu_id, $menu_item_db_id, $args)
|
26 |
{
|
27 |
$oldMenuItems = array();
|
@@ -81,6 +101,10 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
81 |
}
|
82 |
}
|
83 |
|
|
|
|
|
|
|
|
|
84 |
public function CreateMenu($term_id, $menu_data)
|
85 |
{
|
86 |
$this->plugin->alerts->Trigger(2078, array(
|
@@ -88,6 +112,10 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
88 |
));
|
89 |
}
|
90 |
|
|
|
|
|
|
|
|
|
91 |
public function ManageMenuLocations()
|
92 |
{
|
93 |
// Manage Location tab
|
@@ -102,6 +130,10 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
102 |
}
|
103 |
}
|
104 |
|
|
|
|
|
|
|
|
|
105 |
private function LocationSetting($new_location, $type)
|
106 |
{
|
107 |
$old_locations = get_nav_menu_locations();
|
@@ -118,6 +150,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
118 |
}
|
119 |
}
|
120 |
|
|
|
|
|
|
|
121 |
public function DeleteMenu($term_id)
|
122 |
{
|
123 |
if ($this->_OldMenu) {
|
@@ -127,6 +162,10 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
127 |
}
|
128 |
}
|
129 |
|
|
|
|
|
|
|
|
|
130 |
public function UpdateMenu($menu_id, $menu_data = null)
|
131 |
{
|
132 |
if (!empty($menu_data)) {
|
@@ -222,6 +261,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
222 |
}
|
223 |
}
|
224 |
|
|
|
|
|
|
|
225 |
private function BuildOldMenuTermsAndItems()
|
226 |
{
|
227 |
$menus = wp_get_nav_menus();
|
@@ -247,6 +289,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
247 |
}
|
248 |
}
|
249 |
|
|
|
|
|
|
|
250 |
public function EventAdminInit()
|
251 |
{
|
252 |
$is_nav_menu = basename($_SERVER['SCRIPT_NAME']) == 'nav-menus.php';
|
@@ -262,6 +307,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
262 |
}
|
263 |
}
|
264 |
|
|
|
|
|
|
|
265 |
public function CustomizeInit()
|
266 |
{
|
267 |
$this->BuildOldMenuTermsAndItems();
|
@@ -269,7 +317,7 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
269 |
}
|
270 |
|
271 |
/**
|
272 |
-
* Customize Events Function
|
273 |
*/
|
274 |
public function CustomizeSave()
|
275 |
{
|
@@ -382,6 +430,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
382 |
}
|
383 |
}
|
384 |
|
|
|
|
|
|
|
385 |
private function EventAddItems($content_type, $content_name, $menu_name)
|
386 |
{
|
387 |
$this->plugin->alerts->Trigger(2079, array(
|
@@ -391,6 +442,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
391 |
));
|
392 |
}
|
393 |
|
|
|
|
|
|
|
394 |
private function EventRemoveItems($content_type, $content_name, $menu_name)
|
395 |
{
|
396 |
$this->plugin->alerts->Trigger(2080, array(
|
@@ -400,6 +454,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
400 |
));
|
401 |
}
|
402 |
|
|
|
|
|
|
|
403 |
private function EventMenuSetting($menu_name, $status, $menu_setting)
|
404 |
{
|
405 |
$this->plugin->alerts->Trigger(2082, array(
|
@@ -409,6 +466,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
409 |
));
|
410 |
}
|
411 |
|
|
|
|
|
|
|
412 |
private function EventModifiedItems($content_type, $content_name, $menu_name)
|
413 |
{
|
414 |
$this->plugin->alerts->Trigger(2083, array(
|
@@ -418,6 +478,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
418 |
));
|
419 |
}
|
420 |
|
|
|
|
|
|
|
421 |
private function EventChangeName($old_menu_name, $new_menu_name)
|
422 |
{
|
423 |
$this->plugin->alerts->Trigger(2084, array(
|
@@ -426,6 +489,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
426 |
));
|
427 |
}
|
428 |
|
|
|
|
|
|
|
429 |
private function EventChangeOrder($item_name, $menu_name)
|
430 |
{
|
431 |
$this->plugin->alerts->Trigger(2085, array(
|
@@ -434,6 +500,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
434 |
));
|
435 |
}
|
436 |
|
|
|
|
|
|
|
437 |
private function EventChangeSubItem($item_name, $parent_name, $menu_name)
|
438 |
{
|
439 |
$this->plugin->alerts->Trigger(2089, array(
|
@@ -443,6 +512,9 @@ class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
|
443 |
));
|
444 |
}
|
445 |
|
|
|
|
|
|
|
446 |
private function GetItemName($term_id, $item_id)
|
447 |
{
|
448 |
$item_name = '';
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Menus sensor.
|
6 |
+
*
|
7 |
+
* 2078 User created new menu
|
8 |
+
* 2079 User added content to a menu
|
9 |
+
* 2080 User removed content from a menu
|
10 |
+
* 2081 User deleted menu
|
11 |
+
* 2082 User changed menu setting
|
12 |
+
* 2083 User modified content in a menu
|
13 |
+
* 2084 User changed name of a menu
|
14 |
+
* 2085 User changed order of the objects in a menu
|
15 |
+
* 2089 User moved objects as a sub-item
|
16 |
+
*/
|
17 |
class WSAL_Sensors_Menus extends WSAL_AbstractSensor
|
18 |
{
|
19 |
protected $_OldMenu = null;
|
21 |
protected $_OldMenuItems = array();
|
22 |
protected $_OldMenuLocations = null;
|
23 |
|
24 |
+
/**
|
25 |
+
* Listening to events using WP hooks.
|
26 |
+
*/
|
27 |
public function HookEvents()
|
28 |
{
|
29 |
add_action('wp_create_nav_menu', array($this, 'CreateMenu'), 10, 2);
|
39 |
add_action('customize_save_after', array($this, 'CustomizeSave'));
|
40 |
}
|
41 |
|
42 |
+
/**
|
43 |
+
* Menu item updated.
|
44 |
+
*/
|
45 |
public function UpdateMenuItem($menu_id, $menu_item_db_id, $args)
|
46 |
{
|
47 |
$oldMenuItems = array();
|
101 |
}
|
102 |
}
|
103 |
|
104 |
+
/**
|
105 |
+
* New menu created.
|
106 |
+
* @param array $menu_data data
|
107 |
+
*/
|
108 |
public function CreateMenu($term_id, $menu_data)
|
109 |
{
|
110 |
$this->plugin->alerts->Trigger(2078, array(
|
112 |
));
|
113 |
}
|
114 |
|
115 |
+
/**
|
116 |
+
* New menu created.
|
117 |
+
* @global array $_POST data post
|
118 |
+
*/
|
119 |
public function ManageMenuLocations()
|
120 |
{
|
121 |
// Manage Location tab
|
130 |
}
|
131 |
}
|
132 |
|
133 |
+
/**
|
134 |
+
* Menu location.
|
135 |
+
* @param integer $new_location location
|
136 |
+
*/
|
137 |
private function LocationSetting($new_location, $type)
|
138 |
{
|
139 |
$old_locations = get_nav_menu_locations();
|
150 |
}
|
151 |
}
|
152 |
|
153 |
+
/**
|
154 |
+
* Menu deleted.
|
155 |
+
*/
|
156 |
public function DeleteMenu($term_id)
|
157 |
{
|
158 |
if ($this->_OldMenu) {
|
162 |
}
|
163 |
}
|
164 |
|
165 |
+
/**
|
166 |
+
* Menu updated.
|
167 |
+
* @param array $menu_data (Optional) data
|
168 |
+
*/
|
169 |
public function UpdateMenu($menu_id, $menu_data = null)
|
170 |
{
|
171 |
if (!empty($menu_data)) {
|
261 |
}
|
262 |
}
|
263 |
|
264 |
+
/**
|
265 |
+
* Set old menu terms and items.
|
266 |
+
*/
|
267 |
private function BuildOldMenuTermsAndItems()
|
268 |
{
|
269 |
$menus = wp_get_nav_menus();
|
289 |
}
|
290 |
}
|
291 |
|
292 |
+
/**
|
293 |
+
* Triggered when a user accesses the admin area.
|
294 |
+
*/
|
295 |
public function EventAdminInit()
|
296 |
{
|
297 |
$is_nav_menu = basename($_SERVER['SCRIPT_NAME']) == 'nav-menus.php';
|
307 |
}
|
308 |
}
|
309 |
|
310 |
+
/**
|
311 |
+
* Customize set old data.
|
312 |
+
*/
|
313 |
public function CustomizeInit()
|
314 |
{
|
315 |
$this->BuildOldMenuTermsAndItems();
|
317 |
}
|
318 |
|
319 |
/**
|
320 |
+
* Customize Events Function.
|
321 |
*/
|
322 |
public function CustomizeSave()
|
323 |
{
|
430 |
}
|
431 |
}
|
432 |
|
433 |
+
/**
|
434 |
+
* Added content to a menu.
|
435 |
+
*/
|
436 |
private function EventAddItems($content_type, $content_name, $menu_name)
|
437 |
{
|
438 |
$this->plugin->alerts->Trigger(2079, array(
|
442 |
));
|
443 |
}
|
444 |
|
445 |
+
/**
|
446 |
+
* Removed content from a menu.
|
447 |
+
*/
|
448 |
private function EventRemoveItems($content_type, $content_name, $menu_name)
|
449 |
{
|
450 |
$this->plugin->alerts->Trigger(2080, array(
|
454 |
));
|
455 |
}
|
456 |
|
457 |
+
/**
|
458 |
+
* Changed menu setting.
|
459 |
+
*/
|
460 |
private function EventMenuSetting($menu_name, $status, $menu_setting)
|
461 |
{
|
462 |
$this->plugin->alerts->Trigger(2082, array(
|
466 |
));
|
467 |
}
|
468 |
|
469 |
+
/**
|
470 |
+
* Modified content in a menu.
|
471 |
+
*/
|
472 |
private function EventModifiedItems($content_type, $content_name, $menu_name)
|
473 |
{
|
474 |
$this->plugin->alerts->Trigger(2083, array(
|
478 |
));
|
479 |
}
|
480 |
|
481 |
+
/**
|
482 |
+
* Changed name of a menu.
|
483 |
+
*/
|
484 |
private function EventChangeName($old_menu_name, $new_menu_name)
|
485 |
{
|
486 |
$this->plugin->alerts->Trigger(2084, array(
|
489 |
));
|
490 |
}
|
491 |
|
492 |
+
/**
|
493 |
+
* Changed order of the objects in a menu.
|
494 |
+
*/
|
495 |
private function EventChangeOrder($item_name, $menu_name)
|
496 |
{
|
497 |
$this->plugin->alerts->Trigger(2085, array(
|
500 |
));
|
501 |
}
|
502 |
|
503 |
+
/**
|
504 |
+
* Moved objects as a sub-item.
|
505 |
+
*/
|
506 |
private function EventChangeSubItem($item_name, $parent_name, $menu_name)
|
507 |
{
|
508 |
$this->plugin->alerts->Trigger(2089, array(
|
512 |
));
|
513 |
}
|
514 |
|
515 |
+
/**
|
516 |
+
* Get menu item name.
|
517 |
+
*/
|
518 |
private function GetItemName($term_id, $item_id)
|
519 |
{
|
520 |
$item_name = '';
|
classes/Sensors/MetaData.php
CHANGED
@@ -1,8 +1,29 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
4 |
{
|
|
|
5 |
|
|
|
|
|
|
|
6 |
public function HookEvents()
|
7 |
{
|
8 |
add_action('add_post_meta', array($this, 'EventPostMetaCreated'), 10, 3);
|
@@ -11,11 +32,13 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
11 |
add_action('deleted_post_meta', array($this, 'EventPostMetaDeleted'), 10, 4);
|
12 |
}
|
13 |
|
14 |
-
|
15 |
-
|
|
|
|
|
16 |
protected function CanLogPostMeta($object_id, $meta_key)
|
17 |
{
|
18 |
-
//check if excluded meta key or starts with _
|
19 |
if (substr($meta_key, 0, 1) == '_') {
|
20 |
return false;
|
21 |
} else if ($this->IsExcludedCustomFields($meta_key)) {
|
@@ -25,6 +48,11 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
25 |
}
|
26 |
}
|
27 |
|
|
|
|
|
|
|
|
|
|
|
28 |
public function IsExcludedCustomFields($custom)
|
29 |
{
|
30 |
$customFields = $this->plugin->settings->GetExcludedMonitoringCustom();
|
@@ -50,13 +78,18 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
50 |
}
|
51 |
}
|
52 |
return false;
|
53 |
-
//return (in_array($custom, $customFields)) ? true : false;
|
54 |
}
|
55 |
-
|
|
|
|
|
|
|
56 |
public function EventPostMetaCreated($object_id, $meta_key, $meta_value)
|
57 |
{
|
58 |
$post = get_post($object_id);
|
59 |
-
if (!$this->CanLogPostMeta($object_id, $meta_key))
|
|
|
|
|
60 |
|
61 |
$WPActions = array('add-meta');
|
62 |
if (isset($_POST['action']) && in_array($_POST['action'], $WPActions)) {
|
@@ -97,6 +130,9 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
97 |
}
|
98 |
}
|
99 |
|
|
|
|
|
|
|
100 |
public function EventPostMetaUpdating($meta_id, $object_id, $meta_key)
|
101 |
{
|
102 |
static $meta_type = 'post';
|
@@ -106,11 +142,15 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
106 |
);
|
107 |
}
|
108 |
|
|
|
|
|
|
|
109 |
public function EventPostMetaUpdated($meta_id, $object_id, $meta_key, $meta_value)
|
110 |
{
|
111 |
$post = get_post($object_id);
|
112 |
-
|
113 |
-
|
|
|
114 |
|
115 |
$WPActions = array('add-meta');
|
116 |
if (isset($_POST['action']) && in_array($_POST['action'], $WPActions)) {
|
@@ -204,6 +244,9 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
204 |
}
|
205 |
}
|
206 |
|
|
|
|
|
|
|
207 |
public function EventPostMetaDeleted($meta_ids, $object_id, $meta_key, $meta_value)
|
208 |
{
|
209 |
$post = get_post($object_id);
|
@@ -212,8 +255,9 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
212 |
if (isset($_POST['action']) && in_array($_POST['action'], $WPActions)) {
|
213 |
$editorLink = $this->GetEditorLink($post);
|
214 |
foreach ($meta_ids as $meta_id) {
|
215 |
-
if (!$this->CanLogPostMeta($object_id, $meta_key))
|
216 |
-
|
|
|
217 |
switch ($post->post_type) {
|
218 |
case 'page':
|
219 |
$this->plugin->alerts->Trigger(2061, array(
|
@@ -251,6 +295,11 @@ class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
|
251 |
}
|
252 |
}
|
253 |
|
|
|
|
|
|
|
|
|
|
|
254 |
private function GetEditorLink($post)
|
255 |
{
|
256 |
$name = 'EditorLink';
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Custom fields (posts, pages and custom posts) sensor.
|
6 |
+
*
|
7 |
+
* 2053 User created a custom field for a post
|
8 |
+
* 2056 User created a custom field for a custom post type
|
9 |
+
* 2059 User created a custom field for a page
|
10 |
+
* 2062 User updated a custom field name for a post
|
11 |
+
* 2063 User updated a custom field name for a custom post type
|
12 |
+
* 2064 User updated a custom field name for a page
|
13 |
+
* 2060 User updated a custom field value for a page
|
14 |
+
* 2057 User updated a custom field for a custom post type
|
15 |
+
* 2054 User updated a custom field value for a post
|
16 |
+
* 2055 User deleted a custom field from a post
|
17 |
+
* 2058 User deleted a custom field from a custom post type
|
18 |
+
* 2061 User deleted a custom field from a page
|
19 |
+
*/
|
20 |
class WSAL_Sensors_MetaData extends WSAL_AbstractSensor
|
21 |
{
|
22 |
+
protected $old_meta = array();
|
23 |
|
24 |
+
/**
|
25 |
+
* Listening to events using WP hooks.
|
26 |
+
*/
|
27 |
public function HookEvents()
|
28 |
{
|
29 |
add_action('add_post_meta', array($this, 'EventPostMetaCreated'), 10, 3);
|
32 |
add_action('deleted_post_meta', array($this, 'EventPostMetaDeleted'), 10, 4);
|
33 |
}
|
34 |
|
35 |
+
/**
|
36 |
+
* Check "Excluded Custom Fields" or meta keys starts with "_".
|
37 |
+
* @return boolean can log true|false
|
38 |
+
*/
|
39 |
protected function CanLogPostMeta($object_id, $meta_key)
|
40 |
{
|
41 |
+
// check if excluded meta key or starts with _
|
42 |
if (substr($meta_key, 0, 1) == '_') {
|
43 |
return false;
|
44 |
} else if ($this->IsExcludedCustomFields($meta_key)) {
|
48 |
}
|
49 |
}
|
50 |
|
51 |
+
/**
|
52 |
+
* Check "Excluded Custom Fields".
|
53 |
+
* Used in the above function.
|
54 |
+
* @return boolean is excluded from monitoring true|false
|
55 |
+
*/
|
56 |
public function IsExcludedCustomFields($custom)
|
57 |
{
|
58 |
$customFields = $this->plugin->settings->GetExcludedMonitoringCustom();
|
78 |
}
|
79 |
}
|
80 |
return false;
|
81 |
+
// return (in_array($custom, $customFields)) ? true : false;
|
82 |
}
|
83 |
+
|
84 |
+
/**
|
85 |
+
* Created a custom field.
|
86 |
+
*/
|
87 |
public function EventPostMetaCreated($object_id, $meta_key, $meta_value)
|
88 |
{
|
89 |
$post = get_post($object_id);
|
90 |
+
if (!$this->CanLogPostMeta($object_id, $meta_key)) {
|
91 |
+
return;
|
92 |
+
}
|
93 |
|
94 |
$WPActions = array('add-meta');
|
95 |
if (isset($_POST['action']) && in_array($_POST['action'], $WPActions)) {
|
130 |
}
|
131 |
}
|
132 |
|
133 |
+
/**
|
134 |
+
* Sets the old meta.
|
135 |
+
*/
|
136 |
public function EventPostMetaUpdating($meta_id, $object_id, $meta_key)
|
137 |
{
|
138 |
static $meta_type = 'post';
|
142 |
);
|
143 |
}
|
144 |
|
145 |
+
/**
|
146 |
+
* Updated a custom field name/value.
|
147 |
+
*/
|
148 |
public function EventPostMetaUpdated($meta_id, $object_id, $meta_key, $meta_value)
|
149 |
{
|
150 |
$post = get_post($object_id);
|
151 |
+
if (!$this->CanLogPostMeta($object_id, $meta_key)) {
|
152 |
+
return;
|
153 |
+
}
|
154 |
|
155 |
$WPActions = array('add-meta');
|
156 |
if (isset($_POST['action']) && in_array($_POST['action'], $WPActions)) {
|
244 |
}
|
245 |
}
|
246 |
|
247 |
+
/**
|
248 |
+
* Deleted a custom field.
|
249 |
+
*/
|
250 |
public function EventPostMetaDeleted($meta_ids, $object_id, $meta_key, $meta_value)
|
251 |
{
|
252 |
$post = get_post($object_id);
|
255 |
if (isset($_POST['action']) && in_array($_POST['action'], $WPActions)) {
|
256 |
$editorLink = $this->GetEditorLink($post);
|
257 |
foreach ($meta_ids as $meta_id) {
|
258 |
+
if (!$this->CanLogPostMeta($object_id, $meta_key)) {
|
259 |
+
continue;
|
260 |
+
}
|
261 |
switch ($post->post_type) {
|
262 |
case 'page':
|
263 |
$this->plugin->alerts->Trigger(2061, array(
|
295 |
}
|
296 |
}
|
297 |
|
298 |
+
/**
|
299 |
+
* Get editor link.
|
300 |
+
* @param stdClass $post the post
|
301 |
+
* @return array $aLink name and value link
|
302 |
+
*/
|
303 |
private function GetEditorLink($post)
|
304 |
{
|
305 |
$name = 'EditorLink';
|
classes/Sensors/Multisite.php
CHANGED
@@ -1,130 +1,200 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
4 |
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
69 |
-
|
70 |
-
|
71 |
-
|
72 |
-
|
73 |
-
|
74 |
-
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
|
79 |
-
|
80 |
-
|
81 |
-
|
82 |
-
|
83 |
-
|
84 |
-
|
85 |
-
|
86 |
-
|
87 |
-
|
88 |
-
|
89 |
-
|
90 |
-
|
91 |
-
public function EventDeactivateBlog($blog_id){
|
92 |
-
$this->plugin->alerts->Trigger(7004, array(
|
93 |
-
'BlogID' => $blog_id,
|
94 |
-
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
95 |
-
));
|
96 |
-
}
|
97 |
-
|
98 |
-
public function EventDeleteBlog($blog_id){
|
99 |
-
$this->plugin->alerts->Trigger(7005, array(
|
100 |
-
'BlogID' => $blog_id,
|
101 |
-
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
102 |
-
));
|
103 |
-
}
|
104 |
-
|
105 |
-
public function EventUserAddedToBlog($user_id, $role, $blog_id){
|
106 |
-
$this->plugin->alerts->TriggerIf(4010, array(
|
107 |
-
'TargetUserID' => $user_id,
|
108 |
-
'TargetUsername' => get_userdata($user_id)->user_login,
|
109 |
-
'TargetUserRole' => $role,
|
110 |
-
'BlogID' => $blog_id,
|
111 |
-
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
112 |
-
), array($this, 'MustNotContainCreateUser'));
|
113 |
-
}
|
114 |
-
|
115 |
-
public function EventUserRemovedFromBlog($user_id){
|
116 |
-
$user = get_userdata($user_id);
|
117 |
$blog_id = (isset($_REQUEST['id']) ? $_REQUEST['id'] : 0);
|
118 |
-
|
119 |
-
|
120 |
-
|
121 |
-
|
122 |
-
|
123 |
-
|
124 |
-
|
125 |
-
|
126 |
-
|
127 |
-
|
128 |
-
|
129 |
-
|
130 |
-
|
|
|
|
|
|
|
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Multisite sensor.
|
6 |
+
*
|
7 |
+
* 4010 Existing user added to a site
|
8 |
+
* 4011 User removed from site
|
9 |
+
* 4012 New network user created
|
10 |
+
* 7000 New site added on the network
|
11 |
+
* 7001 Existing site archived
|
12 |
+
* 7002 Archived site has been unarchived
|
13 |
+
* 7003 Deactivated site has been activated
|
14 |
+
* 7004 Site has been deactivated
|
15 |
+
* 7005 Existing site deleted from network
|
16 |
+
* 5008 Activated theme on network
|
17 |
+
* 5009 Deactivated theme from network
|
18 |
+
*/
|
19 |
+
class WSAL_Sensors_Multisite extends WSAL_AbstractSensor
|
20 |
+
{
|
21 |
+
protected $old_allowedthemes = null;
|
22 |
|
23 |
+
/**
|
24 |
+
* Listening to events using WP hooks.
|
25 |
+
*/
|
26 |
+
public function HookEvents()
|
27 |
+
{
|
28 |
+
if ($this->plugin->IsMultisite()) {
|
29 |
+
add_action('admin_init', array($this, 'EventAdminInit'));
|
30 |
+
if (current_user_can('switch_themes')) {
|
31 |
+
add_action('shutdown', array($this, 'EventAdminShutdown'));
|
32 |
+
}
|
33 |
+
add_action('wpmu_new_blog', array($this, 'EventNewBlog'), 10, 1);
|
34 |
+
add_action('archive_blog', array($this, 'EventArchiveBlog'));
|
35 |
+
add_action('unarchive_blog', array($this, 'EventUnarchiveBlog'));
|
36 |
+
add_action('activate_blog', array($this, 'EventActivateBlog'));
|
37 |
+
add_action('deactivate_blog', array($this, 'EventDeactivateBlog'));
|
38 |
+
add_action('delete_blog', array($this, 'EventDeleteBlog'));
|
39 |
+
add_action('add_user_to_blog', array($this, 'EventUserAddedToBlog'), 10, 3);
|
40 |
+
add_action('remove_user_from_blog', array($this, 'EventUserRemovedFromBlog'));
|
41 |
+
}
|
42 |
+
}
|
43 |
+
|
44 |
+
/**
|
45 |
+
* Triggered when a user accesses the admin area.
|
46 |
+
*/
|
47 |
+
public function EventAdminInit()
|
48 |
+
{
|
49 |
+
$this->old_allowedthemes = array_keys((array)get_site_option('allowedthemes'));
|
50 |
+
}
|
51 |
+
|
52 |
+
/**
|
53 |
+
* Activated/Deactivated theme on network.
|
54 |
+
*/
|
55 |
+
public function EventAdminShutdown()
|
56 |
+
{
|
57 |
+
if (is_null($this->old_allowedthemes)) {
|
58 |
+
return;
|
59 |
+
}
|
60 |
+
$new_allowedthemes = array_keys((array)get_site_option('allowedthemes'));
|
61 |
+
|
62 |
+
// check for enabled themes
|
63 |
+
foreach ($new_allowedthemes as $theme) {
|
64 |
+
if (!in_array($theme, (array)$this->old_allowedthemes)) {
|
65 |
+
$theme = wp_get_theme($theme);
|
66 |
+
$this->plugin->alerts->Trigger(5008, array(
|
67 |
+
'Theme' => (object)array(
|
68 |
+
'Name' => $theme->Name,
|
69 |
+
'ThemeURI' => $theme->ThemeURI,
|
70 |
+
'Description' => $theme->Description,
|
71 |
+
'Author' => $theme->Author,
|
72 |
+
'Version' => $theme->Version,
|
73 |
+
'get_template_directory' => $theme->get_template_directory(),
|
74 |
+
),
|
75 |
+
));
|
76 |
+
}
|
77 |
+
}
|
78 |
+
|
79 |
+
// check for disabled themes
|
80 |
+
foreach ((array)$this->old_allowedthemes as $theme) {
|
81 |
+
if (!in_array($theme, $new_allowedthemes)) {
|
82 |
+
$theme = wp_get_theme($theme);
|
83 |
+
$this->plugin->alerts->Trigger(5009, array(
|
84 |
+
'Theme' => (object)array(
|
85 |
+
'Name' => $theme->Name,
|
86 |
+
'ThemeURI' => $theme->ThemeURI,
|
87 |
+
'Description' => $theme->Description,
|
88 |
+
'Author' => $theme->Author,
|
89 |
+
'Version' => $theme->Version,
|
90 |
+
'get_template_directory' => $theme->get_template_directory(),
|
91 |
+
),
|
92 |
+
));
|
93 |
+
}
|
94 |
+
}
|
95 |
+
}
|
96 |
|
97 |
+
/**
|
98 |
+
* New site added on the network.
|
99 |
+
*/
|
100 |
+
public function EventNewBlog($blog_id)
|
101 |
+
{
|
102 |
+
$this->plugin->alerts->Trigger(7000, array(
|
103 |
+
'BlogID' => $blog_id,
|
104 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
105 |
+
));
|
106 |
+
}
|
107 |
+
|
108 |
+
/**
|
109 |
+
* Existing site archived.
|
110 |
+
*/
|
111 |
+
public function EventArchiveBlog($blog_id)
|
112 |
+
{
|
113 |
+
$this->plugin->alerts->Trigger(7001, array(
|
114 |
+
'BlogID' => $blog_id,
|
115 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
116 |
+
));
|
117 |
+
}
|
118 |
+
|
119 |
+
/**
|
120 |
+
* Archived site has been unarchived.
|
121 |
+
*/
|
122 |
+
public function EventUnarchiveBlog($blog_id)
|
123 |
+
{
|
124 |
+
$this->plugin->alerts->Trigger(7002, array(
|
125 |
+
'BlogID' => $blog_id,
|
126 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
127 |
+
));
|
128 |
+
}
|
129 |
+
|
130 |
+
/**
|
131 |
+
* Deactivated site has been activated.
|
132 |
+
*/
|
133 |
+
public function EventActivateBlog($blog_id)
|
134 |
+
{
|
135 |
+
$this->plugin->alerts->Trigger(7003, array(
|
136 |
+
'BlogID' => $blog_id,
|
137 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
138 |
+
));
|
139 |
+
}
|
140 |
+
|
141 |
+
/**
|
142 |
+
* Site has been deactivated.
|
143 |
+
*/
|
144 |
+
public function EventDeactivateBlog($blog_id)
|
145 |
+
{
|
146 |
+
$this->plugin->alerts->Trigger(7004, array(
|
147 |
+
'BlogID' => $blog_id,
|
148 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
149 |
+
));
|
150 |
+
}
|
151 |
+
|
152 |
+
/**
|
153 |
+
* Existing site deleted from network.
|
154 |
+
*/
|
155 |
+
public function EventDeleteBlog($blog_id)
|
156 |
+
{
|
157 |
+
$this->plugin->alerts->Trigger(7005, array(
|
158 |
+
'BlogID' => $blog_id,
|
159 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
160 |
+
));
|
161 |
+
}
|
162 |
+
|
163 |
+
/**
|
164 |
+
* Existing user added to a site.
|
165 |
+
*/
|
166 |
+
public function EventUserAddedToBlog($user_id, $role, $blog_id)
|
167 |
+
{
|
168 |
+
$this->plugin->alerts->TriggerIf(4010, array(
|
169 |
+
'TargetUserID' => $user_id,
|
170 |
+
'TargetUsername' => get_userdata($user_id)->user_login,
|
171 |
+
'TargetUserRole' => $role,
|
172 |
+
'BlogID' => $blog_id,
|
173 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
174 |
+
), array($this, 'MustNotContainCreateUser'));
|
175 |
+
}
|
176 |
+
|
177 |
+
/**
|
178 |
+
* User removed from site.
|
179 |
+
*/
|
180 |
+
public function EventUserRemovedFromBlog($user_id)
|
181 |
+
{
|
182 |
+
$user = get_userdata($user_id);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
183 |
$blog_id = (isset($_REQUEST['id']) ? $_REQUEST['id'] : 0);
|
184 |
+
$this->plugin->alerts->TriggerIf(4011, array(
|
185 |
+
'TargetUserID' => $user_id,
|
186 |
+
'TargetUsername' => $user->user_login,
|
187 |
+
'TargetUserRole' => is_array($user->roles) ? implode(', ', $user->roles) : $user->roles,
|
188 |
+
'BlogID' => $blog_id,
|
189 |
+
'SiteName' => get_blog_option($blog_id, 'blogname'),
|
190 |
+
), array($this, 'MustNotContainCreateUser'));
|
191 |
+
}
|
192 |
+
|
193 |
+
/**
|
194 |
+
* New network user created.
|
195 |
+
*/
|
196 |
+
public function MustNotContainCreateUser(WSAL_AlertManager $mgr)
|
197 |
+
{
|
198 |
+
return !$mgr->WillTrigger(4012);
|
199 |
+
}
|
200 |
+
}
|
classes/Sensors/PhpErrors.php
CHANGED
@@ -1,104 +1,139 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
69 |
-
|
70 |
-
|
71 |
-
|
72 |
-
|
73 |
-
|
74 |
-
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
|
79 |
-
|
80 |
-
|
81 |
-
|
82 |
-
|
83 |
-
|
84 |
-
|
85 |
-
|
86 |
-
|
87 |
-
|
88 |
-
|
89 |
-
|
90 |
-
|
91 |
-
|
92 |
-
|
93 |
-
|
94 |
-
|
95 |
-
|
96 |
-
|
97 |
-
|
98 |
-
|
99 |
-
|
100 |
-
|
101 |
-
|
102 |
-
|
103 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
104 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Php Errors sensor.
|
6 |
+
*
|
7 |
+
* 0001 PHP error
|
8 |
+
* 0002 PHP warning
|
9 |
+
* 0003 PHP notice
|
10 |
+
* 0004 PHP exception
|
11 |
+
* 0005 PHP shutdown error
|
12 |
+
*/
|
13 |
+
class WSAL_Sensors_PhpErrors extends WSAL_AbstractSensor
|
14 |
+
{
|
15 |
+
protected $_avoid_error_recursion = false;
|
16 |
+
protected $_maybe_last_error = null;
|
17 |
+
|
18 |
+
protected $_error_types = array(
|
19 |
+
0001 => array(1,4,16,64,256,4096), // errors
|
20 |
+
0002 => array(2,32,128,512), // warnings
|
21 |
+
0003 => array(8,1024,2048,8192,16384), // notices
|
22 |
+
0004 => array(), // exceptions
|
23 |
+
0005 => array(), // shutdown
|
24 |
+
);
|
25 |
+
|
26 |
+
/**
|
27 |
+
* Listening to Php events.
|
28 |
+
*/
|
29 |
+
public function HookEvents()
|
30 |
+
{
|
31 |
+
if ($this->plugin->settings->IsPhpErrorLoggingEnabled()) {
|
32 |
+
set_error_handler(array($this, 'EventError'), E_ALL);
|
33 |
+
set_exception_handler(array($this, 'EventException'));
|
34 |
+
register_shutdown_function(array($this, 'EventShutdown'));
|
35 |
+
}
|
36 |
+
}
|
37 |
+
|
38 |
+
/**
|
39 |
+
* Get the hash of the error.
|
40 |
+
*/
|
41 |
+
protected function GetErrorHash($code, $mesg, $file, $line)
|
42 |
+
{
|
43 |
+
return md5(implode(':', func_get_args()));
|
44 |
+
}
|
45 |
+
|
46 |
+
/**
|
47 |
+
* PHP error, warning or notice.
|
48 |
+
*/
|
49 |
+
public function EventError($errno, $errstr, $errfile = 'unknown', $errline = 0, $errcontext = array())
|
50 |
+
{
|
51 |
+
if ($this->_avoid_error_recursion) {
|
52 |
+
return;
|
53 |
+
}
|
54 |
+
|
55 |
+
$errbacktrace = 'No Backtrace';
|
56 |
+
if ($this->plugin->settings->IsBacktraceLoggingEnabled()) {
|
57 |
+
ob_start();
|
58 |
+
debug_print_backtrace();
|
59 |
+
$errbacktrace = ob_get_clean();
|
60 |
+
}
|
61 |
+
|
62 |
+
$data = array(
|
63 |
+
'Code' => $errno,
|
64 |
+
'Message' => $errstr,
|
65 |
+
'File' => $errfile,
|
66 |
+
'Line' => $errline,
|
67 |
+
'Context' => $errcontext,
|
68 |
+
'Trace' => $errbacktrace,
|
69 |
+
);
|
70 |
+
|
71 |
+
$type = 0002; // default (middle ground)
|
72 |
+
foreach ($this->_error_types as $temp => $codes) {
|
73 |
+
if (in_array($errno, $codes)) {
|
74 |
+
$type = $temp;
|
75 |
+
}
|
76 |
+
}
|
77 |
+
|
78 |
+
$this->_maybe_last_error = $this->GetErrorHash($errno, $errstr, $errfile, $errline);
|
79 |
+
|
80 |
+
$this->_avoid_error_recursion = true;
|
81 |
+
$this->plugin->alerts->Trigger($type, $data);
|
82 |
+
$this->_avoid_error_recursion = false;
|
83 |
+
}
|
84 |
+
|
85 |
+
/**
|
86 |
+
* PHP exception.
|
87 |
+
*/
|
88 |
+
public function EventException(Exception $ex)
|
89 |
+
{
|
90 |
+
if ($this->_avoid_error_recursion) {
|
91 |
+
return;
|
92 |
+
}
|
93 |
+
|
94 |
+
$errbacktrace = 'No Backtrace';
|
95 |
+
if ($this->plugin->settings->IsBacktraceLoggingEnabled()) {
|
96 |
+
$errbacktrace = $ex->getTraceAsString();
|
97 |
+
}
|
98 |
+
|
99 |
+
$data = array(
|
100 |
+
'Class' => get_class($ex),
|
101 |
+
'Code' => $ex->getCode(),
|
102 |
+
'Message' => $ex->getMessage(),
|
103 |
+
'File' => $ex->getFile(),
|
104 |
+
'Line' => $ex->getLine(),
|
105 |
+
'Trace' => $errbacktrace,
|
106 |
+
);
|
107 |
+
|
108 |
+
if (method_exists($ex, 'getContext')) {
|
109 |
+
$data['Context'] = $ex->getContext();
|
110 |
+
}
|
111 |
+
|
112 |
+
$this->_avoid_error_recursion = true;
|
113 |
+
$this->plugin->alerts->Trigger(0004, $data);
|
114 |
+
$this->_avoid_error_recursion = false;
|
115 |
+
}
|
116 |
+
|
117 |
+
/**
|
118 |
+
* PHP shutdown error.
|
119 |
+
*/
|
120 |
+
public function EventShutdown()
|
121 |
+
{
|
122 |
+
if ($this->_avoid_error_recursion) {
|
123 |
+
return;
|
124 |
+
}
|
125 |
+
|
126 |
+
if (!!($e = error_get_last()) && ($this->_maybe_last_error != $this->GetErrorHash($e['type'], $e['message'], $e['file'], $e['line']))) {
|
127 |
+
$data = array(
|
128 |
+
'Code' => $e['type'],
|
129 |
+
'Message' => $e['message'],
|
130 |
+
'File' => $e['file'],
|
131 |
+
'Line' => $e['line'],
|
132 |
+
);
|
133 |
+
|
134 |
+
$this->_avoid_error_recursion = true;
|
135 |
+
$this->plugin->alerts->Trigger(0005, $data);
|
136 |
+
$this->_avoid_error_recursion = false;
|
137 |
+
}
|
138 |
+
}
|
139 |
}
|
classes/Sensors/PluginsThemes.php
CHANGED
@@ -1,29 +1,65 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
4 |
{
|
|
|
|
|
5 |
|
6 |
-
|
|
|
|
|
|
|
|
|
7 |
$hasPermission = (current_user_can("install_plugins") || current_user_can("activate_plugins") ||
|
8 |
current_user_can("delete_plugins") || current_user_can("update_plugins") || current_user_can("install_themes"));
|
9 |
|
10 |
add_action('admin_init', array($this, 'EventAdminInit'));
|
11 |
-
if($hasPermission)
|
|
|
|
|
12 |
add_action('switch_theme', array($this, 'EventThemeActivated'));
|
13 |
// TO DO
|
14 |
add_action('wp_insert_post', array($this, 'EventPluginPostCreate'), 10, 2);
|
15 |
add_action('delete_post', array($this, 'EventPluginPostDelete'), 10, 1);
|
16 |
}
|
17 |
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
public function EventAdminInit()
|
|
|
22 |
$this->old_themes = wp_get_themes();
|
23 |
$this->old_plugins = get_plugins();
|
24 |
}
|
25 |
|
26 |
-
|
|
|
|
|
|
|
|
|
27 |
$action = (isset($_REQUEST['action']) && $_REQUEST['action'] != "-1") ? $_REQUEST['action'] : '';
|
28 |
$action = (isset($_REQUEST['action2']) && $_REQUEST['action2'] != "-1") ? $_REQUEST['action2'] : $action;
|
29 |
$actype = basename($_SERVER['SCRIPT_NAME'], '.php');
|
@@ -35,9 +71,9 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
35 |
$plugin = array_values(array_diff(array_keys(get_plugins()), array_keys($this->old_plugins)));
|
36 |
if (count($plugin) != 1) {
|
37 |
return $this->LogError(
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
}
|
42 |
$pluginPath = $plugin[0];
|
43 |
$plugin = get_plugins();
|
@@ -227,7 +263,12 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
227 |
}
|
228 |
}
|
229 |
|
230 |
-
|
|
|
|
|
|
|
|
|
|
|
231 |
$theme = null;
|
232 |
foreach (wp_get_themes() as $item) {
|
233 |
if ($item->Name == $themeName) {
|
@@ -237,9 +278,9 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
237 |
}
|
238 |
if ($theme == null) {
|
239 |
return $this->LogError(
|
240 |
-
|
241 |
-
|
242 |
-
|
243 |
}
|
244 |
$this->plugin->alerts->Trigger(5006, array(
|
245 |
'Theme' => (object)array(
|
@@ -254,7 +295,8 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
254 |
}
|
255 |
|
256 |
/**
|
257 |
-
*
|
|
|
258 |
*/
|
259 |
public function EventPluginPostCreate($insert, $post)
|
260 |
{
|
@@ -284,6 +326,10 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
284 |
}
|
285 |
}
|
286 |
|
|
|
|
|
|
|
|
|
287 |
public function EventPluginPostDelete($post_id)
|
288 |
{
|
289 |
if (empty($_REQUEST['action']) && isset($_REQUEST['page'])) {
|
@@ -300,6 +346,10 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
300 |
}
|
301 |
}
|
302 |
|
|
|
|
|
|
|
|
|
303 |
protected function GetRemovedThemes()
|
304 |
{
|
305 |
$result = $this->old_themes;
|
@@ -311,6 +361,9 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
311 |
return array_values($result);
|
312 |
}
|
313 |
|
|
|
|
|
|
|
314 |
protected function GetEventTypeForPostType($post, $typePost, $typePage, $typeCustom)
|
315 |
{
|
316 |
switch ($post->post_type) {
|
@@ -323,6 +376,11 @@ class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
|
323 |
}
|
324 |
}
|
325 |
|
|
|
|
|
|
|
|
|
|
|
326 |
private function GetEditorLink($post)
|
327 |
{
|
328 |
$name = 'EditorLink';
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Plugins & Themes sensor.
|
6 |
+
*
|
7 |
+
* 5000 User installed a plugin
|
8 |
+
* 5001 User activated a WordPress plugin
|
9 |
+
* 5002 User deactivated a WordPress plugin
|
10 |
+
* 5003 User uninstalled a plugin
|
11 |
+
* 5004 User upgraded a plugin
|
12 |
+
* 5005 User installed a theme
|
13 |
+
* 5006 User activated a theme
|
14 |
+
* 5007 User uninstalled a theme
|
15 |
+
* 5019 A plugin created a post
|
16 |
+
* 5020 A plugin created a page
|
17 |
+
* 5021 A plugin created a custom post
|
18 |
+
* 5025 A plugin deleted a post
|
19 |
+
* 5026 A plugin deleted a page
|
20 |
+
* 5027 A plugin deleted a custom post
|
21 |
+
* 5031 User updated a theme
|
22 |
+
* 2106 A plugin modified a post
|
23 |
+
* 2107 A plugin modified a page
|
24 |
+
* 2108 A plugin modified a custom post
|
25 |
+
*/
|
26 |
class WSAL_Sensors_PluginsThemes extends WSAL_AbstractSensor
|
27 |
{
|
28 |
+
protected $old_themes = array();
|
29 |
+
protected $old_plugins = array();
|
30 |
|
31 |
+
/**
|
32 |
+
* Listening to events using WP hooks.
|
33 |
+
*/
|
34 |
+
public function HookEvents()
|
35 |
+
{
|
36 |
$hasPermission = (current_user_can("install_plugins") || current_user_can("activate_plugins") ||
|
37 |
current_user_can("delete_plugins") || current_user_can("update_plugins") || current_user_can("install_themes"));
|
38 |
|
39 |
add_action('admin_init', array($this, 'EventAdminInit'));
|
40 |
+
if ($hasPermission) {
|
41 |
+
add_action('shutdown', array($this, 'EventAdminShutdown'));
|
42 |
+
}
|
43 |
add_action('switch_theme', array($this, 'EventThemeActivated'));
|
44 |
// TO DO
|
45 |
add_action('wp_insert_post', array($this, 'EventPluginPostCreate'), 10, 2);
|
46 |
add_action('delete_post', array($this, 'EventPluginPostDelete'), 10, 1);
|
47 |
}
|
48 |
|
49 |
+
/**
|
50 |
+
* Triggered when a user accesses the admin area.
|
51 |
+
*/
|
52 |
+
public function EventAdminInit()
|
53 |
+
{
|
54 |
$this->old_themes = wp_get_themes();
|
55 |
$this->old_plugins = get_plugins();
|
56 |
}
|
57 |
|
58 |
+
/**
|
59 |
+
* Install, uninstall, activate, deactivate, upgrade and update.
|
60 |
+
*/
|
61 |
+
public function EventAdminShutdown()
|
62 |
+
{
|
63 |
$action = (isset($_REQUEST['action']) && $_REQUEST['action'] != "-1") ? $_REQUEST['action'] : '';
|
64 |
$action = (isset($_REQUEST['action2']) && $_REQUEST['action2'] != "-1") ? $_REQUEST['action2'] : $action;
|
65 |
$actype = basename($_SERVER['SCRIPT_NAME'], '.php');
|
71 |
$plugin = array_values(array_diff(array_keys(get_plugins()), array_keys($this->old_plugins)));
|
72 |
if (count($plugin) != 1) {
|
73 |
return $this->LogError(
|
74 |
+
'Expected exactly one new plugin but found ' . count($plugin),
|
75 |
+
array('NewPlugin' => $plugin, 'OldPlugins' => $this->old_plugins, 'NewPlugins' => get_plugins())
|
76 |
+
);
|
77 |
}
|
78 |
$pluginPath = $plugin[0];
|
79 |
$plugin = get_plugins();
|
263 |
}
|
264 |
}
|
265 |
|
266 |
+
/**
|
267 |
+
* Activated a theme.
|
268 |
+
* @param string $themeName name
|
269 |
+
*/
|
270 |
+
public function EventThemeActivated($themeName)
|
271 |
+
{
|
272 |
$theme = null;
|
273 |
foreach (wp_get_themes() as $item) {
|
274 |
if ($item->Name == $themeName) {
|
278 |
}
|
279 |
if ($theme == null) {
|
280 |
return $this->LogError(
|
281 |
+
'Could not locate theme named "' . $theme . '".',
|
282 |
+
array('ThemeName' => $themeName, 'Themes' => wp_get_themes())
|
283 |
+
);
|
284 |
}
|
285 |
$this->plugin->alerts->Trigger(5006, array(
|
286 |
'Theme' => (object)array(
|
295 |
}
|
296 |
|
297 |
/**
|
298 |
+
* Plugin creates/modifies posts.
|
299 |
+
* @param WP_Post $post post object
|
300 |
*/
|
301 |
public function EventPluginPostCreate($insert, $post)
|
302 |
{
|
326 |
}
|
327 |
}
|
328 |
|
329 |
+
/**
|
330 |
+
* Plugin deletes posts.
|
331 |
+
* @param integer $post_id post ID
|
332 |
+
*/
|
333 |
public function EventPluginPostDelete($post_id)
|
334 |
{
|
335 |
if (empty($_REQUEST['action']) && isset($_REQUEST['page'])) {
|
346 |
}
|
347 |
}
|
348 |
|
349 |
+
/**
|
350 |
+
* Get removed themes.
|
351 |
+
* @return array of WP_Theme objects
|
352 |
+
*/
|
353 |
protected function GetRemovedThemes()
|
354 |
{
|
355 |
$result = $this->old_themes;
|
361 |
return array_values($result);
|
362 |
}
|
363 |
|
364 |
+
/**
|
365 |
+
* Get event code by post type.
|
366 |
+
*/
|
367 |
protected function GetEventTypeForPostType($post, $typePost, $typePage, $typeCustom)
|
368 |
{
|
369 |
switch ($post->post_type) {
|
376 |
}
|
377 |
}
|
378 |
|
379 |
+
/**
|
380 |
+
* Get editor link.
|
381 |
+
* @param stdClass $post the post
|
382 |
+
* @return array $aLink name and value link
|
383 |
+
*/
|
384 |
private function GetEditorLink($post)
|
385 |
{
|
386 |
$name = 'EditorLink';
|
classes/Sensors/Request.php
CHANGED
@@ -1,7 +1,16 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_Request extends WSAL_AbstractSensor
|
4 |
{
|
|
|
|
|
|
|
|
|
|
|
5 |
public function HookEvents()
|
6 |
{
|
7 |
if ($this->plugin->settings->IsRequestLoggingEnabled()) {
|
@@ -9,6 +18,9 @@ class WSAL_Sensors_Request extends WSAL_AbstractSensor
|
|
9 |
}
|
10 |
}
|
11 |
|
|
|
|
|
|
|
12 |
public function EventShutdown()
|
13 |
{
|
14 |
$upload_dir = wp_upload_dir();
|
@@ -43,13 +55,17 @@ class WSAL_Sensors_Request extends WSAL_AbstractSensor
|
|
43 |
}
|
44 |
}
|
45 |
|
46 |
-
|
47 |
-
|
|
|
48 |
public static function SetVar($name, $value)
|
49 |
{
|
50 |
self::$envvars[$name] = $value;
|
51 |
}
|
52 |
|
|
|
|
|
|
|
53 |
public static function SetVars($data)
|
54 |
{
|
55 |
foreach ($data as $name => $value) {
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Writes the Request.log.php file.
|
6 |
+
*/
|
7 |
class WSAL_Sensors_Request extends WSAL_AbstractSensor
|
8 |
{
|
9 |
+
protected static $envvars = array();
|
10 |
+
|
11 |
+
/**
|
12 |
+
* Listening to events using WP hooks.
|
13 |
+
*/
|
14 |
public function HookEvents()
|
15 |
{
|
16 |
if ($this->plugin->settings->IsRequestLoggingEnabled()) {
|
18 |
}
|
19 |
}
|
20 |
|
21 |
+
/**
|
22 |
+
* Fires just before PHP shuts down execution.
|
23 |
+
*/
|
24 |
public function EventShutdown()
|
25 |
{
|
26 |
$upload_dir = wp_upload_dir();
|
55 |
}
|
56 |
}
|
57 |
|
58 |
+
/**
|
59 |
+
* Sets $envvars element with key and value.
|
60 |
+
*/
|
61 |
public static function SetVar($name, $value)
|
62 |
{
|
63 |
self::$envvars[$name] = $value;
|
64 |
}
|
65 |
|
66 |
+
/**
|
67 |
+
* Copy data array into $envvars array.
|
68 |
+
*/
|
69 |
public static function SetVars($data)
|
70 |
{
|
71 |
foreach ($data as $name => $value) {
|
classes/Sensors/System.php
CHANGED
@@ -1,32 +1,83 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
|
|
|
|
|
|
|
6 |
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
11 |
|
12 |
-
|
13 |
-
|
|
|
|
|
|
|
|
|
14 |
|
15 |
-
|
16 |
-
$
|
17 |
-
|
18 |
-
|
|
|
19 |
}
|
20 |
|
21 |
-
// Cron Job 404 log files pruning
|
22 |
-
add_action('log_files_pruning', array($this,'LogFilesPruning'));
|
23 |
-
if (!wp_next_scheduled('log_files_pruning')) {
|
24 |
-
wp_schedule_event(time(), 'daily', 'log_files_pruning');
|
25 |
}
|
26 |
-
// whitelist options
|
27 |
-
add_action('whitelist_options', array($this, 'EventOptions'), 10, 1);
|
28 |
}
|
29 |
-
|
30 |
/**
|
31 |
* @param int $count The number of deleted events.
|
32 |
* @param string $query Query that selected events for deletion.
|
@@ -39,25 +90,55 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
39 |
));
|
40 |
}
|
41 |
|
|
|
|
|
|
|
|
|
42 |
protected function Get404LogLimit()
|
43 |
{
|
44 |
return $this->plugin->settings->Get404LogLimit();
|
45 |
}
|
46 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
47 |
protected function Get404Expiration()
|
48 |
{
|
49 |
return 24 * 60 * 60;
|
50 |
}
|
51 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
52 |
protected function IsPast404Limit($site_id, $username, $ip)
|
53 |
{
|
54 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
55 |
$data = $get_fn(self::TRANSIENT_404);
|
56 |
return ($data !== false) && isset($data[$site_id.":".$username.":".$ip]) && ($data[$site_id.":".$username.":".$ip] > $this->Get404LogLimit());
|
57 |
}
|
58 |
-
|
59 |
-
protected function
|
60 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
61 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
62 |
$set_fn = $this->IsMultisite() ? 'set_site_transient' : 'set_transient';
|
63 |
|
@@ -71,95 +152,187 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
71 |
$data[$site_id.":".$username.":".$ip]++;
|
72 |
$set_fn(self::TRANSIENT_404, $data, $this->Get404Expiration());
|
73 |
}
|
74 |
-
|
75 |
-
|
76 |
-
|
77 |
-
$
|
78 |
-
|
79 |
-
|
80 |
-
|
|
|
|
|
|
|
|
|
81 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
82 |
global $wp_query;
|
83 |
-
if (
|
84 |
return;
|
85 |
}
|
86 |
$msg = 'times';
|
87 |
|
88 |
-
list($y, $m, $d) = explode('-', date('Y-m-d'));
|
89 |
|
90 |
-
$site_id
|
91 |
-
$ip
|
92 |
|
93 |
-
if (!is_user_logged_in()) {
|
94 |
-
$username =
|
95 |
} else {
|
96 |
$username = wp_get_current_user()->user_login;
|
97 |
}
|
98 |
-
|
99 |
-
if ($this->IsPast404Limit($site_id, $username, $ip)) {
|
100 |
-
return;
|
101 |
-
}
|
102 |
|
103 |
-
$
|
104 |
-
|
105 |
-
|
106 |
-
|
107 |
-
|
108 |
-
|
109 |
-
|
110 |
-
|
111 |
-
|
112 |
-
|
113 |
-
|
114 |
-
|
115 |
-
|
116 |
-
|
117 |
-
|
118 |
-
|
119 |
-
|
120 |
-
|
121 |
-
|
122 |
-
|
123 |
-
|
124 |
-
|
125 |
-
|
126 |
-
|
127 |
-
$
|
128 |
-
|
129 |
-
|
130 |
-
|
131 |
-
|
132 |
-
|
133 |
-
$
|
134 |
-
|
135 |
-
|
136 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
137 |
} else {
|
138 |
-
|
139 |
-
//
|
140 |
-
$
|
141 |
-
|
142 |
-
|
143 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
144 |
);
|
145 |
-
|
146 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
147 |
}
|
148 |
-
$this->plugin->alerts->Trigger(6007, $fields);
|
149 |
}
|
150 |
}
|
151 |
|
152 |
-
|
153 |
-
|
154 |
-
|
155 |
-
|
156 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
157 |
$action = isset($_REQUEST['action']) ? $_REQUEST['action'] : '';
|
158 |
$actype = basename($_SERVER['SCRIPT_NAME'], '.php');
|
159 |
$is_option_page = $actype == 'options';
|
160 |
$is_network_settings = $actype == 'settings';
|
161 |
$is_permalink_page = $actype == 'options-permalink';
|
162 |
-
|
163 |
if ($is_option_page && (get_option('users_can_register') xor isset($_POST['users_can_register']))) {
|
164 |
$old = get_option('users_can_register') ? 'Enabled' : 'Disabled';
|
165 |
$new = isset($_POST['users_can_register']) ? 'Enabled' : 'Disabled';
|
@@ -195,7 +368,7 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
195 |
));
|
196 |
}
|
197 |
}
|
198 |
-
|
199 |
if ($is_network_settings && !empty($_POST['admin_email'])) {
|
200 |
$old = get_site_option('admin_email');
|
201 |
$new = trim($_POST['admin_email']);
|
@@ -207,7 +380,7 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
207 |
));
|
208 |
}
|
209 |
}
|
210 |
-
|
211 |
if ($is_permalink_page && !empty($_REQUEST['permalink_structure'])) {
|
212 |
$old = get_option('permalink_structure');
|
213 |
$new = trim($_REQUEST['permalink_structure']);
|
@@ -219,7 +392,7 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
219 |
));
|
220 |
}
|
221 |
}
|
222 |
-
|
223 |
if ($action == 'do-core-upgrade' && isset($_REQUEST['version'])) {
|
224 |
$oldVersion = get_bloginfo('version');
|
225 |
$newVersion = $_REQUEST['version'];
|
@@ -230,7 +403,7 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
230 |
));
|
231 |
}
|
232 |
}
|
233 |
-
|
234 |
/* BBPress Forum support Setting */
|
235 |
if ($action == 'update' && isset($_REQUEST['_bbp_default_role'])) {
|
236 |
$oldRole = get_option('_bbp_default_role');
|
@@ -275,12 +448,6 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
275 |
));
|
276 |
}
|
277 |
}
|
278 |
-
// Destroy all the session of the same user from user profile page
|
279 |
-
if ($action == 'destroy-sessions' && isset($_REQUEST['user_id'])) {
|
280 |
-
$this->plugin->alerts->Trigger(1006, array(
|
281 |
-
'TargetUserID' => $_REQUEST['user_id']
|
282 |
-
));
|
283 |
-
}
|
284 |
}
|
285 |
|
286 |
/**
|
@@ -299,13 +466,12 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
299 |
}
|
300 |
|
301 |
/**
|
302 |
-
* Purge log files older than one month
|
303 |
*/
|
304 |
-
public function LogFilesPruning()
|
305 |
-
{
|
306 |
if ($this->plugin->GetGlobalOption('purge-404-log', 'off') == 'on') {
|
307 |
$upload_dir = wp_upload_dir();
|
308 |
-
$uploadsDirPath = trailingslashit($upload_dir['basedir']).'wp-security-audit-log/404s/';
|
309 |
if (is_dir($uploadsDirPath)) {
|
310 |
if ($handle = opendir($uploadsDirPath)) {
|
311 |
while (false !== ($entry = readdir($handle))) {
|
@@ -323,6 +489,26 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
323 |
}
|
324 |
}
|
325 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
326 |
}
|
327 |
|
328 |
/**
|
@@ -418,60 +604,112 @@ class WSAL_Sensors_System extends WSAL_AbstractSensor
|
|
418 |
* Write a new line on 404 log file
|
419 |
* Folder: /uploads/wp-security-audit-log/404s/
|
420 |
*/
|
421 |
-
private function WriteLog($attempts, $ip, $username = '')
|
422 |
-
{
|
423 |
$nameFile = null;
|
424 |
-
|
425 |
-
|
426 |
-
|
427 |
-
|
428 |
-
|
429 |
-
|
430 |
-
$
|
431 |
-
|
432 |
-
|
433 |
-
|
434 |
-
|
435 |
-
|
436 |
-
|
437 |
-
|
438 |
-
|
439 |
-
|
440 |
-
|
441 |
-
|
442 |
-
|
443 |
-
|
444 |
-
|
445 |
-
|
446 |
-
|
447 |
-
|
448 |
-
$
|
449 |
-
|
450 |
-
|
451 |
-
$
|
452 |
-
|
453 |
-
|
454 |
-
|
455 |
-
$
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
456 |
}
|
457 |
-
|
458 |
-
|
459 |
-
|
460 |
-
|
461 |
-
|
462 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
463 |
}
|
464 |
-
|
465 |
-
$
|
466 |
-
}
|
|
|
|
|
467 |
}
|
468 |
-
fwrite($file, sprintf("%s\n", $data));
|
469 |
-
fclose($file);
|
470 |
}
|
471 |
}
|
|
|
472 |
return $nameFile;
|
473 |
}
|
474 |
|
|
|
|
|
|
|
|
|
475 |
private function GetLastModified($uploadsDirPath, $filename)
|
476 |
{
|
477 |
$filename = substr($filename, 0, -4);
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* System Activity sensor.
|
6 |
+
*
|
7 |
+
* 6000 Events automatically pruned by system
|
8 |
+
* 6001 Option Anyone Can Register in WordPress settings changed
|
9 |
+
* 6002 New User Default Role changed
|
10 |
+
* 6003 WordPress Administrator Notification email changed
|
11 |
+
* 6004 WordPress was updated
|
12 |
+
* 6005 User changes the WordPress Permalinks
|
13 |
+
* 6007 User requests non-existing pages (404 Error Pages)
|
14 |
+
* 8009 User changed forum's role
|
15 |
+
* 8010 User changed option of a forum
|
16 |
+
* 8012 User changed time to disallow post editing
|
17 |
+
* 8013 User changed the forum setting posting throttle time
|
18 |
+
* 1006 User logged out all other sessions with the same username
|
19 |
+
* 6004 WordPress was updated
|
20 |
+
* 6008 Enabled/Disabled the option Discourage search engines from indexing this site
|
21 |
+
* 6009 Enabled/Disabled comments on all the website
|
22 |
+
* 6010 Enabled/Disabled the option Comment author must fill out name and email
|
23 |
+
* 6011 Enabled/Disabled the option Users must be logged in and registered to comment
|
24 |
+
* 6012 Enabled/Disabled the option to automatically close comments
|
25 |
+
* 6013 Changed the value of the option Automatically close comments
|
26 |
+
* 6014 Enabled/Disabled the option for comments to be manually approved
|
27 |
+
* 6015 Enabled/Disabled the option for an author to have previously approved comments for the comments to appear
|
28 |
+
* 6016 Changed the number of links that a comment must have to be held in the queue
|
29 |
+
* 6017 Modified the list of keywords for comments moderation
|
30 |
+
* 6018 Modified the list of keywords for comments blacklisting
|
31 |
+
*/
|
32 |
+
class WSAL_Sensors_System extends WSAL_AbstractSensor {
|
33 |
|
34 |
+
/**
|
35 |
+
* Transient name.
|
36 |
+
* WordPress will prefix the name with "_transient_" or "_transient_timeout_" in the options table.
|
37 |
+
*/
|
38 |
+
const TRANSIENT_404 = 'wsal-404-attempts';
|
39 |
+
const TRANSIENT_VISITOR_404 = 'wsal-visitor-404-attempts';
|
40 |
|
41 |
+
/**
|
42 |
+
* Listening to events using WP hooks.
|
43 |
+
*/
|
44 |
+
public function HookEvents() {
|
45 |
+
|
46 |
+
add_action( 'wsal_prune', array( $this, 'EventPruneEvents' ), 10, 2 );
|
47 |
+
add_action( 'admin_init', array( $this, 'EventAdminInit' ) );
|
48 |
+
|
49 |
+
add_action( 'automatic_updates_complete', array( $this, 'WPUpdate' ), 10, 1 );
|
50 |
+
add_filter( 'template_redirect', array( $this, 'Event404' ) );
|
51 |
+
|
52 |
+
$upload_dir = wp_upload_dir();
|
53 |
+
$uploadsDirPath = trailingslashit( $upload_dir['basedir'] ) . 'wp-security-audit-log/404s/';
|
54 |
+
if ( ! $this->CheckDirectory( $uploadsDirPath ) ) {
|
55 |
+
wp_mkdir_p( $uploadsDirPath );
|
56 |
+
}
|
57 |
|
58 |
+
// Directory for logged in users log files.
|
59 |
+
$user_upload_dir = wp_upload_dir();
|
60 |
+
$user_upload_path = trailingslashit( $user_upload_dir['basedir'] . '/wp-security-audit-log/404s/users/' );
|
61 |
+
if ( ! $this->CheckDirectory( $user_upload_path ) ) {
|
62 |
+
wp_mkdir_p( $user_upload_path );
|
63 |
+
}
|
64 |
|
65 |
+
// Directory for visitor log files.
|
66 |
+
$visitor_upload_dir = wp_upload_dir();
|
67 |
+
$visitor_upload_path = trailingslashit( $visitor_upload_dir['basedir'] . '/wp-security-audit-log/404s/visitors/' );
|
68 |
+
if ( ! $this->CheckDirectory( $visitor_upload_path ) ) {
|
69 |
+
wp_mkdir_p( $visitor_upload_path );
|
70 |
}
|
71 |
|
72 |
+
// Cron Job 404 log files pruning.
|
73 |
+
add_action( 'log_files_pruning', array( $this, 'LogFilesPruning' ) );
|
74 |
+
if ( ! wp_next_scheduled( 'log_files_pruning' ) ) {
|
75 |
+
wp_schedule_event( time(), 'daily', 'log_files_pruning' );
|
76 |
}
|
77 |
+
// whitelist options.
|
78 |
+
add_action( 'whitelist_options', array( $this, 'EventOptions' ), 10, 1 );
|
79 |
}
|
80 |
+
|
81 |
/**
|
82 |
* @param int $count The number of deleted events.
|
83 |
* @param string $query Query that selected events for deletion.
|
90 |
));
|
91 |
}
|
92 |
|
93 |
+
/**
|
94 |
+
* 404 limit count.
|
95 |
+
* @return integer limit
|
96 |
+
*/
|
97 |
protected function Get404LogLimit()
|
98 |
{
|
99 |
return $this->plugin->settings->Get404LogLimit();
|
100 |
}
|
101 |
+
|
102 |
+
protected function GetVisitor404LogLimit() {
|
103 |
+
return $this->plugin->settings->GetVisitor404LogLimit();
|
104 |
+
}
|
105 |
+
|
106 |
+
/**
|
107 |
+
* Expiration of the transient saved in the WP database.
|
108 |
+
* @return integer Time until expiration in seconds from now
|
109 |
+
*/
|
110 |
protected function Get404Expiration()
|
111 |
{
|
112 |
return 24 * 60 * 60;
|
113 |
}
|
114 |
|
115 |
+
/**
|
116 |
+
* Check 404 limit.
|
117 |
+
* @param integer $site_id blog ID
|
118 |
+
* @param string $username username
|
119 |
+
* @param string $ip IP address
|
120 |
+
* @return boolean passed limit true|false
|
121 |
+
*/
|
122 |
protected function IsPast404Limit($site_id, $username, $ip)
|
123 |
{
|
124 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
125 |
$data = $get_fn(self::TRANSIENT_404);
|
126 |
return ($data !== false) && isset($data[$site_id.":".$username.":".$ip]) && ($data[$site_id.":".$username.":".$ip] > $this->Get404LogLimit());
|
127 |
}
|
128 |
+
|
129 |
+
protected function IsPastVisitor404Limit( $site_id, $username, $ip ) {
|
130 |
+
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
131 |
+
$data = $get_fn( self::TRANSIENT_VISITOR_404 );
|
132 |
+
return ( false !== $data ) && isset( $data[ $site_id . ':' . $username . ':' . $ip ] ) && ( $data[ $site_id . ':' . $username . ':' . $ip ] > $this->GetVisitor404LogLimit() );
|
133 |
+
}
|
134 |
+
|
135 |
+
/**
|
136 |
+
* Increment 404 limit.
|
137 |
+
* @param integer $site_id blog ID
|
138 |
+
* @param string $username username
|
139 |
+
* @param string $ip IP address
|
140 |
+
*/
|
141 |
+
protected function Increment404($site_id, $username, $ip) {
|
142 |
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
143 |
$set_fn = $this->IsMultisite() ? 'set_site_transient' : 'set_transient';
|
144 |
|
152 |
$data[$site_id.":".$username.":".$ip]++;
|
153 |
$set_fn(self::TRANSIENT_404, $data, $this->Get404Expiration());
|
154 |
}
|
155 |
+
|
156 |
+
protected function IncrementVisitor404( $site_id, $username, $ip ) {
|
157 |
+
$get_fn = $this->IsMultisite() ? 'get_site_transient' : 'get_transient';
|
158 |
+
$set_fn = $this->IsMultisite() ? 'set_site_transient' : 'set_transient';
|
159 |
+
|
160 |
+
$data = $get_fn( self::TRANSIENT_VISITOR_404 );
|
161 |
+
if ( ! $data ) {
|
162 |
+
$data = array();
|
163 |
+
}
|
164 |
+
if ( ! isset( $data[ $site_id . ':' . $username . ':' . $ip ] ) ) {
|
165 |
+
$data[ $site_id . ':' . $username . ':' . $ip ] = 1;
|
166 |
}
|
167 |
+
$data[ $site_id . ':' . $username . ':' . $ip ]++;
|
168 |
+
$set_fn( self::TRANSIENT_VISITOR_404, $data, $this->Get404Expiration() );
|
169 |
+
}
|
170 |
+
|
171 |
+
/**
|
172 |
+
* Event 404 Not found.
|
173 |
+
*/
|
174 |
+
public function Event404() {
|
175 |
+
|
176 |
+
$attempts = 1;
|
177 |
+
|
178 |
global $wp_query;
|
179 |
+
if ( ! $wp_query->is_404 ) {
|
180 |
return;
|
181 |
}
|
182 |
$msg = 'times';
|
183 |
|
184 |
+
list( $y, $m, $d ) = explode( '-', date( 'Y-m-d' ) );
|
185 |
|
186 |
+
$site_id = ( function_exists( 'get_current_blog_id' ) ? get_current_blog_id() : 0 );
|
187 |
+
$ip = $this->plugin->settings->GetMainClientIP();
|
188 |
|
189 |
+
if ( ! is_user_logged_in() ) {
|
190 |
+
$username = 'Website Visitor';
|
191 |
} else {
|
192 |
$username = wp_get_current_user()->user_login;
|
193 |
}
|
|
|
|
|
|
|
|
|
194 |
|
195 |
+
if ( 'Website Visitor' !== $username ) {
|
196 |
+
|
197 |
+
// Check if the alert is disabled from the "Enable/Disable Alerts" section.
|
198 |
+
if ( ! $this->plugin->alerts->IsEnabled( 6007 ) ) {
|
199 |
+
return;
|
200 |
+
}
|
201 |
+
|
202 |
+
if ( $this->IsPast404Limit( $site_id, $username, $ip ) ) {
|
203 |
+
return;
|
204 |
+
}
|
205 |
+
|
206 |
+
$objOcc = new WSAL_Models_Occurrence();
|
207 |
+
|
208 |
+
$occ = $objOcc->CheckAlert404(
|
209 |
+
array(
|
210 |
+
$ip,
|
211 |
+
$username,
|
212 |
+
6007,
|
213 |
+
$site_id,
|
214 |
+
mktime(0, 0, 0, $m, $d, $y),
|
215 |
+
mktime(0, 0, 0, $m, $d + 1, $y) - 1
|
216 |
+
)
|
217 |
+
);
|
218 |
+
|
219 |
+
$occ = count( $occ ) ? $occ[0] : null;
|
220 |
+
if ( ! empty( $occ ) ) {
|
221 |
+
// update existing record.
|
222 |
+
$this->Increment404($site_id, $username, $ip);
|
223 |
+
$new = $occ->GetMetaValue('Attempts', 0) + 1;
|
224 |
+
|
225 |
+
if ($new > $this->Get404LogLimit()) {
|
226 |
+
$new = 'more than ' . $this->Get404LogLimit();
|
227 |
+
$msg .= ' This could possible be a scan, therefore keep an eye on the activity from this IP Address';
|
228 |
+
}
|
229 |
+
|
230 |
+
$linkFile = $this->WriteLog( $new, $ip, $username );
|
231 |
+
|
232 |
+
$occ->UpdateMetaValue('Attempts', $new);
|
233 |
+
$occ->UpdateMetaValue('Username', $username);
|
234 |
+
$occ->UpdateMetaValue('Msg', $msg);
|
235 |
+
if (!empty($linkFile)) {
|
236 |
+
$occ->UpdateMetaValue('LinkFile', $linkFile);
|
237 |
+
}
|
238 |
+
$occ->created_on = null;
|
239 |
+
$occ->Save();
|
240 |
+
} else {
|
241 |
+
$linkFile = $this->WriteLog( 1, $ip, $username );
|
242 |
+
// create a new record
|
243 |
+
$fields = array(
|
244 |
+
'Attempts' => 1,
|
245 |
+
'Username' => $username,
|
246 |
+
'Msg' => $msg
|
247 |
+
);
|
248 |
+
if (!empty($linkFile)) {
|
249 |
+
$fields['LinkFile'] = $linkFile;
|
250 |
+
}
|
251 |
+
$this->plugin->alerts->Trigger(6007, $fields);
|
252 |
+
}
|
253 |
} else {
|
254 |
+
|
255 |
+
// Check if the alert is disabled from the "Enable/Disable Alerts" section.
|
256 |
+
if ( ! $this->plugin->alerts->IsEnabled( 6023 ) ) {
|
257 |
+
return;
|
258 |
+
}
|
259 |
+
|
260 |
+
if ( $this->IsPastVisitor404Limit( $site_id, $username, $ip ) ) {
|
261 |
+
return;
|
262 |
+
}
|
263 |
+
|
264 |
+
$objOcc = new WSAL_Models_Occurrence();
|
265 |
+
|
266 |
+
$occ = $objOcc->CheckAlert404(
|
267 |
+
array(
|
268 |
+
$ip,
|
269 |
+
$username,
|
270 |
+
6023,
|
271 |
+
$site_id,
|
272 |
+
mktime(0, 0, 0, $m, $d, $y),
|
273 |
+
mktime(0, 0, 0, $m, $d + 1, $y) - 1
|
274 |
+
)
|
275 |
);
|
276 |
+
|
277 |
+
$occ = count( $occ ) ? $occ[0] : null;
|
278 |
+
if ( ! empty( $occ ) ) {
|
279 |
+
// update existing record.
|
280 |
+
$this->IncrementVisitor404( $site_id, $username, $ip );
|
281 |
+
$new = $occ->GetMetaValue( 'Attempts', 0 ) + 1;
|
282 |
+
|
283 |
+
if ( $new > $this->GetVisitor404LogLimit() ) {
|
284 |
+
$new = 'more than ' . $this->GetVisitor404LogLimit();
|
285 |
+
$msg .= ' This could possible be a scan, therefore keep an eye on the activity from this IP Address';
|
286 |
+
}
|
287 |
+
|
288 |
+
$linkFile = $this->WriteLog( $new, $ip, $username, false );
|
289 |
+
|
290 |
+
$occ->UpdateMetaValue( 'Attempts', $new );
|
291 |
+
$occ->UpdateMetaValue( 'Username', $username );
|
292 |
+
$occ->UpdateMetaValue( 'Msg', $msg );
|
293 |
+
if ( ! empty( $linkFile ) ) {
|
294 |
+
$occ->UpdateMetaValue( 'LinkFile', $linkFile );
|
295 |
+
}
|
296 |
+
$occ->created_on = null;
|
297 |
+
$occ->Save();
|
298 |
+
} else {
|
299 |
+
$linkFile = $this->WriteLog( 1, $ip, $username, false );
|
300 |
+
// create a new record.
|
301 |
+
$fields = array(
|
302 |
+
'Attempts' => 1,
|
303 |
+
'Username' => $username,
|
304 |
+
'Msg' => $msg,
|
305 |
+
);
|
306 |
+
if ( ! empty( $linkFile ) ) {
|
307 |
+
$fields['LinkFile'] = $linkFile;
|
308 |
+
}
|
309 |
+
$this->plugin->alerts->Trigger( 6023, $fields );
|
310 |
}
|
|
|
311 |
}
|
312 |
}
|
313 |
|
314 |
+
/**
|
315 |
+
* Triggered when a user accesses the admin area.
|
316 |
+
*/
|
317 |
+
public function EventAdminInit() {
|
318 |
+
|
319 |
+
// Destroy all the session of the same user from user profile page.
|
320 |
+
if ( isset( $_REQUEST['action'] ) && ( 'destroy-sessions' == $_REQUEST['action'] ) && isset( $_REQUEST['user_id'] ) ) {
|
321 |
+
$this->plugin->alerts->Trigger( 1006, array(
|
322 |
+
'TargetUserID' => $_REQUEST['user_id'],
|
323 |
+
) );
|
324 |
+
}
|
325 |
+
|
326 |
+
// Make sure user can actually modify target options.
|
327 |
+
if ( ! current_user_can( 'manage_options' ) ) {
|
328 |
+
return;
|
329 |
+
}
|
330 |
$action = isset($_REQUEST['action']) ? $_REQUEST['action'] : '';
|
331 |
$actype = basename($_SERVER['SCRIPT_NAME'], '.php');
|
332 |
$is_option_page = $actype == 'options';
|
333 |
$is_network_settings = $actype == 'settings';
|
334 |
$is_permalink_page = $actype == 'options-permalink';
|
335 |
+
|
336 |
if ($is_option_page && (get_option('users_can_register') xor isset($_POST['users_can_register']))) {
|
337 |
$old = get_option('users_can_register') ? 'Enabled' : 'Disabled';
|
338 |
$new = isset($_POST['users_can_register']) ? 'Enabled' : 'Disabled';
|
368 |
));
|
369 |
}
|
370 |
}
|
371 |
+
|
372 |
if ($is_network_settings && !empty($_POST['admin_email'])) {
|
373 |
$old = get_site_option('admin_email');
|
374 |
$new = trim($_POST['admin_email']);
|
380 |
));
|
381 |
}
|
382 |
}
|
383 |
+
|
384 |
if ($is_permalink_page && !empty($_REQUEST['permalink_structure'])) {
|
385 |
$old = get_option('permalink_structure');
|
386 |
$new = trim($_REQUEST['permalink_structure']);
|
392 |
));
|
393 |
}
|
394 |
}
|
395 |
+
|
396 |
if ($action == 'do-core-upgrade' && isset($_REQUEST['version'])) {
|
397 |
$oldVersion = get_bloginfo('version');
|
398 |
$newVersion = $_REQUEST['version'];
|
403 |
));
|
404 |
}
|
405 |
}
|
406 |
+
|
407 |
/* BBPress Forum support Setting */
|
408 |
if ($action == 'update' && isset($_REQUEST['_bbp_default_role'])) {
|
409 |
$oldRole = get_option('_bbp_default_role');
|
448 |
));
|
449 |
}
|
450 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
451 |
}
|
452 |
|
453 |
/**
|
466 |
}
|
467 |
|
468 |
/**
|
469 |
+
* Purge log files older than one month.
|
470 |
*/
|
471 |
+
public function LogFilesPruning() {
|
|
|
472 |
if ($this->plugin->GetGlobalOption('purge-404-log', 'off') == 'on') {
|
473 |
$upload_dir = wp_upload_dir();
|
474 |
+
$uploadsDirPath = trailingslashit($upload_dir['basedir']).'wp-security-audit-log/404s/users/';
|
475 |
if (is_dir($uploadsDirPath)) {
|
476 |
if ($handle = opendir($uploadsDirPath)) {
|
477 |
while (false !== ($entry = readdir($handle))) {
|
489 |
}
|
490 |
}
|
491 |
}
|
492 |
+
if ( 'on' == $this->plugin->GetGlobalOption( 'purge-visitor-404-log', 'off' ) ) {
|
493 |
+
$upload_dir = wp_upload_dir();
|
494 |
+
$uploadsDirPath = trailingslashit( $upload_dir['basedir'] ) . 'wp-security-audit-log/404s/visitors/';
|
495 |
+
if ( is_dir( $uploadsDirPath ) ) {
|
496 |
+
if ( $handle = opendir( $uploadsDirPath ) ) {
|
497 |
+
while ( false !== ( $entry = readdir( $handle ) ) ) {
|
498 |
+
if ( $entry != "." && $entry != ".." ) {
|
499 |
+
if ( file_exists( $uploadsDirPath . $entry ) ) {
|
500 |
+
$modified = filemtime( $uploadsDirPath . $entry );
|
501 |
+
if ( $modified < strtotime( '-4 weeks' ) ) {
|
502 |
+
// Delete file.
|
503 |
+
unlink( $uploadsDirPath . $entry );
|
504 |
+
}
|
505 |
+
}
|
506 |
+
}
|
507 |
+
}
|
508 |
+
closedir( $handle );
|
509 |
+
}
|
510 |
+
}
|
511 |
+
}
|
512 |
}
|
513 |
|
514 |
/**
|
604 |
* Write a new line on 404 log file
|
605 |
* Folder: /uploads/wp-security-audit-log/404s/
|
606 |
*/
|
607 |
+
private function WriteLog( $attempts, $ip, $username = '', $logged_in = true ) {
|
|
|
608 |
$nameFile = null;
|
609 |
+
|
610 |
+
if ( $logged_in ) {
|
611 |
+
if ( 'on' == $this->plugin->GetGlobalOption( 'log-404', 'off' ) ) {
|
612 |
+
// Request URL
|
613 |
+
$url = $_SERVER["HTTP_HOST"] . $_SERVER['REQUEST_URI'];
|
614 |
+
// Create/Append to the log file
|
615 |
+
$data = 'Attempts: ' . $attempts . ' - Request URL: ' . $url;
|
616 |
+
if (!is_user_logged_in()) {
|
617 |
+
$username = '';
|
618 |
+
} else {
|
619 |
+
$username = $username . '_';
|
620 |
+
}
|
621 |
+
|
622 |
+
if ($ip == '127.0.0.1' || $ip == '::1') {
|
623 |
+
$ip = 'localhost';
|
624 |
+
}
|
625 |
+
$upload_dir = wp_upload_dir();
|
626 |
+
$uploadsDirPath = trailingslashit($upload_dir['basedir']).'wp-security-audit-log/404s/users/';
|
627 |
+
$uploadsURL = trailingslashit($upload_dir['baseurl']).'wp-security-audit-log/404s/users/';
|
628 |
+
|
629 |
+
// Check directory
|
630 |
+
if ($this->CheckDirectory($uploadsDirPath)) {
|
631 |
+
$filename = date('Ymd') . '_' . $username . $ip . '.log';
|
632 |
+
$fp = $uploadsDirPath . $filename;
|
633 |
+
$nameFile = $uploadsURL . $filename;
|
634 |
+
if (!$file = fopen($fp, 'a')) {
|
635 |
+
$i = 1;
|
636 |
+
$fileOpened = false;
|
637 |
+
do {
|
638 |
+
$fp2 = substr($fp, 0, -4) . '_' . $i . '.log';
|
639 |
+
if (!file_exists($fp2)) {
|
640 |
+
if ($file = fopen($fp2, 'a')) {
|
641 |
+
$fileOpened = true;
|
642 |
+
$nameFile = $uploadsURL . substr($nameFile, 0, -4) . '_' . $i . '.log';
|
643 |
+
}
|
644 |
+
} else {
|
645 |
+
$latestFilename = $this->GetLastModified($uploadsDirPath, $filename);
|
646 |
+
$fpLast = $uploadsDirPath . $latestFilename;
|
647 |
+
if ($file = fopen($fpLast, 'a')) {
|
648 |
+
$fileOpened = true;
|
649 |
+
$nameFile = $uploadsURL . $latestFilename;
|
650 |
+
}
|
651 |
}
|
652 |
+
$i++;
|
653 |
+
} while (!$fileOpened);
|
654 |
+
}
|
655 |
+
fwrite($file, sprintf("%s\n", $data));
|
656 |
+
fclose($file);
|
657 |
+
}
|
658 |
+
}
|
659 |
+
} else {
|
660 |
+
if ( 'on' == $this->plugin->GetGlobalOption( 'log-visitor-404', 'off' ) ) {
|
661 |
+
// Request URL.
|
662 |
+
$url = $_SERVER["HTTP_HOST"] . $_SERVER['REQUEST_URI'];
|
663 |
+
// Create/Append to the log file.
|
664 |
+
$data = 'Attempts: ' . $attempts . ' - Request URL: ' . $url;
|
665 |
+
$username = '';
|
666 |
+
|
667 |
+
if ( '127.0.0.1' == $ip || '::1' == $ip ) {
|
668 |
+
$ip = 'localhost';
|
669 |
+
}
|
670 |
+
$upload_dir = wp_upload_dir();
|
671 |
+
$uploadsDirPath = trailingslashit( $upload_dir['basedir'] ) . 'wp-security-audit-log/404s/visitors/';
|
672 |
+
$uploadsURL = trailingslashit( $upload_dir['baseurl'] ) . 'wp-security-audit-log/404s/visitors/';
|
673 |
+
|
674 |
+
// Check directory.
|
675 |
+
if ( $this->CheckDirectory( $uploadsDirPath ) ) {
|
676 |
+
$filename = date( 'Ymd' ) . '_' . $username . $ip . '.log';
|
677 |
+
$fp = $uploadsDirPath . $filename;
|
678 |
+
$nameFile = $uploadsURL . $filename;
|
679 |
+
if ( ! $file = fopen( $fp, 'a' ) ) {
|
680 |
+
$i = 1;
|
681 |
+
$fileOpened = false;
|
682 |
+
do {
|
683 |
+
$fp2 = substr( $fp, 0, -4 ) . '_' . $i . '.log';
|
684 |
+
if ( ! file_exists( $fp2 ) ) {
|
685 |
+
if ( $file = fopen( $fp2, 'a' ) ) {
|
686 |
+
$fileOpened = true;
|
687 |
+
$nameFile = $uploadsURL . substr( $nameFile, 0, -4 ) . '_' . $i . '.log';
|
688 |
+
}
|
689 |
+
} else {
|
690 |
+
$latestFilename = $this->GetLastModified( $uploadsDirPath, $filename );
|
691 |
+
$fpLast = $uploadsDirPath . $latestFilename;
|
692 |
+
if ( $file = fopen( $fpLast, 'a' ) ) {
|
693 |
+
$fileOpened = true;
|
694 |
+
$nameFile = $uploadsURL . $latestFilename;
|
695 |
+
}
|
696 |
}
|
697 |
+
$i++;
|
698 |
+
} while ( ! $fileOpened );
|
699 |
+
}
|
700 |
+
fwrite( $file, sprintf( "%s\n", $data ) );
|
701 |
+
fclose( $file );
|
702 |
}
|
|
|
|
|
703 |
}
|
704 |
}
|
705 |
+
|
706 |
return $nameFile;
|
707 |
}
|
708 |
|
709 |
+
/**
|
710 |
+
* Get the latest file modified.
|
711 |
+
* @return string $latest_filename file name
|
712 |
+
*/
|
713 |
private function GetLastModified($uploadsDirPath, $filename)
|
714 |
{
|
715 |
$filename = substr($filename, 0, -4);
|
classes/Sensors/UserProfile.php
CHANGED
@@ -1,8 +1,27 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
class WSAL_Sensors_UserProfile extends WSAL_AbstractSensor
|
4 |
{
|
5 |
-
|
|
|
|
|
6 |
public function HookEvents()
|
7 |
{
|
8 |
add_action('admin_init', array($this, 'EventAdminInit'));
|
@@ -15,16 +34,19 @@ class WSAL_Sensors_UserProfile extends WSAL_AbstractSensor
|
|
15 |
|
16 |
add_action('edit_user_profile', array($this, 'EventOpenProfile'), 10, 1);
|
17 |
}
|
18 |
-
|
19 |
protected $old_superadmins;
|
20 |
-
|
|
|
|
|
|
|
21 |
public function EventAdminInit()
|
22 |
{
|
23 |
if ($this->IsMultisite()) {
|
24 |
$this->old_superadmins = get_super_admins();
|
25 |
}
|
26 |
}
|
27 |
-
|
28 |
public function EventUserRegister($user_id)
|
29 |
{
|
30 |
$user = get_userdata($user_id);
|
@@ -43,7 +65,7 @@ class WSAL_Sensors_UserProfile extends WSAL_AbstractSensor
|
|
43 |
),
|
44 |
), true);
|
45 |
}
|
46 |
-
|
47 |
public function EventUserRoleChanged($user_id, $role, $oldRoles)
|
48 |
{
|
49 |
$user = get_userdata($user_id);
|
@@ -109,11 +131,11 @@ class WSAL_Sensors_UserProfile extends WSAL_AbstractSensor
|
|
109 |
));
|
110 |
}
|
111 |
}
|
112 |
-
|
113 |
if ($this->IsMultisite()) {
|
114 |
$username = $user->user_login;
|
115 |
$enabled = isset($_REQUEST['super_admin']);
|
116 |
-
|
117 |
if ($user_id != get_current_user_id()) {
|
118 |
// super admin enabled
|
119 |
if ($enabled && !in_array($username, $this->old_superadmins)) {
|
@@ -130,11 +152,11 @@ class WSAL_Sensors_UserProfile extends WSAL_AbstractSensor
|
|
130 |
'TargetUsername' => $user->user_login,
|
131 |
));
|
132 |
}
|
133 |
-
|
134 |
}
|
135 |
}
|
136 |
}
|
137 |
-
|
138 |
public function EventUserDeleted($user_id)
|
139 |
{
|
140 |
$user = get_userdata($user_id);
|
@@ -151,24 +173,24 @@ class WSAL_Sensors_UserProfile extends WSAL_AbstractSensor
|
|
151 |
), array($this, 'MustNotContainCreateUser'));
|
152 |
}
|
153 |
|
154 |
-
public function EventOpenProfile($user)
|
155 |
-
|
156 |
-
if (!empty($user)) {
|
157 |
$current_user = wp_get_current_user();
|
158 |
-
|
159 |
-
|
|
|
160 |
'UserChanger' => $current_user->user_login,
|
161 |
-
'TargetUsername' => $user->user_login
|
162 |
-
));
|
163 |
}
|
164 |
}
|
165 |
}
|
166 |
-
|
167 |
public function MustNotContainCreateUser(WSAL_AlertManager $mgr)
|
168 |
{
|
169 |
return !$mgr->WillTrigger(4012);
|
170 |
}
|
171 |
-
|
172 |
public function MustNotContainUserChanges(WSAL_AlertManager $mgr)
|
173 |
{
|
174 |
return !( $mgr->WillOrHasTriggered(4010)
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* User Profiles sensor.
|
6 |
+
*
|
7 |
+
* 4000 New user was created on WordPress
|
8 |
+
* 4001 User created another WordPress user
|
9 |
+
* 4002 The role of a user was changed by another WordPress user
|
10 |
+
* 4003 User has changed his or her password
|
11 |
+
* 4004 User changed another user's password
|
12 |
+
* 4005 User changed his or her email address
|
13 |
+
* 4006 User changed another user's email address
|
14 |
+
* 4007 User was deleted by another user
|
15 |
+
* 4008 User granted Super Admin privileges
|
16 |
+
* 4009 User revoked from Super Admin privileges
|
17 |
+
* 4013 The forum role of a user was changed by another WordPress user
|
18 |
+
* 4014 User opened the profile page of another user
|
19 |
+
*/
|
20 |
class WSAL_Sensors_UserProfile extends WSAL_AbstractSensor
|
21 |
{
|
22 |
+
/**
|
23 |
+
* Listening to events using WP hooks.
|
24 |
+
*/
|
25 |
public function HookEvents()
|
26 |
{
|
27 |
add_action('admin_init', array($this, 'EventAdminInit'));
|
34 |
|
35 |
add_action('edit_user_profile', array($this, 'EventOpenProfile'), 10, 1);
|
36 |
}
|
37 |
+
|
38 |
protected $old_superadmins;
|
39 |
+
|
40 |
+
/**
|
41 |
+
* Triggered when a user accesses the admin area.
|
42 |
+
*/
|
43 |
public function EventAdminInit()
|
44 |
{
|
45 |
if ($this->IsMultisite()) {
|
46 |
$this->old_superadmins = get_super_admins();
|
47 |
}
|
48 |
}
|
49 |
+
|
50 |
public function EventUserRegister($user_id)
|
51 |
{
|
52 |
$user = get_userdata($user_id);
|
65 |
),
|
66 |
), true);
|
67 |
}
|
68 |
+
|
69 |
public function EventUserRoleChanged($user_id, $role, $oldRoles)
|
70 |
{
|
71 |
$user = get_userdata($user_id);
|
131 |
));
|
132 |
}
|
133 |
}
|
134 |
+
|
135 |
if ($this->IsMultisite()) {
|
136 |
$username = $user->user_login;
|
137 |
$enabled = isset($_REQUEST['super_admin']);
|
138 |
+
|
139 |
if ($user_id != get_current_user_id()) {
|
140 |
// super admin enabled
|
141 |
if ($enabled && !in_array($username, $this->old_superadmins)) {
|
152 |
'TargetUsername' => $user->user_login,
|
153 |
));
|
154 |
}
|
155 |
+
|
156 |
}
|
157 |
}
|
158 |
}
|
159 |
+
|
160 |
public function EventUserDeleted($user_id)
|
161 |
{
|
162 |
$user = get_userdata($user_id);
|
173 |
), array($this, 'MustNotContainCreateUser'));
|
174 |
}
|
175 |
|
176 |
+
public function EventOpenProfile( $user ) {
|
177 |
+
if ( ! empty( $user ) ) {
|
|
|
178 |
$current_user = wp_get_current_user();
|
179 |
+
$updated = ( isset( $_GET['updated'] ) ) ? true : false;
|
180 |
+
if ( ! empty( $current_user ) && ( $user->ID !== $current_user->ID ) && empty( $updated ) ) {
|
181 |
+
$this->plugin->alerts->Trigger( 4014, array(
|
182 |
'UserChanger' => $current_user->user_login,
|
183 |
+
'TargetUsername' => $user->user_login,
|
184 |
+
) );
|
185 |
}
|
186 |
}
|
187 |
}
|
188 |
+
|
189 |
public function MustNotContainCreateUser(WSAL_AlertManager $mgr)
|
190 |
{
|
191 |
return !$mgr->WillTrigger(4012);
|
192 |
}
|
193 |
+
|
194 |
public function MustNotContainUserChanges(WSAL_AlertManager $mgr)
|
195 |
{
|
196 |
return !( $mgr->WillOrHasTriggered(4010)
|
classes/Sensors/Widgets.php
CHANGED
@@ -1,31 +1,48 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
|
|
|
|
7 |
add_action('admin_init', array($this, 'EventWidgetMove'));
|
8 |
add_action('admin_init', array($this, 'EventWidgetPostMove'));
|
9 |
}
|
10 |
add_action('sidebar_admin_setup', array($this, 'EventWidgetActivity'));
|
11 |
}
|
12 |
-
|
13 |
-
protected $_WidgetMoveData = null;
|
14 |
|
15 |
-
|
16 |
-
|
17 |
-
|
|
|
|
|
|
|
|
|
18 |
$crtSidebars = $_POST['sidebars'];
|
19 |
$sidebars = array();
|
20 |
-
foreach (
|
21 |
-
{
|
22 |
$sb = array();
|
23 |
-
if (
|
24 |
-
{
|
25 |
$val = explode(',', $val);
|
26 |
-
foreach (
|
27 |
-
|
28 |
-
|
|
|
29 |
$sb[$k] = substr($v, strpos($v, '_') + 1);
|
30 |
}
|
31 |
}
|
@@ -34,20 +51,14 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
34 |
$crtSidebars = $sidebars;
|
35 |
$dbSidebars = get_option('sidebars_widgets');
|
36 |
$wName = $fromSidebar = $toSidebar = '';
|
37 |
-
foreach($crtSidebars as $sidebarName => $values)
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
foreach($values as $widgetName)
|
42 |
-
{
|
43 |
-
if(! in_array($widgetName, $dbSidebars[$sidebarName]))
|
44 |
-
{
|
45 |
$toSidebar = $sidebarName;
|
46 |
$wName = $widgetName;
|
47 |
-
foreach($dbSidebars as $name => $v)
|
48 |
-
|
49 |
-
if(is_array($v) && !empty($v) && in_array($widgetName, $v))
|
50 |
-
{
|
51 |
$fromSidebar = $name;
|
52 |
continue;
|
53 |
}
|
@@ -57,9 +68,11 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
57 |
}
|
58 |
}
|
59 |
|
60 |
-
if (empty($wName) || empty($fromSidebar) || empty($toSidebar))
|
|
|
|
|
61 |
|
62 |
-
if(preg_match('/^sidebar-/', $fromSidebar) || preg_match('/^sidebar-/', $toSidebar)){
|
63 |
// This option will hold the data needed to trigger the event 2045
|
64 |
// as at this moment the $wp_registered_sidebars variable is not yet populated
|
65 |
// so we cannot retrieve the name for sidebar-1 || sidebar-2
|
@@ -76,21 +89,25 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
76 |
}
|
77 |
}
|
78 |
|
79 |
-
|
80 |
-
|
81 |
-
|
82 |
-
|
|
|
|
|
|
|
|
|
83 |
if (isset($_REQUEST['sidebars'])) {
|
84 |
// Get the sidebars from $_REQUEST
|
85 |
$requestSidebars = array();
|
86 |
if ($_REQUEST['sidebars']) {
|
87 |
-
foreach($_REQUEST['sidebars'] as $key => &$value){
|
88 |
-
if(!empty($value)){
|
89 |
// build the sidebars array
|
90 |
$value = explode(',', $value);
|
91 |
// Cleanup widgets' name
|
92 |
-
foreach($value as $k => &$widgetName){
|
93 |
-
$widgetName = preg_replace("/^([a-z]+-[0-9]+)+?_/i",'', $widgetName);
|
94 |
}
|
95 |
$requestSidebars[$key] = $value;
|
96 |
}
|
@@ -128,25 +145,28 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
128 |
}
|
129 |
}
|
130 |
}
|
131 |
-
|
132 |
|
133 |
-
if($this->_WidgetMoveData){
|
134 |
$wName = $this->_WidgetMoveData['widget'];
|
135 |
$fromSidebar = $this->_WidgetMoveData['from'];
|
136 |
$toSidebar = $this->_WidgetMoveData['to'];
|
137 |
|
138 |
global $wp_registered_sidebars;
|
139 |
|
140 |
-
if(preg_match('/^sidebar-/', $fromSidebar))
|
141 |
$fromSidebar = isset($wp_registered_sidebars[$fromSidebar])
|
142 |
? $wp_registered_sidebars[$fromSidebar]['name']
|
143 |
: $fromSidebar
|
144 |
;
|
145 |
-
|
|
|
|
|
146 |
$toSidebar = isset($wp_registered_sidebars[$toSidebar])
|
147 |
? $wp_registered_sidebars[$toSidebar]['name']
|
148 |
: $toSidebar
|
149 |
;
|
|
|
150 |
|
151 |
$this->plugin->alerts->Trigger(2045, array(
|
152 |
'WidgetName' => $wName,
|
@@ -156,8 +176,12 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
156 |
}
|
157 |
}
|
158 |
|
159 |
-
|
160 |
-
|
|
|
|
|
|
|
|
|
161 |
return;
|
162 |
}
|
163 |
|
@@ -165,12 +189,11 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
165 |
global $wp_registered_sidebars;
|
166 |
$canCheckSidebar = (empty($wp_registered_sidebars) ? false : true);
|
167 |
|
168 |
-
switch(true){
|
169 |
-
|
170 |
// added widget
|
171 |
case isset($postData['add_new']) && $postData['add_new'] == 'multi':
|
172 |
$sidebar = isset($postData['sidebar']) ? $postData['sidebar'] : null;
|
173 |
-
if($canCheckSidebar && preg_match('/^sidebar-/', $sidebar)){
|
174 |
$sidebar = $wp_registered_sidebars[$sidebar]['name'];
|
175 |
}
|
176 |
$this->plugin->alerts->Trigger(2042, array(
|
@@ -178,11 +201,10 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
178 |
'Sidebar' => $sidebar,
|
179 |
));
|
180 |
break;
|
181 |
-
|
182 |
// deleted widget
|
183 |
case isset($postData['delete_widget']) && intval($postData['delete_widget']) == 1:
|
184 |
$sidebar = isset($postData['sidebar']) ? $postData['sidebar'] : null;
|
185 |
-
if($canCheckSidebar && preg_match('/^sidebar-/'
|
186 |
$sidebar = $wp_registered_sidebars[$sidebar]['name'];
|
187 |
}
|
188 |
$this->plugin->alerts->Trigger(2044, array(
|
@@ -190,16 +212,17 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
190 |
'Sidebar' => $sidebar,
|
191 |
));
|
192 |
break;
|
193 |
-
|
194 |
// modified widget
|
195 |
case isset($postData['id_base']) && !empty($postData['id_base']):
|
196 |
$wId = 0;
|
197 |
-
if(!empty($postData['multi_number'])){
|
198 |
$wId = intval($postData['multi_number']);
|
199 |
-
}elseif(!empty($postData['widget_number'])){
|
200 |
$wId = intval($postData['widget_number']);
|
201 |
}
|
202 |
-
if(empty($wId))
|
|
|
|
|
203 |
|
204 |
$wName = $postData['id_base'];
|
205 |
$sidebar = isset($postData['sidebar']) ? $postData['sidebar'] : null;
|
@@ -207,20 +230,27 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
207 |
? $postData["widget-$wName"][$wId]
|
208 |
: null;
|
209 |
|
210 |
-
if(empty($wData))
|
211 |
-
|
|
|
212 |
// get info from db
|
213 |
$wdbData = get_option("widget_".$wName);
|
214 |
-
if(empty($wdbData[$wId]))
|
|
|
|
|
215 |
|
216 |
// transform 'on' -> 1
|
217 |
-
foreach($wData as $k => $v)
|
|
|
|
|
|
|
|
|
218 |
|
219 |
// compare - checks for any changes inside widgets
|
220 |
$diff = array_diff_assoc($wData, $wdbData[$wId]);
|
221 |
$count = count($diff);
|
222 |
-
if($count > 0){
|
223 |
-
if($canCheckSidebar && preg_match("/^sidebar-/"
|
224 |
$sidebar = $wp_registered_sidebars[$sidebar]['name'];
|
225 |
}
|
226 |
$this->plugin->alerts->Trigger(2043, array(
|
@@ -229,7 +259,6 @@ class WSAL_Sensors_Widgets extends WSAL_AbstractSensor {
|
|
229 |
));
|
230 |
}
|
231 |
break;
|
232 |
-
|
233 |
}
|
234 |
}
|
235 |
-
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Widgets sensor.
|
6 |
+
*
|
7 |
+
* 2042 User added a new widget
|
8 |
+
* 2043 User modified a widget
|
9 |
+
* 2044 User deleted widget
|
10 |
+
* 2045 User moved widget
|
11 |
+
* 2071 User changed widget position
|
12 |
+
*/
|
13 |
+
class WSAL_Sensors_Widgets extends WSAL_AbstractSensor
|
14 |
+
{
|
15 |
+
protected $_WidgetMoveData = null;
|
16 |
|
17 |
+
/**
|
18 |
+
* Listening to events using WP hooks.
|
19 |
+
*/
|
20 |
+
public function HookEvents()
|
21 |
+
{
|
22 |
+
if (current_user_can("edit_theme_options")) {
|
23 |
add_action('admin_init', array($this, 'EventWidgetMove'));
|
24 |
add_action('admin_init', array($this, 'EventWidgetPostMove'));
|
25 |
}
|
26 |
add_action('sidebar_admin_setup', array($this, 'EventWidgetActivity'));
|
27 |
}
|
|
|
|
|
28 |
|
29 |
+
/**
|
30 |
+
* Triggered when a user accesses the admin area.
|
31 |
+
* Moved widget.
|
32 |
+
*/
|
33 |
+
public function EventWidgetMove()
|
34 |
+
{
|
35 |
+
if (isset($_POST) && !empty($_POST['sidebars'])) {
|
36 |
$crtSidebars = $_POST['sidebars'];
|
37 |
$sidebars = array();
|
38 |
+
foreach ($crtSidebars as $key => $val) {
|
|
|
39 |
$sb = array();
|
40 |
+
if (!empty($val)) {
|
|
|
41 |
$val = explode(',', $val);
|
42 |
+
foreach ($val as $k => $v) {
|
43 |
+
if (strpos($v, 'widget-') === false) {
|
44 |
+
continue;
|
45 |
+
}
|
46 |
$sb[$k] = substr($v, strpos($v, '_') + 1);
|
47 |
}
|
48 |
}
|
51 |
$crtSidebars = $sidebars;
|
52 |
$dbSidebars = get_option('sidebars_widgets');
|
53 |
$wName = $fromSidebar = $toSidebar = '';
|
54 |
+
foreach ($crtSidebars as $sidebarName => $values) {
|
55 |
+
if (is_array($values) && ! empty($values) && isset($dbSidebars[$sidebarName])) {
|
56 |
+
foreach ($values as $widgetName) {
|
57 |
+
if (! in_array($widgetName, $dbSidebars[$sidebarName])) {
|
|
|
|
|
|
|
|
|
58 |
$toSidebar = $sidebarName;
|
59 |
$wName = $widgetName;
|
60 |
+
foreach ($dbSidebars as $name => $v) {
|
61 |
+
if (is_array($v) && !empty($v) && in_array($widgetName, $v)) {
|
|
|
|
|
62 |
$fromSidebar = $name;
|
63 |
continue;
|
64 |
}
|
68 |
}
|
69 |
}
|
70 |
|
71 |
+
if (empty($wName) || empty($fromSidebar) || empty($toSidebar)) {
|
72 |
+
return;
|
73 |
+
}
|
74 |
|
75 |
+
if (preg_match('/^sidebar-/', $fromSidebar) || preg_match('/^sidebar-/', $toSidebar)) {
|
76 |
// This option will hold the data needed to trigger the event 2045
|
77 |
// as at this moment the $wp_registered_sidebars variable is not yet populated
|
78 |
// so we cannot retrieve the name for sidebar-1 || sidebar-2
|
89 |
}
|
90 |
}
|
91 |
|
92 |
+
/**
|
93 |
+
* Triggered when a user accesses the admin area.
|
94 |
+
* Changed widget position or moved widget.
|
95 |
+
*/
|
96 |
+
public function EventWidgetPostMove()
|
97 |
+
{
|
98 |
+
// #!-- generates the event 2071
|
99 |
+
if (isset($_REQUEST['action']) && ($_REQUEST['action']=='widgets-order')) {
|
100 |
if (isset($_REQUEST['sidebars'])) {
|
101 |
// Get the sidebars from $_REQUEST
|
102 |
$requestSidebars = array();
|
103 |
if ($_REQUEST['sidebars']) {
|
104 |
+
foreach ($_REQUEST['sidebars'] as $key => &$value) {
|
105 |
+
if (!empty($value)) {
|
106 |
// build the sidebars array
|
107 |
$value = explode(',', $value);
|
108 |
// Cleanup widgets' name
|
109 |
+
foreach ($value as $k => &$widgetName) {
|
110 |
+
$widgetName = preg_replace("/^([a-z]+-[0-9]+)+?_/i", '', $widgetName);
|
111 |
}
|
112 |
$requestSidebars[$key] = $value;
|
113 |
}
|
145 |
}
|
146 |
}
|
147 |
}
|
148 |
+
// #!--
|
149 |
|
150 |
+
if ($this->_WidgetMoveData) {
|
151 |
$wName = $this->_WidgetMoveData['widget'];
|
152 |
$fromSidebar = $this->_WidgetMoveData['from'];
|
153 |
$toSidebar = $this->_WidgetMoveData['to'];
|
154 |
|
155 |
global $wp_registered_sidebars;
|
156 |
|
157 |
+
if (preg_match('/^sidebar-/', $fromSidebar)) {
|
158 |
$fromSidebar = isset($wp_registered_sidebars[$fromSidebar])
|
159 |
? $wp_registered_sidebars[$fromSidebar]['name']
|
160 |
: $fromSidebar
|
161 |
;
|
162 |
+
}
|
163 |
+
|
164 |
+
if (preg_match('/^sidebar-/', $toSidebar)) {
|
165 |
$toSidebar = isset($wp_registered_sidebars[$toSidebar])
|
166 |
? $wp_registered_sidebars[$toSidebar]['name']
|
167 |
: $toSidebar
|
168 |
;
|
169 |
+
}
|
170 |
|
171 |
$this->plugin->alerts->Trigger(2045, array(
|
172 |
'WidgetName' => $wName,
|
176 |
}
|
177 |
}
|
178 |
|
179 |
+
/**
|
180 |
+
* Widgets Activity (added, modified, deleted).
|
181 |
+
*/
|
182 |
+
public function EventWidgetActivity()
|
183 |
+
{
|
184 |
+
if (!isset($_POST) || !isset($_POST['widget-id']) || empty($_POST['widget-id'])) {
|
185 |
return;
|
186 |
}
|
187 |
|
189 |
global $wp_registered_sidebars;
|
190 |
$canCheckSidebar = (empty($wp_registered_sidebars) ? false : true);
|
191 |
|
192 |
+
switch (true) {
|
|
|
193 |
// added widget
|
194 |
case isset($postData['add_new']) && $postData['add_new'] == 'multi':
|
195 |
$sidebar = isset($postData['sidebar']) ? $postData['sidebar'] : null;
|
196 |
+
if ($canCheckSidebar && preg_match('/^sidebar-/', $sidebar)) {
|
197 |
$sidebar = $wp_registered_sidebars[$sidebar]['name'];
|
198 |
}
|
199 |
$this->plugin->alerts->Trigger(2042, array(
|
201 |
'Sidebar' => $sidebar,
|
202 |
));
|
203 |
break;
|
|
|
204 |
// deleted widget
|
205 |
case isset($postData['delete_widget']) && intval($postData['delete_widget']) == 1:
|
206 |
$sidebar = isset($postData['sidebar']) ? $postData['sidebar'] : null;
|
207 |
+
if ($canCheckSidebar && preg_match('/^sidebar-/', $sidebar)) {
|
208 |
$sidebar = $wp_registered_sidebars[$sidebar]['name'];
|
209 |
}
|
210 |
$this->plugin->alerts->Trigger(2044, array(
|
212 |
'Sidebar' => $sidebar,
|
213 |
));
|
214 |
break;
|
|
|
215 |
// modified widget
|
216 |
case isset($postData['id_base']) && !empty($postData['id_base']):
|
217 |
$wId = 0;
|
218 |
+
if (!empty($postData['multi_number'])) {
|
219 |
$wId = intval($postData['multi_number']);
|
220 |
+
} elseif (!empty($postData['widget_number'])) {
|
221 |
$wId = intval($postData['widget_number']);
|
222 |
}
|
223 |
+
if (empty($wId)) {
|
224 |
+
return;
|
225 |
+
}
|
226 |
|
227 |
$wName = $postData['id_base'];
|
228 |
$sidebar = isset($postData['sidebar']) ? $postData['sidebar'] : null;
|
230 |
? $postData["widget-$wName"][$wId]
|
231 |
: null;
|
232 |
|
233 |
+
if (empty($wData)) {
|
234 |
+
return;
|
235 |
+
}
|
236 |
// get info from db
|
237 |
$wdbData = get_option("widget_".$wName);
|
238 |
+
if (empty($wdbData[$wId])) {
|
239 |
+
return;
|
240 |
+
}
|
241 |
|
242 |
// transform 'on' -> 1
|
243 |
+
foreach ($wData as $k => $v) {
|
244 |
+
if ($v == 'on') {
|
245 |
+
$wData[$k] = 1;
|
246 |
+
}
|
247 |
+
}
|
248 |
|
249 |
// compare - checks for any changes inside widgets
|
250 |
$diff = array_diff_assoc($wData, $wdbData[$wId]);
|
251 |
$count = count($diff);
|
252 |
+
if ($count > 0) {
|
253 |
+
if ($canCheckSidebar && preg_match("/^sidebar-/", $sidebar)) {
|
254 |
$sidebar = $wp_registered_sidebars[$sidebar]['name'];
|
255 |
}
|
256 |
$this->plugin->alerts->Trigger(2043, array(
|
259 |
));
|
260 |
}
|
261 |
break;
|
|
|
262 |
}
|
263 |
}
|
264 |
+
}
|
classes/Sensors/WooCommerce.php
CHANGED
@@ -1,6 +1,43 @@
|
|
1 |
<?php
|
2 |
/**
|
3 |
-
*
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
4 |
*/
|
5 |
class WSAL_Sensors_WooCommerce extends WSAL_AbstractSensor
|
6 |
{
|
@@ -12,6 +49,9 @@ class WSAL_Sensors_WooCommerce extends WSAL_AbstractSensor
|
|
12 |
protected $_OldFileNames = array();
|
13 |
protected $_OldFileUrls = array();
|
14 |
|
|
|
|
|
|
|
15 |
public function HookEvents()
|
16 |
{
|
17 |
if (current_user_can("edit_posts")) {
|
@@ -26,6 +66,9 @@ class WSAL_Sensors_WooCommerce extends WSAL_AbstractSensor
|
|
26 |
// add_action('edit_product_cat', array($this, 'EventCategoryChanged'), 10, 1);
|
27 |
}
|
28 |
|
|
|
|
|
|
|
29 |
public function EventAdminInit()
|
30 |
{
|
31 |
// load old data, if applicable
|
@@ -33,6 +76,10 @@ class WSAL_Sensors_WooCommerce extends WSAL_AbstractSensor
|
|
33 |
$this->CheckSettingsChange();
|
34 |
}
|
35 |
|
|
|
|
|
|
|
|
|
36 |
protected function RetrieveOldData()
|
37 |
{
|
38 |
if (isset($_POST) && isset($_POST['post_ID'])
|
@@ -783,6 +830,10 @@ class WSAL_Sensors_WooCommerce extends WSAL_AbstractSensor
|
|
783 |
return $fn('woocommerce_' . $option_name);
|
784 |
}
|
785 |
|
|
|
|
|
|
|
|
|
786 |
private function CheckWooCommerce($post)
|
787 |
{
|
788 |
switch ($post->post_type) {
|
@@ -793,6 +844,11 @@ class WSAL_Sensors_WooCommerce extends WSAL_AbstractSensor
|
|
793 |
}
|
794 |
}
|
795 |
|
|
|
|
|
|
|
|
|
|
|
796 |
private function GetEditorLink($post)
|
797 |
{
|
798 |
$name = 'EditorLinkProduct';
|
1 |
<?php
|
2 |
/**
|
3 |
+
* @package Wsal
|
4 |
+
* @subpackage Sensors
|
5 |
+
* Support for WooCommerce Plugin.
|
6 |
+
*
|
7 |
+
* 9000 User created a new product
|
8 |
+
* 9001 User published a product
|
9 |
+
* 9002 User created a new product category
|
10 |
+
* 9003 User changed the category of a product
|
11 |
+
* 9004 User modified the short description of a product
|
12 |
+
* 9005 User modified the text of a product
|
13 |
+
* 9006 User changed the URL of a product
|
14 |
+
* 9007 User changed the Product Data of a product
|
15 |
+
* 9008 User changed the date of a product
|
16 |
+
* 9009 User changed the visibility of a product
|
17 |
+
* 9010 User modified the published product
|
18 |
+
* 9011 User modified the draft product
|
19 |
+
* 9012 User moved a product to trash
|
20 |
+
* 9013 User permanently deleted a product
|
21 |
+
* 9014 User restored a product from the trash
|
22 |
+
* 9015 User changed status of a product
|
23 |
+
* 9016 User changed type of a price
|
24 |
+
* 9017 User changed the SKU of a product
|
25 |
+
* 9018 User changed the stock status of a product
|
26 |
+
* 9019 User changed the stock quantity
|
27 |
+
* 9020 User set a product type
|
28 |
+
* 9021 User changed the weight of a product
|
29 |
+
* 9022 User changed the dimensions of a product
|
30 |
+
* 9023 User added the Downloadable File to a product
|
31 |
+
* 9024 User Removed the Downloadable File from a product
|
32 |
+
* 9025 User changed the name of a Downloadable File in a product
|
33 |
+
* 9026 User changed the URL of the Downloadable File in a product
|
34 |
+
* 9027 User changed the Weight Unit
|
35 |
+
* 9028 User changed the Dimensions Unit
|
36 |
+
* 9029 User changed the Base Location
|
37 |
+
* 9030 User Enabled/Disabled taxes
|
38 |
+
* 9031 User changed the currency
|
39 |
+
* 9032 User Enabled/Disabled the use of coupons during checkout
|
40 |
+
* 9033 User Enabled/Disabled guest checkout
|
41 |
*/
|
42 |
class WSAL_Sensors_WooCommerce extends WSAL_AbstractSensor
|
43 |
{
|
49 |
protected $_OldFileNames = array();
|
50 |
protected $_OldFileUrls = array();
|
51 |
|
52 |
+
/**
|
53 |
+
* Listening to events using WP hooks.
|
54 |
+
*/
|
55 |
public function HookEvents()
|
56 |
{
|
57 |
if (current_user_can("edit_posts")) {
|
66 |
// add_action('edit_product_cat', array($this, 'EventCategoryChanged'), 10, 1);
|
67 |
}
|
68 |
|
69 |
+
/**
|
70 |
+
* Triggered when a user accesses the admin area.
|
71 |
+
*/
|
72 |
public function EventAdminInit()
|
73 |
{
|
74 |
// load old data, if applicable
|
76 |
$this->CheckSettingsChange();
|
77 |
}
|
78 |
|
79 |
+
/**
|
80 |
+
* Retrieve Old data.
|
81 |
+
* @global mixed $_POST post data
|
82 |
+
*/
|
83 |
protected function RetrieveOldData()
|
84 |
{
|
85 |
if (isset($_POST) && isset($_POST['post_ID'])
|
830 |
return $fn('woocommerce_' . $option_name);
|
831 |
}
|
832 |
|
833 |
+
/**
|
834 |
+
* Check post type.
|
835 |
+
* @param stdClass $post post
|
836 |
+
*/
|
837 |
private function CheckWooCommerce($post)
|
838 |
{
|
839 |
switch ($post->post_type) {
|
844 |
}
|
845 |
}
|
846 |
|
847 |
+
/**
|
848 |
+
* Get editor link.
|
849 |
+
* @param stdClass $post the post
|
850 |
+
* @return array $aLink name and value link
|
851 |
+
*/
|
852 |
private function GetEditorLink($post)
|
853 |
{
|
854 |
$name = 'EditorLinkProduct';
|
classes/Settings.php
CHANGED
@@ -1,13 +1,16 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
/**
|
4 |
* @var WpSecurityAuditLog
|
5 |
*/
|
6 |
protected $_plugin;
|
7 |
-
|
8 |
-
$this->_plugin = $plugin;
|
9 |
-
}
|
10 |
-
|
11 |
// <editor-fold desc="Developer Options">
|
12 |
const OPT_DEV_DATA_INSPECTOR = 'd';
|
13 |
const OPT_DEV_PHP_ERRORS = 'p';
|
@@ -17,18 +20,57 @@ class WSAL_Settings {
|
|
17 |
const ERROR_CODE_INVALID_IP = 901;
|
18 |
|
19 |
protected $_devoption = null;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
20 |
/**
|
21 |
* @return array Array of developer options to be enabled by default.
|
22 |
*/
|
23 |
-
public function GetDefaultDevOptions()
|
|
|
24 |
return array();
|
25 |
}
|
|
|
26 |
/**
|
27 |
* Returns whether a developer option is enabled or not.
|
28 |
* @param string $option See self::OPT_DEV_* constants.
|
29 |
* @return boolean If option is enabled or not.
|
30 |
*/
|
31 |
-
public function IsDevOptionEnabled($option)
|
|
|
32 |
if (is_null($this->_devoption)) {
|
33 |
$this->_devoption = $this->_plugin->GetGlobalOption(
|
34 |
'dev-options',
|
@@ -38,18 +80,22 @@ class WSAL_Settings {
|
|
38 |
}
|
39 |
return in_array($option, $this->_devoption);
|
40 |
}
|
|
|
41 |
/**
|
42 |
* @return boolean Whether any developer option has been enabled or not.
|
43 |
*/
|
44 |
-
public function IsAnyDevOptionEnabled()
|
|
|
45 |
return !!$this->_plugin->GetGlobalOption('dev-options', null);
|
46 |
}
|
|
|
47 |
/**
|
48 |
* Sets whether a developer option is enabled or not.
|
49 |
* @param string $option See self::OPT_DEV_* constants.
|
50 |
* @param boolean $enabled If option should be enabled or not.
|
51 |
*/
|
52 |
-
public function SetDevOptionEnabled($option, $enabled)
|
|
|
53 |
// make sure options have been loaded
|
54 |
$this->IsDevOptionEnabled('');
|
55 |
// remove option if it exists
|
@@ -66,88 +112,112 @@ class WSAL_Settings {
|
|
66 |
implode(',', $this->_devoption)
|
67 |
);
|
68 |
}
|
|
|
69 |
/**
|
70 |
* Remove all enabled developer options.
|
71 |
*/
|
72 |
-
public function ClearDevOptions()
|
|
|
73 |
$this->_devoption = array();
|
74 |
$this->_plugin->SetGlobalOption('dev-options', '');
|
75 |
}
|
|
|
76 |
/**
|
77 |
* @return boolean Whether to enable data inspector or not.
|
78 |
*/
|
79 |
-
public function IsDataInspectorEnabled()
|
|
|
80 |
return $this->IsDevOptionEnabled(self::OPT_DEV_DATA_INSPECTOR);
|
81 |
}
|
|
|
82 |
/**
|
83 |
* @return boolean Whether to PHP error logging or not.
|
84 |
*/
|
85 |
-
public function IsPhpErrorLoggingEnabled()
|
|
|
86 |
return $this->IsDevOptionEnabled(self::OPT_DEV_PHP_ERRORS);
|
87 |
}
|
|
|
88 |
/**
|
89 |
* @return boolean Whether to log requests to file or not.
|
90 |
*/
|
91 |
-
public function IsRequestLoggingEnabled()
|
|
|
92 |
return $this->IsDevOptionEnabled(self::OPT_DEV_REQUEST_LOG);
|
93 |
}
|
|
|
94 |
/**
|
95 |
* @return boolean Whether to store debug backtrace for PHP alerts or not.
|
96 |
*/
|
97 |
-
public function IsBacktraceLoggingEnabled()
|
|
|
98 |
return $this->IsDevOptionEnabled(self::OPT_DEV_BACKTRACE_LOG);
|
99 |
}
|
100 |
-
|
101 |
// </editor-fold>
|
|
|
102 |
/**
|
103 |
* @return boolean Whether dashboard widgets are enabled or not.
|
104 |
*/
|
105 |
-
public function IsWidgetsEnabled()
|
|
|
106 |
return !$this->_plugin->GetGlobalOption('disable-widgets');
|
107 |
}
|
|
|
108 |
/**
|
109 |
* @param boolean $newvalue Whether dashboard widgets are enabled or not.
|
110 |
*/
|
111 |
-
public function SetWidgetsEnabled($newvalue)
|
|
|
112 |
$this->_plugin->SetGlobalOption('disable-widgets', !$newvalue);
|
113 |
}
|
|
|
114 |
/**
|
115 |
* @return boolean Whether alerts in audit log view refresh automatically or not.
|
116 |
*/
|
117 |
-
public function IsRefreshAlertsEnabled()
|
|
|
118 |
return !$this->_plugin->GetGlobalOption('disable-refresh');
|
119 |
}
|
|
|
120 |
/**
|
121 |
* @param boolean $newvalue Whether alerts in audit log view refresh automatically or not.
|
122 |
*/
|
123 |
-
public function SetRefreshAlertsEnabled($newvalue)
|
|
|
124 |
$this->_plugin->SetGlobalOption('disable-refresh', !$newvalue);
|
125 |
}
|
|
|
126 |
/**
|
127 |
* @return int Maximum number of alerts to show in dashboard widget.
|
128 |
*/
|
129 |
-
public function GetDashboardWidgetMaxAlerts()
|
|
|
130 |
return 5;
|
131 |
}
|
132 |
-
|
133 |
// <editor-fold desc="Pruning Settings">
|
134 |
/**
|
135 |
* @return int The maximum number of alerts allowable.
|
136 |
*/
|
137 |
-
public function GetMaxAllowedAlerts()
|
|
|
138 |
return 5000;
|
139 |
}
|
|
|
140 |
/**
|
141 |
* @return string The default pruning date.
|
142 |
*/
|
143 |
-
public function GetDefaultPruningDate()
|
|
|
144 |
return '1 month';
|
145 |
}
|
146 |
-
|
147 |
/**
|
148 |
* @return string The current pruning date.
|
149 |
*/
|
150 |
-
public function GetPruningDate()
|
|
|
151 |
if (!$this->_pruning) {
|
152 |
$this->_pruning = $this->_plugin->GetGlobalOption('pruning-date');
|
153 |
if (!strtotime($this->_pruning)) {
|
@@ -156,65 +226,85 @@ class WSAL_Settings {
|
|
156 |
}
|
157 |
return $this->_pruning;
|
158 |
}
|
|
|
159 |
/**
|
160 |
* @param string $newvalue The new pruning date.
|
161 |
*/
|
162 |
-
public function SetPruningDate($newvalue)
|
|
|
163 |
if (strtotime($newvalue)) {
|
164 |
$this->_plugin->SetGlobalOption('pruning-date', $newvalue);
|
165 |
$this->_pruning = $newvalue;
|
166 |
}
|
167 |
}
|
|
|
168 |
/**
|
169 |
* @return integer Maximum number of alerts to keep.
|
170 |
*/
|
171 |
-
public function GetPruningLimit()
|
|
|
172 |
$val = (int)$this->_plugin->GetGlobalOption('pruning-limit');
|
173 |
return $val ? $val : $this->GetMaxAllowedAlerts();
|
174 |
}
|
|
|
175 |
/**
|
176 |
* @param integer $newvalue The new maximum number of alerts.
|
177 |
*/
|
178 |
-
public function SetPruningLimit($newvalue)
|
|
|
179 |
$newvalue = max(/*min(*/(int)$newvalue/*, $this->GetMaxAllowedAlerts())*/, 1);
|
180 |
$this->_plugin->SetGlobalOption('pruning-limit', $newvalue);
|
181 |
}
|
182 |
-
|
|
|
|
|
183 |
$this->_plugin->SetGlobalOption('pruning-date-e', $enabled);
|
184 |
}
|
185 |
-
|
|
|
|
|
186 |
$this->_plugin->SetGlobalOption('pruning-limit-e', $enabled);
|
187 |
}
|
|
|
188 |
public function IsPruningDateEnabled(){
|
189 |
return $this->_plugin->GetGlobalOption('pruning-date-e');
|
190 |
}
|
191 |
-
|
|
|
|
|
192 |
return $this->_plugin->GetGlobalOption('pruning-limit-e');
|
193 |
}
|
194 |
|
195 |
-
public function IsRestrictAdmins()
|
|
|
196 |
return $this->_plugin->GetGlobalOption('restrict-admins', false);
|
197 |
}
|
|
|
198 |
/**
|
199 |
* @deprecated Sandbox functionality is now in an external plugin.
|
200 |
*/
|
201 |
-
public function IsSandboxPageEnabled()
|
|
|
202 |
$plugins = $this->_plugin->licensing->plugins();
|
203 |
return isset($plugins['wsal-sandbox-extensionphp']);
|
204 |
}
|
205 |
-
|
|
|
|
|
206 |
$this->_plugin->SetGlobalOption('restrict-admins', (bool)$enable);
|
207 |
}
|
208 |
-
|
209 |
// </editor-fold>
|
210 |
-
|
211 |
-
|
212 |
return array(0000, 0001, 0002, 0003, 0004, 0005);
|
213 |
}
|
|
|
214 |
/**
|
215 |
* @return array IDs of disabled alerts.
|
216 |
*/
|
217 |
-
public function GetDisabledAlerts()
|
|
|
218 |
if (!$this->_disabled) {
|
219 |
$this->_disabled = implode(',', $this->GetDefaultDisabledAlerts());
|
220 |
$this->_disabled = $this->_plugin->GetGlobalOption('disabled-alerts', $this->_disabled);
|
@@ -223,94 +313,118 @@ class WSAL_Settings {
|
|
223 |
}
|
224 |
return $this->_disabled;
|
225 |
}
|
|
|
226 |
/**
|
227 |
* @param array $types IDs alerts to disable.
|
228 |
*/
|
229 |
-
public function SetDisabledAlerts($types)
|
|
|
230 |
$this->_disabled = array_unique(array_map('intval', $types));
|
231 |
$this->_plugin->SetGlobalOption('disabled-alerts', implode(',', $this->_disabled));
|
232 |
}
|
233 |
-
|
|
|
|
|
234 |
return $this->_plugin->GetGlobalOption('hide-plugin');
|
235 |
}
|
236 |
-
|
|
|
|
|
237 |
return $this->_plugin->SetGlobalOption('hide-plugin', $enabled);
|
238 |
}
|
239 |
|
240 |
/**
|
241 |
* Checking if Logging is enabled.
|
242 |
*/
|
243 |
-
public function IsLoggingDisabled()
|
|
|
244 |
return $this->_plugin->GetGlobalOption('disable-logging');
|
245 |
}
|
246 |
|
247 |
-
public function SetLoggingDisabled($disabled)
|
|
|
248 |
return $this->_plugin->SetGlobalOption('disable-logging', $disabled);
|
249 |
}
|
250 |
-
|
251 |
/**
|
252 |
* Checking if the data will be removed.
|
253 |
*/
|
254 |
-
public function IsDeleteData()
|
|
|
255 |
return $this->_plugin->GetGlobalOption('delete-data');
|
256 |
}
|
257 |
|
258 |
-
public function SetDeleteData($enabled)
|
|
|
259 |
return $this->_plugin->SetGlobalOption('delete-data', $enabled);
|
260 |
}
|
261 |
|
262 |
// <editor-fold desc="Access Control">
|
263 |
-
|
264 |
-
|
265 |
-
|
266 |
$this->_viewers = $usersOrRoles;
|
267 |
$this->_plugin->SetGlobalOption('plugin-viewers', implode(',', $this->_viewers));
|
268 |
}
|
269 |
-
|
|
|
|
|
270 |
if (is_null($this->_viewers)) {
|
271 |
$this->_viewers = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('plugin-viewers'))));
|
272 |
}
|
273 |
return $this->_viewers;
|
274 |
}
|
275 |
-
|
276 |
-
public function SetAllowedPluginEditors($usersOrRoles)
|
|
|
277 |
$this->_editors = $usersOrRoles;
|
278 |
$this->_plugin->SetGlobalOption('plugin-editors', implode(',', $this->_editors));
|
279 |
}
|
280 |
-
|
|
|
|
|
281 |
if (is_null($this->_editors)) {
|
282 |
$this->_editors = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('plugin-editors'))));
|
283 |
}
|
284 |
return $this->_editors;
|
285 |
}
|
286 |
-
|
287 |
-
public function SetViewPerPage($newvalue)
|
|
|
288 |
$this->_perpage = max($newvalue, 1);
|
289 |
$this->_plugin->SetGlobalOption('items-per-page', $this->_perpage);
|
290 |
}
|
291 |
-
|
|
|
|
|
292 |
if (is_null($this->_perpage)) {
|
293 |
$this->_perpage = (int)$this->_plugin->GetGlobalOption('items-per-page', 10);
|
294 |
}
|
295 |
return $this->_perpage;
|
296 |
}
|
|
|
297 |
/**
|
298 |
* @param string $action Type of action, either 'view' or 'edit'.
|
299 |
* @return boolean If user has access or not.
|
300 |
*/
|
301 |
-
public function CurrentUserCan($action)
|
|
|
302 |
return $this->UserCan(wp_get_current_user(), $action);
|
303 |
}
|
|
|
304 |
/**
|
305 |
* @return string[] List of superadmin usernames.
|
306 |
*/
|
307 |
-
protected function GetSuperAdmins()
|
|
|
308 |
return $this->_plugin->IsMultisite() ? get_super_admins() : array();
|
309 |
}
|
|
|
310 |
/**
|
311 |
* @return string[] List of admin usernames.
|
312 |
*/
|
313 |
-
protected function GetAdmins()
|
|
|
314 |
if ($this->_plugin->IsMultisite()) {
|
315 |
// see: https://gist.github.com/1508426/65785a15b8638d43a9905effb59e4d97319ef8f8
|
316 |
global $wpdb;
|
@@ -324,16 +438,20 @@ class WSAL_Settings {
|
|
324 |
} else {
|
325 |
$result = array();
|
326 |
$query = 'role=administrator&fields[]=user_login';
|
327 |
-
foreach (get_users($query) as $user)
|
|
|
|
|
328 |
return $result;
|
329 |
}
|
330 |
}
|
|
|
331 |
/**
|
332 |
* Returns access tokens for a particular action.
|
333 |
* @param string $action Type of action.
|
334 |
* @return string[] List of tokens (usernames, roles etc).
|
335 |
*/
|
336 |
-
public function GetAccessTokens($action)
|
|
|
337 |
$allowed = array();
|
338 |
switch ($action) {
|
339 |
case 'view':
|
@@ -362,12 +480,14 @@ class WSAL_Settings {
|
|
362 |
}
|
363 |
return array_unique($allowed);
|
364 |
}
|
|
|
365 |
/**
|
366 |
* @param integer|WP_user $user User object to check.
|
367 |
* @param string $action Type of action, either 'view' or 'edit'.
|
368 |
* @return boolean If user has access or not.
|
369 |
*/
|
370 |
-
public function UserCan($user, $action)
|
|
|
371 |
if (is_int($user)) {
|
372 |
$user = get_userdata($user);
|
373 |
}
|
@@ -380,84 +500,125 @@ class WSAL_Settings {
|
|
380 |
}
|
381 |
return false;
|
382 |
}
|
383 |
-
|
384 |
-
|
385 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
386 |
return $baseRoles;
|
387 |
}
|
388 |
|
389 |
-
public function IsLoginSuperAdmin($username)
|
|
|
390 |
$userId = username_exists($username);
|
391 |
-
if (function_exists('is_super_admin') && is_super_admin($userId)
|
392 |
-
|
|
|
|
|
|
|
393 |
}
|
394 |
-
|
395 |
// </editor-fold>
|
396 |
-
|
397 |
// <editor-fold desc="Licensing">
|
398 |
-
public function GetLicenses()
|
|
|
399 |
return $this->_plugin->GetGlobalOption('licenses');
|
400 |
}
|
401 |
-
|
|
|
|
|
402 |
$data = $this->GetLicenses();
|
403 |
$name = sanitize_key(basename($name));
|
404 |
return isset($data[$name]) ? $data[$name] : array();
|
405 |
}
|
406 |
-
|
|
|
|
|
407 |
$this->_plugin->SetGlobalOption('licenses', $data);
|
408 |
}
|
409 |
-
|
|
|
|
|
410 |
$data = $this->GetLicense($name);
|
411 |
return isset($data['key']) ? $data['key'] : '';
|
412 |
}
|
|
|
413 |
public function GetLicenseStatus($name){
|
414 |
$data = $this->GetLicense($name);
|
415 |
return isset($data['sts']) ? $data['sts'] : '';
|
416 |
}
|
417 |
-
|
|
|
|
|
418 |
$data = $this->GetLicense($name);
|
419 |
return isset($data['err']) ? $data['err'] : '';
|
420 |
}
|
421 |
-
|
|
|
|
|
422 |
$data = $this->GetLicenses();
|
423 |
-
if (!isset($data[$name]))
|
|
|
|
|
424 |
$data[$name]['key'] = $key;
|
425 |
$this->SetLicenses($data);
|
426 |
}
|
427 |
-
|
|
|
|
|
428 |
$data = $this->GetLicenses();
|
429 |
-
if (!isset($data[$name]))
|
|
|
|
|
430 |
$data[$name]['sts'] = $status;
|
431 |
$this->SetLicenses($data);
|
432 |
}
|
433 |
-
|
|
|
|
|
434 |
$data = $this->GetLicenses();
|
435 |
-
if (!isset($data[$name]))
|
|
|
|
|
436 |
$data[$name]['err'] = $errors;
|
437 |
$this->SetLicenses($data);
|
438 |
}
|
439 |
-
|
|
|
|
|
440 |
$this->SetLicenses(array());
|
441 |
}
|
442 |
-
|
443 |
// </editor-fold>
|
444 |
// <editor-fold desc="Client IP Retrieval">
|
445 |
-
|
446 |
-
public function IsMainIPFromProxy()
|
|
|
447 |
return $this->_plugin->GetGlobalOption('use-proxy-ip');
|
448 |
}
|
449 |
-
|
|
|
|
|
450 |
return $this->_plugin->SetGlobalOption('use-proxy-ip', $enabled);
|
451 |
}
|
452 |
-
|
453 |
-
public function IsInternalIPsFiltered()
|
|
|
454 |
return $this->_plugin->GetGlobalOption('filter-internal-ip');
|
455 |
}
|
456 |
-
|
|
|
|
|
457 |
return $this->_plugin->SetGlobalOption('filter-internal-ip', $enabled);
|
458 |
}
|
459 |
-
|
460 |
-
public function GetMainClientIP()
|
|
|
461 |
$result = null;
|
462 |
if ($this->IsMainIPFromProxy()) {
|
463 |
// TODO the algorithm below just gets the first IP in the list...we might want to make this more intelligent somehow
|
@@ -472,8 +633,9 @@ class WSAL_Settings {
|
|
472 |
}
|
473 |
return $result;
|
474 |
}
|
475 |
-
|
476 |
-
public function GetClientIPs()
|
|
|
477 |
$ips = array();
|
478 |
foreach (array('HTTP_CLIENT_IP', 'HTTP_X_FORWARDED_FOR', 'HTTP_X_FORWARDED', 'HTTP_X_CLUSTER_CLIENT_IP', 'HTTP_FORWARDED_FOR', 'HTTP_FORWARDED', 'REMOTE_ADDR') as $key) {
|
479 |
if (isset($_SERVER[$key])) {
|
@@ -487,8 +649,9 @@ class WSAL_Settings {
|
|
487 |
}
|
488 |
return $ips;
|
489 |
}
|
490 |
-
|
491 |
-
protected function NormalizeIP($ip)
|
|
|
492 |
$ip = trim($ip);
|
493 |
if (strpos($ip, ':') !== false && substr_count($ip, '.') == 3 && strpos($ip, '[') === false) {
|
494 |
// IPv4 with a port (eg: 11.22.33.44:80)
|
@@ -501,16 +664,23 @@ class WSAL_Settings {
|
|
501 |
}
|
502 |
return $ip;
|
503 |
}
|
504 |
-
|
505 |
-
protected function ValidateIP($ip)
|
|
|
506 |
$opts = FILTER_FLAG_IPV4 | FILTER_FLAG_IPV6;
|
507 |
-
if ($this->IsInternalIPsFiltered())
|
|
|
|
|
508 |
$filteredIP = filter_var($ip, FILTER_VALIDATE_IP, $opts);
|
509 |
if (!$filteredIP || empty($filteredIP)) {
|
510 |
//Regex IPV4
|
511 |
-
if (preg_match("/^(([1-9]?[0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]).){3}([1-9]?[0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])$/", $ip))
|
|
|
|
|
512 |
//Regex IPV6
|
513 |
-
elseif (preg_match("/^\s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:)))(%.+)?\s*$/", $ip))
|
|
|
|
|
514 |
if (!$this->IsLoggingDisabled) {
|
515 |
error_log("Invalid IP in ValidateIP function: ".$ip);
|
516 |
}
|
@@ -523,12 +693,12 @@ class WSAL_Settings {
|
|
523 |
/**
|
524 |
* Users excluded from monitoring
|
525 |
*/
|
526 |
-
protected $_excluded_users = array();
|
527 |
public function SetExcludedMonitoringUsers($users)
|
528 |
{
|
529 |
$this->_excluded_users = $users;
|
530 |
$this->_plugin->SetGlobalOption('excluded-users', esc_html(implode(',', $this->_excluded_users)));
|
531 |
}
|
|
|
532 |
public function GetExcludedMonitoringUsers()
|
533 |
{
|
534 |
if (empty($this->_excluded_users)) {
|
@@ -540,12 +710,14 @@ class WSAL_Settings {
|
|
540 |
/**
|
541 |
* Roles excluded from monitoring
|
542 |
*/
|
543 |
-
|
544 |
-
|
545 |
$this->_excluded_roles = $roles;
|
546 |
$this->_plugin->SetGlobalOption('excluded-roles', esc_html(implode(',', $this->_excluded_roles)));
|
547 |
}
|
548 |
-
|
|
|
|
|
549 |
if (empty($this->_excluded_roles)) {
|
550 |
$this->_excluded_roles = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('excluded-roles'))));
|
551 |
}
|
@@ -555,12 +727,14 @@ class WSAL_Settings {
|
|
555 |
/**
|
556 |
* Custom fields excluded from monitoring
|
557 |
*/
|
558 |
-
|
559 |
-
|
560 |
$this->_excluded_custom = $custom;
|
561 |
$this->_plugin->SetGlobalOption('excluded-custom', esc_html(implode(',', $this->_excluded_custom)));
|
562 |
}
|
563 |
-
|
|
|
|
|
564 |
if (empty($this->_excluded_custom)) {
|
565 |
$this->_excluded_custom = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('excluded-custom'))));
|
566 |
asort($this->_excluded_custom);
|
@@ -571,12 +745,14 @@ class WSAL_Settings {
|
|
571 |
/**
|
572 |
* IP excluded from monitoring
|
573 |
*/
|
574 |
-
|
575 |
-
|
576 |
$this->_excluded_ip = $ip;
|
577 |
$this->_plugin->SetGlobalOption('excluded-ip', esc_html(implode(',', $this->_excluded_ip)));
|
578 |
}
|
579 |
-
|
|
|
|
|
580 |
if (empty($this->_excluded_ip)) {
|
581 |
$this->_excluded_ip = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('excluded-ip'))));
|
582 |
}
|
@@ -586,7 +762,8 @@ class WSAL_Settings {
|
|
586 |
/**
|
587 |
* Datetime used in the Alerts.
|
588 |
*/
|
589 |
-
public function GetDatetimeFormat($lineBreak = true)
|
|
|
590 |
if ($lineBreak) {
|
591 |
$date_time_format = $this->GetDateFormat() . '<\b\r>' . $this->GetTimeFormat();
|
592 |
} else {
|
@@ -605,7 +782,8 @@ class WSAL_Settings {
|
|
605 |
/**
|
606 |
* Date Format from WordPress General Settings.
|
607 |
*/
|
608 |
-
public function GetDateFormat()
|
|
|
609 |
$wp_date_format = get_option('date_format');
|
610 |
$search = array('F', 'M', 'n', 'j', ' ', '/', 'y', 'S', ',', 'l', 'D');
|
611 |
$replace = array('m', 'm', 'm', 'd', '-', '-', 'Y', '', '', '', '');
|
@@ -616,7 +794,8 @@ class WSAL_Settings {
|
|
616 |
/**
|
617 |
* Time Format from WordPress General Settings.
|
618 |
*/
|
619 |
-
public function GetTimeFormat()
|
|
|
620 |
$wp_time_format = get_option('time_format');
|
621 |
$search = array('a', 'A', 'T', ' ');
|
622 |
$replace = array('', '', '', '');
|
@@ -628,23 +807,28 @@ class WSAL_Settings {
|
|
628 |
* Alerts Timestamp
|
629 |
* Server's timezone or WordPress' timezone
|
630 |
*/
|
631 |
-
public function GetTimezone()
|
|
|
632 |
return $this->_plugin->GetGlobalOption('timezone', 0);
|
633 |
}
|
634 |
|
635 |
-
public function SetTimezone($newvalue)
|
|
|
636 |
return $this->_plugin->SetGlobalOption('timezone', $newvalue);
|
637 |
}
|
638 |
|
639 |
-
public function GetAdapterConfig($name_field)
|
|
|
640 |
return $this->_plugin->GetGlobalOption($name_field);
|
641 |
}
|
642 |
|
643 |
-
public function SetAdapterConfig($name_field, $newvalue)
|
|
|
644 |
return $this->_plugin->SetGlobalOption($name_field, trim($newvalue));
|
645 |
}
|
646 |
|
647 |
-
public function GetColumns()
|
|
|
648 |
$columns = array('alert_code' => '1', 'type' => '1', 'date' => '1', 'username' => '1', 'source_ip' => '1', 'message' => '1');
|
649 |
if ($this->_plugin->IsMultisite()) {
|
650 |
$columns = array_slice($columns, 0, 5, true) + array('site' => '1') + array_slice($columns, 5, null, true);
|
@@ -663,49 +847,79 @@ class WSAL_Settings {
|
|
663 |
}
|
664 |
}
|
665 |
|
666 |
-
public function GetColumnsSelected()
|
|
|
667 |
return $this->_plugin->GetGlobalOption('columns');
|
668 |
}
|
669 |
|
670 |
-
public function SetColumns($columns)
|
|
|
671 |
return $this->_plugin->SetGlobalOption('columns', json_encode($columns));
|
672 |
}
|
673 |
-
|
674 |
-
public function IsWPBackend()
|
|
|
675 |
return $this->_plugin->GetGlobalOption('wp-backend');
|
676 |
}
|
677 |
|
678 |
-
public function SetWPBackend($enabled)
|
|
|
679 |
return $this->_plugin->SetGlobalOption('wp-backend', $enabled);
|
680 |
}
|
681 |
|
682 |
-
public function SetFromEmail($email_address)
|
|
|
683 |
return $this->_plugin->SetGlobalOption('from-email', trim($email_address));
|
684 |
}
|
685 |
|
686 |
-
public function GetFromEmail()
|
|
|
687 |
return $this->_plugin->GetGlobalOption('from-email');
|
688 |
}
|
689 |
|
690 |
-
public function SetDisplayName($display_name)
|
|
|
691 |
return $this->_plugin->SetGlobalOption('display-name', trim($display_name));
|
692 |
}
|
693 |
|
694 |
-
public function GetDisplayName()
|
|
|
695 |
return $this->_plugin->GetGlobalOption('display-name');
|
696 |
}
|
697 |
|
698 |
-
public function Set404LogLimit($value)
|
|
|
699 |
return $this->_plugin->SetGlobalOption('log-404-limit', abs($value));
|
700 |
}
|
701 |
|
702 |
-
public function Get404LogLimit()
|
|
|
703 |
return $this->_plugin->GetGlobalOption('log-404-limit', 99);
|
704 |
}
|
705 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
706 |
/*============================== Support Archive Database ==============================*/
|
707 |
|
708 |
-
public function IsArchivingEnabled()
|
|
|
709 |
return $this->_plugin->GetGlobalOption('archiving-e');
|
710 |
}
|
711 |
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* This class is the actual controller of the Settings Page.
|
6 |
+
*/
|
7 |
+
class WSAL_Settings
|
8 |
+
{
|
9 |
/**
|
10 |
* @var WpSecurityAuditLog
|
11 |
*/
|
12 |
protected $_plugin;
|
13 |
+
|
|
|
|
|
|
|
14 |
// <editor-fold desc="Developer Options">
|
15 |
const OPT_DEV_DATA_INSPECTOR = 'd';
|
16 |
const OPT_DEV_PHP_ERRORS = 'p';
|
20 |
const ERROR_CODE_INVALID_IP = 901;
|
21 |
|
22 |
protected $_devoption = null;
|
23 |
+
|
24 |
+
protected $_pruning = 0;
|
25 |
+
|
26 |
+
protected $_disabled = null;
|
27 |
+
|
28 |
+
protected $_viewers = null;
|
29 |
+
|
30 |
+
protected $_editors = null;
|
31 |
+
|
32 |
+
protected $_perpage = null;
|
33 |
+
|
34 |
+
/**
|
35 |
+
* Users excluded from monitoring
|
36 |
+
*/
|
37 |
+
protected $_excluded_users = array();
|
38 |
+
|
39 |
+
/**
|
40 |
+
* Roles excluded from monitoring
|
41 |
+
*/
|
42 |
+
protected $_excluded_roles = array();
|
43 |
+
|
44 |
+
/**
|
45 |
+
* Custom fields excluded from monitoring
|
46 |
+
*/
|
47 |
+
protected $_excluded_custom = array();
|
48 |
+
|
49 |
+
/**
|
50 |
+
* IP excluded from monitoring
|
51 |
+
*/
|
52 |
+
protected $_excluded_ip = array();
|
53 |
+
|
54 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
55 |
+
{
|
56 |
+
$this->_plugin = $plugin;
|
57 |
+
}
|
58 |
+
|
59 |
/**
|
60 |
* @return array Array of developer options to be enabled by default.
|
61 |
*/
|
62 |
+
public function GetDefaultDevOptions()
|
63 |
+
{
|
64 |
return array();
|
65 |
}
|
66 |
+
|
67 |
/**
|
68 |
* Returns whether a developer option is enabled or not.
|
69 |
* @param string $option See self::OPT_DEV_* constants.
|
70 |
* @return boolean If option is enabled or not.
|
71 |
*/
|
72 |
+
public function IsDevOptionEnabled($option)
|
73 |
+
{
|
74 |
if (is_null($this->_devoption)) {
|
75 |
$this->_devoption = $this->_plugin->GetGlobalOption(
|
76 |
'dev-options',
|
80 |
}
|
81 |
return in_array($option, $this->_devoption);
|
82 |
}
|
83 |
+
|
84 |
/**
|
85 |
* @return boolean Whether any developer option has been enabled or not.
|
86 |
*/
|
87 |
+
public function IsAnyDevOptionEnabled()
|
88 |
+
{
|
89 |
return !!$this->_plugin->GetGlobalOption('dev-options', null);
|
90 |
}
|
91 |
+
|
92 |
/**
|
93 |
* Sets whether a developer option is enabled or not.
|
94 |
* @param string $option See self::OPT_DEV_* constants.
|
95 |
* @param boolean $enabled If option should be enabled or not.
|
96 |
*/
|
97 |
+
public function SetDevOptionEnabled($option, $enabled)
|
98 |
+
{
|
99 |
// make sure options have been loaded
|
100 |
$this->IsDevOptionEnabled('');
|
101 |
// remove option if it exists
|
112 |
implode(',', $this->_devoption)
|
113 |
);
|
114 |
}
|
115 |
+
|
116 |
/**
|
117 |
* Remove all enabled developer options.
|
118 |
*/
|
119 |
+
public function ClearDevOptions()
|
120 |
+
{
|
121 |
$this->_devoption = array();
|
122 |
$this->_plugin->SetGlobalOption('dev-options', '');
|
123 |
}
|
124 |
+
|
125 |
/**
|
126 |
* @return boolean Whether to enable data inspector or not.
|
127 |
*/
|
128 |
+
public function IsDataInspectorEnabled()
|
129 |
+
{
|
130 |
return $this->IsDevOptionEnabled(self::OPT_DEV_DATA_INSPECTOR);
|
131 |
}
|
132 |
+
|
133 |
/**
|
134 |
* @return boolean Whether to PHP error logging or not.
|
135 |
*/
|
136 |
+
public function IsPhpErrorLoggingEnabled()
|
137 |
+
{
|
138 |
return $this->IsDevOptionEnabled(self::OPT_DEV_PHP_ERRORS);
|
139 |
}
|
140 |
+
|
141 |
/**
|
142 |
* @return boolean Whether to log requests to file or not.
|
143 |
*/
|
144 |
+
public function IsRequestLoggingEnabled()
|
145 |
+
{
|
146 |
return $this->IsDevOptionEnabled(self::OPT_DEV_REQUEST_LOG);
|
147 |
}
|
148 |
+
|
149 |
/**
|
150 |
* @return boolean Whether to store debug backtrace for PHP alerts or not.
|
151 |
*/
|
152 |
+
public function IsBacktraceLoggingEnabled()
|
153 |
+
{
|
154 |
return $this->IsDevOptionEnabled(self::OPT_DEV_BACKTRACE_LOG);
|
155 |
}
|
156 |
+
|
157 |
// </editor-fold>
|
158 |
+
|
159 |
/**
|
160 |
* @return boolean Whether dashboard widgets are enabled or not.
|
161 |
*/
|
162 |
+
public function IsWidgetsEnabled()
|
163 |
+
{
|
164 |
return !$this->_plugin->GetGlobalOption('disable-widgets');
|
165 |
}
|
166 |
+
|
167 |
/**
|
168 |
* @param boolean $newvalue Whether dashboard widgets are enabled or not.
|
169 |
*/
|
170 |
+
public function SetWidgetsEnabled($newvalue)
|
171 |
+
{
|
172 |
$this->_plugin->SetGlobalOption('disable-widgets', !$newvalue);
|
173 |
}
|
174 |
+
|
175 |
/**
|
176 |
* @return boolean Whether alerts in audit log view refresh automatically or not.
|
177 |
*/
|
178 |
+
public function IsRefreshAlertsEnabled()
|
179 |
+
{
|
180 |
return !$this->_plugin->GetGlobalOption('disable-refresh');
|
181 |
}
|
182 |
+
|
183 |
/**
|
184 |
* @param boolean $newvalue Whether alerts in audit log view refresh automatically or not.
|
185 |
*/
|
186 |
+
public function SetRefreshAlertsEnabled($newvalue)
|
187 |
+
{
|
188 |
$this->_plugin->SetGlobalOption('disable-refresh', !$newvalue);
|
189 |
}
|
190 |
+
|
191 |
/**
|
192 |
* @return int Maximum number of alerts to show in dashboard widget.
|
193 |
*/
|
194 |
+
public function GetDashboardWidgetMaxAlerts()
|
195 |
+
{
|
196 |
return 5;
|
197 |
}
|
198 |
+
|
199 |
// <editor-fold desc="Pruning Settings">
|
200 |
/**
|
201 |
* @return int The maximum number of alerts allowable.
|
202 |
*/
|
203 |
+
public function GetMaxAllowedAlerts()
|
204 |
+
{
|
205 |
return 5000;
|
206 |
}
|
207 |
+
|
208 |
/**
|
209 |
* @return string The default pruning date.
|
210 |
*/
|
211 |
+
public function GetDefaultPruningDate()
|
212 |
+
{
|
213 |
return '1 month';
|
214 |
}
|
215 |
+
|
216 |
/**
|
217 |
* @return string The current pruning date.
|
218 |
*/
|
219 |
+
public function GetPruningDate()
|
220 |
+
{
|
221 |
if (!$this->_pruning) {
|
222 |
$this->_pruning = $this->_plugin->GetGlobalOption('pruning-date');
|
223 |
if (!strtotime($this->_pruning)) {
|
226 |
}
|
227 |
return $this->_pruning;
|
228 |
}
|
229 |
+
|
230 |
/**
|
231 |
* @param string $newvalue The new pruning date.
|
232 |
*/
|
233 |
+
public function SetPruningDate($newvalue)
|
234 |
+
{
|
235 |
if (strtotime($newvalue)) {
|
236 |
$this->_plugin->SetGlobalOption('pruning-date', $newvalue);
|
237 |
$this->_pruning = $newvalue;
|
238 |
}
|
239 |
}
|
240 |
+
|
241 |
/**
|
242 |
* @return integer Maximum number of alerts to keep.
|
243 |
*/
|
244 |
+
public function GetPruningLimit()
|
245 |
+
{
|
246 |
$val = (int)$this->_plugin->GetGlobalOption('pruning-limit');
|
247 |
return $val ? $val : $this->GetMaxAllowedAlerts();
|
248 |
}
|
249 |
+
|
250 |
/**
|
251 |
* @param integer $newvalue The new maximum number of alerts.
|
252 |
*/
|
253 |
+
public function SetPruningLimit($newvalue)
|
254 |
+
{
|
255 |
$newvalue = max(/*min(*/(int)$newvalue/*, $this->GetMaxAllowedAlerts())*/, 1);
|
256 |
$this->_plugin->SetGlobalOption('pruning-limit', $newvalue);
|
257 |
}
|
258 |
+
|
259 |
+
public function SetPruningDateEnabled($enabled)
|
260 |
+
{
|
261 |
$this->_plugin->SetGlobalOption('pruning-date-e', $enabled);
|
262 |
}
|
263 |
+
|
264 |
+
public function SetPruningLimitEnabled($enabled)
|
265 |
+
{
|
266 |
$this->_plugin->SetGlobalOption('pruning-limit-e', $enabled);
|
267 |
}
|
268 |
+
|
269 |
public function IsPruningDateEnabled(){
|
270 |
return $this->_plugin->GetGlobalOption('pruning-date-e');
|
271 |
}
|
272 |
+
|
273 |
+
public function IsPruningLimitEnabled()
|
274 |
+
{
|
275 |
return $this->_plugin->GetGlobalOption('pruning-limit-e');
|
276 |
}
|
277 |
|
278 |
+
public function IsRestrictAdmins()
|
279 |
+
{
|
280 |
return $this->_plugin->GetGlobalOption('restrict-admins', false);
|
281 |
}
|
282 |
+
|
283 |
/**
|
284 |
* @deprecated Sandbox functionality is now in an external plugin.
|
285 |
*/
|
286 |
+
public function IsSandboxPageEnabled()
|
287 |
+
{
|
288 |
$plugins = $this->_plugin->licensing->plugins();
|
289 |
return isset($plugins['wsal-sandbox-extensionphp']);
|
290 |
}
|
291 |
+
|
292 |
+
public function SetRestrictAdmins($enable)
|
293 |
+
{
|
294 |
$this->_plugin->SetGlobalOption('restrict-admins', (bool)$enable);
|
295 |
}
|
296 |
+
|
297 |
// </editor-fold>
|
298 |
+
public function GetDefaultDisabledAlerts()
|
299 |
+
{
|
300 |
return array(0000, 0001, 0002, 0003, 0004, 0005);
|
301 |
}
|
302 |
+
|
303 |
/**
|
304 |
* @return array IDs of disabled alerts.
|
305 |
*/
|
306 |
+
public function GetDisabledAlerts()
|
307 |
+
{
|
308 |
if (!$this->_disabled) {
|
309 |
$this->_disabled = implode(',', $this->GetDefaultDisabledAlerts());
|
310 |
$this->_disabled = $this->_plugin->GetGlobalOption('disabled-alerts', $this->_disabled);
|
313 |
}
|
314 |
return $this->_disabled;
|
315 |
}
|
316 |
+
|
317 |
/**
|
318 |
* @param array $types IDs alerts to disable.
|
319 |
*/
|
320 |
+
public function SetDisabledAlerts($types)
|
321 |
+
{
|
322 |
$this->_disabled = array_unique(array_map('intval', $types));
|
323 |
$this->_plugin->SetGlobalOption('disabled-alerts', implode(',', $this->_disabled));
|
324 |
}
|
325 |
+
|
326 |
+
public function IsIncognito()
|
327 |
+
{
|
328 |
return $this->_plugin->GetGlobalOption('hide-plugin');
|
329 |
}
|
330 |
+
|
331 |
+
public function SetIncognito($enabled)
|
332 |
+
{
|
333 |
return $this->_plugin->SetGlobalOption('hide-plugin', $enabled);
|
334 |
}
|
335 |
|
336 |
/**
|
337 |
* Checking if Logging is enabled.
|
338 |
*/
|
339 |
+
public function IsLoggingDisabled()
|
340 |
+
{
|
341 |
return $this->_plugin->GetGlobalOption('disable-logging');
|
342 |
}
|
343 |
|
344 |
+
public function SetLoggingDisabled($disabled)
|
345 |
+
{
|
346 |
return $this->_plugin->SetGlobalOption('disable-logging', $disabled);
|
347 |
}
|
348 |
+
|
349 |
/**
|
350 |
* Checking if the data will be removed.
|
351 |
*/
|
352 |
+
public function IsDeleteData()
|
353 |
+
{
|
354 |
return $this->_plugin->GetGlobalOption('delete-data');
|
355 |
}
|
356 |
|
357 |
+
public function SetDeleteData($enabled)
|
358 |
+
{
|
359 |
return $this->_plugin->SetGlobalOption('delete-data', $enabled);
|
360 |
}
|
361 |
|
362 |
// <editor-fold desc="Access Control">
|
363 |
+
|
364 |
+
public function SetAllowedPluginViewers($usersOrRoles)
|
365 |
+
{
|
366 |
$this->_viewers = $usersOrRoles;
|
367 |
$this->_plugin->SetGlobalOption('plugin-viewers', implode(',', $this->_viewers));
|
368 |
}
|
369 |
+
|
370 |
+
public function GetAllowedPluginViewers()
|
371 |
+
{
|
372 |
if (is_null($this->_viewers)) {
|
373 |
$this->_viewers = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('plugin-viewers'))));
|
374 |
}
|
375 |
return $this->_viewers;
|
376 |
}
|
377 |
+
|
378 |
+
public function SetAllowedPluginEditors($usersOrRoles)
|
379 |
+
{
|
380 |
$this->_editors = $usersOrRoles;
|
381 |
$this->_plugin->SetGlobalOption('plugin-editors', implode(',', $this->_editors));
|
382 |
}
|
383 |
+
|
384 |
+
public function GetAllowedPluginEditors()
|
385 |
+
{
|
386 |
if (is_null($this->_editors)) {
|
387 |
$this->_editors = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('plugin-editors'))));
|
388 |
}
|
389 |
return $this->_editors;
|
390 |
}
|
391 |
+
|
392 |
+
public function SetViewPerPage($newvalue)
|
393 |
+
{
|
394 |
$this->_perpage = max($newvalue, 1);
|
395 |
$this->_plugin->SetGlobalOption('items-per-page', $this->_perpage);
|
396 |
}
|
397 |
+
|
398 |
+
public function GetViewPerPage()
|
399 |
+
{
|
400 |
if (is_null($this->_perpage)) {
|
401 |
$this->_perpage = (int)$this->_plugin->GetGlobalOption('items-per-page', 10);
|
402 |
}
|
403 |
return $this->_perpage;
|
404 |
}
|
405 |
+
|
406 |
/**
|
407 |
* @param string $action Type of action, either 'view' or 'edit'.
|
408 |
* @return boolean If user has access or not.
|
409 |
*/
|
410 |
+
public function CurrentUserCan($action)
|
411 |
+
{
|
412 |
return $this->UserCan(wp_get_current_user(), $action);
|
413 |
}
|
414 |
+
|
415 |
/**
|
416 |
* @return string[] List of superadmin usernames.
|
417 |
*/
|
418 |
+
protected function GetSuperAdmins()
|
419 |
+
{
|
420 |
return $this->_plugin->IsMultisite() ? get_super_admins() : array();
|
421 |
}
|
422 |
+
|
423 |
/**
|
424 |
* @return string[] List of admin usernames.
|
425 |
*/
|
426 |
+
protected function GetAdmins()
|
427 |
+
{
|
428 |
if ($this->_plugin->IsMultisite()) {
|
429 |
// see: https://gist.github.com/1508426/65785a15b8638d43a9905effb59e4d97319ef8f8
|
430 |
global $wpdb;
|
438 |
} else {
|
439 |
$result = array();
|
440 |
$query = 'role=administrator&fields[]=user_login';
|
441 |
+
foreach (get_users($query) as $user) {
|
442 |
+
$result[] = $user->user_login;
|
443 |
+
}
|
444 |
return $result;
|
445 |
}
|
446 |
}
|
447 |
+
|
448 |
/**
|
449 |
* Returns access tokens for a particular action.
|
450 |
* @param string $action Type of action.
|
451 |
* @return string[] List of tokens (usernames, roles etc).
|
452 |
*/
|
453 |
+
public function GetAccessTokens($action)
|
454 |
+
{
|
455 |
$allowed = array();
|
456 |
switch ($action) {
|
457 |
case 'view':
|
480 |
}
|
481 |
return array_unique($allowed);
|
482 |
}
|
483 |
+
|
484 |
/**
|
485 |
* @param integer|WP_user $user User object to check.
|
486 |
* @param string $action Type of action, either 'view' or 'edit'.
|
487 |
* @return boolean If user has access or not.
|
488 |
*/
|
489 |
+
public function UserCan($user, $action)
|
490 |
+
{
|
491 |
if (is_int($user)) {
|
492 |
$user = get_userdata($user);
|
493 |
}
|
500 |
}
|
501 |
return false;
|
502 |
}
|
503 |
+
|
504 |
+
public function GetCurrentUserRoles($baseRoles = null)
|
505 |
+
{
|
506 |
+
if ($baseRoles == null) {
|
507 |
+
$baseRoles = wp_get_current_user()->roles;
|
508 |
+
}
|
509 |
+
if (function_exists('is_super_admin') && is_super_admin()) {
|
510 |
+
$baseRoles[] = 'superadmin';
|
511 |
+
}
|
512 |
return $baseRoles;
|
513 |
}
|
514 |
|
515 |
+
public function IsLoginSuperAdmin($username)
|
516 |
+
{
|
517 |
$userId = username_exists($username);
|
518 |
+
if (function_exists('is_super_admin') && is_super_admin($userId)) {
|
519 |
+
return true;
|
520 |
+
} else {
|
521 |
+
return false;
|
522 |
+
}
|
523 |
}
|
524 |
+
|
525 |
// </editor-fold>
|
526 |
+
|
527 |
// <editor-fold desc="Licensing">
|
528 |
+
public function GetLicenses()
|
529 |
+
{
|
530 |
return $this->_plugin->GetGlobalOption('licenses');
|
531 |
}
|
532 |
+
|
533 |
+
public function GetLicense($name)
|
534 |
+
{
|
535 |
$data = $this->GetLicenses();
|
536 |
$name = sanitize_key(basename($name));
|
537 |
return isset($data[$name]) ? $data[$name] : array();
|
538 |
}
|
539 |
+
|
540 |
+
public function SetLicenses($data)
|
541 |
+
{
|
542 |
$this->_plugin->SetGlobalOption('licenses', $data);
|
543 |
}
|
544 |
+
|
545 |
+
public function GetLicenseKey($name)
|
546 |
+
{
|
547 |
$data = $this->GetLicense($name);
|
548 |
return isset($data['key']) ? $data['key'] : '';
|
549 |
}
|
550 |
+
|
551 |
public function GetLicenseStatus($name){
|
552 |
$data = $this->GetLicense($name);
|
553 |
return isset($data['sts']) ? $data['sts'] : '';
|
554 |
}
|
555 |
+
|
556 |
+
public function GetLicenseErrors($name)
|
557 |
+
{
|
558 |
$data = $this->GetLicense($name);
|
559 |
return isset($data['err']) ? $data['err'] : '';
|
560 |
}
|
561 |
+
|
562 |
+
public function SetLicenseKey($name, $key)
|
563 |
+
{
|
564 |
$data = $this->GetLicenses();
|
565 |
+
if (!isset($data[$name])) {
|
566 |
+
$data[$name] = array();
|
567 |
+
}
|
568 |
$data[$name]['key'] = $key;
|
569 |
$this->SetLicenses($data);
|
570 |
}
|
571 |
+
|
572 |
+
public function SetLicenseStatus($name, $status)
|
573 |
+
{
|
574 |
$data = $this->GetLicenses();
|
575 |
+
if (!isset($data[$name])) {
|
576 |
+
$data[$name] = array();
|
577 |
+
}
|
578 |
$data[$name]['sts'] = $status;
|
579 |
$this->SetLicenses($data);
|
580 |
}
|
581 |
+
|
582 |
+
public function SetLicenseErrors($name, $errors)
|
583 |
+
{
|
584 |
$data = $this->GetLicenses();
|
585 |
+
if (!isset($data[$name])) {
|
586 |
+
$data[$name] = array();
|
587 |
+
}
|
588 |
$data[$name]['err'] = $errors;
|
589 |
$this->SetLicenses($data);
|
590 |
}
|
591 |
+
|
592 |
+
public function ClearLicenses()
|
593 |
+
{
|
594 |
$this->SetLicenses(array());
|
595 |
}
|
596 |
+
|
597 |
// </editor-fold>
|
598 |
// <editor-fold desc="Client IP Retrieval">
|
599 |
+
|
600 |
+
public function IsMainIPFromProxy()
|
601 |
+
{
|
602 |
return $this->_plugin->GetGlobalOption('use-proxy-ip');
|
603 |
}
|
604 |
+
|
605 |
+
public function SetMainIPFromProxy($enabled)
|
606 |
+
{
|
607 |
return $this->_plugin->SetGlobalOption('use-proxy-ip', $enabled);
|
608 |
}
|
609 |
+
|
610 |
+
public function IsInternalIPsFiltered()
|
611 |
+
{
|
612 |
return $this->_plugin->GetGlobalOption('filter-internal-ip');
|
613 |
}
|
614 |
+
|
615 |
+
public function SetInternalIPsFiltering($enabled)
|
616 |
+
{
|
617 |
return $this->_plugin->SetGlobalOption('filter-internal-ip', $enabled);
|
618 |
}
|
619 |
+
|
620 |
+
public function GetMainClientIP()
|
621 |
+
{
|
622 |
$result = null;
|
623 |
if ($this->IsMainIPFromProxy()) {
|
624 |
// TODO the algorithm below just gets the first IP in the list...we might want to make this more intelligent somehow
|
633 |
}
|
634 |
return $result;
|
635 |
}
|
636 |
+
|
637 |
+
public function GetClientIPs()
|
638 |
+
{
|
639 |
$ips = array();
|
640 |
foreach (array('HTTP_CLIENT_IP', 'HTTP_X_FORWARDED_FOR', 'HTTP_X_FORWARDED', 'HTTP_X_CLUSTER_CLIENT_IP', 'HTTP_FORWARDED_FOR', 'HTTP_FORWARDED', 'REMOTE_ADDR') as $key) {
|
641 |
if (isset($_SERVER[$key])) {
|
649 |
}
|
650 |
return $ips;
|
651 |
}
|
652 |
+
|
653 |
+
protected function NormalizeIP($ip)
|
654 |
+
{
|
655 |
$ip = trim($ip);
|
656 |
if (strpos($ip, ':') !== false && substr_count($ip, '.') == 3 && strpos($ip, '[') === false) {
|
657 |
// IPv4 with a port (eg: 11.22.33.44:80)
|
664 |
}
|
665 |
return $ip;
|
666 |
}
|
667 |
+
|
668 |
+
protected function ValidateIP($ip)
|
669 |
+
{
|
670 |
$opts = FILTER_FLAG_IPV4 | FILTER_FLAG_IPV6;
|
671 |
+
if ($this->IsInternalIPsFiltered()) {
|
672 |
+
$opts = $opts | FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE;
|
673 |
+
}
|
674 |
$filteredIP = filter_var($ip, FILTER_VALIDATE_IP, $opts);
|
675 |
if (!$filteredIP || empty($filteredIP)) {
|
676 |
//Regex IPV4
|
677 |
+
if (preg_match("/^(([1-9]?[0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]).){3}([1-9]?[0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])$/", $ip)) {
|
678 |
+
return $ip;
|
679 |
+
}
|
680 |
//Regex IPV6
|
681 |
+
elseif (preg_match("/^\s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:)))(%.+)?\s*$/", $ip)) {
|
682 |
+
return $ip;
|
683 |
+
}
|
684 |
if (!$this->IsLoggingDisabled) {
|
685 |
error_log("Invalid IP in ValidateIP function: ".$ip);
|
686 |
}
|
693 |
/**
|
694 |
* Users excluded from monitoring
|
695 |
*/
|
|
|
696 |
public function SetExcludedMonitoringUsers($users)
|
697 |
{
|
698 |
$this->_excluded_users = $users;
|
699 |
$this->_plugin->SetGlobalOption('excluded-users', esc_html(implode(',', $this->_excluded_users)));
|
700 |
}
|
701 |
+
|
702 |
public function GetExcludedMonitoringUsers()
|
703 |
{
|
704 |
if (empty($this->_excluded_users)) {
|
710 |
/**
|
711 |
* Roles excluded from monitoring
|
712 |
*/
|
713 |
+
public function SetExcludedMonitoringRoles($roles)
|
714 |
+
{
|
715 |
$this->_excluded_roles = $roles;
|
716 |
$this->_plugin->SetGlobalOption('excluded-roles', esc_html(implode(',', $this->_excluded_roles)));
|
717 |
}
|
718 |
+
|
719 |
+
public function GetExcludedMonitoringRoles()
|
720 |
+
{
|
721 |
if (empty($this->_excluded_roles)) {
|
722 |
$this->_excluded_roles = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('excluded-roles'))));
|
723 |
}
|
727 |
/**
|
728 |
* Custom fields excluded from monitoring
|
729 |
*/
|
730 |
+
public function SetExcludedMonitoringCustom($custom)
|
731 |
+
{
|
732 |
$this->_excluded_custom = $custom;
|
733 |
$this->_plugin->SetGlobalOption('excluded-custom', esc_html(implode(',', $this->_excluded_custom)));
|
734 |
}
|
735 |
+
|
736 |
+
public function GetExcludedMonitoringCustom()
|
737 |
+
{
|
738 |
if (empty($this->_excluded_custom)) {
|
739 |
$this->_excluded_custom = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('excluded-custom'))));
|
740 |
asort($this->_excluded_custom);
|
745 |
/**
|
746 |
* IP excluded from monitoring
|
747 |
*/
|
748 |
+
public function SetExcludedMonitoringIP($ip)
|
749 |
+
{
|
750 |
$this->_excluded_ip = $ip;
|
751 |
$this->_plugin->SetGlobalOption('excluded-ip', esc_html(implode(',', $this->_excluded_ip)));
|
752 |
}
|
753 |
+
|
754 |
+
public function GetExcludedMonitoringIP()
|
755 |
+
{
|
756 |
if (empty($this->_excluded_ip)) {
|
757 |
$this->_excluded_ip = array_unique(array_filter(explode(',', $this->_plugin->GetGlobalOption('excluded-ip'))));
|
758 |
}
|
762 |
/**
|
763 |
* Datetime used in the Alerts.
|
764 |
*/
|
765 |
+
public function GetDatetimeFormat($lineBreak = true)
|
766 |
+
{
|
767 |
if ($lineBreak) {
|
768 |
$date_time_format = $this->GetDateFormat() . '<\b\r>' . $this->GetTimeFormat();
|
769 |
} else {
|
782 |
/**
|
783 |
* Date Format from WordPress General Settings.
|
784 |
*/
|
785 |
+
public function GetDateFormat()
|
786 |
+
{
|
787 |
$wp_date_format = get_option('date_format');
|
788 |
$search = array('F', 'M', 'n', 'j', ' ', '/', 'y', 'S', ',', 'l', 'D');
|
789 |
$replace = array('m', 'm', 'm', 'd', '-', '-', 'Y', '', '', '', '');
|
794 |
/**
|
795 |
* Time Format from WordPress General Settings.
|
796 |
*/
|
797 |
+
public function GetTimeFormat()
|
798 |
+
{
|
799 |
$wp_time_format = get_option('time_format');
|
800 |
$search = array('a', 'A', 'T', ' ');
|
801 |
$replace = array('', '', '', '');
|
807 |
* Alerts Timestamp
|
808 |
* Server's timezone or WordPress' timezone
|
809 |
*/
|
810 |
+
public function GetTimezone()
|
811 |
+
{
|
812 |
return $this->_plugin->GetGlobalOption('timezone', 0);
|
813 |
}
|
814 |
|
815 |
+
public function SetTimezone($newvalue)
|
816 |
+
{
|
817 |
return $this->_plugin->SetGlobalOption('timezone', $newvalue);
|
818 |
}
|
819 |
|
820 |
+
public function GetAdapterConfig($name_field)
|
821 |
+
{
|
822 |
return $this->_plugin->GetGlobalOption($name_field);
|
823 |
}
|
824 |
|
825 |
+
public function SetAdapterConfig($name_field, $newvalue)
|
826 |
+
{
|
827 |
return $this->_plugin->SetGlobalOption($name_field, trim($newvalue));
|
828 |
}
|
829 |
|
830 |
+
public function GetColumns()
|
831 |
+
{
|
832 |
$columns = array('alert_code' => '1', 'type' => '1', 'date' => '1', 'username' => '1', 'source_ip' => '1', 'message' => '1');
|
833 |
if ($this->_plugin->IsMultisite()) {
|
834 |
$columns = array_slice($columns, 0, 5, true) + array('site' => '1') + array_slice($columns, 5, null, true);
|
847 |
}
|
848 |
}
|
849 |
|
850 |
+
public function GetColumnsSelected()
|
851 |
+
{
|
852 |
return $this->_plugin->GetGlobalOption('columns');
|
853 |
}
|
854 |
|
855 |
+
public function SetColumns($columns)
|
856 |
+
{
|
857 |
return $this->_plugin->SetGlobalOption('columns', json_encode($columns));
|
858 |
}
|
859 |
+
|
860 |
+
public function IsWPBackend()
|
861 |
+
{
|
862 |
return $this->_plugin->GetGlobalOption('wp-backend');
|
863 |
}
|
864 |
|
865 |
+
public function SetWPBackend($enabled)
|
866 |
+
{
|
867 |
return $this->_plugin->SetGlobalOption('wp-backend', $enabled);
|
868 |
}
|
869 |
|
870 |
+
public function SetFromEmail($email_address)
|
871 |
+
{
|
872 |
return $this->_plugin->SetGlobalOption('from-email', trim($email_address));
|
873 |
}
|
874 |
|
875 |
+
public function GetFromEmail()
|
876 |
+
{
|
877 |
return $this->_plugin->GetGlobalOption('from-email');
|
878 |
}
|
879 |
|
880 |
+
public function SetDisplayName($display_name)
|
881 |
+
{
|
882 |
return $this->_plugin->SetGlobalOption('display-name', trim($display_name));
|
883 |
}
|
884 |
|
885 |
+
public function GetDisplayName()
|
886 |
+
{
|
887 |
return $this->_plugin->GetGlobalOption('display-name');
|
888 |
}
|
889 |
|
890 |
+
public function Set404LogLimit($value)
|
891 |
+
{
|
892 |
return $this->_plugin->SetGlobalOption('log-404-limit', abs($value));
|
893 |
}
|
894 |
|
895 |
+
public function Get404LogLimit()
|
896 |
+
{
|
897 |
return $this->_plugin->GetGlobalOption('log-404-limit', 99);
|
898 |
}
|
899 |
|
900 |
+
/**
|
901 |
+
* Sets the 404 log limit for visitor.
|
902 |
+
*
|
903 |
+
* @param int $value - 404 log limit.
|
904 |
+
* @since 2.6.3
|
905 |
+
*/
|
906 |
+
public function SetVisitor404LogLimit( $value ) {
|
907 |
+
return $this->_plugin->SetGlobalOption( 'log-visitor-404-limit', abs( $value ) );
|
908 |
+
}
|
909 |
+
|
910 |
+
/**
|
911 |
+
* Get the 404 log limit for visitor.
|
912 |
+
*
|
913 |
+
* @since 2.6.3
|
914 |
+
*/
|
915 |
+
public function GetVisitor404LogLimit() {
|
916 |
+
return $this->_plugin->GetGlobalOption( 'log-visitor-404-limit', 99 );
|
917 |
+
}
|
918 |
+
|
919 |
/*============================== Support Archive Database ==============================*/
|
920 |
|
921 |
+
public function IsArchivingEnabled()
|
922 |
+
{
|
923 |
return $this->_plugin->GetGlobalOption('archiving-e');
|
924 |
}
|
925 |
|
classes/SimpleProfiler.php
CHANGED
@@ -1,44 +1,54 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
23 |
}
|
24 |
|
25 |
-
class WSAL_SimpleProfiler_Item
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
|
|
|
|
|
|
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*/
|
5 |
+
class WSAL_SimpleProfiler
|
6 |
+
{
|
7 |
+
protected $_items = array();
|
8 |
+
|
9 |
+
public function Start($name)
|
10 |
+
{
|
11 |
+
$item = new WSAL_SimpleProfiler_Item($name);
|
12 |
+
$this->_items[] = $item;
|
13 |
+
return $item;
|
14 |
+
}
|
15 |
+
|
16 |
+
public function AsComment()
|
17 |
+
{
|
18 |
+
echo '<!-- ' . PHP_EOL;
|
19 |
+
foreach ($this->_items as $item) {
|
20 |
+
echo ' ' . $item . PHP_EOL;
|
21 |
+
}
|
22 |
+
echo '-->' . PHP_EOL;
|
23 |
+
}
|
24 |
+
|
25 |
+
public function GetItems()
|
26 |
+
{
|
27 |
+
return $this->_items;
|
28 |
+
}
|
29 |
}
|
30 |
|
31 |
+
class WSAL_SimpleProfiler_Item
|
32 |
+
{
|
33 |
+
public function __construct($name)
|
34 |
+
{
|
35 |
+
$this->name = $name;
|
36 |
+
$this->t_bgn = microtime(true);
|
37 |
+
$this->m_bgn = memory_get_usage();
|
38 |
+
}
|
39 |
+
|
40 |
+
public function Stop()
|
41 |
+
{
|
42 |
+
$this->t_end = microtime(true);
|
43 |
+
$this->m_end = memory_get_usage();
|
44 |
+
}
|
45 |
+
|
46 |
+
public function __toString()
|
47 |
+
{
|
48 |
+
$t_diff = $this->t_end - $this->t_bgn;
|
49 |
+
$m_diff = $this->m_end - $this->m_bgn;
|
50 |
+
return number_format($t_diff, 6) . 's '
|
51 |
+
. str_pad(number_format($m_diff, 0), 12, ' ', STR_PAD_LEFT) . 'b '
|
52 |
+
. $this->name;
|
53 |
+
}
|
54 |
+
}
|
classes/ViewManager.php
CHANGED
@@ -1,79 +1,96 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
/**
|
6 |
-
* @var WSAL_AbstractView[]
|
7 |
*/
|
8 |
public $views = array();
|
9 |
-
|
10 |
/**
|
11 |
* @var WpSecurityAuditLog
|
12 |
*/
|
13 |
protected $_plugin;
|
14 |
|
15 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
16 |
$this->_plugin = $plugin;
|
17 |
-
|
18 |
// load views
|
19 |
-
foreach(glob(dirname(__FILE__) . '/Views/*.php') as $file)
|
20 |
$this->AddFromFile($file);
|
21 |
-
|
|
|
22 |
// add menus
|
23 |
add_action('admin_menu', array($this, 'AddAdminMenus'));
|
24 |
add_action('network_admin_menu', array($this, 'AddAdminMenus'));
|
25 |
-
|
26 |
// add plugin shortcut links
|
27 |
add_filter('plugin_action_links_' . $plugin->GetBaseName(), array($this, 'AddPluginShortcuts'));
|
28 |
-
|
29 |
// render header
|
30 |
add_action('admin_enqueue_scripts', array($this, 'RenderViewHeader'));
|
31 |
-
|
32 |
// render footer
|
33 |
add_action('admin_footer', array($this, 'RenderViewFooter'));
|
34 |
}
|
35 |
-
|
36 |
/**
|
37 |
* Add new view from file inside autoloader path.
|
38 |
* @param string $file Path to file.
|
39 |
*/
|
40 |
-
public function AddFromFile($file)
|
|
|
41 |
$this->AddFromClass($this->_plugin->GetClassFileClassName($file));
|
42 |
}
|
43 |
-
|
44 |
/**
|
45 |
* Add new view given class name.
|
46 |
* @param string $class Class name.
|
47 |
*/
|
48 |
-
public function AddFromClass($class)
|
|
|
49 |
$this->AddInstance(new $class($this->_plugin));
|
50 |
}
|
51 |
-
|
52 |
/**
|
53 |
* Add newly created view to list.
|
54 |
* @param WSAL_AbstractView $view The new view.
|
55 |
*/
|
56 |
-
public function AddInstance(WSAL_AbstractView $view)
|
|
|
57 |
$this->views[] = $view;
|
58 |
}
|
59 |
-
|
60 |
/**
|
61 |
* Order views by their declared weight.
|
62 |
*/
|
63 |
-
public function ReorderViews()
|
|
|
64 |
usort($this->views, array($this, 'OrderByWeight'));
|
65 |
}
|
66 |
-
|
67 |
/**
|
68 |
* @internal This has to be public for PHP to call it.
|
69 |
* @param WSAL_AbstractView $a
|
70 |
* @param WSAL_AbstractView $b
|
71 |
* @return int
|
72 |
*/
|
73 |
-
public function OrderByWeight(WSAL_AbstractView $a, WSAL_AbstractView $b)
|
|
|
74 |
$wa = $a->GetWeight();
|
75 |
$wb = $b->GetWeight();
|
76 |
-
switch(true){
|
77 |
case $wa < $wb:
|
78 |
return -1;
|
79 |
case $wa > $wb:
|
@@ -82,14 +99,15 @@ class WSAL_ViewManager {
|
|
82 |
return 0;
|
83 |
}
|
84 |
}
|
85 |
-
|
86 |
/**
|
87 |
* Wordpress Action
|
88 |
*/
|
89 |
-
public function AddAdminMenus()
|
|
|
90 |
$this->ReorderViews();
|
91 |
-
|
92 |
-
if($this->_plugin->settings->CurrentUserCan('view') && count($this->views)){
|
93 |
// add main menu
|
94 |
$this->views[0]->hook_suffix = add_menu_page(
|
95 |
'WP Security Audit Log',
|
@@ -120,81 +138,91 @@ class WSAL_ViewManager {
|
|
120 |
}
|
121 |
}
|
122 |
}
|
123 |
-
|
124 |
/**
|
125 |
* Wordpress Filter
|
126 |
*/
|
127 |
-
public function AddPluginShortcuts($old_links)
|
|
|
128 |
$this->ReorderViews();
|
129 |
-
|
130 |
$new_links = array();
|
131 |
-
foreach($this->views as $view){
|
132 |
-
if($view->HasPluginShortcutLink()){
|
133 |
$new_links[] =
|
134 |
'<a href="'
|
135 |
-
|
136 |
-
|
137 |
-
) . '">'
|
138 |
. $view->GetName()
|
139 |
. '</a>';
|
140 |
}
|
141 |
}
|
142 |
return array_merge($new_links, $old_links);
|
143 |
}
|
144 |
-
|
145 |
/**
|
146 |
* @return int Returns page id of current page (or false on error).
|
147 |
*/
|
148 |
-
protected function GetBackendPageIndex()
|
149 |
-
|
150 |
-
|
151 |
-
|
|
|
152 |
return $i;
|
|
|
|
|
|
|
153 |
return false;
|
154 |
}
|
155 |
-
|
156 |
-
/**
|
157 |
-
*
|
158 |
-
* @var WSAL_AbstractView|null
|
159 |
-
*/
|
160 |
-
protected $_active_view = false;
|
161 |
-
|
162 |
/**
|
163 |
* @return WSAL_AbstractView|null Returns the current active view or null if none.
|
164 |
*/
|
165 |
-
public function GetActiveView()
|
166 |
-
|
|
|
167 |
$this->_active_view = null;
|
168 |
-
|
169 |
-
if(isset($_REQUEST['page']))
|
170 |
-
foreach($this->views as $view)
|
171 |
-
if($_REQUEST['page'] == $view->GetSafeViewName())
|
172 |
$this->_active_view = $view;
|
173 |
-
|
174 |
-
|
|
|
|
|
|
|
175 |
$this->_active_view->is_active = true;
|
|
|
176 |
}
|
177 |
return $this->_active_view;
|
178 |
}
|
179 |
-
|
180 |
/**
|
181 |
* Render header of the current view.
|
182 |
*/
|
183 |
-
public function RenderViewHeader()
|
184 |
-
|
|
|
|
|
|
|
185 |
}
|
186 |
-
|
187 |
/**
|
188 |
* Render footer of the current view.
|
189 |
*/
|
190 |
-
public function RenderViewFooter()
|
191 |
-
|
|
|
|
|
|
|
192 |
}
|
193 |
-
|
194 |
/**
|
195 |
* Render content of the current view.
|
196 |
*/
|
197 |
-
public function RenderViewBody()
|
|
|
198 |
$view = $this->GetActiveView();
|
199 |
?><div class="wrap"><?php
|
200 |
$view->RenderIcon();
|
@@ -202,16 +230,19 @@ class WSAL_ViewManager {
|
|
202 |
$view->RenderContent();
|
203 |
?></div><?php
|
204 |
}
|
205 |
-
|
206 |
/**
|
207 |
* Returns view instance corresponding to its class name.
|
208 |
* @param string $className View class name.
|
209 |
* @return WSAL_AbstractView The view or false on failure.
|
210 |
*/
|
211 |
-
public function FindByClassName($className)
|
212 |
-
|
213 |
-
|
|
|
214 |
return $view;
|
|
|
|
|
215 |
return false;
|
216 |
}
|
217 |
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* This Class load all the views, initialize them and shows the active one.
|
6 |
+
* It creates also the menu items.
|
7 |
+
*/
|
8 |
+
class WSAL_ViewManager
|
9 |
+
{
|
10 |
/**
|
11 |
+
* @var WSAL_AbstractView[]
|
12 |
*/
|
13 |
public $views = array();
|
14 |
+
|
15 |
/**
|
16 |
* @var WpSecurityAuditLog
|
17 |
*/
|
18 |
protected $_plugin;
|
19 |
|
20 |
+
/**
|
21 |
+
* @var WSAL_AbstractView|null
|
22 |
+
*/
|
23 |
+
protected $_active_view = false;
|
24 |
+
|
25 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
26 |
+
{
|
27 |
$this->_plugin = $plugin;
|
28 |
+
|
29 |
// load views
|
30 |
+
foreach (glob(dirname(__FILE__) . '/Views/*.php') as $file) {
|
31 |
$this->AddFromFile($file);
|
32 |
+
}
|
33 |
+
|
34 |
// add menus
|
35 |
add_action('admin_menu', array($this, 'AddAdminMenus'));
|
36 |
add_action('network_admin_menu', array($this, 'AddAdminMenus'));
|
37 |
+
|
38 |
// add plugin shortcut links
|
39 |
add_filter('plugin_action_links_' . $plugin->GetBaseName(), array($this, 'AddPluginShortcuts'));
|
40 |
+
|
41 |
// render header
|
42 |
add_action('admin_enqueue_scripts', array($this, 'RenderViewHeader'));
|
43 |
+
|
44 |
// render footer
|
45 |
add_action('admin_footer', array($this, 'RenderViewFooter'));
|
46 |
}
|
47 |
+
|
48 |
/**
|
49 |
* Add new view from file inside autoloader path.
|
50 |
* @param string $file Path to file.
|
51 |
*/
|
52 |
+
public function AddFromFile($file)
|
53 |
+
{
|
54 |
$this->AddFromClass($this->_plugin->GetClassFileClassName($file));
|
55 |
}
|
56 |
+
|
57 |
/**
|
58 |
* Add new view given class name.
|
59 |
* @param string $class Class name.
|
60 |
*/
|
61 |
+
public function AddFromClass($class)
|
62 |
+
{
|
63 |
$this->AddInstance(new $class($this->_plugin));
|
64 |
}
|
65 |
+
|
66 |
/**
|
67 |
* Add newly created view to list.
|
68 |
* @param WSAL_AbstractView $view The new view.
|
69 |
*/
|
70 |
+
public function AddInstance(WSAL_AbstractView $view)
|
71 |
+
{
|
72 |
$this->views[] = $view;
|
73 |
}
|
74 |
+
|
75 |
/**
|
76 |
* Order views by their declared weight.
|
77 |
*/
|
78 |
+
public function ReorderViews()
|
79 |
+
{
|
80 |
usort($this->views, array($this, 'OrderByWeight'));
|
81 |
}
|
82 |
+
|
83 |
/**
|
84 |
* @internal This has to be public for PHP to call it.
|
85 |
* @param WSAL_AbstractView $a
|
86 |
* @param WSAL_AbstractView $b
|
87 |
* @return int
|
88 |
*/
|
89 |
+
public function OrderByWeight(WSAL_AbstractView $a, WSAL_AbstractView $b)
|
90 |
+
{
|
91 |
$wa = $a->GetWeight();
|
92 |
$wb = $b->GetWeight();
|
93 |
+
switch (true) {
|
94 |
case $wa < $wb:
|
95 |
return -1;
|
96 |
case $wa > $wb:
|
99 |
return 0;
|
100 |
}
|
101 |
}
|
102 |
+
|
103 |
/**
|
104 |
* Wordpress Action
|
105 |
*/
|
106 |
+
public function AddAdminMenus()
|
107 |
+
{
|
108 |
$this->ReorderViews();
|
109 |
+
|
110 |
+
if ($this->_plugin->settings->CurrentUserCan('view') && count($this->views)) {
|
111 |
// add main menu
|
112 |
$this->views[0]->hook_suffix = add_menu_page(
|
113 |
'WP Security Audit Log',
|
138 |
}
|
139 |
}
|
140 |
}
|
141 |
+
|
142 |
/**
|
143 |
* Wordpress Filter
|
144 |
*/
|
145 |
+
public function AddPluginShortcuts($old_links)
|
146 |
+
{
|
147 |
$this->ReorderViews();
|
148 |
+
|
149 |
$new_links = array();
|
150 |
+
foreach ($this->views as $view) {
|
151 |
+
if ($view->HasPluginShortcutLink()) {
|
152 |
$new_links[] =
|
153 |
'<a href="'
|
154 |
+
. admin_url('admin.php?page=' . $view->GetSafeViewName())
|
155 |
+
. '">'
|
|
|
156 |
. $view->GetName()
|
157 |
. '</a>';
|
158 |
}
|
159 |
}
|
160 |
return array_merge($new_links, $old_links);
|
161 |
}
|
162 |
+
|
163 |
/**
|
164 |
* @return int Returns page id of current page (or false on error).
|
165 |
*/
|
166 |
+
protected function GetBackendPageIndex()
|
167 |
+
{
|
168 |
+
if (isset($_REQUEST['page'])) {
|
169 |
+
foreach ($this->views as $i => $view) {
|
170 |
+
if ($_REQUEST['page'] == $view->GetSafeViewName()) {
|
171 |
return $i;
|
172 |
+
}
|
173 |
+
}
|
174 |
+
}
|
175 |
return false;
|
176 |
}
|
177 |
+
|
|
|
|
|
|
|
|
|
|
|
|
|
178 |
/**
|
179 |
* @return WSAL_AbstractView|null Returns the current active view or null if none.
|
180 |
*/
|
181 |
+
public function GetActiveView()
|
182 |
+
{
|
183 |
+
if ($this->_active_view === false) {
|
184 |
$this->_active_view = null;
|
185 |
+
|
186 |
+
if (isset($_REQUEST['page'])) {
|
187 |
+
foreach ($this->views as $view) {
|
188 |
+
if ($_REQUEST['page'] == $view->GetSafeViewName()) {
|
189 |
$this->_active_view = $view;
|
190 |
+
}
|
191 |
+
}
|
192 |
+
}
|
193 |
+
|
194 |
+
if ($this->_active_view) {
|
195 |
$this->_active_view->is_active = true;
|
196 |
+
}
|
197 |
}
|
198 |
return $this->_active_view;
|
199 |
}
|
200 |
+
|
201 |
/**
|
202 |
* Render header of the current view.
|
203 |
*/
|
204 |
+
public function RenderViewHeader()
|
205 |
+
{
|
206 |
+
if (!!($view = $this->GetActiveView())) {
|
207 |
+
$view->Header();
|
208 |
+
}
|
209 |
}
|
210 |
+
|
211 |
/**
|
212 |
* Render footer of the current view.
|
213 |
*/
|
214 |
+
public function RenderViewFooter()
|
215 |
+
{
|
216 |
+
if (!!($view = $this->GetActiveView())) {
|
217 |
+
$view->Footer();
|
218 |
+
}
|
219 |
}
|
220 |
+
|
221 |
/**
|
222 |
* Render content of the current view.
|
223 |
*/
|
224 |
+
public function RenderViewBody()
|
225 |
+
{
|
226 |
$view = $this->GetActiveView();
|
227 |
?><div class="wrap"><?php
|
228 |
$view->RenderIcon();
|
230 |
$view->RenderContent();
|
231 |
?></div><?php
|
232 |
}
|
233 |
+
|
234 |
/**
|
235 |
* Returns view instance corresponding to its class name.
|
236 |
* @param string $className View class name.
|
237 |
* @return WSAL_AbstractView The view or false on failure.
|
238 |
*/
|
239 |
+
public function FindByClassName($className)
|
240 |
+
{
|
241 |
+
foreach ($this->views as $view) {
|
242 |
+
if ($view instanceof $className) {
|
243 |
return $view;
|
244 |
+
}
|
245 |
+
}
|
246 |
return false;
|
247 |
}
|
248 |
|
classes/Views/About.php
CHANGED
@@ -1,86 +1,94 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
69 |
-
|
70 |
-
|
71 |
-
|
72 |
-
|
73 |
-
|
74 |
-
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
|
79 |
-
|
80 |
-
|
81 |
-
|
82 |
-
|
83 |
-
|
84 |
-
|
85 |
-
|
86 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* About Page.
|
6 |
+
*/
|
7 |
+
class WSAL_Views_About extends WSAL_AbstractView
|
8 |
+
{
|
9 |
+
public function GetTitle()
|
10 |
+
{
|
11 |
+
return __('About WP Security Audit Log', 'wp-security-audit-log');
|
12 |
+
}
|
13 |
+
|
14 |
+
public function GetIcon()
|
15 |
+
{
|
16 |
+
return 'dashicons-editor-help';
|
17 |
+
}
|
18 |
+
|
19 |
+
public function GetName()
|
20 |
+
{
|
21 |
+
return __('About', 'wp-security-audit-log');
|
22 |
+
}
|
23 |
+
|
24 |
+
public function GetWeight()
|
25 |
+
{
|
26 |
+
return 6;
|
27 |
+
}
|
28 |
+
|
29 |
+
public function Render()
|
30 |
+
{
|
31 |
+
?><div class="metabox-holder" style="position: relative;">
|
32 |
+
|
33 |
+
<div class="postbox" style="margin-right: 270px;">
|
34 |
+
<!--h3 class="hndl"><span>About WP Security Audit Log</span></h3-->
|
35 |
+
<div class="inside">
|
36 |
+
<div class="activity-block">
|
37 |
+
<?php _e('WP Security Audit Log enables WordPress administrators and owners to identify WordPress security issues before they become a security problem by keeping a security audit log. WP Security Audit Log is developed by WordPress security professionals WP White Security.', 'wp-security-audit-log'); ?>
|
38 |
+
|
39 |
+
<h2><?php _e('Keep A WordPress Security Audit Log & Identify WordPress Security Issues', 'wp-security-audit-log'); ?></h2>
|
40 |
+
<p>
|
41 |
+
<?php _e('WP Security Audit Log logs everything happening on your WordPress blog or website and WordPress multisite network. By using WP Security Audit Log security plugin it is very easy to track suspicious user activity before it becomes a problem or a security issue. A WordPress security alert is generated by the plugin when:', 'wp-security-audit-log'); ?>
|
42 |
+
</p>
|
43 |
+
<ul style="list-style-type: disc; margin-left: 2.5em; list-style-position: outside;">
|
44 |
+
<li><?php _e('User creates a new user or a new user is registered', 'wp-security-audit-log'); ?></li>
|
45 |
+
<li><?php _e('Existing user changes the role, password or other properties of another user', 'wp-security-audit-log'); ?></li>
|
46 |
+
<li><?php _e('Existing user on a WordPress multisite network is added to a site', 'wp-security-audit-log'); ?></li>
|
47 |
+
<li><?php _e('User uploads or deletes a file, changes a password or email address', 'wp-security-audit-log'); ?></li>
|
48 |
+
<li><?php _e('User installs, activates, deactivates, upgrades or uninstalls a plugin', 'wp-security-audit-log'); ?></li>
|
49 |
+
<li><?php _e('User creates, modifies or deletes a new post, page, category or a custom post type', 'wp-security-audit-log'); ?></li>
|
50 |
+
<li><?php _e('User installs or activates a WordPress theme', 'wp-security-audit-log'); ?></li>
|
51 |
+
<li><?php _e('User adds, modifies or deletes a widget', 'wp-security-audit-log'); ?></li>
|
52 |
+
<li><?php _e('User uses the dashboard file editor', 'wp-security-audit-log'); ?></li>
|
53 |
+
<li><?php _e('WordPress settings are changed', 'wp-security-audit-log'); ?></li>
|
54 |
+
<li><?php _e('Failed login attempts', 'wp-security-audit-log'); ?></li>
|
55 |
+
<li><?php _e('and much more…', 'wp-security-audit-log'); ?></li>
|
56 |
+
</ul>
|
57 |
+
<br/>
|
58 |
+
Refer to the complete list of <a href="http://www.wpsecurityauditlog.com/documentation/list-monitoring-wordpress-security-alerts-audit-log/?utm_source=wsalabt&utm_medium=txtlink&utm_campaign=wsal" target="_blank">WordPress Security Alerts</a> for more information.
|
59 |
+
</div>
|
60 |
+
</div>
|
61 |
+
</div>
|
62 |
+
|
63 |
+
<div style="position: absolute; right: 70px; width: 180px; top: 10px;">
|
64 |
+
<div class="postbox">
|
65 |
+
<h3 class="hndl"><span><?php _e('Extend the Functionality & Get More Value from WP Security Audit Log', 'wp-security-audit-log'); ?></span></h3>
|
66 |
+
<div class="inside">
|
67 |
+
<p>
|
68 |
+
<?php _e('Get more value out of WP Security Audit Log by extending the functionality of WP Security Audit Log with the premium Add-Ons.'); ?>
|
69 |
+
</p>
|
70 |
+
<a class="button button-primary" href="http://www.wpsecurityauditlog.com/plugin-extensions/" target="_blank"><?php _e('See Add-Ons', 'wp-security-audit-log'); ?></a>
|
71 |
+
</div>
|
72 |
+
</div>
|
73 |
+
<div class="postbox">
|
74 |
+
<h3 class="hndl"><span><?php _e('WP Security Audit Log in your Language!', 'wp-security-audit-log'); ?></span></h3>
|
75 |
+
<div class="inside">
|
76 |
+
<?php _e('If you are interested in translating our plugin please drop us an email on', 'wp-security-audit-log'); ?>
|
77 |
+
<a href="mailto:plugins@wpwhitesecurity.com">plugins@wpwhitesecurity.com</a>.
|
78 |
+
</div>
|
79 |
+
</div>
|
80 |
+
<div class="postbox">
|
81 |
+
<h3 class="hndl"><span><?php _e('WordPress Security Services', 'wp-security-audit-log'); ?></span></h3>
|
82 |
+
<div class="inside">
|
83 |
+
<?php _e('Professional WordPress security services provided by WP White Security', 'wp-security-audit-log'); ?>
|
84 |
+
<ul>
|
85 |
+
<li><a href="http://www.wpwhitesecurity.com/wordpress-security-services/wordpress-security-hardening/?utm_source=wpsalabt&utm_medium=txtlink&utm_campaign=wpsal" target="_blank">Security Hardening</a></li>
|
86 |
+
<li><a href="http://www.wpwhitesecurity.com/wordpress-security-services/wordpress-security-audit/?utm_source=wpsalabt&utm_medium=txtlink&utm_campaign=wpsal" target="_blank">Security Audit</a></li>
|
87 |
+
<li><a href="http://www.wpwhitesecurity.com/wordpress-security-services/wordpress-plugins-security-code-audit-review/?utm_source=wpsalabt&utm_medium=txtlink&utm_campaign=wpsal" target="_blank">Plugin Security Code Audit</a></li>
|
88 |
+
</ul>
|
89 |
+
</div>
|
90 |
+
</div>
|
91 |
+
</div>
|
92 |
+
</div><?php
|
93 |
+
}
|
94 |
+
}
|
classes/Views/AuditLog.php
CHANGED
@@ -1,7 +1,12 @@
|
|
1 |
<?php
|
2 |
require_once(ABSPATH . 'wp-admin/includes/plugin.php');
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
/**
|
6 |
* @var WSAL_AuditLogListView
|
7 |
*/
|
@@ -9,7 +14,8 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
9 |
|
10 |
protected $_version;
|
11 |
|
12 |
-
public function __construct(WpSecurityAuditLog $plugin)
|
|
|
13 |
parent::__construct($plugin);
|
14 |
add_action('wp_ajax_AjaxInspector', array($this, 'AjaxInspector'));
|
15 |
add_action('wp_ajax_AjaxRefresh', array($this, 'AjaxRefresh'));
|
@@ -43,36 +49,43 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
43 |
}
|
44 |
}
|
45 |
|
46 |
-
public function HasPluginShortcutLink()
|
|
|
47 |
return true;
|
48 |
}
|
49 |
|
50 |
-
public function GetTitle()
|
|
|
51 |
return __('Audit Log Viewer', 'wp-security-audit-log');
|
52 |
}
|
53 |
|
54 |
-
public function GetIcon()
|
|
|
55 |
return $this->_wpversion < 3.8
|
56 |
? $this->_plugin->GetBaseUrl() . '/img/logo-main-menu.png'
|
57 |
: 'dashicons-welcome-view-site';
|
58 |
}
|
59 |
|
60 |
-
public function GetName()
|
|
|
61 |
return __('Audit Log Viewer', 'wp-security-audit-log');
|
62 |
}
|
63 |
|
64 |
-
public function GetWeight()
|
|
|
65 |
return 1;
|
66 |
}
|
67 |
|
68 |
-
protected function GetListView()
|
|
|
69 |
if (is_null($this->_listview)) {
|
70 |
$this->_listview = new WSAL_AuditLogListView($this->_plugin);
|
71 |
}
|
72 |
return $this->_listview;
|
73 |
}
|
74 |
|
75 |
-
public function Render()
|
|
|
76 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
77 |
wp_die(__('You do not have sufficient permissions to access this page.', 'wp-security-audit-log'));
|
78 |
}
|
@@ -108,7 +121,8 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
108 |
</script><?php
|
109 |
}
|
110 |
|
111 |
-
public function AjaxInspector()
|
|
|
112 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
113 |
die('Access Denied.');
|
114 |
}
|
@@ -133,7 +147,8 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
133 |
die;
|
134 |
}
|
135 |
|
136 |
-
public function AjaxRefresh()
|
|
|
137 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
138 |
die('Access Denied.');
|
139 |
}
|
@@ -145,9 +160,11 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
145 |
$max = 40; // 40*500msec = 20sec
|
146 |
|
147 |
$is_archive = false;
|
148 |
-
|
149 |
-
|
150 |
-
$
|
|
|
|
|
151 |
}
|
152 |
|
153 |
do {
|
@@ -164,7 +181,8 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
164 |
die;
|
165 |
}
|
166 |
|
167 |
-
public function AjaxSetIpp()
|
|
|
168 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
169 |
die('Access Denied.');
|
170 |
}
|
@@ -175,7 +193,8 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
175 |
die;
|
176 |
}
|
177 |
|
178 |
-
public function AjaxSearchSite()
|
|
|
179 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
180 |
die('Access Denied.');
|
181 |
}
|
@@ -197,14 +216,15 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
197 |
die(json_encode(array_slice($grp1 + $grp2, 0, 7)));
|
198 |
}
|
199 |
|
200 |
-
public function AjaxSwitchDB()
|
|
|
201 |
if (isset($_REQUEST['selected_db'])) {
|
202 |
-
$
|
203 |
-
$wp_session['selected_db'] = $_REQUEST['selected_db'];
|
204 |
}
|
205 |
}
|
206 |
|
207 |
-
public function Header()
|
|
|
208 |
add_thickbox();
|
209 |
wp_enqueue_style('darktooltip', $this->_plugin->GetBaseUrl() . '/css/darktooltip.css', array(), '');
|
210 |
wp_enqueue_style(
|
@@ -215,7 +235,8 @@ class WSAL_Views_AuditLog extends WSAL_AbstractView {
|
|
215 |
);
|
216 |
}
|
217 |
|
218 |
-
public function Footer()
|
|
|
219 |
wp_enqueue_script('jquery');
|
220 |
wp_enqueue_script('darktooltip', $this->_plugin->GetBaseUrl() . '/js/jquery.darktooltip.js', array('jquery'), '');
|
221 |
wp_enqueue_script('suggest');
|
1 |
<?php
|
2 |
require_once(ABSPATH . 'wp-admin/includes/plugin.php');
|
3 |
+
/**
|
4 |
+
* @package Wsal
|
5 |
+
*
|
6 |
+
* Audit Log Viewer Page
|
7 |
+
*/
|
8 |
+
class WSAL_Views_AuditLog extends WSAL_AbstractView
|
9 |
+
{
|
10 |
/**
|
11 |
* @var WSAL_AuditLogListView
|
12 |
*/
|
14 |
|
15 |
protected $_version;
|
16 |
|
17 |
+
public function __construct(WpSecurityAuditLog $plugin)
|
18 |
+
{
|
19 |
parent::__construct($plugin);
|
20 |
add_action('wp_ajax_AjaxInspector', array($this, 'AjaxInspector'));
|
21 |
add_action('wp_ajax_AjaxRefresh', array($this, 'AjaxRefresh'));
|
49 |
}
|
50 |
}
|
51 |
|
52 |
+
public function HasPluginShortcutLink()
|
53 |
+
{
|
54 |
return true;
|
55 |
}
|
56 |
|
57 |
+
public function GetTitle()
|
58 |
+
{
|
59 |
return __('Audit Log Viewer', 'wp-security-audit-log');
|
60 |
}
|
61 |
|
62 |
+
public function GetIcon()
|
63 |
+
{
|
64 |
return $this->_wpversion < 3.8
|
65 |
? $this->_plugin->GetBaseUrl() . '/img/logo-main-menu.png'
|
66 |
: 'dashicons-welcome-view-site';
|
67 |
}
|
68 |
|
69 |
+
public function GetName()
|
70 |
+
{
|
71 |
return __('Audit Log Viewer', 'wp-security-audit-log');
|
72 |
}
|
73 |
|
74 |
+
public function GetWeight()
|
75 |
+
{
|
76 |
return 1;
|
77 |
}
|
78 |
|
79 |
+
protected function GetListView()
|
80 |
+
{
|
81 |
if (is_null($this->_listview)) {
|
82 |
$this->_listview = new WSAL_AuditLogListView($this->_plugin);
|
83 |
}
|
84 |
return $this->_listview;
|
85 |
}
|
86 |
|
87 |
+
public function Render()
|
88 |
+
{
|
89 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
90 |
wp_die(__('You do not have sufficient permissions to access this page.', 'wp-security-audit-log'));
|
91 |
}
|
121 |
</script><?php
|
122 |
}
|
123 |
|
124 |
+
public function AjaxInspector()
|
125 |
+
{
|
126 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
127 |
die('Access Denied.');
|
128 |
}
|
147 |
die;
|
148 |
}
|
149 |
|
150 |
+
public function AjaxRefresh()
|
151 |
+
{
|
152 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
153 |
die('Access Denied.');
|
154 |
}
|
160 |
$max = 40; // 40*500msec = 20sec
|
161 |
|
162 |
$is_archive = false;
|
163 |
+
if ($this->_plugin->settings->IsArchivingEnabled()) {
|
164 |
+
$selected_db = get_transient('wsal_wp_selected_db');
|
165 |
+
if ($selected_db && $selected_db == 'archive') {
|
166 |
+
$is_archive = true;
|
167 |
+
}
|
168 |
}
|
169 |
|
170 |
do {
|
181 |
die;
|
182 |
}
|
183 |
|
184 |
+
public function AjaxSetIpp()
|
185 |
+
{
|
186 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
187 |
die('Access Denied.');
|
188 |
}
|
193 |
die;
|
194 |
}
|
195 |
|
196 |
+
public function AjaxSearchSite()
|
197 |
+
{
|
198 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
199 |
die('Access Denied.');
|
200 |
}
|
216 |
die(json_encode(array_slice($grp1 + $grp2, 0, 7)));
|
217 |
}
|
218 |
|
219 |
+
public function AjaxSwitchDB()
|
220 |
+
{
|
221 |
if (isset($_REQUEST['selected_db'])) {
|
222 |
+
set_transient('wsal_wp_selected_db', $_REQUEST['selected_db'], HOUR_IN_SECONDS);
|
|
|
223 |
}
|
224 |
}
|
225 |
|
226 |
+
public function Header()
|
227 |
+
{
|
228 |
add_thickbox();
|
229 |
wp_enqueue_style('darktooltip', $this->_plugin->GetBaseUrl() . '/css/darktooltip.css', array(), '');
|
230 |
wp_enqueue_style(
|
235 |
);
|
236 |
}
|
237 |
|
238 |
+
public function Footer()
|
239 |
+
{
|
240 |
wp_enqueue_script('jquery');
|
241 |
wp_enqueue_script('darktooltip', $this->_plugin->GetBaseUrl() . '/js/jquery.darktooltip.js', array('jquery'), '');
|
242 |
wp_enqueue_script('suggest');
|
classes/Views/EmailNotifications.php
CHANGED
@@ -1,6 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
4 |
|
5 |
public function GetTitle()
|
6 |
{
|
@@ -22,7 +28,8 @@ class WSAL_Views_EmailNotifications extends WSAL_AbstractView {
|
|
22 |
return 7;
|
23 |
}
|
24 |
|
25 |
-
public function Header()
|
|
|
26 |
wp_enqueue_style(
|
27 |
'extensions',
|
28 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Email Notifications Add-On promo Page.
|
6 |
+
* Used only if the plugin is not activated.
|
7 |
+
*/
|
8 |
+
class WSAL_Views_EmailNotifications extends WSAL_AbstractView
|
9 |
+
{
|
10 |
|
11 |
public function GetTitle()
|
12 |
{
|
28 |
return 7;
|
29 |
}
|
30 |
|
31 |
+
public function Header()
|
32 |
+
{
|
33 |
wp_enqueue_style(
|
34 |
'extensions',
|
35 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
classes/Views/Extensions.php
CHANGED
@@ -1,26 +1,35 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
|
|
|
|
|
|
|
|
4 |
class WSAL_Views_Extensions extends WSAL_AbstractView
|
5 |
{
|
6 |
|
7 |
-
public function GetTitle()
|
|
|
8 |
return __('WP Security Audit Log Add-Ons', 'wp-security-audit-log');
|
9 |
}
|
10 |
|
11 |
-
public function GetIcon()
|
|
|
12 |
return 'dashicons-external';
|
13 |
}
|
14 |
|
15 |
-
public function GetName()
|
|
|
16 |
return __(' Add Functionality', 'wp-security-audit-log');
|
17 |
}
|
18 |
|
19 |
-
public function GetWeight()
|
|
|
20 |
return 3.5;
|
21 |
}
|
22 |
|
23 |
-
public function Header()
|
|
|
24 |
wp_enqueue_style(
|
25 |
'extensions',
|
26 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* All Add-Ons promo Page.
|
6 |
+
* Used only if no plugins are activated.
|
7 |
+
*/
|
8 |
class WSAL_Views_Extensions extends WSAL_AbstractView
|
9 |
{
|
10 |
|
11 |
+
public function GetTitle()
|
12 |
+
{
|
13 |
return __('WP Security Audit Log Add-Ons', 'wp-security-audit-log');
|
14 |
}
|
15 |
|
16 |
+
public function GetIcon()
|
17 |
+
{
|
18 |
return 'dashicons-external';
|
19 |
}
|
20 |
|
21 |
+
public function GetName()
|
22 |
+
{
|
23 |
return __(' Add Functionality', 'wp-security-audit-log');
|
24 |
}
|
25 |
|
26 |
+
public function GetWeight()
|
27 |
+
{
|
28 |
return 3.5;
|
29 |
}
|
30 |
|
31 |
+
public function Header()
|
32 |
+
{
|
33 |
wp_enqueue_style(
|
34 |
'extensions',
|
35 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
classes/Views/ExternalDB.php
CHANGED
@@ -1,6 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
4 |
|
5 |
public function GetTitle()
|
6 |
{
|
@@ -22,7 +28,8 @@ class WSAL_Views_ExternalDB extends WSAL_AbstractView {
|
|
22 |
return 10;
|
23 |
}
|
24 |
|
25 |
-
public function Header()
|
|
|
26 |
wp_enqueue_style(
|
27 |
'extensions',
|
28 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* External DB Add-On promo Page.
|
6 |
+
* Used only if the plugin is not activated.
|
7 |
+
*/
|
8 |
+
class WSAL_Views_ExternalDB extends WSAL_AbstractView
|
9 |
+
{
|
10 |
|
11 |
public function GetTitle()
|
12 |
{
|
28 |
return 10;
|
29 |
}
|
30 |
|
31 |
+
public function Header()
|
32 |
+
{
|
33 |
wp_enqueue_style(
|
34 |
'extensions',
|
35 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
classes/Views/Help.php
CHANGED
@@ -1,24 +1,35 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
5 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
6 |
return __('Help', 'wp-security-audit-log');
|
7 |
}
|
8 |
|
9 |
-
public function GetIcon()
|
|
|
10 |
return 'dashicons-sos';
|
11 |
}
|
12 |
|
13 |
-
public function GetName()
|
|
|
14 |
return __('Help', 'wp-security-audit-log');
|
15 |
}
|
16 |
|
17 |
-
public function GetWeight()
|
|
|
18 |
return 5;
|
19 |
}
|
20 |
|
21 |
-
public function Render()
|
|
|
22 |
?><div class="metabox-holder" style="position: relative;">
|
23 |
|
24 |
<div class="postbox" style="margin-right: 270px;">
|
@@ -75,5 +86,4 @@ class WSAL_Views_Help extends WSAL_AbstractView {
|
|
75 |
|
76 |
</div><?php
|
77 |
}
|
78 |
-
|
79 |
-
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Help Page.
|
6 |
+
* - Plugin support
|
7 |
+
* - Plugin Documentation
|
8 |
+
*/
|
9 |
+
class WSAL_Views_Help extends WSAL_AbstractView
|
10 |
+
{
|
11 |
+
public function GetTitle()
|
12 |
+
{
|
13 |
return __('Help', 'wp-security-audit-log');
|
14 |
}
|
15 |
|
16 |
+
public function GetIcon()
|
17 |
+
{
|
18 |
return 'dashicons-sos';
|
19 |
}
|
20 |
|
21 |
+
public function GetName()
|
22 |
+
{
|
23 |
return __('Help', 'wp-security-audit-log');
|
24 |
}
|
25 |
|
26 |
+
public function GetWeight()
|
27 |
+
{
|
28 |
return 5;
|
29 |
}
|
30 |
|
31 |
+
public function Render()
|
32 |
+
{
|
33 |
?><div class="metabox-holder" style="position: relative;">
|
34 |
|
35 |
<div class="postbox" style="margin-right: 270px;">
|
86 |
|
87 |
</div><?php
|
88 |
}
|
89 |
+
}
|
|
classes/Views/Licensing.php
CHANGED
@@ -1,88 +1,100 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
|
6 |
-
|
7 |
-
|
8 |
-
|
9 |
-
|
10 |
-
|
11 |
-
|
12 |
-
|
13 |
-
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
69 |
-
|
70 |
-
<?php if($licenseStatus === 'valid'){ ?>
|
71 |
-
<?php _e('Active', 'wp-security-audit-log'); ?>
|
72 |
-
<?php }else{ ?>
|
73 |
-
<?php _e('Inactive', 'wp-security-audit-log'); ?><br/>
|
74 |
-
<small><?php echo esc_html($licenseErrors); ?></small>
|
75 |
-
<?php } ?>
|
76 |
-
<?php } ?>
|
77 |
-
</td>
|
78 |
-
</tr>
|
79 |
-
<?php } ?>
|
80 |
-
</tbody><tfoot>
|
81 |
-
<tr><th>Plugin</th><th>License</th><th></th></tr>
|
82 |
-
</tfoot>
|
83 |
-
</table>
|
84 |
-
<?php submit_button(); ?>
|
85 |
-
</form><?php
|
86 |
-
}
|
87 |
-
|
88 |
-
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Licensing Page for all the Add-Ons enabled.
|
6 |
+
*/
|
7 |
+
class WSAL_Views_Licensing extends WSAL_AbstractView
|
8 |
+
{
|
9 |
+
public function GetTitle()
|
10 |
+
{
|
11 |
+
return __('Licensing', 'wp-security-audit-log');
|
12 |
+
}
|
13 |
+
|
14 |
+
public function GetIcon()
|
15 |
+
{
|
16 |
+
return 'dashicons-cart';
|
17 |
+
}
|
18 |
+
|
19 |
+
public function GetName()
|
20 |
+
{
|
21 |
+
return __('Licensing', 'wp-security-audit-log');
|
22 |
+
}
|
23 |
+
|
24 |
+
public function GetWeight()
|
25 |
+
{
|
26 |
+
return 4;
|
27 |
+
}
|
28 |
+
|
29 |
+
public function IsAccessible()
|
30 |
+
{
|
31 |
+
return !!$this->_plugin->licensing->CountPlugins();
|
32 |
+
}
|
33 |
|
34 |
+
protected function Save()
|
35 |
+
{
|
36 |
+
$this->_plugin->settings->ClearLicenses();
|
37 |
+
if (isset($_REQUEST['license'])) {
|
38 |
+
foreach ($_REQUEST['license'] as $name => $key) {
|
39 |
+
$this->_plugin->licensing->ActivateLicense($name, $key);
|
40 |
+
}
|
41 |
+
}
|
42 |
+
}
|
43 |
+
|
44 |
+
public function Render()
|
45 |
+
{
|
46 |
+
if (!$this->_plugin->settings->CurrentUserCan('edit')) {
|
47 |
+
wp_die(__('You do not have sufficient permissions to access this page.', 'wp-security-audit-log'));
|
48 |
+
}
|
49 |
+
if (isset($_POST['submit'])) {
|
50 |
+
try {
|
51 |
+
$this->Save();
|
52 |
+
?><div class="updated"><p><?php _e('Settings have been saved.', 'wp-security-audit-log'); ?></p></div><?php
|
53 |
+
} catch (Exception $ex) {
|
54 |
+
?><div class="error"><p><?php _e('Error: ', 'wp-security-audit-log'); ?><?php echo $ex->getMessage(); ?></p></div><?php
|
55 |
+
}
|
56 |
+
}
|
57 |
+
?><form id="audit-log-licensing" method="post">
|
58 |
+
<input type="hidden" name="page" value="<?php echo esc_attr($_REQUEST['page']); ?>" />
|
59 |
+
|
60 |
+
<table class="wp-list-table widefat fixed">
|
61 |
+
<thead>
|
62 |
+
<tr><th>Plugin</th><th>License</th><th></th></tr>
|
63 |
+
</thead><tbody>
|
64 |
+
<?php $counter = 0; ?>
|
65 |
+
<?php foreach ($this->_plugin->licensing->Plugins() as $name => $plugin) { ?>
|
66 |
+
<?php $licenseKey = trim($this->_plugin->settings->GetLicenseKey($name)); ?>
|
67 |
+
<?php $licenseStatus = trim($this->_plugin->settings->GetLicenseStatus($name)); ?>
|
68 |
+
<?php $licenseErrors = trim($this->_plugin->settings->GetLicenseErrors($name)); ?>
|
69 |
+
<tr class="<?php echo ($counter++ % 2 === 0) ? 'alternate' : ''; ?>">
|
70 |
+
<td>
|
71 |
+
<a href="<?php echo esc_attr($plugin['PluginData']['PluginURI']); ?>" target="_blank">
|
72 |
+
<?php echo esc_html($plugin['PluginData']['Name']); ?>
|
73 |
+
</a><br/><small><b>
|
74 |
+
<?php _e('Version', 'wp-security-audit-log'); ?>
|
75 |
+
<?php echo esc_html($plugin['PluginData']['Version']); ?>
|
76 |
+
</b></small>
|
77 |
+
</td><td>
|
78 |
+
<input type="text" style="width: 360px; margin: 6px 0;"
|
79 |
+
name="license[<?php echo esc_attr($name); ?>]"
|
80 |
+
value="<?php echo esc_attr($licenseKey); ?>"/>
|
81 |
+
</td><td style="vertical-align: middle;">
|
82 |
+
<?php if ($licenseKey) { ?>
|
83 |
+
<?php if ($licenseStatus === 'valid') { ?>
|
84 |
+
<?php _e('Active', 'wp-security-audit-log'); ?>
|
85 |
+
<?php } else { ?>
|
86 |
+
<?php _e('Inactive', 'wp-security-audit-log'); ?><br/>
|
87 |
+
<small><?php echo esc_html($licenseErrors); ?></small>
|
88 |
+
<?php } ?>
|
89 |
+
<?php } ?>
|
90 |
+
</td>
|
91 |
+
</tr>
|
92 |
+
<?php } ?>
|
93 |
+
</tbody><tfoot>
|
94 |
+
<tr><th>Plugin</th><th>License</th><th></th></tr>
|
95 |
+
</tfoot>
|
96 |
+
</table>
|
97 |
+
<?php submit_button(); ?>
|
98 |
+
</form><?php
|
99 |
+
}
|
100 |
+
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/Views/LogInUsers.php
CHANGED
@@ -1,7 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
public function GetTitle()
|
6 |
{
|
7 |
return __('User Sessions Management Add-On', 'wp-security-audit-log');
|
@@ -22,7 +27,8 @@ class WSAL_Views_LogInUsers extends WSAL_AbstractView {
|
|
22 |
return 8;
|
23 |
}
|
24 |
|
25 |
-
public function Header()
|
|
|
26 |
wp_enqueue_style(
|
27 |
'extensions',
|
28 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* User Sessions Management Add-On promo Page.
|
6 |
+
* Used only if the plugin is not activated.
|
7 |
+
*/
|
8 |
+
class WSAL_Views_LogInUsers extends WSAL_AbstractView
|
9 |
+
{
|
10 |
public function GetTitle()
|
11 |
{
|
12 |
return __('User Sessions Management Add-On', 'wp-security-audit-log');
|
27 |
return 8;
|
28 |
}
|
29 |
|
30 |
+
public function Header()
|
31 |
+
{
|
32 |
wp_enqueue_style(
|
33 |
'extensions',
|
34 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
classes/Views/Reports.php
CHANGED
@@ -1,7 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
public function GetTitle()
|
6 |
{
|
7 |
return __('Reports Add-On', 'wp-security-audit-log');
|
@@ -22,7 +27,8 @@ class WSAL_Views_Reports extends WSAL_AbstractView {
|
|
22 |
return 9;
|
23 |
}
|
24 |
|
25 |
-
public function Header()
|
|
|
26 |
wp_enqueue_style(
|
27 |
'extensions',
|
28 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Reports Add-On promo Page.
|
6 |
+
* Used only if the plugin is not activated.
|
7 |
+
*/
|
8 |
+
class WSAL_Views_Reports extends WSAL_AbstractView
|
9 |
+
{
|
10 |
public function GetTitle()
|
11 |
{
|
12 |
return __('Reports Add-On', 'wp-security-audit-log');
|
27 |
return 9;
|
28 |
}
|
29 |
|
30 |
+
public function Header()
|
31 |
+
{
|
32 |
wp_enqueue_style(
|
33 |
'extensions',
|
34 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
classes/Views/Search.php
CHANGED
@@ -1,7 +1,12 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
|
4 |
-
|
|
|
|
|
|
|
|
|
|
|
5 |
public function GetTitle()
|
6 |
{
|
7 |
return __('Search Add-On', 'wp-security-audit-log');
|
@@ -22,7 +27,8 @@ class WSAL_Views_Search extends WSAL_AbstractView {
|
|
22 |
return 9;
|
23 |
}
|
24 |
|
25 |
-
public function Header()
|
|
|
26 |
wp_enqueue_style(
|
27 |
'extensions',
|
28 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Search Add-On promo Page.
|
6 |
+
* Used only if the plugin is not activated.
|
7 |
+
*/
|
8 |
+
class WSAL_Views_Search extends WSAL_AbstractView
|
9 |
+
{
|
10 |
public function GetTitle()
|
11 |
{
|
12 |
return __('Search Add-On', 'wp-security-audit-log');
|
27 |
return 9;
|
28 |
}
|
29 |
|
30 |
+
public function Header()
|
31 |
+
{
|
32 |
wp_enqueue_style(
|
33 |
'extensions',
|
34 |
$this->_plugin->GetBaseUrl() . '/css/extensions.css',
|
classes/Views/Settings.php
CHANGED
@@ -1,9 +1,13 @@
|
|
1 |
<?php
|
|
|
|
|
|
|
|
|
|
|
2 |
class WSAL_Views_Settings extends WSAL_AbstractView
|
3 |
{
|
4 |
-
|
5 |
public $adapterMsg = '';
|
6 |
-
|
7 |
public function __construct(WpSecurityAuditLog $plugin)
|
8 |
{
|
9 |
parent::__construct($plugin);
|
@@ -13,38 +17,49 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
13 |
add_action('wp_ajax_AjaxGetAllUsers', array($this, 'AjaxGetAllUsers'));
|
14 |
add_action('wp_ajax_AjaxGetAllRoles', array($this, 'AjaxGetAllRoles'));
|
15 |
}
|
16 |
-
|
17 |
-
public function HasPluginShortcutLink()
|
|
|
18 |
return true;
|
19 |
}
|
20 |
-
|
21 |
-
public function GetTitle()
|
|
|
22 |
return __('Settings', 'wp-security-audit-log');
|
23 |
}
|
24 |
-
|
25 |
-
public function GetIcon()
|
|
|
26 |
return 'dashicons-admin-generic';
|
27 |
}
|
28 |
-
|
29 |
-
public function GetName()
|
|
|
30 |
return __('Settings', 'wp-security-audit-log');
|
31 |
}
|
32 |
-
|
33 |
-
public function GetWeight()
|
|
|
34 |
return 3;
|
35 |
}
|
36 |
-
|
37 |
-
protected function GetTokenType($token)
|
|
|
38 |
$users = array();
|
39 |
-
foreach (get_users('blog_id=0&fields[]=user_login') as $obj)
|
40 |
$users[] = $obj->user_login;
|
|
|
41 |
$roles = array_keys(get_editable_roles());
|
42 |
-
|
43 |
-
if(in_array($token, $users))
|
44 |
-
|
|
|
|
|
|
|
|
|
45 |
return 'other';
|
46 |
}
|
47 |
-
|
48 |
protected function Save()
|
49 |
{
|
50 |
check_admin_referer('wsal-settings');
|
@@ -84,27 +99,29 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
84 |
$this->_plugin->settings->SetDevOptionEnabled($opt, true);
|
85 |
}
|
86 |
}
|
87 |
-
$this->_plugin->settings->Set404LogLimit($_REQUEST['404Limit']);
|
88 |
}
|
89 |
-
|
90 |
public function AjaxCheckSecurityToken()
|
91 |
{
|
92 |
-
if (!$this->_plugin->settings->CurrentUserCan('view'))
|
93 |
die('Access Denied.');
|
94 |
-
|
|
|
95 |
die('Token parameter expected.');
|
|
|
96 |
die($this->GetTokenType($_REQUEST['token']));
|
97 |
}
|
98 |
-
|
99 |
public function AjaxRunCleanup()
|
100 |
{
|
101 |
-
if (!$this->_plugin->settings->CurrentUserCan('view'))
|
102 |
die('Access Denied.');
|
|
|
103 |
$this->_plugin->CleanUp();
|
104 |
wp_redirect($this->GetUrl());
|
105 |
exit;
|
106 |
}
|
107 |
-
|
108 |
public function Render()
|
109 |
{
|
110 |
if (!$this->_plugin->settings->CurrentUserCan('edit')) {
|
@@ -131,7 +148,7 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
131 |
<input type="hidden" name="page" value="<?php echo esc_attr($_REQUEST['page']); ?>" />
|
132 |
<input type="hidden" id="ajaxurl" value="<?php echo esc_attr(admin_url('admin-ajax.php')); ?>" />
|
133 |
<?php wp_nonce_field('wsal-settings'); ?>
|
134 |
-
|
135 |
<div id="audit-log-adverts">
|
136 |
</div>
|
137 |
<div class="nav-tabs">
|
@@ -203,7 +220,7 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
203 |
?>/> <?php _e('Filter Internal IP Addresses', 'wp-security-audit-log'); ?>
|
204 |
</label>
|
205 |
<br/>
|
206 |
-
<span class="description"><?php _e('Enable this option to filter internal IP addresses from the proxy headers.', 'wp-security-audit-log'); ?></span>
|
207 |
</fieldset>
|
208 |
</td>
|
209 |
</tr>
|
@@ -512,19 +529,6 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
512 |
</fieldset>
|
513 |
</td>
|
514 |
</tr>
|
515 |
-
<!-- Number of 404 Requests to Log -->
|
516 |
-
<tr>
|
517 |
-
<th><label for="404Limit"><?php _e('Number of 404 Requests to Log', 'wp-security-audit-log'); ?></label></th>
|
518 |
-
<td>
|
519 |
-
<fieldset>
|
520 |
-
<input type="number" id="404Limit" name="404Limit" value="<?php echo $this->_plugin->settings->Get404LogLimit(); ?>" />
|
521 |
-
</fieldset>
|
522 |
-
<p class="description">
|
523 |
-
<?php _e('By default the plugin keeps up to 99 requests to non-existing pages from the same IP address. Increase the value in this setting to the desired amount to keep a log of more or less requests.', 'wp-security-audit-log'); ?><br />
|
524 |
-
<?php _e('Note that by increasing this value to a high number, should your website be scanned the plugin will consume more resources to log all the requests.', 'wp-security-audit-log'); ?>
|
525 |
-
</p>
|
526 |
-
</td>
|
527 |
-
</tr>
|
528 |
</tbody>
|
529 |
</table>
|
530 |
<!-- Third tab -->
|
@@ -642,11 +646,11 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
642 |
{
|
643 |
if ( window.confirm('Do you want remove all data when the plugin is deleted?') == false )
|
644 |
elementRef.checked = false;
|
645 |
-
}
|
646 |
}
|
647 |
|
648 |
jQuery(document).ready(function() {
|
649 |
-
var statusConfig = <?php
|
650 |
var logging_status = jQuery('#logging_status');
|
651 |
var txtNot = jQuery('#logging_status_text');
|
652 |
|
@@ -663,14 +667,14 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
663 |
}
|
664 |
wsalUpdateLoggingStatus(logging_status, txtNot);
|
665 |
|
666 |
-
logging_status.on('change', function() {
|
667 |
-
wsalUpdateLoggingStatus(logging_status, txtNot);
|
668 |
});
|
669 |
});
|
670 |
// -->
|
671 |
</script><?php
|
672 |
}
|
673 |
-
|
674 |
public function Header()
|
675 |
{
|
676 |
wp_enqueue_style(
|
@@ -691,7 +695,7 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
691 |
}
|
692 |
</style><?php
|
693 |
}
|
694 |
-
|
695 |
public function Footer()
|
696 |
{
|
697 |
wp_enqueue_script(
|
@@ -722,13 +726,13 @@ class WSAL_Views_Settings extends WSAL_AbstractView
|
|
722 |
if(this.checked) notChecked = 0;
|
723 |
})
|
724 |
if(notChecked == 1){
|
725 |
-
alert("You have to select at least one column!");
|
726 |
}
|
727 |
});
|
728 |
});
|
729 |
</script><?php
|
730 |
}
|
731 |
-
|
732 |
public function AjaxGetAllUsers()
|
733 |
{
|
734 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Settings Page.
|
6 |
+
*/
|
7 |
class WSAL_Views_Settings extends WSAL_AbstractView
|
8 |
{
|
|
|
9 |
public $adapterMsg = '';
|
10 |
+
|
11 |
public function __construct(WpSecurityAuditLog $plugin)
|
12 |
{
|
13 |
parent::__construct($plugin);
|
17 |
add_action('wp_ajax_AjaxGetAllUsers', array($this, 'AjaxGetAllUsers'));
|
18 |
add_action('wp_ajax_AjaxGetAllRoles', array($this, 'AjaxGetAllRoles'));
|
19 |
}
|
20 |
+
|
21 |
+
public function HasPluginShortcutLink()
|
22 |
+
{
|
23 |
return true;
|
24 |
}
|
25 |
+
|
26 |
+
public function GetTitle()
|
27 |
+
{
|
28 |
return __('Settings', 'wp-security-audit-log');
|
29 |
}
|
30 |
+
|
31 |
+
public function GetIcon()
|
32 |
+
{
|
33 |
return 'dashicons-admin-generic';
|
34 |
}
|
35 |
+
|
36 |
+
public function GetName()
|
37 |
+
{
|
38 |
return __('Settings', 'wp-security-audit-log');
|
39 |
}
|
40 |
+
|
41 |
+
public function GetWeight()
|
42 |
+
{
|
43 |
return 3;
|
44 |
}
|
45 |
+
|
46 |
+
protected function GetTokenType($token)
|
47 |
+
{
|
48 |
$users = array();
|
49 |
+
foreach (get_users('blog_id=0&fields[]=user_login') as $obj) {
|
50 |
$users[] = $obj->user_login;
|
51 |
+
}
|
52 |
$roles = array_keys(get_editable_roles());
|
53 |
+
|
54 |
+
if (in_array($token, $users)) {
|
55 |
+
return 'user';
|
56 |
+
}
|
57 |
+
if (in_array($token, $roles)) {
|
58 |
+
return 'role';
|
59 |
+
}
|
60 |
return 'other';
|
61 |
}
|
62 |
+
|
63 |
protected function Save()
|
64 |
{
|
65 |
check_admin_referer('wsal-settings');
|
99 |
$this->_plugin->settings->SetDevOptionEnabled($opt, true);
|
100 |
}
|
101 |
}
|
|
|
102 |
}
|
103 |
+
|
104 |
public function AjaxCheckSecurityToken()
|
105 |
{
|
106 |
+
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
107 |
die('Access Denied.');
|
108 |
+
}
|
109 |
+
if (!isset($_REQUEST['token'])) {
|
110 |
die('Token parameter expected.');
|
111 |
+
}
|
112 |
die($this->GetTokenType($_REQUEST['token']));
|
113 |
}
|
114 |
+
|
115 |
public function AjaxRunCleanup()
|
116 |
{
|
117 |
+
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
118 |
die('Access Denied.');
|
119 |
+
}
|
120 |
$this->_plugin->CleanUp();
|
121 |
wp_redirect($this->GetUrl());
|
122 |
exit;
|
123 |
}
|
124 |
+
|
125 |
public function Render()
|
126 |
{
|
127 |
if (!$this->_plugin->settings->CurrentUserCan('edit')) {
|
148 |
<input type="hidden" name="page" value="<?php echo esc_attr($_REQUEST['page']); ?>" />
|
149 |
<input type="hidden" id="ajaxurl" value="<?php echo esc_attr(admin_url('admin-ajax.php')); ?>" />
|
150 |
<?php wp_nonce_field('wsal-settings'); ?>
|
151 |
+
|
152 |
<div id="audit-log-adverts">
|
153 |
</div>
|
154 |
<div class="nav-tabs">
|
220 |
?>/> <?php _e('Filter Internal IP Addresses', 'wp-security-audit-log'); ?>
|
221 |
</label>
|
222 |
<br/>
|
223 |
+
<span class="description"><?php _e('Enable this option to filter internal IP addresses from the proxy headers.', 'wp-security-audit-log'); ?></span>
|
224 |
</fieldset>
|
225 |
</td>
|
226 |
</tr>
|
529 |
</fieldset>
|
530 |
</td>
|
531 |
</tr>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
532 |
</tbody>
|
533 |
</table>
|
534 |
<!-- Third tab -->
|
646 |
{
|
647 |
if ( window.confirm('Do you want remove all data when the plugin is deleted?') == false )
|
648 |
elementRef.checked = false;
|
649 |
+
}
|
650 |
}
|
651 |
|
652 |
jQuery(document).ready(function() {
|
653 |
+
var statusConfig = <?php if ($this->_plugin->settings->IsLoggingDisabled()) { echo 1; } else { echo 0; } ?>;
|
654 |
var logging_status = jQuery('#logging_status');
|
655 |
var txtNot = jQuery('#logging_status_text');
|
656 |
|
667 |
}
|
668 |
wsalUpdateLoggingStatus(logging_status, txtNot);
|
669 |
|
670 |
+
logging_status.on('change', function() {
|
671 |
+
wsalUpdateLoggingStatus(logging_status, txtNot);
|
672 |
});
|
673 |
});
|
674 |
// -->
|
675 |
</script><?php
|
676 |
}
|
677 |
+
|
678 |
public function Header()
|
679 |
{
|
680 |
wp_enqueue_style(
|
695 |
}
|
696 |
</style><?php
|
697 |
}
|
698 |
+
|
699 |
public function Footer()
|
700 |
{
|
701 |
wp_enqueue_script(
|
726 |
if(this.checked) notChecked = 0;
|
727 |
})
|
728 |
if(notChecked == 1){
|
729 |
+
alert("You have to select at least one column!");
|
730 |
}
|
731 |
});
|
732 |
});
|
733 |
</script><?php
|
734 |
}
|
735 |
+
|
736 |
public function AjaxGetAllUsers()
|
737 |
{
|
738 |
if (!$this->_plugin->settings->CurrentUserCan('view')) {
|
classes/Views/ToggleAlerts.php
CHANGED
@@ -1,29 +1,38 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
3 |
{
|
4 |
-
|
5 |
-
|
6 |
return __('Enable/Disable Alerts', 'wp-security-audit-log');
|
7 |
}
|
8 |
-
|
9 |
-
public function GetIcon()
|
|
|
10 |
return 'dashicons-forms';
|
11 |
}
|
12 |
-
|
13 |
-
public function GetName()
|
|
|
14 |
return __('Enable/Disable Alerts', 'wp-security-audit-log');
|
15 |
}
|
16 |
-
|
17 |
-
public function GetWeight()
|
|
|
18 |
return 2;
|
19 |
}
|
20 |
-
|
21 |
-
protected function GetSafeCatgName($name)
|
|
|
22 |
return strtolower(
|
23 |
preg_replace('/[^A-Za-z0-9\-]/', '-', $name)
|
24 |
);
|
25 |
}
|
26 |
-
|
27 |
public function Render()
|
28 |
{
|
29 |
if (!$this->_plugin->settings->CurrentUserCan('edit')) {
|
@@ -38,9 +47,11 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
38 |
try {
|
39 |
$enabled = array_map('intval', $_POST['alert']);
|
40 |
$disabled = array();
|
41 |
-
foreach ($this->_plugin->alerts->GetAlerts() as $alert)
|
42 |
-
if (!in_array($alert->type, $enabled))
|
43 |
$disabled[] = $alert->type;
|
|
|
|
|
44 |
$this->_plugin->alerts->SetDisabledAlerts($disabled);
|
45 |
?><div class="updated"><p><?php _e('Settings have been saved.', 'wp-security-audit-log'); ?></p></div><?php
|
46 |
} catch (Exception $ex) {
|
@@ -48,6 +59,12 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
48 |
}
|
49 |
$this->_plugin->SetGlobalOption('log-404', isset($_REQUEST['log_404']) ? 'on' : 'off');
|
50 |
$this->_plugin->SetGlobalOption('purge-404-log', isset($_REQUEST['purge_log']) ? 'on' : 'off');
|
|
|
|
|
|
|
|
|
|
|
|
|
51 |
}
|
52 |
?><h2 id="wsal-tabs" class="nav-tab-wrapper"><?php
|
53 |
foreach ($safeNames as $name => $safe) {
|
@@ -57,7 +74,7 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
57 |
<form id="audit-log-viewer" method="post">
|
58 |
<input type="hidden" name="page" value="<?php echo esc_attr($_REQUEST['page']); ?>" />
|
59 |
<?php wp_nonce_field('wsal-togglealerts'); ?>
|
60 |
-
|
61 |
<div class="nav-tabs"><?php
|
62 |
foreach ($groupedAlerts as $name => $group) { ?>
|
63 |
<div class="wsal-tab" id="tab-<?php echo $safeNames[$name]; ?>">
|
@@ -74,10 +91,16 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
74 |
$active = array();
|
75 |
$allactive = true;
|
76 |
foreach ($alerts as $alert) {
|
77 |
-
if ($alert->type <= 0006)
|
78 |
-
|
|
|
|
|
|
|
|
|
79 |
$active[$alert->type] = $this->_plugin->alerts->IsEnabled($alert->type);
|
80 |
-
if (!$active[$alert->type])
|
|
|
|
|
81 |
}
|
82 |
?><table class="wp-list-table wsal-tab widefat fixed wsal-sub-tab" cellspacing="0" id="tab-<?php echo $this->GetSafeCatgName($subname); ?>">
|
83 |
<thead>
|
@@ -90,8 +113,12 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
90 |
</thead>
|
91 |
<tbody><?php
|
92 |
foreach ($alerts as $alert) {
|
93 |
-
if ($alert->type <= 0006)
|
94 |
-
|
|
|
|
|
|
|
|
|
95 |
$attrs = '';
|
96 |
switch (true) {
|
97 |
case !$alert->mesg:
|
@@ -119,10 +146,51 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
119 |
<td></td>
|
120 |
<td><input name="purge_log" type="checkbox" class="check_log" value="1" <?php if ($purge_log == 'on') echo 'checked="checked"'; ?>></td>
|
121 |
<td colspan="2"><?php _e('Purge log files older than one month', 'wp-security-audit-log'); ?></td>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
122 |
</tr><?php
|
123 |
}
|
124 |
}
|
125 |
-
|
|
|
126 |
</table><?php
|
127 |
}
|
128 |
?>
|
@@ -132,7 +200,7 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
132 |
<p class="submit"><input type="submit" name="submit" id="submit" class="button button-primary" value="<?php echo esc_attr(__('Save Changes', 'wp-security-audit-log')); ?>"></p>
|
133 |
</form><?php
|
134 |
}
|
135 |
-
|
136 |
public function Header()
|
137 |
{
|
138 |
?><style type="text/css">
|
@@ -152,9 +220,13 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
152 |
background-color: #fff;
|
153 |
border-bottom: 1px solid #fff;
|
154 |
}
|
|
|
|
|
|
|
|
|
155 |
</style><?php
|
156 |
}
|
157 |
-
|
158 |
public function Footer()
|
159 |
{
|
160 |
?><script type="text/javascript">
|
@@ -187,7 +259,7 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
187 |
var allchecked = jQuery(this).parents('tbody:first').find('th>:checkbox:not(:checked)').length === 0;
|
188 |
jQuery(this).parents('table:first').find('thead>tr>th:first>:checkbox:first').attr('checked', allchecked);
|
189 |
});
|
190 |
-
|
191 |
var hashlink = jQuery('#wsal-tabs>a[href="' + location.hash + '"]');
|
192 |
var hashsublink = jQuery('.wsal-sub-tabs>a[href="' + location.hash + '"]');
|
193 |
if (hashlink.length) {
|
@@ -201,7 +273,7 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
201 |
jQuery('#wsal-tabs>a:first').click();
|
202 |
jQuery('.wsal-sub-tabs>a:first').click();
|
203 |
}
|
204 |
-
|
205 |
// Specific for alert 6007
|
206 |
jQuery("input[value=6007]").on("change", function(){
|
207 |
var check = jQuery("input[value=6007]").is(":checked");
|
@@ -210,7 +282,17 @@ class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
|
210 |
} else {
|
211 |
jQuery(".check_log").removeAttr('checked');
|
212 |
}
|
213 |
-
});
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
214 |
});
|
215 |
</script><?php
|
216 |
}
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Enable/Disable Alerts Page.
|
6 |
+
*/
|
7 |
+
class WSAL_Views_ToggleAlerts extends WSAL_AbstractView
|
8 |
{
|
9 |
+
public function GetTitle()
|
10 |
+
{
|
11 |
return __('Enable/Disable Alerts', 'wp-security-audit-log');
|
12 |
}
|
13 |
+
|
14 |
+
public function GetIcon()
|
15 |
+
{
|
16 |
return 'dashicons-forms';
|
17 |
}
|
18 |
+
|
19 |
+
public function GetName()
|
20 |
+
{
|
21 |
return __('Enable/Disable Alerts', 'wp-security-audit-log');
|
22 |
}
|
23 |
+
|
24 |
+
public function GetWeight()
|
25 |
+
{
|
26 |
return 2;
|
27 |
}
|
28 |
+
|
29 |
+
protected function GetSafeCatgName($name)
|
30 |
+
{
|
31 |
return strtolower(
|
32 |
preg_replace('/[^A-Za-z0-9\-]/', '-', $name)
|
33 |
);
|
34 |
}
|
35 |
+
|
36 |
public function Render()
|
37 |
{
|
38 |
if (!$this->_plugin->settings->CurrentUserCan('edit')) {
|
47 |
try {
|
48 |
$enabled = array_map('intval', $_POST['alert']);
|
49 |
$disabled = array();
|
50 |
+
foreach ($this->_plugin->alerts->GetAlerts() as $alert) {
|
51 |
+
if (!in_array($alert->type, $enabled)) {
|
52 |
$disabled[] = $alert->type;
|
53 |
+
}
|
54 |
+
}
|
55 |
$this->_plugin->alerts->SetDisabledAlerts($disabled);
|
56 |
?><div class="updated"><p><?php _e('Settings have been saved.', 'wp-security-audit-log'); ?></p></div><?php
|
57 |
} catch (Exception $ex) {
|
59 |
}
|
60 |
$this->_plugin->SetGlobalOption('log-404', isset($_REQUEST['log_404']) ? 'on' : 'off');
|
61 |
$this->_plugin->SetGlobalOption('purge-404-log', isset($_REQUEST['purge_log']) ? 'on' : 'off');
|
62 |
+
|
63 |
+
$this->_plugin->SetGlobalOption( 'log-visitor-404', isset( $_REQUEST['log_visitor_404'] ) ? 'on' : 'off' );
|
64 |
+
$this->_plugin->SetGlobalOption( 'purge-visitor-404-log', isset( $_REQUEST['purge_visitor_log'] ) ? 'on' : 'off' );
|
65 |
+
|
66 |
+
$this->_plugin->settings->Set404LogLimit( $_REQUEST['user_404Limit'] );
|
67 |
+
$this->_plugin->settings->SetVisitor404LogLimit( $_REQUEST['visitor_404Limit'] );
|
68 |
}
|
69 |
?><h2 id="wsal-tabs" class="nav-tab-wrapper"><?php
|
70 |
foreach ($safeNames as $name => $safe) {
|
74 |
<form id="audit-log-viewer" method="post">
|
75 |
<input type="hidden" name="page" value="<?php echo esc_attr($_REQUEST['page']); ?>" />
|
76 |
<?php wp_nonce_field('wsal-togglealerts'); ?>
|
77 |
+
|
78 |
<div class="nav-tabs"><?php
|
79 |
foreach ($groupedAlerts as $name => $group) { ?>
|
80 |
<div class="wsal-tab" id="tab-<?php echo $safeNames[$name]; ?>">
|
91 |
$active = array();
|
92 |
$allactive = true;
|
93 |
foreach ($alerts as $alert) {
|
94 |
+
if ($alert->type <= 0006) {
|
95 |
+
continue; // <- ignore php alerts
|
96 |
+
}
|
97 |
+
if ($alert->type == 9999) {
|
98 |
+
continue; // <- ignore promo alerts
|
99 |
+
}
|
100 |
$active[$alert->type] = $this->_plugin->alerts->IsEnabled($alert->type);
|
101 |
+
if (!$active[$alert->type]) {
|
102 |
+
$allactive = false;
|
103 |
+
}
|
104 |
}
|
105 |
?><table class="wp-list-table wsal-tab widefat fixed wsal-sub-tab" cellspacing="0" id="tab-<?php echo $this->GetSafeCatgName($subname); ?>">
|
106 |
<thead>
|
113 |
</thead>
|
114 |
<tbody><?php
|
115 |
foreach ($alerts as $alert) {
|
116 |
+
if ($alert->type <= 0006) {
|
117 |
+
continue; // <- ignore php alerts
|
118 |
+
}
|
119 |
+
if ($alert->type == 9999) {
|
120 |
+
continue; // <- ignore promo alerts
|
121 |
+
}
|
122 |
$attrs = '';
|
123 |
switch (true) {
|
124 |
case !$alert->mesg:
|
146 |
<td></td>
|
147 |
<td><input name="purge_log" type="checkbox" class="check_log" value="1" <?php if ($purge_log == 'on') echo 'checked="checked"'; ?>></td>
|
148 |
<td colspan="2"><?php _e('Purge log files older than one month', 'wp-security-audit-log'); ?></td>
|
149 |
+
</tr>
|
150 |
+
<tr>
|
151 |
+
<td></td>
|
152 |
+
<td colspan="1"><input type="number" id="user_404Limit" name="user_404Limit" value="<?php echo $this->_plugin->settings->Get404LogLimit(); ?>" /></td>
|
153 |
+
<td colspan="2"><?php esc_html_e( 'Number of 404 Requests to Log', 'wp-security-audit-log' ); ?></td>
|
154 |
+
</tr>
|
155 |
+
<tr>
|
156 |
+
<td></td>
|
157 |
+
<td></td>
|
158 |
+
<td colspan="2">
|
159 |
+
<?php esc_html_e( 'By default the plugin keeps up to 99 requests to non-existing pages from the same IP address. Increase the value in this setting to the desired amount to keep a log of more or less requests.', 'wp-security-audit-log' ); ?><br />
|
160 |
+
<?php esc_html_e( 'Note that by increasing this value to a high number, should your website be scanned the plugin will consume more resources to log all the requests.', 'wp-security-audit-log' ); ?>
|
161 |
+
</td>
|
162 |
+
</tr><?php
|
163 |
+
}
|
164 |
+
if ( 6023 == $alert->type ) {
|
165 |
+
$log_visitor_404 = $this->_plugin->GetGlobalOption( 'log-visitor-404' );
|
166 |
+
$purge_visitor_log = $this->_plugin->GetGlobalOption( 'purge-visitor-404-log' );
|
167 |
+
?><tr>
|
168 |
+
<td></td>
|
169 |
+
<td><input name="log_visitor_404" type="checkbox" class="check_visitor_log" value="1" <?php if ( 'on' == $log_visitor_404 ) echo 'checked="checked"'; ?>></td>
|
170 |
+
<td colspan="2"><?php esc_html_e( 'Capture 404 requests to file (the log file are created in the /wp-content/uploads/wp-security-audit-log/404s/ directory)', 'wp-security-audit-log' ); ?></td>
|
171 |
+
</tr>
|
172 |
+
<tr>
|
173 |
+
<td></td>
|
174 |
+
<td><input name="purge_visitor_log" type="checkbox" class="check_visitor_log" value="1" <?php if ( 'on' == $purge_visitor_log ) echo 'checked="checked"'; ?>></td>
|
175 |
+
<td colspan="2"><?php esc_html_e( 'Purge log files older than one month', 'wp-security-audit-log' ); ?></td>
|
176 |
+
</tr>
|
177 |
+
<tr>
|
178 |
+
<td></td>
|
179 |
+
<td colspan="1"><input type="number" id="visitor_404Limit" name="visitor_404Limit" value="<?php echo esc_attr( $this->_plugin->settings->GetVisitor404LogLimit() ); ?>" /></td>
|
180 |
+
<td colspan="2"><?php esc_html_e( 'Number of 404 Requests to Log', 'wp-security-audit-log' ); ?></td>
|
181 |
+
</tr>
|
182 |
+
<tr>
|
183 |
+
<td></td>
|
184 |
+
<td></td>
|
185 |
+
<td colspan="2">
|
186 |
+
<?php esc_html_e( 'By default the plugin keeps up to 99 requests to non-existing pages from the same IP address. Increase the value in this setting to the desired amount to keep a log of more or less requests.', 'wp-security-audit-log' ); ?><br />
|
187 |
+
<?php esc_html_e( 'Note that by increasing this value to a high number, should your website be scanned the plugin will consume more resources to log all the requests.', 'wp-security-audit-log' ); ?>
|
188 |
+
</td>
|
189 |
</tr><?php
|
190 |
}
|
191 |
}
|
192 |
+
?>
|
193 |
+
</tbody>
|
194 |
</table><?php
|
195 |
}
|
196 |
?>
|
200 |
<p class="submit"><input type="submit" name="submit" id="submit" class="button button-primary" value="<?php echo esc_attr(__('Save Changes', 'wp-security-audit-log')); ?>"></p>
|
201 |
</form><?php
|
202 |
}
|
203 |
+
|
204 |
public function Header()
|
205 |
{
|
206 |
?><style type="text/css">
|
220 |
background-color: #fff;
|
221 |
border-bottom: 1px solid #fff;
|
222 |
}
|
223 |
+
#user_404Limit,
|
224 |
+
#visitor_404Limit {
|
225 |
+
width: 100%;
|
226 |
+
}
|
227 |
</style><?php
|
228 |
}
|
229 |
+
|
230 |
public function Footer()
|
231 |
{
|
232 |
?><script type="text/javascript">
|
259 |
var allchecked = jQuery(this).parents('tbody:first').find('th>:checkbox:not(:checked)').length === 0;
|
260 |
jQuery(this).parents('table:first').find('thead>tr>th:first>:checkbox:first').attr('checked', allchecked);
|
261 |
});
|
262 |
+
|
263 |
var hashlink = jQuery('#wsal-tabs>a[href="' + location.hash + '"]');
|
264 |
var hashsublink = jQuery('.wsal-sub-tabs>a[href="' + location.hash + '"]');
|
265 |
if (hashlink.length) {
|
273 |
jQuery('#wsal-tabs>a:first').click();
|
274 |
jQuery('.wsal-sub-tabs>a:first').click();
|
275 |
}
|
276 |
+
|
277 |
// Specific for alert 6007
|
278 |
jQuery("input[value=6007]").on("change", function(){
|
279 |
var check = jQuery("input[value=6007]").is(":checked");
|
282 |
} else {
|
283 |
jQuery(".check_log").removeAttr('checked');
|
284 |
}
|
285 |
+
});
|
286 |
+
|
287 |
+
// Specific for alert 6023
|
288 |
+
jQuery("input[value=6023]").on("change", function(){
|
289 |
+
var check = jQuery("input[value=6023]").is(":checked");
|
290 |
+
if(check) {
|
291 |
+
jQuery(".check_visitor_log").attr ( "checked" ,"checked" );
|
292 |
+
} else {
|
293 |
+
jQuery(".check_visitor_log").removeAttr('checked');
|
294 |
+
}
|
295 |
+
});
|
296 |
});
|
297 |
</script><?php
|
298 |
}
|
classes/WidgetManager.php
CHANGED
@@ -1,5 +1,9 @@
|
|
1 |
<?php
|
2 |
-
|
|
|
|
|
|
|
|
|
3 |
class WSAL_WidgetManager
|
4 |
{
|
5 |
/**
|
1 |
<?php
|
2 |
+
/**
|
3 |
+
* @package Wsal
|
4 |
+
*
|
5 |
+
* Plugin Widget used in the Wordpress Dashboard.
|
6 |
+
*/
|
7 |
class WSAL_WidgetManager
|
8 |
{
|
9 |
/**
|
defaults.php
CHANGED
@@ -223,6 +223,7 @@ function wsaldefaults_wsal_init(WpSecurityAuditLog $wsal)
|
|
223 |
array(6004, E_CRITICAL, __('WordPress was updated', 'wp-security-audit-log'), __('Updated WordPress from version %OldVersion% to %NewVersion%.', 'wp-security-audit-log')),
|
224 |
array(6005, E_CRITICAL, __('User changes the WordPress Permalinks', 'wp-security-audit-log'), __('Changed the WordPress permalinks from %OldPattern% to %NewPattern%.', 'wp-security-audit-log')),
|
225 |
array(6007, E_CRITICAL, __('User requests non-existing pages (404 Error Pages)', 'wp-security-audit-log'), __('Has requested a non existing page (404 Error Pages) %Attempts% %Msg%. %LinkFile%.', 'wp-security-audit-log')),
|
|
|
226 |
array(9999, E_CRITICAL, __('Advertising Add-ons.', 'wp-security-audit-log'), __('%PromoName% %PromoMessage%', 'wp-security-audit-log'))
|
227 |
),
|
228 |
__('Menus', 'wp-security-audit-log') => array(
|
@@ -266,6 +267,7 @@ function wsaldefaults_wsal_init(WpSecurityAuditLog $wsal)
|
|
266 |
array(1004, E_WARNING, __('Login blocked', 'wp-security-audit-log'), __('Blocked from logging in because the same WordPress user is logged in from %ClientIP%.', 'wp-security-audit-log')),
|
267 |
array(1005, E_WARNING, __('User logged in with existing session(s)', 'wp-security-audit-log'), __('Successfully logged in. Another session from %IPAddress% for this user already exist.', 'wp-security-audit-log')),
|
268 |
array(1006, E_CRITICAL, __('User logged out all other sessions with the same username', 'wp-security-audit-log'), __('Logged out all other sessions with the same username.', 'wp-security-audit-log')),
|
|
|
269 |
array(2010, E_NOTICE, __('User uploaded file from Uploads directory', 'wp-security-audit-log'), __('Uploaded the file %FileName% in %FilePath%.', 'wp-security-audit-log')),
|
270 |
array(2011, E_WARNING, __('User deleted file from Uploads directory', 'wp-security-audit-log'), __('Deleted the file %FileName% from %FilePath%.', 'wp-security-audit-log'))
|
271 |
),
|
223 |
array(6004, E_CRITICAL, __('WordPress was updated', 'wp-security-audit-log'), __('Updated WordPress from version %OldVersion% to %NewVersion%.', 'wp-security-audit-log')),
|
224 |
array(6005, E_CRITICAL, __('User changes the WordPress Permalinks', 'wp-security-audit-log'), __('Changed the WordPress permalinks from %OldPattern% to %NewPattern%.', 'wp-security-audit-log')),
|
225 |
array(6007, E_CRITICAL, __('User requests non-existing pages (404 Error Pages)', 'wp-security-audit-log'), __('Has requested a non existing page (404 Error Pages) %Attempts% %Msg%. %LinkFile%.', 'wp-security-audit-log')),
|
226 |
+
array( 6023, E_CRITICAL, __( 'Website Visitor User requests non-existing pages (404 Error Pages)', 'wp-security-audit-log' ), __( 'Website Visitor Has requested a non existing page (404 Error Pages) %Attempts% %Msg%. %LinkFile%.', 'wp-security-audit-log' ) ),
|
227 |
array(9999, E_CRITICAL, __('Advertising Add-ons.', 'wp-security-audit-log'), __('%PromoName% %PromoMessage%', 'wp-security-audit-log'))
|
228 |
),
|
229 |
__('Menus', 'wp-security-audit-log') => array(
|
267 |
array(1004, E_WARNING, __('Login blocked', 'wp-security-audit-log'), __('Blocked from logging in because the same WordPress user is logged in from %ClientIP%.', 'wp-security-audit-log')),
|
268 |
array(1005, E_WARNING, __('User logged in with existing session(s)', 'wp-security-audit-log'), __('Successfully logged in. Another session from %IPAddress% for this user already exist.', 'wp-security-audit-log')),
|
269 |
array(1006, E_CRITICAL, __('User logged out all other sessions with the same username', 'wp-security-audit-log'), __('Logged out all other sessions with the same username.', 'wp-security-audit-log')),
|
270 |
+
array( 1007, E_CRITICAL, __( 'User session destroyed and logged out.', 'wp-security-audit-log' ), __( 'Logged out session %TargetSessionID% which belonged to %TargetUserName%', 'wp-security-audit-log' ) ),
|
271 |
array(2010, E_NOTICE, __('User uploaded file from Uploads directory', 'wp-security-audit-log'), __('Uploaded the file %FileName% in %FilePath%.', 'wp-security-audit-log')),
|
272 |
array(2011, E_WARNING, __('User deleted file from Uploads directory', 'wp-security-audit-log'), __('Deleted the file %FileName% from %FilePath%.', 'wp-security-audit-log'))
|
273 |
),
|
readme.txt
CHANGED
@@ -7,7 +7,7 @@ License URI: http://www.gnu.org/licenses/gpl.html
|
|
7 |
Tags: wordpress security plugin, wordpress security audit log, audit log, wordpress log, event log wordpress, wordpress user tracking, wordpress activity log, wordpress audit, security event log, audit trail, security audit trail, wordpress security alerts, wordpress monitor, wordpress security monitor, wordpress admin, wordpress admin monitoring, analytics, activity, admin, multisite, wordpress multisite, actions, dashboard, log, notification, wordpress monitoring, email notification, wordpress email alerts, tracking, user tracking, user activity report, wordpress audit trail
|
8 |
Requires at least: 3.6
|
9 |
Tested up to: 4.8
|
10 |
-
Stable tag: 2.6.
|
11 |
|
12 |
Keep an audit trail of all changes and under the hood WordPress activity to ensure productivity and thwart possible WordPress hacker attacks.
|
13 |
|
@@ -118,6 +118,7 @@ WP Security Audit Log plugin also has a number of features that make WordPress a
|
|
118 |
* [WPLift](http://wplift.com/audit-wordpress-security-logs) - Review by Ahmad Awais
|
119 |
* [WP SmackDown](https://wpsmackdown.com/wp-plugins/wp-security-audit-log/)
|
120 |
* [WPKube](http://www.wpkube.com/improve-wordpress-security-wp-security-audit-log/)
|
|
|
121 |
* [ManageWP Plugins of the month](https://managewp.com/free-wordpress-plugins-june-2014)
|
122 |
* [MyWPExpert](http://www.mywpexpert.com/wp-security-audit-log/)
|
123 |
* [BlogVault](https://blogvault.net/wp-security-audit-log-plugin-review/)
|
@@ -186,6 +187,18 @@ Please refer to the [FAQs page](https://www.wpsecurityauditlog.com/documentation
|
|
186 |
|
187 |
== Changelog ==
|
188 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
189 |
= 2.6.4 (2017-06-01) =
|
190 |
|
191 |
* **New Features**
|
7 |
Tags: wordpress security plugin, wordpress security audit log, audit log, wordpress log, event log wordpress, wordpress user tracking, wordpress activity log, wordpress audit, security event log, audit trail, security audit trail, wordpress security alerts, wordpress monitor, wordpress security monitor, wordpress admin, wordpress admin monitoring, analytics, activity, admin, multisite, wordpress multisite, actions, dashboard, log, notification, wordpress monitoring, email notification, wordpress email alerts, tracking, user tracking, user activity report, wordpress audit trail
|
8 |
Requires at least: 3.6
|
9 |
Tested up to: 4.8
|
10 |
+
Stable tag: 2.6.5
|
11 |
|
12 |
Keep an audit trail of all changes and under the hood WordPress activity to ensure productivity and thwart possible WordPress hacker attacks.
|
13 |
|
118 |
* [WPLift](http://wplift.com/audit-wordpress-security-logs) - Review by Ahmad Awais
|
119 |
* [WP SmackDown](https://wpsmackdown.com/wp-plugins/wp-security-audit-log/)
|
120 |
* [WPKube](http://www.wpkube.com/improve-wordpress-security-wp-security-audit-log/)
|
121 |
+
* [Cloudways](https://www.cloudways.com/blog/monitor-wordpress-with-wp-security-audit-log-plugin/)
|
122 |
* [ManageWP Plugins of the month](https://managewp.com/free-wordpress-plugins-june-2014)
|
123 |
* [MyWPExpert](http://www.mywpexpert.com/wp-security-audit-log/)
|
124 |
* [BlogVault](https://blogvault.net/wp-security-audit-log-plugin-review/)
|
187 |
|
188 |
== Changelog ==
|
189 |
|
190 |
+
= 2.6.5 (2017-07-18) =
|
191 |
+
|
192 |
+
* **New Audit Trail Alerts**
|
193 |
+
* Alert 1007 for when an administrator terminate's a logged in session using the Users Sessions Management Add-On
|
194 |
+
* Alert 6023 to log 404 HTTP errors (requests to non-existing pages) by website visitors (non WordPress users)
|
195 |
+
|
196 |
+
* **Improvements**
|
197 |
+
* Seggregated the logging of 404 HTTP Errors by who generates them. Alert 6007 for logged in users, 6023 for anonymous website visitors.
|
198 |
+
* Improved the logging of Alert 4014 so it is not reported every time a user's profile page is reloaded with a refresh or when a change is applied.
|
199 |
+
* Removed the wsal_wp_session cookie, which was used to store the selected database when [archiving of audit trail alerts is enabled](https://www.wpsecurityauditlog.com/wordpress-user-monitoring-plugin-documentation/faq-archiving-wordpress-audit-trail/). Using LocalStorage instead.
|
200 |
+
* Replaced mcrypt (deprecated in PHP 7) with OpenSSL. Mcrypt still used temporarily to convert configured password. Will be removed completely in future updates. [Support Ticket](https://wordpress.org/support/topic/php-issues-9/)
|
201 |
+
|
202 |
= 2.6.4 (2017-06-01) =
|
203 |
|
204 |
* **New Features**
|
wp-security-audit-log.php
CHANGED
@@ -4,7 +4,7 @@ Plugin Name: WP Security Audit Log
|
|
4 |
Plugin URI: http://www.wpsecurityauditlog.com/
|
5 |
Description: Identify WordPress security issues before they become a problem. Keep track of everything happening on your WordPress including WordPress users activity. Similar to Windows Event Log and Linux Syslog, WP Security Audit Log generates a security alert for everything that happens on your WordPress blogs and websites. Use the Audit Log Viewer included in the plugin to see all the security alerts.
|
6 |
Author: WP White Security
|
7 |
-
Version: 2.6.
|
8 |
Text Domain: wp-security-audit-log
|
9 |
Author URI: http://www.wpsecurityauditlog.com/
|
10 |
License: GPL2
|
@@ -26,58 +26,61 @@ License: GPL2
|
|
26 |
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
27 |
*/
|
28 |
|
|
|
|
|
|
|
29 |
class WpSecurityAuditLog {
|
30 |
-
|
31 |
// <editor-fold desc="Properties & Constants">
|
32 |
-
|
33 |
const PLG_CLS_PRFX = 'WSAL_';
|
34 |
-
|
35 |
const MIN_PHP_VERSION = '5.3.0';
|
36 |
-
|
37 |
const OPT_PRFX = 'wsal-';
|
38 |
-
|
39 |
/**
|
40 |
* Views supervisor.
|
41 |
* @var WSAL_ViewManager
|
42 |
*/
|
43 |
public $views;
|
44 |
-
|
45 |
/**
|
46 |
* Logger supervisor.
|
47 |
* @var WSAL_AlertManager
|
48 |
*/
|
49 |
public $alerts;
|
50 |
-
|
51 |
/**
|
52 |
* Sensors supervisor.
|
53 |
* @var WSAL_SensorManager
|
54 |
*/
|
55 |
public $sensors;
|
56 |
-
|
57 |
/**
|
58 |
* Settings manager.
|
59 |
* @var WSAL_Settings
|
60 |
*/
|
61 |
public $settings;
|
62 |
-
|
63 |
/**
|
64 |
* Class loading manager.
|
65 |
* @var WSAL_Autoloader
|
66 |
*/
|
67 |
public $autoloader;
|
68 |
-
|
69 |
/**
|
70 |
* Constants manager.
|
71 |
* @var WSAL_ConstantManager
|
72 |
*/
|
73 |
public $constants;
|
74 |
-
|
75 |
/**
|
76 |
* Licenses manager.
|
77 |
* @var WSAL_LicenseManager
|
78 |
*/
|
79 |
public $licensing;
|
80 |
-
|
81 |
/**
|
82 |
* Simple profiler.
|
83 |
* @var WSAL_SimpleProfiler
|
@@ -89,34 +92,37 @@ class WpSecurityAuditLog {
|
|
89 |
* @var WSAL_DB_Option
|
90 |
*/
|
91 |
public $options;
|
92 |
-
|
93 |
/**
|
94 |
* Contains a list of cleanup callbacks.
|
95 |
* @var callable[]
|
96 |
*/
|
97 |
protected $_cleanup_hooks = array();
|
98 |
-
|
99 |
// </editor-fold>
|
100 |
-
|
101 |
// <editor-fold desc="Entry Points">
|
102 |
-
|
103 |
/**
|
104 |
* Standard singleton pattern.
|
105 |
* WARNING! To ensure the system always works as expected, AVOID using this method.
|
106 |
* Instead, make use of the plugin instance provided by 'wsal_init' action.
|
107 |
* @return WpSecurityAuditLog Returns the current plugin instance.
|
108 |
*/
|
109 |
-
public static function GetInstance()
|
|
|
110 |
static $instance = null;
|
111 |
-
if(!$instance)
|
|
|
|
|
112 |
return $instance;
|
113 |
}
|
114 |
-
|
115 |
/**
|
116 |
* Initialize plugin.
|
117 |
*/
|
118 |
-
public function __construct()
|
119 |
-
|
120 |
require_once('classes/Helpers/DataHelper.php');
|
121 |
// profiler has to be loaded manually
|
122 |
require_once('classes/SimpleProfiler.php');
|
@@ -127,28 +133,11 @@ class WpSecurityAuditLog {
|
|
127 |
require_once('classes/Models/Option.php');
|
128 |
require_once('classes/Models/TmpUser.php');
|
129 |
|
130 |
-
// Use WP_Session (default)
|
131 |
-
if (!defined('WP_SESSION_COOKIE')) {
|
132 |
-
define('WP_SESSION_COOKIE', 'wsal_wp_session');
|
133 |
-
}
|
134 |
-
if (!class_exists('Recursive_ArrayAccess')) {
|
135 |
-
require_once('classes/Lib/class-recursive-arrayaccess.php');
|
136 |
-
}
|
137 |
-
if (!class_exists('WP_Session')) {
|
138 |
-
require_once('classes/Lib/class-wp-session.php');
|
139 |
-
require_once('classes/Lib/wp-session.php');
|
140 |
-
}
|
141 |
-
|
142 |
-
if (!class_exists('WP_Session_Utils')) {
|
143 |
-
require_once('classes/Lib/class-wp-session-utils.php');
|
144 |
-
}
|
145 |
-
|
146 |
-
|
147 |
// load autoloader and register base paths
|
148 |
require_once('classes/Autoloader.php');
|
149 |
$this->autoloader = new WSAL_Autoloader($this);
|
150 |
$this->autoloader->Register(self::PLG_CLS_PRFX, $this->GetBaseDir() . 'classes' . DIRECTORY_SEPARATOR);
|
151 |
-
|
152 |
// load dependencies
|
153 |
$this->views = new WSAL_ViewManager($this);
|
154 |
$this->alerts = new WSAL_AlertManager($this);
|
@@ -157,19 +146,19 @@ class WpSecurityAuditLog {
|
|
157 |
$this->constants = new WSAL_ConstantManager($this);
|
158 |
$this->licensing = new WSAL_LicenseManager($this);
|
159 |
$this->widgets = new WSAL_WidgetManager($this);
|
160 |
-
|
161 |
-
//
|
162 |
-
register_activation_hook(__FILE__, array($this, 'Install'));
|
163 |
|
164 |
// listen for init event
|
165 |
add_action('init', array($this, 'Init'));
|
166 |
-
|
167 |
// listen for cleanup event
|
168 |
add_action('wsal_cleanup', array($this, 'CleanUp'));
|
169 |
-
|
170 |
// render wsal header
|
171 |
add_action('admin_enqueue_scripts', array($this, 'RenderHeader'));
|
172 |
-
|
173 |
// render wsal footer
|
174 |
add_action('admin_footer', array($this, 'RenderFooter'));
|
175 |
|
@@ -183,15 +172,29 @@ class WpSecurityAuditLog {
|
|
183 |
/**
|
184 |
* @internal Start to trigger the events after installation.
|
185 |
*/
|
186 |
-
public function Init()
|
|
|
|
|
187 |
WpSecurityAuditLog::GetInstance()->sensors->HookEvents();
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
188 |
}
|
189 |
|
190 |
-
|
191 |
/**
|
192 |
* @internal Render plugin stuff in page header.
|
193 |
*/
|
194 |
-
public function RenderHeader()
|
|
|
195 |
// common.css?
|
196 |
}
|
197 |
|
@@ -199,7 +202,8 @@ class WpSecurityAuditLog {
|
|
199 |
* Disable Custom Field through ajax.
|
200 |
* @internal
|
201 |
*/
|
202 |
-
public function AjaxDisableCustomField()
|
|
|
203 |
$fields = $this->GetGlobalOption('excluded-custom');
|
204 |
if (isset($fields) && $fields != "") {
|
205 |
$fields .= "," . esc_html($_POST['notice']);
|
@@ -215,7 +219,8 @@ class WpSecurityAuditLog {
|
|
215 |
* Disable Alert through ajax.
|
216 |
* @internal
|
217 |
*/
|
218 |
-
public function AjaxDisableByCode()
|
|
|
219 |
$sAlerts = $this->GetGlobalOption('disabled-alerts');
|
220 |
if (isset($sAlerts) && $sAlerts != "") {
|
221 |
$sAlerts .= "," . esc_html($_POST['code']);
|
@@ -227,11 +232,12 @@ class WpSecurityAuditLog {
|
|
227 |
echo 'You can enable this alert again from the Enable/Disable Alerts node in the plugin menu.</p>';
|
228 |
die;
|
229 |
}
|
230 |
-
|
231 |
/**
|
232 |
* @internal Render plugin stuff in page footer.
|
233 |
*/
|
234 |
-
public function RenderFooter()
|
|
|
235 |
wp_enqueue_script(
|
236 |
'wsal-common',
|
237 |
$this->GetBaseUrl() . '/js/common.js',
|
@@ -239,12 +245,12 @@ class WpSecurityAuditLog {
|
|
239 |
filemtime($this->GetBaseDir() . '/js/common.js')
|
240 |
);
|
241 |
}
|
242 |
-
|
243 |
/**
|
244 |
* @internal Load the rest of the system.
|
245 |
*/
|
246 |
-
public function Load()
|
247 |
-
|
248 |
$optionsTable = new WSAL_Models_Option();
|
249 |
if (!$optionsTable->IsInstalled()) {
|
250 |
$optionsTable->Install();
|
@@ -281,12 +287,20 @@ class WpSecurityAuditLog {
|
|
281 |
if ($this->settings->IsIncognito()) {
|
282 |
add_action('admin_head', array($this, 'HidePlugin'));
|
283 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
284 |
}
|
285 |
-
|
286 |
/**
|
287 |
* Install all assets required for a useable system.
|
288 |
*/
|
289 |
-
public function Install()
|
|
|
290 |
if (version_compare(PHP_VERSION, self::MIN_PHP_VERSION) < 0) {
|
291 |
?><html>
|
292 |
<head>
|
@@ -302,16 +316,19 @@ class WpSecurityAuditLog {
|
|
302 |
</html><?php
|
303 |
die(1);
|
304 |
}
|
305 |
-
|
306 |
// ensure that the system is installed and schema is correct
|
307 |
self::getConnector()->installAll();
|
308 |
-
|
309 |
$PreInstalled = $this->IsInstalled();
|
310 |
-
|
311 |
// if system already installed, do updates now (if any)
|
312 |
$OldVersion = $this->GetOldVersion();
|
313 |
$NewVersion = $this->GetNewVersion();
|
314 |
-
|
|
|
|
|
|
|
315 |
|
316 |
// Load options from wp_options table or wp_sitemeta in multisite enviroment
|
317 |
$data = $this->read_options_prefixed("wsal-");
|
@@ -319,9 +336,11 @@ class WpSecurityAuditLog {
|
|
319 |
$this->SetOptions($data);
|
320 |
}
|
321 |
$this->deleteAllOptions();
|
322 |
-
|
323 |
// if system wasn't installed, try migration now
|
324 |
-
if (!$PreInstalled && $this->CanMigrate())
|
|
|
|
|
325 |
|
326 |
// setting the prunig date with the old value or the default value
|
327 |
$pruningDate = $this->settings->GetPruningDate();
|
@@ -350,34 +369,86 @@ class WpSecurityAuditLog {
|
|
350 |
if ($purge_log_404 === false) {
|
351 |
$this->SetGlobalOption('purge-404-log', 'on');
|
352 |
}
|
353 |
-
|
354 |
// install cleanup hook (remove older one if it exists)
|
355 |
wp_clear_scheduled_hook('wsal_cleanup');
|
356 |
wp_schedule_event(current_time('timestamp') + 600, 'hourly', 'wsal_cleanup');
|
357 |
}
|
358 |
-
|
359 |
/**
|
360 |
* Run some code that updates critical components required for a newwer version.
|
|
|
361 |
* @param string $old_version The old version.
|
362 |
* @param string $new_version The new version.
|
363 |
*/
|
364 |
-
public function Update($old_version, $new_version){
|
365 |
-
//
|
366 |
-
$this->
|
367 |
-
|
368 |
-
//
|
369 |
//$this->settings->ClearDevOptions();
|
370 |
-
|
371 |
-
//
|
372 |
-
if(version_compare($old_version,
|
373 |
-
|
374 |
}
|
375 |
}
|
376 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
377 |
/**
|
378 |
* Uninstall plugin.
|
379 |
*/
|
380 |
-
public function Uninstall()
|
|
|
381 |
if ($this->GetGlobalOption("delete-data") == 1) {
|
382 |
self::getConnector()->uninstallAll();
|
383 |
$this->deleteAllOptions();
|
@@ -385,40 +456,60 @@ class WpSecurityAuditLog {
|
|
385 |
wp_clear_scheduled_hook('wsal_cleanup');
|
386 |
}
|
387 |
|
388 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
389 |
global $wpdb;
|
390 |
-
|
391 |
-
if ( $this->IsMultisite() ) {
|
392 |
$table_name = $wpdb->prefix .'sitemeta';
|
393 |
-
$result = $wpdb->query(
|
394 |
} else {
|
395 |
-
$result = $wpdb->query(
|
396 |
}
|
397 |
return ($result) ? true : false;
|
398 |
}
|
399 |
|
400 |
-
|
|
|
|
|
|
|
|
|
401 |
$flag = true;
|
402 |
-
while (
|
403 |
-
$flag = $this->delete_options_prefixed(
|
404 |
}
|
405 |
}
|
406 |
-
|
407 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
408 |
global $wpdb;
|
409 |
-
if (
|
410 |
$table_name = $wpdb->prefix .'sitemeta';
|
411 |
-
$results = $wpdb->get_results(
|
412 |
} else {
|
413 |
-
$results = $wpdb->get_results(
|
414 |
}
|
415 |
return $results;
|
416 |
}
|
417 |
|
418 |
-
|
419 |
-
|
|
|
|
|
|
|
|
|
|
|
420 |
$this->options = new WSAL_Models_Option();
|
421 |
-
if (
|
422 |
$this->options->SetOptionValue($option['meta_key'], $option['meta_value']);
|
423 |
} else {
|
424 |
$this->options->SetOptionValue($option['option_name'], $option['option_value']);
|
@@ -429,49 +520,57 @@ class WpSecurityAuditLog {
|
|
429 |
/**
|
430 |
* Migrate data from old plugin.
|
431 |
*/
|
432 |
-
public function Migrate()
|
|
|
433 |
global $wpdb;
|
434 |
static $migTypes = array(
|
435 |
3000 => 5006
|
436 |
);
|
437 |
-
|
438 |
// load data
|
439 |
$sql = 'SELECT * FROM ' . $wpdb->base_prefix . 'wordpress_auditlog_events';
|
440 |
$events = array();
|
441 |
-
foreach($wpdb->get_results($sql, ARRAY_A) as $item)
|
442 |
$events[$item['EventID']] = $item;
|
|
|
443 |
$sql = 'SELECT * FROM ' . $wpdb->base_prefix . 'wordpress_auditlog';
|
444 |
$auditlog = $wpdb->get_results($sql, ARRAY_A);
|
445 |
-
|
446 |
// migrate using db logger
|
447 |
-
foreach($auditlog as $entry){
|
448 |
$data = array(
|
449 |
'ClientIP' => $entry['UserIP'],
|
450 |
'UserAgent' => '',
|
451 |
'CurrentUserID' => $entry['UserID'],
|
452 |
);
|
453 |
-
if($entry['UserName'])
|
454 |
$data['Username'] = base64_decode($entry['UserName']);
|
|
|
455 |
$mesg = $events[$entry['EventID']]['EventDescription'];
|
456 |
$date = strtotime($entry['EventDate']);
|
457 |
$type = $entry['EventID'];
|
458 |
-
if(isset($migTypes[$type]))
|
|
|
|
|
459 |
// convert message from '<strong>%s</strong>' to '%Arg1%' format
|
460 |
-
$c = 0;
|
461 |
-
|
|
|
|
|
462 |
$mesg = substr_replace($mesg, '%MigratedArg' . ($c++) .'%', $pos, $l);
|
463 |
}
|
464 |
$data['MigratedMesg'] = $mesg;
|
465 |
// generate new meta data args
|
466 |
$temp = unserialize(base64_decode($entry['EventData']));
|
467 |
-
foreach((array)$temp as $i => $item)
|
468 |
$data['MigratedArg' . $i] = $item;
|
|
|
469 |
// send event data to logger!
|
470 |
-
foreach($this->alerts->GetLoggers() as $logger){
|
471 |
$logger->Log($type, $data, $date, $entry['BlogId'], true);
|
472 |
}
|
473 |
}
|
474 |
-
|
475 |
// migrate settings
|
476 |
$this->settings->SetAllowedPluginEditors(
|
477 |
get_option('WPPH_PLUGIN_ALLOW_CHANGE')
|
@@ -485,30 +584,33 @@ class WpSecurityAuditLog {
|
|
485 |
$this->settings->SetViewPerPage(max($s->showEventsViewList, 5));
|
486 |
$this->settings->SetWidgetsEnabled(!!$s->showDW);
|
487 |
}
|
488 |
-
|
489 |
// </editor-fold>
|
490 |
-
|
491 |
// <editor-fold desc="Utility Methods">
|
492 |
-
|
493 |
/**
|
494 |
* @return string The current plugin version (according to plugin file metadata).
|
495 |
*/
|
496 |
-
public function GetNewVersion()
|
|
|
497 |
$version = get_plugin_data(__FILE__, false, false);
|
498 |
return isset($version['Version']) ? $version['Version'] : '0.0.0';
|
499 |
}
|
500 |
-
|
501 |
/**
|
502 |
* @return string The plugin version as stored in DB (will be the old version during an update/install).
|
503 |
*/
|
504 |
-
public function GetOldVersion()
|
|
|
505 |
return $this->GetGlobalOption('version', '0.0.0');
|
506 |
}
|
507 |
-
|
508 |
/**
|
509 |
* @internal To be called in admin header for hiding plugin form Plugins list.
|
510 |
*/
|
511 |
-
public function HidePlugin()
|
|
|
512 |
$selectr = '';
|
513 |
$plugins = array('wp-security-audit-log');
|
514 |
foreach ($this->licensing->Plugins() as $plugin) {
|
@@ -519,24 +621,26 @@ class WpSecurityAuditLog {
|
|
519 |
}
|
520 |
?><style type="text/css"> <?php echo rtrim($selectr, ", "); ?> { display: none; }</style><?php
|
521 |
}
|
522 |
-
|
523 |
/**
|
524 |
* Returns the class name of a particular file that contains the class.
|
525 |
* @param string $file File name.
|
526 |
* @return string Class name.
|
527 |
* @deprecated since 1.2.5 Use autoloader->GetClassFileClassName() instead.
|
528 |
*/
|
529 |
-
public function GetClassFileClassName($file)
|
|
|
530 |
return $this->autoloader->GetClassFileClassName($file);
|
531 |
}
|
532 |
-
|
533 |
/**
|
534 |
* @return boolean Whether we are running on multisite or not.
|
535 |
*/
|
536 |
-
public function IsMultisite()
|
|
|
537 |
return function_exists('is_multisite') && is_multisite();
|
538 |
}
|
539 |
-
|
540 |
/**
|
541 |
* Get a global option.
|
542 |
* @param string $option Option name.
|
@@ -544,27 +648,24 @@ class WpSecurityAuditLog {
|
|
544 |
* @param string $prefix (Optional) A prefix used before option name.
|
545 |
* @return mixed Option's value or $default if option not set.
|
546 |
*/
|
547 |
-
public function GetGlobalOption($option, $default = false, $prefix = self::OPT_PRFX)
|
548 |
-
|
549 |
-
//var_dump($fn($prefix . $option, $default));
|
550 |
-
//return $fn($prefix . $option, $default);
|
551 |
$this->options = new WSAL_Models_Option();
|
552 |
-
return $this->options->GetOptionValue($prefix . $option, $default);
|
553 |
}
|
554 |
-
|
555 |
/**
|
556 |
* Set a global option.
|
557 |
* @param string $option Option name.
|
558 |
* @param mixed $value New value for option.
|
559 |
* @param string $prefix (Optional) A prefix used before option name.
|
560 |
*/
|
561 |
-
public function SetGlobalOption($option, $value, $prefix = self::OPT_PRFX)
|
562 |
-
|
563 |
-
//$fn($prefix . $option, $value);
|
564 |
$this->options = new WSAL_Models_Option();
|
565 |
$this->options->SetOptionValue($prefix . $option, $value);
|
566 |
}
|
567 |
-
|
568 |
/**
|
569 |
* Get a user-specific option.
|
570 |
* @param string $option Option name.
|
@@ -572,93 +673,111 @@ class WpSecurityAuditLog {
|
|
572 |
* @param string $prefix (Optional) A prefix used before option name.
|
573 |
* @return mixed Option's value or $default if option not set.
|
574 |
*/
|
575 |
-
public function GetUserOption($option, $default = false, $prefix = self::OPT_PRFX)
|
|
|
576 |
$result = get_user_option($prefix . $option, get_current_user_id());
|
577 |
return $result === false ? $default : $result;
|
578 |
}
|
579 |
-
|
580 |
/**
|
581 |
* Set a user-specific option.
|
582 |
* @param string $option Option name.
|
583 |
* @param mixed $value New value for option.
|
584 |
* @param string $prefix (Optional) A prefix used before option name.
|
585 |
*/
|
586 |
-
public function SetUserOption($option, $value, $prefix = self::OPT_PRFX)
|
|
|
587 |
update_user_option(get_current_user_id(), $prefix . $option, $value, false);
|
588 |
}
|
589 |
-
|
590 |
/**
|
591 |
* Run cleanup routines.
|
592 |
*/
|
593 |
-
public function CleanUp()
|
|
|
594 |
$s = $this->profiler->Start('Clean Up');
|
595 |
-
foreach($this->_cleanup_hooks as $hook)
|
596 |
call_user_func($hook);
|
|
|
597 |
$s->Stop();
|
598 |
}
|
599 |
-
|
600 |
/**
|
601 |
* Add callback to be called when a cleanup operation is required.
|
602 |
* @param callable $hook
|
603 |
*/
|
604 |
-
public function AddCleanupHook($hook)
|
|
|
605 |
$this->_cleanup_hooks[] = $hook;
|
606 |
}
|
607 |
-
|
608 |
/**
|
609 |
* Remove a callback from the cleanup callbacks list.
|
610 |
* @param callable $hook
|
611 |
*/
|
612 |
-
public function RemoveCleanupHook($hook)
|
613 |
-
|
|
|
614 |
unset($this->_cleanup_hooks[$pos]);
|
|
|
615 |
}
|
616 |
|
|
|
|
|
|
|
|
|
|
|
617 |
public static function getConnector($config = null, $reset = false)
|
618 |
{
|
619 |
return WSAL_Connector_ConnectorFactory::getConnector($config, $reset);
|
620 |
}
|
621 |
-
|
622 |
/**
|
623 |
* Do we have an existing installation? This only applies for version 1.0 onwards.
|
624 |
* @return boolean
|
625 |
*/
|
626 |
-
public function IsInstalled()
|
|
|
627 |
return self::getConnector()->isInstalled();
|
628 |
}
|
629 |
-
|
630 |
/**
|
631 |
* @return boolean Whether the old plugin was present or not.
|
632 |
*/
|
633 |
-
public function CanMigrate()
|
|
|
634 |
return self::getConnector()->canMigrate();
|
635 |
}
|
636 |
-
|
637 |
/**
|
638 |
* @return string Absolute URL to plugin directory WITHOUT final slash.
|
639 |
*/
|
640 |
-
public function GetBaseUrl()
|
|
|
641 |
return plugins_url('', __FILE__);
|
642 |
}
|
643 |
-
|
644 |
/**
|
645 |
* @return string Full path to plugin directory WITH final slash.
|
646 |
*/
|
647 |
-
public function GetBaseDir()
|
|
|
648 |
return plugin_dir_path(__FILE__);
|
649 |
}
|
650 |
-
|
651 |
/**
|
652 |
* @return string Plugin directory name.
|
653 |
*/
|
654 |
-
public function GetBaseName()
|
|
|
655 |
return plugin_basename(__FILE__);
|
656 |
}
|
657 |
-
|
658 |
/**
|
659 |
* Load default configuration / data.
|
660 |
*/
|
661 |
-
public function LoadDefaults()
|
|
|
662 |
$s = $this->profiler->Start('Load Defaults');
|
663 |
require_once('defaults.php');
|
664 |
$s->Stop();
|
4 |
Plugin URI: http://www.wpsecurityauditlog.com/
|
5 |
Description: Identify WordPress security issues before they become a problem. Keep track of everything happening on your WordPress including WordPress users activity. Similar to Windows Event Log and Linux Syslog, WP Security Audit Log generates a security alert for everything that happens on your WordPress blogs and websites. Use the Audit Log Viewer included in the plugin to see all the security alerts.
|
6 |
Author: WP White Security
|
7 |
+
Version: 2.6.5
|
8 |
Text Domain: wp-security-audit-log
|
9 |
Author URI: http://www.wpsecurityauditlog.com/
|
10 |
License: GPL2
|
26 |
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
27 |
*/
|
28 |
|
29 |
+
/**
|
30 |
+
* @package Wsal
|
31 |
+
*/
|
32 |
class WpSecurityAuditLog {
|
33 |
+
|
34 |
// <editor-fold desc="Properties & Constants">
|
35 |
+
|
36 |
const PLG_CLS_PRFX = 'WSAL_';
|
37 |
+
|
38 |
const MIN_PHP_VERSION = '5.3.0';
|
39 |
+
|
40 |
const OPT_PRFX = 'wsal-';
|
41 |
+
|
42 |
/**
|
43 |
* Views supervisor.
|
44 |
* @var WSAL_ViewManager
|
45 |
*/
|
46 |
public $views;
|
47 |
+
|
48 |
/**
|
49 |
* Logger supervisor.
|
50 |
* @var WSAL_AlertManager
|
51 |
*/
|
52 |
public $alerts;
|
53 |
+
|
54 |
/**
|
55 |
* Sensors supervisor.
|
56 |
* @var WSAL_SensorManager
|
57 |
*/
|
58 |
public $sensors;
|
59 |
+
|
60 |
/**
|
61 |
* Settings manager.
|
62 |
* @var WSAL_Settings
|
63 |
*/
|
64 |
public $settings;
|
65 |
+
|
66 |
/**
|
67 |
* Class loading manager.
|
68 |
* @var WSAL_Autoloader
|
69 |
*/
|
70 |
public $autoloader;
|
71 |
+
|
72 |
/**
|
73 |
* Constants manager.
|
74 |
* @var WSAL_ConstantManager
|
75 |
*/
|
76 |
public $constants;
|
77 |
+
|
78 |
/**
|
79 |
* Licenses manager.
|
80 |
* @var WSAL_LicenseManager
|
81 |
*/
|
82 |
public $licensing;
|
83 |
+
|
84 |
/**
|
85 |
* Simple profiler.
|
86 |
* @var WSAL_SimpleProfiler
|
92 |
* @var WSAL_DB_Option
|
93 |
*/
|
94 |
public $options;
|
95 |
+
|
96 |
/**
|
97 |
* Contains a list of cleanup callbacks.
|
98 |
* @var callable[]
|
99 |
*/
|
100 |
protected $_cleanup_hooks = array();
|
101 |
+
|
102 |
// </editor-fold>
|
103 |
+
|
104 |
// <editor-fold desc="Entry Points">
|
105 |
+
|
106 |
/**
|
107 |
* Standard singleton pattern.
|
108 |
* WARNING! To ensure the system always works as expected, AVOID using this method.
|
109 |
* Instead, make use of the plugin instance provided by 'wsal_init' action.
|
110 |
* @return WpSecurityAuditLog Returns the current plugin instance.
|
111 |
*/
|
112 |
+
public static function GetInstance()
|
113 |
+
{
|
114 |
static $instance = null;
|
115 |
+
if (!$instance) {
|
116 |
+
$instance = new self();
|
117 |
+
}
|
118 |
return $instance;
|
119 |
}
|
120 |
+
|
121 |
/**
|
122 |
* Initialize plugin.
|
123 |
*/
|
124 |
+
public function __construct()
|
125 |
+
{
|
126 |
require_once('classes/Helpers/DataHelper.php');
|
127 |
// profiler has to be loaded manually
|
128 |
require_once('classes/SimpleProfiler.php');
|
133 |
require_once('classes/Models/Option.php');
|
134 |
require_once('classes/Models/TmpUser.php');
|
135 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
136 |
// load autoloader and register base paths
|
137 |
require_once('classes/Autoloader.php');
|
138 |
$this->autoloader = new WSAL_Autoloader($this);
|
139 |
$this->autoloader->Register(self::PLG_CLS_PRFX, $this->GetBaseDir() . 'classes' . DIRECTORY_SEPARATOR);
|
140 |
+
|
141 |
// load dependencies
|
142 |
$this->views = new WSAL_ViewManager($this);
|
143 |
$this->alerts = new WSAL_AlertManager($this);
|
146 |
$this->constants = new WSAL_ConstantManager($this);
|
147 |
$this->licensing = new WSAL_LicenseManager($this);
|
148 |
$this->widgets = new WSAL_WidgetManager($this);
|
149 |
+
|
150 |
+
// Listen for installation event.
|
151 |
+
register_activation_hook( __FILE__, array( $this, 'Install' ) );
|
152 |
|
153 |
// listen for init event
|
154 |
add_action('init', array($this, 'Init'));
|
155 |
+
|
156 |
// listen for cleanup event
|
157 |
add_action('wsal_cleanup', array($this, 'CleanUp'));
|
158 |
+
|
159 |
// render wsal header
|
160 |
add_action('admin_enqueue_scripts', array($this, 'RenderHeader'));
|
161 |
+
|
162 |
// render wsal footer
|
163 |
add_action('admin_footer', array($this, 'RenderFooter'));
|
164 |
|
172 |
/**
|
173 |
* @internal Start to trigger the events after installation.
|
174 |
*/
|
175 |
+
public function Init()
|
176 |
+
{
|
177 |
+
// Start listening to events
|
178 |
WpSecurityAuditLog::GetInstance()->sensors->HookEvents();
|
179 |
+
|
180 |
+
if ($this->settings->IsArchivingEnabled()) {
|
181 |
+
// Check the current page
|
182 |
+
if ((!isset($_REQUEST['page']) || $_REQUEST['page'] != 'wsal-auditlog') && (!defined('DOING_AJAX') || !DOING_AJAX)) {
|
183 |
+
$selected_db = get_transient('wsal_wp_selected_db');
|
184 |
+
if ($selected_db) {
|
185 |
+
// Delete the transient
|
186 |
+
delete_transient('wsal_wp_selected_db');
|
187 |
+
}
|
188 |
+
}
|
189 |
+
}
|
190 |
}
|
191 |
|
192 |
+
|
193 |
/**
|
194 |
* @internal Render plugin stuff in page header.
|
195 |
*/
|
196 |
+
public function RenderHeader()
|
197 |
+
{
|
198 |
// common.css?
|
199 |
}
|
200 |
|
202 |
* Disable Custom Field through ajax.
|
203 |
* @internal
|
204 |
*/
|
205 |
+
public function AjaxDisableCustomField()
|
206 |
+
{
|
207 |
$fields = $this->GetGlobalOption('excluded-custom');
|
208 |
if (isset($fields) && $fields != "") {
|
209 |
$fields .= "," . esc_html($_POST['notice']);
|
219 |
* Disable Alert through ajax.
|
220 |
* @internal
|
221 |
*/
|
222 |
+
public function AjaxDisableByCode()
|
223 |
+
{
|
224 |
$sAlerts = $this->GetGlobalOption('disabled-alerts');
|
225 |
if (isset($sAlerts) && $sAlerts != "") {
|
226 |
$sAlerts .= "," . esc_html($_POST['code']);
|
232 |
echo 'You can enable this alert again from the Enable/Disable Alerts node in the plugin menu.</p>';
|
233 |
die;
|
234 |
}
|
235 |
+
|
236 |
/**
|
237 |
* @internal Render plugin stuff in page footer.
|
238 |
*/
|
239 |
+
public function RenderFooter()
|
240 |
+
{
|
241 |
wp_enqueue_script(
|
242 |
'wsal-common',
|
243 |
$this->GetBaseUrl() . '/js/common.js',
|
245 |
filemtime($this->GetBaseDir() . '/js/common.js')
|
246 |
);
|
247 |
}
|
248 |
+
|
249 |
/**
|
250 |
* @internal Load the rest of the system.
|
251 |
*/
|
252 |
+
public function Load()
|
253 |
+
{
|
254 |
$optionsTable = new WSAL_Models_Option();
|
255 |
if (!$optionsTable->IsInstalled()) {
|
256 |
$optionsTable->Install();
|
287 |
if ($this->settings->IsIncognito()) {
|
288 |
add_action('admin_head', array($this, 'HidePlugin'));
|
289 |
}
|
290 |
+
|
291 |
+
// Update routine.
|
292 |
+
$old_version = $this->GetOldVersion();
|
293 |
+
$new_version = $this->GetNewVersion();
|
294 |
+
if ( $old_version !== $new_version ) {
|
295 |
+
$this->Update( $old_version, $new_version );
|
296 |
+
}
|
297 |
}
|
298 |
+
|
299 |
/**
|
300 |
* Install all assets required for a useable system.
|
301 |
*/
|
302 |
+
public function Install()
|
303 |
+
{
|
304 |
if (version_compare(PHP_VERSION, self::MIN_PHP_VERSION) < 0) {
|
305 |
?><html>
|
306 |
<head>
|
316 |
</html><?php
|
317 |
die(1);
|
318 |
}
|
319 |
+
|
320 |
// ensure that the system is installed and schema is correct
|
321 |
self::getConnector()->installAll();
|
322 |
+
|
323 |
$PreInstalled = $this->IsInstalled();
|
324 |
+
|
325 |
// if system already installed, do updates now (if any)
|
326 |
$OldVersion = $this->GetOldVersion();
|
327 |
$NewVersion = $this->GetNewVersion();
|
328 |
+
|
329 |
+
if ( $PreInstalled && $OldVersion != $NewVersion ) {
|
330 |
+
$this->Update( $OldVersion, $NewVersion );
|
331 |
+
}
|
332 |
|
333 |
// Load options from wp_options table or wp_sitemeta in multisite enviroment
|
334 |
$data = $this->read_options_prefixed("wsal-");
|
336 |
$this->SetOptions($data);
|
337 |
}
|
338 |
$this->deleteAllOptions();
|
339 |
+
|
340 |
// if system wasn't installed, try migration now
|
341 |
+
if (!$PreInstalled && $this->CanMigrate()) {
|
342 |
+
$this->Migrate();
|
343 |
+
}
|
344 |
|
345 |
// setting the prunig date with the old value or the default value
|
346 |
$pruningDate = $this->settings->GetPruningDate();
|
369 |
if ($purge_log_404 === false) {
|
370 |
$this->SetGlobalOption('purge-404-log', 'on');
|
371 |
}
|
372 |
+
|
373 |
// install cleanup hook (remove older one if it exists)
|
374 |
wp_clear_scheduled_hook('wsal_cleanup');
|
375 |
wp_schedule_event(current_time('timestamp') + 600, 'hourly', 'wsal_cleanup');
|
376 |
}
|
377 |
+
|
378 |
/**
|
379 |
* Run some code that updates critical components required for a newwer version.
|
380 |
+
*
|
381 |
* @param string $old_version The old version.
|
382 |
* @param string $new_version The new version.
|
383 |
*/
|
384 |
+
public function Update( $old_version, $new_version ) {
|
385 |
+
// Update version in db.
|
386 |
+
$this->SetGlobalOption( 'version', $new_version );
|
387 |
+
|
388 |
+
// Disable all developer options.
|
389 |
//$this->settings->ClearDevOptions();
|
390 |
+
|
391 |
+
// Do version-to-version specific changes.
|
392 |
+
if ( -1 === version_compare( $old_version, $new_version ) ) {
|
393 |
+
$this->update_external_db_password();
|
394 |
}
|
395 |
}
|
396 |
|
397 |
+
/**
|
398 |
+
* Method: Update external DB password.
|
399 |
+
*
|
400 |
+
* @since 2.6.3
|
401 |
+
*/
|
402 |
+
public function update_external_db_password() {
|
403 |
+
|
404 |
+
// Get the passwords.
|
405 |
+
$external_password = $this->settings->GetAdapterConfig( 'adapter-password' );
|
406 |
+
$mirror_password = $this->settings->GetAdapterConfig( 'mirror-password' );
|
407 |
+
$archive_password = $this->settings->GetAdapterConfig( 'archive-password' );
|
408 |
+
|
409 |
+
// Update external db password.
|
410 |
+
if ( ! empty( $external_password ) ) {
|
411 |
+
// Decrypt the password using fallback method.
|
412 |
+
$password = $this->getConnector()->decryptString_fallback( $external_password );
|
413 |
+
|
414 |
+
// Encrypt the password with latest encryption method.
|
415 |
+
$encrypted_password = $this->getConnector()->encryptString( $password );
|
416 |
+
|
417 |
+
// Store the new password.
|
418 |
+
$this->settings->SetAdapterConfig( 'adapter-password', $encrypted_password );
|
419 |
+
}
|
420 |
+
|
421 |
+
// Update mirror db password.
|
422 |
+
if ( ! empty( $mirror_password ) ) {
|
423 |
+
// Decrypt the password using fallback method.
|
424 |
+
$password = $this->getConnector()->decryptString_fallback( $mirror_password );
|
425 |
+
|
426 |
+
// Encrypt the password with latest encryption method.
|
427 |
+
$encrypted_password = $this->getConnector()->encryptString( $password );
|
428 |
+
|
429 |
+
// Store the new password.
|
430 |
+
$this->settings->SetAdapterConfig( 'mirror-password', $encrypted_password );
|
431 |
+
}
|
432 |
+
|
433 |
+
// Update archive db password.
|
434 |
+
if ( ! empty( $archive_password ) ) {
|
435 |
+
// Decrypt the password using fallback method.
|
436 |
+
$password = $this->getConnector()->decryptString_fallback( $archive_password );
|
437 |
+
|
438 |
+
// Encrypt the password with latest encryption method.
|
439 |
+
$encrypted_password = $this->getConnector()->encryptString( $password );
|
440 |
+
|
441 |
+
// Store the new password.
|
442 |
+
$this->settings->SetAdapterConfig( 'archive-password', $encrypted_password );
|
443 |
+
}
|
444 |
+
|
445 |
+
}
|
446 |
+
|
447 |
/**
|
448 |
* Uninstall plugin.
|
449 |
*/
|
450 |
+
public function Uninstall()
|
451 |
+
{
|
452 |
if ($this->GetGlobalOption("delete-data") == 1) {
|
453 |
self::getConnector()->uninstallAll();
|
454 |
$this->deleteAllOptions();
|
456 |
wp_clear_scheduled_hook('wsal_cleanup');
|
457 |
}
|
458 |
|
459 |
+
/**
|
460 |
+
* Delete from the options table of WP.
|
461 |
+
* @param string $prefix table prefix
|
462 |
+
* @return boolean query result
|
463 |
+
*/
|
464 |
+
public function delete_options_prefixed($prefix)
|
465 |
+
{
|
466 |
global $wpdb;
|
467 |
+
if ($this->IsMultisite()) {
|
|
|
468 |
$table_name = $wpdb->prefix .'sitemeta';
|
469 |
+
$result = $wpdb->query("DELETE FROM {$table_name} WHERE meta_key LIKE '{$prefix}%'");
|
470 |
} else {
|
471 |
+
$result = $wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '{$prefix}%'");
|
472 |
}
|
473 |
return ($result) ? true : false;
|
474 |
}
|
475 |
|
476 |
+
/**
|
477 |
+
* Delete all the Wsal options from the options table of WP.
|
478 |
+
*/
|
479 |
+
private function deleteAllOptions()
|
480 |
+
{
|
481 |
$flag = true;
|
482 |
+
while ($flag) {
|
483 |
+
$flag = $this->delete_options_prefixed(self::OPT_PRFX);
|
484 |
}
|
485 |
}
|
486 |
+
|
487 |
+
/**
|
488 |
+
* Read options from the options table of WP.
|
489 |
+
* @param string $prefix table prefix
|
490 |
+
* @return boolean query result
|
491 |
+
*/
|
492 |
+
public function read_options_prefixed($prefix)
|
493 |
+
{
|
494 |
global $wpdb;
|
495 |
+
if ($this->IsMultisite()) {
|
496 |
$table_name = $wpdb->prefix .'sitemeta';
|
497 |
+
$results = $wpdb->get_results("SELECT site_id,meta_key,meta_value FROM {$table_name} WHERE meta_key LIKE '{$prefix}%'", ARRAY_A);
|
498 |
} else {
|
499 |
+
$results = $wpdb->get_results("SELECT option_name,option_value FROM {$wpdb->options} WHERE option_name LIKE '{$prefix}%'", ARRAY_A);
|
500 |
}
|
501 |
return $results;
|
502 |
}
|
503 |
|
504 |
+
/**
|
505 |
+
* Set options in the Wsal options table.
|
506 |
+
* @param array $data table prefix
|
507 |
+
*/
|
508 |
+
public function SetOptions($data)
|
509 |
+
{
|
510 |
+
foreach ($data as $key => $option) {
|
511 |
$this->options = new WSAL_Models_Option();
|
512 |
+
if ($this->IsMultisite()) {
|
513 |
$this->options->SetOptionValue($option['meta_key'], $option['meta_value']);
|
514 |
} else {
|
515 |
$this->options->SetOptionValue($option['option_name'], $option['option_value']);
|
520 |
/**
|
521 |
* Migrate data from old plugin.
|
522 |
*/
|
523 |
+
public function Migrate()
|
524 |
+
{
|
525 |
global $wpdb;
|
526 |
static $migTypes = array(
|
527 |
3000 => 5006
|
528 |
);
|
529 |
+
|
530 |
// load data
|
531 |
$sql = 'SELECT * FROM ' . $wpdb->base_prefix . 'wordpress_auditlog_events';
|
532 |
$events = array();
|
533 |
+
foreach ($wpdb->get_results($sql, ARRAY_A) as $item) {
|
534 |
$events[$item['EventID']] = $item;
|
535 |
+
}
|
536 |
$sql = 'SELECT * FROM ' . $wpdb->base_prefix . 'wordpress_auditlog';
|
537 |
$auditlog = $wpdb->get_results($sql, ARRAY_A);
|
538 |
+
|
539 |
// migrate using db logger
|
540 |
+
foreach ($auditlog as $entry) {
|
541 |
$data = array(
|
542 |
'ClientIP' => $entry['UserIP'],
|
543 |
'UserAgent' => '',
|
544 |
'CurrentUserID' => $entry['UserID'],
|
545 |
);
|
546 |
+
if ($entry['UserName']) {
|
547 |
$data['Username'] = base64_decode($entry['UserName']);
|
548 |
+
}
|
549 |
$mesg = $events[$entry['EventID']]['EventDescription'];
|
550 |
$date = strtotime($entry['EventDate']);
|
551 |
$type = $entry['EventID'];
|
552 |
+
if (isset($migTypes[$type])) {
|
553 |
+
$type = $migTypes[$type];
|
554 |
+
}
|
555 |
// convert message from '<strong>%s</strong>' to '%Arg1%' format
|
556 |
+
$c = 0;
|
557 |
+
$n = '<strong>%s</strong>';
|
558 |
+
$l = strlen($n);
|
559 |
+
while (($pos = strpos($mesg, $n)) !== false) {
|
560 |
$mesg = substr_replace($mesg, '%MigratedArg' . ($c++) .'%', $pos, $l);
|
561 |
}
|
562 |
$data['MigratedMesg'] = $mesg;
|
563 |
// generate new meta data args
|
564 |
$temp = unserialize(base64_decode($entry['EventData']));
|
565 |
+
foreach ((array)$temp as $i => $item) {
|
566 |
$data['MigratedArg' . $i] = $item;
|
567 |
+
}
|
568 |
// send event data to logger!
|
569 |
+
foreach ($this->alerts->GetLoggers() as $logger) {
|
570 |
$logger->Log($type, $data, $date, $entry['BlogId'], true);
|
571 |
}
|
572 |
}
|
573 |
+
|
574 |
// migrate settings
|
575 |
$this->settings->SetAllowedPluginEditors(
|
576 |
get_option('WPPH_PLUGIN_ALLOW_CHANGE')
|
584 |
$this->settings->SetViewPerPage(max($s->showEventsViewList, 5));
|
585 |
$this->settings->SetWidgetsEnabled(!!$s->showDW);
|
586 |
}
|
587 |
+
|
588 |
// </editor-fold>
|
589 |
+
|
590 |
// <editor-fold desc="Utility Methods">
|
591 |
+
|
592 |
/**
|
593 |
* @return string The current plugin version (according to plugin file metadata).
|
594 |
*/
|
595 |
+
public function GetNewVersion()
|
596 |
+
{
|
597 |
$version = get_plugin_data(__FILE__, false, false);
|
598 |
return isset($version['Version']) ? $version['Version'] : '0.0.0';
|
599 |
}
|
600 |
+
|
601 |
/**
|
602 |
* @return string The plugin version as stored in DB (will be the old version during an update/install).
|
603 |
*/
|
604 |
+
public function GetOldVersion()
|
605 |
+
{
|
606 |
return $this->GetGlobalOption('version', '0.0.0');
|
607 |
}
|
608 |
+
|
609 |
/**
|
610 |
* @internal To be called in admin header for hiding plugin form Plugins list.
|
611 |
*/
|
612 |
+
public function HidePlugin()
|
613 |
+
{
|
614 |
$selectr = '';
|
615 |
$plugins = array('wp-security-audit-log');
|
616 |
foreach ($this->licensing->Plugins() as $plugin) {
|
621 |
}
|
622 |
?><style type="text/css"> <?php echo rtrim($selectr, ", "); ?> { display: none; }</style><?php
|
623 |
}
|
624 |
+
|
625 |
/**
|
626 |
* Returns the class name of a particular file that contains the class.
|
627 |
* @param string $file File name.
|
628 |
* @return string Class name.
|
629 |
* @deprecated since 1.2.5 Use autoloader->GetClassFileClassName() instead.
|
630 |
*/
|
631 |
+
public function GetClassFileClassName($file)
|
632 |
+
{
|
633 |
return $this->autoloader->GetClassFileClassName($file);
|
634 |
}
|
635 |
+
|
636 |
/**
|
637 |
* @return boolean Whether we are running on multisite or not.
|
638 |
*/
|
639 |
+
public function IsMultisite()
|
640 |
+
{
|
641 |
return function_exists('is_multisite') && is_multisite();
|
642 |
}
|
643 |
+
|
644 |
/**
|
645 |
* Get a global option.
|
646 |
* @param string $option Option name.
|
648 |
* @param string $prefix (Optional) A prefix used before option name.
|
649 |
* @return mixed Option's value or $default if option not set.
|
650 |
*/
|
651 |
+
public function GetGlobalOption($option, $default = false, $prefix = self::OPT_PRFX)
|
652 |
+
{
|
|
|
|
|
653 |
$this->options = new WSAL_Models_Option();
|
654 |
+
return $this->options->GetOptionValue($prefix . $option, $default);
|
655 |
}
|
656 |
+
|
657 |
/**
|
658 |
* Set a global option.
|
659 |
* @param string $option Option name.
|
660 |
* @param mixed $value New value for option.
|
661 |
* @param string $prefix (Optional) A prefix used before option name.
|
662 |
*/
|
663 |
+
public function SetGlobalOption($option, $value, $prefix = self::OPT_PRFX)
|
664 |
+
{
|
|
|
665 |
$this->options = new WSAL_Models_Option();
|
666 |
$this->options->SetOptionValue($prefix . $option, $value);
|
667 |
}
|
668 |
+
|
669 |
/**
|
670 |
* Get a user-specific option.
|
671 |
* @param string $option Option name.
|
673 |
* @param string $prefix (Optional) A prefix used before option name.
|
674 |
* @return mixed Option's value or $default if option not set.
|
675 |
*/
|
676 |
+
public function GetUserOption($option, $default = false, $prefix = self::OPT_PRFX)
|
677 |
+
{
|
678 |
$result = get_user_option($prefix . $option, get_current_user_id());
|
679 |
return $result === false ? $default : $result;
|
680 |
}
|
681 |
+
|
682 |
/**
|
683 |
* Set a user-specific option.
|
684 |
* @param string $option Option name.
|
685 |
* @param mixed $value New value for option.
|
686 |
* @param string $prefix (Optional) A prefix used before option name.
|
687 |
*/
|
688 |
+
public function SetUserOption($option, $value, $prefix = self::OPT_PRFX)
|
689 |
+
{
|
690 |
update_user_option(get_current_user_id(), $prefix . $option, $value, false);
|
691 |
}
|
692 |
+
|
693 |
/**
|
694 |
* Run cleanup routines.
|
695 |
*/
|
696 |
+
public function CleanUp()
|
697 |
+
{
|
698 |
$s = $this->profiler->Start('Clean Up');
|
699 |
+
foreach ($this->_cleanup_hooks as $hook) {
|
700 |
call_user_func($hook);
|
701 |
+
}
|
702 |
$s->Stop();
|
703 |
}
|
704 |
+
|
705 |
/**
|
706 |
* Add callback to be called when a cleanup operation is required.
|
707 |
* @param callable $hook
|
708 |
*/
|
709 |
+
public function AddCleanupHook($hook)
|
710 |
+
{
|
711 |
$this->_cleanup_hooks[] = $hook;
|
712 |
}
|
713 |
+
|
714 |
/**
|
715 |
* Remove a callback from the cleanup callbacks list.
|
716 |
* @param callable $hook
|
717 |
*/
|
718 |
+
public function RemoveCleanupHook($hook)
|
719 |
+
{
|
720 |
+
while (($pos = array_search($hook, $this->_cleanup_hooks)) !== false) {
|
721 |
unset($this->_cleanup_hooks[$pos]);
|
722 |
+
}
|
723 |
}
|
724 |
|
725 |
+
/**
|
726 |
+
* DB connection.
|
727 |
+
* @param mixed $config DB configuration.
|
728 |
+
* @return WSAL_Connector_ConnectorInterface
|
729 |
+
*/
|
730 |
public static function getConnector($config = null, $reset = false)
|
731 |
{
|
732 |
return WSAL_Connector_ConnectorFactory::getConnector($config, $reset);
|
733 |
}
|
734 |
+
|
735 |
/**
|
736 |
* Do we have an existing installation? This only applies for version 1.0 onwards.
|
737 |
* @return boolean
|
738 |
*/
|
739 |
+
public function IsInstalled()
|
740 |
+
{
|
741 |
return self::getConnector()->isInstalled();
|
742 |
}
|
743 |
+
|
744 |
/**
|
745 |
* @return boolean Whether the old plugin was present or not.
|
746 |
*/
|
747 |
+
public function CanMigrate()
|
748 |
+
{
|
749 |
return self::getConnector()->canMigrate();
|
750 |
}
|
751 |
+
|
752 |
/**
|
753 |
* @return string Absolute URL to plugin directory WITHOUT final slash.
|
754 |
*/
|
755 |
+
public function GetBaseUrl()
|
756 |
+
{
|
757 |
return plugins_url('', __FILE__);
|
758 |
}
|
759 |
+
|
760 |
/**
|
761 |
* @return string Full path to plugin directory WITH final slash.
|
762 |
*/
|
763 |
+
public function GetBaseDir()
|
764 |
+
{
|
765 |
return plugin_dir_path(__FILE__);
|
766 |
}
|
767 |
+
|
768 |
/**
|
769 |
* @return string Plugin directory name.
|
770 |
*/
|
771 |
+
public function GetBaseName()
|
772 |
+
{
|
773 |
return plugin_basename(__FILE__);
|
774 |
}
|
775 |
+
|
776 |
/**
|
777 |
* Load default configuration / data.
|
778 |
*/
|
779 |
+
public function LoadDefaults()
|
780 |
+
{
|
781 |
$s = $this->profiler->Start('Load Defaults');
|
782 |
require_once('defaults.php');
|
783 |
$s->Stop();
|