SMTP-Server für HP-Scanner

Ich habe mir einen neuen Drucker mit Scanner zugetan, nur leider habe ich erst zu spät bemerkt, dass die Scan-Zu-Mail funktion einen SMTP-Server ohne Sicherheit braucht. Also habe ich mir was gebastelt. Das Ziel war, das ich auf den Scanner eine Email-Adresse auswählen kann und die PDF-Datei am Ende im home Benutzer Ordner auf meinem NAS landet. Der Fake-SMTP-Server ist auch auf dem NAS installiert.

Umsetzung

Ich habe dafür zum Glück schon fertigen Code gefunden, den ich nur noch zusammen bauen musste. Ich verwende zum einen die fakeSMTP Klasse in Verbindung mit inetd zum Empfang der Mail. Und dazu noch die mailreader Klasse zum extrahieren des Datei-Anhangs aus dem Email.

Wie auf der angegeben Seite gezeigt wird diese Zeile zur inetd konfigurations Datei hinzugefügt (/etc/inetd.conf ):

smtp   stream    tcp    nowait    root    /volume1/home¬
						/user1/fakeSMTP.php

Dies lief ohne grosse Probleme, der einzige Stolperstein war das ich keine Möglichkeit finden konnte die inetd Konifguration neu zu laden ohne das ganze NAS neu zustarten. Der NAS-Neustart war am Ende halt doch die einfachste Lösung.

Der nächste Schritt war die Datei aus dem empfangenen Email zu extrahieren. Dafür habe ich ein mailreader gefunden, welches nicht zu viele Abhängigkeiten hat. Leider erwartet diese Skript die Daten auf dem stdin, was für meine Zwecke nicht funktioniert, ich musste also eine zusätzliche Funktion einbauen damit ich das email als string übergeben kann, dies war aber nicht weiter wild: Die originale readEmail Funktion:

public function readEmail($src = 'php://stdin') {
	// Process the e-mail from stdin
	$fd = fopen($src,'r');
	while(!feof($fd)){ $this->raw .= fread($fd,1024); }
	
	$this->readEmail2($this->raw);
}
Die neue Funktion, die jetzt ein String-Argument erwartet (ich zeige nur den Start der Methode):
public function readEmail2($data){
	// Now decode it!
	// http://pear.php.net/manual/en/package.mail.mail-
	// mimedecode.decode.php
	$decoder = new Mail_mimeDecode($data);
	$this->decoded = $decoder->decode(
		Array(
			'decode_headers' => TRUE,
			'include_bodies' => TRUE,
			'decode_bodies' => TRUE,
		)
	);
	// More code to follow here...
Durch diese Umbauten ist es jetzt möglich die Klasse aus dem fakeSMTP.php Datei wie folgt zu verwenden:
require_once('mailReader.php');

$allowed_senders = Array('scanner@example.com');

$hp = new fakeSMTP;
$hp->serverHello = 'hp.axllent.org ESMTP Postfix';
$hp->logFile = '/volume1/homes/username/mail/emails.log';
$hp->receive();
if (!$hp->mail['rawEmail']) exit;

$hp->log("received email from " . $hp->mail['emailTo']);

$save_directory = '/volume1/homes/user1/scanner/';
if ($hp->mail['emailTo'] == 'user2@example.com') {
    $save_directory = '/volume1/homes/user2/scanner/';
}

$hp->log("parsing email and save to " . $save_directory);

$mr = new mailReader($save_directory,$allowed_senders,NULL);
$mr->save_msg_to_db = FALSE;
$mr->send_email = FALSE;
$hp->log("parsing email");

$mr->readEmail2($hp->mail['rawEmail']);

$hp->log("done email " . $mr->from . " sent to " . 
	$mr->decoded->headers['to']);
Nach dem Scannen wird das PDF im richtigen Ordner auf dem NAS abgelegt abhängig von der Email-Adresse die man beim scannen ausgewählt hat.

Damit das mit den Pfaden auf dem NAS klappt, muss man die Home-Folder-Optionen aktivieren, und dann einen Ordner mit dem Namen "scanner" für jeden Benutzer erstellen, auf dem der PHP-Prozess Schreibrechte besitzt.