Каждый раз настраивая локальный вебсервер, сталкиваюсь с вопросом о заглушке для Sendmail.
Есть прекрасное решение для Windows: fake sendmail for windows (sendmail.exe) http://glob.com.au/sendmail/
На хабре есть статья об этом решении: PHP mail под Windows http://habrahabr.ru/post/26518/
Ещё одно решение под Windows: Test Mail Server Tool http://www.toolheap.com/test-mail-server-tool/
Так же есть статья для линуксоидов: Sendmail-заглушка для Linux http://habrahabr.ru/post/49665/
Лично мне больше понравилось решение на чистом PHP, о котором и пойдёт дальнейшее описание.
Из плюсов:
- Отсутствие сторонних сервисов
- Кроссплатформенное решение для OS на которой установлен PHP
- Минимальный размер файла заглушки
- Вся логика заглушки доступна для редактирования на PHP
- Сохранение сообщения в файле
Из минусов:
- Отсутствие пересылки на реальный почтовый ящик
Список аргументов и возможностей заглушки:
- --dir <Путь к папке> — Папка для файлов
- --file <имя файла> — Сохранять каждое сообщение в конкретном общем файле
- --prepend — Добавлять новое сообщение в начало общего файла
- --open — Автоматически открывать файл сообщения в Notepad
Параметры для PHP.INI файла:
[mail function]
;SMTP = localhost
;smtp_port = 25
;sendmail_from = me@example.com
sendmail_path = "php.exe C:sendmail.php --dir C:mail --open"
Если путь к php.exe прописан в PATH, то можно не указывать его в PHP.INI иначе желательно изменить php.exe на <Путь к папке с PHP>php.exe
sendmail_path = "C:serverbinphpphp.exe C:sendmail.php --dir C:mail --open"
На линукс можно сразу указать путь к файлу, не забыв предварительно сделать его запускаемым: chmod 755 sendmail.php
sendmail_path = "/home/someuser/sendmail.php --dir /tmp/mail"
Сам sendmail.php скрипт:
#!/usr/local/bin/php
<?php
/* PHP.INI
* [mail function]
* ;SMTP = localhost
* ;smtp_port = 25
* ;sendmail_from = me@example.com
* sendmail_path = php.exe sendmail.php --dir C:mail --open
*/
$is_windows = substr(php_uname(), 0, 7) === "Windows";
$is_open = (empty($argv) || !in_array('--open', $argv)) ? FALSE : TRUE;
$is_prepend = (empty($argv) || !in_array('--prepend', $argv)) ? FALSE : TRUE;
$is_onefile = (empty($argv) || !in_array('--file', $argv)) ? FALSE : TRUE;
$mail_dir = get_next_arg('--dir', sys_get_temp_dir().'/mail');
$file_name = get_next_arg('--file', mkname());
$file_path = $mail_dir.'/'.$file_name;
if( !is_dir( $mail_dir ) ) {
mkdir( $mail_dir, 0777, TRUE );
if( !is_dir( $mail_dir ) ) {
die('Mail folder ['.$mail_dir.'] not created');
}
}
$stream = $is_onefile ? PHP_EOL . str_repeat("-=", 10) . date('Y-m-d H:i:s') . str_repeat("-=", 10) . PHP_EOL : '';
$fp = fopen('php://stdin','r');
if (!$fp) {
die('Unable to open stdin for input');
}
while($t=fread($fp,2048)) {
if( $t===chr(0) ) {
break;
}
$stream .= ($is_windows ? str_replace("n", PHP_EOL, $t) : $t);
}
fclose($fp);
if($is_prepend && file_exists($file_path)) {
$file_contents = file_get_contents($file_path);
$stream .= $file_contents;
}
file_put_contents($file_path, $stream, $is_prepend ? 0 : FILE_APPEND);
if ($is_open && $is_windows){
pclose(popen("start /B notepad ". $file_path, "r"));
}
function mkname($i=0) {
global $mail_dir;
$fn = 'mail_'.date('Y-m-d_H-i-s_').$i.'.txt';
return file_exists($mail_dir.'/'.$fn) ? mkname(++$i) : $fn;
}
function get_next_arg($key, $default = NULL) {
global $argv;
if(empty($argv) || !in_array($key, $argv) || empty($argv[array_search($key, $argv, TRUE)+1])) {
return $default;
} else {
return $argv[array_search($key, $argv, TRUE)+1];
}
}
Буду рад, если Вам это будет полезным.
Автор: klev
А есть наоборот – не заглушка, а рабочий сенд-майл для windows? чтоб подменить его в денвере и оно реально бы слало письма, а не складировало в папку