Mercurial > hg > pnewss
comparison server.php @ 7:01dc7eeaf5df
Added some more checks to article data, added some commands, added 'dot stuffing' for block transfers
author | Ivo Smits <Ivo@UCIS.nl> |
---|---|
date | Tue, 12 Apr 2011 14:10:41 +0200 |
parents | 5d62af5270dd |
children | 005339a1b2ce |
comparison
equal
deleted
inserted
replaced
6:bc6045ed0b2e | 7:01dc7eeaf5df |
---|---|
24 while (TRUE) { | 24 while (TRUE) { |
25 $line = nntp_readline(STDIN); | 25 $line = nntp_readline(STDIN); |
26 if ($line === FALSE || $line === NULL) break; | 26 if ($line === FALSE || $line === NULL) break; |
27 $cmd = strtoupper(strtok($line, " \t")); | 27 $cmd = strtoupper(strtok($line, " \t")); |
28 switch ($cmd) { | 28 switch ($cmd) { |
29 case 'CAPABILITIES': | |
30 nntp_writeline(STDOUT, '101 Capability list:'); | |
31 nntp_writeline_data(STDOUT, 'VERSION 2'); | |
32 nntp_writeline_data(STDOUT, 'IMPLEMENTATION pNewss [http://wiki.ucis.nl/pNewss]'); | |
33 nntp_writeline_data(STDOUT, 'POST'); | |
34 nntp_writeline_data(STDOUT, 'READER'); | |
35 nntp_writeline_data(STDOUT, 'IHAVE'); | |
36 nntp_writeline_data(STDOUT, 'LIST ACTIVE'); | |
37 nntp_writeline(STDOUT, '.'); | |
38 //HDR, LIST, OVER, STARTTLS, STREAMING, | |
39 break; | |
40 case 'DATE': | |
41 nntp_writeline(STDOUT, '111 '.gmdate('YmdHis')); | |
42 break; | |
43 case 'HELP': | |
44 nntp_writeline(STDOUT, '100 Help text follows:'); | |
45 nntp_writeline_data(STDOUT, 'Supported commands: CAPABILITIES,DATE,HELP,LIST,GROUP,LISTGROUP,STAT,HEAD,BODY,ARTICLE,LAST,NEXT,POST,IHAVE,QUIT'); | |
46 nntp_writeline(STDOUT, '.'); | |
47 break; | |
29 case 'LIST': | 48 case 'LIST': |
30 nntp_writeline(STDOUT, '215 list of groups follows'); | 49 nntp_writeline(STDOUT, '215 list of groups follows'); |
31 foreach ($db->evalAllAssoc('SELECT * FROM `groups`') as $group) { | 50 foreach ($db->evalAllAssoc('SELECT * FROM `groups`') as $group) { |
32 $groupmessages = $db->evalRow('SELECT MIN(`number`), MAX(`number`) FROM `groupmessages` WHERE `group` = ?', $group['id']); | 51 $groupmessages = $db->evalRow('SELECT MIN(`number`), MAX(`number`) FROM `groupmessages` WHERE `group` = ?', $group['id']); |
33 nntp_writeline(STDOUT, $group['name'].' '.intval($groupmessages[1]).' '.intval($groupmessages[0]).' n'); | 52 nntp_writeline_data(STDOUT, $group['name'].' '.intval($groupmessages[1]).' '.intval($groupmessages[0]).' n'); |
34 } | 53 } |
35 nntp_writeline(STDOUT, '.'); | 54 nntp_writeline(STDOUT, '.'); |
36 break; | 55 break; |
37 case 'GROUP': | 56 case 'GROUP': |
57 case 'LISTGROUP': | |
38 $groupname = strtok(" \t"); | 58 $groupname = strtok(" \t"); |
39 $group = $db->evalRowAssoc('SELECT * FROM `groups` WHERE `name` = ?', $groupname); | 59 if ($groupname === FALSE) { |
60 $group = $currentgroup; | |
61 } else { | |
62 $group = $db->evalRowAssoc('SELECT * FROM `groups` WHERE `name` = ?', $groupname); | |
63 } | |
40 if ($group === FALSE) { | 64 if ($group === FALSE) { |
41 nntp_writeline(STDOUT, '411 No such group '.$groupname); | 65 nntp_writeline(STDOUT, '411 No such group '.$groupname); |
42 } else { | 66 } else { |
43 $currentgroup = $group; | 67 $currentgroup = $group; |
44 $groupmessages = $db->evalRow('SELECT MIN(`number`), MAX(`number`), COUNT(`number`) FROM `groupmessages` WHERE `group` = ?', $group['id']); | 68 $groupmessages = $db->evalRow('SELECT MIN(`number`), MAX(`number`), COUNT(`number`) FROM `groupmessages` WHERE `group` = ?', $group['id']); |
47 $currentarticle = NULL; | 71 $currentarticle = NULL; |
48 } else { | 72 } else { |
49 $currentarticle = $db->evalRowAssoc('SELECT * FROM `groupmessages` WHERE `group` = ? AND `number` = ?', array($group['id'], $groupmessages[0])); | 73 $currentarticle = $db->evalRowAssoc('SELECT * FROM `groupmessages` WHERE `group` = ? AND `number` = ?', array($group['id'], $groupmessages[0])); |
50 if ($currentarticle === FALSE) $currentarticle = NULL; | 74 if ($currentarticle === FALSE) $currentarticle = NULL; |
51 } | 75 } |
76 if ($cmd == 'LISTGROUP') { | |
77 $range = strtok(" \t"); | |
78 if ($range !== FALSE) { | |
79 $parts = explode('-', $range); | |
80 if (count($parts) == 1 || !strlen($parts[1])) { | |
81 $query = 'SELECT `number` FROM `groupmessages` WHERE `group` = ? AND `number` >= ?'; | |
82 $queryargs = array($group['id'], $parts[0]); | |
83 } else { | |
84 $query = 'SELECT `number` FROM `groupmessages` WHERE `group` = ? AND `number` BETWEEN ? AND ?'; | |
85 $queryargs = array($group['id'], $parts[0], $parts[1]); | |
86 } | |
87 } else { | |
88 $query = 'SELECT `number` FROM `groupmessages` WHERE `group` = ?'; | |
89 $queryargs = array($group['id']); | |
90 } | |
91 foreach ($db->evalColumn($query, $queryargs) as $number) nntp_writeline_data(STDOUT, $number); | |
92 nntp_writeline(STDOUT, '.'); | |
93 } | |
52 } | 94 } |
53 break; | 95 break; |
54 case 'STAT': | 96 case 'STAT': |
55 case 'HEAD': | 97 case 'HEAD': |
56 case 'BODY': | 98 case 'BODY': |
62 case 'HEAD': nntp_writeline(STDOUT, '221 '.$article['messagenumber'].' <'.$article['messageid'].'> head'); break; | 104 case 'HEAD': nntp_writeline(STDOUT, '221 '.$article['messagenumber'].' <'.$article['messageid'].'> head'); break; |
63 case 'BODY': nntp_writeline(STDOUT, '222 '.$article['messagenumber'].' <'.$article['messageid'].'> body'); break; | 105 case 'BODY': nntp_writeline(STDOUT, '222 '.$article['messagenumber'].' <'.$article['messageid'].'> body'); break; |
64 case 'STAT': nntp_writeline(STDOUT, '223 '.$article['messagenumber'].' <'.$article['messageid'].'> stat'); break; | 106 case 'STAT': nntp_writeline(STDOUT, '223 '.$article['messagenumber'].' <'.$article['messageid'].'> stat'); break; |
65 default: throw new Exception('Internal error'); | 107 default: throw new Exception('Internal error'); |
66 } | 108 } |
67 if ($cmd == 'HEAD' || $cmd == 'ARTICLE') foreach (explode("\r\n", $article['header']) as $line) nntp_writeline(STDOUT, $line); | 109 if ($cmd == 'HEAD' || $cmd == 'ARTICLE') foreach (explode("\r\n", $article['header']) as $line) nntp_writeline_data(STDOUT, $line); |
68 if ($cmd == 'ARTICLE') nntp_writeline(STDOUT, ''); | 110 if ($cmd == 'ARTICLE') nntp_writeline(STDOUT, ''); |
69 if ($cmd == 'BODY' || $cmd == 'ARTICLE') foreach (explode("\r\n", $article['body']) as $line) nntp_writeline(STDOUT, $line); | 111 if ($cmd == 'BODY' || $cmd == 'ARTICLE') foreach (explode("\r\n", $article['body']) as $line) nntp_writeline_data(STDOUT, $line); |
70 if ($cmd != 'STAT') nntp_writeline(STDOUT, '.'); | 112 if ($cmd != 'STAT') nntp_writeline(STDOUT, '.'); |
71 break; | 113 break; |
72 case 'LAST': | 114 case 'LAST': |
73 case 'NEXT': | 115 case 'NEXT': |
74 if ($currentarticle === NULL) { | 116 if ($currentarticle === NULL) { |
95 break; | 137 break; |
96 case 'POST': | 138 case 'POST': |
97 nntp_writeline(STDOUT, '340 Ok, recommended message-ID <'.md5(time().rand()).'@pNews.Core.UCIS.nl>'); | 139 nntp_writeline(STDOUT, '340 Ok, recommended message-ID <'.md5(time().rand()).'@pNews.Core.UCIS.nl>'); |
98 $lines = nntp_readlines(STDIN); | 140 $lines = nntp_readlines(STDIN); |
99 try { | 141 try { |
100 $msgid = nntp_article_store($lines); | 142 $messageid = nntp_article_store($lines); |
101 nntp_writeline(STDOUT, '240 Article received <'.$msgid.'>'); | 143 nntp_writeline(STDOUT, '240 Article received <'.$messageid.'>'); |
102 } catch (Exception $ex) { | 144 } catch (Exception $ex) { |
103 nntp_writeline(STDOUT, '441 '.$ex->getMessage()); | 145 nntp_writeline(STDOUT, '441 '.$ex->getMessage()); |
104 } | 146 } |
105 break; | 147 break; |
148 case 'IHAVE': | |
149 $messageid = strtok(" \t"); | |
150 if ($messageid === FALSE || strlen($messageid) <= 2 || $messageid[0] != '<' || $messageid[strlen($messageid)-1] == '>') { | |
151 nntp_writeline(STDOUT, '435 Argument error'); | |
152 break; | |
153 } | |
154 $messageid = substr($messageid, 1, -1); | |
155 if ($db->evalRow('SELECT `id` FROM `messages` WHERE `messageid` = ?', $messageid) !== FALSE) { | |
156 nntp_writeline(STDOUT, '435 Duplicate'); | |
157 break; | |
158 } | |
159 nntp_writeline(STDOUT, '335 Send article to be transferred'); | |
160 $lines = nntp_readlines(STDIN); | |
161 try { | |
162 $messageid = nntp_article_store($lines); | |
163 nntp_writeline(STDOUT, '235 Article received <'.$messageid.'>'); | |
164 } catch (Exception $ex) { | |
165 nntp_writeline(STDOUT, '437 '.$ex->getMessage()); | |
166 } | |
167 break; | |
106 case 'QUIT': | 168 case 'QUIT': |
107 nntp_writeline(STDOUT, '205 .'); | 169 nntp_writeline(STDOUT, '205 Bye.'); |
108 return; | 170 return; |
109 default: | 171 default: |
110 nntp_writeline(STDOUT, '500 Command not understood'); | 172 nntp_writeline(STDOUT, '500 Command not understood'); |
111 break; | 173 break; |
112 } | 174 } |