support nocache files to disable caching
[noxon-gateway.git] / www / index.php
1 <?php
2 require_once __DIR__ . '/../src/header.php';
3
4 if (strtolower($fullUri) == '/setupapp/radio567/asp/browsexpa/loginxml.asp?token=0'
5     || $fullUri == '/RadioNativeLogin.phpb'
6 ) {
7     //initial login for "internet radio", podcasts and "my noxon"
8     header('Content-type: text/html');
9     readfile($dataDir . 'login-camelcase.xml');
10     exit();
11 } else if ($path == '/setupapp/radio567/asp/BrowseXPA/LoginXML.asp') {
12     //"Internet Radio"
13     $path = '/internetradio/';
14 } else if ($path == '/setupapp/radio567/asp/BrowseXPA/navXML.asp') {
15     //"Podcasts"
16     $path = '/podcasts/';
17 } else if ($path == '/RadioNative.php') {
18     //"My Noxon"
19     $path = '/mynoxon/';
20 } else if ($path == '/setupapp/radio567/asp/BrowseXML/FavXML.asp') {
21     //Internet Radio Station favorites favorited on device
22     sendMessage('Unsupported');
23 } else if ($path == '/RadioNativeFavorites.php') {
24     //Favorites, defined via web interface
25     sendMessage('Unsupported');
26 }
27
28 handleRequest(ltrim($path, '/'));
29
30 function handleRequest($path)
31 {
32     global $varDir;
33     if (strpos($path, '..') !== false) {
34         sendMessage('No');
35         return;
36     }
37
38     if (substr($path, 0, 14) == 'internetradio/') {
39         require_once 'mediatomb.php';
40         handleMediatomb('browse', $path, 'internetradio/');
41         return;
42     } else if (substr($path, 0, 11) == '.mt-single/') {
43         require_once 'mediatomb.php';
44         handleMediatomb('single', $path, '.mt-single/');
45         return;
46     }
47
48
49     $fullPath = $varDir . $path;
50     if (!file_exists($fullPath)) {
51         sendMessage('Not found: ' . $path);
52         return;
53     }
54
55     $ext = pathinfo($path, PATHINFO_EXTENSION);
56     if (is_dir($fullPath)) {
57         sendDir($path);
58     } else if ($ext == 'url') {
59         require_once 'podcasts.php';
60         sendPodcast($path);
61     } else if ($ext == 'txt') {
62         sendTextFile($path);
63     } else if (is_executable($fullPath)) {
64         sendScript($path);
65     } else {
66         sendMessage('Unknown file type');
67     }
68 }
69
70 function pathEncode($urlPath)
71 {
72     return str_replace('%2F', '/', rawurlencode($urlPath));
73 }
74
75 function sendDir($path)
76 {
77     global $varDir;
78
79     $listItems = array();
80     $enablePaging = true;
81
82     $entries = glob(str_replace('//', '/', $varDir . rtrim($path, '/') . '/*'));
83     $count = 0;
84     $noCache = false;
85     foreach ($entries as $entry) {
86         $urlPath = pathEncode(substr($entry, strlen($varDir)));
87         $ext = pathinfo($entry, PATHINFO_EXTENSION);
88
89         $titleBase = basename($entry);
90         $titleBase = preg_replace('#^[0-9]+_#', '', $titleBase);
91         if (is_dir($entry)) {
92             ++$count;
93             $listItems[] = getDirItem($titleBase, $urlPath . '/');
94         } else if ($ext == 'url') {
95             //podcast
96             ++$count;
97             $listItems[] = getPodcastItem(basename($titleBase, '.url'), $urlPath);
98         } else if (is_executable($entry)
99             && strpos(basename($entry), '.auto') !== false
100         ) {
101             //automatically execute script while listing this directory
102             addScriptOutput($listItems, $entry);
103             $enablePaging = false;
104         } else if ($ext == 'txt' || is_executable($entry)) {
105             //plain text file
106             ++$count;
107             $listItems[] = getDirItem(basename($titleBase, '.' . $ext), $urlPath);
108         } else  if (basename($entry) == 'nocache') {
109             $noCache = true;
110         }
111     }
112     if (!$count) {
113         $listItems[] = getMessageItem('No files or folders');
114     }
115     sendListItems(
116         $listItems, buildPreviousItem($path),
117         $enablePaging, $noCache
118     );
119 }
120
121 function sendScript($path)
122 {
123     global $varDir;
124
125     $listItems = array();
126
127     $fullPath = $varDir . $path;
128     addScriptOutput($listItems, $fullPath);
129     sendListItems($listItems, buildPreviousItem($path), false);
130 }
131
132 function addScriptOutput(&$listItems, $fullPath)
133 {
134     exec($fullPath . ' 2>&1', $output, $retVal);
135
136     if ($retVal == 0) {
137         addTextLines($listItems, $output);
138     } else {
139         $listItems[] = getMessageItem('Error executing script');
140         addTextLines($listItems, $output);
141     }
142 }
143
144 function sendTextFile($path)
145 {
146     global $varDir;
147     $listItems = array();
148
149     $lines = file($varDir . $path);
150     addTextLines($listItems, $lines);
151     sendListItems($listItems, buildPreviousItem($path));
152 }
153
154 function addTextLines(&$listItems, $lines)
155 {
156     foreach ($lines as $line) {
157         $line = trim($line);
158         if ($line != '') {
159             $listItems[] = getDisplayItem($line);
160         }
161     }
162 }
163
164 function getDisplayItem($line)
165 {
166     $line = preg_replace('#\s+#', ' ', $line);
167     return '<Item>'
168         . '<ItemType>Display</ItemType>'
169         . '<Display>' . nox_esc($line) . '</Display>'
170         . '</Item>';
171 }
172
173 function getDirItem($title, $urlPath)
174 {
175     global $host1, $host2;
176     return '<Item>'
177         . '<ItemType>Dir</ItemType>'
178         . '<Title>' . nox_esc($title) . '</Title>'
179         . '<UrlDir>' . $host1 . nox_esc($urlPath) . '</UrlDir>'
180         . '<UrlDirBackUp>' . $host2 . nox_esc($urlPath) . '</UrlDirBackUp>'
181         . '</Item>';
182 }
183
184 function getEpisodeItem($title, $fullUrl, $desc, $type)
185 {
186     return '<Item>'
187         . '<ItemType>ShowEpisode</ItemType>'
188         . '<ShowEpisodeName>' . nox_esc($title) . '</ShowEpisodeName>'
189         . '<ShowEpisodeURL>' . htmlspecialchars($fullUrl) . '</ShowEpisodeURL>'
190         . '<ShowDesc>' . nox_esc($desc) . '</ShowDesc>'
191         . '<ShowMime>' . $type . '</ShowMime>'
192         . '</Item>';
193 }
194
195 function getPodcastItem($title, $urlPath)
196 {
197     global $host1;
198     return '<Item>'
199         . '<ItemType>ShowOnDemand</ItemType>'
200         . '<ShowOnDemandName>' . nox_esc($title) . '</ShowOnDemandName>'
201         . '<ShowOnDemandURL>' . $host1 . nox_esc($urlPath) . '</ShowOnDemandURL>'
202         . '</Item>';
203 }
204
205 function getMessageItem($msg)
206 {
207     return '<Item>'
208         . '<ItemType>Message</ItemType>'
209         . '<Message>' . nox_esc($msg) . '</Message>'
210         . '</Item>';
211 }
212
213 function getPreviousItem($urlPath)
214 {
215     global $host1, $host2;
216     return '<Item>'
217         . '<ItemType>Previous</ItemType>'
218         . '<UrlPrevious>' . $host1 . nox_esc($urlPath) . '</UrlPrevious>'
219         . '<UrlPreviousBackUp>' . $host1 . nox_esc($urlPath) . '</UrlPreviousBackUp>'
220         . '</Item>';
221 }
222
223 function buildPreviousItem($urlPath)
224 {
225     $parentDir = dirname($urlPath) . '/';
226     if ($parentDir == '/') {
227         return null;
228     }
229     return getPreviousItem($parentDir);
230 }
231
232 function nox_esc($string)
233 {
234     return utf8_decode(htmlspecialchars($string));
235 }
236
237 function sendMessage($msg)
238 {
239     sendListItems(array(getMessageItem($msg)));
240 }
241
242 function sendListItems(
243     $listItems, $previous = null, $enablePaging = true, $noCache = false
244 ) {
245     $startitems = 1;
246     $enditems   = 100000;
247     if (isset($_GET['startitems'])) {
248         $startitems = (int) $_GET['startitems'];
249     }
250     if (isset($_GET['enditems'])) {
251         $enditems = (int) $_GET['enditems'];
252     }
253
254     if ($enablePaging) {
255         $itemCount = count($listItems);
256     } else {
257         $itemCount = -1;
258     }
259     if ($previous !== null) {
260         $previous .= "\n";
261     }
262
263     $xml = '<?xml version="1.0" encoding="iso-8859-1"?>' . "\n";
264     $xml .= '<?xml-stylesheet type="text/xsl" href="/html.xsl"?>' . "\n";
265     $xml .= '<ListOfItems>' . "\n";
266     if ($noCache) {
267         $xml .= "<NoCache>1</NoCache>\n";
268     }
269     $xml .= '<ItemCount>' . $itemCount . '</ItemCount>' . "\n";
270     $xml .= $previous;
271
272     $num = 0;
273     foreach ($listItems as $item) {
274         ++$num;
275         if (!$enablePaging || ($num >= $startitems && $num <= $enditems)) {
276             $xml .= $item . "\n";
277         }
278     }
279     $xml .= "</ListOfItems>\n";
280
281     header('Content-type: text/xml; charset=iso-8859-1');
282     echo $xml;
283 }
284 ?>