Merge pull request #12285 from eileenmcnaughton/master
[civicrm-core.git] / CRM / Mailing / Selector / Event.php
1 <?php
2 /*
3 +--------------------------------------------------------------------+
4 | CiviCRM version 5 |
5 +--------------------------------------------------------------------+
6 | Copyright CiviCRM LLC (c) 2004-2018 |
7 +--------------------------------------------------------------------+
8 | This file is a part of CiviCRM. |
9 | |
10 | CiviCRM is free software; you can copy, modify, and distribute it |
11 | under the terms of the GNU Affero General Public License |
12 | Version 3, 19 November 2007 and the CiviCRM Licensing Exception. |
13 | |
14 | CiviCRM is distributed in the hope that it will be useful, but |
15 | WITHOUT ANY WARRANTY; without even the implied warranty of |
16 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
17 | See the GNU Affero General Public License for more details. |
18 | |
19 | You should have received a copy of the GNU Affero General Public |
20 | License and the CiviCRM Licensing Exception along |
21 | with this program; if not, contact CiviCRM LLC |
22 | at info[AT]civicrm[DOT]org. If you have questions about the |
23 | GNU Affero General Public License or the licensing of CiviCRM, |
24 | see the CiviCRM license FAQ at http://civicrm.org/licensing |
25 +--------------------------------------------------------------------+
26 */
27
28 /**
29 *
30 * @package CRM
31 * @copyright CiviCRM LLC (c) 2004-2018
32 */
33
34 /**
35 * This class is used to retrieve and display a range of
36 * contacts that match the given criteria (specifically for
37 * results of advanced search options.
38 */
39 class CRM_Mailing_Selector_Event extends CRM_Core_Selector_Base implements CRM_Core_Selector_API {
40
41 /**
42 * Array of supported links, currently null
43 *
44 * @var array
45 */
46 static $_links = NULL;
47
48 /**
49 * What event type are we browsing?
50 */
51 private $_event;
52
53 /**
54 * Should we only count distinct contacts?
55 */
56 private $_is_distinct;
57
58 /**
59 * Which mailing are we browsing events from?
60 */
61 private $_mailing_id;
62
63 /**
64 * Do we want events tied to a specific job?
65 */
66 private $_job_id;
67
68 /**
69 * For click-through events, do we only want those from a specific url?
70 */
71 private $_url_id;
72
73 /**
74 * We use desc to remind us what that column is, name is used in the tpl
75 *
76 * @var array
77 */
78 public $_columnHeaders;
79
80 /**
81 * Class constructor.
82 *
83 * @param string $event
84 * The event type (queue/delivered/open...).
85 * @param bool $distinct
86 * Count only distinct contact events?.
87 * @param int $mailing
88 * ID of the mailing to query.
89 * @param int $job
90 * ID of the job to query. If null, all jobs from $mailing are queried.
91 * @param int $url
92 * If the event type is a click-through, do we want only those from a specific url?.
93 *
94 * @return \CRM_Mailing_Selector_Event
95 */
96 public function __construct($event, $distinct, $mailing, $job = NULL, $url = NULL) {
97 $this->_event_type = $event;
98 $this->_is_distinct = $distinct;
99 $this->_mailing_id = $mailing;
100 $this->_job_id = $job;
101 $this->_url_id = $url;
102 }
103
104 /**
105 * This method returns the links that are given for each search row.
106 *
107 * @return array
108 */
109 public static function &links() {
110 return self::$_links;
111 }
112
113 /**
114 * Getter for array of the parameters required for creating pager.
115 *
116 * @param $action
117 * @param array $params
118 */
119 public function getPagerParams($action, &$params) {
120 $params['csvString'] = NULL;
121 $params['rowCount'] = CRM_Utils_Pager::ROWCOUNT;
122 $params['status'] = ts('%1 %%StatusMessage%%', array(1 => $this->eventToTitle()));
123 $params['buttonTop'] = 'PagerTopButton';
124 $params['buttonBottom'] = 'PagerBottomButton';
125 }
126
127 /**
128 * Returns the column headers as an array of tuples:
129 * (name, sortName (key to the sort array))
130 *
131 * @param string $action
132 * The action being performed.
133 * @param string $output
134 * What should the result set include (web/email/csv).
135 *
136 * @return array
137 * the column headers that need to be displayed
138 */
139 public function &getColumnHeaders($action = NULL, $output = NULL) {
140 $mailing = CRM_Mailing_BAO_Mailing::getTableName();
141
142 $contact = CRM_Contact_BAO_Contact::getTableName();
143
144 $email = CRM_Core_BAO_Email::getTableName();
145
146 $job = CRM_Mailing_BAO_MailingJob::getTableName();
147 if (!isset($this->_columnHeaders)) {
148
149 $this->_columnHeaders = array(
150 'sort_name' => array(
151 'name' => ts('Contact'),
152 'sort' => $contact . '.sort_name',
153 'direction' => CRM_Utils_Sort::ASCENDING,
154 ),
155 'email' => array(
156 'name' => ts('Email Address'),
157 'sort' => $email . '.email',
158 'direction' => CRM_Utils_Sort::DONTCARE,
159 ),
160 );
161
162 switch ($this->_event_type) {
163 case 'queue':
164 $dateSort = $job . '.start_date';
165 break;
166
167 case 'delivered':
168 $this->_columnHeaders = array(
169 'contact_id' => array(
170 'name' => ts('Internal Contact ID'),
171 'sort' => $contact . '.id',
172 'direction' => CRM_Utils_Sort::ASCENDING,
173 ),
174 ) + $this->_columnHeaders;
175 $dateSort = CRM_Mailing_Event_BAO_Delivered::getTableName() . '.time_stamp';
176 break;
177
178 case 'opened':
179 $dateSort = CRM_Mailing_Event_BAO_Opened::getTableName() . '.time_stamp';
180 break;
181
182 case 'bounce':
183 $dateSort = CRM_Mailing_Event_BAO_Bounce::getTableName() . '.time_stamp';
184 $this->_columnHeaders = array_merge($this->_columnHeaders,
185 array(
186 array(
187 'name' => ts('Bounce Type'),
188 ),
189 array(
190 'name' => ts('Bounce Reason'),
191 ),
192 )
193 );
194 break;
195
196 case 'forward':
197 $dateSort = CRM_Mailing_Event_BAO_Forward::getTableName() . '.time_stamp';
198
199 $this->_columnHeaders = array_merge($this->_columnHeaders,
200 array(
201 array(
202 'name' => ts('Forwarded Email'),
203 ),
204 )
205 );
206 break;
207
208 case 'reply':
209 $dateSort = CRM_Mailing_Event_BAO_Reply::getTableName() . '.time_stamp';
210 break;
211
212 case 'unsubscribe':
213 $dateSort = CRM_Mailing_Event_BAO_Unsubscribe::getTableName() . '.time_stamp';
214 $this->_columnHeaders = array_merge($this->_columnHeaders, array(
215 array(
216 'name' => ts('Unsubscribe'),
217 ),
218 ));
219 break;
220
221 case 'optout':
222 $dateSort = CRM_Mailing_Event_BAO_Unsubscribe::getTableName() . '.time_stamp';
223 $this->_columnHeaders = array_merge($this->_columnHeaders, array(
224 array(
225 'name' => ts('Opt-Out'),
226 ),
227 ));
228 break;
229
230 case 'click':
231 $dateSort = CRM_Mailing_Event_BAO_TrackableURLOpen::getTableName() . '.time_stamp';
232 $this->_columnHeaders = array_merge($this->_columnHeaders, array(
233 array(
234 'name' => ts('URL'),
235 ),
236 ));
237 break;
238
239 default:
240 return 0;
241 }
242
243 $this->_columnHeaders = array_merge($this->_columnHeaders, array(
244 'date' => array(
245 'name' => ts('Date'),
246 'sort' => $dateSort,
247 'direction' => CRM_Utils_Sort::DESCENDING,
248 ),
249 ));
250 }
251 return $this->_columnHeaders;
252 }
253
254 /**
255 * Returns total number of rows for the query.
256 *
257 * @param string $action
258 *
259 * @return int
260 * Total number of rows
261 */
262 public function getTotalCount($action) {
263 switch ($this->_event_type) {
264 case 'queue':
265 $event = new CRM_Mailing_Event_BAO_Queue();
266 $result = $event->getTotalCount($this->_mailing_id,
267 $this->_job_id
268 );
269 return $result;
270
271 case 'delivered':
272 $event = new CRM_Mailing_Event_BAO_Delivered();
273 $result = $event->getTotalCount($this->_mailing_id,
274 $this->_job_id,
275 $this->_is_distinct
276 );
277 return $result;
278
279 case 'opened':
280 $event = new CRM_Mailing_Event_BAO_Opened();
281 $result = $event->getTotalCount($this->_mailing_id,
282 $this->_job_id,
283 $this->_is_distinct
284 );
285 return $result;
286
287 case 'bounce':
288 $event = new CRM_Mailing_Event_BAO_Bounce();
289 $result = $event->getTotalCount($this->_mailing_id,
290 $this->_job_id,
291 $this->_is_distinct
292 );
293 return $result;
294
295 case 'forward':
296 $event = new CRM_Mailing_Event_BAO_Forward();
297 $result = $event->getTotalCount($this->_mailing_id,
298 $this->_job_id,
299 $this->_is_distinct
300 );
301 return $result;
302
303 case 'reply':
304 $event = new CRM_Mailing_Event_BAO_Reply();
305 $result = $event->getTotalCount($this->_mailing_id,
306 $this->_job_id,
307 $this->_is_distinct
308 );
309 return $result;
310
311 case 'unsubscribe':
312 $event = new CRM_Mailing_Event_BAO_Unsubscribe();
313 $result = $event->getTotalCount($this->_mailing_id,
314 $this->_job_id,
315 $this->_is_distinct
316 );
317 return $result;
318
319 case 'optout':
320 $event = new CRM_Mailing_Event_BAO_Unsubscribe();
321 $result = $event->getTotalCount($this->_mailing_id,
322 $this->_job_id,
323 $this->_is_distinct,
324 FALSE
325 );
326 return $result;
327
328 case 'click':
329 $event = new CRM_Mailing_Event_BAO_TrackableURLOpen();
330 $result = $event->getTotalCount($this->_mailing_id,
331 $this->_job_id,
332 $this->_is_distinct,
333 $this->_url_id
334 );
335 return $result;
336
337 default:
338 return 0;
339 }
340 }
341
342 /**
343 * Returns all the rows in the given offset and rowCount.
344 *
345 * @param string $action
346 * The action being performed.
347 * @param int $offset
348 * The row number to start from.
349 * @param int $rowCount
350 * The number of rows to return.
351 * @param string $sort
352 * The sql string that describes the sort order.
353 * @param string $output
354 * What should the result set include (web/email/csv).
355 *
356 * @return int
357 * the total number of rows for this action
358 */
359 public function &getRows($action, $offset, $rowCount, $sort, $output = NULL) {
360 switch ($this->_event_type) {
361 case 'queue':
362 $rows = CRM_Mailing_Event_BAO_Queue::getRows($this->_mailing_id,
363 $this->_job_id, $offset, $rowCount, $sort
364 );
365 return $rows;
366
367 case 'delivered':
368 $rows = CRM_Mailing_Event_BAO_Delivered::getRows($this->_mailing_id,
369 $this->_job_id, $this->_is_distinct,
370 $offset, $rowCount, $sort
371 );
372 return $rows;
373
374 case 'opened':
375 $rows = CRM_Mailing_Event_BAO_Opened::getRows($this->_mailing_id,
376 $this->_job_id, $this->_is_distinct,
377 $offset, $rowCount, $sort
378 );
379 return $rows;
380
381 case 'bounce':
382 $rows = CRM_Mailing_Event_BAO_Bounce::getRows($this->_mailing_id,
383 $this->_job_id, $this->_is_distinct,
384 $offset, $rowCount, $sort
385 );
386 return $rows;
387
388 case 'forward':
389 $rows = CRM_Mailing_Event_BAO_Forward::getRows($this->_mailing_id,
390 $this->_job_id, $this->_is_distinct,
391 $offset, $rowCount, $sort
392 );
393 return $rows;
394
395 case 'reply':
396 $rows = CRM_Mailing_Event_BAO_Reply::getRows($this->_mailing_id,
397 $this->_job_id, $this->_is_distinct,
398 $offset, $rowCount, $sort
399 );
400 return $rows;
401
402 case 'unsubscribe':
403 $rows = CRM_Mailing_Event_BAO_Unsubscribe::getRows($this->_mailing_id,
404 $this->_job_id, $this->_is_distinct,
405 $offset, $rowCount, $sort, TRUE
406 );
407 return $rows;
408
409 case 'optout':
410 $rows = CRM_Mailing_Event_BAO_Unsubscribe::getRows($this->_mailing_id,
411 $this->_job_id, $this->_is_distinct,
412 $offset, $rowCount, $sort, FALSE
413 );
414 return $rows;
415
416 case 'click':
417 $rows = CRM_Mailing_Event_BAO_TrackableURLOpen::getRows(
418 $this->_mailing_id, $this->_job_id,
419 $this->_is_distinct, $this->_url_id,
420 $offset, $rowCount, $sort
421 );
422 return $rows;
423
424 default:
425 return NULL;
426 }
427 }
428
429 /**
430 * Name of export file.
431 *
432 * @param string $output
433 * Type of output.
434 *
435 * @return string|NULL
436 * name of the file
437 */
438 public function getExportFileName($output = 'csv') {
439 return NULL;
440 }
441
442 /**
443 * Get the title for the mailing event type.
444 *
445 * @return string
446 */
447 public function eventToTitle() {
448 static $events = NULL;
449
450 if (empty($events)) {
451 $events = array(
452 'queue' => ts('Intended Recipients'),
453 'delivered' => ts('Successful Deliveries'),
454 'bounce' => ts('Bounces'),
455 'forward' => ts('Forwards'),
456 'reply' => $this->_is_distinct ? ts('Unique Replies') : ts('Replies'),
457 'unsubscribe' => ts('Unsubscribe Requests'),
458 'optout' => ts('Opt-out Requests'),
459 'click' => $this->_is_distinct ? ts('Unique Click-throughs') : ts('Click-throughs'),
460 'opened' => $this->_is_distinct ? ts('Unique Tracked Opens') : ts('Total Tracked Opens'),
461 );
462 }
463 return $events[$this->_event_type];
464 }
465
466 /**
467 * Get the title of the event.
468 *
469 * @return string
470 */
471 public function getTitle() {
472 return $this->eventToTitle();
473 }
474
475 }