From b155c8167ddd5562f30fcfadd9eeb60d80e2619e Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Tue, 3 May 2022 17:36:29 +0200 Subject: [locations/news] Add per-location news/help/loginscreentext --- modules-available/locations/pages/details.inc.php | 1 + .../locations/templates/location-subnets.html | 6 +++ modules-available/news/api.inc.php | 61 ++++++++++++++++------ modules-available/news/install.inc.php | 25 ++++++--- modules-available/news/page.inc.php | 39 +++++++++----- .../news/permissions/permissions.json | 12 ++--- modules-available/news/templates/page-news.html | 6 +++ 7 files changed, 109 insertions(+), 41 deletions(-) diff --git a/modules-available/locations/pages/details.inc.php b/modules-available/locations/pages/details.inc.php index d2ec7b24..77f96221 100644 --- a/modules-available/locations/pages/details.inc.php +++ b/modules-available/locations/pages/details.inc.php @@ -342,6 +342,7 @@ class SubPage 'locationname' => $loc['locationname'], 'list' => $rows, 'roomplanner' => Module::get('roomplanner') !== false, + 'news' => Module::get('news') !== false && User::hasPermission('.news.*', $loc['locationid']), 'parents' => Location::getLocations($loc['parentlocationid'], $locationId, true) ); diff --git a/modules-available/locations/templates/location-subnets.html b/modules-available/locations/templates/location-subnets.html index 85c5a744..976c3cc7 100644 --- a/modules-available/locations/templates/location-subnets.html +++ b/modules-available/locations/templates/location-subnets.html @@ -91,6 +91,12 @@ {{lang_openingTime}} + {{#news}} + + + {{lang_editNews}} + + {{/news}} {{#roomplanner}} diff --git a/modules-available/news/api.inc.php b/modules-available/news/api.inc.php index 851f31a8..e8ef11d1 100644 --- a/modules-available/news/api.inc.php +++ b/modules-available/news/api.inc.php @@ -4,23 +4,54 @@ header('Content-Type: application/xml; charset=utf-8'); $type = Request::any('type', 'news', 'string'); +$locationId = Request::any('location', 0, 'int'); +if ($locationId === 0) { + $locationId = Location::getFromIp($_SERVER['REMOTE_ADDR']); +} +$locations = Location::getLocationRootChain($locationId); +$locations[] = 0; + // Fetch news from DB -$row = Database::queryFirst('SELECT title, content, dateline FROM vmchooser_pages' - . ' WHERE type = :type AND expires > UNIX_TIMESTAMP() ORDER BY dateline DESC LIMIT 1', compact('type')); -if ($row !== false ) { +$res = Database::simpleQuery('SELECT title, locationid, content, dateline FROM vmchooser_pages + WHERE type = :type AND (locationid IS NULL OR locationid IN (:lids)) + AND expires > UNIX_TIMESTAMP() ORDER BY dateline DESC', [ + 'type' => $type, + 'lids' => $locations, + ]); - echo '' . "\n"; - echo "" . "\n"; - echo "\t" . '' . "\n"; - echo "\t\t" . htmlspecialchars($row['title']) . "\n"; - echo "\t" . '' . "\n"; - echo "\t" . "" . "\n"; - echo "\t\t" . htmlspecialchars($row['content']) . "\n"; - echo "\t" . '' . "\n"; - echo "\t" . "" . "\n"; - echo "\t\t" . $row['dateline'] . "\n"; - echo "\t" . "" . "\n"; - echo ""; +// Get one for each location. As we sort by dateline and check expiry in the query, we only +// need one per location and then pick the first one that is set, as the locations are ordered +// by closest to furthest +$locations = array_flip($locations); +foreach ($res as $row) { + $lid = $row['locationid']; + if (is_array($locations[$lid])) + continue; // Already have one + $locations[$lid] = $row; +} +// Pick first one +foreach ($locations as $row) { + if (is_array($row)) + break; +} + +if (is_array($row)) { + $title = htmlspecialchars($row['title']); + $content = htmlspecialchars($row['content']); + echo << + + + $title + + + $content + + + {$row['dateline']} + + +EOF; } else { // no news in DB, output a 'null' news xml diff --git a/modules-available/news/install.inc.php b/modules-available/news/install.inc.php index 88a20749..89fc7069 100644 --- a/modules-available/news/install.inc.php +++ b/modules-available/news/install.inc.php @@ -1,6 +1,6 @@ locationId = Request::get('locationid', 0, 'int'); if ($pageType === false && $newsId === false) { - Util::redirect('?do=news&type=news'); + Util::redirect('?do=news&type=news&locationid=' . $this->locationId); } $this->pageType = $pageType === false ? 'news' : $pageType; $this->loadNews($newsId, $pageType); foreach (self::TYPES as $type => $entry) { - Dashboard::addSubmenu('?do=news&type=' . $type, Dictionary::translate('type_' . $type, true)); + Dashboard::addSubmenu('?do=news&type=' . $type . '&locationid=' . $this->locationId, + Dictionary::translate('type_' . $type, true)); } } else { $action = Request::post('action', false, 'string'); $pageType = Request::post('type', false, 'string'); + $this->locationId = Request::post('locationid', Request::REQUIRED_EMPTY, 'int'); if (!array_key_exists($pageType, self::TYPES)) { Message::addError('invalid-type', $pageType); - Util::redirect('?do=news'); + Util::redirect('?do=news&locationid=' . $this->locationId); } if ($action === 'save') { // save to DB - User::assertPermission("$pageType.save"); + User::assertPermission("$pageType.save", $this->locationId); if (!$this->saveNews($pageType)) { Message::addError('save-error'); } else { @@ -95,14 +102,14 @@ class Page_News extends Page } elseif ($action === 'delete') { // delete it - User::assertPermission("$pageType.delete"); + User::assertPermission("$pageType.delete", $this->locationId); $this->delNews(Request::post('newsid', false, 'int'), $pageType); } else { // unknown action, redirect user Message::addError('invalid-action', $action); } - Util::redirect('?do=news&type=' . $pageType); + Util::redirect('?do=news&type=' . $pageType . '&locationid=' . $this->locationId); } /* load summernote module if available */ @@ -119,8 +126,9 @@ class Page_News extends Page // fetch the list of the older news $NOW = time(); $lines = array(); + $str = $this->locationId === 0 ? 'IS NULL' : ' = ' . $this->locationId; $res = Database::simpleQuery("SELECT newsid, dateline, expires, title, content FROM vmchooser_pages - WHERE type = :type ORDER BY dateline DESC LIMIT 20", ['type' => $this->pageType]); + WHERE type = :type AND locationid $str ORDER BY dateline DESC LIMIT 20", ['type' => $this->pageType]); $foundActive = false; foreach ($res as $row) { $row['dateline_s'] = Util::prettyTime($row['dateline']); @@ -169,6 +177,10 @@ class Page_News extends Page 'disabled' => 'disabled', ]; } + $data['locationid'] = $this->locationId; + if ($this->locationId > 0) { + $data['location_name'] = Location::getName($this->locationId); + } Render::addTemplate('page-news', $data); } @@ -199,8 +211,9 @@ class Page_News extends Page Message::addError('news-empty'); } } else { + $str = $this->locationId === 0 ? 'IS NULL' : ' = ' . $this->locationId; $row = Database::queryFirst("SELECT newsid, title, content, dateline, expires, type FROM vmchooser_pages - WHERE type = :type AND expires > UNIX_TIMESTAMP() ORDER BY dateline DESC LIMIT 1", [ + WHERE type = :type AND locationid $str AND expires > UNIX_TIMESTAMP() ORDER BY dateline DESC LIMIT 1", [ 'type' => $pageType, ]); } @@ -234,11 +247,12 @@ class Page_News extends Page $expires = strtotime(Request::post('enddate', 'today', 'string') . ' ' . Request::post('endtime', '23:59', 'string')); } + $str = $this->locationId === 0 ? 'IS NULL' : ' = ' . $this->locationId; if (!empty($newsContent)) { // we got title and content, save it to DB // dup check first - $row = Database::queryFirst('SELECT newsid FROM vmchooser_pages - WHERE content = :content AND type = :type LIMIT 1', [ + $row = Database::queryFirst("SELECT newsid FROM vmchooser_pages + WHERE content = :content AND type = :type AND locationid $str LIMIT 1", [ 'content' => $newsContent, 'type' => $pageType, ]); @@ -253,10 +267,11 @@ class Page_News extends Page return true; } // new one - Database::exec("INSERT INTO vmchooser_pages (dateline, expires, title, content, type) - VALUES (:dateline, :expires, :title, :content, :type)", array( + Database::exec("INSERT INTO vmchooser_pages (dateline, expires, locationid, title, content, type) + VALUES (:dateline, :expires, :locationid, :title, :content, :type)", array( 'dateline' => time(), 'expires' => $expires, + 'locationid' => $this->locationId, 'title' => $newsTitle, 'content' => $newsContent, 'type' => $pageType, diff --git a/modules-available/news/permissions/permissions.json b/modules-available/news/permissions/permissions.json index 4ff1a01b..83fad86c 100644 --- a/modules-available/news/permissions/permissions.json +++ b/modules-available/news/permissions/permissions.json @@ -3,21 +3,21 @@ "location-aware": false }, "help.delete": { - "location-aware": false + "location-aware": true }, "help.save": { - "location-aware": false + "location-aware": true }, "news.delete": { - "location-aware": false + "location-aware": true }, "news.save": { - "location-aware": false + "location-aware": true }, "login-news.delete": { - "location-aware": false + "location-aware": true }, "login-news.save": { - "location-aware": false + "location-aware": true } } \ No newline at end of file diff --git a/modules-available/news/templates/page-news.html b/modules-available/news/templates/page-news.html index 1c944cb8..aa5785da 100644 --- a/modules-available/news/templates/page-news.html +++ b/modules-available/news/templates/page-news.html @@ -4,10 +4,16 @@

{{newsTypeName}}

+{{#locationid}} +

{{location_name}}

+
{{lang_editingForLocation}}
+{{/locationid}} +
+ {{#withTitle}}
-- cgit v1.2.3-55-g7522