Skip to content

Commit

Permalink
Merge pull request #28 from KIMB-technologies/more-configs
Browse files Browse the repository at this point in the history
More config values #26
  • Loading branch information
kimbtech authored Nov 27, 2023
2 parents 4608720 + 0f56e55 commit 8993f3e
Show file tree
Hide file tree
Showing 30 changed files with 228 additions and 84 deletions.
4 changes: 2 additions & 2 deletions .github/workflows/docker-build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ jobs:
# Multi platform image build and push

- name: Build and push the latest Docker image
run: docker buildx build --platform "$PLATFORMS" . --file "Dockerfile" --tag "$IMAGE_OWNER/$IMAGE_NAME:latest" --push
run: docker buildx build --platform "$PLATFORMS" . --file "./utils/Dockerfile" --tag "$IMAGE_OWNER/$IMAGE_NAME:latest" --push
if: ${{ (github.event_name == 'push') || (steps.check.outputs.needs-updating == 'true') }}

- name: Push more tags
Expand All @@ -61,6 +61,6 @@ jobs:
echo "Skipping $TAG";
else
echo "Tagging image as $TAG and pushing";
docker buildx build --platform "$PLATFORMS" . --file "Dockerfile" --tag "$IMAGE_OWNER/$IMAGE_NAME:$TAG" --push
docker buildx build --platform "$PLATFORMS" . --file "./utils/Dockerfile" --tag "$IMAGE_OWNER/$IMAGE_NAME:$TAG" --push
fi;
done;
7 changes: 4 additions & 3 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
/php/data/log.txt
/php/data/*.log
/php/data/cache
/php/getr.php

/data/
/redis/
/php/getr.php
.DS_Store
.DS_Store
6 changes: 3 additions & 3 deletions .phan/config.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,9 @@
return [
'target_php_version' => '8.0',
'file_list' => [
'cron.php',
'startup.php',
'getr.php'
'./utils/cron.php',
'./utils/startup.php',
'./utils/getr.php'
],
'directory_list' => [
'php'
Expand Down
2 changes: 1 addition & 1 deletion Readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ This redirect is possible by manipulating the DNS queries.
→ [Have a look at **screenshots**](./screenshots/Readme.md)

## Usage
- First [set up](./Setup.md) the Docker Container of this *Radio-API* and change the DNS resolver of the radio (e.g., as described there).
- First [set up](./Setup.md) *Radio-API* and change the DNS resolver of the radio (e.g., as described there).
- Afterwards start the radio and open "Internet Radio".
- The *Radio-API* should provide a list of:
- **Podcast**
Expand Down
23 changes: 19 additions & 4 deletions Setup.md
Original file line number Diff line number Diff line change
Expand Up @@ -57,9 +57,10 @@ The image of [Radio DNS](https://hub.docker.com/r/kimbtechnologies/radio_dns) is
- The manual setup does not rely on *Redis* (which is replaced by a file-based caching).
- The only requirement a current version of PHP (code analysis shows compatibility with PHP > 8.0, code is tested with 8.2 and 8.3).
- You do not need a cron job, all data is stored in `./data/` and the cache files in `./data/cache/`.
- You may change the folder for cache files to, e.g., a ramdisk. If you do so, use the script `./utils/backup-restore.php` to backup data which is only stored by the cache (using Docker this is done by the cron job).
- The proxy feature is provided by PHP, but might be less stable than the NGINX proxy.
- The EndURL feature uses the cURL extension of PHP (else it will error!).
- Assure, that PHP/ the webserver can write to `./data/`!
- Assure, that PHP/ the webserver can write to `./data/` (and the folders configured for logs and cache files)!
- Download the lastest source of the *Radio-API* [here](https://github.com/KIMB-technologies/Radio-API/releases/latest).
- Extract the zip and place the folder `php` in the web-root of our server (this is our `./`, other files are not needed).
- Configure *Radio-API* in `./data/env.json` (The config values are the same as for the Docker-based mode, always use strings for the values!):
Expand All @@ -70,6 +71,8 @@ The image of [Radio DNS](https://hub.docker.com/r/kimbtechnologies/radio_dns) is
- `CONF_SHUFFLE_MUSIC` Randomly shuffle music in Nextcloud radio stations
- `CONF_CACHE_EXPIRE` Cache duration of ips, podcasts, RadioBrowser requests, ...
- `CONF_STREAM_JSON` Url to a JSON list of streams or `false` to disable (see [Own Streams](#own-streams)).
- `CONF_LOG_DIR` (optional) Change the folder where log files are written to (defaults to `./data/`).
- `CONF_CACHE_DIR` (optional) Change the folder used by the file based cache (defaults to `./data/cache/`).
- Make sure, that *Radio-API* is available at port `80` for requests with the hostname `*.wifiradiofrontier.com` and `CONF_DOMAIN`.
- Block HTTP access to `./data/` (and `./classes/`) for security reasons (might be omitted in a local network installation).
- Rewrite requests to PHP:
Expand All @@ -78,11 +81,23 @@ The image of [Radio DNS](https://hub.docker.com/r/kimbtechnologies/radio_dns) is
- `./index.php` checks the get parameter `uri` for the path value, e.g., `"/setupapp/iden/asp/BrowseXML/loginXML.asp"`.
If this fails, `$_SERVER['REQUEST_URI']` is checked and the part before the first `?` is taken as path value.
- It is important, that the path value starts with `/` and contains the full path, but without get parameters starting at `?`.
- See the example for NGINX below. The built in webserver of PHP may be used for development with the `router.php` in the repository's root.
- See the example for NGINX below. The built in webserver of PHP may be used for development with the `./utils/router.php` in this repository.
3. Done
- Start the radio and open `Internet Radio`.
- You will see the entries described above at [Usage](./#usage).

### Updates
> This is for manual installs, Docker users must make sure to store the redis volume or to run the cron job.
> Then Radio-API can be restarted using a newer version of the Docker Image.
- Run the `./utils/backup-restore.php` script to export all relevant data from the cache.
This will result in two files, which may be stored in `./data` or somewhere else.
- Create a copy of files in the folder `./data` (`./data/cache` can be deleted).
- Install the new version of Radio-API (download zip, extract `./php` folder to webroot).
- Copy the previously saved files back to `./data`.
- Run the `./utils/backup-restore.php` script to import all relevant data to the cache.
This will read the two files created during the export.

### Rewrite with NGINX

```nginx
Expand All @@ -109,8 +124,8 @@ location @nofile {

## General Information
### Troubleshooting
- A log file of (unknown) request received by the Radio-API is created at `./data/log.txt`.
- Errors with the RadioBrowser API are logged at `./data/log_radiobrowser.txt`.
- A log file of (unknown) request received by the Radio-API is created at `CONF_LOG_DIR/requests.log`. (`CONF_LOG_DIR` default to `./data`)
- Errors with the RadioBrowser API are logged at `CONF_LOG_DIR/radiobrowser.log`.
- If the Radio-API is unable to parse a JSON-file in `./data/`, it will initialize a new one, while the old one is renamed to `*.error.json`.
- PHP error messages are disabled by default, set `DEV=dev` in the environment to enable them.
- Erase the data folder/ volume of redis and restart Radio-API.
Expand Down
4 changes: 3 additions & 1 deletion docker-compose.dev.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,15 @@ services:
radio_api:
build:
context: .
dockerfile: ./utils/Dockerfile
container_name: radio_api_dev
ports:
- "8080:80"
volumes:
- ./php/:/php-code/
- ./data/:/php-code/data/
- ./getr.php:/php-code/getr.php:ro # redis all values listing
- ./utils/getr.php:/php-code/getr.php:ro # redis all values listing
- ./utils/backup-restore.php:/backup-restore.php:ro # backup restore tool for cache values
environment:
- DEV=dev
- CONF_DOMAIN=http://localhost:8080/
Expand Down
1 change: 1 addition & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ services:
# - CONF_REDIS_PORT=6379 # default 6379
# - CONF_REDIS_PASS= # default no auth
- CONF_STREAM_JSON=false # to disable or an url where to fetch list of own streams, e.g., http://stream.example.com/list.json
# -CONF_LOG_DIR= # set a custom directory for log files (defaults to ./data/)
depends_on:
- redis
redis:
Expand Down
45 changes: 38 additions & 7 deletions php/classes/Config.php
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,32 @@
}

// load ENV values
define( 'ENV_DOMAIN', $ENV['CONF_DOMAIN'] . (substr( $ENV['CONF_DOMAIN'], -1) !== '/' ? '/' : '') );
define( 'ENV_ALLOWED_DOMAIN', !empty($ENV['CONF_ALLOWED_DOMAIN']) ? $ENV['CONF_ALLOWED_DOMAIN'] : null );
define( 'ENV_CACHE_EXPIRE', intval($ENV['CONF_CACHE_EXPIRE']));
define( 'ENV_STREAM_JSON', !empty($ENV['CONF_STREAM_JSON']) && $ENV['CONF_STREAM_JSON'] != 'false' ? $ENV['CONF_STREAM_JSON'] : false );
define( 'ENV_SHUFFLE_MUSIC', $ENV['CONF_SHUFFLE_MUSIC'] == 'true');
define( 'ENV_DOMAIN',
$ENV['CONF_DOMAIN'] . (substr( $ENV['CONF_DOMAIN'], -1) !== '/' ? '/' : '')
);
define( 'ENV_ALLOWED_DOMAIN',
!empty($ENV['CONF_ALLOWED_DOMAIN']) ?
strval($ENV['CONF_ALLOWED_DOMAIN']) : null
);
define( 'ENV_CACHE_EXPIRE',
intval($ENV['CONF_CACHE_EXPIRE'])
);
define( 'ENV_STREAM_JSON',
!empty($ENV['CONF_STREAM_JSON']) && $ENV['CONF_STREAM_JSON'] != 'false' ?
strval($ENV['CONF_STREAM_JSON']) : false
);
define( 'ENV_SHUFFLE_MUSIC',
$ENV['CONF_SHUFFLE_MUSIC'] == 'true'
);
define( 'ENV_LOG_DIR',
!empty($ENV['CONF_LOG_DIR']) && realpath($ENV['CONF_LOG_DIR']) ?
realpath($ENV['CONF_LOG_DIR']) : __DIR__ . '/../data'
);
define(
'ENV_CACHE_DIR',
!empty($ENV['CONF_CACHE_DIR']) && realpath(substr($ENV['CONF_LOG_DIR'], 0, strrpos($ENV['CONF_LOG_DIR'], '/', -2))) ?
$ENV['CONF_CACHE_DIR'] : __DIR__ . '/../data/cache'
);

// IP on reverse proxy setup
if( !empty($_SERVER['HTTP_X_REAL_IP']) ){
Expand All @@ -48,7 +69,7 @@ class Config {
/**
* The system's version.
*/
const VERSION = 'v2.7.0';
const VERSION = 'v2.7.1-dev';

/**
* The real domain which should be used.
Expand All @@ -68,7 +89,17 @@ class Config {
/**
* Random shuffle music station streams from nc
*/
CONST SHUFFLE_MUSIC = ENV_SHUFFLE_MUSIC;
const SHUFFLE_MUSIC = ENV_SHUFFLE_MUSIC;

/**
* The directory where the logfiles are stored.
*/
const LOG_DIR = ENV_LOG_DIR;

/**
* The directory used by the json cache (replacement for Redis in non-Docker mode)
*/
const CACHE_DIR = ENV_CACHE_DIR;

/**
* Store redis cache for ALLOWED_DOMAINS
Expand Down
2 changes: 1 addition & 1 deletion php/classes/JSONCache.php
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
*/
class JSONCache implements CacheInterface {

const BASE_DIR = __DIR__ . '/../data/cache';
const BASE_DIR = Config::CACHE_DIR;

private $file, $data, $cleanupRan = false;

Expand Down
16 changes: 10 additions & 6 deletions php/classes/RadioBrowser.php
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ public function __construct( Id|int $id ){

private function log(array $data) : void {
file_put_contents(
__DIR__ . '/../data/log_radiobrowser.txt',
Config::LOG_DIR . '/radiobrowser.log',
date('d.m.Y H:i:s') . " : " . json_encode( $data ) . PHP_EOL,
FILE_APPEND
);
Expand Down Expand Up @@ -434,7 +434,7 @@ public function handleStationPlay(Output $out, string $id) : void {
/**
* Dump all last stations to disk (called by cron)
*/
public static function dumpToDisk() : bool {
public static function dumpToDisk(?string $exportDir = null) : bool {
if( is_file( __DIR__ . '/../data/table.json' ) ){
$table = json_decode(file_get_contents( __DIR__ . '/../data/table.json' ), true);
$redis = new Cache("radio-browser");
Expand All @@ -444,17 +444,21 @@ public static function dumpToDisk() : bool {
$lasts[$id] = $redis->arrayGet('last_stations.'.$id);
}

return file_put_contents(__DIR__ . '/../data/radiobrowser.json', json_encode( $lasts, JSON_PRETTY_PRINT)) !== false;
return file_put_contents(
(is_null($exportDir) ? __DIR__ . '/../data' : $exportDir) . '/radiobrowser.json',
json_encode( $lasts, JSON_PRETTY_PRINT)
) !== false;
}
return true;
}

/**
* Load dumped last stations into Redis (done on container startup)
*/
public static function loadFromDisk() : array {
if( is_file(__DIR__ . '/../data/radiobrowser.json') ){
$lasts = json_decode(file_get_contents(__DIR__ . '/../data/radiobrowser.json'), true);
public static function loadFromDisk(?string $exportDir = null) : array {
$file = (is_null($exportDir) ? __DIR__ . '/../data' : $exportDir) . '/radiobrowser.json';
if( is_file($file) ){
$lasts = json_decode(file_get_contents($file), true);
$redis = new Cache("radio-browser");

foreach( $lasts as $id => $last ){
Expand Down
9 changes: 6 additions & 3 deletions php/classes/RedisCache.php
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ private function generateKey( string $key ) : string {
return $this->prefix . str_replace( ':', '', $key );
}

public function getAllKeysOfGroup() : array {
public function getAllKeysOfGroup(bool $trimPrefix = true) : array {
$all = array();
$lenpref = strlen($this->prefix);
$iterator = NULL;
Expand All @@ -74,11 +74,14 @@ public function getAllKeysOfGroup() : array {
}));
}
} while ($iterator > 0);
if($trimPrefix){
$all = array_map(fn($k) => substr($k, $lenpref), $all);
}
return $all;
}

public function removeGroup() : bool {
$dels = $this->getAllKeysOfGroup();
$dels = $this->getAllKeysOfGroup(false);
return $this->redis->unlink($dels) == count($dels);
}

Expand Down Expand Up @@ -154,7 +157,7 @@ public function output(): void {
echo 'Key' . "\t\t : " . 'Value' . PHP_EOL;
echo '---------------------------------' . PHP_EOL;
$lenpref = strlen($this->prefix);
foreach( $this->getAllKeysOfGroup() as $fullkey ){
foreach( $this->getAllKeysOfGroup(false) as $fullkey ){
$key = substr($fullkey, $lenpref);
if( $this->redis->type($fullkey) !== Redis::REDIS_HASH ){
$val = $this->get($key);
Expand Down
6 changes: 5 additions & 1 deletion php/classes/Router.php
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,11 @@ public function handleGet(string $uri) : void {
preg_match('/^\/setupapp\/[A-Za-z0-9\-\_]+\/asp\/BrowseXML\/loginXML.asp/i', $uri) === 0 &&
(!isset( $_GET['go'] ) || $_GET['go'] != "initial")
){
file_put_contents( __DIR__ . '/../data/log.txt', date('d.m.Y H:i:s') . " : " . json_encode( $_GET ) . PHP_EOL, FILE_APPEND );
file_put_contents(
Config::LOG_DIR . '/requests.log',
date('d.m.Y H:i:s') . " : " . json_encode( $_GET ) . PHP_EOL,
FILE_APPEND
);
}
}
}
Expand Down
5 changes: 3 additions & 2 deletions php/classes/Template.php
Original file line number Diff line number Diff line change
Expand Up @@ -213,8 +213,9 @@ public function getOutputString() : string {
$htmldata = $a[0] . $middle . $b[1];
}

$this->placeholder['%%SERVERURL%%'] = 'http'. ( empty($_SERVER['HTTPS']) ? '' : 's' ) .':'. substr(Config::DOMAIN, strpos(Config::DOMAIN, '//'));

$this->placeholder['%%SERVERURL%%'] = 'http'. ( empty($_SERVER['HTTPS']) ? '' : 's' ) .':'.
substr(Config::DOMAIN, strpos(Config::DOMAIN, '//'));
$this->placeholder['%%VERSION%%'] = Config::VERSION;

if( $this->inner !== null ){
$this->placeholder['%%INNERCONTAINER%%'] = $this->inner->getOutputString();
Expand Down
18 changes: 10 additions & 8 deletions php/classes/UnRead.php
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,7 @@ public function __destruct(){
/**
* Dump all known podcast episodes to disk (called by cron)
*/
public static function dumpToDisk() : bool {
public static function dumpToDisk(?string $exportDir = null) : bool {
if( is_file( __DIR__ . '/../data/table.json' ) ){
$table = json_decode(file_get_contents( __DIR__ . '/../data/table.json' ), true);

Expand All @@ -93,23 +93,25 @@ public static function dumpToDisk() : bool {
$redis = new Cache('unread_podcasts.' . $id );
$reads[$id] = array();
foreach($redis->getAllKeysOfGroup() as $key ){
if( preg_match('/^.*:([^0-9s].*)$/', $key, $matches) === 1){
$reads[$id][] = $matches[1];
}
$reads[$id][] = $key;
}
}

return file_put_contents(__DIR__ . '/../data/unread.json', json_encode( $reads, JSON_PRETTY_PRINT)) !== false;
return file_put_contents(
(is_null($exportDir) ? __DIR__ . '/../data' : $exportDir) . '/unread.json',
json_encode( $reads, JSON_PRETTY_PRINT)
) !== false;
}
return true;
}

/**
* Load dumped known episodes into Redis (done on container startup)
*/
public static function loadFromDisk() : array {
if( is_file(__DIR__ . '/../data/unread.json') ){
$reads = json_decode(file_get_contents(__DIR__ . '/../data/unread.json'), true);
public static function loadFromDisk(?string $exportDir = null) : array {
$file = (is_null($exportDir) ? __DIR__ . '/../data' : $exportDir) . '/unread.json';
if( is_file($file) ){
$reads = json_decode(file_get_contents($file), true);
foreach( $reads as $id => $read ){
if( !empty($read) ){
$redis = new Cache('unread_podcasts.' . $id );
Expand Down
1 change: 0 additions & 1 deletion php/classes/templates/main.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,5 @@
"%%MOREHEADER%%" : "",
"%%TITLE%%": "",
"%%INNERCONTAINER%%" : "",
"%%VERSION%%" : "unknown",
"%%UPDATEINFO%%" : "style=\"display:none;\""
}
4 changes: 2 additions & 2 deletions php/classes/templates/main_de.html
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Radio API &ndash; %%TITLE%%</title>

<link rel="stylesheet" type="text/css" href="%%SERVERURL%%gui/style.css?v=2">
<script src="%%SERVERURL%%gui/jquery.min.js?v=2"></script>
<link rel="stylesheet" type="text/css" href="%%SERVERURL%%gui/style.css?%%VERSION%%">
<script src="%%SERVERURL%%gui/jquery.min.js?%%VERSION%%"></script>
%%MOREHEADER%%
</head>
<body>
Expand Down
4 changes: 2 additions & 2 deletions php/classes/templates/main_en.html
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Radio API &ndash; %%TITLE%%</title>

<link rel="stylesheet" type="text/css" href="%%SERVERURL%%gui/style.css?v=2">
<script src="%%SERVERURL%%gui/jquery.min.js?v=2"></script>
<link rel="stylesheet" type="text/css" href="%%SERVERURL%%gui/style.css?%%VERSION%%">
<script src="%%SERVERURL%%gui/jquery.min.js?%%VERSION%%"></script>
%%MOREHEADER%%
</head>
<body>
Expand Down
4 changes: 3 additions & 1 deletion php/data/env.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,7 @@
"CONF_ALLOWED_DOMAIN" : "all",
"CONF_SHUFFLE_MUSIC" : "true",
"CONF_CACHE_EXPIRE" : "1200",
"CONF_STREAM_JSON" : "false"
"CONF_STREAM_JSON" : "false",
"_CONF_LOG_DIR" : "/my/log/folder",
"_CONF_CACHE_DIR" : "/my/cache/folder/radio-cache"
}
Loading

0 comments on commit 8993f3e

Please sign in to comment.