Changeset 151 for trunk/instant_messenger/inc/Jabber.abstract.php
- Timestamp:
- 01/18/08 15:17:58 (16 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/instant_messenger/inc/Jabber.abstract.php
r64 r151 1 1 <?php 2 2 /* 3 +------------------------------------------------------------------------- +4 | |5 | @FILE: Jabber.abstract.php |6 | @ABSTRACT: Jabber |7 | @EXTENDS: Socket (Socket.class.php) |8 | |9 | @DATE: Wed May,16 2007 08:18:59 |10 | @LAST_CHANGE: Wed May,16 2007 09:03:28 |11 | |12 | @AUTHOR: [NUTS] Rodrigo Souza - rod souza@celepar.pr.gov.br|13 | |14 | @BRIEF: Abstract class for connect with any Jabber server |15 | |16 +------------------------------------------------------------------------- +3 +---------------------------------------------------------------------------------+ 4 | | 5 | @FILE: Jabber.abstract.php | 6 | @ABSTRACT: Jabber | 7 | @EXTENDS: Socket (Socket.class.php) | 8 | | 9 | @DATE: Wed May,16 2007 08:18:59 | 10 | @LAST_CHANGE: Wed May,16 2007 09:03:28 | 11 | | 12 | @AUTHOR: [NUTS] Rodrigo Souza - rodrigosouzadossantos [at] gmail [dot] com | 13 | | 14 | @BRIEF: Abstract class for connect with any Jabber server | 15 | | 16 +---------------------------------------------------------------------------------+ 17 17 */ 18 18 … … 21 21 abstract class Jabber extends Socket 22 22 { 23 const J_FILE = '/var/log/expresso/Jabber.log'; 24 const J_ALL = false; 25 const J_ERROR = true; 26 const J_WARNING = true; 27 const J_NOTICE = true; 28 29 const ALL = 'ALL'; 30 const ERROR = 'ERROR'; 31 const WARNING = 'WARNING'; 32 const NOTICE = 'NOTICE'; 33 34 private final function _connect( $pUser = false, $pPassword = false ) 35 { 36 try 37 { 38 if ( !preg_match('/^(.+)@(.+)\/(.+):(\d+)$/',$pUser, $matches) ) 39 throw new Exception('[connect] #1 ' . $pUser . ' must be [USER]@[DOMAIN]/[RESOURCE]:[PORT] and [PORT] is integer. File: ' . __FILE__ . ' :: ' . __LINE__); 40 41 list($subject, $USER, $SERVER, $RESOURCE, $PORT) = $matches; 42 43 if ( !($socket = $this->open('tcp://' . $SERVER . ':' . $PORT, 1, 1)) ) 44 throw new Exception('[connect] #2 can\'t access tcp://' . $SERVER . ':' . $PORT . '. File: ' . __FILE__ . ' :: ' . __LINE__); 45 46 $this->_socket = $socket; 47 48 $xml = "<?xml version='1.0' encoding='UTF-8'?>"; 49 $xml .= "<stream:stream to='" . $SERVER . "' xmlns='jabber:client' "; 50 $xml .= "xmlns:stream='http://etherx.jabber.org/streams' version='1.0'>"; 51 52 if ( $this->write($xml) === false ) 53 throw new Exception('[connect] #3 it isn\'t possible write in the socket ' . $socket . '. File: ' . __FILE__ . ' :: ' . __LINE__); 54 55 $this->_server = $SERVER; 56 $this->_username = $USER; 57 $this->_password = $pPassword; 58 $this->_resource = $RESOURCE; 59 } 60 catch(Exception $e) 61 { 62 $this->writeLog('ERROR', $e->getMessage()); 63 return false; 64 } 65 } 66 67 protected function connect( $pUser = false, $pPassword = false ) 68 { 69 try 70 { 71 $this->_connect($pUser, $pPassword); 23 const J_FILE = 'Jabber.log'; 24 const J_ALL = false; 25 const J_ERROR = true; 26 const J_WARNING = true; 27 const J_NOTICE = true; 28 29 const ALL = 'ALL'; 30 const ERROR = 'ERROR'; 31 const WARNING = 'WARNING'; 32 const NOTICE = 'NOTICE'; 33 34 private final function _connect( $pUser = false, $pPassword = false ) 35 { 36 try 37 { 38 if ( !preg_match('/^(.+)@(.+)\/(.+):(\d+)$/',$pUser, $matches) ) 39 throw new Exception('[connect] #1 ' . $pUser . ' must be [USER]@[DOMAIN]/[RESOURCE]:[PORT] and [PORT] is integer. File: ' . __FILE__ . ' :: ' . __LINE__); 40 41 list($subject, $USER, $SERVER, $RESOURCE, $PORT) = $matches; 42 43 if ( !($socket = $this->open('tcp://' . $SERVER . ':' . $PORT, 1, 1)) ) 44 throw new Exception('[connect] #2 can\'t access tcp://' . $SERVER . ':' . $PORT . '. File: ' . __FILE__ . ' :: ' . __LINE__); 45 46 $this->_socket = $socket; 47 48 $return = fread($socket, 4096); 49 fwrite($socket, $pUser); 50 51 $return = fread($socket, 4096); 52 fwrite($socket, $pPassword); 53 54 $return = fread($socket, 4096); 55 #echo __FUNCTION__ . "<br>\n"; 56 #var_dump($return); 57 #exit; 58 59 if ( $return == "new" ) 60 { 61 $xml = "<?xml version='1.0' encoding='UTF-8'?>"; 62 $xml .= "<stream:stream to='" . $SERVER . "' xmlns='jabber:client' "; 63 $xml .= "xmlns:stream='http://etherx.jabber.org/streams' version='1.0'>"; 64 65 if ( $this->write($xml) === false ) 66 throw new Exception('[connect] #4 it isn\'t possible connect in the server becase exists a client connected with same user. File: ' . __FILE__ . ' :: ' . __LINE__); 67 } 68 69 $this->_server = $SERVER; 70 $this->_username = $USER; 71 $this->_password = $pPassword; 72 $this->_resource = $RESOURCE; 73 74 #var_dump($return); 75 #exit; 76 return $return; 77 } 78 catch(Exception $e) 79 { 80 $this->writeLog('ERROR', $e->getMessage()); 81 return false; 82 } 83 } 84 85 protected function connect( $pUser = false, $pPassword = false ) 86 { 87 try 88 { 89 $_connect = $this->_connect($pUser, $pPassword); 72 90 73 if ( ($xml = $this->read()) === false ) 74 throw new Exception('[connect] #1 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 75 76 if ( preg_match('/(<starttls .*<required\/><\/starttls>)/', $xml, $matches) ) 77 { 78 if ( !$this->starttls() ) 79 throw new Exception('[connect] #2 it isn\'t possible start tls. File: ' . __FILE__ . ' :: ' . __LINE__); 80 81 # $this->writeLog('NOTICE', 'Connected TLS'); 82 } 83 else 84 { 85 if ( !$this->_plain() ) 86 throw new Exception('[connect] #3 it isn\'t possible carry out the verification. File: ' . __FILE__ . ' :: ' . __LINE__); 87 } 88 89 return true; 90 } 91 catch(Exception $e) 92 { 93 $this->writeLog('ERROR', $e->getMessage()); 94 $this->_disconnect(); 95 return false; 96 } 97 } 98 99 protected final function _disconnect() 100 { 101 try 102 { 103 $xml = "</stream:stream>"; 104 105 if ( $this->write($xml) === false ) 106 throw new Exception('[disconnect] #1 Cannot write to socket (' . $this->_socket . '). File: ' . __FILE__ . ' :: ' . __LINE__); 107 108 if ( ($xml = $this->read()) === false ) 109 throw new Exception('[disconnect] #2 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 110 } 111 catch(Exception $e) 112 { 113 $this->writeLog('ERROR', $e->getMessage()); 114 return false; 115 } 116 } 117 118 private final function starttls() 119 { 120 try 121 { 122 $xml = "<starttls xmlns='urn:ietf:params:xml:ns:xmpp-tls'/>"; 123 if ( $this->write($xml) === false ) 124 throw new Exception('[starttls] #1 Cannot write to socket (' . $this->_socket . '). File: ' . __FILE__ . ' :: ' . __LINE__); 125 126 if ( ($xml = $this->read()) === false ) 127 throw new Exception('[starttls] #2 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 128 129 if ( !preg_match('/<proceed.*\/>/', $xml, $matches) ) 130 throw new Exception('[starttls] #3 can\'t start tls in the socket ' .$this->_socket . '. File: ' . __FILE__ . ' :: ' . __LINE__); 131 132 stream_socket_enable_crypto($this->_socket, TRUE, STREAM_CRYPTO_METHOD_TLS_CLIENT); 133 134 $xml = "<?xml version='1.0' encoding='UTF-8'?>"; 135 $xml .= "<stream:stream to='" . $this->_server . "' xmlns='jabber:client' "; 136 $xml .= "xmlns:stream='http://etherx.jabber.org/streams' version='1.0'>"; 137 if ( $this->write($xml) === false ) 138 throw new Exception('[starttls] #4 Cannot write to socket (' . $this->_socket . '). File: ' . __FILE__ . ' :: ' . __LINE__); 139 140 usleep(90000); 141 $this->blocking($this->_socket, 0); 142 143 if ( ($xml = $this->read()) === false ) 144 throw new Exception('[starttls] #5 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 145 146 if ( !$this->_plain() ) 147 throw new Exception('[starttls] #6 it isn\'t possible carry out the verification. File: ' . __FILE__ . ' :: ' . __LINE__); 148 149 return true; 150 } 151 catch(Exception $e) 152 { 153 $this->writeLog('ERROR', $e->getMessage()); 154 return false; 155 } 156 } 157 158 private final function _plain() 159 { 160 try 161 { 162 $this->blocking($this->_socket, 0); 163 164 if ( ($xml = $this->read()) === false ) 165 throw new Exception('[_plain] #1 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 166 167 $xml = "<username>" . $this->_username . "</username>"; 168 $xml .= "<password>" . $this->_password . "</password>"; 169 $xml .= "<resource>" . $this->_resource . "</resource>"; 170 171 unset($this->_password); 172 173 if ( !$this->iq('set', 'auth_1', NULL, NULL, "jabber:iq:auth", $xml) ) 174 throw new Exception('[_plain] #2 it isn\'t possible carry out the verification. File: ' . __FILE__ . ' :: ' . __LINE__); 175 176 while ( !preg_match("/<iq xmlns='jabber:client' id='auth_1' type='(result|error)'/", ($readSocket = $this->read()), $matches) ) 177 usleep(10000); 91 if ( !$_connect ) 92 throw new Exception('[connect] #0. File: ' . __FILE__ . ' :: ' . __LINE__); 93 94 if ( $_connect == "new" ) 95 { 96 if ( ($xml = $this->read()) === false ) 97 throw new Exception('[connect] #1 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 98 99 if ( preg_match('/(<starttls .*<required\/><\/starttls>)/', $xml, $matches) ) 100 { 101 if ( !$this->starttls() ) 102 throw new Exception('[connect] #2 it isn\'t possible start tls. File: ' . __FILE__ . ' :: ' . __LINE__); 103 104 # $this->writeLog('NOTICE', 'Connected TLS'); 105 } 106 else 107 { 108 if ( !$this->_plain() ) 109 throw new Exception('[connect] #3 it isn\'t possible carry out the verification. File: ' . __FILE__ . ' :: ' . __LINE__); 110 } 111 } 112 113 return $_connect; 114 } 115 catch(Exception $e) 116 { 117 $this->writeLog('ERROR', $e->getMessage()); 118 $this->_disconnect(); 119 return false; 120 } 121 } 122 123 protected final function _disconnect() 124 { 125 try 126 { 127 $xml = "</stream:stream>"; 128 129 if ( $this->write($xml) === false ) 130 throw new Exception('[disconnect] #1 Cannot write to socket (' . $this->_socket . '). File: ' . __FILE__ . ' :: ' . __LINE__); 131 132 if ( ($xml = $this->read()) === false ) 133 throw new Exception('[disconnect] #2 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 134 } 135 catch(Exception $e) 136 { 137 $this->writeLog('ERROR', $e->getMessage()); 138 return false; 139 } 140 } 141 142 private final function starttls() 143 { 144 try 145 { 146 $xml = "<starttls xmlns='urn:ietf:params:xml:ns:xmpp-tls'/>"; 147 if ( $this->write($xml) === false ) 148 throw new Exception('[starttls] #1 Cannot write to socket (' . $this->_socket . '). File: ' . __FILE__ . ' :: ' . __LINE__); 149 150 if ( ($xml = $this->read()) === false ) 151 throw new Exception('[starttls] #2 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 152 153 if ( !preg_match('/<proceed.*\/>/', $xml, $matches) ) 154 throw new Exception('[starttls] #3 can\'t start tls in the socket ' .$this->_socket . '. File: ' . __FILE__ . ' :: ' . __LINE__); 155 156 stream_socket_enable_crypto($this->_socket, TRUE, STREAM_CRYPTO_METHOD_TLS_CLIENT); 157 158 $xml = "<?xml version='1.0' encoding='UTF-8'?>"; 159 $xml .= "<stream:stream to='" . $this->_server . "' xmlns='jabber:client' "; 160 $xml .= "xmlns:stream='http://etherx.jabber.org/streams' version='1.0'>"; 161 if ( $this->write($xml) === false ) 162 throw new Exception('[starttls] #4 Cannot write to socket (' . $this->_socket . '). File: ' . __FILE__ . ' :: ' . __LINE__); 163 164 usleep(90000); 165 $this->blocking($this->_socket, 0); 166 167 if ( ($xml = $this->read()) === false ) 168 throw new Exception('[starttls] #5 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 169 170 if ( !$this->_plain() ) 171 throw new Exception('[starttls] #6 it isn\'t possible carry out the verification. File: ' . __FILE__ . ' :: ' . __LINE__); 172 173 return true; 174 } 175 catch(Exception $e) 176 { 177 $this->writeLog('ERROR', $e->getMessage()); 178 return false; 179 } 180 } 181 182 private final function _plain() 183 { 184 try 185 { 186 $this->blocking($this->_socket, 0); 187 188 if ( ($xml = $this->read()) === false ) 189 throw new Exception('[_plain] #1 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 190 191 $xml = "<username>" . $this->_username . "</username>"; 192 $xml .= "<password>" . $this->_password . "</password>"; 193 $xml .= "<resource>" . $this->_resource . "</resource>"; 194 195 unset($this->_password); 196 197 if ( !$this->iq('set', 'auth_1', NULL, NULL, "jabber:iq:auth", $xml) ) 198 throw new Exception('[_plain] #2 it isn\'t possible carry out the verification. File: ' . __FILE__ . ' :: ' . __LINE__); 199 200 while ( !preg_match("/<iq xmlns='jabber:client' id='auth_1' type='(result|error)'/", ($readSocket = $this->read()), $matches) ) 201 usleep(10000); 178 202 179 203 if($matches[1] == "error") 180 204 return false; 181 205 182 183 184 185 186 187 188 189 190 191 192 206 if ( ($xml = $this->read()) === false ) 207 throw new Exception('[_plain] #3 it isn\'t possible read the socket. File: ' . __FILE__ . ' :: ' . __LINE__); 208 209 return true; 210 } 211 catch(Exception $e) 212 { 213 $this->writeLog('ERROR', $e->getMessage()); 214 return false; 215 } 216 } 193 217 194 218 private final function _iq($pType = false, $pId = false, $pTo = false, $pFrom = false, $pXmlns = false, $pLoad = false ) … … 199 223 200 224 if ( $pXmlns == "vcard-temp" ) 201 225 { 202 226 $xml .= ">"; 203 227 $xml .= $pLoad; 204 228 } 205 206 229 else 230 { 207 231 $xml .= "><query xmlns='" . $pXmlns . "'"; 208 232 $xml .= ( $pLoad ) ? ">" . $pLoad . "</query>" : "/>"; … … 210 234 211 235 $xml .= "</iq>"; 212 213 return $xml; 214 } 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 236 237 return $xml; 238 } 239 240 protected final function iq($pType = false, $pId = false, $pTo = false, $pFrom = false, $pXmlns = false, $pLoad = false) 241 { 242 try 243 { 244 if ( !preg_match("/^(get|set|result|error)$/i", $pType, $matches) ) 245 throw new Exception('[iq] #1 type must be GET, SET, RESULT or ERROR. File: ' . __FILE__ . ' :: ' . __LINE__); 246 247 if ( $this->write($this->_iq($pType, $pId, $pTo, $pFrom, $pXmlns, $pLoad)) === false ) 248 throw new Exception('[iq] #2 Cannot write to socket (' . $this->_socket . '). File: ' . __FILE__ . ' :: ' . __LINE__); 249 else 250 return true; 251 } 252 catch(Exception $e) 253 { 254 $this->writeLog('ERROR', $e->getMessage()); 255 return false; 256 } 257 } 234 258 235 259 protected final function presence($pType = false, $pTo = false, $pShow = false, $pStatus = false, $pPriority = false) 236 260 { 237 try 238 { 239 $xml = "<presence"; 240 $xml .= ($pTo) ? " to='{$pTo}'" : ''; 241 $xml .= ($pType) ? " type='{$pType}'" : ''; 242 243 //$xml .= ($pStatus || $pShow || $pPriority) ? ">" : "/>"; 244 if ( !($pStatus || $pShow || $pPriority) ) 261 try 262 { 263 $xml = "<presence"; 264 $xml .= ($pTo) ? " to='{$pTo}'" : ''; 265 $xml .= ($pType) ? " type='{$pType}'" : ''; 266 267 if ( !($pStatus || $pShow || $pPriority) ) 245 268 $xml .= "/>"; 246 269 else 247 270 { 248 249 250 251 252 271 $xml .= ">"; 272 $xml .= ($pStatus) ? "<status>" . $pStatus . "</status>" : ''; 273 $xml .= ($pShow) ? "<show>" . $pShow . "</show>" : ''; 274 $xml .= ($pPriority) ? "<priority>" . $pPriority . "</priority>" : ''; 275 $xml .= ($pStatus || $pShow || $pPriority) ? "</presence>" : ''; 253 276 } 254 255 256 257 258 259 260 261 262 263 264 265 } 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 277 278 if ( $this->write($xml) === false ) 279 throw new Exception('[presence] #1 it isn\'t possible send presence for ' . $this->_server . '. File: ' . __FILE__ . ' :: ' . __LINE__); 280 281 return true; 282 } 283 catch(Exception $e) 284 { 285 $this->writeLog('ERROR', $e->getMessage()); 286 return false; 287 } 288 } 289 290 protected final function read() 291 { 292 $return = NULL; 293 do 294 { 295 $line = NULL; 296 $line = utf8_decode(parent::read($this->_socket, 4096)); 297 298 if ( $line === false ) 299 { 300 $return = false; 301 break; 302 } 303 304 if ( $line != NULL ) 305 $return .= $line;// . "\n"; 306 } 307 while ( $line != NULL ); 308 309 return $return; 310 } 288 311 289 312 protected final function write($pData = false) 290 { 291 if ( !$pData ) 292 return false; 293 294 return parent::write($this->_socket, utf8_encode($pData)); 295 } 296 297 protected final function writeLog($pType = false, $pLog = false) 298 { 299 if ( !defined('self::'.$pType) && !$pLog ) 300 return false; 301 302 if ( !(bool)constant('self::J_'.$pType) && !(bool)constant('self::J_ALL') ) 303 return false; 304 305 $log = date('m/d/Y H:i:s'); 306 $log .= ' [' . constant('self::'.$pType) . '] :: '; 307 $log .= $pLog . "\n"; 308 if ( $fp = fopen (self::J_FILE, "a+") ) 309 { 310 fwrite($fp, $log); 311 fclose($fp); 312 } 313 } 313 { 314 if ( !$pData ) 315 return false; 316 317 return parent::write($this->_socket, utf8_encode($pData)); 318 } 319 320 function __destruct() 321 { 322 $this->close($this->_socket); 323 } 324 325 protected final function writeLog($pType = false, $pLog = false) 326 { 327 if ( !defined('self::'.$pType) && !$pLog ) 328 return false; 329 330 if ( !(bool)constant('self::J_'.$pType) && !(bool)constant('self::J_ALL') ) 331 return false; 332 333 $log = date('m/d/Y H:i:s'); 334 $log .= ' [' . constant('self::'.$pType) . '] :: '; 335 $log .= $pLog . "\n"; 336 if ( $fp = fopen (self::J_FILE, "a+") ) 337 { 338 fwrite($fp, $log); 339 fclose($fp); 340 } 341 } 314 342 } 315 316 343 ?>
Note: See TracChangeset
for help on using the changeset viewer.