MailPoet Newsletters (Previous) - Version 2.7

Version Description

  • 2016-01-29 =
  • Enabled PHP7 compatibility
  • Fixed security issues. Thanks to Immunity and Netsparker (https://www.netsparker.com) for alerting us.
  • Fixed an issue with newsletters not saving during the creation process
  • Disabled SSL verification on hosts with invalid SSL certificates and PHP 5.6
  • Updated SendGrid mailer
  • Improved URL validation logic
  • Addressed PHP notices that appeared in cron output
  • Fixed other minor issues
Download this release

Release Info

Developer JoN1oP
Plugin Icon 128x128 MailPoet Newsletters (Previous)
Version 2.7
Comparing to
See all releases

Code changes from version 2.6.19 to 2.7

add-ons/add-ons.php CHANGED
@@ -11,7 +11,7 @@ class MailPoet_Add_ons {
11
  $this->plugin_path = WYSIJA_DIR;
12
  $this->wp_plugin_path = str_replace( 'wysija-newsletters', '', $this->plugin_path );
13
  $this->plugin_url = WYSIJA_URL;
14
- $this->image_url = 'http://ps.w.org/wysija-newsletters/assets/add-ons/';
15
 
16
  $this->mailpoet_add_on_activated_notice();
17
  $this->mailpoet_add_on_deactivated_notice();
11
  $this->plugin_path = WYSIJA_DIR;
12
  $this->wp_plugin_path = str_replace( 'wysija-newsletters', '', $this->plugin_path );
13
  $this->plugin_url = WYSIJA_URL;
14
+ $this->image_url = '//ps.w.org/wysija-newsletters/assets/add-ons/';
15
 
16
  $this->mailpoet_add_on_activated_notice();
17
  $this->mailpoet_add_on_deactivated_notice();
classes/WJ_Analytics.php CHANGED
@@ -1,879 +1,899 @@
1
- <?php
2
- defined('WYSIJA') or die('Restricted access');
3
- /*
4
- Class Analytics.
5
- It's a sort of useful stats and numbers generator about MailPoet usage.
6
- It also handles the MixPanel integration.
7
- $analytics = new WJ_Analytics();
8
- $analytics->generate_data();
9
- $analytics->send();
10
- */
11
- class WJ_Analytics {
12
-
13
- // All analytics data to be sent to JS.
14
- private $analytics_data = array(
15
- 'php_version' => array(
16
- 'label' => 'PHP version',
17
- 'value' => ''
18
- ),
19
- 'monthly_emails_sent' => array(
20
- 'label' => 'Monthly emails sent',
21
- 'value' => ''
22
- ),
23
- 'lists_with_more_than_25' => array(
24
- 'label' => 'Lists with more than 25 subscribers',
25
- 'value' => ''
26
- ),
27
- 'confirmed_subscribers' => array(
28
- 'label' => 'Confirmed subscribers',
29
- 'value' => ''
30
- ),
31
- 'range_confirmed_subscribers' => array(
32
- 'label' => 'Range Confirmed subscribers',
33
- 'value' => ''
34
- ),
35
- 'unconfirmed_subscribers' => array(
36
- 'label' => 'Unconfirmed subscribers',
37
- 'value' => ''
38
- ),
39
- 'standard_newsletters' => array(
40
- 'label' => 'Standard newsletters',
41
- 'value' => ''
42
- ),
43
- 'auto_newsletters' => array(
44
- 'label' => 'Auto newsletters',
45
- 'value' => ''
46
- ),
47
- 'wordpress_version' => array(
48
- 'label' => 'WordPress Version',
49
- 'value' => ''
50
- ),
51
- 'plugin_version' => array(
52
- 'label' => 'Plugin Version',
53
- 'value' => ''
54
- ),
55
- 'license_type' => array(
56
- 'label' => 'License type',
57
- 'value' => ''
58
- ),
59
- 'sending_method' => array(
60
- 'label' => 'Sending method',
61
- 'value' => ''
62
- ),
63
- 'smtp_hostname' => array(
64
- 'label' => 'Smtp hostname',
65
- 'value' => ''
66
- ),
67
- 'activation_email_status' => array(
68
- 'label' => 'Activation Email',
69
- 'value' => ''
70
- ),
71
- 'average_open_rate' => array(
72
- 'label' => 'Open rate',
73
- 'value' => ''
74
- ),
75
- 'average_click_rate' => array(
76
- 'label' => 'Click rate',
77
- 'value' => ''
78
- ),
79
- 'industry' => array(
80
- 'label' => 'Industry',
81
- 'value' => ''
82
- ),
83
- 'wordpress_language' => array(
84
- 'label' => 'WordPress Language',
85
- 'value' => ''
86
- ),
87
- 'rtl' => array(
88
- 'label' => 'Rtl',
89
- 'value' => ''
90
- ),
91
- 'beta' => array(
92
- 'label' => 'Beta',
93
- 'value' => ''
94
- ),
95
- 'archive_page' => array(
96
- 'label' => 'Archive Page',
97
- 'value' => ''
98
- ),
99
- 'dkim_status' => array(
100
- 'label' => 'DKIM Active',
101
- 'value' => ''
102
- ),
103
- 'subscribe_in_comments' => array(
104
- 'label' => 'Subscribe in comments',
105
- 'value' => ''
106
- ),
107
- 'subscribe_on_register' => array(
108
- 'label' => 'Subscribe on registration',
109
- 'value' => ''
110
- ),
111
- 'browser_link' => array(
112
- 'label' => 'View in browser link',
113
- 'value' => ''
114
- ),
115
- 'profile_edit'=> array(
116
- 'label' => 'Subcsribers can edit profile',
117
- 'value' => ''
118
- ),
119
- 'html_edit' => array(
120
- 'label' => 'Allow HTML edit',
121
- 'value' => ''
122
- ),
123
- 'mailpoet_cron' => array(
124
- 'label' => 'MailPoet Cron Enabled',
125
- 'value' => ''
126
- ),
127
- 'forms_number' => array(
128
- 'label' => 'Total number of forms',
129
- 'value' => ''
130
- ),
131
- 'using_custom_fields' => array(
132
- 'label' => 'Using custom fields',
133
- 'value' => ''
134
- ),
135
- 'custom_fields_input' => array(
136
- 'label' => 'Custom Fields: Input field',
137
- 'value' => ''
138
- ),
139
- 'custom_fields_textarea' => array(
140
- 'label' => 'Custom Fields: Textarea',
141
- 'value' => ''
142
- ),
143
- 'custom_fields_select' => array(
144
- 'label' => 'Custom Fields: Select',
145
- 'value' => ''
146
- ),
147
- 'custom_fields_checkbox' => array(
148
- 'label' => 'Custom Fields: Checkbox',
149
- 'value' => ''
150
- ),
151
- 'custom_fields_radio' => array(
152
- 'label' => 'Custom Fields: Radio',
153
- 'value' => ''
154
- ),
155
- 'active_last_week' => array(
156
- 'label' => 'Active last week',
157
- 'value' => ''
158
- ),
159
- 'is_multisite' => array(
160
- 'label' => 'Using Multisite',
161
- 'value' => ''
162
- )
163
- );
164
-
165
- function __construct() {}
166
-
167
- /**
168
- * Send data to Mixpanel by enqueuing the analytics JS file.
169
- * @return
170
- */
171
- public function send() {
172
-
173
- // Enqueue analytics Javascript.
174
- wp_enqueue_script('analytics', WYSIJA_URL . 'js/analytics.js', array(), WYSIJA::get_version());
175
- // Make analytics data available in JS.
176
- wp_localize_script('analytics', 'analytics_data', $this->analytics_data);
177
- }
178
-
179
- /**
180
- * Generate fresh data and store it in the $analytics_data Class property.
181
- * @return
182
- */
183
- public function generate_data() {
184
-
185
- foreach ($this->analytics_data as $key => $data) {
186
- $method = $key;
187
- $this->analytics_data[$key]['value'] = $this->$method();
188
- }
189
-
190
- }
191
-
192
- /**
193
- * Calculate Emails sent in the last 30 days.
194
- * @return Int
195
- */
196
- private function monthly_emails_sent() {
197
-
198
- $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
199
- $query = 'SELECT COUNT(*) as total_emails
200
- FROM ' . '[wysija]' . $model_email_user_stat->table_name . '
201
- WHERE DATE_SUB(CURDATE(),INTERVAL 30 DAY) <= sent_at';
202
- $result = $model_email_user_stat->query('get_res', $query);
203
-
204
- $total_emails = $result[0]['total_emails'];
205
- switch (true) {
206
- case ($total_emails <= 1000):
207
- $track = 'Less than 1000';
208
- break;
209
- case ((1001 <= $total_emails) && ($total_emails <= 2500)):
210
- $track = '1001 to 2500';
211
- break;
212
- case ((2501 <= $total_emails) && ($total_emails <= 5000)):
213
- $track = '2501 to 5000';
214
- break;
215
- case ((5001 <= $total_emails) && ($total_emails <= 10000)):
216
- $track = '5001 to 10000';
217
- break;
218
- case ((10001 <= $total_emails) && ($total_emails <= 25000)):
219
- $track = '10001 to 25000';
220
- break;
221
- case ((25001 <= $total_emails) && ($total_emails <= 50000)):
222
- $track = '25001 to 50000';
223
- break;
224
- case ((50001 <= $total_emails) && ($total_emails <= 100000)):
225
- $track = '50001 to 100000';
226
- break;
227
- case (100001 <= $total_emails):
228
- $track = 'More than 100001';
229
- break;
230
- default:
231
- $track = 'No emails sent';
232
- break;
233
- }
234
-
235
- return $track;
236
-
237
- }
238
-
239
- /*
240
- Pass through the WordPress version.
241
- */
242
- private function wordpress_version() {
243
- return get_bloginfo('version');
244
- }
245
-
246
- /*
247
- Pass through the WordPress language.
248
- */
249
- private function wordpress_language() {
250
- return get_bloginfo('language');
251
- }
252
-
253
- /*
254
- The plugin version.
255
- */
256
- private function plugin_version() {
257
- return WYSIJA::get_version();
258
- }
259
-
260
- /**
261
- * Calculate lists with more than 25 subscribers.
262
- * @return Int
263
- */
264
- private function lists_with_more_than_25() {
265
-
266
- $model_user_list = WYSIJA::get('user_list', 'model');
267
- $query = 'SELECT list_id, COUNT(*) as count
268
- FROM ' . '[wysija]' . $model_user_list->table_name . '
269
- GROUP BY list_id
270
- HAVING COUNT(*) >= 25';
271
- $result = $model_user_list->query('get_res', $query);
272
- $lists_count = count($result);
273
-
274
- return $lists_count;
275
- }
276
-
277
- /**
278
- * Calculate total subscribers.
279
- * @return Int
280
- */
281
- private function total_subcsribers() {
282
-
283
- $model_user = WYSIJA::get('user', 'model');
284
- $query = 'SELECT COUNT(*) as total_subscribers
285
- FROM ' . '[wysija]' . $model_user->table_name;
286
- $result = $model_user->query('get_res', $query);
287
-
288
- return $result[0]['total_subscribers'];
289
- }
290
-
291
- /**
292
- * Calculate confirmed subscribers.
293
- * @return Int
294
- */
295
- private function confirmed_subscribers() {
296
-
297
- $model_user = WYSIJA::get('user', 'model');
298
- $query = 'SELECT COUNT(*) as confirmed_subscribers
299
- FROM ' . '[wysija]' . $model_user->table_name . '
300
- WHERE status = 1';
301
- $result = $model_user->query('get_res', $query);
302
-
303
- $confirmed_subscribers = $result[0]['confirmed_subscribers'];
304
- $total_subscribers = $this->total_subcsribers();
305
- $confirmed_percentage = round(($confirmed_subscribers * 100) / $total_subscribers);
306
-
307
- return $confirmed_percentage;
308
- }
309
-
310
- /**
311
- *
312
- * @return string range eg: 0-100 101-200 2001-500
313
- */
314
- private function range_confirmed_subscribers(){
315
- $model_user = WYSIJA::get('user', 'model');
316
- $query = 'SELECT COUNT(*) as confirmed_subscribers
317
- FROM ' . '[wysija]' . $model_user->table_name . '
318
- WHERE status = 1';
319
- $result = $model_user->query('get_res', $query);
320
-
321
- $confirmed_subscribers = (int) $result[0]['confirmed_subscribers'];
322
-
323
- $ranges_increment = array( 2000 => 100, 10000 => 500, 20000 => 1000, 40000 => 2000, 100000 => 5000, 200000 => 10000, 500000 => 25000, 1000000 => 50000);
324
-
325
- $found_range = $this->range_finder( $confirmed_subscribers, $ranges_increment );
326
-
327
- return $found_range['lower'].' - '.$found_range['upper'];
328
- }
329
-
330
- private function range_finder($value, $ranges_increment){
331
-
332
- $limit_max = 0;
333
- foreach( $ranges_increment as $limit => $range_increment ){
334
- $small_limit = $limit_max + $range_increment;
335
- $limit_max = $limit;
336
-
337
- if( $value > $limit_max){
338
- continue;
339
- }
340
-
341
- while( $value >= $small_limit && $small_limit <= $limit_max ){
342
-
343
- if( $value > $small_limit ){
344
- $min_value = $small_limit - $range_increment + 1;
345
- }
346
- if( $value == $small_limit ){
347
- break;
348
- }
349
- $small_limit += $range_increment;
350
- }
351
-
352
- if( $value <= $small_limit){
353
- break;
354
- }
355
- }
356
-
357
- if( $value > $limit_max){
358
- return array( 'lower' => $limit_max , 'upper' => 'above' );
359
- }else{
360
- if( $value < 1 ){
361
- return array( 'lower' => 0 , 'upper' => 'or undefined' );
362
- }else{
363
- $min_value = $small_limit - $range_increment + 1;
364
- return array( 'lower' => $min_value , 'upper' => $small_limit );
365
- }
366
- }
367
-
368
- }
369
-
370
- /**
371
- * Calculate unconfirmed subscribers.
372
- * @return Int
373
- */
374
- public function unconfirmed_subscribers() {
375
-
376
- $model_user = WYSIJA::get('user', 'model');
377
- $query = 'SELECT COUNT(*) as unconfirmed_subscribers
378
- FROM ' . '[wysija]' . $model_user->table_name . '
379
- WHERE status = 0';
380
- $result = $model_user->query('get_res', $query);
381
-
382
- return $result[0]['unconfirmed_subscribers'];
383
- }
384
-
385
- /**
386
- * Calculate standard newsletters total.
387
- * @return Int
388
- */
389
- private function standard_newsletters() {
390
-
391
- $model_email = WYSIJA::get('email', 'model');
392
- $query = 'SELECT COUNT(*) as standard_newsletters
393
- FROM ' . '[wysija]' . $model_email->table_name . '
394
- WHERE type = 1
395
- AND status = 2';
396
- $result = $model_email->query('get_res', $query);
397
-
398
- return $result[0]['standard_newsletters'];
399
- }
400
-
401
- /**
402
- * Calculate auto newsletters total.
403
- * @return Int
404
- */
405
- private function auto_newsletters() {
406
-
407
- $model_email = WYSIJA::get('email', 'model');
408
- $query = 'SELECT COUNT(*) as auto_newsletters
409
- FROM ' . '[wysija]' . $model_email->table_name . '
410
- WHERE type = 2';
411
- $result = $model_email->query('get_res', $query);
412
-
413
- return $result[0]['auto_newsletters'];
414
- }
415
-
416
- /**
417
- * Check license type in use.
418
- * @return String Free | Premium
419
- */
420
- private function license_type() {
421
-
422
- $model_config = WYSIJA::get('config', 'model');
423
- $is_premium = $model_config->getValue('premium_key');
424
-
425
- if ($is_premium) {
426
- $license_type = 'Premium';
427
- } else {
428
- $license_type = 'Free';
429
- }
430
-
431
- return $license_type;
432
- }
433
-
434
- /**
435
- * Get sending method in use.
436
- * @return String
437
- */
438
- private function sending_method() {
439
-
440
- $model_config = WYSIJA::get('config', 'model');
441
- return $model_config->getValue('sending_method');
442
- }
443
-
444
- /**
445
- * Get smtp hostname in use.
446
- * @return String
447
- */
448
- private function smtp_hostname() {
449
-
450
- $model_config = WYSIJA::get('config', 'model');
451
- return $model_config->getValue('smtp_host');
452
- }
453
-
454
- /**
455
- * Get activation email status.
456
- * @return String On | Off
457
- */
458
- private function activation_email_status() {
459
-
460
- $model_config = WYSIJA::get('config', 'model');
461
- $activation_email_status = $model_config->getValue('confirm_dbleoptin');
462
-
463
- if ($activation_email_status === 1) {
464
- $result = 'On';
465
- } else {
466
- $result = 'Off';
467
- }
468
-
469
- return $result;
470
- }
471
-
472
- /**
473
- * Get DKIM status.
474
- * @return String Yes | No
475
- */
476
- private function dkim_status() {
477
- $model_config = WYSIJA::get('config', 'model');
478
- $dkim_status = $model_config->getValue('dkim_active');
479
- if ($dkim_status === 1) {
480
- $result = 'Yes';
481
- } else {
482
- $result = 'No';
483
- }
484
- return $result;
485
- }
486
-
487
- /**
488
- * Get subscribe in comments.
489
- * @return String Yes | No
490
- */
491
- private function subscribe_in_comments() {
492
- $model_config = WYSIJA::get('config', 'model');
493
- $subscribe_in_comments = $model_config->getValue('commentform');
494
- if ($subscribe_in_comments == 1) {
495
- $result = 'Yes';
496
- } else {
497
- $result = 'No';
498
- }
499
- return $result;
500
- }
501
-
502
- /**
503
- * Get subscribe during registration option.
504
- * @return String Yes | No
505
- */
506
- private function subscribe_on_register() {
507
- $model_config = WYSIJA::get('config', 'model');
508
- $subscribe_on_register = $model_config->getValue('registerform');
509
- if ($subscribe_on_register == 1) {
510
- $result = 'Yes';
511
- } else {
512
- $result = 'No';
513
- }
514
- return $result;
515
- }
516
-
517
- /**
518
- * Get view in browser option.
519
- * @return String Yes | No
520
- */
521
- private function browser_link() {
522
- $model_config = WYSIJA::get('config', 'model');
523
- $browser_link = $model_config->getValue('viewinbrowser');
524
- if ($browser_link == 1) {
525
- $result = 'Yes';
526
- } else {
527
- $result = 'No';
528
- }
529
- return $result;
530
- }
531
-
532
- /**
533
- * Get profile edit option.
534
- * @return String Yes | No
535
- */
536
- private function profile_edit() {
537
- $model_config = WYSIJA::get('config', 'model');
538
- $profile_edit = $model_config->getValue('manage_subscriptions');
539
- if ($profile_edit == 1) {
540
- $result = 'Yes';
541
- } else {
542
- $result = 'No';
543
- }
544
- return $result;
545
- }
546
-
547
- /**
548
- * Get html edit in newsletter option.
549
- * @return String Yes | No
550
- */
551
- private function html_edit() {
552
- $model_config = WYSIJA::get('config', 'model');
553
- $html_edit = $model_config->getValue('html_source');
554
- if ($html_edit == 1) {
555
- $result = 'Yes';
556
- } else {
557
- $result = 'No';
558
- }
559
- return $result;
560
- }
561
-
562
- /**
563
- * Get mailpoet cron option.
564
- * @return String Yes | No
565
- */
566
- private function mailpoet_cron() {
567
- $model_config = WYSIJA::get('config', 'model');
568
- $cron_option = $model_config->getValue('cron_manual');
569
- if ($cron_option == 1) {
570
- $result = 'Yes';
571
- } else {
572
- $result = 'No';
573
- }
574
- return $result;
575
- }
576
-
577
- /**
578
- * Calculate average open rate.
579
- * @return Int
580
- */
581
- private function average_open_rate() {
582
-
583
- $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
584
- $query = 'SELECT COUNT(*) as opened_emails
585
- FROM ' . '[wysija]' . $model_email_user_stat->table_name . '
586
- WHERE status = 1';
587
- $result = $model_email_user_stat->query('get_res', $query);
588
-
589
- $opened_emails = $result[0]['opened_emails'];
590
- $total_emails = $this->total_emails_sent();
591
-
592
- if ($total_emails == 0) {
593
- $average_open_rate = 0;
594
- } else {
595
- $average_open_rate = round(($opened_emails * 100) / $total_emails);
596
- }
597
-
598
- return $average_open_rate;
599
- }
600
-
601
- /**
602
- * Calculate average click rate.
603
- * @return String opened/total
604
- */
605
- private function average_click_rate() {
606
-
607
- $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
608
- $query = 'SELECT COUNT(*) as clicked_emails
609
- FROM ' . '[wysija]' . $model_email_user_stat->table_name . '
610
- WHERE status = 2';
611
- $result = $model_email_user_stat->query('get_res', $query);
612
-
613
- $clicked_emails = $result[0]['clicked_emails'];
614
- $total_emails = $this->total_emails_sent();
615
-
616
- if ($total_emails == 0) {
617
- $average_click_rate = 0;
618
- } else {
619
- $average_click_rate = round(($clicked_emails * 100) / $total_emails);
620
- }
621
-
622
- return $average_click_rate;
623
- }
624
-
625
- /**
626
- * Get all emails sent.
627
- * @return Int
628
- */
629
- private function total_emails_sent() {
630
-
631
- $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
632
- $query = 'SELECT COUNT(*) as all_emails
633
- FROM ' . '[wysija]' . $model_email_user_stat->table_name . '';
634
- $result = $model_email_user_stat->query('get_res', $query);
635
-
636
- return $result[0]['all_emails'];
637
- }
638
-
639
- /**
640
- * Get total number of forms.
641
- * @return Int
642
- */
643
- private function forms_number() {
644
-
645
- $model_form = WYSIJA::get('forms', 'model');
646
- $query = 'SELECT COUNT(*) as forms_number
647
- FROM ' . '[wysija]' . $model_form->table_name . '';
648
- $result = $model_form->query('get_res', $query);
649
-
650
- return $result[0]['forms_number'];
651
- }
652
-
653
- /**
654
- * Get Industry specified in the settings page.
655
- * @return String
656
- */
657
- public function industry() {
658
- $model_config = WYSIJA::get('config', 'model');
659
- return $model_config->getValue('industry');
660
- }
661
-
662
- /**
663
- * Get if is using right to left language.
664
- * @return String
665
- */
666
- private function rtl() {
667
-
668
- if (is_rtl()) {
669
- $is_rtl = 'Yes';
670
- } else {
671
- $is_rtl = 'No';
672
- }
673
-
674
- return $is_rtl;
675
- }
676
-
677
- /**
678
- * Check if it's multisite.
679
- * @return String
680
- */
681
- private function is_multisite() {
682
-
683
- if (is_multisite()) {
684
- $is_multisite = 'Yes';
685
- } else {
686
- $is_multisite = 'No';
687
- }
688
-
689
- return $is_multisite;
690
- }
691
-
692
- /**
693
- * Get if is using beta mode
694
- * @return String
695
- */
696
- private function beta() {
697
-
698
- $model_config = WYSIJA::get('config', 'model');
699
-
700
- if ($model_config->getValue('beta_mode')) {
701
- $is_beta = 'Yes';
702
- } else {
703
- $is_beta = 'No';
704
- }
705
-
706
- return $is_beta;
707
- }
708
-
709
- /**
710
- * Checks if user used the archive page feature.
711
- * @return String true | false
712
- */
713
- private function archive_page() {
714
-
715
- $model_config = WYSIJA::get('config', 'model');
716
- $archive_lists = $model_config->getValue('archive_lists');
717
-
718
- if (!empty($archive_lists)) {
719
- $used_archive = 'true';
720
- } else {
721
- $used_archive = 'false';
722
- }
723
-
724
- return $used_archive;
725
- }
726
-
727
- /*
728
- Check if user is using custom fields or not.
729
- # => Yes | No
730
- */
731
- private function using_custom_fields() {
732
- $fields = WJ_Field::get_all();
733
- if ($fields != null) {
734
- $result = 'Yes';
735
- } else {
736
- $result = 'No';
737
- }
738
- return $result;
739
- }
740
-
741
- /*
742
- How many input custom fields are in use.
743
- # => int | null
744
- */
745
- private function custom_fields_input() {
746
- global $wpdb;
747
- $field = new WJ_Field();
748
- $table_name = $field->get_table_name();
749
- $result = $wpdb->get_var(
750
- "SELECT COUNT(*) as inputs
751
- FROM $table_name
752
- WHERE type = 'input'"
753
- );
754
- if ($result == null) {
755
- $result = '0';
756
- }
757
- return $result;
758
- }
759
-
760
- /*
761
- How many textarea custom fields are in use.
762
- # => int | null
763
- */
764
- private function custom_fields_textarea() {
765
- global $wpdb;
766
- $field = new WJ_Field();
767
- $table_name = $field->get_table_name();
768
- $result = $wpdb->get_var(
769
- "SELECT COUNT(*) as textareas
770
- FROM $table_name
771
- WHERE type = 'textarea'"
772
- );
773
- if ($result == null) {
774
- $result = '0';
775
- }
776
- return $result;
777
- }
778
-
779
- /*
780
- How many select custom fields are in use.
781
- # => int | null
782
- */
783
- private function custom_fields_select() {
784
- global $wpdb;
785
- $field = new WJ_Field();
786
- $table_name = $field->get_table_name();
787
- $result = $wpdb->get_var(
788
- "SELECT COUNT(*) as selects
789
- FROM $table_name
790
- WHERE type = 'select'"
791
- );
792
- if ($result == null) {
793
- $result = '0';
794
- }
795
- return $result;
796
- }
797
-
798
- /*
799
- How many checkbox custom fields are in use.
800
- # => int | null
801
- */
802
- private function custom_fields_checkbox() {
803
- global $wpdb;
804
- $field = new WJ_Field();
805
- $table_name = $field->get_table_name();
806
- $result = $wpdb->get_var(
807
- "SELECT COUNT(*) as checkboxes
808
- FROM $table_name
809
- WHERE type = 'checkbox'"
810
- );
811
- if ($result == null) {
812
- $result = '0';
813
- }
814
- return $result;
815
- }
816
-
817
- /*
818
- How many checkbox custom fields are in use.
819
- # => int | null
820
- */
821
- private function custom_fields_radio() {
822
- global $wpdb;
823
- $field = new WJ_Field();
824
- $table_name = $field->get_table_name();
825
- $result = $wpdb->get_var(
826
- "SELECT COUNT(*) as radios
827
- FROM $table_name
828
- WHERE type = 'radio'"
829
- );
830
- if ($result == null) {
831
- $result = '0';
832
- }
833
- return $result;
834
- }
835
-
836
- /*
837
- Check if user has been active in the last week.
838
- This means he sent at least one email.
839
- # => Yes | No
840
- */
841
- private function active_last_week() {
842
- global $wpdb;
843
- $model_stats = WYSIJA::get('email_user_stat', 'model');
844
- $table_name = '[wysija]' . $model_stats->table_name;
845
-
846
- $query = 'SELECT COUNT(*) as activities
847
- FROM ' . $table_name .
848
- ' WHERE sent_at > UNIX_TIMESTAMP(date_sub(now(), interval 1 week))';
849
-
850
- $result = $model_stats->query('get_res', $query);
851
- $result = $result[0]['activities'];
852
-
853
- if ($result > 0) {
854
- return 'Yes';
855
- }
856
- return 'No';
857
- }
858
-
859
- /**
860
- * Check PHP versions
861
- * @return string
862
- */
863
- private function php_version() {
864
- $php_version_factors = explode('.', phpversion());
865
- $main_version = (int)$php_version_factors[0];
866
- $sub_version = isset($php_version_factors[1]) ? (int)$php_version_factors[1] : null;
867
-
868
- $php_version = 'others';
869
- if ($sub_version !== null) {
870
- if ($main_version == 4) {
871
- $php_version = '4.x';
872
- } elseif ($main_version >= 5) {
873
- $php_version = implode('.', array( $main_version, $sub_version ));
874
- }
875
- }
876
- return $php_version;
877
- }
878
-
879
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ defined('WYSIJA') or die('Restricted access');
3
+ /*
4
+ Class Analytics.
5
+ It's a sort of useful stats and numbers generator about MailPoet usage.
6
+ It also handles the MixPanel integration.
7
+ $analytics = new WJ_Analytics();
8
+ $analytics->generate_data();
9
+ $analytics->send();
10
+ */
11
+ class WJ_Analytics {
12
+
13
+ // All analytics data to be sent to JS.
14
+ private $analytics_data = array(
15
+ 'php_version' => array(
16
+ 'label' => 'PHP version',
17
+ 'value' => ''
18
+ ),
19
+ 'monthly_emails_sent' => array(
20
+ 'label' => 'Monthly emails sent',
21
+ 'value' => ''
22
+ ),
23
+ 'lists_with_more_than_25' => array(
24
+ 'label' => 'Lists with more than 25 subscribers',
25
+ 'value' => ''
26
+ ),
27
+ 'confirmed_subscribers' => array(
28
+ 'label' => 'Confirmed subscribers',
29
+ 'value' => ''
30
+ ),
31
+ 'range_confirmed_subscribers' => array(
32
+ 'label' => 'Range Confirmed subscribers',
33
+ 'value' => ''
34
+ ),
35
+ 'unconfirmed_subscribers' => array(
36
+ 'label' => 'Unconfirmed subscribers',
37
+ 'value' => ''
38
+ ),
39
+ 'standard_newsletters' => array(
40
+ 'label' => 'Standard newsletters',
41
+ 'value' => ''
42
+ ),
43
+ 'auto_newsletters' => array(
44
+ 'label' => 'Auto newsletters',
45
+ 'value' => ''
46
+ ),
47
+ 'wordpress_version' => array(
48
+ 'label' => 'WordPress Version',
49
+ 'value' => ''
50
+ ),
51
+ 'plugin_version' => array(
52
+ 'label' => 'Plugin Version',
53
+ 'value' => ''
54
+ ),
55
+ 'license_type' => array(
56
+ 'label' => 'License type',
57
+ 'value' => ''
58
+ ),
59
+ 'sending_method' => array(
60
+ 'label' => 'Sending method',
61
+ 'value' => ''
62
+ ),
63
+ 'smtp_hostname' => array(
64
+ 'label' => 'Smtp hostname',
65
+ 'value' => ''
66
+ ),
67
+ 'activation_email_status' => array(
68
+ 'label' => 'Activation Email',
69
+ 'value' => ''
70
+ ),
71
+ 'average_open_rate' => array(
72
+ 'label' => 'Open rate',
73
+ 'value' => ''
74
+ ),
75
+ 'average_click_rate' => array(
76
+ 'label' => 'Click rate',
77
+ 'value' => ''
78
+ ),
79
+ 'industry' => array(
80
+ 'label' => 'Industry',
81
+ 'value' => ''
82
+ ),
83
+ 'wordpress_language' => array(
84
+ 'label' => 'WordPress Language',
85
+ 'value' => ''
86
+ ),
87
+ 'rtl' => array(
88
+ 'label' => 'Rtl',
89
+ 'value' => ''
90
+ ),
91
+ 'beta' => array(
92
+ 'label' => 'Beta',
93
+ 'value' => ''
94
+ ),
95
+ 'archive_page' => array(
96
+ 'label' => 'Archive Page',
97
+ 'value' => ''
98
+ ),
99
+ 'dkim_status' => array(
100
+ 'label' => 'DKIM Active',
101
+ 'value' => ''
102
+ ),
103
+ 'subscribe_in_comments' => array(
104
+ 'label' => 'Subscribe in comments',
105
+ 'value' => ''
106
+ ),
107
+ 'subscribe_on_register' => array(
108
+ 'label' => 'Subscribe on registration',
109
+ 'value' => ''
110
+ ),
111
+ 'browser_link' => array(
112
+ 'label' => 'View in browser link',
113
+ 'value' => ''
114
+ ),
115
+ 'profile_edit'=> array(
116
+ 'label' => 'Subcsribers can edit profile',
117
+ 'value' => ''
118
+ ),
119
+ 'html_edit' => array(
120
+ 'label' => 'Allow HTML edit',
121
+ 'value' => ''
122
+ ),
123
+ 'mailpoet_cron' => array(
124
+ 'label' => 'MailPoet Cron Enabled',
125
+ 'value' => ''
126
+ ),
127
+ 'forms_number' => array(
128
+ 'label' => 'Total number of forms',
129
+ 'value' => ''
130
+ ),
131
+ 'using_custom_fields' => array(
132
+ 'label' => 'Using custom fields',
133
+ 'value' => ''
134
+ ),
135
+ 'custom_fields_input' => array(
136
+ 'label' => 'Custom Fields: Input field',
137
+ 'value' => ''
138
+ ),
139
+ 'custom_fields_textarea' => array(
140
+ 'label' => 'Custom Fields: Textarea',
141
+ 'value' => ''
142
+ ),
143
+ 'custom_fields_select' => array(
144
+ 'label' => 'Custom Fields: Select',
145
+ 'value' => ''
146
+ ),
147
+ 'custom_fields_checkbox' => array(
148
+ 'label' => 'Custom Fields: Checkbox',
149
+ 'value' => ''
150
+ ),
151
+ 'custom_fields_radio' => array(
152
+ 'label' => 'Custom Fields: Radio',
153
+ 'value' => ''
154
+ ),
155
+ 'active_last_week' => array(
156
+ 'label' => 'Active last week',
157
+ 'value' => ''
158
+ ),
159
+ 'is_multisite' => array(
160
+ 'label' => 'Using Multisite',
161
+ 'value' => ''
162
+ ),
163
+ 'bounce_enabled' => array(
164
+ 'label' => 'Using bounce',
165
+ 'value' => ''
166
+ )
167
+ );
168
+
169
+ function __construct() {
170
+ }
171
+
172
+ /**
173
+ * Send data to Mixpanel by enqueuing the analytics JS file.
174
+ * @return
175
+ */
176
+ public function send() {
177
+
178
+ // Enqueue analytics Javascript.
179
+ wp_enqueue_script('analytics', WYSIJA_URL . 'js/analytics.js', array(), WYSIJA::get_version());
180
+ // Make analytics data available in JS.
181
+ wp_localize_script('analytics', 'analytics_data', $this->analytics_data);
182
+ }
183
+
184
+ /**
185
+ * Generate fresh data and store it in the $analytics_data Class property.
186
+ * @return
187
+ */
188
+ public function generate_data() {
189
+
190
+ foreach ($this->analytics_data as $key => $data) {
191
+ $method = $key;
192
+ $this->analytics_data[$key]['value'] = call_user_func(array($this, $method));
193
+ }
194
+
195
+ }
196
+
197
+ /**
198
+ * Calculate Emails sent in the last 30 days.
199
+ * @return Int
200
+ */
201
+ private function monthly_emails_sent() {
202
+
203
+ $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
204
+ $query = 'SELECT COUNT(*) as total_emails
205
+ FROM ' . '[wysija]' . $model_email_user_stat->table_name . '
206
+ WHERE DATE_SUB(CURDATE(),INTERVAL 30 DAY) <= sent_at';
207
+ $result = $model_email_user_stat->query('get_res', $query);
208
+
209
+ $total_emails = $result[0]['total_emails'];
210
+ switch (true) {
211
+ case ($total_emails <= 1000):
212
+ $track = 'Less than 1000';
213
+ break;
214
+ case ((1001 <= $total_emails) && ($total_emails <= 2500)):
215
+ $track = '1001 to 2500';
216
+ break;
217
+ case ((2501 <= $total_emails) && ($total_emails <= 5000)):
218
+ $track = '2501 to 5000';
219
+ break;
220
+ case ((5001 <= $total_emails) && ($total_emails <= 10000)):
221
+ $track = '5001 to 10000';
222
+ break;
223
+ case ((10001 <= $total_emails) && ($total_emails <= 25000)):
224
+ $track = '10001 to 25000';
225
+ break;
226
+ case ((25001 <= $total_emails) && ($total_emails <= 50000)):
227
+ $track = '25001 to 50000';
228
+ break;
229
+ case ((50001 <= $total_emails) && ($total_emails <= 100000)):
230
+ $track = '50001 to 100000';
231
+ break;
232
+ case (100001 <= $total_emails):
233
+ $track = 'More than 100001';
234
+ break;
235
+ default:
236
+ $track = 'No emails sent';
237
+ break;
238
+ }
239
+
240
+ return $track;
241
+
242
+ }
243
+
244
+ /*
245
+ Pass through the WordPress version.
246
+ */
247
+ private function wordpress_version() {
248
+ return get_bloginfo('version');
249
+ }
250
+
251
+ /*
252
+ Pass through the WordPress language.
253
+ */
254
+ private function wordpress_language() {
255
+ return get_bloginfo('language');
256
+ }
257
+
258
+ /*
259
+ The plugin version.
260
+ */
261
+ private function plugin_version() {
262
+ return WYSIJA::get_version();
263
+ }
264
+
265
+ /**
266
+ * Calculate lists with more than 25 subscribers.
267
+ * @return Int
268
+ */
269
+ private function lists_with_more_than_25() {
270
+
271
+ $model_user_list = WYSIJA::get('user_list', 'model');
272
+ $query = 'SELECT list_id, COUNT(*) as count
273
+ FROM ' . '[wysija]' . $model_user_list->table_name . '
274
+ GROUP BY list_id
275
+ HAVING COUNT(*) >= 25';
276
+ $result = $model_user_list->query('get_res', $query);
277
+ $lists_count = count($result);
278
+
279
+ return $lists_count;
280
+ }
281
+
282
+ /**
283
+ * Calculate total subscribers.
284
+ * @return Int
285
+ */
286
+ private function total_subcsribers() {
287
+
288
+ $model_user = WYSIJA::get('user', 'model');
289
+ $query = 'SELECT COUNT(*) as total_subscribers
290
+ FROM ' . '[wysija]' . $model_user->table_name;
291
+ $result = $model_user->query('get_res', $query);
292
+
293
+ return $result[0]['total_subscribers'];
294
+ }
295
+
296
+ /**
297
+ * Calculate confirmed subscribers.
298
+ * @return Int
299
+ */
300
+ private function confirmed_subscribers() {
301
+
302
+ $model_user = WYSIJA::get('user', 'model');
303
+ $query = 'SELECT COUNT(*) as confirmed_subscribers
304
+ FROM ' . '[wysija]' . $model_user->table_name . '
305
+ WHERE status = 1';
306
+ $result = $model_user->query('get_res', $query);
307
+
308
+ $confirmed_subscribers = $result[0]['confirmed_subscribers'];
309
+ $total_subscribers = $this->total_subcsribers();
310
+ $confirmed_percentage = round(($confirmed_subscribers * 100) / $total_subscribers);
311
+
312
+ return $confirmed_percentage;
313
+ }
314
+
315
+ /**
316
+ *
317
+ * @return string range eg: 0-100 101-200 2001-500
318
+ */
319
+ private function range_confirmed_subscribers(){
320
+ $model_user = WYSIJA::get('user', 'model');
321
+ $query = 'SELECT COUNT(*) as confirmed_subscribers
322
+ FROM ' . '[wysija]' . $model_user->table_name . '
323
+ WHERE status = 1';
324
+ $result = $model_user->query('get_res', $query);
325
+
326
+ $confirmed_subscribers = (int) $result[0]['confirmed_subscribers'];
327
+
328
+ $ranges_increment = array( 2000 => 100, 10000 => 500, 20000 => 1000, 40000 => 2000, 100000 => 5000, 200000 => 10000, 500000 => 25000, 1000000 => 50000);
329
+
330
+ $found_range = $this->range_finder( $confirmed_subscribers, $ranges_increment );
331
+
332
+ return $found_range['lower'].' - '.$found_range['upper'];
333
+ }
334
+
335
+ private function range_finder($value, $ranges_increment){
336
+
337
+ $limit_max = 0;
338
+ foreach( $ranges_increment as $limit => $range_increment ){
339
+ $small_limit = $limit_max + $range_increment;
340
+ $limit_max = $limit;
341
+
342
+ if( $value > $limit_max){
343
+ continue;
344
+ }
345
+
346
+ while( $value >= $small_limit && $small_limit <= $limit_max ){
347
+
348
+ if( $value > $small_limit ){
349
+ $min_value = $small_limit - $range_increment + 1;
350
+ }
351
+ if( $value == $small_limit ){
352
+ break;
353
+ }
354
+ $small_limit += $range_increment;
355
+ }
356
+
357
+ if( $value <= $small_limit){
358
+ break;
359
+ }
360
+ }
361
+
362
+ if( $value > $limit_max){
363
+ return array( 'lower' => $limit_max , 'upper' => 'above' );
364
+ }else{
365
+ if( $value < 1 ){
366
+ return array( 'lower' => 0 , 'upper' => 'or undefined' );
367
+ }else{
368
+ $min_value = $small_limit - $range_increment + 1;
369
+ return array( 'lower' => $min_value , 'upper' => $small_limit );
370
+ }
371
+ }
372
+
373
+ }
374
+
375
+ /**
376
+ * Calculate unconfirmed subscribers.
377
+ * @return Int
378
+ */
379
+ public function unconfirmed_subscribers() {
380
+
381
+ $model_user = WYSIJA::get('user', 'model');
382
+ $query = 'SELECT COUNT(*) as unconfirmed_subscribers
383
+ FROM ' . '[wysija]' . $model_user->table_name . '
384
+ WHERE status = 0';
385
+ $result = $model_user->query('get_res', $query);
386
+
387
+ return $result[0]['unconfirmed_subscribers'];
388
+ }
389
+
390
+ /**
391
+ * Calculate standard newsletters total.
392
+ * @return Int
393
+ */
394
+ private function standard_newsletters() {
395
+
396
+ $model_email = WYSIJA::get('email', 'model');
397
+ $query = 'SELECT COUNT(*) as standard_newsletters
398
+ FROM ' . '[wysija]' . $model_email->table_name . '
399
+ WHERE type = 1
400
+ AND status = 2';
401
+ $result = $model_email->query('get_res', $query);
402
+
403
+ return $result[0]['standard_newsletters'];
404
+ }
405
+
406
+ /**
407
+ * Calculate auto newsletters total.
408
+ * @return Int
409
+ */
410
+ private function auto_newsletters() {
411
+
412
+ $model_email = WYSIJA::get('email', 'model');
413
+ $query = 'SELECT COUNT(*) as auto_newsletters
414
+ FROM ' . '[wysija]' . $model_email->table_name . '
415
+ WHERE type = 2';
416
+ $result = $model_email->query('get_res', $query);
417
+
418
+ return $result[0]['auto_newsletters'];
419
+ }
420
+
421
+ /**
422
+ * Check license type in use.
423
+ * @return String Free | Premium
424
+ */
425
+ private function license_type() {
426
+
427
+ $model_config = WYSIJA::get('config', 'model');
428
+ $is_premium = $model_config->getValue('premium_key');
429
+
430
+ if ($is_premium) {
431
+ $license_type = 'Premium';
432
+ } else {
433
+ $license_type = 'Free';
434
+ }
435
+
436
+ return $license_type;
437
+ }
438
+
439
+ /**
440
+ * Get sending method in use.
441
+ * @return String
442
+ */
443
+ private function sending_method() {
444
+
445
+ $model_config = WYSIJA::get('config', 'model');
446
+ return $model_config->getValue('sending_method');
447
+ }
448
+
449
+ /**
450
+ * Get smtp hostname in use.
451
+ * @return String
452
+ */
453
+ private function smtp_hostname() {
454
+
455
+ $model_config = WYSIJA::get('config', 'model');
456
+ return $model_config->getValue('smtp_host');
457
+ }
458
+
459
+ /**
460
+ * Get activation email status.
461
+ * @return String On | Off
462
+ */
463
+ private function activation_email_status() {
464
+
465
+ $model_config = WYSIJA::get('config', 'model');
466
+ $activation_email_status = $model_config->getValue('confirm_dbleoptin');
467
+
468
+ if ($activation_email_status === 1) {
469
+ $result = 'On';
470
+ } else {
471
+ $result = 'Off';
472
+ }
473
+
474
+ return $result;
475
+ }
476
+
477
+ /**
478
+ * Get DKIM status.
479
+ * @return String Yes | No
480
+ */
481
+ private function dkim_status() {
482
+ $model_config = WYSIJA::get('config', 'model');
483
+ $dkim_status = $model_config->getValue('dkim_active');
484
+ if ($dkim_status === 1) {
485
+ $result = 'Yes';
486
+ } else {
487
+ $result = 'No';
488
+ }
489
+ return $result;
490
+ }
491
+
492
+ /**
493
+ * Get subscribe in comments.
494
+ * @return String Yes | No
495
+ */
496
+ private function subscribe_in_comments() {
497
+ $model_config = WYSIJA::get('config', 'model');
498
+ $subscribe_in_comments = $model_config->getValue('commentform');
499
+ if ($subscribe_in_comments == 1) {
500
+ $result = 'Yes';
501
+ } else {
502
+ $result = 'No';
503
+ }
504
+ return $result;
505
+ }
506
+
507
+ /**
508
+ * Get subscribe during registration option.
509
+ * @return String Yes | No
510
+ */
511
+ private function subscribe_on_register() {
512
+ $model_config = WYSIJA::get('config', 'model');
513
+ $subscribe_on_register = $model_config->getValue('registerform');
514
+ if ($subscribe_on_register == 1) {
515
+ $result = 'Yes';
516
+ } else {
517
+ $result = 'No';
518
+ }
519
+ return $result;
520
+ }
521
+
522
+ /**
523
+ * Get view in browser option.
524
+ * @return String Yes | No
525
+ */
526
+ private function browser_link() {
527
+ $model_config = WYSIJA::get('config', 'model');
528
+ $browser_link = $model_config->getValue('viewinbrowser');
529
+ if ($browser_link == 1) {
530
+ $result = 'Yes';
531
+ } else {
532
+ $result = 'No';
533
+ }
534
+ return $result;
535
+ }
536
+
537
+ /**
538
+ * Get profile edit option.
539
+ * @return String Yes | No
540
+ */
541
+ private function profile_edit() {
542
+ $model_config = WYSIJA::get('config', 'model');
543
+ $profile_edit = $model_config->getValue('manage_subscriptions');
544
+ if ($profile_edit == 1) {
545
+ $result = 'Yes';
546
+ } else {
547
+ $result = 'No';
548
+ }
549
+ return $result;
550
+ }
551
+
552
+ /**
553
+ * Get html edit in newsletter option.
554
+ * @return String Yes | No
555
+ */
556
+ private function html_edit() {
557
+ $model_config = WYSIJA::get('config', 'model');
558
+ $html_edit = $model_config->getValue('html_source');
559
+ if ($html_edit == 1) {
560
+ $result = 'Yes';
561
+ } else {
562
+ $result = 'No';
563
+ }
564
+ return $result;
565
+ }
566
+
567
+ /**
568
+ * Get mailpoet cron option.
569
+ * @return String Yes | No
570
+ */
571
+ private function mailpoet_cron() {
572
+ $model_config = WYSIJA::get('config', 'model');
573
+ $cron_option = $model_config->getValue('cron_manual');
574
+ if ($cron_option == 1) {
575
+ $result = 'Yes';
576
+ } else {
577
+ $result = 'No';
578
+ }
579
+ return $result;
580
+ }
581
+
582
+ /**
583
+ * Calculate average open rate.
584
+ * @return Int
585
+ */
586
+ private function average_open_rate() {
587
+
588
+ $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
589
+ $query = 'SELECT COUNT(*) as opened_emails
590
+ FROM ' . '[wysija]' . $model_email_user_stat->table_name . '
591
+ WHERE status = 1';
592
+ $result = $model_email_user_stat->query('get_res', $query);
593
+
594
+ $opened_emails = $result[0]['opened_emails'];
595
+ $total_emails = $this->total_emails_sent();
596
+
597
+ if ($total_emails == 0) {
598
+ $average_open_rate = 0;
599
+ } else {
600
+ $average_open_rate = round(($opened_emails * 100) / $total_emails);
601
+ }
602
+
603
+ return $average_open_rate;
604
+ }
605
+
606
+ /**
607
+ * Calculate average click rate.
608
+ * @return String opened/total
609
+ */
610
+ private function average_click_rate() {
611
+
612
+ $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
613
+ $query = 'SELECT COUNT(*) as clicked_emails
614
+ FROM ' . '[wysija]' . $model_email_user_stat->table_name . '
615
+ WHERE status = 2';
616
+ $result = $model_email_user_stat->query('get_res', $query);
617
+
618
+ $clicked_emails = $result[0]['clicked_emails'];
619
+ $total_emails = $this->total_emails_sent();
620
+
621
+ if ($total_emails == 0) {
622
+ $average_click_rate = 0;
623
+ } else {
624
+ $average_click_rate = round(($clicked_emails * 100) / $total_emails);
625
+ }
626
+
627
+ return $average_click_rate;
628
+ }
629
+
630
+ /**
631
+ * Get all emails sent.
632
+ * @return Int
633
+ */
634
+ private function total_emails_sent() {
635
+
636
+ $model_email_user_stat = WYSIJA::get('email_user_stat', 'model');
637
+ $query = 'SELECT COUNT(*) as all_emails
638
+ FROM ' . '[wysija]' . $model_email_user_stat->table_name . '';
639
+ $result = $model_email_user_stat->query('get_res', $query);
640
+
641
+ return $result[0]['all_emails'];
642
+ }
643
+
644
+ /**
645
+ * Get total number of forms.
646
+ * @return Int
647
+ */
648
+ private function forms_number() {
649
+
650
+ $model_form = WYSIJA::get('forms', 'model');
651
+ $query = 'SELECT COUNT(*) as forms_number
652
+ FROM ' . '[wysija]' . $model_form->table_name . '';
653
+ $result = $model_form->query('get_res', $query);
654
+
655
+ return $result[0]['forms_number'];
656
+ }
657
+
658
+ /**
659
+ * Get Industry specified in the settings page.
660
+ * @return String
661
+ */
662
+ public function industry() {
663
+ $model_config = WYSIJA::get('config', 'model');
664
+ return $model_config->getValue('industry');
665
+ }
666
+
667
+ /**
668
+ * Get if is using right to left language.
669
+ * @return String
670
+ */
671
+ private function rtl() {
672
+
673
+ if (is_rtl()) {
674
+ $is_rtl = 'Yes';
675
+ } else {
676
+ $is_rtl = 'No';
677
+ }
678
+
679
+ return $is_rtl;
680
+ }
681
+
682
+ /**
683
+ * Check if it's multisite.
684
+ * @return String
685
+ */
686
+ private function is_multisite() {
687
+
688
+ if (is_multisite()) {
689
+ $is_multisite = 'Yes';
690
+ } else {
691
+ $is_multisite = 'No';
692
+ }
693
+
694
+ return $is_multisite;
695
+ }
696
+
697
+ /**
698
+ * Get if is using beta mode
699
+ * @return String
700
+ */
701
+ private function beta() {
702
+
703
+ $model_config = WYSIJA::get('config', 'model');
704
+
705
+ if ($model_config->getValue('beta_mode')) {
706
+ $is_beta = 'Yes';
707
+ } else {
708
+ $is_beta = 'No';
709
+ }
710
+
711
+ return $is_beta;
712
+ }
713
+
714
+ /**
715
+ * Checks if user used the archive page feature.
716
+ * @return String true | false
717
+ */
718
+ private function archive_page() {
719
+
720
+ $model_config = WYSIJA::get('config', 'model');
721
+ $archive_lists = $model_config->getValue('archive_lists');
722
+
723
+ if (!empty($archive_lists)) {
724
+ $used_archive = 'true';
725
+ } else {
726
+ $used_archive = 'false';
727
+ }
728
+
729
+ return $used_archive;
730
+ }
731
+
732
+ /*
733
+ Check if user is using custom fields or not.
734
+ # => Yes | No
735
+ */
736
+ private function using_custom_fields() {
737
+ $fields = WJ_Field::get_all();
738
+ if ($fields != null) {
739
+ $result = 'Yes';
740
+ } else {
741
+ $result = 'No';
742
+ }
743
+ return $result;
744
+ }
745
+
746
+ /*
747
+ How many input custom fields are in use.
748
+ # => int | null
749
+ */
750
+ private function custom_fields_input() {
751
+ global $wpdb;
752
+ $field = new WJ_Field();
753
+ $table_name = $field->get_table_name();
754
+ $result = $wpdb->get_var(
755
+ "SELECT COUNT(*) as inputs
756
+ FROM $table_name
757
+ WHERE type = 'input'"
758
+ );
759
+ if ($result == null) {
760
+ $result = '0';
761
+ }
762
+ return $result;
763
+ }
764
+
765
+ /*
766
+ How many textarea custom fields are in use.
767
+ # => int | null
768
+ */
769
+ private function custom_fields_textarea() {
770
+ global $wpdb;
771
+ $field = new WJ_Field();
772
+ $table_name = $field->get_table_name();
773
+ $result = $wpdb->get_var(
774
+ "SELECT COUNT(*) as textareas
775
+ FROM $table_name
776
+ WHERE type = 'textarea'"
777
+ );
778
+ if ($result == null) {
779
+ $result = '0';
780
+ }
781
+ return $result;
782
+ }
783
+
784
+ /*
785
+ How many select custom fields are in use.
786
+ # => int | null
787
+ */
788
+ private function custom_fields_select() {
789
+ global $wpdb;
790
+ $field = new WJ_Field();
791
+ $table_name = $field->get_table_name();
792
+ $result = $wpdb->get_var(
793
+ "SELECT COUNT(*) as selects
794
+ FROM $table_name
795
+ WHERE type = 'select'"
796
+ );
797
+ if ($result == null) {
798
+ $result = '0';
799
+ }
800
+ return $result;
801
+ }
802
+
803
+ /*
804
+ How many checkbox custom fields are in use.
805
+ # => int | null
806
+ */
807
+ private function custom_fields_checkbox() {
808
+ global $wpdb;
809
+ $field = new WJ_Field();
810
+ $table_name = $field->get_table_name();
811
+ $result = $wpdb->get_var(
812
+ "SELECT COUNT(*) as checkboxes
813
+ FROM $table_name
814
+ WHERE type = 'checkbox'"
815
+ );
816
+ if ($result == null) {
817
+ $result = '0';
818
+ }
819
+ return $result;
820
+ }
821
+
822
+ /*
823
+ How many checkbox custom fields are in use.
824
+ # => int | null
825
+ */
826
+ private function custom_fields_radio() {
827
+ global $wpdb;
828
+ $field = new WJ_Field();
829
+ $table_name = $field->get_table_name();
830
+ $result = $wpdb->get_var(
831
+ "SELECT COUNT(*) as radios
832
+ FROM $table_name
833
+ WHERE type = 'radio'"
834
+ );
835
+ if ($result == null) {
836
+ $result = '0';
837
+ }
838
+ return $result;
839
+ }
840
+
841
+ /*
842
+ Check if user has been active in the last week.
843
+ This means he sent at least one email.
844
+ # => Yes | No
845
+ */
846
+ private function active_last_week() {
847
+ global $wpdb;
848
+ $model_stats = WYSIJA::get('email_user_stat', 'model');
849
+ $table_name = '[wysija]' . $model_stats->table_name;
850
+
851
+ $query = 'SELECT COUNT(*) as activities
852
+ FROM ' . $table_name .
853
+ ' WHERE sent_at > UNIX_TIMESTAMP(date_sub(now(), interval 1 week))';
854
+
855
+ $result = $model_stats->query('get_res', $query);
856
+ $result = $result[0]['activities'];
857
+
858
+ if ($result > 0) {
859
+ return 'Yes';
860
+ }
861
+ return 'No';
862
+ }
863
+
864
+ /**
865
+ * Check PHP versions
866
+ * @return string
867
+ */
868
+ private function php_version() {
869
+ $php_version_factors = explode('.', phpversion());
870
+ $main_version = (int)$php_version_factors[0];
871
+ $sub_version = isset($php_version_factors[1]) ? (int)$php_version_factors[1] : null;
872
+
873
+ $php_version = 'others';
874
+ if ($sub_version !== null) {
875
+ if ($main_version == 4) {
876
+ $php_version = '4.x';
877
+ } elseif ($main_version >= 5) {
878
+ $php_version = implode('.', array( $main_version, $sub_version ));
879
+ }
880
+ }
881
+ return $php_version;
882
+ }
883
+
884
+
885
+ /**
886
+ * Check if bounce is enabled
887
+ * @return string
888
+ */
889
+ private function bounce_enabled() {
890
+ $multisite_prefix = '';
891
+ if ( is_multisite() ) {
892
+ $multisite_prefix = 'ms_';
893
+ }
894
+ $model_config = WYSIJA::get('config', 'model');
895
+ return ($model_config->getValue(
896
+ $multisite_prefix . 'bounce_process_auto')
897
+ ) ? "Yes" : "No";
898
+ }
899
+ }
classes/WJ_Bridge.php CHANGED
@@ -61,9 +61,8 @@ class WJ_Bridge {
61
 
62
  $result = null;
63
  $result = wp_remote_post($url, $params);
64
-
65
  try {
66
- if (!($result instanceof WP_Error) && in_array( (int)$result['response']['code'], array( 201, 400, 401) ) )
67
  {
68
  switch( $result['response']['code'] ){
69
  case 201:
@@ -76,7 +75,9 @@ class WJ_Bridge {
76
  $this->error = 'Not Authorized';
77
  break;
78
  }
79
-
 
 
80
  }
81
  } catch(Exception $e) {
82
  $this->error = 'Unexpected error: '.$e->getMessage() . ' ['.var_export($result, true).']';// do nothing
61
 
62
  $result = null;
63
  $result = wp_remote_post($url, $params);
 
64
  try {
65
+ if (!is_wp_error($result) && in_array( (int)$result['response']['code'], array( 201, 400, 401) ) )
66
  {
67
  switch( $result['response']['code'] ){
68
  case 201:
75
  $this->error = 'Not Authorized';
76
  break;
77
  }
78
+ }
79
+ else if (is_wp_error($result)) {
80
+ $this->error = $result->get_error_messages();
81
  }
82
  } catch(Exception $e) {
83
  $this->error = 'Unexpected error: '.$e->getMessage() . ' ['.var_export($result, true).']';// do nothing
controllers/front/confirm.php CHANGED
@@ -62,7 +62,7 @@ class WYSIJA_control_front_confirm extends WYSIJA_control_front{
62
 
63
  $wysija_key = '';
64
  if(isset( $_GET['wysija-key'] )){
65
- $wysija_key = $_GET['wysija-key'];
66
  }
67
  $undo_paramsurl = array(
68
  'wysija-page' => 1,
62
 
63
  $wysija_key = '';
64
  if(isset( $_GET['wysija-key'] )){
65
+ $wysija_key = filter_var($_GET['wysija-key'], FILTER_SANITIZE_STRING);
66
  }
67
  $undo_paramsurl = array(
68
  'wysija-page' => 1,
controllers/front/stats.php CHANGED
@@ -28,15 +28,17 @@ class WYSIJA_control_front_stats extends WYSIJA_control_front{
28
  if(!empty($WJ_Stats->clicked_url)){
29
  // clicked stats
30
  $url = $this->encode_url($WJ_Stats->subscriber_clicked());
31
- $external_url = htmlentities($WJ_Stats->subscriber_clicked()); // escape HTML characters (that's how URLs are saved in the DB)
32
- $external_url = preg_replace('!/?\?utm.*!', '', $external_url); // remove anything that starts with ?utm or /?utm
33
- $internal_site_url = htmlentities(get_site_url());
34
- $internal_home_url = htmlentities(get_home_url());
35
  $model_email = WYSIJA::get('email', 'model');
36
  $email_object = $model_email->getOne(false,array('email_id' => $_REQUEST['email_id']));
37
- if (preg_match('/'. preg_quote($external_url, '/') .'/', $email_object['body']) ||
38
- preg_match('/^'. preg_quote($internal_site_url, '/') .'/', $url) ||
39
- preg_match('/^'. preg_quote($internal_home_url, '/') .'/', $url)
 
 
40
  ) {
41
  do_action('mpoet_click_stats', $WJ_Stats);
42
  $this->redirect($url);
28
  if(!empty($WJ_Stats->clicked_url)){
29
  // clicked stats
30
  $url = $this->encode_url($WJ_Stats->subscriber_clicked());
31
+ $external_url_unescaped_and_without_utm = preg_replace('!/?\?utm.*!i', '', $url);
32
+ $external_url_escaped_and_without_utm = preg_replace('!/?\?utm.*!i', '', htmlentities($WJ_Stats->subscriber_clicked())); // remove anything that starts with ?utm or /?utm
33
+ $internal_site_url = preg_replace('!https?://!i', '', htmlentities(get_site_url()));
34
+ $internal_home_url = preg_replace('!https?://!i', '', htmlentities(get_home_url()));
35
  $model_email = WYSIJA::get('email', 'model');
36
  $email_object = $model_email->getOne(false,array('email_id' => $_REQUEST['email_id']));
37
+ if (preg_match('!'. preg_quote($external_url_unescaped_and_without_utm, '!') .'!i', $email_object['body']) ||
38
+ preg_match('!'. preg_quote($external_url_escaped_and_without_utm, '!') .'!i', $email_object['body']) ||
39
+ preg_match('!^https?://'. preg_quote($internal_site_url, '!') .'!i', $url) ||
40
+ preg_match('!^https?://'. preg_quote($internal_home_url, '!') .'!i', $url)
41
+
42
  ) {
43
  do_action('mpoet_click_stats', $WJ_Stats);
44
  $this->redirect($url);
core/base.php CHANGED
@@ -19,7 +19,7 @@ class WYSIJA_object{
19
  * Static variable holding core MailPoet's version
20
  * @var array
21
  */
22
- static $version = '2.6.19';
23
 
24
  function __construct(){}
25
 
@@ -270,7 +270,7 @@ class WYSIJA_help extends WYSIJA_object{
270
  add_action( 'admin_enqueue_scripts', array( $this, 'admin_enqueue_scripts' ) );
271
  add_filter( 'admin_body_class', array( $this, 'admin_body_class' ) );
272
  }
273
-
274
  function widgets_init() {
275
  //load the widget file
276
  require_once(WYSIJA_WIDGETS.'wysija_nl.php');
@@ -392,7 +392,7 @@ class WYSIJA_help extends WYSIJA_object{
392
 
393
  // let's make sure the requested task exist
394
  if( method_exists( $this->controller , $_REQUEST['task'] ) ){
395
- $result_array['result'] = $this->controller->$_REQUEST['task']();
396
  }else{
397
  $this->error( 'Method "' . $_REQUEST['task'] . '" doesn\'t exist for controller : "'.$_REQUEST['controller'] );
398
  }
19
  * Static variable holding core MailPoet's version
20
  * @var array
21
  */
22
+ static $version = '2.7';
23
 
24
  function __construct(){}
25
 
270
  add_action( 'admin_enqueue_scripts', array( $this, 'admin_enqueue_scripts' ) );
271
  add_filter( 'admin_body_class', array( $this, 'admin_body_class' ) );
272
  }
273
+
274
  function widgets_init() {
275
  //load the widget file
276
  require_once(WYSIJA_WIDGETS.'wysija_nl.php');
392
 
393
  // let's make sure the requested task exist
394
  if( method_exists( $this->controller , $_REQUEST['task'] ) ){
395
+ $result_array['result'] = call_user_func(array($this->controller, $_REQUEST['task']));
396
  }else{
397
  $this->error( 'Method "' . $_REQUEST['task'] . '" doesn\'t exist for controller : "'.$_REQUEST['controller'] );
398
  }
core/model.php CHANGED
@@ -1,1052 +1,1040 @@
1
- <?php
2
- defined('WYSIJA') or die('Restricted access');
3
- class WYSIJA_model extends WYSIJA_object{
4
-
5
- var $table_prefix='wysija';
6
- var $table_name='';
7
- var $pk='';
8
- var $values=array();
9
- var $conditions=array();
10
- var $orderby=array();
11
- var $groupby=false;
12
- var $noCheck =false;
13
- var $replaceQRY=false;
14
- var $limitON=false;
15
- var $dbg=false;
16
- var $colCheck=true;
17
- var $getFormat=ARRAY_A;
18
- var $getOne=false;
19
- var $fieldValid=true;
20
- var $specialUpdate=false;
21
- var $escapeFields=array();
22
- var $escapingOn=false;
23
- var $tableWP=false;
24
- var $columns=array();
25
- var $joins=array();
26
- var $ignore = false;
27
- var $sql_error = false;
28
- var $last_error = '';
29
- var $comparisonKeys = array('equal', 'notequal', 'like', 'greater', 'less', 'greater_eq', 'less_eq', 'is');
30
- var $time_start = 0;
31
- var $query_duration = 0;
32
-
33
- function __construct($extensions=''){
34
- if(defined('WYSIJA_DBG') && WYSIJA_DBG>0) $this->dbg=true;
35
- global $wpdb;
36
- $this->wpprefix=$wpdb->prefix;
37
- if($extensions) $this->table_prefix=$extensions;
38
- //fix for radiokapi
39
- //$this->wpprefix=$wpdb->base_prefix;
40
- }
41
- /**
42
- * since we reuse the same objects accross the whole application
43
- * once in a while for instance between a delete and a select we need to reset the objects to update the conditions
44
- */
45
- function reset(){
46
- $this->values = array();
47
- $this->conditions = array();
48
- $this->orderby = array();
49
- $this->groupby = false;
50
- $this->getFormat = ARRAY_A;
51
- $this->getOne = false;
52
- $this->limitON = false;
53
- $this->sql_error = false;
54
- $this->last_error = '';
55
- }
56
-
57
- /**
58
- *
59
- * @param type $columnsOrPKval
60
- * @param type $conditions
61
- * @return type
62
- */
63
- function get($columnsOrPKval=false,$conditions=array()){
64
- /*then columns becomes the pk value*/
65
- if(!$conditions){
66
- $conditions=array('equal'=>array($this->pk=>$columnsOrPKval));
67
- $columnsOrPKval=false;
68
- $this->noCheck=true;
69
- }
70
-
71
- /* if we pass just the id strong in the get conditions then it's the pk*/
72
- if($conditions && !is_array($conditions)){
73
- $conditions=array('equal'=>array($this->pk=>$conditions));
74
- }
75
- if($this->setConditions($conditions)){
76
- if($this->getOne) $results=$this->getRows($columnsOrPKval,0,1);
77
- else $results=$this->getRows($columnsOrPKval);
78
- //$this->escapeQuotesFromRes($results);
79
- if($this->getOne && count($results)==1){
80
- switch($this->getFormat){
81
- case ARRAY_A:
82
- foreach($results as $res)return $res;
83
- break;
84
- case OBJECT:
85
- foreach($results as $res)return $res;
86
- break;
87
- }
88
- }
89
- else return $results;
90
- }
91
-
92
- return false;
93
- }
94
-
95
- function getOne($columnsOrPKval=false,$conditions=array()){
96
- $this->getOne=true;
97
- $this->limitON=true;
98
-
99
- return $this->get($columnsOrPKval,$conditions);
100
- }
101
-
102
- /**
103
- * get a list of result based on a select query
104
- * @global type $wpdb
105
- * @param type $columns
106
- * @param type $page
107
- * @param type $limit
108
- * @return type
109
- */
110
- function getRows($columns=false,$page=0,$limit=false){
111
-
112
- /*set the columns*/
113
- if($columns !== false){
114
- if(is_array($columns)){
115
-
116
- foreach($columns as $column){
117
-
118
- if(!isset($this->columns[$column])){
119
- $this->error(sprintf('Column does not exist.'));
120
- return false;
121
- }
122
- }
123
- $columns=implode(', ',$columns);
124
- }else{
125
- if(!isset($this->columns[$columns])){
126
- $this->error(sprintf('Column does not exist.'));
127
- return false;
128
- }
129
- }
130
- }else{
131
- $columns='*';
132
-
133
- }
134
-
135
-
136
- $query='SELECT '.$columns.' FROM `'.$this->getSelectTableName()."`";
137
- $query.=$this->makeJoins();
138
- $query.=$this->makeWhere();
139
- $query.=$this->makeGroupBY();
140
- $query.=$this->makeOrderBY();
141
-
142
- if($this->limitON) $query.=$this->setLimit($page,$limit);
143
- $results=$this->query('get_res',$query,$this->getFormat);
144
-
145
- //$this->escapeQuotesFromRes($results);
146
-
147
- return $results;
148
- }
149
-
150
- function escapeQuotesFromRes(&$results){
151
- if(!$this->escapingOn) return false;
152
- foreach($results as $k =>$r){
153
-
154
- if(in_array($this->getFormat,array(ARRAY_A,ARRAY_N))){
155
- foreach($r as $k1 =>$v1){
156
- if(in_array($k1,$this->escapeFields)){
157
- $results[$k][$k1]= stripslashes($v1);
158
- }
159
- }
160
- }
161
- }
162
- }
163
-
164
- function setLimit($page=0,$limit=false){
165
- /*set the limit of the selection*/
166
-
167
- if(!$this->getOne){
168
- if($page==0){
169
- if(isset($_REQUEST['pagi'])){
170
- $page=(int)$_REQUEST['pagi'];
171
- if($page!=0) $page=$page-1;
172
- }
173
-
174
- }else $page=$page-1;
175
- }
176
-
177
- if(!$limit){
178
- if(isset($this->limit_pp)) $limit=$this->limit_pp;
179
- else{
180
- $config=WYSIJA::get('config','model');
181
- $limit=$config->getValue('limit_listing');
182
- }
183
- }
184
-
185
- $this->limit=(int)$limit;
186
- $this->page=$page;
187
- $this->limit_start=(int)($this->page*$this->limit);
188
- $this->limit_end=(int)($this->limit_start+$this->limit);
189
-
190
- return " LIMIT $this->limit_start , $this->limit";
191
- }
192
-
193
- /**
194
- * DEPRECATED
195
- * to have a custom query through the model and get the result immediately
196
- * @param type $query
197
- * @return type
198
- */
199
- function getResults($query,$type=ARRAY_A){
200
- return $this->query('get_res',$query, $type);
201
- }
202
-
203
- /**
204
- * to have a custom query through the model and get the result immediately
205
- * @param type $query
206
- * @return type
207
- */
208
- public function get_results($query,$type=ARRAY_A){
209
- return $this->getResults($query,$type);
210
- }
211
-
212
-
213
- function getSelectTableName(){
214
- if($this->joins && isset($this->joins['tablestart'])){
215
- if(isset($this->joins['prefstart'])) return $this->wpprefix.$this->joins['prefstart'].'_'.$this->joins['tablestart'];
216
- else return $this->getPrefix().$this->joins['tablestart'];
217
- }else return $this->getPrefix().$this->table_name;
218
- }
219
-
220
- /**
221
- * simple SQL count
222
- * @global type $wpdb
223
- * @return type
224
- */
225
- function count($query=false,$keygetcount=false){
226
- if(!$query){
227
- $groupBy=$this->makeGroupBY();
228
- $columnMore='';
229
- if($groupBy) $columnMore=','.$this->groupby;
230
- $query='SELECT COUNT('.$this->getPk().') as count '.$columnMore.' FROM `'.$this->getSelectTableName().'`';
231
- $query.=$this->makeJoins();
232
-
233
- $query.=$this->makeWhere();
234
- $query.=$groupBy;
235
- }
236
-
237
-
238
- // if dbg is on we track the duration of the query
239
- if($this->dbg){
240
- $this->timer_start();
241
- }
242
- $results=$this->query('get_res',$query,$this->getFormat);
243
-
244
- // if dbg is on we track the duration of the query
245
- if($this->dbg){
246
- $this->timer_stop();
247
- $this->keepQry('count');
248
- }
249
-
250
- if(!$results || count($results)>1) return $results;
251
- else {
252
- if($keygetcount) return $results[0][$keygetcount];
253
- else{
254
- foreach($results[0] as $key => $count) return $count;
255
- }
256
- }
257
-
258
-
259
- return $results;
260
- }
261
-
262
- /**
263
- * make the SQL WHERE condition string
264
- * @return string
265
- */
266
- function makeWhere(){
267
- $query='';
268
- if($this->conditions){
269
- /*set the WHERE clause*/
270
- $conditions=array();
271
- foreach($this->conditions as $type=>$values){
272
- if(!in_array($type, $this->comparisonKeys)){
273
- $conditionsss=$this->conditions;
274
- $this->conditions=array();
275
- $this->conditions['equal']=$conditionsss;
276
-
277
- break;
278
- }
279
- }
280
- foreach($this->conditions as $type=>$values){
281
- if($type=='like' && count($values)>1){
282
- if(is_array($values)){
283
- $total=count($values);
284
- $i=1;
285
- $likeCond='';
286
- foreach($values as $qfield => $qval){
287
- $qval = html_entity_decode($qval, ENT_QUOTES);
288
- $likeCond.=$qfield." LIKE '%".esc_sql(addcslashes($qval, '%_' ))."%'";
289
- if($i<$total){
290
- $likeCond.=' OR ';
291
- }
292
- $i++;
293
- }
294
- $conditions[]='('.$likeCond.')';
295
- }
296
- continue;
297
- }
298
-
299
- foreach($values as $condK => $condVal){
300
-
301
- //secure from injections
302
- $this->_secureFieldVal($condK, $condVal);
303
-
304
- switch($type){
305
- case 'equal':
306
- if(is_array($condVal)){
307
- $conditions[]=$condK.' IN ("'.implode('","', $condVal).'")';
308
- }else{
309
- if(is_null($condVal)) {
310
- $conditions[] = $condK.' IS NULL';
311
- } else {
312
- if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
313
- $conditions[] = $condK.'='.$condVal;
314
- }
315
- }
316
- break;
317
- case 'notequal':
318
- if(is_array($condVal)){
319
- $conditions[]=$condK.' NOT IN ("'.implode('","', $condVal).'")';
320
- }else{
321
- //this means that if I delete something with a list of ids and the array happens to be empty array of ids it will just delete everything by
322
- if(is_null($condVal)) {
323
- $conditions[] = $condK.' IS NOT NULL';
324
- } else {
325
- if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
326
- $conditions[] = $condK.' != '.$condVal;
327
- }
328
- }
329
- break;
330
- case 'like':
331
- $conditions[]=$condK." LIKE '%".esc_sql(addcslashes($condVal, '%_' ))."%'";
332
- break;
333
- case 'greater':
334
- if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
335
- $conditions[]=$condK.' > '.$condVal;
336
- break;
337
- case 'less':
338
- if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
339
- $conditions[]=$condK.' < '.$condVal;
340
- break;
341
- case 'greater_eq':
342
- if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
343
- $conditions[]=$condK.' >= '.$condVal;
344
- break;
345
- case 'less_eq':
346
- if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
347
- $conditions[]=$condK.' <= '.$condVal;
348
- break;
349
- case 'is':
350
-
351
- $conditions[]=$condK.' '.$condVal;
352
- break;
353
- }
354
- }
355
-
356
- }
357
-
358
- $query.=' WHERE '.implode(' AND ',$conditions);
359
- }
360
-
361
- return $query;
362
- }
363
-
364
- /**
365
- * make the SQL ORDER BY condition string
366
- * @return string
367
- */
368
- function makeOrderBY(){
369
- $query=' ORDER BY ';
370
- if($this->orderby){
371
- /*set the ORDER BY clause*/
372
- $query.=$this->orderby.' '.$this->orderbyt;
373
- }else{
374
- /*by default we order by pk desc*/
375
- if(is_array($this->pk)) return '';
376
- $query.=$this->pk.' DESC';
377
- }
378
- return $query;
379
- }
380
-
381
-
382
- function makeJoins(){
383
-
384
- if($this->joins){
385
- $join=' as A';
386
- $arrayLetters=array('B','C','D','E');
387
- foreach($this->joins['tablejoins'] as $table => $fk){
388
- $letter=array_shift($arrayLetters);
389
- $join.=' JOIN `'.$this->getPrefix().$table.'` AS '.$letter." on $letter.$fk=A.".$this->joins['keystart'].' ';
390
- }
391
- /*set the ORDER BY clause*/
392
- return $join;
393
- }else return '';
394
-
395
- }
396
- /**
397
- * make the SQL ORDER BY condition string
398
- * @return string
399
- */
400
- function makeGroupBY(){
401
-
402
- if($this->groupby){
403
- /*set the ORDER BY clause*/
404
- return ' GROUP BY '.$this->groupby;
405
- }else return '';
406
-
407
- }
408
- function groupBy($name){
409
-
410
- if (!is_string($name) OR preg_match('|[^a-z0-9#_.-]|i',$name) !== 0 ){
411
- $this->groupby=false;
412
- }else $this->groupby=$name;
413
- }
414
- function orderBy($name,$type = 'ASC'){
415
-
416
- if(is_array($name) and count($name) > 0) {
417
- // set order by to empty string
418
- $this->orderby = '';
419
- $this->ordert = '';
420
-
421
- // count number of arguments
422
- $count = count($name);
423
-
424
- // build order by query
425
- for($i = 0; $i < $count; $i++) {
426
-
427
- $value = current($name);
428
-
429
- //security escaping
430
- if(!is_string(key($name)) OR preg_match('|[^a-z0-9#_.-]|i',key($name)) !== 0 ){
431
- $orderByCol="";
432
- }else $orderByCol=key($name);
433
- //security escaping
434
- if(!is_string($value) OR preg_match('|[^a-z0-9#_.-]|i',$value) !== 0 ){
435
- $orderByVal="";
436
- }else $orderByVal=$value;
437
-
438
- if($i === ($count - 1)) {
439
- $this->orderby .= $orderByCol;
440
- $this->ordert = $orderByVal;
441
- } else {
442
- $this->orderby .=$orderByCol.' '.$orderByVal;
443
- $this->orderby .= ', ';
444
- next($name);
445
- }
446
- }
447
- } else if(!is_string($name) OR preg_match('|[^a-z0-9#_.-]|i',$name) !== 0 ){
448
- $this->orderby="";
449
- }else {
450
- $this->orderby=$name;
451
- }
452
-
453
- if(!in_array($type,array('DESC','ASC'))) $type = 'DESC';
454
- $this->orderbyt=$type;
455
- }
456
-
457
-
458
-
459
- /**
460
- * prepare for an insert procedure
461
- * @param type $values
462
- */
463
- function insert($values,$ignore=false){
464
- if($ignore)$this->ignore=true;
465
- if($this->setValues($values)){
466
- return $this->save();
467
- }else{
468
- $this->error(sprintf('missing values in model insert : %1$s.', get_class($this)));
469
- }
470
- }
471
-
472
-
473
- function replace($values=array()){
474
- $this->replaceQRY=true;
475
- $this->insert($values);
476
- $this->replaceQRY=false;
477
- }
478
-
479
- /**
480
- * prepare for an update procedure
481
- * @param type $values
482
- * @param type $conditions
483
- */
484
- function update($values=array(),$conditions=array()){
485
-
486
- if($this->setValues($values)){
487
- /*if no condition is set then we set it mannualy based on the primary key*/
488
- if(!$conditions){
489
- if(!$this->conditions){
490
- if(isset($values[$this->pk]) && $values[$this->pk]){
491
-
492
- $this->setConditions(array($this->pk => $values[$this->pk]), true);
493
-
494
- unset($values[$this->pk]);
495
-
496
- return $this->save(true);
497
-
498
- }else{
499
- $this->error(sprintf('missing pk value in model update : %1$s.', get_class($this)));
500
- }
501
- }
502
-
503
- }else{
504
- if($this->setConditions($conditions,true)){
505
- return $this->save(true);
506
- }else{
507
- $this->error(sprintf('missing conditions in model update : %1$s.', get_class($this)));
508
- }
509
- }
510
-
511
- }else{
512
- $this->error(sprintf('missing values in model update : %1$s.', get_class($this)));
513
- }
514
- }
515
-
516
- /**
517
- * UPDATE with a special where condition
518
- * @param type $table
519
- * @param type $data
520
- * @param type $where
521
- * @param type $format
522
- * @param type $where_format
523
- * @return type
524
- */
525
- function specialUpdate( $table, $data, $where, $format = null, $where_format = null ) {
526
- if ( ! is_array( $data ) || ! is_array( $where ) )
527
- return false;
528
-
529
- $formats = $format = (array) $format;
530
- $bits = $wheres = array();
531
-
532
- $i=0;
533
- foreach ( $data as $field => $val) {
534
- $this->_secureFieldVal($field,$val);
535
-
536
- switch($format[$i]){
537
- case "%d":
538
- $bits[] = "`$field` = ".(int)$val;
539
- break;
540
- case '[increment]':
541
- $bits[] = "`$field` = ".$field.'+1';
542
- break;
543
- case '[decrement]':
544
- $bits[] = "`$field` = ".$field.'-1';
545
- break;
546
- default :
547
- $bits[] = "`$field` = '".$val."'";
548
- }
549
- $i++;
550
- }
551
-
552
- $sql = "UPDATE `$table` SET " . implode( ', ', $bits ) . ' ' . $this->makeWhere();
553
- return $this->query( $sql );
554
- }
555
-
556
-
557
- function _secureFieldVal( &$field, &$mixed ) {
558
- if ( ! is_string( $field ) || preg_match( '|[^a-z0-9#_.-]|i', $field ) !== 0 ) {
559
- die('field "'.$field .'" not secured');
560
- }
561
- if ( is_string( $mixed ) || is_numeric( $mixed ) || is_bool( $mixed ) ) {
562
- $mixed = esc_sql( $mixed );
563
- } else {
564
- if(!empty($mixed) && is_array($mixed)){
565
- foreach ( $mixed as $key => &$value ) {
566
- $this->_secureFieldVal( $field, $value );
567
- }
568
- }
569
- }
570
- }
571
- /**
572
- * save information as an update or an insert
573
- * @global type $wpdb
574
- * @param type $update
575
- * @return type
576
- */
577
- function save($update=false){
578
-
579
- if($update)$updateStr='Update';
580
- else $updateStr='Insert';
581
- $beforeSave='before'.$updateStr;
582
- $afterSave='after'.$updateStr;
583
-
584
-
585
-
586
- if(!$update && isset($this->columns['created_at']))$this->values['created_at']=time();
587
- foreach($this->columns as $key => $params){
588
- /*check for auto columns */
589
- if((isset($params['autoup']) && $update) || (!$update && $key!='sent_at')){
590
- if(isset($params['type']) && !isset($this->values[$key])){
591
- switch($params['type']){
592
- case 'date':
593
- $this->values[$key]=time();
594
- break;
595
- case 'ip':
596
- $userHelper=WYSIJA::get("user","helper");
597
- /*record the ip and save the user*/
598
- $this->values[$key]=$userHelper->getIP();
599
- break;
600
- case 'referer':
601
- /*record the ip and save the user*/
602
- $this->values[$key]=$_SERVER['HTTP_REFERER'];
603
- break;
604
- }
605
- }
606
-
607
- }
608
- }
609
-
610
- if(method_exists($this,$beforeSave)){
611
- if(!$this->$beforeSave()){
612
- //$this->error(sprintf('Problem during validation "%2$s" in model : %1$s.', get_class($this), $beforeSave));
613
- return false;
614
- }
615
- }
616
-
617
- /*prepare a format list for the update and insert function*/
618
- $fieldsFormats=array();
619
- if(!is_array($this->pk) && isset($this->values[$this->pk])) unset($this->values[$this->pk]);
620
- foreach($this->values as $key =>$val){
621
- if(!isset($this->columns[$key]['html'])) $this->values[$key]=strip_tags($val);
622
- /* let's correct the type of the values based on the one defined in the model*/
623
- if(in_array($val, array('[increment]','[decrement]'))){
624
- $fieldsFormats[]=$val;
625
- $this->specialUpdate=true;
626
- }else{
627
- //dbg($this->values);
628
- if(!isset($this->columns[$key]['type'])){
629
- $this->columns[$key]['type']='default';
630
- }
631
- switch($this->columns[$key]['type']){
632
- case 'integer':
633
- case 'boolean':
634
- $fieldsFormats[]="%d";
635
- break;
636
- default:
637
- $fieldsFormats[]="%s";
638
-
639
- }
640
- }
641
-
642
- }
643
-
644
- if($this->fieldValid && !$this->validateFields()) {
645
- $this->error(__('Error Validating the fields',WYSIJA),true);
646
- $this->stay=true;
647
- return false;
648
- }
649
-
650
- global $wpdb;
651
-
652
- // if dbg is on we track the duration of the query
653
- if($this->dbg){
654
- $this->timer_start();
655
- }
656
-
657
- if($update){
658
-
659
- if( $this->specialUpdate || isset($this->conditions['equal']) || isset($this->conditions['notequal']) || isset($this->conditions['like'])){
660
-
661
- $resultSave=$this->specialUpdate($this->getPrefix().$this->table_name,$this->values,$this->conditions,$fieldsFormats);
662
- $this->logError();
663
- }else{
664
-
665
- $wpdb->update($this->getPrefix().$this->table_name,$this->values,$this->conditions,$fieldsFormats);
666
- $this->logError();
667
- $resultSave=$wpdb->result;
668
- }
669
-
670
- }else{
671
- if($this->replaceQRY){
672
- $resultSave=$wpdb->replace($this->getPrefix().$this->table_name,$this->values,$fieldsFormats);
673
- $this->logError();
674
- }else{
675
-
676
- if($this->ignore) $resultSave=$wpdb->insert($this->getPrefix().$this->table_name,$this->values,$fieldsFormats);
677
- else $resultSave=$wpdb->insert($this->getPrefix().$this->table_name,$this->values,$fieldsFormats);
678
-
679
- $this->logError();
680
- //dbg('hello');
681
- }
682
-
683
- }
684
-
685
- // if dbg is on we track the duration of the query
686
- if($this->dbg){
687
- $this->timer_stop();
688
- $this->keepQry('save');
689
- }
690
-
691
- if(!$resultSave){
692
- $wpdb->show_errors();
693
- return false;
694
- }else{
695
- if($update){
696
- if(isset($this->conditions[$this->getPk()])){
697
- $resultSave=$this->conditions[$this->getPk()];
698
- }else{
699
- if(isset($this->conditions[$this->getPk(1)])) $resultSave=$this->conditions[$this->getPk(1)];
700
- }
701
-
702
- }else{
703
- $resultSave=$wpdb->insert_id;
704
- }
705
- }
706
-
707
- $wpdb->flush();
708
-
709
- if(method_exists($this,$afterSave)){
710
- if(!$this->$afterSave($resultSave)){
711
- //$this->error(sprintf('Problem during validation "%2$s" in model : %1$s.', get_class($this), $afterSave));
712
- return false;
713
- }
714
- }
715
- return $resultSave;
716
- }
717
-
718
-
719
- function insertMany($values){
720
- $fields=array_keys($values[0]);
721
-
722
- $query='INSERT INTO `'.$this->getPrefix().$this->table_name.'` (`' . implode( '`,`', $fields ) . '`) VALUES ';
723
-
724
- $total=count($values);
725
- $i=1;
726
- foreach($values as &$vals){
727
- foreach($vals as &$v) $v=esc_sql($v);
728
- $query.= "('" . implode( "','", $vals )."')";
729
- if($i<$total) $query.=',';
730
- $i++;
731
- }
732
-
733
- $this->query($query.$myvalues);
734
-
735
- }
736
-
737
- /**
738
- * validate the fields type(defined in each model) in the save procedure
739
- * @return type
740
- */
741
- function validateFields(){
742
- $error=false;
743
- foreach($this->values as $key =>$val){
744
- if(isset($this->columns[$key]['req']) && !$val && !in_array( $this->columns[$key]['type'], array( 'boolean', 'integer' )) ){
745
- $this->error(sprintf(__('Field "%1$s" is required in table "%2$s".',WYSIJA), $key,$this->table_name),true);
746
- $error=true;
747
- }
748
- /* let's correct the type of the values based on the one defined in the model*/
749
- switch($this->columns[$key]['type']){
750
- case 'email':
751
- $userHelper = WYSIJA::get('user','helper');
752
- if(!$userHelper->validEmail($val)){
753
- $this->error(sprintf(__('Field "%1$s" needs to be a valid Email.',WYSIJA), $key),true);
754
- $error=true;
755
- }
756
- break;
757
- }
758
- }
759
-
760
- if($error) return false;
761
- return true;
762
- }
763
-
764
- /**
765
- * delete procedure
766
- * @global type $wpdb
767
- * @param type $conditions
768
- * @return type
769
- */
770
- function delete($conditions){
771
- $query='DELETE FROM `'.$this->getPrefix().$this->table_name.'`';
772
-
773
- if($this->setConditions($conditions)){
774
- $whereQuery=$this->makeWhere();
775
- if(!$whereQuery){
776
- $this->error('Cannot delete element without conditions in model : '.get_class($this));
777
- }
778
- }else{
779
- $this->error('Cannot delete element without conditions in model : '.get_class($this));
780
- return false;
781
- }
782
- $result=$this->beforeDelete($conditions);
783
- if($result) $result=$this->query($query.$whereQuery);
784
- else return false;
785
- $this->afterDelete();
786
-
787
- return true;
788
- }
789
-
790
- function exists($conditions){
791
-
792
- $query='SELECT '.$this->getPk().' FROM `'.$this->getSelectTableName().'`';
793
-
794
- $query.=$this->makeJoins();
795
- if($this->setConditions($conditions)){
796
- $whereQuery=$this->makeWhere();
797
- if(!$whereQuery){
798
- $this->error('Cannot test element without conditions in model : '.get_class($this));
799
- }
800
- }else{
801
- $this->error('Cannot test element without conditions in model : '.get_class($this));
802
- return false;
803
- }
804
- $res=$this->query('get_res',$query.$whereQuery, ARRAY_A);
805
- if($res) return $res;
806
- else return false;
807
- }
808
-
809
- function getPk($numb=0){
810
- $pk=$this->pk;
811
- if(is_array($pk)) $pk=$pk[$numb];
812
- return $pk;
813
- }
814
-
815
- /**
816
- * set the values after verifying them
817
- * @param type $values
818
- * @return type
819
- */
820
- function setValues($values){
821
- if($this->colCheck && !$this->checkAreColumns($values)) return false;
822
-
823
- $this->values=array();
824
- $this->values=$values;
825
- return true;
826
- }
827
-
828
- /**
829
- *
830
- * @param type $values
831
- * @return type
832
- */
833
- function setJoin($joins){
834
- $this->joins=$joins;
835
- return true;
836
- }
837
-
838
- /**
839
- * set the conditions after verifying them
840
- * @param type $conditions
841
- * @return type
842
- */
843
- function setConditions($conditions,$update=false){
844
- if($conditions && is_array($conditions)){
845
-
846
- $this->conditions=array();
847
- if($update){
848
- foreach($conditions as $key =>$cond){
849
- if($this->colCheck && !$this->checkAreColumns($conditions)) return false;
850
-
851
- if(is_array($cond)){
852
- $this->specialUpdate=true;
853
- $this->conditions=$conditions;
854
-
855
- return true;
856
- }else $this->conditions[$key]=$cond;
857
-
858
- }
859
- } else {
860
- foreach($conditions as $key => $cond) {
861
- if(!in_array($key, $this->comparisonKeys /*array('like','equal','notequal','greater','less','greater_eq','less_eq')*/)){
862
- if($this->colCheck && !$this->checkAreColumns($conditions)) return false;
863
- if(array_key_exists('equal', $this->conditions) === false) $this->conditions['equal'] = array();
864
- $this->conditions['equal'][$key] = $cond;
865
- }else{
866
- if($this->colCheck && !$this->checkAreColumns($cond)) return false;
867
- $this->conditions[$key]=$cond;
868
- }
869
-
870
- }
871
- }
872
-
873
- return true;
874
- }else return false;
875
- }
876
-
877
- /**
878
- * check that the columns corresponds to the columns in the model
879
- * @param type $arrayColumns
880
- * @return type
881
- */
882
- function checkAreColumns($columns){
883
- if($this->noCheck) return true;
884
- foreach($columns as $column => $values) {
885
- // skip when column is a comparison key
886
- if(in_array($column, $this->comparisonKeys)) continue;
887
-
888
- $columnName = $column;
889
- if(!isset($this->columns[$columnName])){
890
- $this->error(sprintf('Column %1$s does not exist in model : %2$s', $columnName, get_class($this)));
891
- return false;
892
- }
893
- }
894
- return true;
895
- }
896
-
897
- function timer_start() {
898
- $this->query_duration = 0;
899
- $this->time_start = microtime( true );
900
- return true;
901
- }
902
-
903
- function timer_stop() {
904
- $this->query_duration = ( microtime( true ) - $this->time_start );
905
- }
906
-
907
- function query($query,$arg2='',$arg3=ARRAY_A){
908
- global $wpdb;
909
- $this->sql_error = false;
910
- if(!$arg2) $query = str_replace(array('[wysija]','[wp]'),array($this->getPrefix(),$wpdb->prefix),$query);
911
- else $arg2 = str_replace(array('[wysija]','[wp]'),array($this->getPrefix(),$wpdb->prefix),$arg2);
912
-
913
- // if dbg is on we track the duration of the query
914
- if($this->dbg){
915
- $this->timer_start();
916
- }
917
-
918
- switch($query){
919
- case 'get_row':
920
- $result = $wpdb->get_row($arg2,$arg3);
921
- $this->logError();
922
- break;
923
- case 'get_res':
924
- $result = $wpdb->get_results($arg2,$arg3);
925
- //$this->escapeQuotesFromRes($results);
926
- $this->logError();
927
- break;
928
- default:
929
- $result = $wpdb->query($query);
930
- $this->logError();
931
-
932
- // get the last insert id if it's an insert query
933
- if(substr($query, 0, 6) == 'INSERT') $result = $wpdb->insert_id;
934
-
935
- }
936
- // if dbg is on we track the duration of the query
937
- if($this->dbg){
938
- $this->timer_stop();
939
- $this->keepQry('query');
940
- }
941
- return $result;
942
- }
943
-
944
- function logError(){
945
- if(defined('WYSIJA_DBG') && WYSIJA_DBG>1){
946
- global $wysija_queries_errors, $wpdb;
947
- if(!$wysija_queries_errors) $wysija_queries_errors = array();
948
-
949
- $this->sql_error = $wpdb->last_error;
950
-
951
- if( $this->sql_error &&
952
- ( empty( $this->last_error ) || $this->last_error != $this->sql_error )) {
953
- $this->last_error = $wysija_queries_errors[] = array('query' => $wpdb->last_query, 'error' => $this->sql_error);
954
- $this->sql_error = false;
955
- WYSIJA::log('queries_errors' , $this->sql_error , 'query_errors');
956
- }
957
-
958
- }
959
-
960
- }
961
-
962
- function keepQry($from = 'wpdb'){
963
- global $wpdb,$wysija_queries;
964
- $wysija_queries[$from][] = array('duration' => $this->query_duration , 'query' => $wpdb->last_query);
965
- }
966
-
967
- function getAffectedRows(){
968
- global $wpdb;
969
- return $wpdb->rows_affected;
970
- }
971
-
972
- function getErrorMsg(){
973
- global $wpdb;
974
- return $wpdb->show_errors();
975
- }
976
- /**
977
- * get the full prefix for the table
978
- * @global type $wpdb
979
- * @return type
980
- */
981
- function getPrefix(){
982
- if($this->tableWP) return $this->wpprefix.$this->table_prefix;
983
- else return $this->wpprefix.$this->table_prefix.'_';
984
- }
985
-
986
- /**
987
- * this function allows you to get the prefix from the main site on a multisite
988
- * @return type
989
- */
990
- function get_site_prefix($blog_id=1){
991
-
992
- switch_to_blog( $blog_id );
993
- global $wpdb;
994
- $main_site_prefix=$wpdb->prefix;
995
- restore_current_blog();
996
-
997
- if($this->tableWP) return $main_site_prefix.$this->table_prefix;
998
- else return $main_site_prefix.$this->table_prefix.'_';
999
- }
1000
-
1001
- /**
1002
- *
1003
- * @param type $field_name name of field which will become a key
1004
- * @param array $dataset list of records
1005
- * @param boolean $removing_field_name decide if we should remove field name from output dataset
1006
- * @param string $field_name_as_value a field in which we consider its value as value of $field_name
1007
- * @return array field based indexed dataset
1008
- */
1009
- protected function indexing_dataset_by_field($field_name, Array $dataset, $removing_field_name = false, $field_name_as_value = null){
1010
- if (empty($dataset))
1011
- return array();
1012
- $tmp = array();
1013
- foreach ($dataset as $record){
1014
- if (isset($record[$field_name]))
1015
- {
1016
- if (!empty($field_name_as_value)){
1017
- $tmp[$record[$field_name]] = isset($record[$field_name_as_value]) ? $record[$field_name_as_value] : null;
1018
- continue;
1019
- }
1020
- $tmp[$record[$field_name]] = $record;
1021
- if ($removing_field_name)
1022
- unset($tmp[$record[$field_name]][$field_name]);
1023
- }
1024
-
1025
- }
1026
- return $tmp;
1027
- }
1028
-
1029
- function beforeInsert(){
1030
- return true;
1031
- }
1032
-
1033
- function afterInsert($resultSaveID){
1034
- return true;
1035
- }
1036
- function beforeDelete($conditions){
1037
- return true;
1038
- }
1039
-
1040
- function afterDelete(){
1041
- return true;
1042
- }
1043
-
1044
- function beforeUpdate($id = null){
1045
- return true;
1046
- }
1047
-
1048
- function afterUpdate($resultSaveID){
1049
- return true;
1050
- }
1051
-
1052
  }
1
+ <?php
2
+ defined('WYSIJA') or die('Restricted access');
3
+ class WYSIJA_model extends WYSIJA_object{
4
+
5
+ var $table_prefix='wysija';
6
+ var $table_name='';
7
+ var $pk='';
8
+ var $values=array();
9
+ var $conditions=array();
10
+ var $orderby=array();
11
+ var $groupby=false;
12
+ var $noCheck =false;
13
+ var $replaceQRY=false;
14
+ var $limitON=false;
15
+ var $dbg=false;
16
+ var $colCheck=true;
17
+ var $getFormat=ARRAY_A;
18
+ var $getOne=false;
19
+ var $fieldValid=true;
20
+ var $specialUpdate=false;
21
+ var $escapeFields=array();
22
+ var $escapingOn=false;
23
+ var $tableWP=false;
24
+ var $columns=array();
25
+ var $joins=array();
26
+ var $ignore = false;
27
+ var $sql_error = false;
28
+ var $last_error = '';
29
+ var $comparisonKeys = array('equal', 'notequal', 'like', 'greater', 'less', 'greater_eq', 'less_eq', 'is');
30
+ var $time_start = 0;
31
+ var $query_duration = 0;
32
+
33
+ function __construct($extensions=''){
34
+ if(defined('WYSIJA_DBG') && WYSIJA_DBG>0) $this->dbg=true;
35
+ global $wpdb;
36
+ $this->wpdb = $wpdb;
37
+ $this->wpprefix=$this->wpdb->prefix;
38
+ if($extensions) $this->table_prefix=$extensions;
39
+ }
40
+ /**
41
+ * since we reuse the same objects accross the whole application
42
+ * once in a while for instance between a delete and a select we need to reset the objects to update the conditions
43
+ */
44
+ function reset(){
45
+ $this->values = array();
46
+ $this->conditions = array();
47
+ $this->orderby = array();
48
+ $this->groupby = false;
49
+ $this->getFormat = ARRAY_A;
50
+ $this->getOne = false;
51
+ $this->limitON = false;
52
+ $this->sql_error = false;
53
+ $this->last_error = '';
54
+ }
55
+
56
+ /**
57
+ *
58
+ * @param type $columnsOrPKval
59
+ * @param type $conditions
60
+ * @return type
61
+ */
62
+ function get($columnsOrPKval=false,$conditions=array()){
63
+ /*then columns becomes the pk value*/
64
+ if(!$conditions){
65
+ $conditions=array('equal'=>array($this->pk=>$columnsOrPKval));
66
+ $columnsOrPKval=false;
67
+ $this->noCheck=true;
68
+ }
69
+
70
+ /* if we pass just the id strong in the get conditions then it's the pk*/
71
+ if($conditions && !is_array($conditions)){
72
+ $conditions=array('equal'=>array($this->pk=>$conditions));
73
+ }
74
+ if($this->setConditions($conditions)){
75
+ if($this->getOne) $results=$this->getRows($columnsOrPKval,0,1);
76
+ else $results=$this->getRows($columnsOrPKval);
77
+ //$this->escapeQuotesFromRes($results);
78
+ if($this->getOne && count($results)==1){
79
+ switch($this->getFormat){
80
+ case ARRAY_A:
81
+ foreach($results as $res)return $res;
82
+ break;
83
+ case OBJECT:
84
+ foreach($results as $res)return $res;
85
+ break;
86
+ }
87
+ }
88
+ else return $results;
89
+ }
90
+
91
+ return false;
92
+ }
93
+
94
+ function getOne($columnsOrPKval=false,$conditions=array()){
95
+ $this->getOne=true;
96
+ $this->limitON=true;
97
+
98
+ return $this->get($columnsOrPKval,$conditions);
99
+ }
100
+
101
+ /**
102
+ * get a list of result based on a select query
103
+ * @param type $columns
104
+ * @param type $page
105
+ * @param type $limit
106
+ * @return type
107
+ */
108
+ function getRows($columns=false,$page=0,$limit=false){
109
+
110
+ /*set the columns*/
111
+ if($columns !== false){
112
+ if(is_array($columns)){
113
+
114
+ foreach($columns as $column){
115
+
116
+ if(!isset($this->columns[$column])){
117
+ $this->error(sprintf('Column does not exist.'));
118
+ return false;
119
+ }
120
+ }
121
+ $columns=implode(', ',$columns);
122
+ }else{
123
+ if(!isset($this->columns[$columns])){
124
+ $this->error(sprintf('Column does not exist.'));
125
+ return false;
126
+ }
127
+ }
128
+ }else{
129
+ $columns='*';
130
+
131
+ }
132
+
133
+
134
+ $query='SELECT '.$columns.' FROM `'.$this->getSelectTableName()."`";
135
+ $query.=$this->makeJoins();
136
+ $query.=$this->makeWhere();
137
+ $query.=$this->makeGroupBY();
138
+ $query.=$this->makeOrderBY();
139
+
140
+ if($this->limitON) $query.=$this->setLimit($page,$limit);
141
+ $results=$this->query('get_res',$query,$this->getFormat);
142
+
143
+ //$this->escapeQuotesFromRes($results);
144
+
145
+ return $results;
146
+ }
147
+
148
+ function escapeQuotesFromRes(&$results){
149
+ if(!$this->escapingOn) return false;
150
+ foreach($results as $k =>$r){
151
+
152
+ if(in_array($this->getFormat,array(ARRAY_A,ARRAY_N))){
153
+ foreach($r as $k1 =>$v1){
154
+ if(in_array($k1,$this->escapeFields)){
155
+ $results[$k][$k1]= stripslashes($v1);
156
+ }
157
+ }
158
+ }
159
+ }
160
+ }
161
+
162
+ function setLimit($page=0,$limit=false){
163
+ /*set the limit of the selection*/
164
+
165
+ if(!$this->getOne){
166
+ if($page==0){
167
+ if(isset($_REQUEST['pagi'])){
168
+ $page=(int)$_REQUEST['pagi'];
169
+ if($page!=0) $page=$page-1;
170
+ }
171
+
172
+ }else $page=$page-1;
173
+ }
174
+
175
+ if(!$limit){
176
+ if(isset($this->limit_pp)) $limit=$this->limit_pp;
177
+ else{
178
+ $config=WYSIJA::get('config','model');
179
+ $limit=$config->getValue('limit_listing');
180
+ }
181
+ }
182
+
183
+ $this->limit=(int)$limit;
184
+ $this->page=$page;
185
+ $this->limit_start=(int)($this->page*$this->limit);
186
+ $this->limit_end=(int)($this->limit_start+$this->limit);
187
+
188
+ return " LIMIT $this->limit_start , $this->limit";
189
+ }
190
+
191
+ /**
192
+ * DEPRECATED
193
+ * to have a custom query through the model and get the result immediately
194
+ * @param type $query
195
+ * @return type
196
+ */
197
+ function getResults($query,$type=ARRAY_A){
198
+ return $this->query('get_res',$query, $type);
199
+ }
200
+
201
+ /**
202
+ * to have a custom query through the model and get the result immediately
203
+ * @param type $query
204
+ * @return type
205
+ */
206
+ public function get_results($query,$type=ARRAY_A){
207
+ return $this->getResults($query,$type);
208
+ }
209
+
210
+
211
+ function getSelectTableName(){
212
+ if($this->joins && isset($this->joins['tablestart'])){
213
+ if(isset($this->joins['prefstart'])) return $this->wpdb->prefix.$this->joins['prefstart'].'_'.$this->joins['tablestart'];
214
+ else return $this->getPrefix().$this->joins['tablestart'];
215
+ }else return $this->getPrefix().$this->table_name;
216
+ }
217
+
218
+ /**
219
+ * simple SQL count
220
+ * @return type
221
+ */
222
+ function count($query=false,$keygetcount=false){
223
+ if(!$query){
224
+ $groupBy=$this->makeGroupBY();
225
+ $columnMore='';
226
+ if($groupBy) $columnMore=','.$this->groupby;
227
+ $query='SELECT COUNT('.$this->getPk().') as count '.$columnMore.' FROM `'.$this->getSelectTableName().'`';
228
+ $query.=$this->makeJoins();
229
+
230
+ $query.=$this->makeWhere();
231
+ $query.=$groupBy;
232
+ }
233
+
234
+
235
+ // if dbg is on we track the duration of the query
236
+ if($this->dbg){
237
+ $this->timer_start();
238
+ }
239
+ $results=$this->query('get_res',$query,$this->getFormat);
240
+
241
+ // if dbg is on we track the duration of the query
242
+ if($this->dbg){
243
+ $this->timer_stop();
244
+ $this->keepQry('count');
245
+ }
246
+
247
+ if(!$results || count($results)>1) return $results;
248
+ else {
249
+ if($keygetcount) return $results[0][$keygetcount];
250
+ else{
251
+ foreach($results[0] as $key => $count) return $count;
252
+ }
253
+ }
254
+
255
+
256
+ return $results;
257
+ }
258
+
259
+ /**
260
+ * make the SQL WHERE condition string
261
+ * @return string
262
+ */
263
+ function makeWhere(){
264
+ $query='';
265
+ if($this->conditions){
266
+ /*set the WHERE clause*/
267
+ $conditions=array();
268
+ foreach($this->conditions as $type=>$values){
269
+ if(!in_array($type, $this->comparisonKeys)){
270
+ $conditionsss=$this->conditions;
271
+ $this->conditions=array();
272
+ $this->conditions['equal']=$conditionsss;
273
+
274
+ break;
275
+ }
276
+ }
277
+ foreach($this->conditions as $type=>$values){
278
+ if($type=='like' && count($values)>1){
279
+ if(is_array($values)){
280
+ $total=count($values);
281
+ $i=1;
282
+ $likeCond='';
283
+ foreach($values as $qfield => $qval){
284
+ $qval = html_entity_decode($qval, ENT_QUOTES);
285
+ $likeCond.=$qfield." LIKE '%".esc_sql(addcslashes($qval, '%_' ))."%'";
286
+ if($i<$total){
287
+ $likeCond.=' OR ';
288
+ }
289
+ $i++;
290
+ }
291
+ $conditions[]='('.$likeCond.')';
292
+ }
293
+ continue;
294
+ }
295
+
296
+ foreach($values as $condK => $condVal){
297
+
298
+ //secure from injections
299
+ $this->_secureFieldVal($condK, $condVal);
300
+
301
+ switch($type){
302
+ case 'equal':
303
+ if(is_array($condVal)){
304
+ $conditions[]=$condK.' IN ("'.implode('","', $condVal).'")';
305
+ }else{
306
+ if(is_null($condVal)) {
307
+ $conditions[] = $condK.' IS NULL';
308
+ } else {
309
+ if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
310
+ $conditions[] = $condK.'='.$condVal;
311
+ }
312
+ }
313
+ break;
314
+ case 'notequal':
315
+ if(is_array($condVal)){
316
+ $conditions[]=$condK.' NOT IN ("'.implode('","', $condVal).'")';
317
+ }else{
318
+ //this means that if I delete something with a list of ids and the array happens to be empty array of ids it will just delete everything by
319
+ if(is_null($condVal)) {
320
+ $conditions[] = $condK.' IS NOT NULL';
321
+ } else {
322
+ if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
323
+ $conditions[] = $condK.' != '.$condVal;
324
+ }
325
+ }
326
+ break;
327
+ case 'like':
328
+ $conditions[]=$condK." LIKE '%".esc_sql(addcslashes($condVal, '%_' ))."%'";
329
+ break;
330
+ case 'greater':
331
+ if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
332
+ $conditions[]=$condK.' > '.$condVal;
333
+ break;
334
+ case 'less':
335
+ if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
336
+ $conditions[]=$condK.' < '.$condVal;
337
+ break;
338
+ case 'greater_eq':
339
+ if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
340
+ $conditions[]=$condK.' >= '.$condVal;
341
+ break;
342
+ case 'less_eq':
343
+ if(is_numeric($condVal) === false) $condVal = '"'.$condVal.'"';
344
+ $conditions[]=$condK.' <= '.$condVal;
345
+ break;
346
+ case 'is':
347
+
348
+ $conditions[]=$condK.' '.$condVal;
349
+ break;
350
+ }
351
+ }
352
+
353
+ }
354
+
355
+ $query.=' WHERE '.implode(' AND ',$conditions);
356
+ }
357
+
358
+ return $query;
359
+ }
360
+
361
+ /**
362
+ * make the SQL ORDER BY condition string
363
+ * @return string
364
+ */
365
+ function makeOrderBY(){
366
+ $query=' ORDER BY ';
367
+ if($this->orderby){
368
+ /*set the ORDER BY clause*/
369
+ $query.=$this->orderby.' '.$this->orderbyt;
370
+ }else{
371
+ /*by default we order by pk desc*/
372
+ if(is_array($this->pk)) return '';
373
+ $query.=$this->pk.' DESC';
374
+ }
375
+ return $query;
376
+ }
377
+
378
+
379
+ function makeJoins(){
380
+
381
+ if($this->joins){
382
+ $join=' as A';
383
+ $arrayLetters=array('B','C','D','E');
384
+ foreach($this->joins['tablejoins'] as $table => $fk){
385
+ $letter=array_shift($arrayLetters);
386
+ $join.=' JOIN `'.$this->getPrefix().$table.'` AS '.$letter." on $letter.$fk=A.".$this->joins['keystart'].' ';
387
+ }
388
+ /*set the ORDER BY clause*/
389
+ return $join;
390
+ }else return '';
391
+
392
+ }
393
+ /**
394
+ * make the SQL ORDER BY condition string
395
+ * @return string
396
+ */
397
+ function makeGroupBY(){
398
+
399
+ if($this->groupby){
400
+ /*set the ORDER BY clause*/
401
+ return ' GROUP BY '.$this->groupby;
402
+ }else return '';
403
+
404
+ }
405
+ function groupBy($name){
406
+
407
+ if (!is_string($name) OR preg_match('|[^a-z0-9#_.-]|i',$name) !== 0 ){
408
+ $this->groupby=false;
409
+ }else $this->groupby=$name;
410
+ }
411
+ function orderBy($name,$type = 'ASC'){
412
+
413
+ if(is_array($name) and count($name) > 0) {
414
+ // set order by to empty string
415
+ $this->orderby = '';
416
+ $this->ordert = '';
417
+
418
+ // count number of arguments
419
+ $count = count($name);
420
+
421
+ // build order by query
422
+ for($i = 0; $i < $count; $i++) {
423
+
424
+ $value = current($name);
425
+
426
+ //security escaping
427
+ if(!is_string(key($name)) OR preg_match('|[^a-z0-9#_.-]|i',key($name)) !== 0 ){
428
+ $orderByCol="";
429
+ }else $orderByCol=key($name);
430
+ //security escaping
431
+ if(!is_string($value) OR preg_match('|[^a-z0-9#_.-]|i',$value) !== 0 ){
432
+ $orderByVal="";
433
+ }else $orderByVal=$value;
434
+
435
+ if($i === ($count - 1)) {
436
+ $this->orderby .= $orderByCol;
437
+ $this->ordert = $orderByVal;
438
+ } else {
439
+ $this->orderby .=$orderByCol.' '.$orderByVal;
440
+ $this->orderby .= ', ';
441
+ next($name);
442
+ }
443
+ }
444
+ } else if(!is_string($name) OR preg_match('|[^a-z0-9#_.-]|i',$name) !== 0 ){
445
+ $this->orderby="";
446
+ }else {
447
+ $this->orderby=$name;
448
+ }
449
+
450
+ if(!in_array($type,array('DESC','ASC'))) $type = 'DESC';
451
+ $this->orderbyt=$type;
452
+ }
453
+
454
+
455
+
456
+ /**
457
+ * prepare for an insert procedure
458
+ * @param type $values
459
+ */
460
+ function insert($values,$ignore=false){
461
+ if($ignore)$this->ignore=true;
462
+ if($this->setValues($values)){
463
+ return $this->save();
464
+ }else{
465
+ $this->error(sprintf('missing values in model insert : %1$s.', get_class($this)));
466
+ }
467
+ }
468
+
469
+
470
+ function replace($values=array()){
471
+ $this->replaceQRY=true;
472
+ $this->insert($values);
473
+ $this->replaceQRY=false;
474
+ }
475
+
476
+ /**
477
+ * prepare for an update procedure
478
+ * @param type $values
479
+ * @param type $conditions
480
+ */
481
+ function update($values=array(),$conditions=array()){
482
+
483
+ if($this->setValues($values)){
484
+ /*if no condition is set then we set it mannualy based on the primary key*/
485
+ if(!$conditions){
486
+ if(!$this->conditions){
487
+ if(isset($values[$this->pk]) && $values[$this->pk]){
488
+
489
+ $this->setConditions(array($this->pk => $values[$this->pk]), true);
490
+
491
+ unset($values[$this->pk]);
492
+
493
+ return $this->save(true);
494
+
495
+ }else{
496
+ $this->error(sprintf('missing pk value in model update : %1$s.', get_class($this)));
497
+ }
498
+ }
499
+
500
+ }else{
501
+ if($this->setConditions($conditions,true)){
502
+ return $this->save(true);
503
+ }else{
504
+ $this->error(sprintf('missing conditions in model update : %1$s.', get_class($this)));
505
+ }
506
+ }
507
+
508
+ }else{
509
+ $this->error(sprintf('missing values in model update : %1$s.', get_class($this)));
510
+ }
511
+ }
512
+
513
+ /**
514
+ * UPDATE with a special where condition
515
+ * @param type $table
516
+ * @param type $data
517
+ * @param type $where
518
+ * @param type $format
519
+ * @param type $where_format
520
+ * @return type
521
+ */
522
+ function specialUpdate( $table, $data, $where, $format = null, $where_format = null ) {
523
+ if ( ! is_array( $data ) || ! is_array( $where ) )
524
+ return false;
525
+
526
+ $formats = $format = (array) $format;
527
+ $bits = $wheres = array();
528
+
529
+ $i=0;
530
+ foreach ( $data as $field => $val) {
531
+ $this->_secureFieldVal($field,$val);
532
+
533
+ switch($format[$i]){
534
+ case "%d":
535
+ $bits[] = "`$field` = ".(int)$val;
536
+ break;
537
+ case '[increment]':
538
+ $bits[] = "`$field` = ".$field.'+1';
539
+ break;
540
+ case '[decrement]':
541
+ $bits[] = "`$field` = ".$field.'-1';
542
+ break;
543
+ default :
544
+ $bits[] = "`$field` = '".$val."'";
545
+ }
546
+ $i++;
547
+ }
548
+
549
+ $sql = "UPDATE `$table` SET " . implode( ', ', $bits ) . ' ' . $this->makeWhere();
550
+ return $this->query( $sql );
551
+ }
552
+
553
+
554
+ function _secureFieldVal( &$field, &$mixed ) {
555
+ if ( ! is_string( $field ) || preg_match( '|[^a-z0-9#_.-]|i', $field ) !== 0 ) {
556
+ die('field "'.$field .'" not secured');
557
+ }
558
+ if ( is_string( $mixed ) || is_numeric( $mixed ) || is_bool( $mixed ) ) {
559
+ $mixed = esc_sql( $mixed );
560
+ } else {
561
+ if(!empty($mixed) && is_array($mixed)){
562
+ foreach ( $mixed as $key => &$value ) {
563
+ $this->_secureFieldVal( $field, $value );
564
+ }
565
+ }
566
+ }
567
+ }
568
+ /**
569
+ * save information as an update or an insert
570
+ * @param type $update
571
+ * @return type
572
+ */
573
+ function save($update=false){
574
+
575
+ if($update)$updateStr='Update';
576
+ else $updateStr='Insert';
577
+ $beforeSave='before'.$updateStr;
578
+ $afterSave='after'.$updateStr;
579
+
580
+
581
+
582
+ if(!$update && isset($this->columns['created_at']))$this->values['created_at']=time();
583
+ foreach($this->columns as $key => $params){
584
+ /*check for auto columns */
585
+ if((isset($params['autoup']) && $update) || (!$update && $key!='sent_at')){
586
+ if(isset($params['type']) && !isset($this->values[$key])){
587
+ switch($params['type']){
588
+ case 'date':
589
+ $this->values[$key]=time();
590
+ break;
591
+ case 'ip':
592
+ $userHelper=WYSIJA::get("user","helper");
593
+ /*record the ip and save the user*/
594
+ $this->values[$key]=$userHelper->getIP();
595
+ break;
596
+ case 'referer':
597
+ /*record the ip and save the user*/
598
+ $this->values[$key]=$_SERVER['HTTP_REFERER'];
599
+ break;
600
+ }
601
+ }
602
+
603
+ }
604
+ }
605
+
606
+ if(method_exists($this,$beforeSave)){
607
+ if(!$this->$beforeSave()){
608
+ //$this->error(sprintf('Problem during validation "%2$s" in model : %1$s.', get_class($this), $beforeSave));
609
+ return false;
610
+ }
611
+ }
612
+
613
+ /*prepare a format list for the update and insert function*/
614
+ $fieldsFormats=array();
615
+ if(!is_array($this->pk) && isset($this->values[$this->pk])) unset($this->values[$this->pk]);
616
+ foreach($this->values as $key =>$val){
617
+ if(!isset($this->columns[$key]['html'])) $this->values[$key]=strip_tags($val);
618
+ /* let's correct the type of the values based on the one defined in the model*/
619
+ if(in_array($val, array('[increment]','[decrement]'))){
620
+ $fieldsFormats[]=$val;
621
+ $this->specialUpdate=true;
622
+ }else{
623
+ //dbg($this->values);
624
+ if(!isset($this->columns[$key]['type'])){
625
+ $this->columns[$key]['type']='default';
626
+ }
627
+ switch($this->columns[$key]['type']){
628
+ case 'integer':
629
+ case 'boolean':
630
+ $fieldsFormats[]="%d";
631
+ break;
632
+ default:
633
+ $fieldsFormats[]="%s";
634
+
635
+ }
636
+ }
637
+
638
+ }
639
+
640
+ if($this->fieldValid && !$this->validateFields()) {
641
+ $this->error(__('Error Validating the fields',WYSIJA),true);
642
+ $this->stay=true;
643
+ return false;
644
+ }
645
+
646
+ // if dbg is on we track the duration of the query
647
+ if($this->dbg){
648
+ $this->timer_start();
649
+ }
650
+
651
+ if($update){
652
+
653
+ if( $this->specialUpdate || isset($this->conditions['equal']) || isset($this->conditions['notequal']) || isset($this->conditions['like'])){
654
+
655
+ $resultSave=$this->specialUpdate($this->getPrefix().$this->table_name,$this->values,$this->conditions,$fieldsFormats);
656
+ $this->logError();
657
+ }else{
658
+
659
+ $this->wpdb->update($this->getPrefix().$this->table_name,$this->values,$this->conditions,$fieldsFormats);
660
+ $this->logError();
661
+ $resultSave=$this->wpdb->result;
662
+ }
663
+
664
+ }else{
665
+ if($this->replaceQRY){
666
+ $resultSave=$this->wpdb->replace($this->getPrefix().$this->table_name,$this->values,$fieldsFormats);
667
+ $this->logError();
668
+ }else{
669
+
670
+ if($this->ignore) $resultSave=$this->wpdb->insert($this->getPrefix().$this->table_name,$this->values,$fieldsFormats);
671
+ else $resultSave=$this->wpdb->insert($this->getPrefix().$this->table_name,$this->values,$fieldsFormats);
672
+
673
+ $this->logError();
674
+ //dbg('hello');
675
+ }
676
+
677
+ }
678
+
679
+ // if dbg is on we track the duration of the query
680
+ if($this->dbg){
681
+ $this->timer_stop();
682
+ $this->keepQry('save');
683
+ }
684
+
685
+ if(!$resultSave){
686
+ $this->wpdb->show_errors();
687
+ return false;
688
+ }else{
689
+ if($update){
690
+ if(isset($this->conditions[$this->getPk()])){
691
+ $resultSave=$this->conditions[$this->getPk()];
692
+ }else{
693
+ if(isset($this->conditions[$this->getPk(1)])) $resultSave=$this->conditions[$this->getPk(1)];
694
+ }
695
+
696
+ }else{
697
+ $resultSave=$this->wpdb->insert_id;
698
+ }
699
+ }
700
+
701
+ $this->wpdb->flush();
702
+
703
+ if(method_exists($this,$afterSave)){
704
+ if(!$this->$afterSave($resultSave)){
705
+ //$this->error(sprintf('Problem during validation "%2$s" in model : %1$s.', get_class($this), $afterSave));
706
+ return false;
707
+ }
708
+ }
709
+ return $resultSave;
710
+ }
711
+
712
+
713
+ function insertMany($values){
714
+ $fields=array_keys($values[0]);
715
+
716
+ $query='INSERT INTO `'.$this->getPrefix().$this->table_name.'` (`' . implode( '`,`', $fields ) . '`) VALUES ';
717
+
718
+ $total=count($values);
719
+ $i=1;
720
+ foreach($values as &$vals){
721
+ foreach($vals as &$v) $v=esc_sql($v);
722
+ $query.= "('" . implode( "','", $vals )."')";
723
+ if($i<$total) $query.=',';
724
+ $i++;
725
+ }
726
+
727
+ $this->query($query.$myvalues);
728
+
729
+ }
730
+
731
+ /**
732
+ * validate the fields type(defined in each model) in the save procedure
733
+ * @return type
734
+ */
735
+ function validateFields(){
736
+ $error=false;
737
+ foreach($this->values as $key =>$val){
738
+ if(isset($this->columns[$key]['req']) && !$val && !in_array( $this->columns[$key]['type'], array( 'boolean', 'integer' )) ){
739
+ $this->error(sprintf(__('Field "%1$s" is required in table "%2$s".',WYSIJA), $key,$this->table_name),true);
740
+ $error=true;
741
+ }
742
+ /* let's correct the type of the values based on the one defined in the model*/
743
+ switch($this->columns[$key]['type']){
744
+ case 'email':
745
+ $userHelper = WYSIJA::get('user','helper');
746
+ if(!$userHelper->validEmail($val)){
747
+ $this->error(sprintf(__('Field "%1$s" needs to be a valid Email.',WYSIJA), $key),true);
748
+ $error=true;
749
+ }
750
+ break;
751
+ }
752
+ }
753
+
754
+ if($error) return false;
755
+ return true;
756
+ }
757
+
758
+ /**
759
+ * delete procedure
760
+ * @param type $conditions
761
+ * @return type
762
+ */
763
+ function delete($conditions){
764
+ $query='DELETE FROM `'.$this->getPrefix().$this->table_name.'`';
765
+
766
+ if($this->setConditions($conditions)){
767
+ $whereQuery=$this->makeWhere();
768
+ if(!$whereQuery){
769
+ $this->error('Cannot delete element without conditions in model : '.get_class($this));
770
+ }
771
+ }else{
772
+ $this->error('Cannot delete element without conditions in model : '.get_class($this));
773
+ return false;
774
+ }
775
+ $result=$this->beforeDelete($conditions);
776
+ if($result) $result=$this->query($query.$whereQuery);
777
+ else return false;
778
+ $this->afterDelete();
779
+
780
+ return true;
781
+ }
782
+
783
+ function exists($conditions){
784
+
785
+ $query='SELECT '.$this->getPk().' FROM `'.$this->getSelectTableName().'`';
786
+
787
+ $query.=$this->makeJoins();
788
+ if($this->setConditions($conditions)){
789
+ $whereQuery=$this->makeWhere();
790
+ if(!$whereQuery){
791
+ $this->error('Cannot test element without conditions in model : '.get_class($this));
792
+ }
793
+ }else{
794
+ $this->error('Cannot test element without conditions in model : '.get_class($this));
795
+ return false;
796
+ }
797
+ $res=$this->query('get_res',$query.$whereQuery, ARRAY_A);
798
+ if($res) return $res;
799
+ else return false;
800
+ }
801
+
802
+ function getPk($numb=0){
803
+ $pk=$this->pk;
804
+ if(is_array($pk)) $pk=$pk[$numb];
805
+ return $pk;
806
+ }
807
+
808
+ /**
809
+ * set the values after verifying them
810
+ * @param type $values
811
+ * @return type
812
+ */
813
+ function setValues($values){
814
+ if($this->colCheck && !$this->checkAreColumns($values)) return false;
815
+
816
+ $this->values=array();
817
+ $this->values=$values;
818
+ return true;
819
+ }
820
+
821
+ /**
822
+ *
823
+ * @param type $values
824
+ * @return type
825
+ */
826
+ function setJoin($joins){
827
+ $this->joins=$joins;
828
+ return true;
829
+ }
830
+
831
+ /**
832
+ * set the conditions after verifying them
833
+ * @param type $conditions
834
+ * @return type
835
+ */
836
+ function setConditions($conditions,$update=false){
837
+ if($conditions && is_array($conditions)){
838
+
839
+ $this->conditions=array();
840
+ if($update){
841
+ foreach($conditions as $key =>$cond){
842
+ if($this->colCheck && !$this->checkAreColumns($conditions)) return false;
843
+
844
+ if(is_array($cond)){
845
+ $this->specialUpdate=true;
846
+ $this->conditions=$conditions;
847
+
848
+ return true;
849
+ }else $this->conditions[$key]=$cond;
850
+
851
+ }
852
+ } else {
853
+ foreach($conditions as $key => $cond) {
854
+ if(!in_array($key, $this->comparisonKeys /*array('like','equal','notequal','greater','less','greater_eq','less_eq')*/)){
855
+ if($this->colCheck && !$this->checkAreColumns($conditions)) return false;
856
+ if(array_key_exists('equal', $this->conditions) === false) $this->conditions['equal'] = array();
857
+ $this->conditions['equal'][$key] = $cond;
858
+ }else{
859
+ if($this->colCheck && !$this->checkAreColumns($cond)) return false;
860
+ $this->conditions[$key]=$cond;
861
+ }
862
+
863
+ }
864
+ }
865
+
866
+ return true;
867
+ }else return false;
868
+ }
869
+
870
+ /**
871
+ * check that the columns corresponds to the columns in the model
872
+ * @param type $arrayColumns
873
+ * @return type
874
+ */
875
+ function checkAreColumns($columns){
876
+ if($this->noCheck) return true;
877
+ foreach($columns as $column => $values) {
878
+ // skip when column is a comparison key
879
+ if(in_array($column, $this->comparisonKeys)) continue;
880
+
881
+ $columnName = $column;
882
+ if(!isset($this->columns[$columnName])){
883
+ $this->error(sprintf('Column %1$s does not exist in model : %2$s', $columnName, get_class($this)));
884
+ return false;
885
+ }
886
+ }
887
+ return true;
888
+ }
889
+
890
+ function timer_start() {
891
+ $this->query_duration = 0;
892
+ $this->time_start = microtime( true );
893
+ return true;
894
+ }
895
+
896
+ function timer_stop() {
897
+ $this->query_duration = ( microtime( true ) - $this->time_start );
898
+ }
899
+
900
+ function query($query,$arg2='',$arg3=ARRAY_A){
901
+ $this->sql_error = false;
902
+ if(!$arg2) $query = str_replace(array('[wysija]','[wp]'),array($this->getPrefix(),$this->wpdb->prefix),$query);
903
+ else $arg2 = str_replace(array('[wysija]','[wp]'),array($this->getPrefix(),$this->wpdb->prefix),$arg2);
904
+
905
+ // if dbg is on we track the duration of the query
906
+ if($this->dbg){
907
+ $this->timer_start();
908
+ }
909
+
910
+ switch($query){
911
+ case 'get_row':
912
+ $result = $this->wpdb->get_row($arg2,$arg3);
913
+ $this->logError();
914
+ break;
915
+ case 'get_res':
916
+ $result = $this->wpdb->get_results($arg2,$arg3);
917
+ //$this->escapeQuotesFromRes($results);
918
+ $this->logError();
919
+ break;
920
+ default:
921
+ $result = $this->wpdb->query($query);
922
+ $this->logError();
923
+
924
+ // get the last insert id if it's an insert query
925
+ if(substr($query, 0, 6) == 'INSERT') $result = $this->wpdb->insert_id;
926
+
927
+ }
928
+ // if dbg is on we track the duration of the query
929
+ if($this->dbg){
930
+ $this->timer_stop();
931
+ $this->keepQry('query');
932
+ }
933
+ return $result;
934
+ }
935
+
936
+ function logError(){
937
+ if(defined('WYSIJA_DBG') && WYSIJA_DBG>1){
938
+ global $wysija_queries_errors;
939
+ if(!$wysija_queries_errors) $wysija_queries_errors = array();
940
+
941
+ $this->sql_error = $this->wpdb->last_error;
942
+
943
+ if( $this->sql_error &&
944
+ ( empty( $this->last_error ) || $this->last_error != $this->sql_error )) {
945
+ $this->last_error = $wysija_queries_errors[] = array('query' => $this->wpdb->last_query, 'error' => $this->sql_error);
946
+ $this->sql_error = false;
947
+ WYSIJA::log('queries_errors' , $this->sql_error , 'query_errors');
948
+ }
949
+
950
+ }
951
+
952
+ }
953
+
954
+ function keepQry($from = 'wpdb'){
955
+ global $wysija_queries;
956
+ $wysija_queries[$from][] = array('duration' => $this->query_duration , 'query' => $this->wpdb->last_query);
957
+ }
958
+
959
+ function getAffectedRows(){
960
+ return $this->wpdb->rows_affected;
961
+ }
962
+
963
+ function getErrorMsg(){
964
+ return $this->wpdb->show_errors();
965
+ }
966
+ /**
967
+ * get the full prefix for the table
968
+ * @return type
969
+ */
970
+ function getPrefix(){
971
+ if($this->tableWP) return $this->wpdb->prefix.$this->table_prefix;
972
+ else return $this->wpdb->prefix.$this->table_prefix.'_';
973
+ }
974
+
975
+ /**
976
+ * this function allows you to get the prefix from the main site on a multisite
977
+ * @return type
978
+ */
979
+ function get_site_prefix($blog_id=1){
980
+
981
+ switch_to_blog( $blog_id );
982
+ $main_site_prefix=$this->wpdb->prefix;
983
+ restore_current_blog();
984
+
985
+ if($this->tableWP) return $main_site_prefix.$this->table_prefix;
986
+ else return $main_site_prefix.$this->table_prefix.'_';
987
+ }
988
+
989
+ /**
990
+ *
991
+ * @param type $field_name name of field which will become a key
992
+ * @param array $dataset list of records
993
+ * @param boolean $removing_field_name decide if we should remove field name from output dataset
994
+ * @param string $field_name_as_value a field in which we consider its value as value of $field_name
995
+ * @return array field based indexed dataset
996
+ */
997
+ protected function indexing_dataset_by_field($field_name, Array $dataset, $removing_field_name = false, $field_name_as_value = null){
998
+ if (empty($dataset))
999
+ return array();
1000
+ $tmp = array();
1001
+ foreach ($dataset as $record){
1002
+ if (isset($record[$field_name]))
1003
+ {
1004
+ if (!empty($field_name_as_value)){
1005
+ $tmp[$record[$field_name]] = isset($record[$field_name_as_value]) ? $record[$field_name_as_value] : null;
1006
+ continue;
1007
+ }
1008
+ $tmp[$record[$field_name]] = $record;
1009
+ if ($removing_field_name)
1010
+ unset($tmp[$record[$field_name]][$field_name]);
1011
+ }
1012
+
1013
+ }
1014
+ return $tmp;
1015
+ }
1016
+
1017
+ function beforeInsert(){
1018
+ return true;
1019
+ }
1020
+
1021
+ function afterInsert($resultSaveID){
1022
+ return true;
1023
+ }
1024
+ function beforeDelete($conditions){
1025
+ return true;
1026
+ }
1027
+
1028
+ function afterDelete(){
1029
+ return true;
1030
+ }
1031
+
1032
+ function beforeUpdate($id = null){
1033
+ return true;
1034
+ }
1035
+
1036
+ function afterUpdate($resultSaveID){
1037
+ return true;
1038
+ }
1039
+
 
 
 
 
 
 
 
 
 
 
 
 
1040
  }
helpers/articles.php CHANGED
@@ -301,7 +301,7 @@ class WYSIJA_help_articles extends WYSIJA_object {
301
  $post_thumbnail = get_post_thumbnail_id($post['ID']);
302
 
303
  // get attachment data (src, width, height)
304
- $image_info = wp_get_attachment_image_src($post_thumbnail, 'single-post-thumbnail');
305
 
306
  // get alt text
307
  $altText = trim(strip_tags(get_post_meta($post_thumbnail, '_wp_attachment_image_alt', true)));
301
  $post_thumbnail = get_post_thumbnail_id($post['ID']);
302
 
303
  // get attachment data (src, width, height)
304
+ $image_info = wp_get_attachment_image_src($post_thumbnail, 'wysija-newsletters-max');
305
 
306
  // get alt text
307
  $altText = trim(strip_tags(get_post_meta($post_thumbnail, '_wp_attachment_image_alt', true)));
helpers/bounce.php CHANGED
@@ -240,11 +240,11 @@ class WYSIJA_help_bounce extends WYSIJA_help {
240
  if (preg_match($this->detectEmail, $this->_message->header->sender_email, $results)) {
241
  $this->_message->header->sender_email = $results[0];
242
  }
243
- $this->_message->header->sender_name = strip_tags(@$this->_message->headerinfo['from']);
244
  $this->_message->header->reply_to_email = $this->_message->header->sender_email;
245
- $this->_message->header->reply_to_name = $this->_message->header->sender_name;
246
  $this->_message->header->from_email = $this->_message->header->sender_email;
247
- $this->_message->header->from_name = $this->_message->header->sender_name;
248
 
249
  return true;
250
  }
240
  if (preg_match($this->detectEmail, $this->_message->header->sender_email, $results)) {
241
  $this->_message->header->sender_email = $results[0];
242
  }
243
+ $this->_message->header->sender_name = (isset($this->_message->headerinfo['from'])) ? strip_tags(@$this->_message->headerinfo['from']) : '';
244
  $this->_message->header->reply_to_email = $this->_message->header->sender_email;
245
+ $this->_message->header->reply_to_name = (property_exists($this->_message->header, 'sender_name')) ? $this->_message->header->sender_name : '';
246
  $this->_message->header->from_email = $this->_message->header->sender_email;
247
+ $this->_message->header->from_name = $this->_message->header->reply_to_name;
248
 
249
  return true;
250
  }
inc/phpmailer/class.sendgrid.php CHANGED
@@ -21,7 +21,7 @@ class acymailingSendgrid {
21
  * First, we do the test if we have enough credit to send emails.
22
  */
23
  function sendMail(& $object) {
24
- $url = 'http://sendgrid.com/';
25
 
26
  $to = array_merge(array($object->to[0][0]), $object->cc, $object->bcc);
27
  /*foreach($to as $oneRecipient){
@@ -64,7 +64,7 @@ class acymailingSendgrid {
64
 
65
 
66
  $params['headers']=json_encode($header);
67
- $request = $url.'api/mail.send.json';
68
 
69
  // Generate curl request
70
  $session = curl_init($request);
21
  * First, we do the test if we have enough credit to send emails.
22
  */
23
  function sendMail(& $object) {
24
+ $url = 'https://api.sendgrid.com';
25
 
26
  $to = array_merge(array($object->to[0][0]), $object->cc, $object->bcc);
27
  /*foreach($to as $oneRecipient){
64
 
65
 
66
  $params['headers']=json_encode($header);
67
+ $request = $url.'/api/mail.send.json';
68
 
69
  // Generate curl request
70
  $session = curl_init($request);
inc/phpmailer/class.smtp.php CHANGED
@@ -1087,6 +1087,8 @@ class acymailingSMTP
1087
  function StartTLS() {
1088
  $this->error = null; # to avoid confusion
1089
 
 
 
1090
  if(!$this->connected()) {
1091
  $this->error = array("error" => "Called StartTLS() without being connected");
1092
  return false;
1087
  function StartTLS() {
1088
  $this->error = null; # to avoid confusion
1089
 
1090
+ stream_context_set_option($this->smtp_conn, "ssl", "verify_peer", false);
1091
+
1092
  if(!$this->connected()) {
1093
  $this->error = array("error" => "Called StartTLS() without being connected");
1094
  return false;
index.php CHANGED
@@ -3,7 +3,7 @@
3
  Plugin Name: MailPoet Newsletters
4
  Plugin URI: http://www.mailpoet.com/
5
  Description: Create and send newsletters or automated emails. Capture subscribers with a widget. Import and manage your lists. MailPoet is a sweet plugin maintained and supported with love by <a target="_blank" href="http://www.mailpoet.com/about-the-wysija-team-members/?utm_medium=plugin&utm_campaign=know_team&utm_source=wp_plugins_list">a team of a dozen</a>.
6
- Version: 2.6.19
7
  Author: MailPoet
8
  Author URI: http://www.mailpoet.com/
9
  License: GPLv2 or later
3
  Plugin Name: MailPoet Newsletters
4
  Plugin URI: http://www.mailpoet.com/
5
  Description: Create and send newsletters or automated emails. Capture subscribers with a widget. Import and manage your lists. MailPoet is a sweet plugin maintained and supported with love by <a target="_blank" href="http://www.mailpoet.com/about-the-wysija-team-members/?utm_medium=plugin&utm_campaign=know_team&utm_source=wp_plugins_list">a team of a dozen</a>.
6
+ Version: 2.7
7
  Author: MailPoet
8
  Author URI: http://www.mailpoet.com/
9
  License: GPLv2 or later
languages/wysija-newsletters-ar.mo CHANGED
Binary file
languages/wysija-newsletters-bg_BG.mo CHANGED
Binary file
languages/wysija-newsletters-ca.mo CHANGED
Binary file
languages/wysija-newsletters-da_DK.mo CHANGED
Binary file
languages/wysija-newsletters-el.mo CHANGED
Binary file
languages/wysija-newsletters-en_AU.mo ADDED
Binary file
languages/wysija-newsletters-es_CO.mo ADDED
Binary file
languages/wysija-newsletters-es_ES.mo CHANGED
Binary file
languages/wysija-newsletters-fi.mo CHANGED
Binary file
languages/wysija-newsletters-hu_HU.mo CHANGED
Binary file
languages/wysija-newsletters-it_IT.mo CHANGED
Binary file
languages/wysija-newsletters-lt_LT.mo CHANGED
Binary file
languages/wysija-newsletters-ml_IN.mo ADDED
Binary file
languages/wysija-newsletters-nl_NL.mo CHANGED
Binary file
languages/wysija-newsletters-oc.mo CHANGED
Binary file
languages/wysija-newsletters-pt_BR.mo CHANGED
Binary file
languages/wysija-newsletters-pt_PT.mo CHANGED
Binary file
languages/wysija-newsletters-ro_RO.mo CHANGED
Binary file
languages/wysija-newsletters-sl_SI.mo CHANGED
Binary file
languages/wysija-newsletters-sr_RS.mo CHANGED
Binary file
languages/wysija-newsletters-uk.mo CHANGED
Binary file
languages/wysija-newsletters-vi.mo CHANGED
Binary file
languages/wysija-newsletters-zh_CN.mo CHANGED
Binary file
languages/wysija-newsletters-zh_TW.mo CHANGED
Binary file
models/wp_posts.php CHANGED
@@ -1,327 +1,348 @@
1
- <?php
2
- defined('WYSIJA') or die('Restricted access');
3
-
4
- class WYSIJA_model_wp_posts extends WYSIJA_model {
5
-
6
- var $pk = 'ID';
7
- var $tableWP = true;
8
- var $table_name = 'posts';
9
- var $columns = array(
10
- 'ID' => array(
11
- 'req' => true,
12
- 'type' => 'integer'
13
- ),
14
- 'post_author' => array('type' => 'integer'),
15
- 'post_date' => array(),
16
- 'post_date_gmt' => array(),
17
- 'post_content' => array(),
18
- 'post_title' => array(),
19
- 'post_excerpt' => array(),
20
- 'post_status' => array(),
21
- 'comment_status' => array(),
22
- 'ping_status' => array(),
23
- 'post_password' => array(),
24
- 'post_name' => array(),
25
- 'to_ping' => array(),
26
- 'pinged' => array(),
27
- 'post_modified' => array(),
28
- 'post_modified_gmt' => array(),
29
- 'post_content_filtered' => array(),
30
- 'post_parent' => array('type' => 'integer'),
31
- 'guid' => array(),
32
- 'menu_order' => array('type' => 'integer'),
33
- 'post_type' => array(),
34
- 'post_mime_type' => array(),
35
- 'comment_count' => array('type' => 'integer'),
36
- );
37
-
38
- function __construct() {
39
- parent::__construct();
40
- $this->table_prefix = '';
41
- }
42
-
43
- function get_posts($args = array()) {
44
- /**
45
- * SELECT A.ID, A.post_title, A.post_content, A.post_date FROM `wp_posts` A
46
- * LEFT JOIN `wp_term_relationships` B ON (A.ID = B.object_id)
47
- * LEFT JOIN `wp_term_taxonomy` C ON (C.term_taxonomy_id = B.term_taxonomy_id)
48
- * WHERE C.term_id IN (326) AND A.post_type IN ('post') AND A.post_status IN ('publish') ORDER BY post_date DESC LIMIT 0,10;
49
- *
50
- */
51
-
52
- $default_args = array(
53
- 'post_limit' => 10,
54
- 'offset' => 0,
55
- 'category' => null,
56
- 'not_category' => null,
57
- 'orderby' => 'post_date',
58
- 'order' => 'DESC',
59
- 'include' => null,
60
- 'exclude' => null,
61
- 'meta_key' => null,
62
- 'meta_value' => null,
63
- 'post_type' => null,
64
- 'post_mime_type' => null,
65
- 'post_parent' => null,
66
- 'post_status' => 'publish',
67
- 'post_date' => null,
68
- 'is_search_query' => false,
69
- 'search' => null
70
- );
71
-
72
- $args = array_merge($default_args, $args);
73
-
74
- // set categories
75
- if(isset($args['category_ids']) && strlen(trim($args['category_ids'])) > 0) {
76
- $args['category'] = explode(',', trim($args['category_ids']));
77
- } else {
78
- if(isset($args['post_category']) && (int) $args['post_category'] > 0) {
79
- $args['category'] = (int) $args['post_category'];
80
- }
81
- }
82
- if(isset($args['include_category_ids']) && !empty($args['include_category_ids'])) {
83
- $args['category'] = $args['include_category_ids'];
84
- }
85
- if(isset($args['exclude_category_ids']) && !empty($args['exclude_category_ids'])) {
86
- $args['not_category'] = $args['exclude_category_ids'];
87
- }
88
-
89
- // default selected fields
90
- $post_fields = array(
91
- 'A.ID',
92
- 'A.post_title',
93
- 'A.post_content',
94
- 'A.post_excerpt',
95
- 'A.post_author',
96
- 'A.post_type',
97
- 'A.post_status'
98
- );
99
-
100
- // look for manual fields to select
101
- if(isset($args['post_fields']) && is_array($args['post_fields']) && !empty($args['post_fields'])) {
102
- $extra_post_fields = $args['post_fields'];
103
- // merge both fields selection
104
- $post_fields = array_merge(array('A.ID'), $extra_post_fields);
105
- }
106
-
107
- // build query
108
- $query = sprintf('SELECT DISTINCT %s FROM `[wp]' . $this->table_name . '` A ', join(', ', $post_fields));
109
-
110
- if($args['is_search_query'] === true) {
111
- $count_query = 'SELECT COUNT(DISTINCT A.ID) as total FROM `[wp]' . $this->table_name . '` A ';
112
- }
113
-
114
- // search by category
115
- if((isset($args['category']) && !empty($args['category'])) || (isset($args['not_category']) && !empty($args['not_category']))) {
116
- $query_joins = 'JOIN `[wp]term_relationships` B ON (A.ID = B.object_id) ';
117
- $query_joins .= 'JOIN `[wp]term_taxonomy` C ON (C.term_taxonomy_id = B.term_taxonomy_id) ';
118
-
119
- $query .= $query_joins;
120
-
121
- if($args['is_search_query'] === true) {
122
- $count_query .= $query_joins;
123
- }
124
- }
125
-
126
- $conditions = array();
127
-
128
- if(isset($args['include']) && $args['include'] !== null) {
129
- $conditions[] = array(
130
- 'col' => 'A.ID',
131
- 'sign' => 'IN',
132
- 'val' => $args['include'],
133
- 'cast' => 'int'
134
- );
135
- } else {
136
- foreach ($args as $type => $value) {
137
- if(!$value) continue;
138
- switch ($type) {
139
- case 'category':
140
- $conditions[] = array(
141
- 'col' => 'C.term_id',
142
- 'sign' => 'IN',
143
- 'val' => $value,
144
- 'cast' => 'int'
145
- );
146
- break;
147
- case 'not_category':
148
- $conditions[] = array(
149
- 'col' => 'C.term_id',
150
- 'sign' => 'NOT IN',
151
- 'val' => $value,
152
- 'cast' => 'int'
153
- );
154
- break;
155
- case 'include':
156
- $conditions[] = array(
157
- 'col' => 'A.ID',
158
- 'sign' => 'IN',
159
- 'val' => $value,
160
- 'cast' => 'int'
161
- );
162
- break;
163
- case 'exclude':
164
- $conditions[] = array(
165
- 'col' => 'A.ID',
166
- 'sign' => 'NOT IN',
167
- 'val' => $value,
168
- 'cast' => 'int'
169
- );
170
- break;
171
- case 'cpt': // this is for backwards compatibility's sake
172
- case 'post_type':
173
- $conditions[] = array(
174
- 'col' => 'A.post_type',
175
- 'sign' => 'IN',
176
- 'val' => $value
177
- );
178
- break;
179
- case 'post_status':
180
- $conditions[] = array(
181
- 'col' => 'A.post_status',
182
- 'sign' => 'IN',
183
- 'val' => $value
184
- );
185
- break;
186
- case 'post_date':
187
- // apply timezone to date value
188
- $helper_toolbox = WYSIJA::get('toolbox', 'helper');
189
- $value = $helper_toolbox->time_tzed($value);
190
-
191
- if($value !== '') {
192
- $conditions[] = array(
193
- 'col' => 'A.post_date',
194
- 'sign' => '>',
195
- 'val' => $value
196
- );
197
- }
198
- break;
199
- case 'search':
200
- $conditions[] = array(
201
- 'col' => 'A.post_title',
202
- 'sign' => 'LIKE',
203
- 'val' => '%' . $value . '%'
204
- );
205
- break;
206
- }
207
- }
208
- }
209
-
210
- // set static conditions for post statuses (we don't want drafts and such to appear in search results)
211
- if($args['include'] === null) {
212
- $conditions[] = array(
213
- 'col' => 'A.post_status',
214
- 'sign' => 'NOT IN',
215
- 'val' => array(
216
- 'auto-draft',
217
- 'inherit'
218
- )
219
- );
220
- }
221
-
222
- // where conditions
223
- if(!empty($conditions)) {
224
- $query_conditions = $this->build_conditions($conditions);
225
-
226
- $query .= $query_conditions;
227
-
228
- if($args['is_search_query'] === true) {
229
- $count_query .= $query_conditions;
230
- }
231
- }
232
-
233
- // order by
234
- if(isset($args['orderby'])) {
235
- $query .= ' ORDER BY ' . $args['orderby'];
236
- if(isset($args['sort_by'])) {
237
- $query .= ' ' . (($args['sort_by'] === 'newest') ? 'DESC' : 'ASC');
238
- } else {
239
- if(isset($args['order'])) {
240
- $query .= ' ' . $args['order'];
241
- }
242
- }
243
- }
244
-
245
- // set limit (only if we are not requesting posts based on their id)
246
- if(array_key_exists('include', $args) && $args['include'] === null) {
247
- $query_offset = (isset($args['query_offset']) ? (int) $args['query_offset'] : 0);
248
- $query_limit = ((isset($args['post_limit']) && (int) $args['post_limit'] > 0) ? (int) $args['post_limit'] : 10);
249
- $query .= sprintf(' LIMIT %d,%d', $query_offset, $query_limit);
250
- }
251
-
252
- if($args['is_search_query'] === true) {
253
- return array(
254
- 'rows' => $this->query('get_res', $query),
255
- 'count' => $this->query('get_row', $count_query)
256
- );
257
- } else {
258
- return $this->query('get_res', $query);
259
- }
260
- }
261
-
262
- function build_conditions($conditions) {
263
- $query = '';
264
- $i = 0;
265
-
266
- foreach ($conditions as $key => $data) {
267
-
268
- if($i > 0) $query .= ' AND ';
269
-
270
- $query .= $data['col'] . ' ';
271
-
272
- $value = $data['val'];
273
-
274
- switch ($data['sign']) {
275
- case 'IN':
276
- case 'NOT IN':
277
- $values = '';
278
- if(is_array($value)) {
279
- if(array_key_exists('cast', $data) && $data['cast'] === 'int') {
280
- $count = count($value);
281
- for ($j = 0; $j < $count; $j++) {
282
- if($value[$j] === null) continue;
283
- $value[$j] = intval($value[$j]);
284
- }
285
- $values = join(', ', $value);
286
- } else {
287
- $values = "'" . join("', '", $value) . "'";
288
- }
289
- $query .= $data['sign'] . ' (' . $values . ')';
290
- } else {
291
- if(strpos($value, ',') === false) {
292
- // single value
293
- if(array_key_exists('cast', $data) && $data['cast'] === 'int') {
294
- $query .= '= ' . (int) $value;
295
- } else {
296
- $query .= '= "' . $value . '"';
297
- }
298
- } else {
299
- // multiple values
300
- $values = "'" . join("','", explode(',', $value)) . "'";
301
- $query .= $data['sign'] . ' (' . $values . ')';
302
- }
303
- }
304
- break;
305
- case 'LIKE':
306
- $query .= ' LIKE "' . $value . '"';
307
- break;
308
- default:
309
- $sign = '=';
310
- if(isset($data['sign'])) $sign = $data['sign'];
311
-
312
- if(array_key_exists('cast', $data) && $data['cast'] === 'int') {
313
- $query .= $sign . (int) $value . " ";
314
- } else {
315
- $query .= $sign . "'" . $value . "' ";
316
- }
317
- }
318
- $i++;
319
- }
320
-
321
- if($query === '') {
322
- return '';
323
- } else {
324
- return 'WHERE ' . $query;
325
- }
326
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
327
  }
1
+ <?php
2
+ defined('WYSIJA') or die('Restricted access');
3
+
4
+ class WYSIJA_model_wp_posts extends WYSIJA_model {
5
+
6
+ var $pk = 'ID';
7
+ var $tableWP = true;
8
+ var $table_name = 'posts';
9
+ var $columns = array(
10
+ 'ID' => array(
11
+ 'req' => true,
12
+ 'type' => 'integer'
13
+ ),
14
+ 'post_author' => array('type' => 'integer'),
15
+ 'post_date' => array(),
16
+ 'post_date_gmt' => array(),
17
+ 'post_content' => array(),
18
+ 'post_title' => array(),
19
+ 'post_excerpt' => array(),
20
+ 'post_status' => array(),
21
+ 'comment_status' => array(),
22
+ 'ping_status' => array(),
23
+ 'post_password' => array(),
24
+ 'post_name' => array(),
25
+ 'to_ping' => array(),
26
+ 'pinged' => array(),
27
+ 'post_modified' => array(),
28
+ 'post_modified_gmt' => array(),
29
+ 'post_content_filtered' => array(),
30
+ 'post_parent' => array('type' => 'integer'),
31
+ 'guid' => array(),
32
+ 'menu_order' => array('type' => 'integer'),
33
+ 'post_type' => array(),
34
+ 'post_mime_type' => array(),
35
+ 'comment_count' => array('type' => 'integer'),
36
+ );
37
+
38
+ function __construct() {
39
+ parent::__construct();
40
+ $this->table_prefix = '';
41
+ }
42
+
43
+ function get_posts($args = array()) {
44
+ /**
45
+ * SELECT A.ID, A.post_title, A.post_content, A.post_date FROM `wp_posts` A
46
+ * LEFT JOIN `wp_term_relationships` B ON (A.ID = B.object_id)
47
+ * LEFT JOIN `wp_term_taxonomy` C ON (C.term_taxonomy_id = B.term_taxonomy_id)
48
+ * WHERE C.term_id IN (326) AND A.post_type IN ('post') AND A.post_status IN ('publish') ORDER BY post_date DESC LIMIT 0,10;
49
+ *
50
+ */
51
+ $default_args = array(
52
+ 'post_limit' => 10,
53
+ 'offset' => 0,
54
+ 'category' => null,
55
+ 'not_category' => null,
56
+ 'orderby' => 'post_date',
57
+ 'order' => 'DESC',
58
+ 'include' => null,
59
+ 'exclude' => null,
60
+ 'meta_key' => null,
61
+ 'meta_value' => null,
62
+ 'post_type' => null,
63
+ 'post_mime_type' => null,
64
+ 'post_parent' => null,
65
+ 'post_status' => 'publish',
66
+ 'post_date' => null,
67
+ 'is_search_query' => false,
68
+ 'search' => null
69
+ );
70
+
71
+ $args = array_merge($default_args, $args);
72
+
73
+ // set categories
74
+ if(isset($args['category_ids']) && strlen(trim($args['category_ids'])) > 0) {
75
+ $args['category'] = explode(',', trim($args['category_ids']));
76
+ } else {
77
+ if(isset($args['post_category']) && (int) $args['post_category'] > 0) {
78
+ $args['category'] = (int) $args['post_category'];
79
+ }
80
+ }
81
+ if(isset($args['include_category_ids']) && !empty($args['include_category_ids'])) {
82
+ $args['category'] = $args['include_category_ids'];
83
+ }
84
+ if(isset($args['exclude_category_ids']) && !empty($args['exclude_category_ids'])) {
85
+ $args['not_category'] = $args['exclude_category_ids'];
86
+ }
87
+
88
+ // default selected fields
89
+ $post_fields = array(
90
+ 'A.ID',
91
+ 'A.post_title',
92
+ 'A.post_content',
93
+ 'A.post_excerpt',
94
+ 'A.post_author',
95
+ 'A.post_type',
96
+ 'A.post_status'
97
+ );
98
+
99
+ $additional_post_fields = array(
100
+ 'post_date',
101
+ 'post_date_gmt',
102
+ 'comment_status',
103
+ 'ping_status',
104
+ 'post_name',
105
+ 'to_ping',
106
+ 'pinged',
107
+ 'post_modified',
108
+ 'post_modified_gmt',
109
+ 'post_content_filtered',
110
+ 'post_parent',
111
+ 'guid',
112
+ 'menu_order',
113
+ 'post_mime_type',
114
+ 'comment_count'
115
+ );
116
+
117
+ // look for manual fields to select
118
+ if(isset($args['post_fields']) && is_array($args['post_fields']) && !empty($args['post_fields'])) {
119
+ $extra_post_fields = array_values(
120
+ array_intersect(
121
+ $additional_post_fields,
122
+ array_map('esc_sql', $args['post_fields'])
123
+ )
124
+ );
125
+ // merge both fields selection
126
+ $post_fields = array_merge(array('A.ID'), $extra_post_fields);
127
+ }
128
+
129
+ $query = sprintf('SELECT DISTINCT %s FROM `[wp]' . $this->table_name . '` A ', join(', ', $post_fields));
130
+
131
+ if($args['is_search_query'] === true) {
132
+ $count_query = 'SELECT COUNT(DISTINCT A.ID) as total FROM `[wp]' . $this->table_name . '` A ';
133
+ }
134
+
135
+ // search by category
136
+ if((isset($args['category']) && !empty($args['category'])) || (isset($args['not_category']) && !empty($args['not_category']))) {
137
+ $query_joins = 'JOIN `[wp]term_relationships` B ON (A.ID = B.object_id) ';
138
+ $query_joins .= 'JOIN `[wp]term_taxonomy` C ON (C.term_taxonomy_id = B.term_taxonomy_id) ';
139
+
140
+ $query .= $query_joins;
141
+
142
+ if($args['is_search_query'] === true) {
143
+ $count_query .= $query_joins;
144
+ }
145
+ }
146
+
147
+ $conditions = array();
148
+
149
+ if(isset($args['include']) && $args['include'] !== null) {
150
+ $conditions[] = array(
151
+ 'col' => 'A.ID',
152
+ 'sign' => 'IN',
153
+ 'val' => $args['include'],
154
+ 'cast' => 'int'
155
+ );
156
+ } else {
157
+ foreach ($args as $type => $value) {
158
+ if(!$value) continue;
159
+ switch ($type) {
160
+ case 'category':
161
+ $conditions[] = array(
162
+ 'col' => 'C.term_id',
163
+ 'sign' => 'IN',
164
+ 'val' => $value,
165
+ 'cast' => 'int'
166
+ );
167
+ break;
168
+ case 'not_category':
169
+ $conditions[] = array(
170
+ 'col' => 'C.term_id',
171
+ 'sign' => 'NOT IN',
172
+ 'val' => $value,
173
+ 'cast' => 'int'
174
+ );
175
+ break;
176
+ case 'include':
177
+ $conditions[] = array(
178
+ 'col' => 'A.ID',
179
+ 'sign' => 'IN',
180
+ 'val' => $value,
181
+ 'cast' => 'int'
182
+ );
183
+ break;
184
+ case 'exclude':
185
+ $conditions[] = array(
186
+ 'col' => 'A.ID',
187
+ 'sign' => 'NOT IN',
188
+ 'val' => $value,
189
+ 'cast' => 'int'
190
+ );
191
+ break;
192
+ case 'cpt': // this is for backwards compatibility's sake
193
+ case 'post_type':
194
+ $conditions[] = array(
195
+ 'col' => 'A.post_type',
196
+ 'sign' => 'IN',
197
+ 'val' => $value
198
+ );
199
+ break;
200
+ case 'post_status':
201
+ $conditions[] = array(
202
+ 'col' => 'A.post_status',
203
+ 'sign' => 'IN',
204
+ 'val' => $value
205
+ );
206
+ break;
207
+ case 'post_date':
208
+ // apply timezone to date value
209
+ $helper_toolbox = WYSIJA::get('toolbox', 'helper');
210
+ $value = $helper_toolbox->time_tzed($value);
211
+
212
+ if($value !== '') {
213
+ $conditions[] = array(
214
+ 'col' => 'A.post_date',
215
+ 'sign' => '>',
216
+ 'val' => $value
217
+ );
218
+ }
219
+ break;
220
+ case 'search':
221
+ $conditions[] = array(
222
+ 'col' => 'A.post_title',
223
+ 'sign' => 'LIKE',
224
+ 'val' => '%' . $value . '%'
225
+ );
226
+ break;
227
+ }
228
+ }
229
+ }
230
+
231
+ // set static conditions for post statuses (we don't want drafts and such to appear in search results)
232
+ if($args['include'] === null) {
233
+ $conditions[] = array(
234
+ 'col' => 'A.post_status',
235
+ 'sign' => 'NOT IN',
236
+ 'val' => array(
237
+ 'auto-draft',
238
+ 'inherit'
239
+ )
240
+ );
241
+ }
242
+
243
+ // where conditions
244
+ if(!empty($conditions)) {
245
+ $query_conditions = $this->build_conditions($conditions);
246
+
247
+ $query .= $query_conditions;
248
+
249
+ if($args['is_search_query'] === true) {
250
+ $count_query .= $query_conditions;
251
+ }
252
+ }
253
+
254
+ // order by
255
+ if(isset($args['orderby'])) {
256
+ $query .= ' ORDER BY ' . $args['orderby'];
257
+ if(isset($args['sort_by'])) {
258
+ $query .= ' ' . (($args['sort_by'] === 'newest') ? 'DESC' : 'ASC');
259
+ } else {
260
+ if(isset($args['order'])) {
261
+ $query .= ' ' . $args['order'];
262
+ }
263
+ }
264
+ }
265
+
266
+ // set limit (only if we are not requesting posts based on their id)
267
+ if(array_key_exists('include', $args) && $args['include'] === null) {
268
+ $query_offset = (isset($args['query_offset']) ? (int) $args['query_offset'] : 0);
269
+ $query_limit = ((isset($args['post_limit']) && (int) $args['post_limit'] > 0) ? (int) $args['post_limit'] : 10);
270
+ $query .= sprintf(' LIMIT %d,%d', $query_offset, $query_limit);
271
+ }
272
+
273
+ if($args['is_search_query'] === true) {
274
+ return array(
275
+ 'rows' => $this->query('get_res', $query),
276
+ 'count' => $this->query('get_row', $count_query)
277
+ );
278
+ } else {
279
+ return $this->query('get_res', $query);
280
+ }
281
+ }
282
+
283
+ function build_conditions($conditions) {
284
+ $query = '';
285
+ $i = 0;
286
+
287
+ foreach ($conditions as $key => $data) {
288
+
289
+ if($i > 0) $query .= ' AND ';
290
+
291
+ $query .= $data['col'] . ' ';
292
+
293
+ $value = $data['val'];
294
+
295
+ switch ($data['sign']) {
296
+ case 'IN':
297
+ case 'NOT IN':
298
+ $values = '';
299
+ if(is_array($value)) {
300
+ if(array_key_exists('cast', $data) && $data['cast'] === 'int') {
301
+ $count = count($value);
302
+ for ($j = 0; $j < $count; $j++) {
303
+ if($value[$j] === null) continue;
304
+ $value[$j] = intval($value[$j]);
305
+ }
306
+ $values = join(', ', $value);
307
+ } else {
308
+ $values = "'" . join("', '", $value) . "'";
309
+ }
310
+ $query .= $data['sign'] . ' (' . $values . ')';
311
+ } else {
312
+ if(strpos($value, ',') === false) {
313
+ // single value
314
+ if(array_key_exists('cast', $data) && $data['cast'] === 'int') {
315
+ $query .= '= ' . (int) $value;
316
+ } else {
317
+ $query .= '= "' . $value . '"';
318
+ }
319
+ } else {
320
+ // multiple values
321
+ $values = "'" . join("','", explode(',', $value)) . "'";
322
+ $query .= $data['sign'] . ' (' . $values . ')';
323
+ }
324
+ }
325
+ break;
326
+ case 'LIKE':
327
+ $query .= ' LIKE "' . $value . '"';
328
+ break;
329
+ default:
330
+ $sign = '=';
331
+ if(isset($data['sign'])) $sign = $data['sign'];
332
+
333
+ if(array_key_exists('cast', $data) && $data['cast'] === 'int') {
334
+ $query .= $sign . (int) $value . " ";
335
+ } else {
336
+ $query .= $sign . "'" . $value . "' ";
337
+ }
338
+ }
339
+ $i++;
340
+ }
341
+
342
+ if($query === '') {
343
+ return '';
344
+ } else {
345
+ return 'WHERE ' . $query;
346
+ }
347
+ }
348
  }
readme.txt CHANGED
@@ -1,9 +1,9 @@
1
  === MailPoet Newsletters ===
2
- Contributors: wysija, kgjerstad, benheu, JoN1oP, badshark, rafaehlers, vvaz, keiferski, mrcasual
3
  Tags: newsletter, newsletters, email newsletter, email subscription, newsletter signup, post notification, autoresponder, newsletter alert, auto newsletter, automatic post notification, email newsletters, email signup, auto post notifications, newsletter widget, newsletter builder, subscribe widget, signup widget, email subscription, newsletter plugin, widget, subscription, emailing, mailpoet, wysija, mandrill, sendgrid
4
  Requires at least: 3.3
5
- Tested up to: 4.3.1
6
- Stable tag: 2.6.19
7
  Send newsletters post notifications or autoresponders from WordPress easily, and beautifully. Start to capture subscribers with our widget now.
8
 
9
  == Description ==
@@ -130,8 +130,18 @@ Our [support site](http://support.mailpoet.com/) has plenty of articles and a ti
130
 
131
  == Changelog ==
132
 
 
 
 
 
 
 
 
 
 
 
133
  = 2.6.19 - 2015-10-13 =
134
- * Fixed a URL validation issue when WP's home & site URLs are different. Kudos to Divaldo for pointing it out
135
 
136
  = 2.6.18 - 2015-09-21 =
137
  * Fixed URL validation issue
1
  === MailPoet Newsletters ===
2
+ Contributors: wysija
3
  Tags: newsletter, newsletters, email newsletter, email subscription, newsletter signup, post notification, autoresponder, newsletter alert, auto newsletter, automatic post notification, email newsletters, email signup, auto post notifications, newsletter widget, newsletter builder, subscribe widget, signup widget, email subscription, newsletter plugin, widget, subscription, emailing, mailpoet, wysija, mandrill, sendgrid
4
  Requires at least: 3.3
5
+ Tested up to: 4.4.1
6
+ Stable tag: 2.7
7
  Send newsletters post notifications or autoresponders from WordPress easily, and beautifully. Start to capture subscribers with our widget now.
8
 
9
  == Description ==
130
 
131
  == Changelog ==
132
 
133
+ = 2.7 - 2016-01-29 =
134
+ * Enabled PHP7 compatibility
135
+ * Fixed security issues. Thanks to Immunity and Netsparker (https://www.netsparker.com) for alerting us.
136
+ * Fixed an issue with newsletters not saving during the creation process
137
+ * Disabled SSL verification on hosts with invalid SSL certificates and PHP 5.6
138
+ * Updated SendGrid mailer
139
+ * Improved URL validation logic
140
+ * Addressed PHP notices that appeared in cron output
141
+ * Fixed other minor issues
142
+
143
  = 2.6.19 - 2015-10-13 =
144
+ * Fixed a URL validation issue when WP's home & site URLs are different. Kudos to Divaldo for pointing it out.
145
 
146
  = 2.6.18 - 2015-09-21 =
147
  * Fixed URL validation issue
views/back/campaigns.php CHANGED
@@ -412,7 +412,6 @@ class WYSIJA_view_back_campaigns extends WYSIJA_view_back {
412
  if (isset($row['params']['schedule']['isscheduled']) && $row['status'] == 4) {
413
  $helper_toolbox = WYSIJA::get('toolbox', 'helper');
414
 
415
-
416
  //no recording just conversion
417
  $scheduletimenoffset = strtotime($row['params']['schedule']['day'] . ' ' . $row['params']['schedule']['time']);
418
  $timeleft = $helper_toolbox->localtime_to_servertime($scheduletimenoffset) - time();
@@ -432,8 +431,6 @@ class WYSIJA_view_back_campaigns extends WYSIJA_view_back {
432
 
433
  }
434
 
435
-
436
-
437
  $statusshared = $durationsent;
438
  echo __('Scheduled', WYSIJA);
439
  } else {
@@ -652,7 +649,6 @@ class WYSIJA_view_back_campaigns extends WYSIJA_view_back {
652
 
653
  break;
654
  case -1:
655
-
656
  if ($row['type'] == 2) {
657
  $resumelink = __('Not active.', WYSIJA) . ' | <a href="admin.php?page=wysija_campaigns&id=' . $row['email_id'] . '&action=resume&_wpnonce='.$this->secure(array('action' => 'resume' , 'id' => $row["email_id"]), true).'" class="submitedit">' . __('Activate', WYSIJA) . '</a>';
658
  echo $resumelink;
@@ -701,8 +697,6 @@ class WYSIJA_view_back_campaigns extends WYSIJA_view_back {
701
  echo '<p>' . $row['sent_at'] . '</p>';
702
  }
703
  ?></td>
704
-
705
-
706
  </tr><?php
707
  $alt = !$alt;
708
  }
@@ -1326,14 +1320,23 @@ class WYSIJA_view_back_campaigns extends WYSIJA_view_back {
1326
 
1327
  function saveWYSIJA(callback) {
1328
  wysijaAJAX.task = 'save_editor';
1329
- wysijaAJAX._wpnonce = wysijanonces.campaigns.save_editor;
1330
  wysijaAJAX.wysijaData = Wysija.save();
1331
  WYSIJA_SYNC_AJAX({success: callback});
1332
  }
1333
 
1334
  // trigger the save on these links/buttons (save, next step, view in browser, unsubscribe)
1335
- $$('#wysija-do-save, #wysija-next-step, #wysija_viewbrowser a, #wysija_unsubscribe a').invoke('observe', 'click', function() {
1336
- saveWYSIJA();
 
 
 
 
 
 
 
 
 
1337
  return false;
1338
  });
1339
 
@@ -3147,7 +3150,7 @@ class WYSIJA_view_back_campaigns extends WYSIJA_view_back {
3147
  // returning the new data array
3148
  return $data;
3149
  }
3150
-
3151
  private function _get_social_buttons($inline=true){
3152
 
3153
  if($inline){
412
  if (isset($row['params']['schedule']['isscheduled']) && $row['status'] == 4) {
413
  $helper_toolbox = WYSIJA::get('toolbox', 'helper');
414
 
 
415
  //no recording just conversion
416
  $scheduletimenoffset = strtotime($row['params']['schedule']['day'] . ' ' . $row['params']['schedule']['time']);
417
  $timeleft = $helper_toolbox->localtime_to_servertime($scheduletimenoffset) - time();
431
 
432
  }
433
 
 
 
434
  $statusshared = $durationsent;
435
  echo __('Scheduled', WYSIJA);
436
  } else {
649
 
650
  break;
651
  case -1:
 
652
  if ($row['type'] == 2) {
653
  $resumelink = __('Not active.', WYSIJA) . ' | <a href="admin.php?page=wysija_campaigns&id=' . $row['email_id'] . '&action=resume&_wpnonce='.$this->secure(array('action' => 'resume' , 'id' => $row["email_id"]), true).'" class="submitedit">' . __('Activate', WYSIJA) . '</a>';
654
  echo $resumelink;
697
  echo '<p>' . $row['sent_at'] . '</p>';
698
  }
699
  ?></td>
 
 
700
  </tr><?php
701
  $alt = !$alt;
702
  }
1320
 
1321
  function saveWYSIJA(callback) {
1322
  wysijaAJAX.task = 'save_editor';
1323
+ wysijaAJAX._wpnonce = wysijanonces.campaigns.save_editor;
1324
  wysijaAJAX.wysijaData = Wysija.save();
1325
  WYSIJA_SYNC_AJAX({success: callback});
1326
  }
1327
 
1328
  // trigger the save on these links/buttons (save, next step, view in browser, unsubscribe)
1329
+ $$('#wysija-do-save, #wysija-next-step, #wysija_viewbrowser a, #wysija_unsubscribe a').invoke('observe', 'click', function(e) {
1330
+ if (this.id === 'wysija-next-step') {
1331
+ e.preventDefault();
1332
+ var id = this.id,
1333
+ href = this.href;
1334
+ var callback = function () {
1335
+ if (id === 'wysija-next-step') window.location.href = href
1336
+ };
1337
+ }
1338
+ else var callback = function() {};
1339
+ saveWYSIJA(callback);
1340
  return false;
1341
  });
1342
 
3150
  // returning the new data array
3151
  return $data;
3152
  }
3153
+
3154
  private function _get_social_buttons($inline=true){
3155
 
3156
  if($inline){