fix mynoxon login
[noxon-gateway.git] / www / index.php
index cc0be0e5c25c009c7f0b2383b17b2cc26ce956cd..1ec3bf1de81f0341cbeb5110c6515edb133e376a 100644 (file)
 <?php
-set_include_path(get_include_path() . PATH_SEPARATOR . __DIR__ . '/../src/');
-$fullUri = $_SERVER['REQUEST_URI'];
-$path    = $_SERVER['REDIRECT_URL'];
-$dataDir = __DIR__ . '/../data/';
-
-if (strtolower($fullUri) == '/setupapp/radio567/asp/browsexpa/loginxml.asp?token=0') {
-    //initial login for "internet radio" and podcasts
-    //lowercase tags
-    header('Content-type: text/html');
-    readfile($dataDir . 'initial-login.xml');
-    exit();
-} else if ($fullUri == '/RadioNativeLogin.php') {
-    //initial login for "My noxon"
-    //this one wants CamelCased tags
+require_once __DIR__ . '/../src/header.php';
+
+if (strtolower($fullUri) == '/setupapp/radio567/asp/browsexpa/loginxml.asp?token=0'
+    || $fullUri == '/RadioNativeLogin.php'
+) {
+    //initial login for "internet radio", podcasts and "my noxon"
     header('Content-type: text/html');
-    readfile($dataDir . 'login-mynoxon.xml');
+    readfile($dataDir . 'login-camelcase.xml');
     exit();
 } else if ($path == '/setupapp/radio567/asp/BrowseXPA/LoginXML.asp') {
     //"Internet Radio"
-    header('Content-type: text/xml');
-    sendList('internetradio');
-    exit();
+    $path = '/internetradio/';
 } else if ($path == '/setupapp/radio567/asp/BrowseXPA/navXML.asp') {
     //"Podcasts"
-    require_once 'podcasts.php';
-    sendPodcastList();
-    exit();
-} else if (substr($path, 0, 9) == '/podcasts') {
-    require_once 'podcasts.php';
-    sendPodcast($path);
-    exit();    
+    $path = '/podcasts/';
 } else if ($path == '/RadioNative.php') {
     //"My Noxon"
-    header('Content-type: text/xml');
-    sendList('mynoxon');
-    exit();
+    $path = '/mynoxon/';
 } else if ($path == '/setupapp/radio567/asp/BrowseXML/FavXML.asp') {
     //Internet Radio Station favorites favorited on device
+    sendMessage('Unsupported');
 } else if ($path == '/RadioNativeFavorites.php') {
     //Favorites, defined via web interface
-} else if (substr($path, 0, 9) == '/play-url') {
-    //play a given URL, but first follow all redirects
-    //noxon iRadio Cube does not like too many redirections
-    // 3 redirects did not work.
-    $url = $_GET['url'];
-    header('HTTP/1.0 301 Moved Permanently');
-    header('Location: ' . getFinalUrl($url));
-    exit();
-} else {
-    sendList(ltrim($path, '/'));
+    sendMessage('Unsupported');
 }
 
+handleRequest(ltrim($path, '/'));
 
-function getFinalUrl($url)
+function handleRequest($path)
 {
-    $ctx = stream_context_set_default(
-        array('http' => array('method' => 'HEAD'))
-    );
-    //get_headers follows redirects automatically
-    $headers = get_headers($url, 1);
-    if ($headers !== false && isset($headers['Location'])) {
-        return end($headers['Location']);
+    global $varDir;
+    if (strpos($path, '..') !== false) {
+        sendMessage('No');
+        return;
+    }
+
+    if (substr($path, 0, 14) == 'internetradio/') {
+        require_once 'mediatomb.php';
+        handleMediatomb('browse', $path, 'internetradio/');
+        return;
+    } else if (substr($path, 0, 11) == '.mt-single/') {
+        require_once 'mediatomb.php';
+        handleMediatomb('single', $path, '.mt-single/');
+        return;
+    }
+
+
+    $fullPath = $varDir . $path;
+    if (!file_exists($fullPath)) {
+        sendMessage('Not found: ' . $path);
+        return;
+    }
+
+    $ext = pathinfo($path, PATHINFO_EXTENSION);
+    if (is_dir($fullPath)) {
+        sendDir($path);
+    } else if ($ext == 'url') {
+        require_once 'podcasts.php';
+        sendPodcast($path);
+    } else if ($ext == 'txt') {
+        sendTextFile($path);
+    } else if (is_executable($fullPath)) {
+        sendScript($path);
+    } else {
+        sendMessage('Unknown file type');
     }
-    return $url;
 }
 
+function pathEncode($urlPath)
+{
+    return str_replace('%2F', '/', rawurlencode($urlPath));
+}
 
-function sendList($path)
+function sendDir($path)
 {
-    $startitems = 1;
-    $enditems = 10;
-    if (isset($_GET['startitems'])) {
-        $startitems = (int) $_GET['startitems'];
+    global $varDir;
+
+    $listItems = array();
+    $enablePaging = true;
+
+    $entries = glob(str_replace('//', '/', $varDir . rtrim($path, '/') . '/*'));
+    $count = 0;
+    $noCache = false;
+    foreach ($entries as $entry) {
+        $urlPath = pathEncode(substr($entry, strlen($varDir)));
+        $ext = pathinfo($entry, PATHINFO_EXTENSION);
+
+        $titleBase = basename($entry);
+        $titleBase = preg_replace('#^[0-9]+_#', '', $titleBase);
+        if (is_dir($entry)) {
+            ++$count;
+            $listItems[] = getDirItem($titleBase, $urlPath . '/');
+        } else if ($ext == 'url') {
+            //podcast
+            ++$count;
+            $listItems[] = getPodcastItem(basename($titleBase, '.url'), $urlPath);
+        } else if (is_executable($entry)
+            && strpos(basename($entry), '.auto') !== false
+        ) {
+            //automatically execute script while listing this directory
+            addScriptOutput($listItems, $entry);
+            $enablePaging = false;
+        } else if ($ext == 'txt' || is_executable($entry)) {
+            //plain text file
+            ++$count;
+            $listItems[] = getDirItem(basename($titleBase, '.' . $ext), $urlPath);
+        } else  if (basename($entry) == 'nocache') {
+            $noCache = true;
+        }
     }
-    if (isset($_GET['enditems'])) {
-        $enditems = (int) $_GET['enditems'];
+    if (!$count) {
+        $listItems[] = getMessageItem('No files or folders');
     }
+    sendListItems(
+        $listItems, buildPreviousItem($path),
+        $enablePaging, $noCache
+    );
+}
 
-    header('Content-type: text/xml');
-    echo <<<XML
-<?xml version="1.0" encoding="iso-8859-1" standalone="yes" ?>
-<ListOfItems>
-  <ItemCount>-1</ItemCount>
-  <Item>
-    <ItemType>Message</ItemType>
-    <Message>$path</Message>
-  </Item>
-  <Item>
-    <ItemType>Dir</ItemType>
-    <Title>$path</Title>
-    <UrlDir>http://radio567.vtuner.com/$path</UrlDir>
-    <UrlDirBackUp>http://radio5672.vtuner.com/$path</UrlDirBackUp>
-  </Item>
-</ListOfItems>
-
-XML;
+function sendScript($path)
+{
+    global $varDir;
+
+    $listItems = array();
+
+    $fullPath = $varDir . $path;
+    addScriptOutput($listItems, $fullPath);
+    sendListItems($listItems, buildPreviousItem($path), false);
 }
 
-function sendMessage($msg)
+function addScriptOutput(&$listItems, $fullPath)
 {
-    header('Content-type: text/xml');
-    $xMsg = htmlspecialchars($msg);
-    echo <<<XML
-<?xml version="1.0" encoding="iso-8859-1" standalone="yes" ?>
-<ListOfItems>
-  <Item>
-    <ItemType>Message</ItemType>
-    <Message>$xMsg</Message>
-  </Item>
-</ListOfItems>
+    exec($fullPath . ' 2>&1', $output, $retVal);
 
-XML;
+    if ($retVal == 0) {
+        addTextLines($listItems, $output);
+    } else {
+        $listItems[] = getMessageItem('Error executing script');
+        addTextLines($listItems, $output);
+    }
 }
 
-function sendListItems($listItems)
+function sendTextFile($path)
 {
+    global $varDir;
+    $listItems = array();
+
+    $lines = file($varDir . $path);
+    addTextLines($listItems, $lines);
+    sendListItems($listItems, buildPreviousItem($path));
+}
+
+function addTextLines(&$listItems, $lines)
+{
+    foreach ($lines as $line) {
+        $line = trim($line);
+        if ($line != '') {
+            $listItems[] = getDisplayItem($line);
+        }
+    }
+}
+
+function getDisplayItem($line)
+{
+    $line = preg_replace('#\s+#', ' ', $line);
+    return '<Item>'
+        . '<ItemType>Display</ItemType>'
+        . '<Display>' . nox_esc($line) . '</Display>'
+        . '</Item>';
+}
+
+function getDirItem($title, $urlPath)
+{
+    global $host1, $host2;
+    return '<Item>'
+        . '<ItemType>Dir</ItemType>'
+        . '<Title>' . nox_esc($title) . '</Title>'
+        . '<UrlDir>' . $host1 . nox_esc($urlPath) . '</UrlDir>'
+        . '<UrlDirBackUp>' . $host2 . nox_esc($urlPath) . '</UrlDirBackUp>'
+        . '</Item>';
+}
+
+function getEpisodeItem($title, $fullUrl, $desc, $type)
+{
+    return '<Item>'
+        . '<ItemType>ShowEpisode</ItemType>'
+        . '<ShowEpisodeName>' . nox_esc($title) . '</ShowEpisodeName>'
+        . '<ShowEpisodeURL>' . htmlspecialchars($fullUrl) . '</ShowEpisodeURL>'
+        . '<ShowDesc>' . nox_esc($desc) . '</ShowDesc>'
+        . '<ShowMime>' . $type . '</ShowMime>'
+        . '</Item>';
+}
+
+function getPodcastItem($title, $urlPath)
+{
+    global $host1;
+    return '<Item>'
+        . '<ItemType>ShowOnDemand</ItemType>'
+        . '<ShowOnDemandName>' . nox_esc($title) . '</ShowOnDemandName>'
+        . '<ShowOnDemandURL>' . $host1 . nox_esc($urlPath) . '</ShowOnDemandURL>'
+        . '</Item>';
+}
+
+function getMessageItem($msg)
+{
+    return '<Item>'
+        . '<ItemType>Message</ItemType>'
+        . '<Message>' . nox_esc($msg) . '</Message>'
+        . '</Item>';
+}
+
+function getPreviousItem($urlPath)
+{
+    global $host1, $host2;
+    return '<Item>'
+        . '<ItemType>Previous</ItemType>'
+        . '<UrlPrevious>' . $host1 . nox_esc($urlPath) . '</UrlPrevious>'
+        . '<UrlPreviousBackUp>' . $host1 . nox_esc($urlPath) . '</UrlPreviousBackUp>'
+        . '</Item>';
+}
+
+function buildPreviousItem($urlPath)
+{
+    $parentDir = dirname($urlPath) . '/';
+    if ($parentDir == '/') {
+        return null;
+    }
+    return getPreviousItem($parentDir);
+}
+
+function nox_esc($string)
+{
+    return utf8_decode(htmlspecialchars($string));
+}
+
+function sendMessage($msg)
+{
+    sendListItems(array(getMessageItem($msg)));
+}
+
+function sendListItems(
+    $listItems, $previous = null, $enablePaging = true, $noCache = false
+) {
+    $startitems = 1;
+    $enditems   = 100000;
+    if (isset($_GET['startitems'])) {
+        $startitems = (int) $_GET['startitems'];
+    }
+    if (isset($_GET['enditems'])) {
+        $enditems = (int) $_GET['enditems'];
+    }
+
+    if ($enablePaging) {
+        $itemCount = count($listItems);
+    } else {
+        $itemCount = -1;
+    }
+    if ($previous !== null) {
+        $previous .= "\n";
+    }
+
     $xml = '<?xml version="1.0" encoding="iso-8859-1"?>' . "\n";
+    $xml .= '<?xml-stylesheet type="text/xsl" href="/html.xsl"?>' . "\n";
     $xml .= '<ListOfItems>' . "\n";
+    if ($noCache) {
+        $xml .= "<NoCache>1</NoCache>\n";
+    }
+    $xml .= '<ItemCount>' . $itemCount . '</ItemCount>' . "\n";
+    $xml .= $previous;
+
+    $num = 0;
     foreach ($listItems as $item) {
-        $xml .= $item . "\n";
+        ++$num;
+        if (!$enablePaging || ($num >= $startitems && $num <= $enditems)) {
+            $xml .= $item . "\n";
+        }
     }
     $xml .= "</ListOfItems>\n";
-    
-    header('Content-type: text/xml');
+
+    header('Content-type: text/xml; charset=iso-8859-1');
     echo $xml;
 }
-
 ?>