PluginProbe ʕ •ᴥ•ʔ
Advanced Ads – Ad Manager & AdSense / 1.34.0
Advanced Ads – Ad Manager & AdSense v1.34.0
2.0.23 2.0.22 2.0.21 1.38.0 1.39.0 1.39.1 1.39.2 1.39.3 1.39.4 1.4.0 1.4.1 1.4.2 1.4.3 1.4.4 1.4.5 1.4.6 1.4.7 1.4.8 1.4.9 1.40.0 1.40.1 1.40.2 1.41.0 1.42.0 1.42.1 1.42.2 1.43.0 1.44.0 1.44.1 1.45.0 1.45.1 1.46.0 1.47.0 1.47.1 1.47.2 1.47.3 1.47.4 1.47.5 1.48.0 1.48.1 1.49.0 1.5.0 1.5.0.1 1.5.1 1.5.2 1.5.2.1 1.5.4 1.5.4.1 1.5.5 1.50.0 1.51.0 1.51.1 1.51.2 1.51.3 1.52.0 1.52.1 1.52.2 1.52.3 1.52.4 1.53.0 1.53.1 1.53.2 1.54.0 1.54.1 1.55.0 1.56.0 1.56.1 1.56.2 1.56.3 1.56.4 1.6 1.6.1 1.6.10 1.6.10.1 1.6.10.2 1.6.11 1.6.11.1 1.6.12 1.6.13 1.6.14 1.6.15 1.6.16 1.6.17 1.6.17.1 1.6.17.2 1.6.2 1.6.2.1 1.6.3 1.6.4 1.6.4.1 1.6.5 1.6.6 1.6.6.1 1.6.7 1.6.7.1 1.6.8 1.6.8.1 1.6.8.2 1.6.8.3 1.6.9 1.6.9.1 1.6.9.2 1.6.9.3 1.6.9.4 1.7 1.7.0.1 1.7.0.2 1.7.0.3 1.7.1 1.7.1.1 1.7.1.2 1.7.1.3 1.7.1.4 1.7.1.5 1.7.10 trunk 1.7.11 1.0.1 1.7.12 1.0.2 1.7.13 1.0.3 1.7.14 1.1.0 1.7.15 1.1.1 1.7.16 1.1.2 1.7.17 1.1.3 1.7.18 1.10 1.7.19 1.10.1 1.7.2 1.10.10 1.7.2.1 1.10.11 1.7.20 1.10.12 1.7.21 1.10.2 1.7.22 1.10.3 1.7.23 1.10.4 1.7.24 1.10.5 1.7.25 1.10.6 1.7.3 1.10.7 1.7.4 1.10.8 1.7.4.1 1.10.9 1.7.4.2 1.11 1.7.4.3 1.11.1 1.7.4.4 1.11.2 1.7.4.5 1.12 1.7.5 1.13 1.7.5.1 1.13.1 1.7.6 1.13.2 1.7.7 1.13.3 1.7.8 1.13.4 1.7.9 1.13.5 1.7.9.1 1.13.6 1.7.9.2 1.13.7 1.7.9.3 1.13.8 1.8 1.14 1.8.1 1.14.1 1.8.10 1.14.10 1.8.11 1.14.11 1.8.12 1.14.2 1.8.13 1.14.3 1.8.14 1.14.4 1.8.15 1.14.5 1.8.16 1.14.6 1.8.17 1.14.7 1.8.18 1.14.8 1.8.19 1.14.9 1.8.2 1.15 1.8.20 1.16 1.8.21 1.16.1 1.8.22 1.17 1.8.23 1.17.1 1.8.24 1.17.10 1.8.25 1.17.10-rc.1 1.8.26 1.17.11 1.8.27 1.17.12 1.8.28 1.17.12-rc.1 1.8.29 1.17.2 1.8.3 1.17.3 1.8.30 1.17.4 1.8.4 1.17.5 1.8.5 1.17.6 1.8.6 1.17.7 1.8.7 1.17.8 1.8.8 1.17.9 1.8.9 1.17.9-beta.1 1.9 1.18.0 2.0.0 1.19.0 2.0.1 1.19.1 2.0.10 1.2 2.0.11 1.2.1 2.0.12 1.2.2 2.0.13 1.2.3 2.0.14 1.2.4 2.0.15 1.2.5 2.0.16 1.2.6 2.0.17 1.2.7 2.0.18 1.20.0 2.0.19 1.20.0-rc.1 2.0.2 1.20.0-rc.2 2.0.20 1.20.1 2.0.3 1.20.2 2.0.4 1.20.3 2.0.5 1.21.0 2.0.6 1.21.1 2.0.7 1.22.0 2.0.8 1.22.1 2.0.9 1.22.2 1.23.0 1.23.1 1.23.2 1.24.0 1.24.1 1.24.2 1.25.0 1.25.1 1.26.0 1.27.0 1.28.0 1.29.0 1.29.1 1.3 1.3.1 1.3.10 1.3.11 1.3.12 1.3.13 1.3.14 1.3.15 1.3.16 1.3.17 1.3.18 1.3.2 1.3.3 1.3.4 1.3.5 1.3.6 1.3.7 1.3.8 1.3.9 1.30.0 1.30.1 1.30.2 1.30.2-rc.1 1.30.3 1.30.4 1.30.4-rc.1 1.30.5 1.31.0 1.31.1 1.32.0 1.32.0-rc.1 1.33.0 1.33.1 1.33.2 1.34.0 1.35.0 1.35.1 1.36.0 1.36.1 1.36.2 1.36.3 1.37.0 1.37.1 1.37.2
advanced-ads / classes / plugin.php
advanced-ads / classes Last commit date
EDD_SL_Plugin_Updater.php 4 years ago ad-ajax.php 5 years ago ad-debug.php 6 years ago ad-expiration.php 4 years ago ad-health-notices.php 4 years ago ad-model.php 5 years ago ad-select.php 9 years ago ad.php 4 years ago ad_ajax_callbacks.php 5 years ago ad_group.php 4 years ago ad_placements.php 4 years ago ad_type_abstract.php 5 years ago ad_type_content.php 5 years ago ad_type_dummy.php 5 years ago ad_type_group.php 5 years ago ad_type_image.php 5 years ago ad_type_plain.php 4 years ago checks.php 4 years ago compatibility.php 4 years ago display-conditions.php 4 years ago filesystem.php 8 years ago frontend-notices.php 6 years ago frontend_checks.php 4 years ago in-content-injector.php 4 years ago inline-css.php 4 years ago plugin.php 4 years ago upgrades.php 6 years ago utils.php 4 years ago visitor-conditions.php 4 years ago widget.php 4 years ago
plugin.php
914 lines
1 <?php
2
3 /**
4 * WordPress integration and definitions:
5 *
6 * - posttypes
7 * - taxonomy
8 * - textdomain
9 */
10 class Advanced_Ads_Plugin {
11 /**
12 * Instance of Advanced_Ads_Plugin
13 *
14 * @var object Advanced_Ads_Plugin
15 */
16 protected static $instance;
17
18 /**
19 * Instance of Advanced_Ads_Model
20 *
21 * @var object Advanced_Ads_Model
22 */
23 protected $model;
24
25 /**
26 * Plugin options
27 *
28 * @var array $options
29 */
30 protected $options;
31
32 /**
33 * Interal plugin options – set by the plugin
34 *
35 * @var array $internal_options
36 */
37 protected $internal_options;
38
39 /**
40 * Default prefix of selectors (id, class) in the frontend
41 * can be changed by options
42 *
43 * @var Advanced_Ads_Plugin
44 */
45 const DEFAULT_FRONTEND_PREFIX = 'advads-';
46
47 /**
48 * Frontend prefix for classes and IDs
49 *
50 * @var string $frontend_prefix
51 */
52 private $frontend_prefix;
53
54 /**
55 * Advanced_Ads_Plugin constructor.
56 */
57 private function __construct() {
58 register_activation_hook( ADVADS_BASE, array( $this, 'activate' ) );
59 register_deactivation_hook( ADVADS_BASE, array( $this, 'deactivate' ) );
60 register_uninstall_hook( ADVADS_BASE, array( 'Advanced_Ads_Plugin', 'uninstall' ) );
61
62 add_action( 'plugins_loaded', array( $this, 'wp_plugins_loaded' ), 20 );
63 add_action( 'init', array( $this, 'run_upgrades' ), 9 );
64 }
65
66 /**
67 * Get instance of Advanced_Ads_Plugin
68 *
69 * @return Advanced_Ads_Plugin
70 */
71 public static function get_instance() {
72 // If the single instance hasn't been set, set it now.
73 if ( null === self::$instance ) {
74 self::$instance = new self();
75 }
76
77 return self::$instance;
78 }
79
80 /**
81 * Get instance of Advanced_Ads_Model
82 *
83 * @param Advanced_Ads_Model $model model to access data.
84 */
85 public function set_model( Advanced_Ads_Model $model ) {
86 $this->model = $model;
87 }
88
89 /**
90 * Execute various hooks after WordPress and all plugins are available
91 */
92 public function wp_plugins_loaded() {
93 // Load plugin text domain.
94 $this->load_plugin_textdomain();
95
96 // activate plugin when new blog is added on multisites // -TODO this is admin-only.
97 add_action( 'wpmu_new_blog', array( $this, 'activate_new_site' ) );
98
99 // Load public-facing style sheet and JavaScript.
100 add_action( 'wp_enqueue_scripts', array( $this, 'enqueue_styles' ) );
101 add_action( 'wp_enqueue_scripts', array( $this, 'enqueue_scripts' ) );
102 add_action( 'wp_head', array( $this, 'print_head_scripts' ), 7 );
103 // higher priority to make sure other scripts are printed before.
104 add_action( 'wp_footer', array( $this, 'print_footer_scripts' ), 100 );
105
106 // add short codes.
107 add_shortcode( 'the_ad', array( $this, 'shortcode_display_ad' ) );
108 add_shortcode( 'the_ad_group', array( $this, 'shortcode_display_ad_group' ) );
109 add_shortcode( 'the_ad_placement', array( $this, 'shortcode_display_ad_placement' ) );
110
111 // remove default ad group menu item // -TODO only for admin.
112 add_action( 'admin_menu', array( $this, 'remove_taxonomy_menu_item' ) );
113 // load widgets.
114 add_action( 'widgets_init', array( $this, 'widget_init' ) );
115
116 // Call action hooks for ad status changes.
117 add_action( 'transition_post_status', array( $this, 'transition_ad_status' ), 10, 3 );
118
119 // register expired post status.
120 Advanced_Ads_Ad_Expiration::register_post_status();
121
122 // if expired ad gets untrashed, revert it to expired status (instead of draft).
123 add_filter( 'wp_untrash_post_status', array( Advanced_Ads_Ad_Expiration::class, 'wp_untrash_post_status' ), 10, 3 );
124
125 // load display conditions.
126 Advanced_Ads_Display_Conditions::get_instance();
127 new Advanced_Ads_Frontend_Checks();
128 new Advanced_Ads_Compatibility();
129 Advanced_Ads_Ad_Health_Notices::get_instance(); // load to fetch notices.
130 }
131
132 /**
133 * Run upgrades.
134 *
135 * Compatibility with the Piklist plugin that has a function hooked to `posts_where` that access $GLOBALS['wp_query'].
136 * Since `Advanced_Ads_Upgrades` applies `posts_where`: (`Advanced_Ads_Admin_Notices::get_instance()` >
137 * `Advanced_Ads::get_number_of_ads()` > new WP_Query > ... 'posts_where') this function is hooked to `init` so that `$GLOBALS['wp_query']` is instantiated.
138 */
139 public function run_upgrades() {
140 /**
141 * Run upgrades, if this is a new version or version does not exist.
142 */
143 $internal_options = $this->internal_options();
144
145 if ( ! defined( 'DOING_AJAX' ) && ( ! isset( $internal_options['version'] ) || version_compare( $internal_options['version'], ADVADS_VERSION, '<' ) ) ) {
146 new Advanced_Ads_Upgrades();
147 }
148 }
149
150 /**
151 * Register and enqueue public-facing style sheet.
152 */
153 public function enqueue_styles() {
154 // wp_enqueue_style( $this->get_plugin_slug() . '-plugin-styles', plugins_url('assets/css/public.css', __FILE__), array(), ADVADS_VERSION);
155 }
156
157 /**
158 * Return the plugin slug.
159 *
160 * @return string plugin slug variable.
161 */
162 public function get_plugin_slug() {
163 return ADVADS_SLUG;
164 }
165
166 /**
167 * Register and enqueues public-facing JavaScript files.
168 */
169 public function enqueue_scripts() {
170 if ( advads_is_amp() ) {
171 return;
172 }
173 // wp_enqueue_script( $this->get_plugin_slug() . '-plugin-script', plugins_url('assets/js/public.js', __FILE__), array('jquery'), ADVADS_VERSION);
174
175 wp_register_script(
176 $this->get_plugin_slug() . '-advanced-js',
177 sprintf( '%spublic/assets/js/advanced%s.js', ADVADS_BASE_URL, defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? '' : '.min' ),
178 array( 'jquery' ),
179 ADVADS_VERSION,
180 false
181 );
182
183 $privacy = Advanced_Ads_Privacy::get_instance();
184 $privacy_options = $privacy->options();
185 $privacy_options['enabled'] = ! empty( $privacy_options['enabled'] );
186 $privacy_options['state'] = $privacy->get_state();
187
188 wp_localize_script(
189 $this->get_plugin_slug() . '-advanced-js',
190 'advads_options',
191 array(
192 'blog_id' => get_current_blog_id(),
193 'privacy' => $privacy_options,
194 )
195 );
196
197 $activated_js = apply_filters( 'advanced-ads-activate-advanced-js', isset( $this->options()['advanced-js'] ) );
198
199 if ( $activated_js || ! empty( $_COOKIE['advads_frontend_picker'] ) ) {
200 wp_enqueue_script( $this->get_plugin_slug() . '-advanced-js' );
201 }
202 }
203
204 /**
205 * Print public-facing JavaScript in the HTML head.
206 */
207 public function print_head_scripts() {
208 $short_url = self::get_short_url();
209 $attribution = '<!-- ' . $short_url . ' is managing ads with Advanced Ads%1$s%2$s -->';
210 $version = self::is_new_user( 1585224000 ) ? ' ' . ADVADS_VERSION : '';
211 $plugin_url = self::get_group_by_url( $short_url, 'a' ) ? '' . ADVADS_URL : '';
212 // escaping would break HTML comment tags so we disable checks here.
213 // phpcs:ignore
214 echo apply_filters( 'advanced-ads-attribution', sprintf( $attribution, $version, $plugin_url ) );
215
216 if ( advads_is_amp() ) {
217 return;
218 }
219
220 ob_start();
221 ?>
222 <script id="<?php echo esc_attr( $this->get_frontend_prefix() ); ?>ready">
223 <?php
224 readfile( sprintf(
225 '%spublic/assets/js/ready%s.js',
226 ADVADS_BASE_PATH,
227 defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? '' : '.min'
228 ) );
229 ?>
230 </script>
231 <?php
232 // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped -- escaping would break the HTML
233 echo Advanced_Ads_Utils::get_inline_asset( ob_get_clean() );
234 }
235
236 /**
237 * Print inline scripts in wp_footer.
238 */
239 public function print_footer_scripts() {
240 if ( advads_is_amp() ) {
241 return;
242 }
243
244 // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped -- escaping would break the HTML
245 echo Advanced_Ads_Utils::get_inline_asset(
246 // phpcs:ignore WordPress.WP.AlternativeFunctions.file_get_contents_file_get_contents -- we're getting the contents of a local file
247 sprintf( '<script>%s</script>', file_get_contents( sprintf(
248 '%spublic/assets/js/ready-queue%s.js',
249 ADVADS_BASE_PATH,
250 defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? '' : '.min'
251 ) ) )
252 );
253 }
254
255 /**
256 * Register the Advanced Ads widget
257 */
258 public function widget_init() {
259 register_widget( 'Advanced_Ads_Widget' );
260 }
261
262 /**
263 * Fired when a new site is activated with a WPMU environment.
264 *
265 * @param int $blog_id ID of the new blog.
266 */
267 public function activate_new_site( $blog_id ) {
268
269 if ( 1 !== did_action( 'wpmu_new_blog' ) ) {
270 return;
271 }
272
273 switch_to_blog( $blog_id );
274 $this->single_activate();
275 restore_current_blog();
276 }
277
278 /**
279 * Fired for each blog when the plugin is activated.
280 */
281 protected function single_activate() {
282 // $this->post_types_rewrite_flush();
283 // -TODO inform modules
284 $this->create_capabilities();
285 }
286
287 /**
288 * Fired for each blog when the plugin is deactivated.
289 */
290 protected function single_deactivate() {
291 // -TODO inform modules
292 $this->remove_capabilities();
293 }
294
295 /**
296 * Load the plugin text domain for translation.
297 */
298 public function load_plugin_textdomain() {
299 load_plugin_textdomain( 'advanced-ads', false, ADVADS_BASE_DIR . '/languages' );
300 }
301
302 /**
303 * Fired when the plugin is activated.
304 *
305 * @param boolean $network_wide True if WPMU superadmin uses
306 * "Network Activate" action, false if
307 * WPMU is disabled or plugin is
308 * activated on an individual blog.
309 */
310 public function activate( $network_wide ) {
311 if ( function_exists( 'is_multisite' ) && is_multisite() ) {
312
313 if ( $network_wide ) {
314 // get all blog ids.
315 global $wpdb;
316 $blog_ids = $wpdb->get_col( "SELECT blog_id FROM {$wpdb->blogs}" );
317 $original_blog_id = $wpdb->blogid;
318
319 foreach ( $blog_ids as $blog_id ) {
320 switch_to_blog( $blog_id );
321 $this->single_activate();
322 }
323
324 switch_to_blog( $original_blog_id );
325 } else {
326 $this->single_activate();
327 }
328 } else {
329 $this->single_activate();
330 }
331 }
332
333 /**
334 * Fired when the plugin is deactivated.
335 *
336 * @param boolean $network_wide true if Advanced Ads should be disabled network-wide.
337 *
338 * True if WPMU superadmin uses
339 * "Network Deactivate" action, false if
340 * WPMU is disabled or plugin is
341 * deactivated on an individual blog.
342 */
343 public function deactivate( $network_wide ) {
344 if ( function_exists( 'is_multisite' ) && is_multisite() ) {
345
346 if ( $network_wide ) {
347 // get all blog ids.
348 global $wpdb;
349 $blog_ids = $wpdb->get_col( "SELECT blog_id FROM {$wpdb->blogs}" );
350 $original_blog_id = $wpdb->blogid;
351
352 foreach ( $blog_ids as $blog_id ) {
353 switch_to_blog( $blog_id );
354 $this->single_deactivate();
355 }
356
357 switch_to_blog( $original_blog_id );
358 } else {
359 $this->single_deactivate();
360 }
361 } else {
362 $this->single_deactivate();
363 }
364 }
365
366 /**
367 * Remove WP tag edit page for the ad group taxonomy
368 * needed, because we can’t remove it with `show_ui` without also removing the meta box
369 */
370 public function remove_taxonomy_menu_item() {
371 remove_submenu_page( 'edit.php?post_type=advanced_ads', 'edit-tags.php?taxonomy=advanced_ads_groups&amp;post_type=advanced_ads' );
372 }
373
374 /**
375 * Shortcode to include ad in frontend
376 *
377 * @param array $atts shortcode attributes.
378 *
379 * @return string ad content.
380 */
381 public function shortcode_display_ad( $atts ) {
382 $atts = is_array( $atts ) ? $atts : array();
383 $id = isset( $atts['id'] ) ? (int) $atts['id'] : 0;
384 // check if there is an inline attribute with or without value.
385 if ( isset( $atts['inline'] ) || in_array( 'inline', $atts, true ) ) {
386 $atts['inline_wrapper_element'] = true;
387 }
388 $atts = $this->prepare_shortcode_atts( $atts );
389
390 // use the public available function here.
391 return get_ad( $id, $atts );
392 }
393
394 /**
395 * Shortcode to include ad from an ad group in frontend
396 *
397 * @param array $atts shortcode attributes.
398 *
399 * @return string ad group content.
400 */
401 public function shortcode_display_ad_group( $atts ) {
402 $atts = is_array( $atts ) ? $atts : array();
403 $id = isset( $atts['id'] ) ? (int) $atts['id'] : 0;
404 $atts = $this->prepare_shortcode_atts( $atts );
405
406 // use the public available function here.
407 return get_ad_group( $id, $atts );
408 }
409
410 /**
411 * Shortcode to display content of an ad placement in frontend
412 *
413 * @param array $atts shortcode attributes.
414 *
415 * @return string ad placement content.
416 */
417 public function shortcode_display_ad_placement( $atts ) {
418 $atts = is_array( $atts ) ? $atts : array();
419 $id = isset( $atts['id'] ) ? (string) $atts['id'] : '';
420 $atts = $this->prepare_shortcode_atts( $atts );
421
422 // use the public available function here.
423 return get_ad_placement( $id, $atts );
424 }
425
426 /**
427 * Prepare shortcode attributes.
428 *
429 * @param array $atts array with strings.
430 *
431 * @return array
432 */
433 private function prepare_shortcode_atts( $atts ) {
434 $result = array();
435
436 /**
437 * Prepare attributes by converting strings to multi-dimensional array
438 * Example: [ 'output__margin__top' => 1 ] => ['output']['margin']['top'] = 1
439 */
440 if ( ! defined( 'ADVANCED_ADS_DISABLE_CHANGE' ) || ! ADVANCED_ADS_DISABLE_CHANGE ) {
441 foreach ( $atts as $attr => $data ) {
442 $levels = explode( '__', $attr );
443 $last = array_pop( $levels );
444
445 $cur_lvl = &$result;
446
447 foreach ( $levels as $lvl ) {
448 if ( ! isset( $cur_lvl[ $lvl ] ) ) {
449 $cur_lvl[ $lvl ] = array();
450 }
451
452 $cur_lvl = &$cur_lvl[ $lvl ];
453 }
454
455 $cur_lvl[ $last ] = $data;
456 }
457
458 $result = array_diff_key(
459 $result,
460 array(
461 'id' => false,
462 'blog_id' => false,
463 'ad_args' => false,
464 )
465 );
466 }
467
468 // Ad type: 'content' and a shortcode inside.
469 if ( isset( $atts['ad_args'] ) ) {
470 $result = array_merge( $result, json_decode( urldecode( $atts['ad_args'] ), true ) );
471
472 }
473
474 return $result;
475 }
476
477 /**
478 * Return plugin options
479 * these are the options updated by the user
480 *
481 * @return array $options
482 */
483 public function options() {
484 // we can’t store options if WPML String Translations is enabled, or it would not translate the "Ad Label" option.
485 if ( ! isset( $this->options ) || class_exists( 'WPML_ST_String' ) ) {
486 $this->options = get_option( ADVADS_SLUG, array() );
487 }
488
489 // allow to change options dynamically
490 $this->options = apply_filters( 'advanced-ads-options', $this->options );
491
492 return $this->options;
493 }
494
495 /**
496 * Update plugin options (not for settings page, but if automatic options are needed)
497 *
498 * @param array $options new options.
499 */
500 public function update_options( array $options ) {
501 // do not allow to clear options.
502 if ( array() === $options ) {
503 return;
504 }
505
506 $this->options = $options;
507 update_option( ADVADS_SLUG, $options );
508 }
509
510 /**
511 * Return internal plugin options
512 * these are options set by the plugin
513 *
514 * @return array $options
515 */
516 public function internal_options() {
517 if ( ! isset( $this->internal_options ) ) {
518 $defaults = array(
519 'version' => ADVADS_VERSION,
520 'installed' => time(), // when was this installed.
521 );
522 $this->internal_options = get_option( ADVADS_SLUG . '-internal', array() );
523
524 // save defaults.
525 if ( array() === $this->internal_options ) {
526 $this->internal_options = $defaults;
527 $this->update_internal_options( $this->internal_options );
528
529 self::get_instance()->create_capabilities();
530 }
531
532 // for versions installed prior to 1.5.3 set installed date for now.
533 if ( ! isset( $this->internal_options['installed'] ) ) {
534 $this->internal_options['installed'] = time();
535 $this->update_internal_options( $this->internal_options );
536 }
537 }
538
539 return $this->internal_options;
540 }
541
542 /**
543 * Update internal plugin options
544 *
545 * @param array $options new internal options.
546 */
547 public function update_internal_options( array $options ) {
548 // do not allow to clear options.
549 if ( array() === $options ) {
550 return;
551 }
552
553 $this->internal_options = $options;
554 update_option( ADVADS_SLUG . '-internal', $options );
555 }
556
557 /**
558 * Get prefix used for frontend elements
559 */
560 public function get_frontend_prefix() {
561 if ( ! $this->frontend_prefix ) {
562 $options = $this->options();
563
564 if ( ! isset( $options['front-prefix'] ) ) {
565 if ( isset( $options['id-prefix'] ) ) {
566 // deprecated: keeps widgets working that previously received an id based on the front-prefix.
567 $frontend_prefix = esc_attr( $options['id-prefix'] );
568 } else {
569 $host = parse_url( get_home_url(), PHP_URL_HOST );
570 $frontend_prefix = preg_match( '/[A-Za-z][A-Za-z0-9_]{4}/', $host, $result ) ? $result[0] . '-' : self::DEFAULT_FRONTEND_PREFIX;
571 }
572 } else {
573 $frontend_prefix = esc_attr( $options['front-prefix'] );
574 }
575 /**
576 * Applying the filter here makes sure that it is the same frontend prefix for all
577 * calls on this page impression
578 */
579 $this->frontend_prefix = apply_filters( 'advanced-ads-frontend-prefix', $frontend_prefix );
580 }
581
582 return $this->frontend_prefix;
583 }
584
585 /**
586 * Get priority used for injection inside content
587 */
588 public function get_content_injection_priority() {
589 $options = $this->options();
590
591 return isset( $options['content-injection-priority'] ) ? (int) $options['content-injection-priority'] : 100;
592 }
593
594 /**
595 * Returns the capability needed to perform an action
596 *
597 * @param string $capability a capability to check, can be internal to Advanced Ads.
598 *
599 * @return string $capability a valid WordPress capability.
600 */
601 public static function user_cap( $capability = 'manage_options' ) {
602
603 global $advanced_ads_capabilities;
604
605 // admins can do everything.
606 // is also a fallback if no option or more specific capability is given.
607 if ( current_user_can( 'manage_options' ) ) {
608 return 'manage_options';
609 }
610
611 return apply_filters( 'advanced-ads-capability', $capability );
612 }
613
614 /**
615 * Create roles and capabilities
616 */
617 public function create_capabilities() {
618 if ( $role = get_role( 'administrator' ) ) {
619 $role->add_cap( 'advanced_ads_manage_options' );
620 $role->add_cap( 'advanced_ads_see_interface' );
621 $role->add_cap( 'advanced_ads_edit_ads' );
622 $role->add_cap( 'advanced_ads_manage_placements' );
623 $role->add_cap( 'advanced_ads_place_ads' );
624 }
625 }
626
627 /**
628 * Remove roles and capabilities
629 */
630 public function remove_capabilities() {
631 if ( $role = get_role( 'administrator' ) ) {
632 $role->remove_cap( 'advanced_ads_manage_options' );
633 $role->remove_cap( 'advanced_ads_see_interface' );
634 $role->remove_cap( 'advanced_ads_edit_ads' );
635 $role->remove_cap( 'advanced_ads_manage_placements' );
636 $role->remove_cap( 'advanced_ads_place_ads' );
637 }
638 }
639
640 /**
641 * Fired when the plugin is uninstalled.
642 */
643 public static function uninstall() {
644 $advads_options = Advanced_Ads::get_instance()->options();
645
646 if ( ! empty( $advads_options['uninstall-delete-data'] ) ) {
647 global $wpdb;
648 $main_blog_id = $wpdb->blogid;
649
650 Advanced_Ads::get_instance()->create_post_types();
651
652 if ( ! is_multisite() ) {
653 self::get_instance()->uninstall_single();
654 } else {
655 $blog_ids = $wpdb->get_col( "SELECT blog_id FROM {$wpdb->blogs}" );
656
657 foreach ( $blog_ids as $blog_id ) {
658 switch_to_blog( $blog_id );
659 self::get_instance()->uninstall_single();
660 }
661 switch_to_blog( $main_blog_id );
662 }
663
664 // Delete assets (main blog).
665 Advanced_Ads_Ad_Blocker_Admin::get_instance()->clear_assets();
666 }
667
668 }
669
670 /**
671 * Fired for each blog when the plugin is uninstalled.
672 */
673 protected function uninstall_single() {
674 global $wpdb;
675
676 // Ads.
677 $post_ids = $wpdb->get_col( $wpdb->prepare( "SELECT ID FROM {$wpdb->posts} WHERE post_type = %s", Advanced_Ads::POST_TYPE_SLUG ) );
678
679 if ( $post_ids ) {
680 $wpdb->delete(
681 $wpdb->posts,
682 array( 'post_type' => Advanced_Ads::POST_TYPE_SLUG ),
683 array( '%s' )
684 );
685
686 $wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->postmeta} WHERE post_id IN( %s )", implode( ',', $post_ids ) ) );
687 }
688
689 // Groups.
690 $term_ids = $wpdb->get_col( $wpdb->prepare( "SELECT t.term_id FROM {$wpdb->terms} AS t INNER JOIN {$wpdb->term_taxonomy} AS tt ON t.term_id = tt.term_id WHERE tt.taxonomy = %s", Advanced_Ads::AD_GROUP_TAXONOMY ) );
691
692 foreach ( $term_ids as $term_id ) {
693 wp_delete_term( $term_id, Advanced_Ads::AD_GROUP_TAXONOMY );
694 }
695
696 delete_option( 'advads-ad-groups' );
697 delete_option( Advanced_Ads::AD_GROUP_TAXONOMY . '_children' );
698 delete_option( 'advads-ad-weights' );
699
700 // Placements.
701 delete_option( 'advads-ads-placements' );
702
703 // User metadata.
704 delete_metadata( 'user', null, 'advanced-ads-hide-wizard', '', true );
705 delete_metadata( 'user', null, 'advanced-ads-subscribed', '', true );
706
707 // Post metadata.
708 delete_metadata( 'post', null, '_advads_ad_settings', '', true );
709
710 // Transients.
711 delete_transient( ADVADS_SLUG . '_add-on-updates-checked' );
712
713 delete_option( GADSENSE_OPT_NAME );
714 delete_option( ADVADS_SLUG );
715 delete_option( ADVADS_SLUG . '-internal' );
716 delete_option( ADVADS_SLUG . '-notices' );
717
718 // Widget.
719 $base_widget_id = Advanced_Ads_Widget::get_base_id();
720 delete_option( 'widget_' . $base_widget_id );
721
722 // Ad blocker disquise.
723 delete_option( ADVADS_AB_SLUG );
724
725 do_action( 'advanced-ads-uninstall' );
726
727 wp_cache_flush();
728 }
729
730 /**
731 * Check if any add-on is activated
732 *
733 * @return bool true if there is any add-on activated
734 */
735 public static function any_activated_add_on() {
736 return ( defined( 'AAP_VERSION' ) // Advanced Ads Pro.
737 || defined( 'AAGAM_VERSION' ) // Google Ad Manager.
738 || defined( 'AASA_VERSION' ) // Selling Ads.
739 || defined( 'AAT_VERSION' ) // Tracking.
740 || defined( 'AASADS_VERSION' ) // Sticky Ads.
741 || defined( 'AAR_VERSION' ) // Responsive Ads.
742 || defined( 'AAPLDS_VERSION' ) // PopUp and Layer Ads.
743 || defined( 'AAGT_SLUG' ) // Geo-Targeting.
744 );
745 }
746
747 /**
748 * Get the correct support URL: wp.org for free users and website for those with any add-on installed
749 *
750 * @param string $utm add UTM parameter to the link leading to https://wpadvancedads.com, if given.
751 *
752 * @return string URL.
753 */
754 public static function support_url( $utm = '' ) {
755
756 $utm = empty( $utm ) ? '?utm_source=advanced-ads&utm_medium=link&utm_campaign=support' : $utm;
757 if ( self::any_activated_add_on() ) {
758 $url = ADVADS_URL . 'support/' . $utm . '-with-addons';
759 } else {
760 $url = ADVADS_URL . 'support/' . $utm . '-free-user';
761 }
762
763 return $url;
764 }
765
766 /**
767 * Create a random group
768 *
769 * @param string $url optional parameter.
770 * @param string $ex group.
771 *
772 * @return bool
773 */
774 public static function get_group_by_url( $url = '', $ex = 'a' ) {
775
776 $url = self::get_short_url( $url );
777
778 $code = intval( substr( md5( $url ), - 1 ), 16 );
779
780 switch ( $ex ) {
781 case 'b':
782 return ( $code & 2 ) >> 1; // returns 1 or 0.
783 case 'c':
784 return ( $code & 4 ) >> 2; // returns 1 or 0.
785 case 'd':
786 return ( $code & 8 ) >> 3; // returns 1 or 0.
787 default:
788 return $code & 1; // returns 1 or 0.
789 }
790 }
791
792 /**
793 * Check if user started after a given date
794 *
795 * @param integer $timestamp time stamp.
796 *
797 * @return bool true if user is added after timestamp.
798 */
799 public static function is_new_user( $timestamp = 0 ) {
800
801 // allow admins to see version for new users in any case.
802 if ( current_user_can( self::user_cap( 'advanced_ads_manage_options' ) )
803 && isset( $_REQUEST['advads-ignore-timestamp'] ) ) {
804 return true;
805 }
806
807 $timestamp = absint( $timestamp );
808
809 $options = self::get_instance()->internal_options();
810 $installed = isset( $options['installed'] ) ? $options['installed'] : 0;
811
812 return ( $installed >= $timestamp );
813 }
814
815 /**
816 * Show stuff to new users only.
817 *
818 * @param integer $timestamp time after which to show whatever.
819 * @param string $group optional group.
820 *
821 * @return bool true if user enabled after given timestamp.
822 */
823 public static function show_to_new_users( $timestamp, $group = 'a' ) {
824
825 return ( self::get_group_by_url( null, $group ) && self::is_new_user( $timestamp ) );
826 }
827
828 /**
829 * Get short version of home_url()
830 * remove protocol and www
831 * remove slash
832 *
833 * @param string $url URL to be shortened.
834 *
835 * @return string
836 */
837 public static function get_short_url( $url = '' ) {
838
839 $url = empty( $url ) ? home_url() : $url;
840
841 // strip protocols.
842 if ( preg_match( '/^(\w[\w\d]*:\/\/)?(www\.)?(.*)$/', trim( $url ), $matches ) ) {
843 $url = $matches[3];
844 }
845
846 // strip slashes.
847 $url = trim( $url, '/' );
848
849 return $url;
850 }
851
852 /**
853 * Return Advanced Ads logo in base64 format for use in WP Admin menu.
854 *
855 * @return string
856 */
857 public static function get_icon_svg() {
858 return 'data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iaXNvLTg4NTktMSI/Pg0KPCEtLSBHZW5lcmF0b3I6IEFkb2JlIElsbHVzdHJhdG9yIDE4LjEuMSwgU1ZHIEV4cG9ydCBQbHVnLUluIC4gU1ZHIFZlcnNpb246IDYuMDAgQnVpbGQgMCkgIC0tPg0KPHN2ZyB2ZXJzaW9uPSIxLjEiIGlkPSJFYmVuZV8xIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB4PSIwcHgiIHk9IjBweCINCgkgdmlld0JveD0iMCAwIDY0Ljk5MyA2NS4wMjQiIHN0eWxlPSJlbmFibGUtYmFja2dyb3VuZDpuZXcgMCAwIDY0Ljk5MyA2NS4wMjQ7IiB4bWw6c3BhY2U9InByZXNlcnZlIj4NCjxwYXRoIHN0eWxlPSJmaWxsOiNFNEU0RTQ7IiBkPSJNNDYuNTcxLDI3LjY0MXYyMy4xMzNIMTQuMjVWMTguNDUzaDIzLjExOGMtMC45NTYtMi4xODMtMS40OTQtNC41OS0xLjQ5NC03LjEyNg0KCWMwLTIuNTM1LDAuNTM4LTQuOTQyLDEuNDk0LTcuMTI0aC02Ljk1N0gwdjQ5LjQ5M2wxLjYxOCwxLjYxOEwwLDUzLjY5NmMwLDYuMjU2LDUuMDY4LDExLjMyNiwxMS4zMjQsMTEuMzI4djBoMTkuMDg3aDMwLjQxMlYyNy42MTENCgljLTIuMTkxLDAuOTY0LTQuNjA5LDEuNTA5LTcuMTU3LDEuNTA5QzUxLjE0MiwyOS4xMiw0OC43NDYsMjguNTg4LDQ2LjU3MSwyNy42NDF6Ii8+DQo8Y2lyY2xlIHN0eWxlPSJmaWxsOiM5ODk4OTg7IiBjeD0iNTMuNjY2IiBjeT0iMTEuMzI4IiByPSIxMS4zMjgiLz4NCjwvc3ZnPg0K';
859 }
860
861 /**
862 * Fires when a post is transitioned from one status to another.
863 *
864 * @param string $new_status New post status.
865 * @param string $old_status Old post status.
866 * @param WP_Post $post Post object.
867 */
868 public function transition_ad_status( $new_status, $old_status, $post ) {
869 if ( ! isset( $post->post_type ) || Advanced_Ads::POST_TYPE_SLUG !== $post->post_type || ! isset( $post->ID ) ) {
870 return;
871 }
872
873 $ad = new Advanced_Ads_Ad( $post->ID );
874
875 if ( $old_status !== $new_status ) {
876 /**
877 * Fires when an ad has transitioned from one status to another.
878 *
879 * @param Advanced_Ads_Ad $ad Ad object.
880 */
881 do_action( "advanced-ads-ad-status-{$old_status}-to-{$new_status}", $ad );
882 }
883
884 if ( 'publish' === $new_status && 'publish' !== $old_status ) {
885 /**
886 * Fires when an ad has transitioned from any other status to `publish`.
887 *
888 * @param Advanced_Ads_Ad $ad Ad object.
889 */
890 do_action( 'advanced-ads-ad-status-published', $ad );
891 }
892
893 if ( 'publish' === $old_status && 'publish' !== $new_status ) {
894 /**
895 * Fires when an ad has transitioned from `publish` to any other status.
896 *
897 * @param Advanced_Ads_Ad $ad Ad object.
898 */
899 do_action( 'advanced-ads-ad-status-unpublished', $ad );
900 }
901
902 if ( $old_status === 'publish' && $new_status === Advanced_Ads_Ad_Expiration::POST_STATUS ) {
903 /**
904 * Fires when an ad is expired.
905 *
906 * @param int $id
907 * @param Advanced_Ads_Ad $ad
908 */
909 do_action( 'advanced-ads-ad-expired', $ad->id, $ad );
910 }
911 }
912
913 }
914