From d84fc5bd6a3d6d655c515014b7d12f12da96046b Mon Sep 17 00:00:00 2001
From: Christian Binder <christian@jaytraxx.de>
Date: Wed, 5 Dec 2007 08:55:10 +0000
Subject: [PATCH] re-commit of winpopup-backend. the commandline to execute is
 now hardcoded into the backend for security reasons

---
 .../inc/class.notification_winpopup.inc.php   | 183 ++++++++++++++++++
 notifications/templates/default/config.tpl    |  19 +-
 2 files changed, 184 insertions(+), 18 deletions(-)
 create mode 100644 notifications/inc/class.notification_winpopup.inc.php

diff --git a/notifications/inc/class.notification_winpopup.inc.php b/notifications/inc/class.notification_winpopup.inc.php
new file mode 100644
index 0000000000..e7df713e91
--- /dev/null
+++ b/notifications/inc/class.notification_winpopup.inc.php
@@ -0,0 +1,183 @@
+<?php
+/**
+ * eGroupWare - Notifications
+ *
+ * @license http://opensource.org/licenses/gpl-license.php GPL - GNU General Public License
+ * @package notifications
+ * @link http://www.egroupware.org
+ * @author Christian Binder <christian@jaytraxx.de>
+ */
+
+require_once('class.iface_notification.inc.php');
+require_once(EGW_INCLUDE_ROOT.'/phpgwapi/inc/class.config.inc.php');
+
+/**
+ * User notification via winpopup.
+ */
+class notification_winpopup implements iface_notification {
+
+	/**
+	 * Appname
+	 */
+	const _appname = 'notifications';
+	
+	/**
+	 * Login table in SQL database
+	 */
+	const _login_table = 'egw_access_log';
+	
+	/**
+	 * holds account object for user who sends the message
+	 *
+	 * @var object
+	 */
+	private $sender;
+	
+	/**
+	 * holds account object for user to notify
+	 *
+	 * @var object
+	 */
+	private $recipient;
+	
+	/**
+	 * holds config object (sitewide application config)
+	 *
+	 * @var object
+	 */
+	private $config;
+	
+	/**
+	 * holds preferences object of user to notify
+	 *
+	 * @var object
+	 */
+	private $preferences;
+	
+	/**
+	 * holds the netbios command to be executed on notification
+	 *
+	 * @abstract 
+	 * Example: /bin/echo '[MESSAGE]' | /usr/bin/smbclient -M computer-[4] -I [IP] -U '[SENDER]'
+	 *
+	 * Placeholders are:
+	 * [MESSAGE] is the notification message itself
+	 * [1] - [4] are the IP-Octets of the windows machine to notify
+	 * [IP] is the IP-Adress of the windows machine to notify
+	 * [SENDER] is the sender of the message
+	 * Note: the webserver-user needs execute rights for this command
+	 * Don't forget to enclose placeholders containing whitespaces with single apostrophes
+	 *
+	 * @var string
+	 */
+	private $netbios_command;
+	
+	/**
+	 * constructor of notification_winpopup
+	 *
+	 * @param object $_sender
+	 * @param object $_recipient
+	 * @param object $_config
+	 * @param object $_preferences
+	 */
+	public function __construct($_sender=false, $_recipient=false, $_config=false, $_preferences=false) {
+		// If we are called from class notification sender, recipient, config and prefs are objects.
+		// otherwise we have to fetch this objects for current user.
+		if (!is_object($_sender)) {
+			$this->sender = (object) $GLOBALS['egw']->accounts->read($_sender);
+			$this->sender->id =& $this->sender->account_id;
+		}
+		else {
+			$this->sender = $_sender;
+		}
+		if (!is_object($_recipient)) {
+			$this->recipient = (object) $GLOBALS['egw']->accounts->read($_recipient);
+			$this->recipient->id =& $this->recipient->account_id;
+		}
+		else {
+			$this->recipient = $_recipient;
+		}
+		if(!is_object($_config)) {
+			$config = new config(self::_appname);
+			$this->config = (object) $config->read_repository();
+		} else {
+			$this->config = $_config;
+		}
+		if(!is_object($_preferences)) {
+			$prefs = new preferences($this->recipient->id);
+			$preferences = $prefs->read();
+			$this->preferences = (object)$preferences[self::_appname ];
+		} else {
+			$this->preferences = $_preferences;
+		}
+	}
+	
+	/**
+	 * sends notification
+	 *
+	 * @param string $_subject
+	 * @param array $_messages
+	 * @param array $_attachments
+	 */
+	public function send( $_subject = false, $_messages, $_attachments = false) {
+		if(!$this->netbios_command) {
+			throw new Exception(	'Winpopup plugin not configured yet. Skipped sending notification message. '.
+									'Please check var "netbios_command" in winpopup backend '.
+									'('.EGW_INCLUDE_ROOT. SEP. self::_appname. SEP. 'inc'. SEP. 'class.notification_winpopup.inc.php).');
+		}
+		
+		$sessions = $GLOBALS['egw']->session->list_sessions(0, 'asc', 'session_dla', true);
+		$user_sessions = array();
+		foreach ($sessions as $session) {
+			if ($session['session_lid'] == $this->recipient->lid. '@'. $GLOBALS['egw_info']['user']['domain']) {
+				if($this->valid_ip($session['session_ip'])) {
+					$user_sessions[] = $session['session_ip'];
+				}
+			}
+		}
+		if ( empty($user_sessions) ) throw new Exception("User #{$this->recipient->id} isn't online. Can't send notification via winpopup");
+		
+		$this->send_winpopup( $_messages['plain']['text'], $user_sessions );
+		return true;
+	}
+	
+	/**
+	 * sends the winpopup message via command line string netbios_command specified above
+	 *
+	 * @param string $_message
+	 * @param array $_user_sessions
+	 */
+	private function send_winpopup( $_message, array $_user_sessions ) {
+		foreach($_user_sessions as $user_session) {
+			$ip_octets=explode(".",$user_session);
+			// format the ip_octets to 3 digits each
+			foreach($ip_octets as $id=>$ip_octet) {
+				if(strlen($ip_octet)==1) { $ip_octets[$id] = '00'.$ip_octet; }
+				if(strlen($ip_octet)==2) { $ip_octets[$id] = '0'.$ip_octet; }
+			}
+			$placeholders = array(	'/\[MESSAGE\]/' => $_message,
+									'/\[1\]/' => $ip_octets[0],
+									'/\[2\]/' => $ip_octets[1],
+									'/\[3\]/' => $ip_octets[2],
+									'/\[4\]/' => $ip_octets[3],
+									'/\[IP\]/' => $user_session,
+									'/\[SENDER\]/' => $GLOBALS['egw']->accounts->id2name($this->sender->id,'account_fullname'),
+									);
+			$command = preg_replace(array_keys($placeholders), $placeholders, $this->netbios_command);
+			exec($command,$output,$returncode);
+			if($returncode != 0) {
+				throw new Exception("Failed sending notification message via winpopup. Error while executing the specified command.");
+			}
+		}
+	}
+	
+	/**
+	 * checks for a valid IPv4-address without CIDR notation
+	 *
+	 * @param string $_ip
+	 * @return true or false
+	 */
+	private function valid_ip($_ip) {
+		return eregi('^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$',$_ip);
+	}
+}
\ No newline at end of file
diff --git a/notifications/templates/default/config.tpl b/notifications/templates/default/config.tpl
index 050f0e32e5..701a03cdcf 100644
--- a/notifications/templates/default/config.tpl
+++ b/notifications/templates/default/config.tpl
@@ -11,24 +11,7 @@
 <!-- END header -->
 <!-- BEGIN body -->
    <tr class="th">
-    <td colspan="2">&nbsp;<b>{lang_Windows_Popup_Configuration}</b></td>
-   </tr>
-   <tr class="row_on">
-    <td>&nbsp;{lang_Netbios_command}:</td>
-    <td><input name="newsettings[winpopup_netbios_command]" value="{value_winpopup_netbios_command}" size="80"></td>
-   </tr>
-	 <tr class="row_n">
-    <td>&nbsp;</td>
-    <td>
-		<strong>Example:</strong> /bin/echo '[MESSAGE]' | /usr/bin/smbclient -M computer-[4] -I [IP] -U '[SENDER]'<br /><br />
-		<strong><u>placeholders:</u></strong><br />
-		[MESSAGE] is the notification message itself<br />
-		[1] - [4] are the IP-Octets of the windows machine to notify<br />
-		[IP] is the IP-Adress of the windows machine to notify<br />
-		[SENDER] is the sender of the netbios message configured above<br />
-		<strong>Note:</strong> the webserver-user needs execute rights for this command<br />
-		Don't forget to enclose placeholders containig whitespaces with apostrophes
-	</td>
+    <td colspan="2">&nbsp;<b>{lang_Notification_backends</b>_(Preferences_for_enabling/disabling_will_follow_soon)}</td>
    </tr>
 <!-- END body -->
 <!-- BEGIN footer -->