Aurora Private Messaging main class. Requires aurora_settings.php
HotScript @ RoŲnašn index for more scripts and extensions.
Run this script as an example.
<?php
/***************************************
* Aurora PM                            *
*                                      *
* Aurora enables you to add            *
* private messaging to your            *
* bulletinboard.                       *
* In addition it allows messages       *
* to be send between different         *
* boards, increasing the flexibility   *
* of this system.                      *
*                                      *
* Aurora depends upon the              *
* aurora_settings class which should   *
* be downloaded and altered to fit your*
* systems environment.                 *
*                                      *
* Aurora uses your own user-inbox-check*
* to determine if an inbox exists or   *
* doesn't. This is implemented in the  *
* aurora_settings class which each     *
* operator should edit.                *
*                                      *
* Although aurora is developed with an *
* simple interface, (aurora_run.php)   *
* there is no access checking or pwd   *
* verification to enter those boxes.   *
*                                      *
* This is because we think that aurora *
* should be implemented as part of an  *
* community platform like an bb or a   *
* weblog and in that case should profit*
* from already developed and available *
* login scripts and engineered         *
* database layouts. This is not        *
* lazyness on our side, but a way to   *
* make Aurora more flexibel.           *
*                                      *
* Aurora is protected by the General   *
* Public License available at:         *
* http://www.gnu.org/licenses/gpl.txt  *
*                                      *
* For Questions and comments:          *
* hotscripts@roonaan.nl                *
* please add script name to your email *
* subject.                             *
*                                      *
* MYSQL TABLE LAYOUT                   *
*                                      *

CREATE TABLE `AURORA` (
  `ID`      int(10) unsigned NOT NULL auto_increment,
  `DATE`    datetime default NULL,
  `FROM`    text NOT NULL,
  `TO`      text NOT NULL,
  `SUBJECT` text NOT NULL,
  `CONTENT` text NOT NULL,
  `STATUS`  tinyint(3) unsigned NOT NULL default '0',
  PRIMARY KEY  (`ID`)
) TYPE=MyISAM COMMENT='AURORA MAILING TABLE';

*                                      *
****************************************/


/* AURORA REQUIRES aurora_settings.php */
require_once(dirname(__FILE__).'/aurora_settings.php');

/* AURORA CLASS */
/*public*/ 
class aurora
{
  
/* Allow storage for inbox name */
  
var $aurora_inbox;
  
  
/* constructor */
  
function aurora($inbox null)
  {
    
$this->aurora_inbox    = empty($inbox) ? '' $inbox;
  }
  
  
/* Forward error to user defined error handler */
  
function aurora_error($error '')
  {
    
aurora_settings::aurora_error($error);
    
  }
  
  function 
aurora_run()
  {
    
/* Output html navigation bar */
    
echo '<div class="aurora">';
    echo 
'<table class="aurora_bar" cellspacing="0" cellpadding="0" border="0">';
    echo 
'<tr><th>Aurora</th><td>';
    echo 
'<a href="'.aurora_settings::aurora_base_url().'aura=inbox">Inbox</a>';
    echo 
'<a href="'.aurora_settings::aurora_base_url().'aura=outbox">Send PM</a>';
    echo 
'</table>';
    
flush();

    
/* Check wether the initiated inbox exists*/
    
    
if(!aurora_settings::aurora_inbox_exists($this->aurora_inbox))
    {
      
$this->aurora_error('Mailbox "'.$this->aurora_inbox.'" does not exist');
    }
    
/* Section below handles POSTDATA actions.
     * this includes:
     * -delete
     * -send
     */
    
elseif($_SERVER['REQUEST_METHOD'] == 'POST')
    {
      
/* Verify requested action */
      
$this->quick_echo('POST');
      
$aurora_action = isset($_GET['aura']) ? $_GET['aura'] : '';
      
$aurora_action = isset($_POST['aura']) ? $_POST['aura'] : $aurora_action;
      
$aurora_allowed_actions = array('none','outbox','delete');
      if(!
in_array($aurora_action$aurora_allowed_actions)) $aurora_action $aurora_allowed_actions[0];
      
/* Execute action */
      
switch($aurora_action)
      {
        case 
'none':
            
aurora_settings::aurora_error('Unknown aurora action.');
            break;
        case 
'delete':
            
/* Delete messages and show userfriendly warning*/
            
$aurd = array();
            if(isset(
$_POST['aurd'])) $aurd $_POST['aurd'];
            if(
is_array($aurd))
            {
              foreach(
$aurd as $id => $m)
              {
                
$this->aurora_message_delete($id);
              }
            }
            else
            {
              
$aurd = array();
            }
            
            echo 
'<table class="aurora_msg"><tr><th>'.count($aurd).' messages were deleted.</th></tr>';
            break;
        case 
'outbox';
          
/* Retrieve $_POST data */
          
$aurora_addr = isset($_POST['aurt']) ? stripslashes($_POST['aurt']) : '';
          
$aurora_msg  = isset($_POST['aurc']) ? stripslashes($_POST['aurc']) : '';
          
$aurora_subj = isset($_POST['aurs']) ? stripslashes($_POST['aurs']) : '';
          
          
/* Only send when addr and message are nonempty */
          
if(!empty($aurora_addr) && !empty($aurora_msg))
          {
            
/* Is the address a remote or a local address */
            
if(strpos($aurora_addr,'@'))
            {
              
/* Remote box */
              
$this->aurora_send_remote($this->aurora_inbox$aurora_addr$aurora_msg$aurora_subj);
            }
            elseif(
aurora_settings::aurora_inbox_exists($aurora_addr))
            {
              
/* Local box found */
              
$this->aurora_send_local($this->aurora_inbox$aurora_addr$aurora_msg$aurora_subj);
            }
            else
            {
              
/* Present a nice error warning */
              
echo '<table class="aurora_send"><tr><th>Message could not be send: Aurorabox not found</th></tr></table>';
            }
          }
          elseif(empty(
$aurora_addr))
          {
            
/* Data not complete */
            
aurora_settings::aurora_error('Message could not be send: Invalid or empty address');
          }
          elseif(empty(
$aurora_msg))
          {
            
/* Data not complete */
            
aurora_settings::aurora_error('Message could not be send: No Message');
          }
          else
          {
            
/* Present a nice userunfriendly warning */
            
aurora_settings::aurora_error('Message could not be send: Internal Error');
          }
          break;
      }
    }
    
/* GETDATA actions include:
     * -delete
     * -send
     */
    
elseif($_SERVER['REQUEST_METHOD'] == 'GET')
    {
      
/* Composition of messages as wel as inbox viewing */
      /* verify requested action */
      
$aurora_action = isset($_GET['aura']) ? $_GET['aura'] : 'inbox';
      
$aurora_allowed_actions = array('inbox','outbox');
      
      
/* Is the action allowed? */
      
if(!in_array($aurora_action$aurora_allowed_actions))
        
$aurora_action $aurora_allowed_actions[0];
      
      
/*execute action*/
      
switch($aurora_action)
      {
        case 
'inbox':
          
/* Maybe users want to view a specific message */
          
if(isset($_GET['auri']))
          {
            
$this->aurora_message_view(intval($_GET['auri']));
          }
          
/* Show listing of all available messages which have not been deleted (STATUS==99 => deleted) */
          /* Query database*/
          
$aurora_q mysql_query('SELECT `ID`, `FROM`, `SUBJECT`, `TO`, `DATE`, `STATUS` FROM `'.aurora_settings::aurora_mysql_table().'` WHERE (`DATE` IS NOT NULL) AND UPPER(`TO`) = "'.strtoupper($this->aurora_inbox).'"  AND STATUS < 99 ORDER BY `DATE` DESC') or $this->aurora_error(true);
          
$aurora_messages mysql_num_rows($aurora_q);
          
/* Fetch Data*/
          
$aurora_message_table = array();
          for(
$i 0$i $aurora_messages$i++)
          {
            
$aurora_message mysql_fetch_array($aurora_q);
            
$aurora_message_table[$aurora_message['ID']] = array('FROM' => $aurora_message['FROM'], 'TO'=> $aurora_message['TO'], 'DATE'=> $aurora_message['DATE'], 'SUBJECT' => $aurora_message['SUBJECT'], 'STATUS'=> $aurora_message['STATUS']);
          }
          
/* Output table and possibility to delete items */
          
echo '<div class="aurora_inb">';
          echo 
'<form method="post">';
          echo 
'<input type="hidden" name="aura" value="delete" />';
          echo 
'<table class="aurora_inb" cellspacing="0" cellpadding="0" border="0">';
          echo 
'<tr><th>Delete</th><th>Datum</th><th>From</th><th>Subject</th></tr>';
          foreach(
$aurora_message_table as $aurora_message_id => $aurora_message)
          {
            
$aurora_message_url aurora_settings::aurora_base_url().'&aura=inbox&auri='.$aurora_message_id;
            
$aurora_class'aurora_message_new';
            if(
$aurora_message['STATUS'] == 1$aurora_class 'aurora_message_read';
            if(
$aurora_message['STATUS'] >  1$aurora_class 'aurora_message_deleted';
            echo 
'<tr class="'.$aurora_class.'">';
            echo 
'<td><input type="checkbox" name="aurd['.$aurora_message_id.']" /></td>';
            echo 
'<td><a href="'.$aurora_message_url.'">'.$aurora_message['DATE'].'</a></td>';
            echo 
'<td><a href="'.$aurora_message_url.'">'.$aurora_message['FROM'].'</a></td>';
            echo 
'<td><a href="'.$aurora_message_url.'">'.$aurora_message['SUBJECT'].'</a></td>';
            echo 
'</tr>';
          }
          echo 
'<tr><th><input type="submit" value="Delete" /></th><th colspan=3">&nbsp;</th></tr>';
          echo 
'</table>';
          echo 
'</form>';
          echo 
'</div>';
          break;
        case 
'outbox':
          
/* Show outbox */
          
echo '<form style="display:inline;" method="POST">';            
          echo 
'<table class="aurora_outb" cellspacing="0" cellpadding="0" border="0">';
          echo 
'<tr><th class="aurora_outb_to">To:</th><td class="aurora_outb_to"><input type="text" name="aurt" value="'.@$_REQUEST['aurt'].'"/></td></tr>';
          echo 
'<tr><th class="aurora_outb_sub">Subject:</th><td class="aurora_outb_sub"><input type="text" name="aurs" value="'.@$_REQUEST['aurs'].'" size="40" /></td></tr>';
          echo 
'<tr><th class="aurora_outb_msg" colspan="2">Message:</td></tr>';
          echo 
'<tr><td class="aurora_outb_msg" colspan="2"><textarea name="aurc" cols="60" rows="10"></textarea></td></tr>';
          echo 
'<tr><th class="aurora_outb_btn">Send:</th><td class="aurora_outb_btn"><input type="submit" value="Send" /></td></tr>';
          echo 
'</table>';
          echo 
'</form>';
          break;
      }
    }
    else 
/* unknown request method */
    
{
      
$this->aurora_error('Aurora Internal Error');
    }
    echo 
'</div>';
  }

  
/* Debug function */
  
function quick_echo($text)
  {
    
//echo '<script><!-- status="'.addslashes($text).'";//--></script>';flush();
  
}

  function 
aurora_message_view($message_id)
  {
     
/* Update unread/read flag*/
    
$aurora_q mysql_query('UPDATE `'.aurora_settings::aurora_mysql_table().'` SET STATUS="1" WHERE (`DATE` IS NOT NULL) AND UPPER(`TO`) = "'.strtoupper($this->aurora_inbox).'" AND `ID`="'.$message_id.'"') or $this->aurora_error(true);
    
/* Query database for message content */
    
$aurora_q mysql_query('SELECT `CONTENT`, `ID`, `FROM`, `SUBJECT`, `TO`, `DATE`, `STATUS` FROM `'.aurora_settings::aurora_mysql_table().'` WHERE (`DATE` IS NOT NULL) AND UPPER(`TO`) = "'.strtoupper($this->aurora_inbox).'" AND `ID`="'.$message_id.'"') or aurora_settings::aurora_error(mysql_error());
    
$aurora_message_exists = (mysql_num_rows($aurora_q) == 1);
    
    if(
$aurora_message_exists)
    {
      
/* Show message*/
      
$aurora_message mysql_fetch_array($aurora_q);
      echo 
'<table class="aurora_msg" borders="0" cellspacing="0" cellpadding="0">';
      echo 
'<tr><th class="aurora_msg_title"   valign="top">'.$aurora_message['SUBJECT'].'</th></tr>';
      echo 
'<tr><th class="aurora_msg_info"    valign="top">From: <a href="'.aurora_settings::aurora_base_url().'aura=outbox&aurt='.$aurora_message['FROM'].'">'.$aurora_message['FROM'].'</a> on '.$aurora_message['DATE'].'</th></tr>';
      echo 
'<tr><td class="aurora_msg_content" valign="top">'.nl2br(htmlspecialchars($aurora_message['CONTENT'])).'</td></tr>';
      echo 
'</table>';
      
$aurora_message['CONTENT'];
    }
  }
  function 
aurora_message_delete($message_id)
  {
     
$aurora_query 'UPDATE `'.aurora_settings::aurora_mysql_table().'` SET STATUS="99" WHERE `ID`="'.$message_id.'" AND UPPER(`TO`) = "'.addslashes(strtoupper($this->aurora_inbox)).'"';
     
mysql_query($aurora_query) or $this->aurora_error('An error occured when trying to delete a message');
  }
  
  function 
aurora_send_local($from$to$content$subject='')
  {
     
$to      addslashes($to);
     
$from    addslashes($from);
     
$content addslashes($content);
     
$subject addslashes($subject);
     
$aurora_query 'INSERT INTO `'.aurora_settings::aurora_mysql_table().'` (`DATE`,`FROM`,`TO`,`SUBJECT`,`CONTENT`,`STATUS`) VALUES(NOW(),"'.$from.'","'.$to.'","'.$subject.'","'.$content.'",0)';
     
mysql_query($aurora_query) or $this->aurora_error(true);
     echo 
'<table class="aurora_send"><tr><th>Your messages has been succesfully transmitted</th></tr></table>';
  }

  function 
aurora_send_remote($aurora_from$aurora_addr$aurora_msg$aurora_subj='')
  {
    
/* Verify address*/
    
$aurora_addr   explode('@',$aurora_addr2);
    
$aurora_box    $aurora_addr[0];
    
$aurora_remote 'http://'.$aurora_addr[1].'/aurora.php?aura='.md5($_SERVER['SERVER_ADDR'].'send').'&aurb='.$aurora_box;

    
/*Retrieving url*/
    
$this->quick_echo('Accessing remote file');
    
$aurora_f fopen($aurora_remote,'r');
    if(!
$aurora_f)
      
$this->aurora_error('Remote Aurora could not be located. Check your message\'s Aurora address.');
    else
    {
      
$aurora_message '';
      while(!
feof($aurora_f))
        
$aurora_message .= fgets($aurora_f1024);
      
fclose($aurora_f);
      
/* Analyze xml respons */
      
$p xml_parser_create();
      
xml_parse_into_struct($p$aurora_message$aurora_message_tree);
      
xml_parser_free($p);
      
$aurora_send_ok false;
      foreach(
$aurora_message_tree as $t)
      {
        if(
$t['tag'] == 'RETRIEVE' && isset($t['attributes']['INBOX'])&& isset($t['attributes']['KEY']))
        {
          
$aurora_send_ok  = ($t['attributes']['INBOX'] == 'yes');
          
$aurora_send_key = ($t['attributes']['KEY']);
          break;
        }
      }
      
      if(
$aurora_send_ok)
      {
        
/* Server has been found. Sending can be send */
        
$aurora_host  substr($aurora_remote,7strpos($aurora_remote,'/',7)-7);
        
$aurora_file  substr($aurora_remote,7);
        
$aurora_file  substr($aurora_filestrpos($aurora_file,'/'));
        
/* Generate http post message*/
        
$postData     'aurc='.urlencode($aurora_msg);
        
$postData    .= '&aurs='.urlencode($aurora_subj);
        
$postData    .= '&aurf='.urlencode($this->aurora_inbox.'@'.aurora_settings::aurora_server_base());
        
$postData    .= '&aurk='.urlencode($aurora_send_key);
        
$length       strlen($postData);
        
$aurora_http  '';
        
$aurora_http .= "POST $aurora_file HTTP/1.1\r\nHOST: $aurora_host \n";
        
$aurora_http .= "User-Agent: shmertmethod\n";
        
$aurora_http .= "Content-Type: application/x-www-form-urlencoded\n";
        
$aurora_http .= "Content-Length: $length\n";
        
$aurora_http .= "\n";
        
$aurora_http .= $postData;
        
        
/* Open socket and transmit message */
        
$socket fsockopen($aurora_host80$errno$errstr,30);
        if(!
$socket)
        {
          
/* Socket failure */
          
echo '<table class="aurora_send"><tr><th>Your message could not be transmitted. Check your message\'s Aurora address.</th></tr></table>';
        }
        else
        {
          
/* Transmit data */
          
fputs($socket$aurora_http);
          
$aurora_message2 '';
          while (!
feof($socket)) {
            
$aurora_message2 .= fgets($socket1024);
          }
          
fclose($socket);
          
/* Send the appropriate message to user fail/success */
          
if(strpos($aurora_message2'<auroraok />'))
            {
            echo 
'<table class="aurora_send"><tr><th>Your message has been succesfully transmitted</th></tr></table>';
            
//echo "\n<!-- $aurora_message2 -->"; //debug
            
}
          else
          {
            
aurora_settings::aurora_error('Your message could not be transmitted. Error occured on remote Aurora. Check your message\'s Aurora address.');
          } 
        }
      }
      else
      {
        
//echo "\n<!--$aurora_message-->\n"; //debug
        
aurora_settings::aurora_error('Your messages could not be transmitted. Check your message\'s Aurora address.');
      }
    }
  }
}

if(
realpath($_SERVER['SCRIPT_FILENAME']) == realpath(__FILE__))
{
  
header('Content-type:text/xml');
  echo 
'<?xml version="1.0"?>';

  
/* STANDALONE AURORA XML MODE */

  /* ESTABLE DATABASE CONNECTION*/
  
$aurora_connection aurora_settings::aurora_mysql_connect();
  
  
/* Check connection */
  
if(!$aurora_connection)
  {
    exit(
'<aurora version="'.AURORA_VERSION.'"><aurora_err msg="nodb" /></aurora>');
  } 
  
  
/* SELECTING AURORA ACTION */
  
$aurora_action 'none';
  if(isset(
$_GET['aura']))  $aurora_action $_GET['aura'];
  if(isset(
$_POST['aura'])) $aurora_action $_POST['aura'];

  
/* Define Actions */
  
DEFINE('AURORA_NONE',     md5($_SERVER['REMOTE_ADDR'].'none'));
  
DEFINE('AURORA_SEND',     md5($_SERVER['REMOTE_ADDR'].'send'));
  
DEFINE('AURORA_RETRIEVE'md5($_SERVER['REMOTE_ADDR'].'retr'));
  
DEFINE('AURORA_ERR',      md5($_SERVER['REMOTE_ADDR'].'err'));

  
/* Check actions */
  
$aurora_allowed_actions = array(AURORA_ERRAURORA_NONEAURORA_SEND);
  if(!
in_array($aurora_action$aurora_allowed_actions))
    
$aurora_action $aurora_allowed_actions[0];
  
  
/* Execute Action */
  
switch($aurora_action)
  {
    case 
AURORA_SEND:
      
/* Output xml */
      
echo '<aurora version="'.AURORA_VERSION.'">';
      
/* verify inbox */
      
$aurora           = new aurora();
      
$aurora_box       = isset($_GET['aurb']) ? $_GET['aurb'] : '';
      
$aurora_found     aurora_settings::aurora_inbox_exists($aurora_box) ? 'yes' 'no';
      
$aurora_key       = isset($_POST['aurk']) ? $_POST['aurk'] : '';
      
$aurora_local_key md5(aurora_settings::aurora_secret_word().$aurora_box.$_SERVER['REMOTE_ADDR']);
      
/* output if the requested inbox exists */
      
echo '<retrieve inbox="'.$aurora_found.'" key="'.$aurora_local_key.'"/>';
      
/* Maybe this is the second connection and a message has been send*/
      
if(isset($_POST['aurc']) && isset($_POST['aurf']))
      {
        if(
$aurora_key == $aurora_local_key)
        {
          
/* Verify data*/
          
$aurora_from  addSlashes(stripslashes(@$_POST['aurf']));
          
$aurora_msg   addSlashes(stripslashes(@$_POST['aurc']));
          
$aurora_subj  addSlashes(stripslashes(@$_POST['aurs']));
          
/*Add item*/
          
aurora::aurora_send_local($aurora_from$aurora_box$aurora_msg$aurora_subj);
          
/* Return ok signal */
          
echo '<auroraok />';
        }
        else
        {
          echo 
'<err msg="Authorization failed" />';
        }
      }
      echo 
'</aurora>';
      break;
    case 
AURORA_NONE:
      
/* No action, show version */
      
echo '<aurora version="'.AURORA_VERSION.'" />';
      break;
    case 
AURORA_ERR:
    default:
      echo 
'<aurora version="'.AURORA_VERSION.'"><err msg="Authorization failed" /></aurora>';
  }
  
mysql_close($aurora_connection);
}


?>