170 while ($arFile = $rsFile->Fetch())
172 $filesSize += $arFile[
'FILE_SIZE'];
174 if ($arFileName[0] == $arSavedName[0] && $arFileName[1] == $arSavedName[1])
176 $arSameNames[$arSavedName[2]] =
true;
180 $max_files_size = COption::GetOptionString(
'subscribe',
'max_files_size') * 1024 * 1024;
181 if ($max_files_size > 0)
183 $filesSize += $file[
'size'];
184 if ($filesSize > $max_files_size)
186 $this->LAST_ERROR =
GetMessage(
'class_post_err_files_size', [
187 '#MAX_FILES_SIZE#' => CFile::FormatSize($max_files_size),
194 while (array_key_exists($arFileName[2], $arSameNames))
199 if ($arFileName[2] > 0)
201 $file[
'name'] = $arFileName[0] .
'(' . ($arFileName[2]) .
')' . $arFileName[1];
205 $file[
'MODULE_ID'] =
'subscribe';
206 $fid = intval(CFile::SaveFile($file,
'subscribe',
true,
true));
207 if (($fid > 0) &&
$DB->Query(
'INSERT INTO b_posting_file (POSTING_ID, FILE_ID) VALUES (' .
$ID .
' ,' . $fid .
')'))
213 $this->LAST_ERROR =
GetMessage(
'class_post_err_att');
446 $post_rub = static::GetRubricList($post_arr[
'ID']);
447 while ($post_rub_arr = $post_rub->Fetch())
449 $aPostRub[] = $post_rub_arr[
'ID'];
455 'RUBRIC_MULTI' => $aPostRub,
458 'FORMAT' => $post_arr[
'SUBSCR_FORMAT'],
459 'EMAIL' => $post_arr[
'EMAIL_FILTER'],
462 while (($subscr_arr = $subscr->Fetch()))
464 $aEmail[] = $subscr_arr[
'EMAIL'];
469 $post_grp = static::GetGroupList($post_arr[
'ID']);
470 while ($post_grp_arr = $post_grp->Fetch())
472 $aPostGrp[] = $post_grp_arr[
'ID'];
475 if (
count($aPostGrp) > 0)
477 $user = CUser::GetList(
479 [
'GROUP_MULTI' => $aPostGrp,
'ACTIVE' =>
'Y',
'EMAIL' => $post_arr[
'EMAIL_FILTER']]
481 while (($user_arr =
$user->Fetch()))
483 $aEmail[] = $user_arr[
'EMAIL'];
488 $BCC = $post_arr[
'BCC_FIELD'];
489 if ($post_arr[
'DIRECT_SEND'] ==
'Y')
491 $BCC .= ($BCC ?
',' :
'') . $post_arr[
'TO_FIELD'];
495 $BCC = str_replace(
"\r\n",
"\n", $BCC);
496 $BCC = str_replace(
"\n",
',', $BCC);
497 $aBcc = explode(
',', $BCC);
498 foreach ($aBcc as $bccEmail)
500 $bccEmail = trim($bccEmail);
501 if ($bccEmail !==
'')
503 $aEmail[] = $bccEmail;
508 $aEmail = array_unique($aEmail);
520 [
'AUTO_SEND_TIME' =>
'ASC',
'ID' =>
'ASC'],
521 [
'STATUS_ID' =>
'P',
'AUTO_SEND_TIME_2' => ConvertTimeStamp(
false,
'FULL')]
523 while ($arPosts = $rsPosts->Fetch())
527 $maxcount = COption::GetOptionInt(
'subscribe',
'subscribe_max_emails_per_hit') - self::$current_emails_per_hit;
537 $cPosting->SendMessage($arPosts[
'ID'], 0, $maxcount);
544 return 'CPosting::AutoSend(' .
$ID . ($limit ?
',true' :
',false') .
',"' .
$site_id .
'");';
550 $maxcount = COption::GetOptionInt(
'subscribe',
'subscribe_max_emails_per_hit') - self::$current_emails_per_hit;
553 return 'CPosting::AutoSend(' .
$ID .
',true' . (
$site_id ?
',"' .
$site_id .
'"' :
'') .
');';
562 $res = $cPosting->SendMessage(
$ID, COption::GetOptionString(
'subscribe',
'posting_interval'), $maxcount,
true);
563 if (
$res ==
'CONTINUE')
565 return 'CPosting::AutoSend(' .
$ID . ($limit ?
',true' :
',false') . (
$site_id ?
',"' .
$site_id .
'"' :
'') .
');';
578 $timeout = intval($timeout);
582 $this->LAST_ERROR =
'';
585 if (!($post_arr =
$post->Fetch()))
587 $this->LAST_ERROR .=
GetMessage(
'class_post_err_notfound');
591 if ($post_arr[
'STATUS'] !=
'P')
593 $this->LAST_ERROR .=
GetMessage(
'class_post_err_status') .
'<br>';
599 && ($post_arr[
'MSG_CHARSET'] <>
'')
600 && (mb_strtoupper($post_arr[
'MSG_CHARSET']) !== mb_strtoupper(
LANG_CHARSET))
611 if ($post_arr[
'VERSION'] <>
'2')
613 if (is_string($post_arr[
'BCC_TO_SEND']) && $post_arr[
'BCC_TO_SEND'] <>
'')
615 $a = explode(
',', $post_arr[
'BCC_TO_SEND']);
618 $e = trim($e,
" \t\n\r");
621 $DB->Query(
'INSERT INTO b_posting_email (POSTING_ID, STATUS, EMAIL) VALUES (' .
$ID .
", 'Y', '" .
$DB->ForSQL($e) .
"')",
true);
626 if (is_string($post_arr[
'ERROR_EMAIL']) && $post_arr[
'ERROR_EMAIL'] <>
'')
628 $a = explode(
',', $post_arr[
'ERROR_EMAIL']);
631 $e = trim($e,
" \t\n\r");
634 $DB->Query(
'INSERT INTO b_posting_email (POSTING_ID, STATUS, EMAIL) VALUES (' .
$ID .
", 'E', '" .
$DB->ForSQL($e) .
"')",
true);
639 if (is_string($post_arr[
'SENT_BCC']) && $post_arr[
'SENT_BCC'] <>
'')
641 $a = explode(
',', $post_arr[
'SENT_BCC']);
644 $e = trim($e,
" \t\n\r");
647 $DB->Query(
'INSERT INTO b_posting_email (POSTING_ID, STATUS, EMAIL) VALUES (' .
$ID .
", 'N', '" .
$DB->ForSQL($e) .
"')",
true);
652 $DB->Query(
"UPDATE b_posting SET VERSION='2', BCC_TO_SEND=null, ERROR_EMAIL=null, SENT_BCC=null WHERE ID=" .
$ID);
657 if ($post_arr[
'BODY_TYPE'] ==
'html' && COption::GetOptionString(
'subscribe',
'attach_images') ==
'Y')
659 $post_arr[
'BODY'] = $tools->ReplaceImages($post_arr[
'BODY']);
662 if ($post_arr[
'CHARSET'] <>
'')
664 $from_charset = $post_arr[
'MSG_CHARSET'] ?:
SITE_CHARSET;
665 $post_arr[
'BODY'] = Encoding::convertEncoding($post_arr[
'BODY'], $from_charset, $post_arr[
'CHARSET']);
666 $post_arr[
'SUBJECT'] = Encoding::convertEncoding($post_arr[
'SUBJECT'], $from_charset, $post_arr[
'CHARSET']);
667 $post_arr[
'FROM_FIELD'] = Encoding::convertEncoding($post_arr[
'FROM_FIELD'], $from_charset, $post_arr[
'CHARSET']);
671 $sBody = str_replace(
"\r\n",
"\n", $post_arr[
'BODY']);
675 preg_split(
'/(.{512}[^ ]* )/', $sBody .
' ', -1, PREG_SPLIT_DELIM_CAPTURE)
678 if (COption::GetOptionString(
'main',
'CONVERT_UNIX_NEWLINE_2_WINDOWS',
'N') ==
'Y')
680 $sBody = str_replace(
"\n",
"\r\n", $sBody);
683 if (COption::GetOptionString(
'subscribe',
'allow_8bit_chars') <>
'Y')
690 $sSubject = $post_arr[
'SUBJECT'];
691 $sFrom = $post_arr[
'FROM_FIELD'];
694 if ($post_arr[
'BODY_TYPE'] ==
'html')
701 $bHasAttachments =
false;
705 if (
count($tools->aMatches) > 0)
707 $bHasAttachments =
true;
709 $sBoundary =
'----------' . uniqid(
'');
711 'From: ' . $sFrom . $eol
712 .
'X-Bitrix-Posting: ' . $post_arr[
'ID'] . $eol
713 .
'MIME-Version: 1.0' . $eol
714 .
'Content-Type: multipart/mixed; boundary="' . $sBoundary .
'"' . $eol
715 .
'Content-Transfer-Encoding: 8bit';
718 '--' . $sBoundary . $eol
719 .
'Content-Type: ' . ($post_arr[
'BODY_TYPE'] ==
'html' ?
'text/html' :
'text/plain') . ($post_arr[
'CHARSET'] <>
'' ?
'; charset=' . $post_arr[
'CHARSET'] :
'') . $eol
720 .
'Content-Transfer-Encoding: 8bit' . $eol . $eol
723 foreach ($tools->aMatches as $attachment)
725 if ($post_arr[
'CHARSET'] <>
'')
727 $from_charset = $post_arr[
'MSG_CHARSET'] ?:
SITE_CHARSET;
728 $attachment[
'DEST'] = Encoding::convertEncoding($attachment[
'DEST'], $from_charset, $post_arr[
'CHARSET']);
731 if (COption::GetOptionString(
'subscribe',
'allow_8bit_chars') <>
'Y')
737 $name = $attachment[
'DEST'];
741 $eol .
'--' . $sBoundary . $eol
742 .
'Content-Type: ' . $attachment[
'CONTENT_TYPE'] .
'; name="' .
$name .
'"' . $eol
743 .
'Content-Transfer-Encoding: base64' . $eol
744 .
'Content-ID: <' . $attachment[
'ID'] .
'>' . $eol . $eol
747 file_get_contents($attachment[
'PATH'])
754 $maxFileSize = intval(COption::GetOptionInt(
'subscribe',
'max_file_size'));
756 while ($arFile = $rsFile->Fetch())
760 || $arFile[
'FILE_SIZE'] <= $maxFileSize
769 if (!$bHasAttachments)
771 $bHasAttachments =
true;
772 $sBoundary =
'----------' . uniqid(
'');
774 'From: ' . $sFrom . $eol
775 .
'X-Bitrix-Posting: ' . $post_arr[
'ID'] . $eol
776 .
'MIME-Version: 1.0' . $eol
777 .
'Content-Type: multipart/mixed; boundary="' . $sBoundary .
'"' . $eol
778 .
'Content-Transfer-Encoding: 8bit';
781 '--' . $sBoundary . $eol
782 .
'Content-Type: ' . ($post_arr[
'BODY_TYPE'] ==
'html' ?
'text/html' :
'text/plain') . ($post_arr[
'CHARSET'] <>
'' ?
'; charset=' . $post_arr[
'CHARSET'] :
'') . $eol
783 .
'Content-Transfer-Encoding: 8bit' . $eol . $eol
789 if ($post_arr[
'CHARSET'] <>
'')
791 $from_charset = $post_arr[
'MSG_CHARSET'] ?:
SITE_CHARSET;
792 $file_name = Encoding::convertEncoding($arFile[
'ORIGINAL_NAME'], $from_charset, $post_arr[
'CHARSET']);
796 $file_name = $arFile[
'ORIGINAL_NAME'];
800 $eol .
'--' . $sBoundary . $eol
801 .
'Content-Type: ' . $arFile[
'CONTENT_TYPE'] .
'; name="' . $file_name .
'"' . $eol
802 .
'Content-Transfer-Encoding: base64' . $eol
805 $arTempFile = CFile::MakeFileArray($arFile[
'ID']);
806 $sBody .= chunk_split(
808 file_get_contents($arTempFile[
'tmp_name'])
816 if ($bHasAttachments)
818 $sBody .= $eol .
'--' . $sBoundary .
'--' . $eol;
824 'From: ' . $sFrom . $eol
825 .
'X-Bitrix-Posting: ' . $post_arr[
'ID'] . $eol
826 .
'MIME-Version: 1.0' . $eol
827 .
'Content-Type: ' . ($post_arr[
'BODY_TYPE'] ==
'html' ?
'text/html' :
'text/plain') . ($post_arr[
'CHARSET'] <>
'' ?
'; charset=' . $post_arr[
'CHARSET'] :
'') . $eol
828 .
'Content-Transfer-Encoding: 8bit';
831 $mail_additional_parameters = trim(COption::GetOptionString(
'subscribe',
'mail_additional_parameters'));
837 if ($post_arr[
'DIRECT_SEND'] ==
'Y')
840 $arEvents =
GetModuleEvents(
'subscribe',
'BeforePostingSendMail',
true);
842 $rsEmails =
$DB->Query(
$DB->TopSql(
'
845 WHERE POSTING_ID = ' .
$ID .
" AND STATUS='Y'
848 while ($arEmail = $rsEmails->Fetch())
853 'EMAIL' => $arEmail[
'EMAIL'],
854 'SUBJECT' => $sSubject,
856 'HEADER' => $sHeader,
857 'EMAIL_EX' => $arEmail,
859 foreach ($arEvents as $arEvent)
878 $DB->Query(
"UPDATE b_posting_email SET STATUS='N' WHERE ID = " . $arEmail[
'ID']);
882 $DB->Query(
"UPDATE b_posting_email SET STATUS='E' WHERE ID = " . $arEmail[
'ID']);
885 if ($timeout > 0 && microtime(1) -
$start_time >= $timeout)
890 self::$current_emails_per_hit++;
896 $rsEmails =
$DB->Query(
$DB->TopSql(
'
899 WHERE POSTING_ID = ' .
$ID .
" AND STATUS='Y'
900 ", COption::GetOptionString(
'subscribe',
'max_bcc_count')));
903 while ($arEmail = $rsEmails->Fetch())
905 $aStep[$arEmail[
'ID']] = $arEmail[
'EMAIL'];
908 if (
count($aStep) > 0)
910 $BCC = implode(
',', $aStep);
911 $sHeaderStep = $sHeader . $eol .
'Bcc: ' . $BCC;
912 $result =
bxmail($post_arr[
'TO_FIELD'], $sSubject, $sBody, $sHeaderStep, $mail_additional_parameters,
$context);
915 $DB->Query(
"UPDATE b_posting_email SET STATUS='N' WHERE ID in (" . implode(
', ', array_keys($aStep)) .
')');
919 $DB->Query(
"UPDATE b_posting_email SET STATUS='E' WHERE ID in (" . implode(
', ', array_keys($aStep)) .
')');
920 $this->LAST_ERROR .=
GetMessage(
'class_post_err_mail') .
'<br>';
929 $STATUS = array_key_exists(
'E',
$arStatuses) ?
'E' :
'S';
930 $DATE =
$DB->GetNowFunction();
940 $DB->Query(
"UPDATE b_posting SET STATUS='" . $STATUS .
"', DATE_SENT=" . $DATE .
' WHERE ID=' .
$ID);
942 return ($STATUS ===
'P' ?
'CONTINUE' :
true);
1147 static $arSelectFields =
false;
1148 if (!$arSelectFields)
1151 'STATUS_TITLE' =>
"case when P.STATUS='S' then '" .
$DB->ForSql(
GetMessage(
'POST_STATUS_SENT')) .
"'
1152 when P.STATUS='P' then '" .
$DB->ForSql(
GetMessage(
'POST_STATUS_PART')) .
"'
1153 when P.STATUS='E' then '" .
$DB->ForSql(
GetMessage(
'POST_STATUS_ERROR')) .
"'
1154 when P.STATUS='W' then '" .
$DB->ForSql(
GetMessage(
'POST_STATUS_WAIT')) .
"'
1155 else '" .
$DB->ForSql(
GetMessage(
'POST_STATUS_DRAFT')) .
"' end",
1157 'STATUS' =>
'P.STATUS',
1158 'FROM_FIELD' =>
'P.FROM_FIELD',
1159 'TO_FIELD' =>
'P.TO_FIELD',
1160 'EMAIL_FILTER' =>
'P.EMAIL_FILTER',
1161 'SUBJECT' =>
'P.SUBJECT',
1162 'BODY_TYPE' =>
'P.BODY_TYPE',
1163 'DIRECT_SEND' =>
'P.DIRECT_SEND',
1164 'CHARSET' =>
'P.CHARSET',
1165 'MSG_CHARSET' =>
'P.MSG_CHARSET',
1166 'SUBSCR_FORMAT' =>
'P.SUBSCR_FORMAT',
1167 'TIMESTAMP_X' =>
$DB->DateToCharFunction(
'P.TIMESTAMP_X'),
1168 'DATE_SENT' =>
$DB->DateToCharFunction(
'P.DATE_SENT'),
1172 $this->LAST_ERROR =
'';
1179 if (!is_array(
$val) && ((
string)
$val ===
'' ||
$val ===
'NOT_REF'))
1184 switch (strtoupper(
$key))
1187 $arSqlSearch[] =
"P.MSG_CHARSET = '" .
$DB->ForSql(
$val) .
"'";
1195 $arSqlSearch[] =
'P.TIMESTAMP_X>=' .
$DB->CharToDateFunction(
$val,
'SHORT');
1199 $this->LAST_ERROR .=
GetMessage(
'POST_WRONG_TIMESTAMP_FROM') .
'<br>';
1205 $arSqlSearch[] =
'P.TIMESTAMP_X < ' . $helper->addDaysToDateTime(1,
$DB->CharToDateFunction(
$val,
'SHORT'));
1209 $this->LAST_ERROR .=
GetMessage(
'POST_WRONG_TIMESTAMP_TILL') .
'<br>';
1215 $arSqlSearch[] =
'P.DATE_SENT>=' .
$DB->CharToDateFunction(
$val,
'SHORT');
1219 $this->LAST_ERROR .=
GetMessage(
'POST_WRONG_DATE_SENT_FROM') .
'<br>';
1225 $arSqlSearch[] =
'P.DATE_SENT < ' . $helper->addDaysToDateTime(1,
$DB->CharToDateFunction(
$val,
'SHORT'));
1229 $this->LAST_ERROR .=
GetMessage(
'POST_WRONG_DATE_SENT_TILL') .
'<br>';
1233 $arSqlSearch[] =
GetFilterQuery([
'P.STATUS', $arSelectFields[
'STATUS_TITLE']],
$val,
'Y', [],
'N',
'N');
1248 $arSqlSearch[] =
"EXISTS (SELECT * FROM b_posting_email PE WHERE PE.POSTING_ID=P.ID AND PE.STATUS='N' AND " . $r .
')';
1252 $arSqlSearch[] = (
$val ==
'html') ?
"P.BODY_TYPE='html'" :
"P.BODY_TYPE='text'";
1258 foreach (
$val as
$i => $v)
1268 $arSqlSearch[] =
'EXISTS (SELECT * from b_posting_rubric PR WHERE PR.POSTING_ID = P.ID AND PR.LIST_RUBRIC_ID in (' . implode(
', ', $rub_id) .
'))';
1275 case 'AUTO_SEND_TIME_1':
1276 if (
$DB->IsDate(
$val,
false,
false,
'FULL'))
1278 $arSqlSearch[] =
'(P.AUTO_SEND_TIME is not null and P.AUTO_SEND_TIME>=' .
$DB->CharToDateFunction(
$val,
'FULL') .
' )';
1282 $arSqlSearch[] =
'(P.AUTO_SEND_TIME is not null and P.AUTO_SEND_TIME>=' .
$DB->CharToDateFunction(
$val,
'SHORT') .
' )';
1286 $this->LAST_ERROR .=
GetMessage(
'POST_WRONG_AUTO_FROM') .
'<br>';
1289 case 'AUTO_SEND_TIME_2':
1290 if (
$DB->IsDate(
$val,
false,
false,
'FULL'))
1292 $arSqlSearch[] =
'(P.AUTO_SEND_TIME is not null and P.AUTO_SEND_TIME<=' .
$DB->CharToDateFunction(
$val,
'FULL') .
' )';
1296 $arSqlSearch[] =
'(P.AUTO_SEND_TIME is not null and P.AUTO_SEND_TIME<=' .
$DB->CharToDateFunction(
$val,
'SHORT') .
' )';
1300 $this->LAST_ERROR .=
GetMessage(
'POST_WRONG_AUTO_TILL') .
'<br>';
1308 foreach ($aSort as
$key => $ord)
1311 $ord = (mb_strtoupper($ord) !==
'ASC' ?
'DESC' :
'ASC');
1315 $arOrder[
$key] =
'P.ID ' . $ord;
1318 $arOrder[
$key] =
'P.TIMESTAMP_X ' . $ord;
1321 $arOrder[
$key] =
'P.SUBJECT ' . $ord;
1324 $arOrder[
$key] =
'P.BODY_TYPE ' . $ord;
1327 $arOrder[
$key] =
'P.STATUS ' . $ord;
1330 $arOrder[
$key] =
'P.DATE_SENT ' . $ord;
1332 case 'AUTO_SEND_TIME':
1333 $arOrder[
$key] =
'P.AUTO_SEND_TIME ' . $ord;
1336 $arOrder[
$key] =
'P.FROM_FIELD ' . $ord;
1339 $arOrder[
$key] =
'P.TO_FIELD ' . $ord;
1345 $arOrder[
'ID'] =
'P.ID DESC';
1347 $strSqlOrder =
' ORDER BY ' . implode(
', ', $arOrder);
1349 if (!is_array($arSelect) || empty($arSelect))
1351 $arSelect = array_keys($arSelectFields);
1355 foreach ($arSelect as $selectField)
1357 if (isset($arSelectFields[$selectField]))
1359 $arSqlSelect[$selectField] = $arSelectFields[$selectField] .
' as ' . $selectField;
1364 $arSqlSelect[
'ID'] = $arSelectFields[
'ID'] .
' as ID';
1369 SELECT ' . implode(
', ', $arSqlSelect) .
'
1372 ' . $strSqlSearch .
'
1375 if (is_array($arNavStartParams))
1377 $nTopCount = (isset($arNavStartParams[
'nTopCount']) ? (int)$arNavStartParams[
'nTopCount'] : 0);
1387 $res_cnt =
$DB->Query(
'
1388 SELECT COUNT(P.ID) as C
1391 ' . $strSqlSearch .
'
1393 $res_cnt = $res_cnt->Fetch();
1395 $res->NavQuery($strSql, $res_cnt[
'C'], $arNavStartParams);