PageSourceSearch

https://www.lenouvelliste.ch/site/commun/scripts/index.js

js lenouvelliste.ch collected 2026-10-02 03:20:53 UTC 25,728 bytes, 685 lines download raw bytes

1/* Rollback pour header.js */
2var timeout = 10000; // 1000000ms = 1000 seconds
3var lib = function() {}; // Let's create an empty
4var referenceNode = function() {};
5let adTagId = '220';
6let webviewApp = false;
7let demo = false;
8let noAds = false;
9let prod = false;
10let refreshIt = false;
11let bloquePub = false;
12window.htag = window.htag || {};
13window.htag.que = window.htag.que || [];
14var headerAdnz = 0;
15
16
17if (sessionStorage.getItem('idArticle') !== null) {
18    dataLayerEcommerce = sessionStorage.getItem('idArticle');
19} else {
20	dataLayerEcommerce = (typeof dataLayerEcommerce !== 'undefined') ? dataLayerEcommerce : 'na';
21}
22
23let noInFeed = false;
24let lacote = false;
25let arcinfo = false;
26let lenouvelliste = false;
27let lnv = false;
28let isPromotedContentPage = false;
29let eventObject = [];
30let goInFeed = false;  // A mettre à true s'il faut réactiver les Infeed AI ET NF
31
32// Liste des URLs sur lesquelles la pub ne doit jamais s'afficher (utilisée par showAddsDirect()).
33// La pub ne se décide plus que sur l'URL : les anciens blocages basés sur le contenu du dataLayer
34// (typeContenu === "faq"/"espace client"/"page simple"/"tunnel"/"autres", contenuPartenaire === '1')
35// ne sont plus appliqués. "/pages/" couvre l'équivalent de l'ancien "page simple" (FAQ, conditions
36// générales, etc. vivent toutes sous /pages/) — voir URL_EXCEPTION_PUB ci-dessous pour les pages
37// sous /pages/ qui doivent malgré tout garder la pub (ex: avis de décès).
38// -> À vérifier avec Laurent : confirmer que "-1481758" (Edito Crans Montana) est toujours
39//    d'actualité (test > 1 an).
40const URL_BLOQUER_PUB = [
41  "contenus-sponsorises-thematiques",
42  "/archives-le-nouvelliste/",
43  "/contact",
44  "/formulairecontact",
45  "/nos-offres-d-abonnement",
46  "/nos-offres-speciales",
47  "/conditions-generales",
48  "/clubabonnes/",
49  "embed=true",
50  "/mon-compte/",
51  "/contenus-partenaires/",
52  "/contenus-sponsorises/",
53  "/auteurs/",
54  "/pages/",    // couvre FAQ, conditions générales, etc. (cf. URL_EXCEPTION_PUB pour les exceptions sous /pages/)
55  "-1481758"    // Edito Crans Montana
56];
57
58// Pages qui doivent TOUJOURS afficher la pub même si elles tombent sous un motif de URL_BLOQUER_PUB
59// (ex: les avis de décès vivent sous /pages/avis-de-deces/, comme la FAQ, mais ne doivent pas être bloqués).
60const URL_EXCEPTION_PUB = [
61  "/pages/avis-de-deces/"
62];
63
64/* petite condition pour exclure inFeed dans un article + LIGNE 239 */
65if (window.location.href.indexOf("1505387") > -1) {
66    noInFeed = true;
67}
68// Condition pour essais sans pub
69if (window.location.href.indexOf("1505387") > -1 || window.location.href.indexOf("1505880") > -1) {
70    noAds = true;
71}
72/* petite condition pour vérifier si c'est las page de promoted Content */
73if (window.location.href.indexOf("1134817") > -1) {
74    isPromotedContentPage = true;
75}
76
77if (window.location.href.indexOf("nouvelliste") > -1) {
78	lenouvelliste = true;
79    adTagId = '220';
80} else if (window.location.href.indexOf("arcinfo") > -1) {
81	arcinfo = true;
82    adTagId = '277';
83} else if (window.location.href.indexOf("lacote") > -1) {
84	lacote = true;
85    adTagId = '276';
86    lacote = true;
87} else if (window.location.href.indexOf("lenordvaudois") > -1) {
88	lnv = true;
89    bloquePub = false;  // true pour bloquer
90	adTagId = '10434';
91}
92
93if (!bloquePub) {
94  // initialisation de la balise SCRIPT   bloquePub = false;
95  var myScript = document.createElement("script");
96  myScript.setAttribute("src", "https://adnz.co/header.js?adTagId=" + adTagId);
97  myScript.setAttribute("data-esh", "adnz");
98
99  // SITE DE DEMO initialisation de la balise SCRIPT
100  var myScriptDEMO = document.createElement("script");
101  myScriptDEMO.setAttribute("src", "https://adnz.co/header.js?adTagId=" + adTagId);
102  myScriptDEMO.setAttribute("data-esh", "adnz");
103
104
105  if (window.location.href.indexOf("?native") > -1) {
106      webviewApp = true;
107      // console.log('webviewApp: ' + webviewApp);
108  }
109  if (window.location.href.indexOf("test.lenouvelliste.ch") > -1
110      || window.location.href.indexOf("test.arcinfo.ch") > -1
111      || window.location.href.indexOf("test.lacote.ch/") > -1
112	  || window.location.href.indexOf("test.lenordvaudois.ch/") > -1) {
113      demo = true;
114  } else {
115      prod = true;
116  }
117
118  // console.log('adTagId: ' + adTagId)
119  if((demo || prod) && !noAds) {
120      // La pub ne se décide plus que sur l'URL (showAddsDirect() / URL_BLOQUER_PUB) : plus de
121      // ciblage par mots-clés (department/premium/connected/article) ni de blocage basé sur le
122      // contenu du dataLayer. Le pageLoad du dataLayer ne sert plus qu'à signaler un changement
123      // de page (navigation interne) pour déclencher un refresh.
124
125      // Déclenche la pub tout de suite, sans attendre l'événement pageLoad du dataLayer (gain de
126      // vitesse, surtout sur le tout premier chargement).
127      adnzDirect();
128      console.log('Trigger direct (1er chargement) ' + adTagId);
129
130      // Le tout premier pageLoad poussé par le dataLayer correspond à LA MÊME page que l'appel
131      // direct ci-dessus (déjà traité) et ne doit pas relancer un refresh. Seuls les pageLoad
132      // suivants (navigation interne, signalant un changement de page) doivent rafraîchir la pub.
133      var firstLoadHandled = true;
134
135      var eventify = function (arr, callback) {
136      // console.log('post eventify');
137        arr.push = function (e) {
138          // console.log('pre push');
139            Array.prototype.push.call(arr, e);
140            console.log('e.event: ' + e.event);
141            callback(e);
142        };
143    };
144
145      // On garde l'écoute du dataLayer pour connexionCompte (qui n'a rien à voir avec la pub) et
146      // pour détecter les changements de page via pageLoad. pageLoadGA a été retiré : tout passe
147      // désormais par pageLoad. On n'utilise plus aucune donnée portée par l'événement pageLoad
148      // pour la pub elle-même (ex-ciblage department/premium/connected/article) : uniquement l'URL.
149      waitForDataLayer(function(dataLayer) {
150          eventify(dataLayer, function (e) {
151              if (e.event === 'pageLoad') {
152                  eventObject = e;
153
154				  // Ex-pageLoadGA : ce bloc tournait auparavant sur l'événement pageLoadGA,
155				  // maintenant fusionné avec pageLoad. Il tourne à chaque pageLoad, indépendamment
156				  // de la logique de pub ci-dessous.
157				  updateDLcommerce(e);
158				  redirectAboTunnelAchat(e);    // redirige tunnel achat si abo
159				  desactivateAbosBtn(e);		// désactives les boutons de la page des abos
160
161				  if (firstLoadHandled) {
162					  // Ce pageLoad correspond au chargement déjà traité par l'appel direct ci-dessus :
163					  // on ne relance rien, on autorise juste le PROCHAIN pageLoad (une vraie navigation
164					  // interne suivante) à rafraîchir.
165					  firstLoadHandled = false;
166				  } else {
167					  adnzDirect();
168					  console.log('Trigger direct (refresh, navigation interne) ' + adTagId);
169				  }
170
171              } else if (e.event === 'connexionCompte') {
172                  eventObject = e;
173				  refreshAfterConnexion(e);  //refresh si connexion dans tunnel
174              }
175          });
176      });
177
178    // Condition pour désactiver sur LC car plus de infeed en dur ET AI NF avec goInFeed
179    if (lacote === false && goInFeed) {
180      addCSSfileToTheDocument();
181    }
182  }
183}
184
185
186//  Function pour rediriger le client qui possède un abo arrive dans le Tunnel d'achat (/abos/)
187// Exception: le onboarding
188function redirectAboTunnelAchat(e) {
189	let URLabos = false;
190	let URLonboarding= false;
191	let connectAbo = false;
192	let typeUserStr = e.typeUser || '';  // GARDE-FOU: e.typeUser peut être absent selon le moment où pageLoad se déclenche
193	// URL onboarding ?
194	if (window.location.href.indexOf("/onboarding") > -1) {
195		URLonboarding = true;
196	}
197	// URL contient-elle /abos/ ?
198	if (window.location.href.indexOf("/abos/") > -1) {
199		URLabos = true;
200	}
201	// typeUser est connecté avec abo?
202	if (typeUserStr.indexOf("avec abo") > -1) {
203		connectAbo = true;
204	}
205	if(connectAbo && URLabos) {
206		if (!URLonboarding && lnv) {  // Pas onboarding et LNV
207			window.location.replace('https://www.lenordvaudois.ch/pages/vous-etes-deja-abonne/');
208		}
209		if (!URLonboarding && arcinfo) {  // Pas onboarding et AI
210			window.location.replace('https://www.arcinfo.ch/pages/erreur-deja-abonne/');
211		}
212		if (!URLonboarding && lacote) {  // Pas onboarding et LC
213			window.location.replace('https://www.lacote.ch/pages/erreur-deja-abonne/');
214		}
215		if (!URLonboarding && lenouvelliste) {  // Pas onboarding et NF
216			window.location.replace('https://www.lenouvelliste.ch/pages/erreur-deja-abonne/');
217		}
218	}
219	return true;
220}
221
222// recharge page si dans tunnel et abonné
223function refreshAfterConnexion(e) {
224	let URLabos = false;
225	let pageAbo = false;
226	console.log('refresh tunnel step 1');
227	if (window.location.href.indexOf("/abos/identification/") > -1) {
228		URLabos = true;
229	}
230	if (window.location.href.indexOf("lenordvaudois.ch/pages/nos-offres-d-abonnement") > -1) {
231		pageAbo = true;
232	}
233	console.log('refresh tunnel step 2: URLabos=' + URLabos +', pageAbo='+ pageAbo );
234	if(URLabos || pageAbo) {
235		window.location.href = window.location.href;
236	}
237}
238
239// pour désactiver les boutons d'abo si tu es abonné
240function desactivateAbosBtn(e) {
241	if (window.location.href.indexOf("lenordvaudois.ch/pages/nos-offres-d-abonnement") > -1) {
242		var typeUser = (e && e.typeUser) ? String(e.typeUser) : '';
243
244	  // Si pas "avec abo", on sort
245	  if (typeUser.indexOf("avec abo") === -1) {
246		console.warn('typeUser ne contient pas "avec abo" => on ne touche à rien');
247		return;
248	  }
249
250	  var attempts = 0;
251	  var maxAttempts = 40; // 40 * 500ms = 20 secondes
252
253	  var intervalId = setInterval(function () {
254		attempts++;
255
256		var lien2 = document.querySelector("#NV-M-LANC_PLUS_30");
257		var lien3 = document.querySelector("#NV-M-LANC_PLUS_50");
258
259		console.log(
260		  'Tentative', attempts,
261		  'lien2:', !!lien2,
262		  'lien3:', !!lien3
263		);
264
265		// On (ré)applique les styles à chaque fois si les boutons existent
266		if (lien2) {
267		  lien2.removeAttribute("href");
268		  lien2.style.pointerEvents = "none";
269		  lien2.style.opacity = "0.5";
270		  lien2.textContent = "Déjà abonné";
271		}
272
273		if (lien3) {
274		  lien3.removeAttribute("href");
275		  lien3.style.pointerEvents = "none";
276		  lien3.style.opacity = "0.5";
277		  lien3.textContent = "Déjà abonné";
278		}
279
280		// On arrête uniquement au bout d'un certain temps
281		if (attempts >= maxAttempts) {
282		  clearInterval(intervalId);
283		  console.log('Stop interval desactivateAbosBtn (maxAttempts atteint)');
284		}
285
286	  }, 500); // on vérifie toutes les 500ms
287	}
288
289}
290
291
292// Pour debugger
293function debugMobile(values) {
294	var idDIV = 'debug-abo';
295  // Si le div existe déjà, on le réutilise
296  var dbg = document.getElementById(idDIV);
297
298  if (!dbg) {
299    dbg = document.createElement(idDIV);
300    dbg.id = 'debug-abo';
301
302    // Style lisible sur iPhone
303    dbg.style.position = "fixed";
304    dbg.style.bottom = "10px";
305    dbg.style.left = "10px";
306    dbg.style.zIndex = "999999";
307    dbg.style.background = "rgba(0,0,0,0.85)";
308    dbg.style.color = "white";
309    dbg.style.padding = "10px";
310    dbg.style.fontSize = "12px";
311    dbg.style.fontFamily = "monospace";
312    dbg.style.maxWidth = "90vw";
313    dbg.style.whiteSpace = "pre-line";
314    dbg.style.borderRadius = "6px";
315
316    document.body.appendChild(dbg);
317  }
318
319  // Écriture des valeurs dans le div
320  dbg.textContent = JSON.stringify(values, null, 2);
321}
322
323
324// On associe l'idArticle à la datalayerEcommerce pour remonter dans vent
325function updateDLcommerce(e) {
326  if (
327    e.idArticle === undefined ||
328    e.idArticle === '' ||
329    e.idArticle === 'na' ||
330    e.idArticle === null
331  ) {
332    console.warn('e.idArticle modifie pas: ' + e.idArticle);
333  } else if (e.idArticle.length > 3) {
334    dataLayerEcommerce = e.idArticle;
335    sessionStorage.setItem("idArticle", e.idArticle);
336  } else {
337    //console.warn('e.idArticle on ne fait rien: ' + e.idArticle);
338  }
339  console.warn('dataLayerEcommerce: ' + dataLayerEcommerce);
340}
341
342
343
344// Les fonctions de pub
345function addCSSfileToTheDocument() {
346  // Get HTML head element
347	var head = document.getElementsByTagName('HEAD')[0];
348	// Create new link Element
349 	var link = document.createElement('link');
350	// set the attributes for link element
351	link.rel = 'stylesheet';
352	link.type = 'text/css';
353	link.href = '/site/commun/scripts/styles-webfile.css';
354	// Append link element to HTML head
355	head.appendChild(link);
356}
357
358// Détecte la page d'accueil uniquement via l'URL (pas de dataLayer) : chemin racine du domaine,
359// quel que soit le site (lenouvelliste/arcinfo/lacote/lenordvaudois) ou la présence d'une query string.
360function isHomepage() {
361	var path = window.location.pathname;
362	return path === '/' || path === '';
363}
364
365// Envoie à Audienzz le seul mot-clé "accueil", uniquement sur la page d'accueil.
366// NB: department en tableau (comme version), pas en chaîne simple, pour rester cohérent avec le
367// format attendu par Audienzz pour toutes les autres clés de updateKeywords.
368// Envoie department: ["accueil"] sur la page d'accueil, et department: [] (vide) partout ailleurs.
369// On envoie systématiquement les deux cas (pas seulement "accueil") pour ne pas laisser une valeur
370// "accueil" collée sur les pages suivantes si updateKeywords fusionne les clés au lieu de les
371// remplacer entièrement à chaque appel.
372// Détecte un article via l'URL uniquement (plus rapide que d'attendre typeContenu du dataLayer) :
373// un chemin qui se termine par un identifiant numérique (ex: ...-1514158), SAUF avis-de-deces,
374// /pages/ ou clubabonnes qui ont la même forme d'URL (numéro à la fin) mais ne sont pas des
375// articles normaux. On teste window.location.pathname pour ignorer une éventuelle query string
376// (ex: ...corrida-d-octodure-1514204?back=%2Fpages%2Fclubabonnes%2F).
377function isArticle() {
378	var path = window.location.pathname;
379	if (!/-\d+$/.test(path)) {
380		return false;
381	}
382	if (path.indexOf('avis-de-deces') > -1 || path.indexOf('/pages/') > -1 || path.indexOf('clubabonnes') > -1) {
383		return false;
384	}
385	return true;
386}
387
388// Envoie à Audienzz department et article ensemble, dans le même appel, systématiquement à chaque  
389// page (pas seulement quand c'est vrai) : department = ["accueil"] sur l'accueil sinon [], article
390// = ["true"] sur un article sinon ["false"]. On envoie toujours les deux valeurs explicitement pour
391// ne pas laisser une valeur d'une page précédente collée à la suivante si updateKeywords fusionne
392// les clés au lieu de les remplacer entièrement à chaque appel.
393function pushUrlKeywords() {
394	var department = isHomepage() ? ["accueil"] : [];
395	var article = isArticle() ? ["true"] : ["false"];
396	console.warn('pushUrlKeywords() sur ' + window.location.pathname + ' -> department=' + JSON.stringify(department) + ', article=' + JSON.stringify(article));
397	window.htag.que.push(function () {
398		console.warn('department=' + JSON.stringify(department) + ', article=' + JSON.stringify(article) + ' ajoutés à updateKeywords');   // <- ICI qu'on ajoute department/article
399		window.htag.api('1').updateKeywords(() => ({
400			version: ["2021"],
401			article: article,
402			department: department
403		}));
404	});
405}
406
407function adnzDirect() {
408	// IMPORTANT: le department doit être déterminé et poussé à Audienzz AVANT de lancer les scripts
409	// (avant addHeaderTagJSfile() qui injecte header.js, et avant tout refreshAds()) — sinon ce n'est
410	// pas pris en compte. window.htag.que existe déjà depuis le tout début du fichier, donc on peut y
411	// pousser ceci en tout premier, avant même de savoir si la pub est bloquée ou non. Appelé à chaque
412	// fois (pas seulement sur l'accueil) pour que la valeur soit bien vidée en quittant l'accueil.
413	pushUrlKeywords();
414
415	var fautPub = showAddsDirect();
416    console.warn('fautPub: ' + fautPub );
417
418    if (headerAdnz === 0) {
419        headerAdnz = 1;
420		var aRetourner = sortAdsOrNot(headerAdnz,fautPub);
421		window.htag = window.htag || { que: [] };
422		window.htag.que.push(function () {
423		  window.htag.isDisabled = function () {
424			return aRetourner;   // BUGFIX: c'était "return false" en dur, showAddsDirect()/aRetourner n'était jamais appliqué
425		  }
426		});
427
428		addHeaderTagJSfile();
429		//console.warn(window.audienzz.keywords); 
430    } else {
431        headerAdnz++;		
432		var aRetourner = sortAdsOrNot(headerAdnz,fautPub);  // BUGFIX: recalculé à chaque refresh (sinon une page bloquée restait sans blocage après un refresh)
433		window.htag.que.push(function () {
434		  window.htag.isDisabled = function () {
435			return aRetourner;
436		  }
437		  window.htag.api('1').refreshAds();
438		});
439		console.warn('refreshAds()');
440		
441    }
442}
443
444// Retourne sit faut désactiver pub
445function sortAdsOrNot(headerAdnz,fautPub) {
446	var disableCheck = false;
447	if (headerAdnz > 1 && fautPub) {
448        disableCheck = false;
449		refreshIt = true;
450    } else if (fautPub && headerAdnz === 1) {
451		disableCheck = false;
452		refreshIt = false;
453    } else { // DONC FAUT PAS PUB
454		disableCheck = true;
455		console.warn('refresh et disableCheck: ' + disableCheck);
456		refreshIt = true;
457	}
458	console.warn('Desactive pub: '+disableCheck);
459	return disableCheck;
460}
461
462// Fonction qui refraîchit la pub ou pas selon contexte
463function refreshOrNot(refreshIt) {
464	if (refreshIt) {
465		htag.api('1').refreshAds();
466		console.warn('refreshIt');
467
468	} else {
469		console.warn('!refreshIt');
470	}
471}
472
473
474function isPartenaireComm(e, arrTags) {
475	console.warn('isPartenaireComm(e)');
476    var isPartenaire = false;
477	const strArrTags = arrTags.join();
478	if (strArrTags.indexOf("mmobilier") > -1) {
479		isPartenaire = false;
480     } else if (strArrTags.indexOf("commercial") > -1 || strArrTags.indexOf("artenaire") > -1 || strArrTags.indexOf("sponsor") > -1 ) {
481		isPartenaire = true;
482     }
483	 console.table(strArrTags);
484  	// Pour le nouveau tag dédié partenaire
485	if (strArrTags.indexOf("mmobilier") > -1) {
486		isPartenaire = false;
487     } else if(e.contenuPartenaire !== '' && e.contenuPartenaire !== '0' && e.contenuPartenaire !== 'na') {
488		isPartenaire = true;
489	}
490	console.dir('contenuPartenaire = ' + e.contenuPartenaire + ' isPartenaire:' + isPartenaire);
491    return isPartenaire;
492}
493
494function isLongFormOrFaceAface(e) {
495    var isLongForm = false;
496    var typeContenu = e.typeContenu;
497    if (typeContenu.indexOf("LongForm") > -1) {
498        isLongForm = true;
499    }
500    return isLongForm;
501}
502
503function deviceFromWidth() {
504    var widthDevice = (window.innerWidth > 0) ? window.innerWidth : screen.width;
505    var device = '';
506    if (widthDevice < 481) {
507        device = 'mobile';
508    } else if (widthDevice < 769 && widthDevice > 480) {
509        device = 'tablet';
510    } else if (widthDevice < 1025 && widthDevice > 768) {
511        device = 'laptop';
512    } else if (widthDevice > 1024) {
513        device = 'desktop';
514    }
515    //console.log('Device: ' + device)
516    return device;
517
518}
519
520function arrDptJSON() {
521    // 1. On se base sur l'URL pour en tirer des mot-clé
522    var department = [];
523    var urlBase = window.location.href;
524    var placement = urlBase.lastIndexOf(".ch/") + 3;
525    var urlSecond = urlBase.substring(placement);
526    var array1 = urlSecond.split("/");
527    array1.pop(); // suppression dernier élément: si article supp titre si index supprime champ vide
528
529    // Si pas vide, on ajoute à department
530    for (i = 0; i < array1.length; i++) {
531        if (array1[i] != '' && array1[i] != null && array1[i] != undefined) {
532            department.push(array1[i].toLowerCase());
533        }
534    }
535
536    // Si court, c'est l'accueil
537    var leLength = urlBase.length;
538    if (leLength <= 30) {
539        department.push('accueil');
540    }
541
542    // 2. On se base sur les données JSON enrichies pour en tirer des sections
543    var JSONDATA = document.querySelectorAll('script[type="application/ld+json"]');
544    var myArray = [];
545    for (var i = 0; i < JSONDATA.length; i++) {
546        var contextJson = JSON.parse(JSONDATA[i].innerHTML);
547      // Si c'est la partie @graph
548      if('@graph' in contextJson) {
549        var avecGraph = contextJson['@graph'];  // Corr sept 2023 pour ajout niveau @graph
550        for (var j = 0;
550 j < avecGraph.length; j++) {
551            var leType = avecGraph[j]['@type'];
552            // S'il s'agit bien d'un article et pas autre chose comme index
553            if (leType === 'NewsArticle') {
554                // On boulce sur Keywords et on ajoute au tableau myArray
555                for (var k = 0; k < avecGraph[j].keywords.length; k++) {
556                    myArray.push(avecGraph[j].keywords[k].toLowerCase());
557                }
558                // On boulce sur articleSection et on ajoute au tableau department
559                for (var k = 0; k < avecGraph[j].articleSection.length; k++) {
560                  var cetteRubrique = avecGraph[j].articleSection[k].toLowerCase()
561                    department.push(cetteRubrique);
562                }
563            }
564            // S'il y a un BreadcrumListe on va en pomper les mot-clé
565            if (leType === 'BreadcrumbList') {
566                if (typeof avecGraph[j].itemListElement !== 'undefined') {
567                    if (typeof avecGraph[j].itemListElement[0] !== 'undefined') {
568                        if (typeof avecGraph[j].itemListElement[0].item !== 'undefined') {
569                            if (typeof avecGraph[j].itemListElement[0].item.name !== 'undefined') {
570                                myArray.push(avecGraph[j].itemListElement[0].item.name);
571                            }
572                        }
573                    }
574                }
575            }
576        }
577
578      }
579
580    }
581    // On boucle sur department et on ajoute son contenu dans myArray si existe pas déjà
582    for (var s = 0; s < department.length; s++) {
583        var conteArray = department[s];
584        if (myArray.indexOf(conteArray) < 0) {
585            myArray.push(conteArray);
586        }
587    }
588
589    // On retourne myArray avec les contenus de department en plus de lui-même
590    return myArray;
591}
592
593// La funciton qui supprimes les deux blocs de pub
594function removeHalfAndWide5() {
595    //components-advertisement  ads-placeholder-container
596    var halfpage = document.getElementById('adnz_halfpage_1');
597    var wideboard5 = document.getElementById('adnz_wideboard_5');
598    var wideboard1 = document.getElementById('adnz_wideboard_1');
599    var wideboardGris1 = document.getElementsByClassName('components-advertisement')[0];
600    var wideboardGris2 = document.getElementsByClassName('components-advertisement')[1];
601
602    if (halfpage !== null && typeof halfpage !== 'undefined') {
603        halfpage.remove();
604        console.log('adnz remove halfpage');
605    }
606    if (wideboard5 !== null && typeof wideboard5 !== 'undefined') {
607        wideboard5.remove();
608        console.log('adnz remove wideboard 5');
609    }
610    if (wideboard1 !== null && typeof wideboard1 !== 'undefined') {
611        wideboard1.remove();
612        console.log('adnz remove wideboard 1');
613    }
614    if (wideboardGris1 !== null && typeof wideboardGris1 !== 'undefined') {
615        wideboardGris1.remove();
616        console.log('adnz remove wideboardGris1');
617    }
618    if (wideboardGris2 !== null && typeof wideboardGris2 !== "undefined") {
619      	console.log('wideboardGris2: ' + wideboardGris2)
620        wideboardGris2.remove();
621        console.log('adnz remove wideboardGris2');
622    }
623
624}
625
626function showAddsDirect() {
627    console.warn('showAddsDirect()');
628    let retour = true;
629
630    let url = window.location.href;
631	let isException = URL_EXCEPTION_PUB.some(x => url.indexOf(x)>=0); //retouren true ou false
632	let blockAds = URL_BLOQUER_PUB.some(x => url.indexOf(x)>=0); //retouren true ou false
633    if (isException) {
634        // ex: avis de décès sous /pages/ : toujours de la pub, même si /pages/ est bloqué par ailleurs
635        retour = true;
636    } else if (blockAds) {
637        retour = false;
638        console.warn('pas pub direct');
639    }
640    return retour;
641}
642
643function addHeaderTagJSfile() {
644	if (demo) { // personnalisation headerTag pour demo
645		// SI le scipt existe déjà
646		/*
647		if (!document.querySelector('script[data-esh="gtm"]')) {
648			document.body.appendChild(myScriptDEMO);
649		} */
650
651	} else {
652		var appendAdnzScript = function () {
653			if (!document.querySelector('script[data-esh="gtm"]')) {
654				document.body.appendChild(myScript);
655				console.warn('balise script ADNZ ajoutée');
656			}
657		};
658		// GARDE-FOU: en mode direct, addHeaderTagJSfile() peut être appelée de façon synchrone
659		// dès l'exécution du script, avant que document.body existe (si header.js est chargé
660		// dans le <head> sans async/defer). On attend DOMContentLoaded dans ce cas.
661		if (document.body) {
662			appendAdnzScript();
663		} else {
664			document.addEventListener('DOMContentLoaded', appendAdnzScript);
665		}
666	}
667}
668
669// Pour attendre que dataLayer soit un array
670function waitForDataLayer(callback, retries = 20, delay = 100) {
671	let attempts = 0;
672
673	function check() {
674		if (Array.isArray(window.dataLayer)) {
675			callback(window.dataLayer);
676		} else if (attempts < retries) {
677			attempts++;
678			setTimeout(check, delay);
679		} else {
680			console.warn("dataLayer non disponible après plusieurs tentatives");
681		}
682	}
683
684	check();
685}

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.