PluginProbe ʕ •ᴥ•ʔ
Independent Analytics – WordPress Analytics Plugin / 2.14.0
Independent Analytics – WordPress Analytics Plugin v2.14.0
2.15.5 2.15.4 2.15.3 2.15.2 2.15.1 2.15.0 2.14.10 trunk 1.1 1.10 1.10.1 1.11 1.12 1.13 1.14 1.15 1.16 1.17 1.17.1 1.17.2 1.17.3 1.17.4 1.18 1.18.1 1.19.0 1.19.1 1.2 1.20.0 1.21.0 1.22.0 1.22.1 1.23.0 1.23.1 1.24.0 1.24.1 1.25.0 1.25.1 1.26.0 1.27.0 1.28.0 1.28.1 1.28.2 1.28.3 1.29.0 1.3 1.30.0 1.30.1 1.4 1.5 1.6 1.7 1.8 1.9 2.0.0 2.0.1 2.1.4 2.1.5 2.1.6 2.10.0 2.10.1 2.10.2 2.10.3 2.10.4 2.11.0 2.11.1 2.11.10 2.11.2 2.11.3 2.11.4 2.11.5 2.11.6 2.11.7 2.11.8 2.11.9 2.12.0 2.12.1 2.12.2 2.13.1 2.13.2 2.13.5 2.13.6 2.14.0 2.14.1 2.14.2 2.14.4 2.14.6 2.14.7 2.14.8 2.14.9 2.2.0 2.2.1 2.3.1 2.3.2 2.4.2 2.4.3 2.5.0 2.5.1 2.6.0 2.6.1 2.6.2 2.6.3 2.6.4 2.7.0 2.7.1 2.7.2 2.7.3 2.8.2 2.8.3 2.8.4 2.8.5 2.8.6 2.8.7 2.8.8 2.8.9 2.9.2 2.9.3 2.9.4 2.9.5 2.9.6 2.9.7
independent-analytics / IAWP / Independent_Analytics.php
independent-analytics / IAWP Last commit date
AJAX 7 months ago Admin_Page 7 months ago Click_Tracking 9 months ago ColumnOptions 7 months ago Cron 10 months ago Custom_WordPress_Columns 9 months ago Data_Pruning 9 months ago Date_Picker 1 year ago Date_Range 1 year ago Ecommerce 7 months ago Email_Reports 7 months ago Examiner 1 year ago Favicon 7 months ago Form_Submissions 7 months ago Integrations 7 months ago Interval 1 year ago Journey 7 months ago Migrations 9 months ago Models 7 months ago Overview 9 months ago Public_API 10 months ago Rows 7 months ago Statistics 7 months ago Tables 7 months ago Utils 7 months ago Views 10 months ago WooCommerceOrderMetaBox 7 months ago Admin_Bar_Stats.php 7 months ago Appearance.php 1 year ago Campaign_Builder.php 1 year ago Capability_Manager.php 1 year ago Chart.php 10 months ago Chart_Data.php 1 year ago Click_Tracking.php 1 year ago Cron_Job.php 7 months ago Cron_Manager.php 7 months ago Current_Traffic_Finder.php 1 year ago Dashboard_Options.php 7 months ago Dashboard_Widget.php 2 years ago Database.php 10 months ago Database_Manager.php 7 months ago Empty_Report_Option.php 2 years ago Env.php 7 months ago Examiner_Config.php 1 year ago FetchFaviconsJob.php 7 months ago Filters.php 7 months ago Geo_Database_Health_Check_Job.php 10 months ago Geo_Database_Manager.php 7 months ago Geoposition.php 1 year ago Icon_Directory.php 7 months ago Icon_Directory_Factory.php 2 years ago Illuminate_Builder.php 1 year ago Independent_Analytics.php 7 months ago Interrupt.php 1 year ago Known_Referrers.php 7 months ago MainWP.php 1 year ago Map.php 10 months ago Map_Data.php 1 year ago Migration_Fixer_Job.php 9 months ago Patch.php 1 year ago Payload_Validator.php 10 months ago Plugin_Conflict_Detector.php 7 months ago Plugin_Group.php 7 months ago Plugin_Group_Option.php 2 years ago Query.php 1 year ago Query_Taps.php 9 months ago Quick_Stats.php 1 year ago REST_API.php 7 months ago Real_Time.php 10 months ago Report.php 1 year ago Report_Finder.php 7 months ago Report_Options_Parser.php 10 months ago Resource_Identifier.php 10 months ago Settings.php 7 months ago Sort_Configuration.php 10 months ago Tables.php 9 months ago Track_Resource_Changes.php 1 year ago View_Counter.php 7 months ago Views_Over_Time_Finder.php 1 year ago VisitorSaltRefreshInterval.php 7 months ago WP_Option_Cache_Bust.php 2 years ago
Independent_Analytics.php
638 lines
1 <?php
2
3 namespace IAWP;
4
5 use IAWPSCOPED\Carbon\CarbonImmutable;
6 use IAWPSCOPED\Carbon\CarbonInterval;
7 use IAWP\Admin_Page\Analytics_Page;
8 use IAWP\Admin_Page\Campaign_Builder_Page;
9 use IAWP\Admin_Page\Click_Tracking_Page;
10 use IAWP\Admin_Page\Debug_Page;
11 use IAWP\Admin_Page\Integrations_Pages;
12 use IAWP\Admin_Page\Settings_Page;
13 use IAWP\Admin_Page\Support_Page;
14 use IAWP\Admin_Page\Updates_Page;
15 use IAWP\Admin_Page\Visitor_Page;
16 use IAWP\AJAX\AJAX_Manager;
17 use IAWP\Click_Tracking\Click_Processing_Job;
18 use IAWP\Data_Pruning\Pruner;
19 use IAWP\Ecommerce\EDD_Order;
20 use IAWP\Ecommerce\Fluent_Cart_Order;
21 use IAWP\Ecommerce\PMPro_Order;
22 use IAWP\Ecommerce\SureCart_Event_Sync_Job;
23 use IAWP\Ecommerce\SureCart_Order;
24 use IAWP\Ecommerce\SureCart_Store;
25 use IAWP\Ecommerce\WooCommerce_Order;
26 use IAWP\Email_Reports\Email_Reports;
27 use IAWP\Form_Submissions\Form;
28 use IAWP\Form_Submissions\Submission_Listener;
29 use IAWP\Journey\JourneyStatisticsJob;
30 use IAWP\Migrations\Migrations;
31 use IAWP\Overview\Module_Refresh_Job;
32 use IAWP\Utils\Plugin;
33 use IAWP\Utils\Request;
34 use IAWP\Utils\Singleton;
35 use IAWP\Utils\Timezone;
36 use IAWP\WooCommerceOrderMetaBox\WooCommerceOrderMetaBox;
37 use IAWPSCOPED\Illuminate\Support\Carbon;
38 use IAWPSCOPED\Illuminate\Support\Str;
39 /** @internal */
40 class Independent_Analytics
41 {
42 use Singleton;
43 public $settings;
44 public $email_reports;
45 public $cron_manager;
46 private $is_woocommerce_support_enabled;
47 private $is_surecart_support_enabled;
48 private $is_edd_support_enabled;
49 private $is_pmpro_support_enabled;
50 private $is_fluent_cart_support_enabled;
51 private $is_form_submission_support_enabled;
52 // This is where we attach functions to WP hooks
53 private function __construct()
54 {
55 $this->configure_carbon();
56 $this->settings = new \IAWP\Settings();
57 new \IAWP\REST_API();
58 new \IAWP\Dashboard_Widget();
59 new \IAWP\View_Counter();
60 new Submission_Listener();
61 Pruner::register_hook();
62 AJAX_Manager::getInstance();
63 if (!Migrations::is_migrating()) {
64 new \IAWP\Track_Resource_Changes();
65 \IAWP\Admin_Bar_Stats::register();
66 WooCommerce_Order::register_hooks();
67 EDD_Order::register_hooks();
68 PMPro_Order::register_hooks();
69 SureCart_Order::register_hooks();
70 Fluent_Cart_Order::register_hooks();
71 }
72 \IAWP\Cron_Job::register_custom_intervals();
73 $this->cron_manager = new \IAWP\Cron_Manager();
74 (new SureCart_Event_Sync_Job())->register_handler();
75 (new JourneyStatisticsJob())->register_handler();
76 (new \IAWP\FetchFaviconsJob())->register_handler();
77 (new Click_Processing_Job())->register_handler();
78 (new Module_Refresh_Job())->register_handler();
79 (new \IAWP\Migration_Fixer_Job())->register_handler();
80 (new \IAWP\Geo_Database_Health_Check_Job())->register_handler();
81 if (\IAWPSCOPED\iawp_is_pro()) {
82 $this->email_reports = new Email_Reports();
83 new \IAWP\Campaign_Builder();
84 WooCommerceOrderMetaBox::register();
85 }
86 \add_action('admin_enqueue_scripts', [$this, 'enqueue_scripts_and_styles'], 110);
87 // Called at 110 to dequeue other scripts
88 \add_action('wp_enqueue_scripts', [$this, 'enqueue_scripts_and_styles_front_end']);
89 \add_action('admin_menu', [$this, 'add_admin_menu_pages']);
90 \add_action('admin_init', [$this, 'remove_freemius_pricing_menu']);
91 \add_filter('plugin_action_links_independent-analytics/iawp.php', [$this, 'plugin_action_links']);
92 \add_action('init', [$this, 'polylang_translations']);
93 \add_action('init', [$this, 'load_text_domain']);
94 // Freemius adjustments
95 \IAWP_FS()->add_filter('pricing_url', [$this, 'change_freemius_pricing_url'], 10);
96 \IAWP_FS()->add_filter('show_affiliate_program_notice', '__return_false');
97 \IAWP_FS()->add_filter('show_deactivation_feedback_form', function () {
98 return \false;
99 });
100 \IAWP_FS()->add_filter('connect-header', [$this, 'freemius_optin_heading']);
101 \IAWP_FS()->add_filter('connect_message', [$this, 'freemius_optin_text']);
102 if (\function_exists('IAWPSCOPED\\fs_override_i18n')) {
103 fs_override_i18n(['opt-in-connect' => \__('Subscribe & Go To Analytics', 'independent-analytics'), 'skip' => \__('No, thanks', 'independent-analytics')], 'independent-analytics');
104 }
105 // Other hooks
106 \add_action('admin_init', [$this, 'maybe_delete_mu_plugin']);
107 \add_action('admin_body_class', [$this, 'add_body_class']);
108 \add_filter('sgs_whitelist_wp_content', [$this, 'whitelist_click_endpoint']);
109 \add_filter('cmplz_whitelisted_script_tags', [$this, 'whitelist_script_tag_for_complianz']);
110 \add_filter('plugin_action_links_independent-analytics/iawp.php', [$this, 'add_upgrade_link_in_plugins_menu'], 999);
111 \add_filter('plugin_row_meta', [$this, 'add_docs_link_in_plugins_menu'], 10, 2);
112 \add_action('admin_footer', [$this, 'attach_system_appearance_script'], 99, 0);
113 \add_filter('sgo_javascript_combine_excluded_inline_content', [$this, 'exclude_tracking_script_from_speed_optimizer'], 10, 1);
114 \add_action('admin_init', [$this, 'maybe_add_cookie']);
115 }
116 public function add_upgrade_link_in_plugins_menu($links)
117 {
118 if (\IAWPSCOPED\iawp_is_pro()) {
119 return $links;
120 }
121 $upgrade_link = '<a target="_blank" style="color:#36B366;font-weight:700;"
122 href="https://independentwp.com/pro/?utm_source=User+Dashboard&utm_medium=WP+Admin&utm_campaign=Plugin+Settings+Link"
123 >' . \esc_html__('Upgrade to Pro', 'independent-analytics') . '</a>';
124 \array_unshift($links, $upgrade_link);
125 return $links;
126 }
127 public function add_docs_link_in_plugins_menu($plugin_meta, $plugin_file)
128 {
129 if ($plugin_file == 'independent-analytics/iawp.php' || $plugin_file == 'independent-analytics-pro/iawp.php') {
130 $plugin_meta[] = '<a target="_blank" href="https://independentwp.com/knowledgebase/">' . \esc_html__('Knowledge Base', 'independent-analytics') . '</a>';
131 }
132 return $plugin_meta;
133 }
134 /**
135 * Attach some JavaScript to manage the color scheme for admin pages.
136 *
137 * @return void
138 */
139 public function attach_system_appearance_script() : void
140 {
141 ?>
142 <script>
143 ;(() => {
144 try {
145 const isLightMode = document.body.classList.contains('iawp-light-mode')
146 const isDarkMode = document.body.classList.contains('iawp-dark-mode')
147 const isSystem = !isLightMode && !isDarkMode
148
149 // Stop if they're not using the systems color scheme
150 if(!isSystem) {
151 return
152 }
153
154 // Switch to dark mode if dark is the system color scheme preference
155 if (window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches) {
156 document.body.classList.add('iawp-dark-mode')
157 }
158
159 // Watching for changes is a nice idea, but it's more complicated than just
160 // adding or removing a class from the body. There are elements like
161 // charts that cannot adapt without a rendered. Holding off on this.
162
163 // window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', event => {
164 // if(event.matches) {
165 // document.body.classList.remove('iawp-light-mode')
166 // document.body.classList.add('iawp-dark-mode')
167 // } else {
168 // document.body.classList.remove('iawp-dark-mode')
169 // document.body.classList.add('iawp-light-mode')
170 // }
171 // });
172 } catch (error) {
173
174 }
175 })();
176
177 </script>
178 <?php
179 }
180 public function add_body_class(string $classes) : string
181 {
182 $newClasses = [];
183 if (\IAWP\Appearance::is_light()) {
184 $newClasses[] = 'iawp-light-mode';
185 } elseif (\IAWP\Appearance::is_dark()) {
186 $newClasses[] = 'iawp-dark-mode';
187 }
188 $page = \IAWP\Env::get_page();
189 if (\is_string($page)) {
190 $newClasses[] = $page;
191 }
192 if (\array_key_exists('examiner', $_GET)) {
193 $newClasses[] = 'iawp-in-examiner';
194 }
195 return $classes . ' ' . \implode(' ', $newClasses) . ' ';
196 }
197 /**
198 * At one point in time, there was a must-use plugin that was created. The plugin file and the
199 * option need to get cleaned up.
200 * @return void
201 */
202 public function maybe_delete_mu_plugin()
203 {
204 $already_attempted = \get_option('iawp_attempted_to_delete_mu_plugin', '0');
205 if ($already_attempted === '1') {
206 return;
207 }
208 if (\get_option('iawp_must_use_directory_not_writable', '0') === '1') {
209 \delete_option('iawp_must_use_directory_not_writable');
210 }
211 $mu_plugin_file = \trailingslashit(\WPMU_PLUGIN_DIR) . 'iawp-performance-boost.php';
212 if (\file_exists($mu_plugin_file)) {
213 \unlink($mu_plugin_file);
214 }
215 \update_option('iawp_attempted_to_delete_mu_plugin', '1', \true);
216 }
217 public function load_text_domain()
218 {
219 \load_plugin_textdomain('independent-analytics', \false, \IAWP_LANGUAGES_DIRECTORY);
220 // Freemius overrides must happen after the text domain is loaded
221 \IAWP_FS()->override_i18n(['yee-haw' => \__('Success', 'independent-analytics')]);
222 }
223 public function polylang_translations()
224 {
225 if (\function_exists('IAWPSCOPED\\pll_register_string')) {
226 pll_register_string('view_counter', 'Views:', 'Independent Analytics');
227 }
228 }
229 // Changes the URL for the "Upgrade" tab in the Account menu
230 public function change_freemius_pricing_url()
231 {
232 return 'https://independentwp.com/pro/?utm_source=User+Dashboard&utm_medium=WP+Admin&utm_campaign=Upgrade+to+Pro&utm_content=Account';
233 }
234 public function freemius_optin_heading()
235 {
236 return '<h2>' . \esc_html__('Congratulations on Your New Analytics! 🎉', 'independent-analytics') . '</h2>';
237 }
238 public function freemius_optin_text()
239 {
240 $html = '<p>' . \esc_html__("You've just taken the first step towards building a better website.", "independent-analytics") . '</p>';
241 $html .= '<br />';
242 $html .= '<p>' . \esc_html__("If you signup for our free email course, we’ll walk you through each feature in Independent Analytics, so you can learn how to analyze and optimize your website for growth.", "independent-analytics") . '</p>';
243 $html .= '<br />';
244 $html .= '<p><strong>' . \esc_html_x("Subscribe now and you'll receive our:", "What follows is a list of benefits", "independent-analytics") . '</strong></p>';
245 $html .= '<ul>';
246 $html .= '<li><span class="dashicons dashicons-yes-alt"></span> ' . \esc_html__('Free email tutorial series', 'independent-analytics') . '</li>';
247 $html .= '<li><span class="dashicons dashicons-yes-alt"></span> ' . \esc_html__('Subscriber-only sales announcements', 'independent-analytics') . '</li>';
248 $html .= '<li><span class="dashicons dashicons-yes-alt"></span> ' . \esc_html__('New feature updates', 'independent-analytics') . '</li>';
249 $html .= '<li><span class="dashicons dashicons-yes-alt"></span> ' . \esc_html__('Security alerts', 'independent-analytics') . '</li>';
250 $html .= '</ul>';
251 $html .= '<p>' . \esc_html('Subscribing will also share some basic info about your WordPress site with us, which helps us make Independent Analytics an even better plugin for everyone.', 'independent-analytics') . '</p>';
252 $html .= '<p class="rating">' . \sprintf(\esc_html__('Rated %s and trusted by over 100,000+ WordPress websites.', 'independent-analytics'), '<span class="star-container"><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span></span>') . '</p>';
253 $html .= '<img src="' . \IAWPSCOPED\iawp_url_to('img/email-review.png') . '" />';
254 return $html;
255 }
256 public function add_admin_menu_pages()
257 {
258 $title = \IAWP\Capability_Manager::show_white_labeled_ui() ? \esc_html__('Analytics', 'independent-analytics') : 'Independent Analytics';
259 \add_menu_page($title, \esc_html__('Analytics', 'independent-analytics'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics', function () {
260 $analytics_page = new Analytics_Page();
261 $analytics_page->render();
262 }, $this->get_menu_icon(), 3);
263 if (\IAWP\Capability_Manager::can_edit()) {
264 \add_submenu_page('independent-analytics', \esc_html__('Settings', 'independent-analytics'), \esc_html__('Settings', 'independent-analytics'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-settings', function () {
265 $settings_page = new Settings_Page();
266 $settings_page->render(\false);
267 });
268 }
269 if (\IAWPSCOPED\iawp_is_pro()) {
270 \add_submenu_page('independent-analytics', \esc_html__('Campaign Builder', 'independent-analytics'), \esc_html__('Campaign Builder', 'independent-analytics'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-campaign-builder', function () {
271 $campaign_builder_page = new Campaign_Builder_Page();
272 $campaign_builder_page->render(\false);
273 });
274 if (\IAWP\Capability_Manager::can_edit()) {
275 \add_submenu_page('independent-analytics', \esc_html__('Click Tracking', 'independent-analytics'), \esc_html__('Click Tracking', 'independent-analytics'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-click-tracking', function () {
276 $click_tracking_page = new Click_Tracking_Page();
277 $click_tracking_page->render(\false);
278 });
279 }
280 }
281 if (\IAWP\Capability_Manager::show_branded_ui()) {
282 \add_submenu_page('independent-analytics', \esc_html__('Help & Support', 'independent-analytics'), \esc_html__('Help & Support', 'independent-analytics'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-support-center', function () {
283 $support_page = new Support_Page();
284 $support_page->render(\false);
285 });
286 }
287 if (\IAWP\Capability_Manager::show_branded_ui()) {
288 \add_submenu_page('independent-analytics', \esc_html__('Integrations', 'independent-analytics'), \esc_html__('Integrations', 'independent-analytics'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-integrations', function () {
289 $integrations_page = new Integrations_Pages();
290 $integrations_page->render(\false);
291 });
292 }
293 if (\IAWP\Capability_Manager::show_branded_ui()) {
294 $menu_html = '<span class="menu-name">' . \esc_html__('Changelog', 'independent-analytics') . '</span>';
295 $menu_html = $this->changelog_viewed_since_update() ? $menu_html . ' <span class="menu-counter">' . \esc_html__('New', 'independent-analytics') . '</span>' : $menu_html;
296 \add_submenu_page('independent-analytics', \esc_html__('Changelog', 'independent-analytics'), $menu_html, \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-updates', function () {
297 $updates_page = new Updates_Page();
298 $updates_page->render(\false);
299 });
300 }
301 if (\IAWPSCOPED\iawp_is_free() && \IAWP\Capability_Manager::show_branded_ui()) {
302 \add_submenu_page('independent-analytics', \esc_html__('Upgrade to Pro &rarr;', 'independent-analytics'), '<span style="color: #F69D0A;">' . \esc_html__('Upgrade to Pro &rarr;', 'independent-analytics') . '</span>', \IAWP\Capability_Manager::menu_page_capability_string(), \esc_url('https://independentwp.com/pro/?utm_source=User+Dashboard&utm_medium=WP+Admin&utm_campaign=Upgrade+to+Pro&utm_content=Sidebar'));
303 }
304 if (\IAWP\Capability_Manager::can_edit()) {
305 \add_submenu_page('options.php', \__('Independent Analytics Debug'), \__('Independent Analytics Debug'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-debug', function () {
306 $debug_page = new Debug_Page();
307 $debug_page->render(\false);
308 });
309 }
310 if (\IAWPSCOPED\iawp_is_pro() && \IAWP\Capability_Manager::can_view()) {
311 \add_submenu_page('options.php', \__('Journey'), \__('Journey'), \IAWP\Capability_Manager::menu_page_capability_string(), 'independent-analytics-visitor', function () {
312 $page = new Visitor_Page();
313 $page->render();
314 });
315 }
316 }
317 // The menu link is removed in the SDK setup, but this makes it completely inaccessible
318 public function remove_freemius_pricing_menu()
319 {
320 \remove_submenu_page('independent-analytics', 'independent-analytics-pricing');
321 }
322 public function register_scripts_and_styles() : void
323 {
324 \wp_register_style('iawp-styles', \IAWPSCOPED\iawp_url_to('dist/styles/style.css'), [], \IAWP_VERSION);
325 \wp_register_style('iawp-dashboard-widget-styles', \IAWPSCOPED\iawp_url_to('dist/styles/dashboard_widget.css'), [], \IAWP_VERSION);
326 \wp_register_style('iawp-freemius-notice-styles', \IAWPSCOPED\iawp_url_to('dist/styles/freemius_notice_styles.css'), [], \IAWP_VERSION);
327 \wp_register_style('iawp-posts-menu-styles', \IAWPSCOPED\iawp_url_to('dist/styles/posts_menu.css'), [], \IAWP_VERSION);
328 \wp_register_style('iawp-wc-order-box-styles', \IAWPSCOPED\iawp_url_to('dist/styles/wc_order_box.css'), [], \IAWP_VERSION);
329 \wp_register_script('iawp-javascript', \IAWPSCOPED\iawp_url_to('dist/js/index.js'), ['wp-i18n'], \IAWP_VERSION);
330 \wp_set_script_translations('iawp-javascript', 'independent-analytics');
331 \wp_register_script('iawp-dashboard-widget-javascript', \IAWPSCOPED\iawp_url_to('dist/js/dashboard_widget.js'), ['wp-i18n'], \IAWP_VERSION);
332 \wp_set_script_translations('iawp-dashboard-widget-javascript', 'independent-analytics');
333 \wp_register_script('iawp-layout-javascript', \IAWPSCOPED\iawp_url_to('dist/js/layout.js'), ['wp-i18n'], \IAWP_VERSION);
334 \wp_set_script_translations('iawp-layout-javascript', 'independent-analytics');
335 \wp_register_script('iawp-settings-javascript', \IAWPSCOPED\iawp_url_to('dist/js/settings.js'), ['wp-color-picker', 'wp-i18n'], \IAWP_VERSION);
336 \wp_set_script_translations('iawp-settings-javascript', 'independent-analytics');
337 \wp_register_script('iawp-click-tracking-menu-javascript', \IAWPSCOPED\iawp_url_to('dist/js/click-tracking-menu.js'), ['wp-i18n'], \IAWP_VERSION);
338 \wp_set_script_translations('iawp-click-tracking-menu-javascript', 'independent-analytics');
339 if (\IAWP\Admin_Bar_Stats::is_option_enabled()) {
340 \wp_register_style('iawp-admin-bar-stats', \IAWPSCOPED\iawp_url_to('dist/styles/admin_bar_stats.css'), [], \IAWP_VERSION);
341 }
342 if (\is_rtl()) {
343 \wp_register_style('iawp-styles-rtl', \IAWPSCOPED\iawp_url_to('dist/styles/rtl.css'), [], \IAWP_VERSION);
344 }
345 }
346 public function enqueue_scripts_and_styles($hook)
347 {
348 $this->register_scripts_and_styles();
349 $page = \IAWP\Env::get_page();
350 $this->enqueue_translations();
351 $this->enqueue_nonces();
352 \wp_enqueue_style('iawp-freemius-notice-styles');
353 if (\is_string($page)) {
354 \wp_enqueue_style('iawp-styles');
355 \wp_enqueue_script('iawp-javascript');
356 \wp_enqueue_script('iawp-layout-javascript');
357 $this->dequeue_bad_actors();
358 $this->maybe_override_adminify_styles();
359 if (\is_rtl()) {
360 \wp_enqueue_style('iawp-styles-rtl');
361 }
362 }
363 if ($page === 'independent-analytics-settings') {
364 \wp_enqueue_style('wp-color-picker');
365 \wp_enqueue_script('iawp-settings-javascript');
366 } elseif ($page === 'independent-analytics-click-tracking') {
367 \wp_enqueue_script('iawp-click-tracking-menu-javascript');
368 } elseif ($hook === 'index.php') {
369 \wp_enqueue_script('iawp-dashboard-widget-javascript');
370 \wp_enqueue_style('iawp-dashboard-widget-styles');
371 } elseif ($hook === 'edit.php') {
372 \wp_enqueue_style('iawp-posts-menu-styles');
373 } elseif (\IAWPSCOPED\iawp_is_pro() && $this->is_woocommerce_support_enabled() && $hook == 'woocommerce_page_wc-orders') {
374 \wp_enqueue_style('iawp-wc-order-box-styles');
375 }
376 if (\IAWP\Admin_Bar_Stats::is_option_enabled()) {
377 \wp_enqueue_style('iawp-admin-bar-stats');
378 }
379 }
380 public function enqueue_scripts_and_styles_front_end()
381 {
382 if (\IAWP\Admin_Bar_Stats::is_option_enabled()) {
383 \wp_register_style('iawp-admin-bar-stats', \IAWPSCOPED\iawp_url_to('dist/styles/admin_bar_stats.css'), [], \IAWP_VERSION);
384 \wp_enqueue_style('iawp-admin-bar-stats');
385 }
386 }
387 public function enqueue_translations()
388 {
389 \wp_register_script('iawp-translations', '');
390 \wp_enqueue_script('iawp-translations');
391 \wp_add_inline_script('iawp-translations', 'const iawpText = ' . \json_encode(['views' => \__('Views', 'independent-analytics'), 'visitors' => \__('Visitors', 'independent-analytics'), 'sessions' => \__('Sessions', 'independent-analytics'), 'exactDates' => \__('Apply Exact Dates', 'independent-analytics'), 'relativeDates' => \__('Apply Relative Dates', 'independent-analytics'), 'copied' => \__('Copied', 'independent-analytics'), 'exportingPages' => \__('Exporting Pages...', 'independent-analytics'), 'exportPages' => \__('Export Pages', 'independent-analytics'), 'exportingReferrers' => \__('Exporting Referrers...', 'independent-analytics'), 'exportReferrers' => \__('Export Referrers', 'independent-analytics'), 'exportingGeolocations' => \__('Exporting Geolocations...', 'independent-analytics'), 'exportGeolocations' => \__('Export Geolocations', 'independent-analytics'), 'exportingDevices' => \__('Exporting Devices...', 'independent-analytics'), 'exportDevices' => \__('Export Devices', 'independent-analytics'), 'exportingCampaigns' => \__('Exporting Campaigns...', 'independent-analytics'), 'exportCampaigns' => \__('Export Campaigns', 'independent-analytics'), 'exportingClicks' => \__('Exporting Clicks', 'independent-analytics'), 'exportClicks' => \__('Export Clicks', 'independent-analytics'), 'invalidReportArchive' => \__('This report archive is invalid. Please export your reports and try again.', 'independent-analytics'), 'openMobileMenu' => \__('Open menu', 'independent-analytics'), 'closeMobileMenu' => \__('Close menu', 'independent-analytics'), 'noComparison' => \__('No Comparison', 'independent-analytics')]), 'before');
392 }
393 public function enqueue_nonces()
394 {
395 \wp_register_script('iawp-nonces', '');
396 \wp_enqueue_script('iawp-nonces');
397 \wp_add_inline_script('iawp-nonces', 'const iawpActions = ' . \json_encode(AJAX_Manager::getInstance()->get_action_signatures()), 'before');
398 }
399 public function get_option($name, $default)
400 {
401 $option = \get_option($name, $default);
402 return $option === '' ? $default : $option;
403 }
404 public function date_i18n(string $format, \DateTime $date) : string
405 {
406 return \date_i18n($format, $date->setTimezone(Timezone::site_timezone())->getTimestamp() + Timezone::site_offset_in_seconds($date));
407 }
408 public function plugin_action_links($links)
409 {
410 // Create the link
411 $settings_link = '<a class="calendar-link" href="' . \esc_url(\IAWPSCOPED\iawp_dashboard_url()) . '">' . \esc_html__('Analytics Dashboard', 'independent-analytics') . '</a>';
412 // Add the link to the start of the array
413 \array_unshift($links, $settings_link);
414 return $links;
415 }
416 public function pagination_page_size()
417 {
418 return 50;
419 }
420 public function dequeue_bad_actors()
421 {
422 // https://wordpress.org/plugins/comment-link-remove/
423 \wp_dequeue_style('qc_clr_admin_style_css');
424 // https://wordpress.org/plugins/webappick-pdf-invoice-for-woocommerce/
425 \wp_dequeue_style('woo-invoice');
426 // https://wordpress.org/plugins/wp-media-files-name-rename/
427 \wp_dequeue_style('wpcmp_bootstrap_css');
428 // https://wordpress.org/plugins/morepuzzles/
429 \wp_dequeue_style('bscss');
430 \wp_dequeue_style('mypluginstyle');
431 }
432 public function maybe_override_adminify_styles()
433 {
434 if (\is_plugin_active('adminify/adminify.php')) {
435 $settings = \get_option('_wpadminify');
436 if ($settings) {
437 if (\array_key_exists('admin_ui', $settings)) {
438 if ($settings['admin_ui']) {
439 \wp_register_style('iawp-adminify-styles', \IAWPSCOPED\iawp_url_to('dist/styles/adminify.css'), [], \IAWP_VERSION);
440 \wp_enqueue_style('iawp-adminify-styles');
441 }
442 }
443 }
444 }
445 }
446 public function maybe_add_cookie()
447 {
448 if (Request::is_blocked_user_role() && $this->get_option('iawp_ignore_via_cookie', \false)) {
449 if (!isset($_COOKIE['iawp_ignore_visitor'])) {
450 \setcookie('iawp_ignore_visitor', '1', \time() + 365 * 24 * 60 * 60, \COOKIEPATH, \COOKIE_DOMAIN);
451 }
452 }
453 }
454 public function changelog_viewed_since_update() : bool
455 {
456 if (\number_format(\floatval(\IAWP_VERSION), 1) > \floatval($this->get_option('iawp_last_update_viewed', '0'))) {
457 return \true;
458 }
459 return \false;
460 }
461 public function is_form_submission_support_enabled() : bool
462 {
463 if (!\is_bool($this->is_form_submission_support_enabled)) {
464 $this->is_form_submission_support_enabled = \IAWPSCOPED\iawp_is_pro() && Form::has_active_form_plugin() && \IAWP\Capability_Manager::can_view_all_analytics();
465 }
466 return $this->is_form_submission_support_enabled;
467 }
468 public function is_woocommerce_support_enabled() : bool
469 {
470 if (!\is_bool($this->is_woocommerce_support_enabled)) {
471 $this->is_woocommerce_support_enabled = $this->actually_check_if_woocommerce_support_is_enabled();
472 }
473 return $this->is_woocommerce_support_enabled;
474 }
475 public function is_surecart_support_enabled() : bool
476 {
477 if (!\is_bool($this->is_surecart_support_enabled)) {
478 $this->is_surecart_support_enabled = $this->actually_check_if_surecart_support_is_enabled();
479 }
480 return $this->is_surecart_support_enabled;
481 }
482 public function is_edd_support_enabled() : bool
483 {
484 if (!\is_bool($this->is_edd_support_enabled)) {
485 $this->is_edd_support_enabled = $this->actually_check_if_edd_support_is_enabled();
486 }
487 return $this->is_edd_support_enabled;
488 }
489 public function is_pmpro_support_enabled() : bool
490 {
491 if (!\is_bool($this->is_pmpro_support_enabled)) {
492 $this->is_pmpro_support_enabled = $this->actually_check_if_pmpro_support_is_enabled();
493 }
494 return $this->is_pmpro_support_enabled;
495 }
496 public function is_fluent_cart_support_enabled() : bool
497 {
498 if (!\is_bool($this->is_fluent_cart_support_enabled)) {
499 $this->is_fluent_cart_support_enabled = $this->actually_check_if_fluent_cart_support_is_enabled();
500 }
501 return $this->is_fluent_cart_support_enabled;
502 }
503 public function is_ecommerce_support_enabled() : bool
504 {
505 return $this->is_woocommerce_support_enabled() || $this->is_surecart_support_enabled() || $this->is_edd_support_enabled() || $this->is_pmpro_support_enabled() || $this->is_fluent_cart_support_enabled();
506 }
507 public function get_currency_code() : ?string
508 {
509 if ($this->is_woocommerce_support_enabled()) {
510 return get_woocommerce_currency();
511 }
512 if ($this->is_surecart_support_enabled()) {
513 return SureCart_Store::get_currency_code();
514 }
515 if ($this->is_edd_support_enabled()) {
516 return \edd_get_currency();
517 }
518 if ($this->is_pmpro_support_enabled()) {
519 global $pmpro_default_currency;
520 return $pmpro_default_currency;
521 }
522 if ($this->is_fluent_cart_support_enabled()) {
523 $settings = new \FluentCart\Api\StoreSettings();
524 return $settings->getCurrency();
525 }
526 return null;
527 }
528 // This is for compatibility with the "Lock and Protect System Folders" setting in the Security Optimizer plugin
529 public function whitelist_click_endpoint($whitelist)
530 {
531 if (\IAWPSCOPED\iawp_is_free()) {
532 return $whitelist;
533 }
534 $whitelist[] = 'iawp-click-endpoint.php';
535 return $whitelist;
536 }
537 public function exclude_tracking_script_from_speed_optimizer($exclude_list)
538 {
539 $exclude_list[] = '// Do not change this comment line otherwise Speed Optimizer won\'t be able to detect this script';
540 return $exclude_list;
541 }
542 // This whitelists our plugin with the "Complianz" plugin
543 public function whitelist_script_tag_for_complianz($scripts)
544 {
545 $scripts[] = '/wp-json/iawp/search';
546 return $scripts;
547 }
548 public function prefers_24_hour_clock() : bool
549 {
550 $time_format = \IAWPSCOPED\iawp()->get_option('time_format', 'g:i a');
551 if (Str::contains($time_format, 'a') || Str::contains($time_format, 'A')) {
552 return \false;
553 }
554 return \true;
555 }
556 private function actually_check_if_woocommerce_support_is_enabled() : bool
557 {
558 global $wpdb;
559 if (\IAWPSCOPED\iawp_is_free()) {
560 return \false;
561 }
562 if (\IAWP\Capability_Manager::can_only_view_authored_analytics()) {
563 return \false;
564 }
565 if (!\is_plugin_active('woocommerce/woocommerce.php')) {
566 return \false;
567 }
568 $table_name = $wpdb->prefix . 'wc_order_stats';
569 $order_stats_table = $wpdb->get_row($wpdb->prepare('
570 SELECT * FROM INFORMATION_SCHEMA.TABLES
571 WHERE TABLE_SCHEMA = %s AND TABLE_NAME = %s
572 ', $wpdb->dbname, $table_name));
573 if (\is_null($order_stats_table)) {
574 return \false;
575 }
576 return \true;
577 }
578 private function actually_check_if_surecart_support_is_enabled() : bool
579 {
580 if (\IAWPSCOPED\iawp_is_free()) {
581 return \false;
582 }
583 if (\IAWP\Capability_Manager::can_only_view_authored_analytics()) {
584 return \false;
585 }
586 return \is_plugin_active('surecart/surecart.php');
587 }
588 private function actually_check_if_edd_support_is_enabled() : bool
589 {
590 if (\IAWPSCOPED\iawp_is_free()) {
591 return \false;
592 }
593 if (\IAWP\Capability_Manager::can_only_view_authored_analytics()) {
594 return \false;
595 }
596 return \is_plugin_active('easy-digital-downloads/easy-digital-downloads.php') || \is_plugin_active('easy-digital-downloads-pro/easy-digital-downloads.php');
597 }
598 private function actually_check_if_pmpro_support_is_enabled() : bool
599 {
600 if (\IAWPSCOPED\iawp_is_free()) {
601 return \false;
602 }
603 if (\IAWP\Capability_Manager::can_only_view_authored_analytics()) {
604 return \false;
605 }
606 return \is_plugin_active('paid-memberships-pro-dev/paid-memberships-pro.php') || \is_plugin_active('paid-memberships-pro/paid-memberships-pro.php');
607 }
608 private function actually_check_if_fluent_cart_support_is_enabled() : bool
609 {
610 if (\IAWPSCOPED\iawp_is_free()) {
611 return \false;
612 }
613 if (\IAWP\Capability_Manager::can_only_view_authored_analytics()) {
614 return \false;
615 }
616 return \is_plugin_active('fluent-cart/fluent-cart.php');
617 }
618 private function get_menu_icon()
619 {
620 if (\is_null(\IAWP\Env::get_page())) {
621 return 'data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iVVRGLTgiPz4KPHN2ZyB3aWR0aD0iNTEzcHgiIGhlaWdodD0iMjU0cHgiIHZpZXdCb3g9IjAgMCA1MTMgMjU0IiB2ZXJzaW9uPSIxLjEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiPgogICAgPHRpdGxlPkljb248L3RpdGxlPgogICAgPGcgaWQ9IlBhZ2UtMSIgc3Ryb2tlPSJub25lIiBzdHJva2Utd2lkdGg9IjEiIGZpbGw9Im5vbmUiIGZpbGwtcnVsZT0iZXZlbm9kZCI+CiAgICAgICAgPGcgaWQ9Ik1lbnUtSWNvbiIgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoLTEyNiwgLTIyOCkiIGZpbGw9IiNBN0FBQUQiPgogICAgICAgICAgICA8ZyBpZD0iV2hpdGUiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDgyLCA1NSkiPgogICAgICAgICAgICAgICAgPGcgaWQ9Ikljb24iIHRyYW5zZm9ybT0idHJhbnNsYXRlKDQ0LjUsIDE3MykiPgogICAgICAgICAgICAgICAgICAgIDxwb2x5Z29uIGlkPSJOZWNrLTMiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDQwMi44MDU3LCAxMDguNjEyNSkgcm90YXRlKDQ1KSB0cmFuc2xhdGUoLTQwMi44MDU3LCAtMTA4LjYxMjUpIiBwb2ludHM9IjM5MS4xNjkzNTYgNTYuMjQ4ODI1OSA0MTQuNDQyMDgzIDU2LjI0ODgyNTkgNDE0LjQ0MjA4MyAxNjAuOTc2MDk5IDM5MS4xNjkzNTYgMTYwLjk3NjA5OSI+PC9wb2x5Z29uPgogICAgICAgICAgICAgICAgICAgIDxwb2x5Z29uIGlkPSJOZWNrLTIiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDI1NiwgMTI1LjY3MjcpIHJvdGF0ZSgtNjApIHRyYW5zbGF0ZSgtMjU2LCAtMTI1LjY3MjcpIiBwb2ludHM9IjI0NC4zNjM2MzYgNzMuMzA5MDkwOSAyNjcuNjM2MzY0IDczLjMwOTA5MDkgMjY3LjYzNjM2NCAxNzguMDM2MzY0IDI0NC4zNjM2MzYgMTc4LjAzNjM2NCI+PC9wb2x5Z29uPgogICAgICAgICAgICAgICAgICAgIDxwb2x5Z29uIGlkPSJOZWNrLTEiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDEwOS41Njk0LCAxNDQuNjg1Mikgcm90YXRlKDQ1KSB0cmFuc2xhdGUoLTEwOS41Njk0LCAtMTQ0LjY4NTIpIiBwb2ludHM9Ijk3LjkzMjk5MjMgOTIuMzIxNTUzMiAxMjEuMjA1NzIgOTIuMzIxNTUzMiAxMjEuMjA1NzIgMTk3LjA0ODgyNiA5Ny45MzI5OTIzIDE5Ny4wNDg4MjYiPjwvcG9seWdvbj4KICAgICAgICAgICAgICAgICAgICA8Y2lyY2xlIGlkPSJQb2ludC00IiBjeD0iNDY4Ljk0NTQ1NSIgY3k9IjQzLjA1NDU0NTUiIHI9IjQzLjA1NDU0NTUiPjwvY2lyY2xlPgogICAgICAgICAgICAgICAgICAgIDxjaXJjbGUgaWQ9IlBvaW50LTMiIGN4PSIzMzYuMjkwOTA5IiBjeT0iMTczLjM4MTgxOCIgcj0iNDMuMDU0NTQ1NSI+PC9jaXJjbGU+CiAgICAgICAgICAgICAgICAgICAgPGNpcmNsZSBpZD0iUG9pbnQtMiIgY3g9IjE3NS43MDkwOTEiIGN5PSI3OS4xMjcyNzI3IiByPSI0My4wNTQ1NDU1Ij48L2NpcmNsZT4KICAgICAgICAgICAgICAgICAgICA8Y2lyY2xlIGlkPSJQb2ludC0xIiBjeD0iNDMuMDU0NTQ1NSIgY3k9IjIxMC42MTgxODIiIHI9IjQzLjA1NDU0NTUiPjwvY2lyY2xlPgogICAgICAgICAgICAgICAgPC9nPgogICAgICAgICAgICA8L2c+CiAgICAgICAgPC9nPgogICAgPC9nPgo8L3N2Zz4=';
622 } else {
623 return 'data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iVVRGLTgiPz4KPHN2ZyB3aWR0aD0iNTEzcHgiIGhlaWdodD0iMjU0cHgiIHZpZXdCb3g9IjAgMCA1MTMgMjU0IiB2ZXJzaW9uPSIxLjEiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiPgogICAgPHRpdGxlPkljb248L3RpdGxlPgogICAgPGcgaWQ9IlBhZ2UtMSIgc3Ryb2tlPSJub25lIiBzdHJva2Utd2lkdGg9IjEiIGZpbGw9Im5vbmUiIGZpbGwtcnVsZT0iZXZlbm9kZCI+CiAgICAgICAgPGcgaWQ9Ik1lbnUtSWNvbiIgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoLTc3NSwgLTIyOSkiIGZpbGw9IiNGRkZGRkYiPgogICAgICAgICAgICA8ZyBpZD0iV2hpdGUtQ29weSIgdHJhbnNmb3JtPSJ0cmFuc2xhdGUoNzMxLCA1NikiPgogICAgICAgICAgICAgICAgPGcgaWQ9Ikljb24iIHRyYW5zZm9ybT0idHJhbnNsYXRlKDQ0LjUsIDE3MykiPgogICAgICAgICAgICAgICAgICAgIDxwb2x5Z29uIGlkPSJOZWNrLTMiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDQwMi44MDU3LCAxMDguNjEyNSkgcm90YXRlKDQ1KSB0cmFuc2xhdGUoLTQwMi44MDU3LCAtMTA4LjYxMjUpIiBwb2ludHM9IjM5MS4xNjkzNTYgNTYuMjQ4ODI1OSA0MTQuNDQyMDgzIDU2LjI0ODgyNTkgNDE0LjQ0MjA4MyAxNjAuOTc2MDk5IDM5MS4xNjkzNTYgMTYwLjk3NjA5OSI+PC9wb2x5Z29uPgogICAgICAgICAgICAgICAgICAgIDxwb2x5Z29uIGlkPSJOZWNrLTIiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDI1NiwgMTI1LjY3MjcpIHJvdGF0ZSgtNjApIHRyYW5zbGF0ZSgtMjU2LCAtMTI1LjY3MjcpIiBwb2ludHM9IjI0NC4zNjM2MzYgNzMuMzA5MDkwOSAyNjcuNjM2MzY0IDczLjMwOTA5MDkgMjY3LjYzNjM2NCAxNzguMDM2MzY0IDI0NC4zNjM2MzYgMTc4LjAzNjM2NCI+PC9wb2x5Z29uPgogICAgICAgICAgICAgICAgICAgIDxwb2x5Z29uIGlkPSJOZWNrLTEiIHRyYW5zZm9ybT0idHJhbnNsYXRlKDEwOS41Njk0LCAxNDQuNjg1Mikgcm90YXRlKDQ1KSB0cmFuc2xhdGUoLTEwOS41Njk0LCAtMTQ0LjY4NTIpIiBwb2ludHM9Ijk3LjkzMjk5MjMgOTIuMzIxNTUzMiAxMjEuMjA1NzIgOTIuMzIxNTUzMiAxMjEuMjA1NzIgMTk3LjA0ODgyNiA5Ny45MzI5OTIzIDE5Ny4wNDg4MjYiPjwvcG9seWdvbj4KICAgICAgICAgICAgICAgICAgICA8Y2lyY2xlIGlkPSJQb2ludC00IiBjeD0iNDY4Ljk0NTQ1NSIgY3k9IjQzLjA1NDU0NTUiIHI9IjQzLjA1NDU0NTUiPjwvY2lyY2xlPgogICAgICAgICAgICAgICAgICAgIDxjaXJjbGUgaWQ9IlBvaW50LTMiIGN4PSIzMzYuMjkwOTA5IiBjeT0iMTczLjM4MTgxOCIgcj0iNDMuMDU0NTQ1NSI+PC9jaXJjbGU+CiAgICAgICAgICAgICAgICAgICAgPGNpcmNsZSBpZD0iUG9pbnQtMiIgY3g9IjE3NS43MDkwOTEiIGN5PSI3OS4xMjcyNzI3IiByPSI0My4wNTQ1NDU1Ij48L2NpcmNsZT4KICAgICAgICAgICAgICAgICAgICA8Y2lyY2xlIGlkPSJQb2ludC0xIiBjeD0iNDMuMDU0NTQ1NSIgY3k9IjIxMC42MTgxODIiIHI9IjQzLjA1NDU0NTUiPjwvY2lyY2xlPgogICAgICAgICAgICAgICAgPC9nPgogICAgICAgICAgICA8L2c+CiAgICAgICAgPC9nPgogICAgPC9nPgo8L3N2Zz4=';
624 }
625 }
626 private function configure_carbon()
627 {
628 $locale = \get_locale();
629 // Carbon will throw an error if de_DE_Formal is used
630 if ('de_de_formal' === \strtolower($locale)) {
631 $locale = 'de_DE';
632 }
633 Carbon::setLocale($locale);
634 CarbonImmutable::setLocale($locale);
635 CarbonInterval::setLocale($locale);
636 }
637 }
638