1<?php 2/** 3 * Mollom class 4 * 5 * This source file can be used to communicate with mollom (http://mollom.com) 6 * 7 * The class is documented in the file itself, but you can find more documentation and examples on the docs-page (http://mollom.crsolutions.be/docs). 8 * If you find any bugs help me out and report them. Reporting can be done by sending an email to php-mollom-bugs[at]verkoyen[dot]eu. If you report a bug, make sure you give me enough information (include your code). 9 * If you have questions, try the Mollom-forum, don't send them by mail, I won't read them. 10 * 11 * Changelog since 1.0.1 12 * - Fixed a nasty bug. Possible infinite loop in doCall(). 13 * - Fixed getServerList. I misinterpreted the documentation, so now the defaultserver is xmlrpc.mollom.com instead of the first fallback-server. 14 * - Fixed the timeout-issue. With fsockopen the timeout on connect wasn't respected. Rewrote the doCall function to use CURL over sockets. 15 * 16 * Changelog since 1.1.0 17 * - Fixed a problem with the IP-addresses. see http://blog.verkoyen.eu/2008/07/12/important-php-mollom-update/ 18 * 19 * Changelog since 1.1.1 20 * - PHPMollom was using HTTP 1.1, now HTTP 1.0. 21 * - Fallbackserver are hardcoded, when no servers could be retrieved the fallbacks are used 22 * 23 * Changelog since 1.1.2 24 * - Typo 25 * - New Licence: BSD Modified 26 * 27 * License 28 * Copyright (c) 2008, Tijs Verkoyen. All rights reserved. 29 * 30 * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 31 * 32 * 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 33 * 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 34 * 3. The name of the author may not be used to endorse or promote products derived from this software without specific prior written permission. 35 * 36 * This software is provided by the author ``as is'' and any express or implied warranties, including, but not limited to, the implied warranties of merchantability and fitness for a particular purpose are disclaimed. In no event shall the author be liable for any direct, indirect, incidental, special, exemplary, or consequential damages (including, but not limited to, procurement of substitute goods or services; loss of use, data, or profits; or business interruption) however caused and on any theory of liability, whether in contract, strict liability, or tort (including negligence or otherwise) arising in any way out of the use of this software, even if advised of the possibility of such damage. 37 * 38 * @author Tijs Verkoyen <mollom@verkoyen.eu> 39 * @version 1.1.3 40 * 41 * @copyright Copyright (c) 2008, Tijs Verkoyen. All rights reserved. 42 * @license http://mollom.local/license BSD License 43 */ 44class Mollom 45{ 46 /** 47 * The allowed reverse proxy addresses 48 * 49 * @var array 50 */ 51 private static $allowedReverseProxyAddresses = array(); 52 53 54 /** 55 * Your private key 56 * 57 * Set it by calling Mollom::setPrivateKey('<your-key>'); 58 * 59 * @var string 60 */ 61 private static $privateKey; 62 63 64 /** 65 * Your public key 66 * 67 * Set it by calling Mollom::setPublicKey('<your-key>'); 68 * 69 * @var string 70 */ 71 private static $publicKey; 72 73 74 /** 75 * Reverse proxy allowed? 76 * 77 * @var bool 78 */ 79 private static $reverseProxy = false; 80 81 82 /** 83 * The default server 84 * 85 * No need to change 86 * 87 * @var string 88 */ 89 private static $serverHost = 'xmlrpc.mollom.com'; 90 91 92 /** 93 * The cache for the serverlist 94 * 95 * No need to change 96 * 97 * @var array 98 */ 99 private static $serverList = array(); 100 101 102 /** 103 * Default timeout 104 * 105 * @var int 106 */ 107 private static $timeout = 10; 108 109 110 /** 111 * The default user-agent 112 * 113 * Change it by calling Mollom::setUserAgent('<your-user-agent>'); 114 * 115 * @var string 116 */ 117 private static $userAgent = 'MollomPHP/1.1.3'; 118 119 120 /** 121 * The current Mollom-version 122 * 123 * No need to change 124 * 125 * @var string 126 */ 127 private static $version = '1.0'; 128 129 130 /** 131 * Build the value so we can use it in XML-RPC requests 132 * 133 * @return string 134 * @param mixed $value 135 */ 136 private function buildValue($value) 137 { 138 // get type 139 $type = gettype($value); 140 141 // build value 142 switch ($type) 143 { 144 case 'string': 145 // escape it, cause Mollom can't handle CDATA (no pun intended) 146 $value = htmlspecialchars($value, ENT_QUOTES, 'ISO-8859-15'); 147 return '<value><string>'. $value .'</string></value>'."\n"; 148 149 case 'array': 150 // init struct 151 $struct = '<value>'."\n"; 152 $struct .= ' <struct>'."\n"; 153 154 // loop array 155 foreach ($value as $key => $value) $struct .= str_replace("\n", '', '<member>'. "\n" .'<name>'. $key .'</name>'. mollom::buildValue($value) .'</member>') . "\n"; 156 157 $struct .= ' </struct>'."\n"; 158 $struct .= '</value>'."\n"; 159 160 // return 161 return $struct; 162 163 default: 164 return '<value>'. $value .'</value>'."\n"; 165 } 166 } 167 168 169 /** 170 * Validates the answer for a CAPTCHA 171 * 172 * When the answer is false, you should request a new image- or audio-CAPTCHA, make sure your provide the current Mollom-sessionid. 173 * The sessionid will be used to track spambots that try to solve CAPTHCA's by brute force. 174 * 175 * @return bool 176 * @param string $sessionId 177 * @param string $solution 178 */ 179 public static function checkCaptcha($sessionId, $solution) 180 { 181 // redefine 182 $sessionId = (string) $sessionId; 183 $solution = (string) $solution; 184 185 // set autor ip 186 $authorIp = self::getIpAddress(); 187 188 // set parameters 189 $parameters['session_id'] = $sessionId; 190 $parameters['solution'] = $solution; 191 if($authorIp != null) $parameters['author_ip'] = (string) $authorIp; 192 193 // do the call 194 $responseString = self::doCall('checkCaptcha', $parameters); 195 // validate 196 if(!isset($responseString->params->param->value->boolean)) throw new Exception('Invalid response in checkCapthca.'); 197 198 // return 199 if((string) $responseString->params->param->value->boolean == '1') return true; 200 201 // fallback 202 return false; 203 } 204 205 206 /** 207 * Check if the data is spam or not, and gets an assessment of the datas quality 208 * 209 * This function will be used most. The more data you submit the more accurate the claasification will be. 210 * If the spamstatus is 'unsure', you could send the user an extra check (eg. a captcha). 211 * 212 * REMARK: the Mollom-sessionid is NOT related to HTTP-session, so don't send 'session_id'. 213 * 214 * The function will return an array with 3 elements: 215 * - spam the spam-status (unknown/ham/spam/unsure) 216 * - quality an assessment of the content's quality (between 0 and 1) 217 * - session_id Molloms session_id 218 * 219 * @return array 220 * @param string[optional] $sessionId 221 * @param string[optional] $postTitle 222 * @param string[optional] $postBody 223 * @param string[optional] $authorName 224 * @param string[optional] $authorUrl 225 * @param string[optional] $authorEmail 226 * @param string[optional] $authorOpenId 227 * @param string[optional] $authorId 228 */ 229 public static function checkContent($sessionId = null, $postTitle = null, $postBody = null, $authorName = null, $authorUrl = null, $authorEmail = null, $authorOpenId = null, $authorId = null, $ips = array()) 230 { 231 // validate 232 if($sessionId === null && $postTitle === null && $postBody === null && $authorName === null && $authorUrl === null && $authorEmail === null && $authorOpenId === null && $authorId === null) throw new Exception('Specify at least on argument'); 233 234 // init var 235 $parameters = array(); 236 $aReturn = array(); 237 238 // add parameters 239 if($sessionId !== null) $parameters['session_id'] = (string) $sessionId; 240 if($postTitle !== null) $parameters['post_title'] = (string) $postTitle; 241 if($postBody !== null) $parameters['post_body'] = (string) $postBody; 242 if($authorName !== null) $parameters['author_name'] = (string) $authorName; 243 if($authorUrl !== null) $parameters['author_url'] = (string) $authorUrl; 244 if($authorEmail !== null) $parameters['author_mail'] = (string) $authorEmail; 245 if($authorOpenId != null) $parameters['author_openid'] = (string) $authorOpenId; 246 if($authorId != null) $parameters['author_id'] = (string) $authorId; 247 248 // set autor ip 249 if (!sizeof($ips)) { 250 $authorIp = self::getIpAddress(); 251 } else { 252 $authorIp = $ips[0]; 253 } 254 if($authorIp != null) $parameters['author_ip'] = (string) $authorIp; 255 256 // do the call 257 $responseString = self::doCall('checkContent', $parameters); 258 259 // validate 260 if(!isset($responseString->params->param->value->struct->member)) throw new Exception('Invalid response in checkContent.'); 261 262 // loop parts 263 foreach ($responseString->params->param->value->struct->member as $part) 264 { 265 // get key 266 $key = $part->name; 267 268 // get value 269 switch ($part->name) 270 { 271 case 'spam': 272 $value = (string) $part->value->int; 273 274 switch($value) 275 { 276 case '0': 277 $aReturn['spam'] = 'unknown'; 278 break; 279 280 case '1': 281 $aReturn['spam'] = 'ham'; 282 break; 283 284 case '2': 285 $aReturn['spam'] = 'spam'; 286 break; 287 288 case '3': 289 $aReturn['spam'] = 'unsure'; 290 break; 291 } 292 break; 293 294 case 'quality': 295 $aReturn['quality'] = (float) $part->value->double; 296 break; 297 298 case 'session_id': 299 $aReturn['session_id'] = (string) $part->value->string; 300 break; 301 } 302 } 303 304 // return 305 return $aReturn; 306 } 307 308 309 /** 310 * Make the call 311 * 312 * @return SimpleXMLElement 313 * @param string $method 314 * @param array[optional] $parameters 315 */ 316 private static function doCall($method, $parameters = array(), $server = null, $counter = 0) 317 { 318 // count available servers 319 $countServerList = count(self::$serverList); 320 321 if($server === null && $countServerList == 0) throw new Exception('No servers found, populate the serverlist. See setServerList().'); 322 323 // redefine var 324 $method = (string) $method; 325 $parameters = (array) $parameters; 326 327 // possible methods 328 $aPossibleMethods = array('checkCaptcha', 'checkContent', 'getAudioCaptcha', 'getImageCaptcha', 'getServerList', 'getStatistics', 'sendFeedback', 'verifyKey'); 329 330 // check if method is valid 331 if(!in_array($method, $aPossibleMethods)) throw new Exception('Invalid method. Only '. implode(', ', $aPossibleMethods) .' are possible methods.'); 332 333 // check if public key is set 334 if(self::$publicKey === null) throw new Exception('Public key wasn\'t set.'); 335 336 // check if private key is set 337 if(self::$privateKey === null) throw new Exception('Private key wasn\'t set.'); 338 339 // still null 340 if($server === null) $server = self::$serverList[$counter]; 341 342 // cleanup server string 343 $server = str_replace(array('http://', 'https://'), '', $server); 344 345 // create timestamp 346 $time = gmdate("Y-m-d\TH:i:s.\\0\\0\\0O", time()); 347 348 // create nonce 349 $nonce = md5(time()); 350 351 // create has 352 $hash = base64_encode( 353 pack("H*", sha1((str_pad(self::$privateKey, 64, chr(0x00)) ^ (str_repeat(chr(0x5c), 64))) . 354 pack("H*", sha1((str_pad(self::$privateKey, 64, chr(0x00)) ^ (str_repeat(chr(0x36), 64))) . 355 $time . ':'. $nonce .':'. self::$privateKey)))) 356 ); 357 358 // add parameters 359 $parameters['public_key'] = self::$publicKey; 360 $parameters['time'] = $time; 361 $parameters['hash'] = $hash; 362 $parameters['nonce'] = $nonce; 363 364 // build request 365 $requestBody = '<?xml version="1.0"?>' ."\n"; 366 $requestBody .= '<methodCall>' ."\n"; 367 $requestBody .= ' <methodName>mollom.'. $method .'</methodName>' ."\n"; 368 $requestBody .= ' <params>' ."\n"; 369 $requestBody .= ' <param>'."\n"; 370 $requestBody .= ' '. self::buildValue($parameters) ."\n"; 371 $requestBody .= ' </param>'."\n"; 372 $requestBody .= ' </params>' ."\n"; 373 $requestBody .= '</methodCall>' ."\n"; 374 375 // create curl 376 $curl = @curl_init(); 377 378 // set useragent 379 @curl_setopt($curl, CURLOPT_USERAGENT, self::$userAgent); 380 381 // set options 382 @curl_setopt($curl, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_0); 383 @curl_setopt($curl, CURLOPT_POST, true); 384 @curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true); 385 @curl_setopt($curl, CURLOPT_HEADER, true); 386 @curl_setopt($curl, CURLOPT_RETURNTRANSFER, true); 387 @curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, self::$timeout); 388 @curl_setopt($curl, CURLOPT_TIMEOUT, self::$timeout); 389 390 // set url 391 @curl_setopt($curl, CURLOPT_URL, $server .'/'. self::$version); 392 393 // set body 394 @curl_setopt($curl, CURLOPT_POSTFIELDS, $requestBody); 395 396 // get response 397 $response = @curl_exec($curl); 398 399 // get errors 400 $errorNumber = (int) @curl_errno($curl); 401 $errorString = @curl_error($curl); 402 403 // close 404 @curl_close($curl); 405 406 // validate response 407 if($response === false || $errorNumber != 0) 408 { 409 // increment counter 410 $counter++; 411 412 // no servers left 413 if($errorNumber == 28 && !isset(self::$serverList[$counter]) && $countServerList != 0) throw new Exception('No more servers available, try to increase the timeout.'); 414 415 // timeout 416 elseif($errorNumber == 28 && isset(self::$serverList[$counter])) return self::doCall($method, $parameters, self::$serverList[$counter], $counter); 417 418 // other error 419 else throw new Exception('Something went wrong. Maybe the following message can be handy.<br />'. $errorString, $errorNumber); 420 } 421 422 // process response 423 $parts = explode("\r\n\r\n", $response); 424 425 // validate 426 if(!isset($parts[0]) || !isset($parts[1])) throw new Exception('Invalid response in doCall.'); 427 428 // get headers 429 $headers = $parts[0]; 430 431 // rebuild body 432 array_shift($parts); 433 $body = implode('', $parts); 434 435 // validate header 436 $aValidHeaders = array('HTTP/1.0 200', 'HTTP/1.1 200'); 437 if(!in_array(substr($headers, 0, 12), $aValidHeaders)) throw new Exception('Invalid headers.'); 438 439 // do some validation 440 $responseXML = @simplexml_load_string($body); 441 if($responseXML === false) throw new Exception('Invalid body.'); 442 443 if(isset($responseXML->fault)) 444 { 445 $code = (isset($responseXML->fault->value->struct->member[0]->value->int)) ? (int) $responseXML->fault->value->struct->member[0]->value->int : 'unknown'; 446 $message = (isset($responseXML->fault->value->struct->member[1]->value->string)) ? (string) $responseXML->fault->value->struct->member[1]->value->string : 'unknown'; 447 448 // handle errors 449 switch ($code) 450 { 451 // code 1000 (Parse error or internal problem) 452 case 1000: 453 throw new Exception('[error '.$code .'] '. $message, $code); 454 455 // code 1100 (Serverlist outdated) 456 case 1100: 457 throw new Exception('[error '.$code .'] '. $message, $code); 458 459 // code 1200 (Server too busy) 460 case 1200: 461 if(self::$serverList === null) self::getServerList(); 462 463 // do call again 464 return self::doCall($method, $parameters, self::$serverList[$counter], $counter++); 465 break; 466 467 default: 468 throw new Exception('[error '.$code .'] '. $message, $code); 469 } 470 } 471 472 // return 473 return $responseXML; 474 } 475 476 477 /** 478 * Get a CAPTCHA-mp3 generated by Mollom 479 * 480 * If your already called getAudioCaptcha make sure you provide at least the $sessionId. It will be used 481 * to identify visitors that are trying to break a CAPTCHA with brute force. 482 * 483 * REMARK: the Mollom-sessionid is NOT related to HTTP-session, so don't send 'session_id'. 484 * 485 * The function will return an array with 3 elements: 486 * - session_id the session_id from Mollom 487 * - url the url to the mp3-file 488 * - html html that can be used on your website to display the CAPTCHA 489 * 490 * @return array 491 * @param string[optional] $sessionId 492 */ 493 public static function getAudioCaptcha($sessionId = null) 494 { 495 // init vars 496 $aReturn = array(); 497 $parameters = array(); 498 499 // set autor ip 500 $authorIp = self::getIpAddress(); 501 502 // set parameters 503 if($sessionId != null) $parameters['session_id'] = (string) $sessionId; 504 if($authorIp != null) $parameters['author_ip'] = (string) $authorIp; 505 506 // do the call 507 $responseString = self::doCall('getAudioCaptcha', $parameters); 508 509 // validate 510 if(!isset($responseString->params->param->value->struct->member)) throw new Exception('Invalid response in getAudioCaptcha.'); 511 512 // loop elements 513 foreach ($responseString->params->param->value->struct->member as $part) $aReturn[(string) $part->name] = (string) $part->value->string; 514 515 // add image html 516 $aReturn['html'] = '<object type="audio/mpeg" data="'. $aReturn['url'] .'" width="50" height="16">'."\n" 517 ."\t".'<param name="autoplay" value="false" />'."\n" 518 ."\t".'<param name="controller" value="true" />'."\n" 519 .'</object>'; 520 521 // return 522 return $aReturn; 523 } 524 525 526 /** 527 * Get a CAPTCHA-image generated by Mollom 528 * 529 * If your already called getImageCaptcha make sure you provide at least the $sessionId. It will be used 530 * to identify visitors that are trying to break a CAPTCHA with brute force. 531 * 532 * REMARK: the Mollom-sessionid is NOT related to HTTP-session, so don't send 'session_id'. 533 * 534 * The function will return an array with 3 elements: 535 * - session_id the session_id from Mollom 536 * - url the url to the image 537 * - html html that can be used on your website to display the CAPTCHA 538 * 539 * @return array 540 * @param string[optional] $sessionId 541 */ 542 public static function getImageCaptcha($sessionId = null) 543 { 544 // init vars 545 $aReturn = array(); 546 $parameters = array(); 547 548 // set autor ip 549 $authorIp = self::getIpAddress(); 550 551 // set parameters 552 if($sessionId !== null) $parameters['session_id'] = (string) $sessionId; 553 if($authorIp !== null) $parameters['author_ip'] = (string) $authorIp; 554 555 // do the call 556 $responseString = self::doCall('getImageCaptcha', $parameters); 557 558 // validate 559 if(!isset($responseString->params->param->value->struct->member)) throw new Exception('Invalid response in getImageCaptcha.'); 560 561 // loop elements 562 foreach ($responseString->params->param->value->struct->member as $part) $aReturn[(string) $part->name] = (string) $part->value->string; 563 564 // add image html 565 $aReturn['html'] = '<img src="'. $aReturn['url'] .'" alt="Mollom CAPTCHA" />'; 566 567 // return 568 return $aReturn; 569 } 570 571 572 /** 573 * Get the real IP-address 574 * 575 * @return string 576 */ 577 public static function getIpAddress() 578 { 579 // pre check 580 if(!isset($_SERVER['REMOTE_ADDR'])) return null; 581 582 // get ip 583 $ipAddress = $_SERVER['REMOTE_ADDR']; 584 585 if(self::$reverseProxy) 586 { 587 if(isset($_SERVER['HTTP_X_FORWARDED_FOR'])) 588 { 589 if(!empty(self::$allowedReverseProxyAddresses) && in_array($ipAddress, self::$allowedProxyAddresses, true)) 590 { 591 return array_pop(explode(',', $_SERVER['HTTP_X_FORWARDED_FOR'])); 592 } 593 } 594 595 // running in a cluster environment 596 if(isset($_SERVER['HTTP_X_CLUSTER_CLIENT_IP'])) return $_SERVER['HTTP_X_CLUSTER_CLIENT_IP']; 597 } 598 599 // fallback 600 print 'IP:'.$ipAddress; 601 return $ipAddress; 602 } 603 604 605 /** 606 * Obtains a list of valid servers 607 * 608 * @return array 609 */ 610 public static function getServerList($counter = 0) 611 { 612 // do the call 613 $responseString = self::doCall('getServerList', array(), self::$serverHost, $counter); 614 615 // validate 616 if(!isset($responseString->params->param->value->array->data->value)) throw new Exception('Invalid response in getServerList.'); 617 618 // loop servers and add them 619 foreach ($responseString->params->param->value->array->data->value as $server) self::$serverList[] = (string) $server->string; 620 621 if(count(self::$serverList) == 0) self::$serverList = array('http://xmlrpc3.mollom.com', 'http://xmlrpc2.mollom.com', 'http://xmlrpc1.mollom.com'); 622 623 // return 624 return self::$serverList; 625 } 626 627 628 /** 629 * Retrieve statistics from Mollom 630 * 631 * Allowed types are listed below: 632 * - total_days Number of days Mollom has been used 633 * - total_accepted Total of blocked spam 634 * - total_rejected Total accepted posts (not working?) 635 * - yesterday_accepted Amount of spam blocked yesterday 636 * - yesterday_rejected Number of posts accepted yesterday (not working?) 637 * - today_accepted Amount of spam blocked today 638 * - today_rejected Number of posts accepted today (not working?) 639 * 640 * @return int 641 * @param string $type 642 */ 643 public static function getStatistics($type) 644 { 645 // possible types 646 $aPossibleTypes = array('total_days', 'total_accepted', 'total_rejected', 'yesterday_accepted', 'yesterday_rejected', 'today_accepted', 'today_rejected'); 647 648 // redefine 649 $type = (string) $type; 650 651 // validate 652 if(!in_array($type, $aPossibleTypes)) throw new Exception('Invalid type. Only '. implode(', ', $aPossibleTypes) .' are possible types.'); 653 654 // do the call 655 $responseString = self::doCall('getStatistics', array('type' => $type)); 656 657 // validate 658 if(!isset($responseString->params->param->value->int)) throw new Exception('Invalid response in getStatistics.'); 659 660 // return 661 return (int) $responseString->params->param->value->int; 662 } 663 664 665 /** 666 * Send feedback to Mollom. 667 * 668 * With this method you can help train Mollom. Implement this method if possible. The more feedback is provided the more accurate 669 * Mollom will be. 670 * 671 * Allowed feedback-strings are listed below: 672 * - spam Spam or unsolicited advertising 673 * - profanity Obscene, violent or profane content 674 * - low-quality Low-quality content or writing 675 * - unwanted Unwanted, taunting or off-topic content 676 * 677 * @return bool 678 * @param string $sessionId 679 * @param string $feedback 680 */ 681 public static function sendFeedback($sessionId, $feedback) 682 { 683 // possible feedback 684 $aPossibleFeedback = array('spam', 'profanity', 'low-quality', 'unwanted'); 685 686 // redefine 687 $sessionId = (string) $sessionId; 688 $feedback = (string) $feedback; 689 690 // validate 691 if(!in_array($feedback, $aPossibleFeedback)) throw new Exception('Invalid feedback. Only '. implode(', ', $aPossibleFeedback) .' are possible feedback-strings.'); 692 693 // build parameters 694 $parameters['session_id'] = $sessionId; 695 $parameters['feedback'] = $feedback; 696 697 // do the call 698 $responseString = self::doCall('sendFeedback', $parameters); 699 700 // validate 701 if(!isset($responseString->params->param->value->boolean)) throw new Exception('Invalid response in sendFeedback.'); 702 703 // return 704 if((string) $responseString->params->param->value->boolean == 1) return true; 705 706 // fallback 707 return false; 708 } 709 710 711 /** 712 * Set the allowed reverse proxy Addresses 713 * 714 * @return void 715 * @param array $addresses 716 */ 717 public static function setAllowedReverseProxyAddresses($addresses) 718 { 719 // store allowed ip-addresses 720 self::$allowedReverseProxyAddresses = (array) $addresses; 721 722 // set reverse proxy 723 self::$reverseProxy = (!empty($addresses)) ? true : false; 724 } 725 726 727 /** 728 * Set the private key 729 * 730 * @return void 731 * @param string $key 732 */ 733 public static function setPrivateKey($key) 734 { 735 self::$privateKey = (string) $key; 736 } 737 738 739 /** 740 * Set the public key 741 * 742 * @return void 743 * @param string $key 744 */ 745 public static function setPublicKey($key) 746 { 747 self::$publicKey = (string) $key; 748 } 749 750 751 /** 752 * Set the server list 753 * 754 * @return void 755 * @param array $servers 756 */ 757 public static function setServerList($servers) 758 { 759 // redefine 760 $server = (array) $servers; 761 762 // loop servers 763 foreach ($servers as $server) self::$serverList[] = $server; 764 } 765 766 767 /** 768 * Set timeout 769 * 770 * @return void 771 * @param int $timeout 772 */ 773 public static function setTimeOut($timeout) 774 { 775 // redefine 776 $timeout = (int) $timeout; 777 778 // validate 779 if($timeout == 0) throw new Exception('Invalid timeout. Timeout shouldn\'t be 0.'); 780 781 // set property 782 self::$timeout = $timeout; 783 } 784 785 786 /** 787 * Set the user agent 788 * 789 * @return void 790 * @param string $newUserAgent 791 */ 792 public static function setUserAgent($newUserAgent) 793 { 794 self::$userAgent .= ' '. (string) $newUserAgent; 795 } 796 797 798 /** 799 * Verifies your key 800 * 801 * Returns information about the status of your key. Mollom will respond with a boolean value (true/false). 802 * False means that your keys is disabled or doesn't exists. True means the key is enabled and working properly. 803 * 804 * @return bool 805 */ 806 public static function verifyKey() 807 { 808 // do the call 809 $responseString = self::doCall('verifyKey'); 810 811 // validate 812 if(!isset($responseString->params->param->value->boolean)) throw new Exception('Invalid response in verifyKey.'); 813 814 // return 815 if((string) $responseString->params->param->value->boolean == '1') return true; 816 817 // fallback 818 return false; 819 } 820 821} 822 823?> 824