Completed
Push — master ( 80f1a6...8c34ac )
by Dominik
03:50
created

AzineEmailOpenTrackingCodeBuilder::getPiwikUrl()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 10
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 2
Bugs 0 Features 2
Metric Value
c 2
b 0
f 2
dl 0
loc 10
ccs 0
cts 7
cp 0
rs 9.4285
cc 1
eloc 8
nc 1
nop 6
crap 2
1
<?php
2
namespace Azine\EmailBundle\Services;
3
4
use Azine\EmailBundle\DependencyInjection\AzineEmailExtension;
5
use Ramsey\Uuid\Uuid;
6
7
/**
8
 * Implementation of the EmailOpenTrackingCodeBuilderInterface used to track email open events.
9
 *
10
 * This impelementation will create a html snippet with the image tracker code for
11
 * either GoogleAnalytics or Piwik, depending on the configured tracking url
12
 * ( azine_email_email_open_tracking_url) in your config.yml
13
 *
14
 * Class AzineEmailOpenTrackingCodeBuilder
15
 * @package Azine\EmailBundle\Services
16
 */
17
class AzineEmailOpenTrackingCodeBuilder implements EmailOpenTrackingCodeBuilderInterface {
18
19
    /**
20
     * @var  string
21
     */
22
    protected $tracking_params_campaign_source;
23
24
    /**
25
     * @var  string
26
     */
27
    protected $tracking_params_campaign_medium;
28
29
    /**
30
     * @var  string
31
     */
32
    protected $tracking_params_campaign_content;
33
34
    /**
35
     * @var  string
36
     */
37
    protected $tracking_params_campaign_name;
38
39
    /**
40
     * @var  string
41
     */
42
    protected $tracking_params_campaign_term;
43
44
    /**
45
     * @var $string|null
46
     */
47
    private $trackingUrlTemplate;
48
49
    /**
50
     * @var string the html-code template
51
     */
52
    protected $imageHtmlCode = "<img src='%s' style='border:0' alt='' />";
53
54
    /**
55
     * @param string $trackingUrlTemplate the url configured in your config.yml or null if you didn't specify a tracking url.
56
     * @param array $parameters array with the parameter names for the campaign tracking
57
     */
58 8
    public function __construct($trackingUrlTemplate, $parameters){
59 8
        $this->trackingUrlTemplate = $trackingUrlTemplate;
60 8
        $this->tracking_params_campaign_content = $parameters[AzineEmailExtension::TRACKING_PARAM_CAMPAIGN_CONTENT];
61 8
        $this->tracking_params_campaign_medium = $parameters[AzineEmailExtension::TRACKING_PARAM_CAMPAIGN_MEDIUM];
62 8
        $this->tracking_params_campaign_name = $parameters[AzineEmailExtension::TRACKING_PARAM_CAMPAIGN_NAME];
63 8
        $this->tracking_params_campaign_source = $parameters[AzineEmailExtension::TRACKING_PARAM_CAMPAIGN_SOURCE];
64 8
        $this->tracking_params_campaign_term = $parameters[AzineEmailExtension::TRACKING_PARAM_CAMPAIGN_TERM];
65 8
    }
66
67
    /**
68
     * @param string $templateBaseId the template used for rendering the email (without the .html.twig or .txt.twig extension)
69
     * @param array $campaignParams the campaign-parameters used for this email
70
     * @param string the $messageId the id of the message
71
     * @param email $to to-recipient-email(s) or null
72
     * @param email $cc cc-recipient-email(s) or null
73
     * @param email $bcc bcc-recipient-email(s) or null
74
     *
75
     * @return null|string Email open tracking code for google analytics or piwik or null
76
     */
77
    public function getTrackingImgCode($templateBaseId, array $campaignParams, array $emailTemplateParams, $messageId, $to, $cc, $bcc){
78
        if($this->trackingUrlTemplate == null){
79
            return null;
80
        }
81
82
        $recipients = md5($this->merge($to, $cc, $bcc));
83
84
        if(strpos($this->trackingUrlTemplate, 'www.google-analytics.com') !== false) {
85
            $trackingUrl = $this->getGoogleAnalyticsUrl($this->trackingUrlTemplate, $templateBaseId, $campaignParams, $emailTemplateParams, $messageId, $recipients);
86
        } else {
87
            $trackingUrl = $this->getPiwikUrl($this->trackingUrlTemplate, $templateBaseId, $campaignParams, $emailTemplateParams, $messageId, $recipients);
88
        }
89
90
        // return the html code for the tracking image
91
        $imgTrackingCode = sprintf($this->imageHtmlCode, $trackingUrl);
92
        return $imgTrackingCode;
93
    }
94
95
    /**
96
     * concatenate all recipients into an array and implode with ';' to a string
97
     * @param string|array $to
98
     * @param string|array $cc
99
     * @param string|array $bcc
100
     * @return string
101
     */
102
    protected function merge($to, $cc, $bcc){
103
        if($to && !is_array($to)){
104
            $to = array($to);
105
        }
106
        if(!is_array($cc)){
107
            $cc = array($cc);
108
        }
109
        if(!is_array($bcc)){
110
            $bcc = array($bcc);
111
        }
112
        $all = array_merge($to, $cc, $bcc);
113
114
        return implode(";", $all);
115
    }
116
117
    /**
118
     * Build tracking image code with an URL according to these sources:
119
     * http://dyn.com/blog/tracking-email-opens-via-google-analytics/
120
     * https://developers.google.com/analytics/devguides/collection/protocol/v1/email#protocol
121
     *
122
     * @param string $baseUrl string something like: https://www.google-analytics.com/collect?v=1&cm=email&t=event&ec=email&ea=open&tid=TRACKING_ID replace the TRACKING_ID with your google analytics tracking ID.
123
     * @param string $templateBaseId
124
     * @param array $campaignParams
125
     * @param array $emailTemplateParams
126
     * @param string $messageId
127
     * @param string|array $recipients
128
     */
129
    protected function getGoogleAnalyticsUrl($baseUrl, $templateBaseId, array $campaignParams, array $emailTemplateParams, $messageId, $recipients){
2 ignored issues
show
Unused Code introduced by
The parameter $emailTemplateParams is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
Unused Code introduced by
The parameter $messageId is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
130
        $url = $baseUrl.
131
            "&uid=".$recipients.                              // anonymized id generated from the concatenated string of all recipients email addresses
132
            "&cid=".Uuid::uuid4()->toString().                // random UUID
133
            "&el=".$recipients.                               // anonymized id generated from the concatenated string of all recipients email addresses
134
            "&dp=/email/".$templateBaseId.                    // the email-template used for this email
135
            "&cs=".$this->getCampaignSource($campaignParams, $templateBaseId). // campaing source for this email
0 ignored issues
show
Documentation introduced by
$campaignParams is of type array, but the function expects a string.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
136
            "&cn=".$this->getCampaignName($campaignParams).   // campaign name for this email
137
            "&z=".microtime();                                // cache buster
138
139
        return $url;
140
    }
141
142
    /**
143
     * Build tracking image code with an URL according to these sources:
144
     *
145
     *
146
     * @param string $baseUrl string something like: https://your.host.com/piwik-directory/piwik.php?&rec=1&bots=1&e_c=email&e_a=open&e_v=1&idsite=SITE_ID replace the path to your piwik.php and the SITE_ID according to your needs.
147
     * @param string $templateBaseId string
148
     * @param array $campaignParams
149
     * @param array $emailTemplateParams
150
     * @param string $messageId
151
     * @param string $recipients
152
     */
153
    protected function getPiwikUrl($baseUrl, $templateBaseId, array $campaignParams, array $emailTemplateParams, $messageId, $recipients){
2 ignored issues
show
Unused Code introduced by
The parameter $emailTemplateParams is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
Unused Code introduced by
The parameter $messageId is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
154
        $url = $baseUrl.
155
            "&_id=".substr($recipients, 0, 16).                     // user: 16 characters hexadecimal string
156
            "&url=/email/".$templateBaseId.                         // document path
157
            "&rand=".microtime().                                   // cache buster
158
            "&e_n=".$this->getCampaignSource($campaignParams, $templateBaseId).      // event name => will be categorized with the / => e.g. email / newsletter
0 ignored issues
show
Documentation introduced by
$campaignParams is of type array, but the function expects a string.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
159
            "&action_name=".$this->getCampaignName($campaignParams);// action name
160
161
        return $url;
162
    }
163
164
    /**
165
     * @param string $campaignParams
166
     * @param string $templateId
167
     * @return string if no source-value is defined in the $campaignParams, $templateId will be used.
168
     */
169
    protected function getCampaignSource($campaignParams, $templateId){
170
        if(array_key_exists($this->tracking_params_campaign_source, $campaignParams)){
171
            return $campaignParams[$this->tracking_params_campaign_source];
172
        }
173
        return $templateId;
174
    }
175
176
    /**
177
     * @param array $campaignParams
178
     * @return string if no name-value is defined in the $campaignParams, date("y-m-d") will be used.
179
     */
180
    protected function getCampaignName($campaignParams){
181
        if(array_key_exists($this->tracking_params_campaign_name, $campaignParams)){
182
            return $campaignParams[$this->tracking_params_campaign_name];
183
        }
184
        return date("y-m-d");
185
    }
186
}