-
-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathYoutube-Link.tcl
414 lines (367 loc) · 21.9 KB
/
Youtube-Link.tcl
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
###############################################################################################
#
# Name :
# TCL-Youtube-Link.tcl
#
# Description :
# This script retrieves information about Youtube titles using Youtube API V3.
# Allows you to search for titles with keywords
# It listens to youtube links on trade shows and displays title information
#
# Ce script récupère des informations sur les titres Youtube à l'aide de l'API Youtube V3.
# Permet de rechercher des titres avec des mots clefs
# Il écoute les liens youtube sur les salons et affiche les informations des titres
#
# Donation :
# github.com/ZarTek-Creole/DONATE
#
# Auteur :
# ZarTek @ github.com/ZarTek-Creole
#
# Website :
# github.com/ZarTek-Creole/TCL-Youtube-Link
#
# Support :
# github.com/ZarTek-Creole/TCL-Youtube-Link/issues
#
# Docs :
# github.com/ZarTek-Creole/TCL-Youtube-Link/wiki
#
# Thanks to :
# m00nie base code www.m00nie.com
# Imhotep ask and details from www.eggdrop.fr
# CrazyCat community french and help of eggdrop https://www.eggdrop.fr
# MenzAgitat tips/toolbox https://boulets.eggdrop.fr
#
###############################################################################################
# Décharger si déjà charger : Reset du script
if { [::tcl::info::commands ::YouTubeLink::Script:Unload] eq "::YouTubeLink::Script:Unload" } { ::YouTubeLink::Script:Unload }
namespace eval ::YouTubeLink {
variable API
variable YTDB
variable CMDIRC
variable Annonce
variable Throttled
variable Script
variable Bind
variable Channels
# Valeur du scripts :
array set Script {
"Name" "TCL-YouTube-Link"
"Auteur" "ZarTek-Creole @ https://github.com/ZarTek-Creole"
"Version" "2.7.2"
"Debug" "0"
}
######################################################################################
### Configuration Utilisateur *** (Modifier les variables dans cette sections) ***
######################################################################################
# Cette clé est la vôtre et devrait rester secrète.
# Pour obtenir une clef visitez :
# https://developers.google.com/youtube/v3/
#
set API(Key) "<YOUR_API_KEY>"
# Après combien de secondes décide-t-on que le site web utilisé par le script
# pour afficher les définitions est offline (ou trop lent) en l'absence de
# réponse de sa part ?
set API(Timeout) 10
# Nombre de resultats maximun
set API(Max_Resultats) 5
# Liste des commandes aux quelles le script doit répondre :
set CMDIRC(Public) "!yt !youtube"
# Autorisations pour la commande publique
# Plus d'information sur https://wiki.eggdrop.fr/Flags
set CMDIRC(Public_Flags) "-"
# Configurer dans la variable Annonce(Prefix) ce que vous desire voir devant les message :
set Annonce(Prefix) "\002\00301,00You\00300,04Tube\003\002"
# Configurer dans la variable Annonce(Message) l'annonce de sortie voulu lors d'un lien url youtube
#
# Les variables disponibles :
#
# \${MUSIC_TITLE} : Affiche le titre de la musique
# \${MUSIC_CHANNEL} : Affiche le nom de la chaine youtube
# \${MUSIC_DURATION} : Affiche la durée du titre
# \${MUSIC_PUBLISH} : Affiche quand le titre a été publié
# \${MUSIC_VIEWED} : Affiche le nombre de fois que le titre a été vue/lue
#
set Annonce(Message) "\002\00307\${MUSIC_TITLE}\002 \00305(\00314Durée:\00307 \${MUSIC_DURATION}\00305)-(\00314Nombre de vues: \00307\${MUSIC_VIEWED}\00305)-(\00314Chaine:\00307 \${MUSIC_CHANNEL}\00305)-(\00314Publiée:\00307 \${MUSIC_PUBLISH}\00305)\003"
# Configurer dans la variable Annonce(Message_Search) l'annonce de sortie voulu lors d'une recherche youtube
#
# Les variables disponibles :
#
# \${ITEM_NUM} : Affiche la numerotation du titre trouvé
# \${ITEM_TITLE} : Affiche le nom/descriptions du titre trouvé
# \${ITEM_LINK} : Affiche l'adresse url du titre trouvé
# Extra :
# \${MUSIC_CHANNEL} : Affiche le nom de la chaine youtube
# \${MUSIC_DURATION} : Affiche la durée du titre
# \${MUSIC_PUBLISH} : Affiche quand le titre a été publié
# \${MUSIC_VIEWED} : Affiche le nombre de fois que le titre a été vue/lue
#
# Annonce basique | Basic Annonce
set Annonce(Message_Search) "\002\00305\${ITEM_NUM}\00314)\003 \00307\${ITEM_TITLE} \002\00314-\003 \00305\${ITEM_LINK}\003"
# Annonce avec plus d'informations | Announcement with more information
# set Annonce(Message_Search) "\002\00305\${ITEM_NUM}\00314)\003 \00307\${ITEM_TITLE} \002\00314-\003 \00305\${ITEM_LINK}\003 \00305(\00314Durée:\00307 \${MUSIC_DURATION}\00305)-(\00314Nombre de vues: \00307\${MUSIC_VIEWED}\00305)"
# Message en cas de aucun resultat lors d'une recherche
set Annonce(Null_Resultat) "\002\00305\Aucun Resultat trouvé.\003"
# Chaine de caractere de séparation entre deux titres :
set Annonce(Split_Char) " \00304|\003 "
# Nombre de lien par annonce
set Annonce(Max_Links) 2
# Format d'affichage de la date de publication du titre
# Plus information sur https://www.tcl.tk/man/tcl/TclCmd/clock.htm#M26
# Exemple: "%a %d %b %Y à %H:%M"
set Format(Date) "%d/%m/%Y"
# La region de la date de publication. en france utilisez "fr"
# Plus d'information sur https://www.tcl.tk/man/tcl/TclCmd/clock.htm#M20
set Format(Date_locale) "fr"
# Liste des salons où le script sera active
# mettre "*" pour tout les salons
# Exemple pour autoriser #channel1 et #channel2
# set Channels(Allow) "#channel1 #channel2"
set Channels(Allow) "*"
######################################################################################
### Fin de la Configuration Utilisateur
######################################################################################
######################################################################################
### Configuration avancées
######################################################################################
# URL (n'y touchez pas à moins d'avoir une bonne raison de le faire)
set API(URL) "https://www.googleapis.com/youtube/v3"
# User client du navigateur API
set API(UserAgent) "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.212 Safari/537.36"
# The two variables below control throttling in seconds. First is per user, second is per channel third is per link
set Throttled(User) 5
set Throttled(Channel) 5
set Throttled(Link) 5
set Bind(RE_URLMatching) {(?:http(?:s|).{3}|)(?:www.|)(?:youtube.com\/watch\?.*v=|youtu.be\/)([\w-]{11})}
set Bind(Matching) {*youtu*be*/*}
set Annonce(URL_YT) "https://youtu.be/"
###############################################################################
### Fin de la Configuration avancées
###############################################################################
}
###############################################################################
### Procédure principale
###############################################################################
setudef flag youtube
# Afficher les séparateurs de milliers dans un nombre
proc ::YouTubeLink::add_thousand_separators { Nombre {seprator " "} } {
# https://boulets.eggdrop.fr/tcl/routines/tcl-toolbox-0001.html
return [::tcl::string::trimleft [::tcl::string::reverse [regsub -all {...} [::tcl::string::reverse ${Nombre}] {&.}]] "${seprator}"]
}
proc ::YouTubeLink::DEBUG { text } {
variable Script
if { ${::YouTubeLink::Script(Debug)} } { putlog "\[${::YouTubeLink::Script(Name)}\] ${text}" }
}
proc ::YouTubeLink::INIT { } {
variable Script
variable API
variable CMDIRC
variable Bind
#############################################################################
### Initialisation
#############################################################################
if { [package vcompare [regexp -inline {^[[:digit:]\.]+} ${::version}] 1.6.20] == -1 } { putloglev o * "\[${::YouTubeLink::Script(Name)} - erreur\] La version de votre Eggdrop est ${::version}\003; ${::YouTubeLink::Script(Name)} ne fonctionnera correctement que sur les Eggdrops version 1.6.20 ou supérieure." ; return }
if { [::tcl::info::tclversion] < 8.5 } { putloglev o * "\[${::YouTubeLink::Script(Name)} - erreur\] ${::YouTubeLink::Script(Name)} nécessite que Tcl 8.5 (ou plus) soit installé pour fonctionner. Votre version actuelle de Tcl est ${::tcl_version}\003." ; return }
if { [catch { package require tls 1.7.11 }] } { putloglev o * "\[${::YouTubeLink::Script(Name)} - erreur\] ${::YouTubeLink::Script(Name)} nécessite le package tls 1.7 (ou plus) pour fonctionner. Le chargement du script a été annulé." ; return }
if { [catch { package require http 2.8.9 }] } { putloglev o * "\[${::YouTubeLink::Script(Name)} - erreur\] ${::YouTubeLink::Script(Name)} nécessite le package http 2.8.9 (ou plus) pour fonctionner. Le chargement du script a été annulé." ; return }
if { [catch { package require json 1.3 }] } { putloglev o * "\[${::YouTubeLink::Script(Name)} - erreur\] ${::YouTubeLink::Script(Name)} nécessite le package json 1.3 (ou plus) pour fonctionner. Le chargement du script a été annulé." ; return }
if { [catch { package require clock::iso8601 0.1 }] } { putloglev o * "\[${::YouTubeLink::Script(Name)} - erreur\] ${::YouTubeLink::Script(Name)} nécessite le package clock::iso8601 0.1 (ou plus) pour fonctionner. Le chargement du script a été annulé." ; return }
::http::config -useragent ${::YouTubeLink::API(UserAgent)}
###############################################################################
### Binds
###############################################################################
foreach b ${::YouTubeLink::CMDIRC(Public)} { bind pub ${::YouTubeLink::CMDIRC(Public_Flags)} ${b} ::YouTubeLink::IRC:Search }
bind pubm ${::YouTubeLink::CMDIRC(Public_Flags)} "% ${::YouTubeLink::Bind(Matching)}" ::YouTubeLink::IRC:Listen:Links
bind evnt - prerehash ::YouTubeLink::Script:Unload
putlog "${::YouTubeLink::Script(Name)} ${::YouTubeLink::Script(Version)} by ${::YouTubeLink::Script(Auteur)} loaded."
}
proc ::YouTubeLink::Script:Unload {args} {
variable Script
putlog "Désallocation des ressources de ${::YouTubeLink::Script(Name)} ..."
foreach binding [lsearch -inline -all -regexp [binds *[set ns [::tcl::string::range [namespace current] 2 end]]*] " \{?(::)?${ns}"] {
putlog "unbind [lindex ${binding} 0] [lindex ${binding} 1] [lindex ${binding} 2] [lindex ${binding} 4]"
}
foreach running_utimer [utimers] {
if { [::tcl::string::match "*[namespace current]::*" [lindex ${running_utimer} 1]] } { killutimer [lindex ${running_utimer} 2] }
}
namespace delete [namespace current] ::[namespace current]
}
proc ::YouTubeLink::ThrottleCheck { nick chan link } {
if { [info exists ::YouTubeLink::Throttled($link)]} {
::YouTubeLink::DEBUG "::YouTubeLink::ThrottleCheck search term or video id: ${link}, is Throttled at the moment"
return 1
} elseif {[info exists ::YouTubeLink::Throttled($chan)]} {
::YouTubeLink::DEBUG "::YouTubeLink::ThrottleCheck Channel ${chan} is Throttled at the moment"
return 1
} elseif {[info exists ::YouTubeLink::Throttled($nick)]} {
::YouTubeLink::DEBUG "::YouTubeLink::ThrottleCheck User ${nick} is Throttled at the moment"
return 1
} else {
set ::YouTubeLink::Throttled($nick) [utimer ${::YouTubeLink::Throttled(User)} [list unset ::YouTubeLink::Throttled($nick)]]
set ::YouTubeLink::Throttled($chan) [utimer ${::YouTubeLink::Throttled(Channel)} [list unset ::YouTubeLink::Throttled($chan)]]
set ::YouTubeLink::Throttled($link) [utimer ${::YouTubeLink::Throttled(Link)} [list unset ::YouTubeLink::Throttled($link)]]
return 0
}
}
proc ::YouTubeLink::API:ControlInfo { URL_DATA } {
if { [dict exists ${URL_DATA} error] } {
return -code error [dict get [dict get ${URL_DATA} error] message]
}
return ${URL_DATA}
}
proc ::YouTubeLink::API:GetInfo { URL_Link } {
::http::register https 443 [list ::tls::socket -tls1 1]
array set httpconfig [::http::config]
::http::config -urlencoding utf-8 -useragent ${::YouTubeLink::API(UserAgent)}
# On remplace les caractères spéciaux par leur équivalent hexadécimal pour
# pouvoir être utilisés dans l'url.
# on restaure l'urlencoding comme il était avant qu'on y touche
::http::config -urlencoding ${httpconfig(-urlencoding)}
if { [catch { set token [::http::geturl ${URL_Link} -timeout [expr ${::YouTubeLink::API(Timeout)} * 1000]] }] } {
::YouTubeLink::DEBUG "::YouTubeLink::API:GetInfo \00314La connexion à \00312\037[set URL_Link]\037\003\00314 n'a pas pu être établie. Il est possible que le site rencontre un problème technique.\003"
} elseif {[::http::status ${token}] eq "ok"} {
# on extrait la partie qui nous intéresse et sur laquelle on va travailler
set received_data [::http::data ${token}]
::http::cleanup ${token}
::http::unregister https
return [json::json2dict ${received_data}]
}
}
proc ::YouTubeLink::IRC:Search { nick uhost hand chan text } {
if {
${::YouTubeLink::Channels(Allow)} != "*" && \
[lsearch -nocase ${::YouTubeLink::Channels(Allow)} ${chan}] == "-1" && \
![channel get ${chan} youtube]
} {
return
}
# !yt info 1
if {
[string match -nocase "info" [lindex ${text} 0]] \
&& [string is digit -strict [lindex ${text} 1]] \
&& [lindex ${text} 2] == "" \
&& [info exists ::YouTubeLink::YTDB([lindex ${text} 1])]
} {
set NUM [lindex ${text} 1]
::YouTubeLink::IRC:Listen:Links ${nick} ${uhost} ${hand} ${chan} "${::YouTubeLink::Annonce(URL_YT)}$::YouTubeLink::YTDB(${NUM})"
return
}
if { [::YouTubeLink::ThrottleCheck ${nick} ${chan} ${text}] } {
::YouTubeLink::DEBUG "::YouTubeLink::IRC:Search INFO: ThrottleCheck protection: ${nick} ${chan} ${text}"
return
}
::YouTubeLink::DEBUG "::YouTubeLink::IRC:Search is running with ${text} from ${chan}/${nick}"
set URL_Link "${::YouTubeLink::API(URL)}/search?part=snippet&fields=items(id(videoId),snippet(title))&[::http::formatQuery key ${::YouTubeLink::API(Key)} maxResults [expr ${::YouTubeLink::API(Max_Resultats)} + 1] q [lrange [split ${text}] 0 end]]"
set URL_DATA [::YouTubeLink::API:GetInfo ${URL_Link}]
if { [ catch {
::YouTubeLink::API:ControlInfo ${URL_DATA}
} ERROR_MSG ] } {
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} ERROR: ${ERROR_MSG}"
return
}
set ITEMS_DATA [dict get ${URL_DATA} items]
set ITEMS_DATA_LENGTH [llength ${ITEMS_DATA}]
set ITEM_NUM 0
set LOOP_NUM 0
if { ${ITEMS_DATA_LENGTH} == 0 } {
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} ${Annonce(Null_Resultat)}"
return
}
for { set i 0 } { ${i} < ${ITEMS_DATA_LENGTH} } { incr i } {
set ITEM_ID [lindex ${ITEMS_DATA} ${i} 1 1];
if { ${ITEM_ID} == "" } { continue }
incr ITEM_NUM
incr LOOP_NUM
set ::YouTubeLink::YTDB($ITEM_NUM) ${ITEM_ID}
set TMP_TITLE [encoding convertfrom [lindex ${ITEMS_DATA} ${i} 3 1]];
set ITEM_TITLE [string map -nocase [list "&" "&" "'" "'" """ "\""] ${TMP_TITLE}];
set ITEM_LINK "${::YouTubeLink::Annonce(URL_YT)}${ITEM_ID}";
if {
[string match "*MUSIC_DURATION*" ${::YouTubeLink::Annonce(Message_Search)}] || \
[string match "*MUSIC_PUBLISH*" ${::YouTubeLink::Annonce(Message_Search)}] || \
[string match "*MUSIC_CHANNEL*" ${::YouTubeLink::Annonce(Message_Search)}] || \
[string match "*MUSIC_DURATION*" ${::YouTubeLink::Annonce(Message_Search)}] || \
[string match "*MUSIC_VIEWED*" ${::YouTubeLink::Annonce(Message_Search)}]
} {
set URL_Link "${::YouTubeLink::API(URL)}/videos?id=${ITEM_ID}&part=snippet,statistics,contentDetails&fields=items(snippet(title,channelTitle,publishedAt),statistics(viewCount),contentDetails(duration))&[::http::formatQuery key ${::YouTubeLink::API(Key)}]"
set URL_DATA [::YouTubeLink::API:GetInfo ${URL_Link}]
if { [ catch {
::YouTubeLink::API:ControlInfo ${URL_DATA}
} ERROR_MSG ] } {
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} ERROR: ${ERROR_MSG} (${URL_Link})"
return
}
set ITEM_DATA {*}[dict get ${URL_DATA} items]
set MP_iso8601 [dict get ${ITEM_DATA} snippet publishedAt]
set MUSIC_PUBLISH [clock format [::clock::iso8601 parse_time ${MP_iso8601}] -format ${::YouTubeLink::Format(Date)} -locale ${::YouTubeLink::Format(Date_locale)}]
set MUSIC_CHANNEL [encoding convertfrom [dict get ${ITEM_DATA} snippet channelTitle]]
set MUSIC_DURATION [::YouTubeLink::FCT:ISO8601:TO:DURATION [dict get ${ITEM_DATA} contentDetails duration]]
set MUSIC_VIEWED [::YouTubeLink::add_thousand_separators [dict get ${ITEM_DATA} statistics viewCount] .]
}
append output [subst ${::YouTubeLink::Annonce(Message_Search)}] ${::YouTubeLink::Annonce(Split_Char)}
if { ${LOOP_NUM} == ${Annonce(Max_Links)} } {
set LOOP_NUM 0
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} [string trimright ${output} ${::YouTubeLink::Annonce(Split_Char)}]"
set output ""
}
}
if { ${output} != "" } {
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} [string trimright ${output} ${::YouTubeLink::Annonce(Split_Char)}]"
}
set CMD [lindex ${::YouTubeLink::CMDIRC(Public)} 0]
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} Info: ${CMD} info <num>"
}
proc ::YouTubeLink::IRC:Listen:Links {nick uhost hand chan text} {
if {
${::YouTubeLink::Channels(Allow)} != "*" && \
[lsearch -nocase ${::YouTubeLink::Channels(Allow)} ${chan}] == "-1" && \
![channel get ${chan} youtube]
} {
return
}
::YouTubeLink::DEBUG "::YouTubeLink::IRC:Listen:Links is running with ${text} from ${chan}/${nick}"
if { ![regexp -nocase -- ${::YouTubeLink::Bind(RE_URLMatching)} ${text} URL_Link id] } {
::YouTubeLink::DEBUG "::YouTubeLink::IRC:Listen:Links ERREUR: regexp ${::YouTubeLink::Bind(RE_URLMatching)} not match ${text} sur ${chan}"
return
}
if { [::YouTubeLink::ThrottleCheck ${nick} ${chan} ${id}] } {
::YouTubeLink::DEBUG "::YouTubeLink::IRC:Listen:Links INFO: ThrottleCheck protection: ${nick} ${chan} ${text}"
return
}
::YouTubeLink::DEBUG "::YouTubeLink::IRC:Listen:Links info: url is: ${URL_Link} and id is: ${id}"
set URL_Link "${::YouTubeLink::API(URL)}/videos?id=${id}&part=snippet,statistics,contentDetails&fields=items(snippet(title,channelTitle,publishedAt),statistics(viewCount),contentDetails(duration))&[::http::formatQuery key ${::YouTubeLink::API(Key)}]"
set URL_DATA [::YouTubeLink::API:GetInfo ${URL_Link}]
if { [ catch {
::YouTubeLink::API:ControlInfo ${URL_DATA}
} ERROR_MSG ] } {
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} ERROR: ${ERROR_MSG}"
return
}
set ITEMS_DATA {*}[dict get ${URL_DATA} items]
set MUSIC_TITLE [encoding convertfrom [dict get ${ITEMS_DATA} snippet title]]
set MUSIC_PUBLISH_iso8601 [dict get ${ITEMS_DATA} snippet publishedAt]
set MUSIC_PUBLISH [clock format [::clock::iso8601 parse_time ${MUSIC_PUBLISH}_iso8601] -format ${::YouTubeLink::Format(Date)} -locale ${::YouTubeLink::Format(Date_locale)}]
set MUSIC_CHANNEL [encoding convertfrom [dict get ${ITEMS_DATA} snippet channelTitle]]
set MUSIC_DURATION [::YouTubeLink::FCT:ISO8601:TO:DURATION [dict get ${ITEMS_DATA} contentDetails duration]]
set MUSIC_VIEWED [::YouTubeLink::add_thousand_separators [dict get ${ITEMS_DATA} statistics viewCount] .]
set isotime [lindex ${ITEMS_DATA} 0 3 1]
set views [lindex ${ITEMS_DATA} 0 5 1]
puthelp "PRIVMSG ${chan} :${::YouTubeLink::Annonce(Prefix)} [subst ${::YouTubeLink::Annonce(Message)}]"
}
proc ::YouTubeLink::FCT:ISO8601:TO:DURATION { isotime } {
regsub -all {PT|S} ${isotime} "" isotime
regsub -all {H|M} ${isotime} ":" isotime
if { [string index ${isotime} end-1] == ":" } {
set sec [string index ${isotime} end]
set trim [string range ${isotime} 0 end-1]
set isotime ${trim}0${sec}
} elseif { [string index ${isotime} 0] == "0" } {
set isotime "stream"
} elseif { [string index ${isotime} end-2] != ":" } {
set isotime "${isotime}s"
}
return ${isotime}
}
# Chargement du script
::YouTubeLink::INIT