Статьи

Отправка электронных писем в приложение Laravel

Вступление

В инструментах управления проектами или поддержки вы можете многое увидеть: вы можете ответить на сообщение электронной почты, и оно автоматически отображается в веб-приложении. Каким-то образом эти инструменты смогли доставить эти электронные письма прямо в их систему.

В этой статье мы рассмотрим, как мы можем направлять электронные письма в наше приложение Laravel 4. Для этого мы начнем с нового проекта Laravel 4, установленного через Composer, как показано здесь .

composer create-project laravel/laravel your-project-name --prefer-dist

Создание команды Artisan

Чтобы иметь возможность помещать нашу электронную почту в наше приложение, мы каким-то образом должны направлять электронную почту через командную строку в наше приложение. К счастью, у Laravel есть инструмент командной строки под названием Artisan, который способен выполнять несколько задач. Чтобы увидеть список всех задач, которые Artisan может выполнить, вы можете запустить php artisan list

В этом случае мы хотим, чтобы он выполнял очень специфическую задачу: принимал необработанные электронные письма и использовал их в нашем приложении. К сожалению, это не одна из основных функций, с которой Artisan может справиться. Мы можем легко расширить его с помощью новой команды: php artisan email:parse Затем мы просто запустим Artisan и выполним определенную задачу, которая в данном случае называется email:parse

Наш первый шаг — создать эту команду. Вы можете создавать новые команды с помощью собственной команды Artisan для создания новых команд. Просто запустите следующее в корне вашего проекта:

 php artisan command:make EmailParserCommand

Если все прошло гладко, теперь вы найдете файл с именем EmailParserCommand.phpapp/commands Откройте его в своем любимом редакторе и посмотрите на свойства $name$description Мы можем настроить это к тому, что мы хотим. Дав ему четкое имя и описание, команда будет хорошо перечислена в списке команд ремесленников.

Я изменил это, например:

 /**
 * The console command name.
 *
 * @var string
 */
protected $name = 'email:parse';

/**
 * The console command description.
 *
 * @var string
 */
protected $description = 'Parses an incoming email.';

Зарегистрировать команду

Когда мы запустим php artisan email:parse Наш следующий шаг — убедиться, что эта команда зарегистрирована в Artisan. Давайте откроем файл app/start/artisan.phpArtisan::add(new EmailParserCommand); до конца файла зарегистрировать нашу вновь созданную команду. Теперь мы можем снова запустить команду list, чтобы увидеть нашу команду email:parse Обратите внимание, что ваше только что заполненное имя и описание отображаются здесь.

Получить сырое письмо

Всякий раз, когда команда вызывается через Artisan, она всегда вызывает метод fire Итак, изначально, мы должны добавить наш разбор электронной почты здесь. В настоящее время электронная почта находится в нашем потоке ввода-вывода, который мы можем получить из php://stdin Мы открываем этот поток ввода-вывода, а затем собираем электронную почту небольшими частями, пока не прочитаем весь поток.

 /**
 * Execute the console command.
 *
 * @return void
 */
public function fire()
{
    // read from stdin
    $fd = fopen("php://stdin", "r");
    $rawEmail = "";
    while (!feof($fd)) {
        $rawEmail .= fread($fd, 1024);
    }
    fclose($fd);
}

Письмо, отправленное нашей команде Artisan, теперь находится в переменной $rawEmail Это целое письмо, содержащее заголовки, текст и любые вложения.

Разбор электронной почты

Сейчас у нас есть сырое письмо, но я бы предпочел, чтобы оно было в нескольких частях. Я хотел бы получить заголовки, такие как тема и тело сообщения. Мы могли бы написать собственный код, который разделяет все эти части, но кто-то уже создал пакет, который мы можем использовать в нашем приложении. Этот пакет может разбить всю нашу электронную почту на логические части. Добавьте следующую строку в ваш файл composer.jsoncomposer update

 "messaged/php-mime-mail-parser": "dev-master"

Теперь нам нужно убедиться, что мы действительно можем использовать этот пакет в нашей команде, поэтому мы снова открываем наш app/command/EmailParserCommand.php

 use MimeMailParser\Parser;

Теперь мы можем разобрать нашу сырую электронную почту на отдельные части. Добавьте следующие строки кода в конец метода огня.

 $parser = new Parser();
$parser->setText($rawEmail);

$to = $parser->getHeader('to');
$from = $parser->getHeader('from');
$subject = $parser->getHeader('subject');
$text = $parser->getMessageBody('text');

Сначала мы создаем новый парсер. Затем мы устанавливаем необработанное электронное письмо как текст нашего синтаксического анализатора и, наконец, мы вызываем все виды различных методов для получения данных из заголовков или тела.

Теперь вы можете легко хранить свою электронную почту в базе данных. Например, если у вас есть объект электронной почты, вы можете сохранить его в своей базе данных:

 $email = new Email;
$email->to = $parser->getHeader('to');
$email->from = $parser->getHeader('from');
$email->subject = $parser->getHeader('subject');
$email->text = $parser->getMessageBody('text');
$email->save();

Работа с вложениями

Вы можете даже хотеть хранить любые вложения, которые прикреплены к электронной почте на вашем сервере. Класс анализатора электронной почты может обрабатывать любые доступные вложения. Сначала снова добавьте следующие строки в начало класса app/command/EmailParserCommand.php

 use Illuminate\Filesystem\Filesystem;
use MimeMailParser\Attachment;

Теперь мы должны расширить наш метод fire с некоторым кодом, который будет обрабатывать вложения:

 $attachments = $parser->getAttachments();

$filesystem = new Filesystem;
foreach ($attachments as $attachment) {
	$filesystem->put(public_path() . '/uploads/' . $attachment->getFilename(), $attachment->getContent());
}

Давайте посмотрим, что на самом деле делает эта часть. Первая строка извлекает вложения из письма. Переменная $attachments Далее мы убедимся, что создан новый объект FileSystem, который будет обрабатывать сохранение файлов на нашем сервере. Затем мы начинаем перебирать все вложения. Мы вызываем метод put В этом случае мы хотим добавить файл в каталог public/uploads Второй параметр — это содержимое самого файла.

Это оно! Ваши файлы теперь хранятся в public/uploads Просто убедитесь, что ваш почтовый сервер действительно может добавлять файлы в этот каталог, устанавливая правильные разрешения.

Настройка нашего почтового сервера

До сих пор мы готовили наше приложение для извлечения, разделения и сохранения нашей электронной почты. Однако код совершенно бесполезен, если вы не знаете, как на самом деле отправить электронное письмо своей недавно созданной команде Artisan.

Ниже вы найдете различные способы передачи ваших писем в ваше приложение, в зависимости от того, какие инструменты или почтовые серверы вы используете. Например, я хочу переслать [email protected]/var/www/supportcenter
Обратите внимание, что в фактической команде, которую вы увидите ниже, я добавлял --env=local Если вы находитесь в производстве, вы, конечно, можете удалить эту часть.

CPanel

Если вы используете CPanel, вы можете щелкнуть в общем меню на серверах forwarders Добавьте новый сервер пересылки и определите, какой адрес вы бы хотели перенаправить в свое приложение. Нажмите на дополнительные настройки и выберите параметры pipe to program
В поле ввода вы можете вставить следующую строку:

 /usr/bin/php -q /var/www/supportcenter/artisan --env=local email:parse

Обратите внимание, что CPanel использует путь относительно вашего домашнего каталога.

Exim

Если в Exim , откройте файл /etc/valiases/peternijssen.nl
Убедитесь, что в этом файле присутствует следующая строка:

 support@peternijssen.nl: “| /usr/bin/php -q /var/www/supportcenter/artisan --env=local email:parse

Запустите newaliases

постфикс

В Postfix убедитесь, что следующие строки присутствуют и не прокомментированы в вашем файле /etc/postfix/main.cf

 alias_maps = hash:/etc/aliases
alias_database = hash:/etc/aliases  

Если вам пришлось изменить файл, перезагрузите postfix, запустив service postfix reload

Теперь мы можем создать новый псевдоним, который будет передан в наше приложение.
Откройте /etc/aliases

 support@peternijssen.nl: "| /usr/bin/php -q /var/www/supportcenter/artisan --env=local email:parse"

Запустите newaliases

Отправить письмо

В Sendmail вы должны сначала создать псевдоним в /etc/aliases

 support: "| /usr/bin/php -q /var/www/supportcenter/artisan --env=local email:parse"

Запустите newaliases Далее, убедитесь, что файл Artisan имеет значение chmod

Наконец, ссылка на файл ремесленника и сам php в / etc / smrsh

 ln -s /usr/bin/php /etc/smrsh/php
ln -s /var/www/supportcenter/artisan /etc/smrsh/pipe.php

QMail

В зависимости от вашей установки, вы должны убедиться, что присутствует следующий файл:

 /usr/local/qmail/mailnames/peternijssen.nl/support/.qmail

или:

 /usr/local/qmail/mailnames/peternijssen.nl/.qmail-support

Откройте любой файл и добавьте следующую строку в качестве содержимого:

 support@peternijssen.nl: "| /usr/bin/php -q /var/www/supportcenter/artisan --env=local email:parse"

Вывод

Любая платформа, в которой есть инструмент командной строки, сможет обрабатывать ваши электронные письма. Код, приведенный здесь, является просто базовой настройкой. В зависимости от вашего проекта вы можете разрешить отправку электронной почты в ваше приложение только определенным адресам электронной почты. Убедитесь, что вы уже отфильтровываете электронные письма в таких инструментах, как postfix, прежде чем отправлять в приложение.

Если вы хотите работать с какой-то системой заявок, вы можете легко попытаться извлечь идентификатор заявки в службу поддержки из темы письма и, основываясь на этом, выполнить несколько различных действий с электронной почтой.

Внимательно изучите файл журнала вашего почтового сервера. Это даст вам некоторые подсказки, когда реальный трубопровод не сможет решить, как его решить.