Merge pull request #16263 from eileenmcnaughton/ids_3
[civicrm-core.git] / CRM / SMS / Form / Upload.php
CommitLineData
6a488035
TO
1<?php
2/*
3 +--------------------------------------------------------------------+
bc77d7c0 4 | Copyright CiviCRM LLC. All rights reserved. |
6a488035 5 | |
bc77d7c0
TO
6 | This work is published under the GNU AGPLv3 license with some |
7 | permitted exceptions and without any warranty. For full license |
8 | and copyright information, see https://civicrm.org/licensing |
6a488035 9 +--------------------------------------------------------------------+
d25dd0ee 10 */
6a488035
TO
11
12/**
13 *
14 * @package CRM
ca5cec67 15 * @copyright CiviCRM LLC https://civicrm.org/licensing
6a488035
TO
16 */
17
18/**
b8c71ffa 19 * This file is used to build the form configuring mass sms details.
6a488035
TO
20 */
21class CRM_SMS_Form_Upload extends CRM_Core_Form {
22 public $_mailingID;
23
00be9182 24 public function preProcess() {
6a488035 25 $this->_mailingID = $this->get('mailing_id');
6a488035
TO
26 }
27
28 /**
c490a46a 29 * Set default values for the form.
6a488035 30 */
00be9182 31 public function setDefaultValues() {
6a488035
TO
32 $mailingID = CRM_Utils_Request::retrieve('mid', 'Integer', $this, FALSE, NULL);
33
39404680 34 // Need to differentiate new/reuse mailing, CRM-2873.
6a488035
TO
35 $reuseMailing = FALSE;
36 if ($mailingID) {
37 $reuseMailing = TRUE;
38 }
39 else {
40 $mailingID = $this->_mailingID;
41 }
42
43 $count = $this->get('count');
44 $this->assign('count', $count);
45
46 $this->set('skipTextFile', FALSE);
47
be2fb01f 48 $defaults = [];
6a488035
TO
49
50 if ($mailingID) {
51 $dao = new CRM_Mailing_DAO_Mailing();
52 $dao->id = $mailingID;
53 $dao->find(TRUE);
54 $dao->storeValues($dao, $defaults);
55
39404680
SB
56 // We don't want to retrieve template details once it is
57 // set in session.
6a488035
TO
58 $templateId = $this->get('template');
59 $this->assign('templateSelected', $templateId ? $templateId : 0);
60 if (isset($defaults['msg_template_id']) && !$templateId) {
1e035d58 61 $defaults['SMStemplate'] = $defaults['msg_template_id'];
c6327d7d 62 $messageTemplate = new CRM_Core_DAO_MessageTemplate();
6a488035
TO
63 $messageTemplate->id = $defaults['msg_template_id'];
64 $messageTemplate->selectAdd();
65 $messageTemplate->selectAdd('msg_text');
66 $messageTemplate->find(TRUE);
67
1e035d58 68 $defaults['sms_text_message'] = $messageTemplate->msg_text;
6a488035
TO
69 }
70
71 if (isset($defaults['body_text'])) {
1e035d58 72 $defaults['sms_text_message'] = $defaults['body_text'];
6a488035
TO
73 $this->set('textFile', $defaults['body_text']);
74 $this->set('skipTextFile', TRUE);
75 }
76 }
77
39404680 78 // Fix for CRM-2873.
6a488035
TO
79 if (!$reuseMailing) {
80 $textFilePath = $this->get('textFilePath');
81 if ($textFilePath &&
82 file_exists($textFilePath)
83 ) {
1e035d58 84 $defaults['sms_text_message'] = file_get_contents($textFilePath);
85 if (strlen($defaults['sms_text_message']) > 0) {
6a488035
TO
86 $this->set('skipTextFile', TRUE);
87 }
88 }
89 }
90
91 $defaults['upload_type'] = 1;
92
93 return $defaults;
94 }
95
96 /**
fe482240 97 * Build the form object.
6a488035
TO
98 */
99 public function buildQuickForm() {
100 $session = CRM_Core_Session::singleton();
353ffa53 101 $config = CRM_Core_Config::singleton();
be2fb01f 102 $options = [];
6a488035
TO
103 $tempVar = FALSE;
104
105 $this->assign('max_sms_length', CRM_SMS_Provider::MAX_SMS_CHAR);
106
107 // this seems so hacky, not sure what we are doing here and why. Need to investigate and fix
108 $session->getVars($options,
109 "CRM_SMS_Controller_Send_{$this->controller->_key}"
110 );
111
be2fb01f
CW
112 $attributes = ['onclick' => "showHideUpload();"];
113 $options = [ts('Upload Content'), ts('Compose On-screen')];
6a488035
TO
114
115 $this->addRadio('upload_type', ts('I want to'), $options, $attributes, "&nbsp;&nbsp;");
116
117 CRM_Mailing_BAO_Mailing::commonCompose($this);
118
119 $this->addElement('file', 'textFile', ts('Upload TEXT Message'), 'size=30 maxlength=60');
120 $this->setMaxFileSize(1024 * 1024);
121 $this->addRule('textFile', ts('File size should be less than 1 MByte'), 'maxfilesize', 1024 * 1024);
122 $this->addRule('textFile', ts('File must be in UTF-8 encoding'), 'utf8File');
123
be2fb01f 124 $this->addFormRule(['CRM_SMS_Form_Upload', 'formRule'], $this);
6a488035 125
be2fb01f
CW
126 $buttons = [
127 [
6ea503d4 128 'type' => 'back',
f212d37d 129 'name' => ts('Previous'),
be2fb01f
CW
130 ],
131 [
6a488035 132 'type' => 'upload',
f212d37d 133 'name' => ts('Next'),
6a488035
TO
134 'spacing' => '&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;',
135 'isDefault' => TRUE,
be2fb01f
CW
136 ],
137 [
6a488035
TO
138 'type' => 'cancel',
139 'name' => ts('Cancel'),
be2fb01f
CW
140 ],
141 ];
6a488035
TO
142
143 $this->addButtons($buttons);
144 }
145
146 public function postProcess() {
77552d44 147 $params = [];
be2fb01f 148 $uploadParams = ['from_name'];
6a488035
TO
149
150 $formValues = $this->controller->exportValues($this->_name);
151
152 foreach ($uploadParams as $key) {
a7488080 153 if (!empty($formValues[$key])) {
6a488035
TO
154 $params[$key] = $formValues[$key];
155 $this->set($key, $formValues[$key]);
156 }
157 }
158
159 if (!$formValues['upload_type']) {
160 $contents = NULL;
161 if (isset($formValues['textFile']) &&
162 !empty($formValues['textFile'])
163 ) {
164 $contents = file_get_contents($formValues['textFile']['name']);
165 $this->set($key, $formValues['textFile']['name']);
166 }
167 if ($contents) {
168 $params['body_text'] = $contents;
169 }
170 else {
171 $params['body_text'] = 'NULL';
172 }
173 }
174 else {
1e035d58 175 $text_message = $formValues['sms_text_message'];
6a488035
TO
176 $params['body_text'] = $text_message;
177 $this->set('textFile', $params['body_text']);
178 $this->set('text_message', $params['body_text']);
179 }
180
181 $params['name'] = $this->get('name');
182
183 $session = CRM_Core_Session::singleton();
184 $params['contact_id'] = $session->get('userID');
be2fb01f 185 $composeFields = [
353ffa53
TO
186 'SMStemplate',
187 'SMSsaveTemplate',
188 'SMSupdateTemplate',
189 'SMSsaveTemplateName',
be2fb01f 190 ];
6a488035 191 $msgTemplate = NULL;
39404680 192 // Mail template is composed.
6a488035 193 if ($formValues['upload_type']) {
be2fb01f 194 $composeParams = [];
6a488035 195 foreach ($composeFields as $key) {
a7488080 196 if (!empty($formValues[$key])) {
6a488035
TO
197 $composeParams[$key] = $formValues[$key];
198 $this->set($key, $formValues[$key]);
199 }
200 }
201
1e035d58 202 if (!empty($composeParams['SMSupdateTemplate'])) {
be2fb01f 203 $templateParams = [
6a488035
TO
204 'msg_text' => $text_message,
205 'is_active' => TRUE,
1e035d58 206 'is_sms' => TRUE,
be2fb01f 207 ];
6a488035 208
1e035d58 209 $templateParams['id'] = $formValues['SMStemplate'];
6a488035 210
c6327d7d 211 $msgTemplate = CRM_Core_BAO_MessageTemplate::add($templateParams);
6a488035
TO
212 }
213
1e035d58 214 if (!empty($composeParams['SMSsaveTemplate'])) {
be2fb01f 215 $templateParams = [
6a488035
TO
216 'msg_text' => $text_message,
217 'is_active' => TRUE,
1e035d58 218 'is_sms' => TRUE,
be2fb01f 219 ];
6a488035 220
1e035d58 221 $templateParams['msg_title'] = $composeParams['SMSsaveTemplateName'];
6a488035 222
c6327d7d 223 $msgTemplate = CRM_Core_BAO_MessageTemplate::add($templateParams);
6a488035
TO
224 }
225
226 if (isset($msgTemplate->id)) {
227 $params['msg_template_id'] = $msgTemplate->id;
228 }
229 else {
1e035d58 230 $params['msg_template_id'] = CRM_Utils_Array::value('SMStemplate', $formValues);
6a488035
TO
231 }
232 $this->set('template', $params['msg_template_id']);
233 }
234
77552d44 235 $params['id'] = $this->_mailingID;
6a488035 236
39404680 237 // Build SMS in mailing table.
77552d44 238 CRM_Mailing_BAO_Mailing::create($params);
6a488035
TO
239 }
240
241 /**
fe482240 242 * Validation.
6a488035 243 *
901b501a
TO
244 * @param array $params
245 * (ref.) an assoc array of name/value pairs.
6a488035 246 *
77b97be7
EM
247 * @param $files
248 * @param $self
249 *
72b3a70c
CW
250 * @return bool|array
251 * mixed true or array of errors
6a488035 252 */
00be9182 253 public static function formRule($params, $files, $self) {
a7488080 254 if (!empty($_POST['_qf_Import_refresh'])) {
6a488035
TO
255 return TRUE;
256 }
be2fb01f 257 $errors = [];
6a488035
TO
258 $template = CRM_Core_Smarty::singleton();
259
6a488035
TO
260 $domain = CRM_Core_BAO_Domain::getDomain();
261
262 $mailing = new CRM_Mailing_BAO_Mailing();
263 $mailing->id = $self->_mailingID;
264 $mailing->find(TRUE);
265
266 $session = CRM_Core_Session::singleton();
be2fb01f 267 $values = [
6ea503d4 268 'contact_id' => $session->get('userID'),
6a488035 269 'version' => 3,
be2fb01f 270 ];
6a488035
TO
271 require_once 'api/api.php';
272 $contact = civicrm_api('contact', 'get', $values);
273
39404680 274 // CRM-4524.
6a488035
TO
275 $contact = reset($contact['values']);
276
be2fb01f 277 $verp = array_flip(['optOut', 'reply', 'unsubscribe', 'resubscribe', 'owner']);
6a488035
TO
278 foreach ($verp as $key => $value) {
279 $verp[$key]++;
280 }
281
be2fb01f 282 $urls = array_flip(['forward', 'optOutUrl', 'unsubscribeUrl', 'resubscribeUrl']);
6a488035
TO
283 foreach ($urls as $key => $value) {
284 $urls[$key]++;
285 }
286
6a488035
TO
287 $skipTextFile = $self->get('skipTextFile');
288
289 if (!$params['upload_type']) {
290 if ((!isset($files['textFile']) || !file_exists($files['textFile']['tmp_name']))) {
291 if (!($skipTextFile)) {
292 $errors['textFile'] = ts('Please provide a Text');
293 }
294 }
295 }
296 else {
1e035d58 297 if (empty($params['sms_text_message'])) {
298 $errors['sms_text_message'] = ts('Please provide a Text');
6a488035
TO
299 }
300 else {
a7488080 301 if (!empty($params['text_message'])) {
6a488035
TO
302 $messageCheck = CRM_Utils_Array::value('text_message', $params);
303 if ($messageCheck && (strlen($messageCheck) > CRM_SMS_Provider::MAX_SMS_CHAR)) {
be2fb01f 304 $errors['text_message'] = ts("You can configure the SMS message body up to %1 characters", [1 => CRM_SMS_Provider::MAX_SMS_CHAR]);
6a488035
TO
305 }
306 }
307 }
1e035d58 308 if (!empty($params['SMSsaveTemplate']) && empty($params['SMSsaveTemplateName'])) {
309 $errors['SMSsaveTemplateName'] = ts('Please provide a Template Name.');
6a488035
TO
310 }
311 }
312
313 if (($params['upload_type'] || file_exists(CRM_Utils_Array::value('tmp_name', $files['textFile']))) ||
314 (!$params['upload_type'] && $params['text_message'])
315 ) {
316
317 if (!$params['upload_type']) {
318 $str = file_get_contents($files['textFile']['tmp_name']);
319 $name = $files['textFile']['name'];
320 }
321 else {
1e035d58 322 $str = $params['sms_text_message'];
6a488035
TO
323 $name = 'text message';
324 }
325
be2fb01f 326 $dataErrors = [];
6a488035 327
39404680
SB
328 // Do a full token replacement on a dummy verp, the current
329 // contact and domain, and the first organization.
6a488035 330
6a488035
TO
331 // here we make a dummy mailing object so that we
332 // can retrieve the tokens that we need to replace
333 // so that we do get an invalid token error
334 // this is qute hacky and I hope that there might
335 // be a suggestion from someone on how to
336 // make it a bit more elegant
337
353ffa53
TO
338 $dummy_mail = new CRM_Mailing_BAO_Mailing();
339 $mess = "body_text";
6a488035 340 $dummy_mail->$mess = $str;
353ffa53 341 $tokens = $dummy_mail->getTokens();
6a488035
TO
342
343 $str = CRM_Utils_Token::replaceSubscribeInviteTokens($str);
344 $str = CRM_Utils_Token::replaceDomainTokens($str, $domain, NULL, $tokens['text']);
345 $str = CRM_Utils_Token::replaceMailingTokens($str, $mailing, NULL, $tokens['text']);
346 $str = CRM_Utils_Token::replaceOrgTokens($str, $org);
347 $str = CRM_Utils_Token::replaceActionTokens($str, $verp, $urls, NULL, $tokens['text']);
348 $str = CRM_Utils_Token::replaceContactTokens($str, $contact, NULL, $tokens['text']);
349
350 $unmatched = CRM_Utils_Token::unmatchedTokens($str);
351 $contentCheck = CRM_Utils_String::htmlToText($str);
352
353 if (!empty($unmatched) && 0) {
354 foreach ($unmatched as $token) {
355 $dataErrors[] = '<li>' . ts('Invalid token code') . ' {' . $token . '}</li>';
356 }
357 }
358 if (strlen($contentCheck) > CRM_SMS_Provider::MAX_SMS_CHAR) {
be2fb01f 359 $dataErrors[] = '<li>' . ts('The body of the SMS cannot exceed %1 characters.', [1 => CRM_SMS_Provider::MAX_SMS_CHAR]) . '</li>';
6a488035
TO
360 }
361 if (!empty($dataErrors)) {
be2fb01f 362 $errors['textFile'] = ts('The following errors were detected in %1:', [
408b79bf 363 1 => $name,
be2fb01f 364 ]) . ' <ul>' . implode('', $dataErrors) . '</ul>';
6a488035
TO
365 }
366 }
367
c6327d7d 368 $templateName = CRM_Core_BAO_MessageTemplate::getMessageTemplates();
1e035d58 369 if (!empty($params['SMSsaveTemplate']) && in_array(CRM_Utils_Array::value('SMSsaveTemplateName', $params), $templateName)
6a488035 370 ) {
1e035d58 371 $errors['SMSsaveTemplate'] = ts('Duplicate Template Name.');
6a488035
TO
372 }
373 return empty($errors) ? TRUE : $errors;
374 }
375
376 /**
fe482240 377 * Display Name of the form.
6a488035 378 *
6a488035
TO
379 *
380 * @return string
381 */
382 public function getTitle() {
383 return ts('SMS Content');
384 }
96025800 385
5ec6b0ad
TM
386 /**
387 * List available tokens for this form.
388 *
389 * @return array
390 */
391 public function listTokens() {
392 $tokens = CRM_Core_SelectValues::contactTokens();
393 return $tokens;
394 }
395
6a488035 396}