2025-04-08 06:37:14 +04:00
< ? php
/**
2025-04-11 06:27:03 +04:00
* Configuration de kaubuntu.re
2025-04-08 06:37:14 +04:00
*
* Ce fichier contient les paramètres de configuration pour connecter
* la plateforme à une instance PeerTube et personnaliser le site.
*/
2025-04-08 16:49:57 +04:00
// Charger d'abord la configuration locale si elle existe
$config_local_file = __DIR__ . '/config.local.php' ;
if ( file_exists ( $config_local_file )) {
require_once $config_local_file ;
}
2025-04-08 16:43:18 +04:00
2025-04-09 20:19:05 +04:00
if ( ! defined ( 'APP_HOST_NAME' )) define ( 'APP_HOST_NAME' , 'kaubuntu.re' );
2025-04-08 16:49:57 +04:00
// Configuration de base - ces valeurs seront utilisées si elles ne sont pas définies dans config.local.php
if ( ! defined ( 'PEERTUBE_URL' )) define ( 'PEERTUBE_URL' , 'https://video.off-investigation.fr' );
2025-04-09 12:27:46 +04:00
if ( ! defined ( 'PEERTUBE_DISPLAY_NAME' )) define ( 'PEERTUBE_DISPLAY_NAME' , 'video.off-investigation.fr' );
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'API_KEY' )) define ( 'API_KEY' , '' );
if ( ! defined ( 'TAG_INDEPENDENCE' )) define ( 'TAG_INDEPENDENCE' , 'indépendance' );
if ( ! defined ( 'SHORTS_MAX_DURATION' )) define ( 'SHORTS_MAX_DURATION' , 120 ); // 2 minutes max pour les shorts
2025-04-08 06:37:14 +04:00
// Pagination et affichage
2025-04-10 13:10:00 +04:00
if ( ! defined ( 'COUNT_VIDEO_SEARCH' )) define ( 'COUNT_VIDEO_SEARCH' , 20 );
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'VIDEOS_PER_PAGE' )) define ( 'VIDEOS_PER_PAGE' , 12 );
if ( ! defined ( 'FEATURED_VIDEOS_COUNT' )) define ( 'FEATURED_VIDEOS_COUNT' , 6 );
if ( ! defined ( 'RECENT_VIDEOS_COUNT' )) define ( 'RECENT_VIDEOS_COUNT' , 6 );
if ( ! defined ( 'SHORTS_COUNT' )) define ( 'SHORTS_COUNT' , 6 );
2025-04-11 13:17:06 +04:00
if ( ! defined ( 'SHORTS_COUNT_SEARCH' )) define ( 'SHORTS_COUNT_SEARCH' , 50 );
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'TRENDING_VIDEOS_COUNT' )) define ( 'TRENDING_VIDEOS_COUNT' , 6 );
if ( ! defined ( 'INDEPENDENCE_VIDEOS_COUNT' )) define ( 'INDEPENDENCE_VIDEOS_COUNT' , 6 );
if ( ! defined ( 'CATEGORY_VIDEOS_COUNT' )) define ( 'CATEGORY_VIDEOS_COUNT' , 6 );
if ( ! defined ( 'LOAD_MORE_COUNT' )) define ( 'LOAD_MORE_COUNT' , 6 );
2025-04-08 06:37:14 +04:00
2025-04-08 15:46:18 +04:00
// Catégories prioritaires avec noms personnalisés (dans l'ordre d'affichage souhaité)
// format: [ID catégorie => Nom personnalisé]
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'PRIORITY_CATEGORIES' )) {
define ( 'PRIORITY_CATEGORIES' , [
11 => 'Actualité & Politique' , // News & Politique
14 => 'Activisme' , // Activism
1 => 'Musique' , // Musique
]);
2025-04-08 16:43:18 +04:00
}
2025-04-08 17:14:34 +04:00
// =========================================
// Configuration Mastodon
// =========================================
if ( ! defined ( 'MASTODON_INSTANCE_URL' )) define ( 'MASTODON_INSTANCE_URL' , 'https://mamot.fr' );
if ( ! defined ( 'MASTODON_DATE_FORMAT' )) define ( 'MASTODON_DATE_FORMAT' , 'fr-FR' );
if ( ! defined ( 'MASTODON_BTN_SEE_MORE' )) define ( 'MASTODON_BTN_SEE_MORE' , 'Voir plus de post' );
if ( ! defined ( 'MASTODON_BTN_RELOAD' )) define ( 'MASTODON_BTN_RELOAD' , 'Rafraichir' );
if ( ! defined ( 'MASTODON_MAX_POST_FETCH' )) define ( 'MASTODON_MAX_POST_FETCH' , '10' );
if ( ! defined ( 'MASTODON_MAX_POST_SHOW' )) define ( 'MASTODON_MAX_POST_SHOW' , '10' );
2025-04-08 06:37:14 +04:00
// Informations du site
2025-04-11 06:27:03 +04:00
if ( ! defined ( 'SITE_NAME' )) define ( 'SITE_NAME' , 'kaubuntu.re' );
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'SITE_DESCRIPTION' )) define ( 'SITE_DESCRIPTION' , 'Votre plateforme de médias libres' );
if ( ! defined ( 'SITE_LOGO' )) define ( 'SITE_LOGO' , 'img/logo.png' );
if ( ! defined ( 'SITE_FAVICON' )) define ( 'SITE_FAVICON' , 'img/favicon.png' );
2025-04-08 06:37:14 +04:00
// Réseaux sociaux
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'FACEBOOK_URL' )) define ( 'FACEBOOK_URL' , '#' );
2025-04-09 07:47:43 +04:00
if ( ! defined ( 'X_URL' )) define ( 'X_URL' , '#' );
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'INSTAGRAM_URL' )) define ( 'INSTAGRAM_URL' , '#' );
if ( ! defined ( 'YOUTUBE_URL' )) define ( 'YOUTUBE_URL' , '#' );
2025-04-09 05:55:32 +04:00
if ( ! defined ( 'TIKTOK_URL' )) define ( 'TIKTOK_URL' , '#' );
2025-04-08 06:37:14 +04:00
// Contacts
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'CONTACT_EMAIL' )) define ( 'CONTACT_EMAIL' , 'contact@kaubuntu.re' );
2025-04-08 06:37:14 +04:00
2025-04-09 20:19:05 +04:00
// Mentions légales
if ( ! defined ( 'LEGAL_COPYRIGHT' )) define ( 'LEGAL_COPYRIGHT' , 'Ka-Ubuntu' );
if ( ! defined ( 'LEGAL_WEBMASTER_NAME' )) define ( 'LEGAL_WEBMASTER_NAME' , 'Cédric Famibelle-Pronzola' );
if ( ! defined ( 'LEGAL_WEBMASTER_EMAIL' )) define ( 'LEGAL_WEBMASTER_EMAIL' , 'contact@cedric-pronzola.re' );
if ( ! defined ( 'LEGAL_HOST_NAME' )) define ( 'LEGAL_HOST_NAME' , 'o2Switch' );
if ( ! defined ( 'LEGAL_HOST_COMPANY' )) define ( 'LEGAL_HOST_COMPANY' , 'société au capital de 100 000 €' );
if ( ! defined ( 'LEGAL_HOST_RCS' )) define ( 'LEGAL_HOST_RCS' , 'immatriculée au RCS de Clermont-Ferrand sous le numéro 510 909 807' );
if ( ! defined ( 'LEGAL_HOST_ADDRESS' )) define ( 'LEGAL_HOST_ADDRESS' , '222 boulevard Gustave Flaubert, 63000 Clermont-Ferrand, France' );
if ( ! defined ( 'LEGAL_CONTACT_EMAIL' )) define ( 'LEGAL_CONTACT_EMAIL' , 'zinfos@kaubuntu.com' );
if ( ! defined ( 'LEGAL_LICENSE' )) define ( 'LEGAL_LICENSE' , 'GNU Affero General Public License version 3 (AGPL-V3)' );
if ( ! defined ( 'LEGAL_LICENSE_URL' )) define ( 'LEGAL_LICENSE_URL' , 'https://www.gnu.org/licenses/agpl-3.0.html' );
if ( ! defined ( 'LEGAL_SOURCE_CODE_URL' )) define ( 'LEGAL_SOURCE_CODE_URL' , 'https://codeberg.org/Ka-Ubuntu/kaubuntu.re' );
2025-04-10 10:55:42 +04:00
if ( ! defined ( 'LEGAL_SERVICE_DESCRIPTION' )) define ( 'LEGAL_SERVICE_DESCRIPTION' , 'est une plateforme multimédia proposant des contenus vidéo, des actualités et des informations liées au mouvement politique indépendantiste et panafricaniste réunionnais Ka-Ubuntu.' );
2025-04-09 20:19:05 +04:00
2025-04-08 06:37:14 +04:00
// Fonctionnalités
2025-04-09 12:27:46 +04:00
define ( 'ENABLE_SEARCH' , true );
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'ENABLE_USER_ACCOUNTS' )) define ( 'ENABLE_USER_ACCOUNTS' , false );
2025-04-08 06:37:14 +04:00
// Cache
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'CACHE_ENABLED' )) define ( 'CACHE_ENABLED' , false );
if ( ! defined ( 'CACHE_DURATION' )) define ( 'CACHE_DURATION' , 3600 ); // En secondes (1 heure)
2025-04-08 06:37:14 +04:00
2025-04-10 10:33:19 +04:00
// Compte pour les lives
if ( ! defined ( 'LIVE_ACCOUNT_NAME' )) define ( 'LIVE_ACCOUNT_NAME' , 'admin' );
2025-04-08 09:12:46 +04:00
// Tags pour filtrer les vidéos selon les catégories
2025-04-08 16:49:57 +04:00
if ( ! defined ( 'TAG_SHORT' )) define ( 'TAG_SHORT' , 'short' );
2025-04-08 09:12:46 +04:00
2025-04-10 13:53:33 +04:00
// Hashtags importants à afficher dans la sidebar, footer et menu mobile
2025-04-10 13:40:25 +04:00
if ( ! defined ( 'IMPORTANT_TAGS' )) {
define ( 'IMPORTANT_TAGS' , [
2025-04-10 13:30:15 +04:00
'Colonialisme' ,
'La Réunion' ,
'Panafricanisme' ,
'Conférence'
]);
}
2025-04-10 13:53:33 +04:00
// Hashtags populaires à afficher sur la page d'accueil
if ( ! defined ( 'POPULAR_TAGS' )) {
define ( 'POPULAR_TAGS' , [
'Justice' ,
'Anticolonial' ,
'Kanaky' ,
'Océan Indien'
]);
}
2025-04-08 06:37:14 +04:00
// Locale et fuseau horaire
setlocale ( LC_TIME , 'fr_FR.UTF-8' );
date_default_timezone_set ( 'Indian/Reunion' );
2025-04-08 15:36:33 +04:00
// Initialisation des catégories de vidéo depuis l'API
$peertube_categories = initCategories ();
define ( 'PEERTUBE_CATEGORIES' , $peertube_categories );
/**
* Initialise et récupère les catégories depuis l'API PeerTube
*
* @return array Liste des catégories
*/
function initCategories () {
// Récupérer la liste des catégories depuis l'API
$categories = callPeerTubeApi ( 'videos/categories' );
2025-04-10 12:07:56 +04:00
// Tableau de correspondance pour traduire les catégories en français
$translations = [
'Music' => 'Musique' ,
'Films' => 'Films' ,
'Vehicles' => 'Véhicules' ,
'Art' => 'Art' ,
'Sports' => 'Sports' ,
'Travels' => 'Voyages' ,
'Gaming' => 'Jeux vidéo' ,
'People' => 'Personnes' ,
'Comedy' => 'Humour' ,
'Entertainment' => 'Divertissement' ,
'News & Politics' => 'Actualités & Politique' ,
'How To' => 'Tutoriels' ,
'Education' => 'Éducation' ,
'Activism' => 'Activisme' ,
'Science & Technology' => 'Science & Technologie' ,
'Animals' => 'Animaux' ,
'Kids' => 'Enfants' ,
'Food' => 'Cuisine' ,
];
// Si une constante PRIORITY_CATEGORIES est définie, utiliser ces traductions
if ( defined ( 'PRIORITY_CATEGORIES' )) {
$priorityCategories = PRIORITY_CATEGORIES ;
foreach ( $priorityCategories as $id => $name ) {
// Trouver la clé anglaise correspondant à l'ID
$englishName = array_search ( $id , array_keys ( $categories ));
if ( $englishName !== false ) {
$translations [ $englishName ] = $name ;
}
}
}
2025-04-08 15:36:33 +04:00
$result = [];
foreach ( $categories as $key => $name ) {
2025-04-10 12:07:56 +04:00
// Utiliser la traduction si disponible, sinon garder le nom original
$translatedName = isset ( $translations [ $name ]) ? $translations [ $name ] : $name ;
$result [ $key ] = $translatedName ;
2025-04-08 15:36:33 +04:00
}
return $result ;
}
2025-04-08 06:37:14 +04:00
/**
* Fonction utilitaire pour appeler l'API PeerTube
*
* @param string $endpoint Point de terminaison de l'API
* @param array $params Paramètres optionnels pour la requête
* @return array Données retournées par l'API
*/
function callPeerTubeApi ( $endpoint , $params = []) {
$url = PEERTUBE_URL . '/api/v1/' . $endpoint ;
// Ajouter les paramètres à l'URL
if ( ! empty ( $params )) {
$url .= '?' . http_build_query ( $params );
}
// Initialiser cURL
$ch = curl_init ();
curl_setopt ( $ch , CURLOPT_URL , $url );
curl_setopt ( $ch , CURLOPT_RETURNTRANSFER , true );
// Ajouter la clé API si définie
if ( defined ( 'API_KEY' ) && ! empty ( API_KEY )) {
curl_setopt ( $ch , CURLOPT_HTTPHEADER , [
'Authorization: ApiKey ' . API_KEY
]);
}
// Exécuter la requête
$response = curl_exec ( $ch );
curl_close ( $ch );
// Traiter la réponse
if ( $response === false ) {
// En cas d'erreur, retourner un tableau vide
return [];
}
// Décoder la réponse JSON
$data = json_decode ( $response , true );
return $data ? : [];
}
2025-04-08 09:12:46 +04:00
/**
* Récupère les catégories depuis l'API PeerTube
*
* @return array Liste des catégories
*/
function getCategories () {
2025-04-08 15:36:33 +04:00
// Utiliser les catégories déjà récupérées
$categories = PEERTUBE_CATEGORIES ;
2025-04-08 09:12:46 +04:00
$result = [];
foreach ( $categories as $key => $name ) {
$result [] = [
'id' => $key ,
'name' => $name
];
}
return $result ;
}
/**
* Récupère les vidéos récentes depuis l'API PeerTube
*
* @param int $count Nombre de vidéos à récupérer
* @return array Liste des vidéos récentes
*/
function getRecentVideos ( $count = RECENT_VIDEOS_COUNT ) {
// Récupérer les vidéos récentes
$data = callPeerTubeApi ( 'videos' , [
'sort' => '-publishedAt' ,
'count' => $count ,
'isLocal' => true
]);
return formatVideosData ( $data [ 'data' ] ? ? []);
}
/**
* Récupère les vidéos tendances depuis l'API PeerTube
*
* @param int $count Nombre de vidéos à récupérer
* @return array Liste des vidéos tendances
*/
function getTrendingVideos ( $count = TRENDING_VIDEOS_COUNT ) {
// Récupérer les vidéos tendances
$data = callPeerTubeApi ( 'videos' , [
'sort' => '-trending' ,
'count' => $count ,
'isLocal' => true
]);
return formatVideosData ( $data [ 'data' ] ? ? []);
}
/**
* Récupère les vidéos avec un tag spécifique depuis l'API PeerTube
*
* @param string $tag Tag à filtrer
* @param int $count Nombre de vidéos à récupérer
* @return array Liste des vidéos
*/
function getVideosByTag ( $tag , $count ) {
// Récupérer les vidéos par tag
$data = callPeerTubeApi ( 'videos' , [
'tagsOneOf' => $tag ,
'count' => $count ,
'isLocal' => true
]);
return formatVideosData ( $data [ 'data' ] ? ? []);
}
/**
* Récupère les shorts (vidéos courtes) depuis l'API PeerTube
* Les shorts sont des vidéos locales de moins de 2 minutes
*
* @param int $count Nombre de shorts à récupérer
* @return array Liste des shorts
*/
function getShorts ( $count = SHORTS_COUNT ) {
// Récupérer plus de vidéos que nécessaire pour pouvoir filtrer
$data = callPeerTubeApi ( 'videos' , [
'sort' => '-publishedAt' , // Les plus récentes d'abord
2025-04-11 13:17:06 +04:00
'count' => SHORTS_COUNT_SEARCH ,
2025-04-08 09:12:46 +04:00
'isLocal' => true
]);
// Formater les données
$allVideos = formatVideosData ( $data [ 'data' ] ? ? []);
2025-04-08 15:06:21 +04:00
// Filtrer pour ne garder que les vidéos de moins de 2 minutes (120 secondes) et en mode portrait
2025-04-08 09:12:46 +04:00
$shortVideos = array_filter ( $allVideos , function ( $video ) {
2025-04-08 15:06:21 +04:00
// Vérifier la durée (moins de 2 minutes)
2025-04-11 13:17:06 +04:00
$durationOk = $video [ 'duration' ] < SHORTS_MAX_DURATION ;
2025-04-08 15:06:21 +04:00
// Vérifier le ratio (mode portrait)
$ratioOk = isset ( $video [ 'aspectRatio' ]) && $video [ 'aspectRatio' ] <= 1 ;
return $durationOk && $ratioOk ;
2025-04-08 09:12:46 +04:00
});
// Limiter au nombre demandé
return array_slice ( $shortVideos , 0 , $count );
}
/**
* Récupère les vidéos sur l'indépendance depuis l'API PeerTube
*
* @param int $count Nombre de vidéos à récupérer
* @return array Liste des vidéos sur l'indépendance
*/
function getIndependenceVideos ( $count = INDEPENDENCE_VIDEOS_COUNT ) {
// Récupérer les vidéos sur l'indépendance
return getVideosByTag ( TAG_INDEPENDENCE , $count );
}
2025-04-10 10:33:19 +04:00
/**
* Vérifie s'il y a un direct en cours du compte LIVE_ACCOUNT_NAME sur l'instance PeerTube
*
* @return array|null Informations sur le direct en cours ou null si aucun direct
*/
function getLiveStream () {
// Récupérer les lives du compte spécifié
$accountName = LIVE_ACCOUNT_NAME ;
$data = callPeerTubeApi ( 'accounts/' . $accountName . '/videos' , [
'count' => 1 ,
'isLocal' => true ,
'isLive' => true , // Filtrer uniquement les lives
'sort' => '-publishedAt' // Les plus récents en premier
]);
// Vérifier si on a des résultats
if ( empty ( $data [ 'data' ]) || count ( $data [ 'data' ]) === 0 ) {
return null ;
}
// Formater les données du live
$liveData = formatVideosData ( $data [ 'data' ]);
// Filtrer pour ne garder que les lives en cours
$activeLives = array_filter ( $liveData , function ( $video ) {
return isset ( $video [ 'isLive' ]) && $video [ 'isLive' ] === true ;
});
// Retourner le premier live trouvé
return ! empty ( $activeLives ) ? reset ( $activeLives ) : null ;
}
2025-04-08 09:12:46 +04:00
/**
* Formate les données brutes des vidéos venant de l'API
*
* @param array $videosData Données brutes des vidéos
* @return array Données formatées
*/
function formatVideosData ( $videosData ) {
$videos = [];
foreach ( $videosData as $video ) {
// Récupérer la vignette (thumbnail)
2025-04-08 12:29:28 +04:00
$thumbnail = isset ( $video [ 'previewPath' ])
? PEERTUBE_URL . $video [ 'previewPath' ]
2025-04-08 09:12:46 +04:00
: 'img/default-thumbnail.jpg' ;
2025-04-09 08:40:03 +04:00
// Récupérer l'avatar de la chaîne
$channelAvatar = isset ( $video [ 'channel' ][ 'avatars' ][ 0 ][ 'path' ]) && isset ( $video [ 'channel' ][ 'avatars' ][ 0 ][ 'path' ])
? PEERTUBE_URL . $video [ 'channel' ][ 'avatars' ][ 0 ][ 'path' ]
: 'img/default-avatar.png' ;
2025-04-08 09:12:46 +04:00
// Formater les données
$videos [] = [
'id' => $video [ 'uuid' ],
'title' => $video [ 'name' ],
'thumbnail' => $thumbnail ,
'duration' => $video [ 'duration' ],
'channel' => $video [ 'channel' ][ 'displayName' ],
2025-04-09 08:40:03 +04:00
'channelAvatar' => $channelAvatar ,
2025-04-08 09:12:46 +04:00
'views' => $video [ 'views' ],
'date' => $video [ 'publishedAt' ],
2025-04-08 15:06:21 +04:00
'aspectRatio' => $video [ 'aspectRatio' ],
2025-04-08 09:12:46 +04:00
'description' => $video [ 'description' ] ? ? '' ,
2025-04-10 10:33:19 +04:00
'tags' => $video [ 'tags' ] ? ? [],
'isLive' => isset ( $video [ 'isLive' ]) ? $video [ 'isLive' ] : false
2025-04-08 09:12:46 +04:00
];
}
return $videos ;
}
// Fonctions utilitaires pour formater les données d'affichage
function formatDuration ( $seconds ) {
$hours = floor ( $seconds / 3600 );
$minutes = floor (( $seconds % 3600 ) / 60 );
$remainingSeconds = $seconds % 60 ;
if ( $hours > 0 ) {
return sprintf ( '%d:%02d:%02d' , $hours , $minutes , $remainingSeconds );
} else {
return sprintf ( '%d:%02d' , $minutes , $remainingSeconds );
}
}
function formatViewCount ( $views ) {
if ( $views >= 1000000 ) {
return round ( $views / 1000000 , 1 ) . 'M' ;
} elseif ( $views >= 1000 ) {
return round ( $views / 1000 , 1 ) . 'K' ;
} else {
return $views ;
}
}
function formatDate ( $dateString ) {
$date = new DateTime ( $dateString );
$now = new DateTime ();
$interval = $now -> diff ( $date );
if ( $interval -> days == 0 ) {
return 'Aujourd\'hui' ;
} elseif ( $interval -> days == 1 ) {
return 'Hier' ;
} elseif ( $interval -> days < 7 ) {
return 'Il y a ' . $interval -> days . ' jours' ;
} elseif ( $interval -> days < 30 ) {
$weeks = floor ( $interval -> days / 7 );
return 'Il y a ' . $weeks . ' semaine' . ( $weeks > 1 ? 's' : '' );
} elseif ( $interval -> days < 365 ) {
$months = floor ( $interval -> days / 30 );
return 'Il y a ' . $months . ' mois' ;
} else {
$years = floor ( $interval -> days / 365 );
return 'Il y a ' . $years . ' an' . ( $years > 1 ? 's' : '' );
}
}
2025-04-08 15:36:33 +04:00
/**
* Récupère les vidéos d'une catégorie spécifique depuis l'API PeerTube
*
* @param int $categoryId Identifiant de la catégorie
* @param int $count Nombre de vidéos à récupérer
* @return array Liste des vidéos de la catégorie
*/
function getVideosByCategory ( $categoryId , $count = CATEGORY_VIDEOS_COUNT ) {
// Récupérer les vidéos par catégorie
$data = callPeerTubeApi ( 'videos' , [
'categoryOneOf' => $categoryId ,
'count' => $count ,
'sort' => '-publishedAt' , // Les plus récentes d'abord
'isLocal' => true
]);
return formatVideosData ( $data [ 'data' ] ? ? []);
}
/**
* Récupère la liste des catégories à afficher (triées selon les priorités)
*
* @return array Liste des catégories avec id, name et videos
*/
function getDisplayCategories () {
$categories = [];
$priorityCategories = PRIORITY_CATEGORIES ;
$allCategories = PEERTUBE_CATEGORIES ;
2025-04-08 15:41:22 +04:00
// Ajouter uniquement les catégories prioritaires dans l'ordre défini
2025-04-08 15:46:18 +04:00
foreach ( $priorityCategories as $catId => $categoryName ) {
$videos = getVideosByCategory ( $catId );
// N'ajouter que les catégories qui ont des vidéos
if ( ! empty ( $videos )) {
$categories [] = [
'id' => $catId ,
'name' => $categoryName ,
'videos' => $videos
];
2025-04-08 15:36:33 +04:00
}
}
return $categories ;
}
2025-04-09 13:03:23 +04:00
/**
* Récupère les commentaires d'une vidéo
* @param string $videoId ID de la vidéo
* @return array Tableau des commentaires
*/
function getVideoComments ( $videoId ) {
$endpoint = " videos/ { $videoId } /comment-threads " ;
$response = callPeerTubeApi ( $endpoint );
if ( ! $response || ! isset ( $response [ 'data' ])) {
return [];
}
return $response [ 'data' ];
}
2025-04-09 13:46:25 +04:00
/**
* Récupère les options de téléchargement pour une vidéo
* @param string $videoId ID de la vidéo
* @return array Options de téléchargement
*/
function getVideoDownloadOptions ( $videoId ) {
// Récupérer les informations complètes de la vidéo
$videoData = callPeerTubeApi ( 'videos/' . $videoId );
$downloadOptions = [];
// Ajouter les fichiers directs s'ils existent
if ( isset ( $videoData [ 'files' ]) && ! empty ( $videoData [ 'files' ])) {
foreach ( $videoData [ 'files' ] as $file ) {
if ( isset ( $file [ 'fileDownloadUrl' ]) && ! empty ( $file [ 'fileDownloadUrl' ])) {
$downloadOptions [] = [
'type' => 'direct' ,
'url' => PEERTUBE_URL . $file [ 'fileDownloadUrl' ],
'resolution' => isset ( $file [ 'resolution' ][ 'label' ]) ? $file [ 'resolution' ][ 'label' ] : 'Original' ,
'size' => isset ( $file [ 'size' ]) ? formatFileSize ( $file [ 'size' ]) : 'Inconnu'
];
}
}
}
// Ajouter les playlists de streaming s'ils existent
if ( isset ( $videoData [ 'streamingPlaylists' ]) && ! empty ( $videoData [ 'streamingPlaylists' ])) {
foreach ( $videoData [ 'streamingPlaylists' ] as $playlist ) {
if ( isset ( $playlist [ 'files' ]) && ! empty ( $playlist [ 'files' ])) {
foreach ( $playlist [ 'files' ] as $file ) {
if ( isset ( $file [ 'fileDownloadUrl' ]) && ! empty ( $file [ 'fileDownloadUrl' ])) {
$downloadOptions [] = [
'type' => 'hls' ,
'url' => $file [ 'fileDownloadUrl' ],
'resolution' => isset ( $file [ 'resolution' ][ 'label' ]) ? $file [ 'resolution' ][ 'label' ] : 'Original' ,
'size' => isset ( $file [ 'size' ]) ? formatFileSize ( $file [ 'size' ]) : 'Inconnu'
];
}
}
}
}
}
return $downloadOptions ;
}
/**
* Formate la taille d'un fichier en format lisible
* @param int $bytes Taille en octets
* @return string Taille formatée
*/
function formatFileSize ( $bytes ) {
$units = [ 'B' , 'KB' , 'MB' , 'GB' , 'TB' ];
$bytes = max ( $bytes , 0 );
$pow = floor (( $bytes ? log ( $bytes ) : 0 ) / log ( 1024 ));
$pow = min ( $pow , count ( $units ) - 1 );
$bytes /= ( 1 << ( 10 * $pow ));
return round ( $bytes , 2 ) . ' ' . $units [ $pow ];
}
2025-04-10 13:10:00 +04:00
/**
* Recherche des vidéos selon un critère
*
* @param string $query Terme de recherche
* @param int $count Nombre de vidéos à récupérer
* @param int $start Index de départ pour la pagination
* @return array Liste des vidéos correspondant à la recherche
*/
function searchVideos ( $query , $count = COUNT_VIDEO_SEARCH , $start = 0 ) {
if ( empty ( $query )) {
return [];
}
// Vérifier si la recherche concerne un tag (commence par #)
$isTagSearch = false ;
if ( substr ( $query , 0 , 1 ) === '#' ) {
$isTagSearch = true ;
$tag = substr ( $query , 1 ); // Enlever le # du début
// Récupérer les vidéos avec ce tag via l'API
$data = callPeerTubeApi ( 'videos' , [
'tagsOneOf' => $tag ,
'count' => $count ,
'start' => $start ,
'isLocal' => true , // Uniquement les vidéos locales
'sort' => '-publishedAt' // Les plus récentes d'abord
]);
return formatVideosData ( $data [ 'data' ] ? ? []);
}
// Recherche normale (pas un tag)
$data = callPeerTubeApi ( 'search/videos' , [
'search' => $query ,
'count' => $count ,
'start' => $start ,
'isLocal' => true , // Uniquement les vidéos locales
'sort' => '-publishedAt' // Les plus récentes d'abord
]);
return formatVideosData ( $data [ 'data' ] ? ? []);
}
2025-04-08 06:37:14 +04:00
?>