Modification des entrées du site. Il est passé sur wordpress. Problème pour l'agenda, c'est que ics -> tranformé en rss
This commit is contained in:
+72
-42
@@ -1,52 +1,82 @@
|
||||
<?php
|
||||
require __DIR__ . '/common.php';
|
||||
|
||||
const SITE = 'https://www.silly.be';
|
||||
const NEWS_API = SITE . '/actualites/@results';
|
||||
const PAGE_SIZE = 20;
|
||||
const MAX_PAGES = 2; // jusqu'a 40 items
|
||||
|
||||
function fetch_all_news(): array
|
||||
{
|
||||
$items = [];
|
||||
for ($page = 0; $page < MAX_PAGES; $page++) {
|
||||
$bStart = $page * PAGE_SIZE;
|
||||
$url = NEWS_API . '?b_size=' . PAGE_SIZE . '&b_start=' . $bStart;
|
||||
$data = json_decode(http_get($url), true);
|
||||
$pageItems = $data['items'] ?? [];
|
||||
if (empty($pageItems)) {
|
||||
break;
|
||||
}
|
||||
$items = array_merge($items, $pageItems);
|
||||
if (count($items) >= ($data['items_total'] ?? 0)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
return $items;
|
||||
}
|
||||
/**
|
||||
* Proxy/cache du flux RSS WordPress natif de silly.be (articles complets
|
||||
* dans content:encoded, categories, 10 derniers articles). On le re-sert
|
||||
* sous notre domaine pour garder une URL stable et on corrige atom:link
|
||||
* rel="self" (il pointe sinon vers silly.be) pour le validateur W3C.
|
||||
*
|
||||
* WordPress limite le flux a 10 articles (reglage du site, non modifiable
|
||||
* d'ici) mais accepte ?paged=N : on concatene NEWS_PAGES pages pour
|
||||
* obtenir jusqu'a 50 articles.
|
||||
*/
|
||||
const NEWS_FEED_URL = 'https://www.silly.be/actualites/feed/';
|
||||
const NEWS_PAGES = 5; // 5 x 10 = 50 articles
|
||||
const SELF_URL = 'https://sillycone-village.be/silly-rss/actualites.php';
|
||||
|
||||
function build_news_feed(): string
|
||||
{
|
||||
$items = [];
|
||||
foreach (fetch_all_news() as $item) {
|
||||
$id = $item['id'] ?? '';
|
||||
$title = $item['title_fr'] ?? $item['title'] ?? '(sans titre)';
|
||||
$uid = $item['UID'] ?? $id;
|
||||
$items[] = [
|
||||
'title' => $title,
|
||||
'link' => SITE . '/actualites/' . slugify($title) . '?u=' . rawurlencode($uid),
|
||||
'guid' => $uid,
|
||||
'pubDate' => $item['effective'] ?? $item['created'] ?? null,
|
||||
'description' => full_body_html($item, $title),
|
||||
];
|
||||
$raw = http_get(NEWS_FEED_URL, ['Accept: application/rss+xml, application/xml']);
|
||||
|
||||
$doc = new DOMDocument();
|
||||
if (!@$doc->loadXML($raw)) {
|
||||
throw new RuntimeException('Flux WordPress illisible (XML invalide)');
|
||||
}
|
||||
return build_rss(
|
||||
'Silly.be - Actualités',
|
||||
SITE . '/actualites',
|
||||
'Actualités de la commune de Silly (Belgique)',
|
||||
$items,
|
||||
'https://sillycone-village.be/silly-rss/actualites.php'
|
||||
);
|
||||
|
||||
$xpath = new DOMXPath($doc);
|
||||
$xpath->registerNamespace('atom', 'http://www.w3.org/2005/Atom');
|
||||
$selfLinks = $xpath->query('/rss/channel/atom:link[@rel="self"]');
|
||||
if ($selfLinks->length === 0) {
|
||||
throw new RuntimeException('Reponse inattendue : pas un flux RSS');
|
||||
}
|
||||
foreach ($selfLinks as $selfLink) {
|
||||
$selfLink->setAttribute('href', SELF_URL);
|
||||
}
|
||||
|
||||
// WordPress emet <sy:updatePeriod>\n\thourly\t</sy:updatePeriod> : on retire
|
||||
// les blancs parasites autour des valeurs.
|
||||
$xpath->registerNamespace('sy', 'http://purl.org/rss/1.0/modules/syndication/');
|
||||
foreach ($xpath->query('/rss/channel/sy:*') as $node) {
|
||||
$node->textContent = trim($node->textContent);
|
||||
}
|
||||
|
||||
// Pages suivantes : un echec (ou une page vide) arrete simplement la
|
||||
// pagination, la premiere page suffit a servir un flux valide.
|
||||
$channel = $xpath->query('/rss/channel')->item(0);
|
||||
$seen = [];
|
||||
foreach ($xpath->query('/rss/channel/item/guid') as $g) {
|
||||
$seen[trim($g->textContent)] = true;
|
||||
}
|
||||
for ($page = 2; $page <= NEWS_PAGES; $page++) {
|
||||
try {
|
||||
$more = new DOMDocument();
|
||||
$raw = http_get(NEWS_FEED_URL . '?paged=' . $page, ['Accept: application/rss+xml, application/xml']);
|
||||
if (!@$more->loadXML($raw)) {
|
||||
break;
|
||||
}
|
||||
} catch (Throwable $e) {
|
||||
break;
|
||||
}
|
||||
$added = 0;
|
||||
$moreXpath = new DOMXPath($more);
|
||||
foreach ($moreXpath->query('/rss/channel/item') as $item) {
|
||||
// Le tri de WordPress n'est pas stable entre articles de meme
|
||||
// date : on dedoublonne par guid aux jonctions de pages.
|
||||
$guid = trim($moreXpath->evaluate('string(guid)', $item));
|
||||
if ($guid === '' || isset($seen[$guid])) {
|
||||
continue;
|
||||
}
|
||||
$seen[$guid] = true;
|
||||
$channel->appendChild($doc->importNode($item, true));
|
||||
$added++;
|
||||
}
|
||||
if ($added === 0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return $doc->saveXML();
|
||||
}
|
||||
|
||||
serve_cached_feed('actualites', 'build_news_feed');
|
||||
|
||||
Reference in New Issue
Block a user