J'ai lu hier un article du blog de John Resig, « Javascript as a language ». J'étais en plein dans des soucis de code Javacript sur la nouvelle version de dascritch.net, justement...
Alors oui, Javascript 2 amène des nouveautés alléchantes, notamment sur les boucles itératives, ou encore le JIT (la compilation à la volée) qui va permettre d'accélérer les applications web... mais JS2 n'est implémenté que dans Firefox...3.
Seulement, dans son article, John Resig ne parle que des fonctions de base de Javascript, en occultant ce qui fait (à la louche) 60% de son usage actuel : La manipulation d'un arbre DOM d'un document HTML pour le rendre “dynamique”, comme les applications AJAX (exemple ultime : Gmail) ou les XML enrichi (Firefox, Thunderbird,... ont leur interface en XML/XUL qui est programmée en javascript). Et c'est là que le bât blesse : là, rien n'est standard.
En fait, il y a tellement d'interprétations différentes du Javascript d'un arbre DOM qu'aujourd'hui je peux certifier ceci : Le Javascript est une collection de dialectes comme le fut à son époque de Basic. Et Microsoft dans les deux cas n'avait pas arrangé la situation.
John Resig est très actif dans l'intégration de Javascript 2 dans Mozilla (Firefox) et l'auteur de la bibliothèque Jquery.js ; il a beau être une pointure dans le domaine mais son enthousiasme ne peut nier la réalité, coder du Javascript reste un immonde foutoir. Firefox est le navigateur qui a le meilleur support Javascript et DOM, mais il est vrai que quand on a le créateur dans ses rangs, on peut difficilement être en-deça.
Safari ne peut en dire autant (quoique les bétas de la version 3 semblent enfin prometteurs), et à priori en codant dans KHTML, on est à 85% compatible à coup de sueurs froides.
Mais pour mettre à rude épreuve vos nerfs, MSIE est le pire de tous.
Par exemple, soit dans votre HTML une <balise title="" />
, que vous associez en javascript à votre variable balise
. Si vous appelez balise.title
, vous vous attendez bien sûr que les navigateurs web répondent logiquement une chaîne de caractère vide.
Pourtant, si vous mettez if (balise.title=='')
, la conditionnelle sera fausse dans MSIE. Car cet abruti vous dira que balise.title=='null'
! Au lieu de renvoyer une chaîne vide, cet incapable crée une chaîne non-vide pour dire qu'elle est vide. Résultat : pour faire proprement votre test, il faudra ruser avec le support de MSIE d'une fonction proprio, par exemple document.all
:
if ((balise.title=='')||((balise.title=='null')&&(document.all)))
Je ne veux pas persifler, mais on a quand même fait mieux comme langage de programmation pour tester si une chaine de caractère est vide.
Maintenant, supposons que vous voulez récupérer le texte dans <balise>texte <em>embarqué</em></balise>
sans le balisage. Vous avez la possibilité de récupérer comme suit (cliquez pour tester) :
fonction suffixiale javascript | résultat escompté | navigateurs supportés |
balise.innerHTML | "texte <em>embarqué</em>" | Compatible chez tout le monde, mais hélas, comporte les balises HTML embarquées |
balise.innerText | "texte embarqué" | MSIE, Konqueror, Safari, mais pas Firefox |
balise.outerHTML | "<balise>texte <em>embarqué</em></balise>" | Exclusivement MSIE, avec tout le balisage dont on veux pas |
balise.textContent | "texte embarqué" | Uniquement Firefox, mais Safari 3 va enfin le comprendre |
Donc si vous voulez faire un code “efficace” marchant “à coup sûr”, il va falloir utiliser innerHTML
, mais avec une regexp (« mmmmhhh les expressions régulières... mmmhhhh » comme dirait De Funès). Une soupe à la grimace genre ça (je garanti pas que ça marche... ah ben si, cliquez) : balise.innerHTML.replace(/<[^<>]+>/g,"")
Vous croyez en avoir fini ? Reste à trouver les versions de MSIE... car les comportements changent entre 5.5, 6, 6SP2 et 7 !
Si un if (document.all)
permet de démasquer MSIE et sa bande, le User Agent sniffing ne marche pas sur des faux navigateurs (comme Avant Browser, PhaseOut ou Maxthon, une bonne liste ici). Impossible d'être exactement sûr de la version du moteur MSIE utilisée sans un commentaire conditionnel, genre <!--[if lt IE 7] -->
niché dans le HTML, rendant illusoire l'idée de dissocier le code de la structure comme on a pu le faire avec le style.
Pire que tout, MSIE 7 dans ses toutes premières bétas montrait des comportements très différents dans le Javascript et les manips DOM. Vous développez votre site aux petits oignons, mixant PHP5, sHTML, CSS, règles Apache, xHTML, DOM et Javascript. Votre site se charge, les Javascripts de votre page sont quasi complètement interprétées... jusqu'à ce qu'une fenêtre d'alerte arrive : « Internet Explorer ne peut afficher le site http://... ». Cliquer dessus efface votre page et mène à une page d'erreur.
Coup de poignard dans le dos, ajoutant l'insulte à l'injure, cette page indique vaguement que MSIE n'arrive pas à contacter le site, ce qui est totalement faux. La réponse de la base d'information MS est risible.
Cette manie d'afficher un message bloquant (pour débugger) et mensonger (sur votre travail) a été backporté dans les MSIE6 SP2. super agréable.
Un des exemples de comportement changeant radicalement, MSIE considère désormais que le SEUL endroit où l'on peut insérer dynamique une librairie javascript c'est dans le <HEAD> de votre HTML. C'est à la fois logique, mais pas trop. Ce souci sans aucune documentation existante m'a empêché d'avancer pendant un an, surtout sans MS-Windows sous la main.
Et là, j'ai encore un autre problème avec exactement les mes symptômes. Je peux délayer mes problèmes de programmation dans Dotclear2, mais que mon site ne soit pas lisible par 70% du marché alors que je cherche un emploi, ça non. Strictement impossible. Cela m'a tellement gâché la journée que je me suis passé les nerfs en ré-installant l'interphone. Si ça continue, je vais faire du ciment d'ici ce soir.
Pour en revenir à John Resig, il a presque raison. Mais hélas, en l'absence de standard DOM parfaitement appliqué, tout comme le CSS2 et les extensions Microsoft, on est actuellement dans la même situation que le Basic du début des années 1980s : la grammaire est identique pour tous, mais les mots varient suivant les dialectes.
Et rien que pour ça, j'en viens à regretter quand je faisais des pages WAP1.1, c'est dire !
7 réactions
1 De Da Scritch - 09/07/2007, 09:55
En lisant le code source de jQuery (motools me semble moins pratique), je remarque que cette bibliothèque js reconnait le navigateur selon le user agent. Pas heureux du tout :
var b = navigator.userAgent.toLowerCase();
// Figure out what browser is being used
jQuery.browser = {
version: (b.match(/.+(?:rv|it|ra|ie)[\/: ]([\d.]+)/) || [])[1],
safari: /webkit/.test(b),
opera: /opera/.test(b),
msie: /msie/.test(b) && !/opera/.test(b),
mozilla: /mozilla/.test(b) && !/(compatible|webkit)/.test(b)
};
Et en cas de spoofing d'UA ?
2 De Da Scritch Net Works - 09/08/2007, 19:15
La seconde guerre du web n'aura pas lieu
Et si... Netscape n'a jamais libéré son code source en mourant. Sans Mozilla, sans Firefox, que serait le World Wide Web de nos jours ? Un peu d'uchronie et beaucoup trop de parano ? Avant-propos Ce texte est issu d'une réflexion personnelle,...
3 De Da Scritch Net Works - 30/08/2007, 19:28
Tassons les Javascripts
au DocMartens™. Encore plus fort... Allez, encore ! Le gain est dérisoire, mais c'est si marrant ! Tassons ! Tassons ! Comme des gros bourrins......
4 De Da Scritch Net Works - 06/09/2007, 11:36
Javascript, l'accent d'la regex
“Javascript comme un dialecte”, acte II. Entre le professeur Louis De Funès : « mmmmh les expressions régulières, mmmmmhhh... vous allez en bouffer... mmmmmhhhh »...
5 De da scritch net works - 03/01/2008, 16:25
Les < button > d'acnée de Microsoft Internet Explorer
Ou comment palier à l'une des plus vicieuses déficiences mentales du navigateur le plus pourri de la planète sans renoncer à un élément HTML très pratique. [MÀJ] : il semblerait que le comprtement de MSIE soit encore plus pernicieux que ça....
6 De da scritch net works - 11/12/2008, 16:55
Microsoft Internet Explorer ou l'inflation dans la
Je ne sais pas comment ils font. Malgré tous leurs efforts pour rendre leur navigateur acceptable, ils arrivent à faire en sorte de devoir reprendre tous les anciens sites pour qu'ils fonctionnent comme avant....
7 De Da Scritch - 16/01/2009, 11:21
Il semble que cette aberration aie été supprimé dans jQuery :
http://nerdlife.net/2009/01/15/jque...
Ce qui du coup permet de passer outre les cas très particuliers des navigateurs faisant du spoofing d'UA, même dans leur propre JS.