diff --git a/api/api.inc.php b/api/api.inc.php
index 926a0e2a9ddb4b0464c5f1385e56665312339d8e..48836382022d6b8ddec422e0afc46ee074930567 100644
--- a/api/api.inc.php
+++ b/api/api.inc.php
@@ -42,7 +42,7 @@ function api_exit($code,$msg='') {
         //Error occured...
         $_SESSION['api']['errors']+=1;
         $_SESSION['api']['time']=time();
-        $ost->logWarning("API error - code #$code",$msg);
+        $ost->logWarning("API error - code #$code", $msg, ($_SESSION['api']['errors']>10));
         //echo "API Error:.$msg";
     }
     if($remotehost){
@@ -66,19 +66,20 @@ function api_exit($code,$msg='') {
 }
 
 //Remote hosts need authorization.
+$apikey = null;
 if($remotehost) {
-
-    $ip=$_SERVER['REMOTE_ADDR'];
-    $key=$_SERVER['HTTP_USER_AGENT']; //pulling all tricks.
-    //Upto 10 consecutive errors allowed...before a 5 minute timeout.
+    //Upto 10 consecutive errors allowed...before a 2 minute timeout.
     //One more error during timeout and timeout starts a new clock
-    if($_SESSION['api']['errors']>10 && (time()-$_SESSION['api']['time'])<=5*60) { // timeout!
-        api_exit(EX_NOPERM,"Remote host [$ip] in timeout - error #".$_SESSION['api']['errors']);
-    }
-    //Check API key & ip
-    if(!Validator::is_ip($ip) || !Api::validate($key,$ip)) { 
-        api_exit(EX_NOPERM,'Unknown remote host ['.$ip.'] or invalid API key ['.$key.']');
-    }
+    if($_SESSION['api']['errors']>10 && (time()-$_SESSION['api']['time'])<=2*60)  // timeout!
+        api_exit(EX_NOPERM, 'Remote host ['.$_SERVER['REMOTE_ADDR'].'] in timeout - error #'.$_SESSION['api']['errors']);
+        
+    if(!isset($_SERVER['HTTP_X_API_KEY']) || !isset($_SERVER['REMOTE_ADDR']))
+        api_exit(EX_NOPERM, 'API key required');
+    elseif(!($apikey=API::lookupByKey($_SERVER['HTTP_X_API_KEY'], $_SERVER['REMOTE_ADDR']))
+                || !$apikey->isActive()
+                || $apikey->getIPAddr()!=$_SERVER['REMOTE_ADDR'])
+        api_exit(EX_NOPERM, 'API key not found/active or source IP not authorized');
+    
     //At this point we know the remote host/IP is allowed.
     $_SESSION['api']['errors']=0; //clear errors for the session.
 }
diff --git a/api/pipe.php b/api/pipe.php
index 699e7400001c8f497a5bbd30b5d921ca353abe2b..ff23cfa1b56c0f6fa75824f8106337c7440f6cb9 100644
--- a/api/pipe.php
+++ b/api/pipe.php
@@ -16,6 +16,7 @@
 **********************************************************************/
 @chdir(realpath(dirname(__FILE__)).'/'); //Change dir.
 ini_set('memory_limit', '256M'); //The concern here is having enough mem for emails with attachments.
+$apikey = null;
 require('api.inc.php');
 require_once(INCLUDE_DIR.'class.mailparse.php');
 require_once(INCLUDE_DIR.'class.email.php');
@@ -23,6 +24,9 @@ require_once(INCLUDE_DIR.'class.email.php');
 //Make sure piping is enabled!
 if(!$cfg->isEmailPipingEnabled())
     api_exit(EX_UNAVAILABLE,'Email piping not enabled - check MTA settings.');
+elseif($apikey && !$apikey->canCreateTickets()) //apikey is ONLY set on remote post - local post don't need a key (for now).
+    api_exit(EX_NOPERM, 'API key not authorized');
+
 //Get the input
 $data=isset($_SERVER['HTTP_HOST'])?file_get_contents('php://input'):file_get_contents('php://stdin');
 if(empty($data)){
@@ -77,8 +81,8 @@ $name=trim($from->personal,'"');
 if($from->comment && $from->comment[0])
     $name.=' ('.$from->comment[0].')';
 $subj=utf8_encode($parser->getSubject());
-if(!($body=Format::stripEmptyLines($parser->getBody())) && $subj)
-    $body=$subj;
+if(!($body=Format::stripEmptyLines($parser->getBody())))
+    $body=$subj?$subj:'(EMPTY)';
 
 $var['mid']=$parser->getMessageId();
 $var['email']=$from->mailbox.'@'.$from->host;