Completed
Push — master ( e0c65e...447f65 )
by Roberto
09:14 queued 06:39
created

Mail::send()   B

Complexity

Conditions 4
Paths 5

Size

Total Lines 24
Code Lines 19

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 5
CRAP Score 10.3998

Importance

Changes 0
Metric Value
dl 0
loc 24
ccs 5
cts 19
cp 0.2632
rs 8.6845
c 0
b 0
f 0
cc 4
eloc 19
nc 5
nop 1
crap 10.3998
1
<?php
2
3
namespace NFePHP\Mail;
4
5
/**
6
 * Class for sending emails related to SPED services
7
 *
8
 * @category  NFePHP
9
 * @package   NFePHP\Mail\Mail
10
 * @copyright NFePHP Copyright (c) 2016
11
 * @license   http://www.gnu.org/licenses/lgpl.txt LGPLv3+
12
 * @license   https://opensource.org/licenses/MIT MIT
13
 * @license   http://www.gnu.org/licenses/gpl.txt GPLv3+
14
 * @author    Roberto L. Machado <linux.rlm at gmail dot com>
15
 * @link      http://github.com/nfephp-org/sped-mail for the canonical source repository
16
 */
17
18
use NFePHP\Mail\Base;
19
use PHPMailer;
20
use Html2Text\Html2Text;
21
22
class Mail extends Base
23
{
24
    /**
25
     * Html Body mail message
26
     * @var string
27
     */
28
    public $body;
29
    /**
30
     * Subject for email
31
     * @var string
32
     */
33
    public $subject;
34
    
35
    /**
36
     * Constructor
37
     * @param \stdClass $config
38
     */
39
    public function __construct(\stdClass $config, PHPMailer $mailer = null)
40
    {
41
        $this->mail = $mailer;
42
        if (is_null($mailer)) {
43
            $this->mail = new PHPMailer();
44
        }
45
        $this->config = $config;
46
        $this->loadService($config);
47
        $this->fields = new \stdClass();
48
        $this->fields->destinatario = '';
49
        $this->fields->data = '';
50
        $this->fields->numero = '';
51
        $this->fields->valor = 0;
52
        $this->fields->chave = '';
53
        $this->fields->data = '';
54
        $this->fields->correcao = '';
55
        $this->fields->conduso = '';
56
    }
57
    
58
    /**
59
     * Load parameters to PHPMailer class
60
     * @param \stdClass $config
61
     */
62
    protected function loadService(\stdClass $config)
63
    {
64
        $this->mail->CharSet = 'UTF-8';
65
        $this->mail->isSMTP();
66
        $this->mail->Host = $config->host;
67
        $this->mail->SMTPAuth = true;
68
        $this->mail->Username = $config->user;
69
        $this->mail->Password = $config->password;
70
        $this->mail->SMTPSecure = $config->secure;
71
        $this->mail->Port = $config->port;
72
        $this->mail->setFrom($config->from, $config->fantasy);
73
        $this->mail->addReplyTo($config->replyTo, $config->replyName);
74
    }
75
    
76
    /**
77
     * Sets a template for body mail
78
     * If no template is passed, it will be used a standard template
79
     * see Base::class
80
     * @param string $htmlTemplate
81
     */
82 1
    public function loadTemplate($htmlTemplate)
83
    {
84 1
        if ($htmlTemplate != '') {
85 1
            $this->template = $htmlTemplate;
86
        }
87 1
    }
88
    
89
    /**
90
     * Load the documents to send
91
     * XML document is required, but PDF is not
92
     * @param string $xml content or path NFe, CTe or CCe in XML
93
     * @param string $pdf content or path document from NFe, CTe or CCe
94
     */
95 2
    public function loadDocuments($xml, $pdf = '')
96
    {
97 2
        $this->xml = $xml;
98 2
        $this->pdf = $pdf;
99 2
        if (is_file($xml)) {
100
            $this->xml = file_get_contents($xml);
101
        }
102 2
        if (is_file($pdf)) {
103
            $this->pdf = file_get_contents($pdf);
104
        }
105
        //get xml data
106 2
        $this->getXmlData($this->xml);
107 1
    }
108
    
109
    /**
110
     * Search xml for data
111
     * @param string $xml
112
     * @throws \InvalidArgumentException
113
     */
114 2
    protected function getXmlData($xml)
115
    {
116 2
        $dom = new \DOMDocument('1.0', 'UTF-8');
117 2
        $dom->preserveWhiteSpace = false;
118 2
        $dom->loadXML($xml);
119 2
        $root = $dom->documentElement;
120 2
        $name = $root->tagName;
121 2
        $dest = $dom->getElementsByTagName('dest')->item(0);
122 2
        $ide = $dom->getElementsByTagName('ide')->item(0);
123
        switch ($name) {
124 2
            case 'nfeProc':
125 1
            case 'NFe':
126 1
                $type = 'NFe';
127 1
                $this->fields->numero = $ide->getElementsByTagName('nNF')->item(0)->nodeValue;
128 1
                $this->fields->valor = $dom->getElementsByTagName('vNF')->item(0)->nodeValue;
129 1
                $this->fields->data = $ide->getElementsByTagName('dhEmi')->item(0)->nodeValue;
130 1
                $this->subject = "NFe n. " . $this->fields->numero . " - " . $this->config->fantasy;
131 1
                break;
132 1
            case 'cteProc':
133 1
            case 'CTe':
134
                $type = 'CTe';
135
                $this->fields->numero = $ide->getElementsByTagName('nCT')->item(0)->nodeValue;
136
                $this->fields->valor = $dom->getElementsByTagName('vRec')->item(0)->nodeValue;
137
                $this->fields->data = $ide->getElementsByTagName('dhEmi')->item(0)->nodeValue;
138
                $this->subject = "CTe n. " . $this->fields->numero . " - " . $this->config->fantasy;
139
                break;
140 1
            case 'procEventoNFe':
141 1
            case 'procEventoCTe':
142
                $type = 'CCe';
143
                $this->fields->chave = $dom->getElementsByTagName('chNFe')->item(0)->nodeValue;
144
                $this->fields->data = $dom->getElementsByTagName('dhEvento')->item(0)->nodeValue;
145
                $this->fields->correcao = $dom->getElementsByTagName('xCorrecao')->item(0)->nodeValue;
146
                $this->fields->conduso = $dom->getElementsByTagName('xCondUso')->item(0)->nodeValue;
147
                if (empty($this->fields->chave)) {
148
                    $this->fields->chave = $dom->getElementsByTagName('chCTe')->item(0)->nodeValue;
149
                }
150
                $this->subject = "Carta de Correção " . $this->config->fantasy;
151
                break;
152
            default:
153 1
                $type = '';
154
        }
155
        //get email adresses from xml, if exists
156
        //may have one address in <dest><email>
157 2
        if (!empty($dest)) {
158 1
            $this->fields->destinatario = $dest->getElementsByTagName('xNome')->item(0)->nodeValue;
159 1
            $email = !empty($dest->getElementsByTagName('email')->item(0)->nodeValue) ?
160 1
                $dest->getElementsByTagName('email')->item(0)->nodeValue : '';
161
        }
162 2
        if (!empty($email)) {
163 1
            $this->addresses[] = $email;
164
        }
165
        //may have others in <obsCont xCampo="email"><xTexto>[email protected]</xTexto>
166 2
        $obs = $dom->getElementsByTagName('obsCont');
167 2
        foreach ($obs as $ob) {
168
            if (strtoupper($ob->getAttribute('xCampo')) === 'EMAIL') {
169
                $this->addresses[] = $ob->getElementsByTagName('xTexto')->item(0)->nodeValue;
170
            }
171
        }
172
        //xml may be a NFe or a CTe or a CCe nothing else
173 2
        if ($type != 'NFe' && $type != 'CTe' && $type != 'CCe') {
174
            $msg = "Você deve passar apenas uma NFe ou um CTe ou um CCe. "
175 1
                    . "Esse documento não foi reconhecido.";
176 1
            throw new \InvalidArgumentException($msg);
177
        }
178 1
        $this->type = $type;
179 1
    }
180
    
181
    
182
    /**
183
     * Set all addresses including those that exists in the xml document
184
     * Send email only to listed addresses ignoring all email addresses in xml
185
     * @param array $addresses
186
     */
187 1
    protected function setAddresses(array $addresses = [])
188
    {
189 1
        if (!empty($addresses)) {
190 1
            $this->addresses = array_merge($this->addresses, $addresses);
191
        }
192 1
        $this->removeInvalidAdresses();
193 1
    }
194
    
195
    /**
196
     * Send mail
197
     * If no parameter was passed, only the email address contained in
198
     * the xml will be used
199
     * @param array $addresses
200
     * @return boolean
201
     * @throws \RuntimeException
202
     */
203 1
    public function send(array $addresses = [])
204
    {
205 1
        $this->setAddresses($addresses);
206 1
        if (empty($this->addresses)) {
207 1
            $msg = 'Não foram passados endereços de email validos !!';
208 1
            throw new \RuntimeException($msg);
209
        }
210
        foreach ($this->addresses as $address) {
211
            $this->mail->addAddress($address);
212
        }
213
        $body = $this->render();
214
        $this->mail->isHTML(true);
215
        $this->mail->Subject = $this->subject;
216
        $this->mail->Body = $body;
217
        $this->mail->AltBody = Html2Text::convert($body);
218
        $this->attach();
219
        if (!$this->mail->send()) {
220
            $msg = 'A mensagem não pode ser enviada. Mail Error: ' . $this->mail->ErrorInfo;
221
            throw new \RuntimeException($msg);
222
        }
223
        $this->mail->ClearAllRecipients();
224
        $this->mail->ClearAttachments();
225
        return true;
226
    }
227
    
228
    /**
229
     * Configure and send documents
230
     * @param \stdClass $config
231
     * @param type $xml
232
     * @param type $pdf
233
     * @param array $addresses
234
     * @param type $htmltemplate
235
     * @param PHPMailer $mailer
236
     * @return Mail
237
     */
238
    public static function sendMail(
239
        \stdClass $config,
240
        $xml,
241
        $pdf = '',
242
        array $addresses = [],
243
        $htmltemplate = '',
244
        PHPMailer $mailer = null
245
    ) {
246
        $mail = new static($config, $mailer);
247
        $mail->loadDocuments($xml, $pdf);
248
        $mail->loadTemplate($htmltemplate);
249
        $mail->send($addresses);
250
        return $mail;
251
    }
252
}
253