Realtime.php 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739
  1. <?php
  2. // +-----------------------------------------------------------------------+
  3. // | |
  4. // | Copyright © 2003 Heino H. Gehlsen. All Rights Reserved. |
  5. // | http://www.heino.gehlsen.dk/software/license |
  6. // | |
  7. // +-----------------------------------------------------------------------+
  8. // | |
  9. // | This work (including software, documents, or other related items) is |
  10. // | being provided by the copyright holders under the following license. |
  11. // | By obtaining, using and/or copying this work, you (the licensee) |
  12. // | agree that you have read, understood, and will comply with the |
  13. // | following terms and conditions: |
  14. // | |
  15. // | Permission to use, copy, modify, and distribute this software and |
  16. // | its documentation, with or without modification, for any purpose and |
  17. // | without fee or royalty is hereby granted, provided that you include |
  18. // | the following on ALL copies of the software and documentation or |
  19. // | portions thereof, including modifications, that you make: |
  20. // | |
  21. // | 1. The full text of this NOTICE in a location viewable to users of |
  22. // | the redistributed or derivative work. |
  23. // | |
  24. // | 2. Any pre-existing intellectual property disclaimers, notices, or |
  25. // | terms and conditions. If none exist, a short notice of the |
  26. // | following form (hypertext is preferred, text is permitted) should |
  27. // | be used within the body of any redistributed or derivative code: |
  28. // | "Copyright © 2003 Heino H. Gehlsen. All Rights Reserved. |
  29. // | http://www.heino.gehlsen.dk/software/license" |
  30. // | |
  31. // | 3. Notice of any changes or modifications to the files, including |
  32. // | the date changes were made. (We recommend you provide URIs to |
  33. // | the location from which the code is derived.) |
  34. // | |
  35. // | THIS SOFTWARE AND DOCUMENTATION IS PROVIDED "AS IS," AND COPYRIGHT |
  36. // | HOLDERS MAKE NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR IMPLIED, |
  37. // | INCLUDING BUT NOT LIMITED TO, WARRANTIES OF MERCHANTABILITY OR |
  38. // | FITNESS FOR ANY PARTICULAR PURPOSE OR THAT THE USE OF THE SOFTWARE |
  39. // | OR DOCUMENTATION WILL NOT INFRINGE ANY THIRD PARTY PATENTS, |
  40. // | COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS. |
  41. // | |
  42. // | COPYRIGHT HOLDERS WILL NOT BE LIABLE FOR ANY DIRECT, INDIRECT, |
  43. // | SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF ANY USE OF THE |
  44. // | SOFTWARE OR DOCUMENTATION. |
  45. // | |
  46. // | The name and trademarks of copyright holders may NOT be used in |
  47. // | advertising or publicity pertaining to the software without specific, |
  48. // | written prior permission. Title to copyright in this software and any |
  49. // | associated documentation will at all times remain with copyright |
  50. // | holders. |
  51. // | |
  52. // +-----------------------------------------------------------------------+
  53. // | |
  54. // | This license is based on the "W3C® SOFTWARE NOTICE AND LICENSE". |
  55. // | No changes have been made to the "W3C® SOFTWARE NOTICE AND LICENSE", |
  56. // | except for the references to the copyright holder, which has either |
  57. // | been changes or removed. |
  58. // | |
  59. // +-----------------------------------------------------------------------+
  60. // $Id: Realtime.php,v 1.1 2003/10/10 13:11:19 heino Exp $
  61. require_once 'Net/NNTP/Protocol.php';
  62. require_once 'Net/NNTP/Header.php';
  63. require_once 'Net/NNTP/Message.php';
  64. /* NNTP Authentication modes */
  65. define('NET_NNTP_AUTHORIGINAL', 'original');
  66. define('NET_NNTP_AUTHSIMPLE', 'simple');
  67. define('NET_NNTP_AUTHGENERIC', 'generic');
  68. /**
  69. * The Net_NNTP_Realtime class is a frontend class to the
  70. * Net_NNTP_Protocol class. It does everything in realtime...
  71. *
  72. * @author Heino H. Gehlsen <heino@gehlsen.dk>
  73. */
  74. class Net_NNTP_Realtime extends Net_NNTP_Protocol
  75. {
  76. // {{{ properties
  77. /**
  78. * Used for storing information about the currently selected group
  79. *
  80. * @var array
  81. * @access private
  82. * @since 0.3
  83. */
  84. var $_currentGroup = null;
  85. // }}}
  86. // {{{ constructor
  87. /**
  88. * Constructor
  89. */
  90. function Net_NNTP_Realtime()
  91. {
  92. parent::Net_NNTP_Protocol();
  93. }
  94. // }}}
  95. // {{{ connect()
  96. /**
  97. * Connect to the NNTP-server.
  98. *
  99. * @param optional string $host The adress of the NNTP-server to connect to.
  100. * @param optional int $port The port to connect to.
  101. *
  102. * @return mixed (bool) true on success or (object) pear_error on failure
  103. * @access public
  104. * @see Net_NNTP::quit()
  105. * @see Net_NNTP::authenticate()
  106. * @see Net_NNTP::connectAuthenticated()
  107. */
  108. function connect($host = NET_NNTP_PROTOCOL_DEFAULT_HOST,
  109. $port = NET_NNTP_PROTOCOL_DEFAULT_PORT)
  110. {
  111. return parent::connect($host, $port);
  112. }
  113. // }}}
  114. // {{{ connectAuthenticated()
  115. /**
  116. * Connect to the NNTP-server, and authenticate using given username and password.
  117. *
  118. * @param optional string $user The username.
  119. * @param optional string $pass The password.
  120. * @param optional string $host The IP-address of the NNTP-server to connect to.
  121. * @param optional int $port The port to connect to.
  122. * @param optional string $authmode The authentication mode.
  123. *
  124. * @return mixed (bool) true on success or (object) pear_error on failure
  125. * @access public
  126. * @since 0.3
  127. * @see Net_NNTP::connect()
  128. * @see Net_NNTP::authenticate()
  129. * @see Net_NNTP::quit()
  130. */
  131. function connectAuthenticated($user = null,
  132. $pass = null,
  133. $host = NET_NNTP_PROTOCOL_DEFAULT_HOST,
  134. $port = NET_NNTP_PROTOCOL_DEFAULT_PORT,
  135. $authmode = NET_NNTP_AUTHORIGINAL)
  136. {
  137. $R = $this->connect($host, $port);
  138. if (PEAR::isError($R)) {
  139. return $R;
  140. }
  141. // Authenticate if username is given
  142. if ($user != null) {
  143. $R = $this->authenticate($user, $pass, $authmode);
  144. if (PEAR::isError($R)) {
  145. return $R;
  146. }
  147. }
  148. return true;
  149. }
  150. // }}}
  151. // {{{ quit()
  152. /**
  153. * Close connection to the newsserver
  154. *
  155. * @access public
  156. * @see Net_NNTP::connect()
  157. */
  158. function quit()
  159. {
  160. return $this->cmdQuit();
  161. }
  162. // }}}
  163. // {{{ authenticate()
  164. /**
  165. * Authenticate
  166. *
  167. * Auth process (not yet standarized but used any way)
  168. * http://www.mibsoftware.com/userkt/nntpext/index.html
  169. *
  170. * @param string $user The username
  171. * @param optional string $pass The password
  172. * @param optional string $mode The authentication mode (original, simple, generic).
  173. *
  174. * @return mixed (bool) true on success or (object) pear_error on failure
  175. * @access public
  176. * @see Net_NNTP::connect()
  177. * @see Net_NNTP::connectAuthenticated()
  178. */
  179. function authenticate($user, $pass, $mode = NET_NNTP_AUTHORIGINAL)
  180. {
  181. // Username is a must...
  182. if ($user == null) {
  183. return $this->throwError('No username supplied', null);
  184. }
  185. // Use selected authentication method
  186. switch ($mode) {
  187. case NET_NNTP_AUTHORIGINAL:
  188. return $this->cmdAuthinfo($user, $pass);
  189. break;
  190. case NET_NNTP_AUTHSIMPLE:
  191. return $this->cmdAuthinfoSimple($user, $pass);
  192. break;
  193. case NET_NNTP_AUTHGENERIC:
  194. return $this->cmdAuthinfoGeneric($user, $pass);
  195. break;
  196. default:
  197. return $this->throwError("The auth mode: '$mode' is unknown", null);
  198. }
  199. }
  200. // }}}
  201. // {{{ isConnected()
  202. /**
  203. * Test whether a connection is currently open.
  204. *
  205. * @return bool true or false
  206. * @access public
  207. * @see Net_NNTP::connect()
  208. * @see Net_NNTP::quit()
  209. */
  210. function isConnected()
  211. {
  212. return parent::isConnected();
  213. }
  214. // }}}
  215. // {{{ selectGroup()
  216. /**
  217. * Selects a newsgroup
  218. *
  219. * @param string $newsgroup Newsgroup name
  220. *
  221. * @return mixed (array) Info about the newsgroup on success or (object) pear_error on failure
  222. * @access public
  223. * @see Net_NNTP::group()
  224. * @see Net_NNTP::first()
  225. * @see Net_NNTP::last()
  226. * @see Net_NNTP::count()
  227. * @see Net_NNTP::getGroups()
  228. */
  229. function selectGroup($newsgroup)
  230. {
  231. $response_arr = $this->cmdGroup($newsgroup);
  232. if (PEAR::isError($response_arr)) {
  233. return $response_arr;
  234. }
  235. // Store group info in the object
  236. $this->_currentGroup = $response_arr;
  237. return $response_arr;
  238. }
  239. // }}}
  240. // {{{ getGroups()
  241. /**
  242. * Fetches a list of all avaible newsgroups
  243. *
  244. * @return mixed (array) nested array with informations about existing newsgroups on success or (object) pear_error on failure
  245. * @access public
  246. * @see Net_NNTP::selectGroup()
  247. * @see Net_NNTP::getDescriptions()
  248. */
  249. function getGroups()
  250. {
  251. // Get groups
  252. $groups = $this->cmdList();
  253. if (PEAR::isError($groups)) {
  254. return $groups;
  255. }
  256. return $groups;
  257. }
  258. // }}}
  259. // {{{ getDescriptions()
  260. /**
  261. * Fetches a list of all avaible newsgroup descriptions.
  262. *
  263. * @return mixed (array) nested array with description of existing newsgroups on success or (object) pear_error on failure
  264. * @access public
  265. * @see Net_NNTP::getGroups()
  266. */
  267. function getDescriptions()
  268. {
  269. // Get group descriptions
  270. $descriptions = $this->cmdListNewsgroups();
  271. if (PEAR::isError($descriptions)) {
  272. return $descriptions;
  273. }
  274. return $descriptions;
  275. }
  276. // }}}
  277. // {{{ getOverview()
  278. /**
  279. * Fetch message header fields from message number $first to $last
  280. *
  281. * The format of the returned array is:
  282. * $messages[message_id][header_name]
  283. *
  284. * @param integer $first first article to fetch
  285. * @param integer $last last article to fetch
  286. *
  287. * @return mixed (array) nested array of message and their headers on success or (object) pear_error on failure
  288. * @access public
  289. * @see Net_NNTP::getOverviewFormat()
  290. * @see Net_NNTP::getReferencesOverview()
  291. */
  292. function getOverview($first, $last)
  293. {
  294. $overview = $this->cmdXOver($first, $last);
  295. if (PEAR::isError($overview)) {
  296. return $overview;
  297. }
  298. return $overview;
  299. }
  300. // }}}
  301. // {{{ getOverviewFmt()
  302. /**
  303. * Returns a list of avaible headers which are send from NNTP-server to the client for every news message
  304. *
  305. * @return mixed (array) header names on success or (object) pear_error on failure
  306. * @access public
  307. * @see Net_NNTP::getOverview()
  308. */
  309. function getOverviewFormat()
  310. {
  311. return $this->cmdListOverviewFmt();
  312. }
  313. // }}}
  314. // {{{ getReferencesOverview()
  315. /**
  316. * Fetch a list of each message's reference header.
  317. *
  318. * @param integer $first first article to fetch
  319. * @param integer $last last article to fetch
  320. *
  321. * @return mixed (array) nested array of references on success or (object) pear_error on failure
  322. * @access public
  323. * @see Net_NNTP::getOverview()
  324. */
  325. function getReferencesOverview($first, $last)
  326. {
  327. $overview = $this->cmdXROver($first, $last);
  328. if (PEAR::isError($overview)) {
  329. return $overview;
  330. }
  331. return $overview;
  332. }
  333. // }}}
  334. // {{{ post()
  335. /**
  336. * Post an article to a number of newsgroups.
  337. *
  338. * (Among the aditional headers you might think of adding could be:
  339. * "NNTP-Posting-Host: <ip-of-author>", which should contain the IP-address
  340. * of the author of the post, so the message can be traced back to him.
  341. * Or "Organization: <org>" which contain the name of the organization
  342. * the post originates from)
  343. *
  344. * @param string $newsgroups The newsgroup to post to.
  345. * @param string $subject The subject of the post.
  346. * @param string $body The body of the post itself.
  347. * @param string $from Name + email-adress of sender.
  348. * @param optional string $aditional Aditional headers to send.
  349. *
  350. * @return mixed (string) server response on success or (object) pear_error on failure
  351. * @access public
  352. */
  353. function post($newsgroups, $subject, $body, $from, $aditional = '')
  354. {
  355. return $this->cmdPost($newsgroups, $subject, $body, $from, $aditional);
  356. }
  357. // }}}
  358. // {{{ getArticle()
  359. /**
  360. * Get an article
  361. *
  362. * The v0.2 version of the this function (which returned the article as a string) has been renamed to getArticleRaw().
  363. *
  364. * @param mixed $article Either the message-id or the message-number on the server of the article to fetch.
  365. *
  366. * @return mixed (object) message object on success or (object) pear_error on failure
  367. * @access public
  368. * @see Net_NNTP::getArticleRaw()
  369. * @see Net_NNTP::getHeader()
  370. * @see Net_NNTP::getBody()
  371. */
  372. function getArticle($article)
  373. {
  374. $message = $this->getArticleRaw($article, false);
  375. if (PEAR::isError($message)) {
  376. return $data;
  377. }
  378. $M = Net_NNTP_Message::create($message);
  379. return $M;
  380. }
  381. // }}}
  382. // {{{ getArticleRaw()
  383. /**
  384. * Get a article (raw data)
  385. *
  386. * @param mixed $article Either the message-id or the message-number on the server of the article to fetch.
  387. * @param optional bool $implode When true the result array is imploded to a string, defaults to false.
  388. *
  389. * @return mixed (array/string) The article on success or (object) pear_error on failure
  390. * @access public
  391. * @see Net_NNTP::getArticle()
  392. * @see Net_NNTP::getHeaderRaw()
  393. * @see Net_NNTP::getBodyRaw()
  394. */
  395. function getArticleRaw($article, $implode = false)
  396. {
  397. $data = $this->cmdArticle($article);
  398. if (PEAR::isError($data)) {
  399. return $data;
  400. }
  401. if ($implode == true) {
  402. $data = implode("\r\n", $data);
  403. }
  404. return $data;
  405. }
  406. // }}}
  407. // {{{ getHeader()
  408. /**
  409. * Get the header of an article
  410. *
  411. * @param mixed $article Either the (string) message-id or the (int) message-number on the server of the article to fetch.
  412. *
  413. * @return mixed (object) header object on success or (object) pear_error on failure
  414. * @access public
  415. * @see Net_NNTP::getHeaderRaw()
  416. * @see Net_NNTP::getArticle()
  417. * @see Net_NNTP::getBody()
  418. */
  419. function getHeader($article)
  420. {
  421. $header = $this->getHeaderRaw($article, false);
  422. if (PEAR::isError($header)) {
  423. return $header;
  424. }
  425. $H = Net_NNTP_Header::create($header);
  426. return $H;
  427. }
  428. // }}}
  429. // {{{ getHeaderRaw()
  430. /**
  431. * Get the header of an article (raw data)
  432. *
  433. * @param mixed $article Either the (string) message-id or the (int) message-number on the server of the article to fetch.
  434. * @param optional bool $implode When true the result array is imploded to a string, defaults to false.
  435. *
  436. * @return mixed (array/string) header fields on success or (object) pear_error on failure
  437. * @access public
  438. * @see Net_NNTP::getHeader()
  439. * @see Net_NNTP::getArticleRaw()
  440. * @see Net_NNTP::getBodyRaw()
  441. */
  442. function getHeaderRaw($article, $implode = false)
  443. {
  444. $data = $this->cmdHead($article);
  445. if (PEAR::isError($data)) {
  446. return $data;
  447. }
  448. if ($implode == true) {
  449. $data = implode("\r\n", $data);
  450. }
  451. return $data;
  452. }
  453. // }}}
  454. // {{{ getBody()
  455. // Not written yet...
  456. // }}}
  457. // {{{ getBodyRaw()
  458. /**
  459. * Get the body of an article (raw data)
  460. *
  461. * @param mixed $article Either the message-id or the message-number on the server of the article to fetch.
  462. * @param optional bool $implode When true the result array is imploded to a string, defaults to false.
  463. *
  464. * @return mixed (array/string) body on success or (object) pear_error on failure
  465. * @access public
  466. * @see Net_NNTP::getBody()
  467. * @see Net_NNTP::getHeaderRaw()
  468. * @see Net_NNTP::getArticleRaw()
  469. */
  470. function getBodyRaw($article, $implode = false)
  471. {
  472. $data = $this->cmdBody($article);
  473. if (PEAR::isError($data)) {
  474. return $data;
  475. }
  476. if ($implode == true) {
  477. $data = implode("\r\n", $data);
  478. }
  479. return $data;
  480. }
  481. // }}}
  482. // {{{ getGroupArticles()
  483. /**
  484. * Experimental
  485. *
  486. * @access public
  487. * @since 0.3
  488. */
  489. function getGroupArticles($newsgroup)
  490. {
  491. return $this->cmdListgroup($newsgroup);
  492. }
  493. // }}}
  494. // {{{ getNewGroups()
  495. /**
  496. * Experimental
  497. *
  498. * @access public
  499. * @since 0.3
  500. */
  501. function getNewGroups($time)
  502. {
  503. switch (gettype($time)) {
  504. case 'integer':
  505. break;
  506. case 'string':
  507. $time = (int) strtotime($time);
  508. break;
  509. default:
  510. return $this->throwError('');
  511. }
  512. return $this->cmdNewgroups($time);
  513. }
  514. // }}}
  515. // {{{ getNewNews()
  516. /**
  517. * Experimental
  518. *
  519. * @access public
  520. * @since 0.3
  521. */
  522. function getNewNews($time, $newsgroups = '*')
  523. {
  524. switch (gettype($time)) {
  525. case 'integer':
  526. break;
  527. case 'string':
  528. $time = (int) strtotime($time);
  529. break;
  530. default:
  531. return PEAR::throwError('UPS...');
  532. }
  533. return $this->cmdNewnews($time, $newsgroups);
  534. }
  535. // }}}
  536. // {{{ getDate()
  537. /**
  538. * Get the NNTP-server's internal date
  539. *
  540. * Get the date from the newsserver format of returned date:
  541. *
  542. * @param optional int $format
  543. * - 0: $date - timestamp
  544. * - 1: $date['y'] - year
  545. * $date['m'] - month
  546. * $date['d'] - day
  547. *
  548. * @return mixed (mixed) date on success or (object) pear_error on failure
  549. * @access public
  550. * @since 0.3
  551. */
  552. function getDate($format = 1)
  553. {
  554. $date = $this->cmdDate();
  555. if (PEAR::isError($date)) {
  556. return $date;
  557. }
  558. switch ($format) {
  559. case 1:
  560. return array('y' => substr($date, 0, 4), 'm' => substr($date, 4, 2), 'd' => substr($date, 6, 2));
  561. break;
  562. case 0:
  563. default:
  564. return $date;
  565. break;
  566. }
  567. }
  568. // }}}
  569. // {{{ count()
  570. /**
  571. * Number of articles in currently selected group
  572. *
  573. * @return integer number of article in group
  574. * @access public
  575. * @since 0.3
  576. * @see Net_NNTP::group()
  577. * @see Net_NNTP::first()
  578. * @see Net_NNTP::last()
  579. * @see Net_NNTP::selectGroup()
  580. */
  581. function count()
  582. {
  583. return $this->_currentGroup['count'];
  584. }
  585. // }}}
  586. // {{{ last()
  587. /**
  588. * Maximum article number in currently selected group
  589. *
  590. * @return integer number of last article
  591. * @access public
  592. * @since 0.3
  593. * @see Net_NNTP::first()
  594. * @see Net_NNTP::group()
  595. * @see Net_NNTP::count()
  596. * @see Net_NNTP::selectGroup()
  597. */
  598. function last()
  599. {
  600. return $this->_currentGroup['last'];
  601. }
  602. // }}}
  603. // {{{ first()
  604. /**
  605. * Minimum article number in currently selected group
  606. *
  607. * @return integer number of first article
  608. * @access public
  609. * @since 0.3
  610. * @see Net_NNTP::last()
  611. * @see Net_NNTP::group()
  612. * @see Net_NNTP::count()
  613. * @see Net_NNTP::selectGroup()
  614. */
  615. function first()
  616. {
  617. return $this->_currentGroup['first'];
  618. }
  619. // }}}
  620. // {{{ group()
  621. /**
  622. * Currently selected group
  623. *
  624. * @return string group name
  625. * @access public
  626. * @since 0.3
  627. * @see Net_NNTP::first()
  628. * @see Net_NNTP::last()
  629. * @see Net_NNTP::count()
  630. * @see Net_NNTP::selectGroup()
  631. */
  632. function group()
  633. {
  634. return $this->_currentGroup['group'];
  635. }
  636. // }}}
  637. // {{{ command()
  638. /**
  639. * Issue a command to the NNTP server
  640. *
  641. * @param string $cmd The command to launch, ie: "ARTICLE 1004853"
  642. *
  643. * @return mixed (int) response code on success or (object) pear_error on failure
  644. * @access public
  645. */
  646. function command($cmd)
  647. {
  648. return $this->_sendCommand($cmd);
  649. }
  650. // }}}
  651. }
  652. ?>