W3Schools.com – runda druga

5 lat temu przyglądnąłem się niesławnej stronie W3Schools. Nadszedł czas, by sprawdzić, czy od tego czasu coś się tam poprawiło.

Artykuł opisuje stan zasobów W3Schools na dzień 30 października 2022. Od tego dnia w zasobach W3Schools mogły zajść zmiany, które można prześledzić przy pomocy Internet Archive Wayback Machine.

Uwagi wstępne

W tym artykule przejrzę dokładnie te same rzeczy co 5 lat temu, porównam, czy i co się zmieniło, a następnie dla każdej testowanej strony stwierdzę, czy wg mnie się poprawiło, czy nie.


HTML Element Reference
[Spis elementów HTML]

Część elementów dalej jest oznaczana jako niewspierana w HTML5. Jeśliby być naprawdę dokładnym, to trzeba by zauważyć, że HTML5 już nawet nie istnieje – choć ta nazwa wciąż jest potocznie używana.

Opisy elementów dalej są mieszane i część jest opisywana wg tego, co było w HTML 4.01 (np. b jako pogrubienie tekstu), a część wg najnowszego standardu (np. u jako nietekstowe adnotacje).

Definicja dla figure dalej nie ma sensu i przypomina bardziej definicję article ze specyfikacji:

The article element represents a complete, or self-contained, composition in a document, page, application, or site and that is, in principle, independently distributable or reusable, e.g. in syndication.

[Element article reprezentuje kompletną, samodzielną kompozycję w dokumencie, na stronie, w aplikacji lub witrynie, która jest, co do zasady, możliwa do samodzielnego dystrybuowania lub używania np. w formatach agregujących treść.]

Tak, samodzielność jest cechą zarówno article, jak i figure, ale w tym drugim wypadku jeszcze bardziej istotnym jest fakt, że to ilustracja do artykułu. I jako ilustrację rozumiem tutaj wszystko to, co dostałoby w tekście swój własny podpis (a więc grafika, zdjęcie, wykres, ale też – tabela, fragment kodu…) i mogło zostać umieszczone w spisie ilustracji na końcu dokumentu. Powiedziałbym, że samodzielność figure jest do pewnego stopnia ograniczona. Owszem, taka ilustracja sama w sobie przekazuje jakieś informacje, ale pełny sens uzyskuje dopiero po umieszczeniu w swoim pierwotnym kontekście. Wykres zwiększania się popularności JavaScriptu w ostatniej dekadzie pokazuje trend, ale to artykuł, w którym był ilustracją, dodaje cały kontekst i wyjaśnia, czemu się tak dzieje. W chwili, gdy całą definicję figure sprowadzamy do samodzielności, pozbywamy się wszystkich tych elementów, które pozwalają odróżnić figure choćby właśnie od article.

Na liście brakuje też kilku elementów, jak np. menu.

Werdykt

Brak poprawy.

Błędy są dokładnie takie same jak 5 lat temu.


HTML figure tag
[Znacznik figure]

Jedyna zmiana, jaka zaszła, to lekko odświeżony przykład, który zawiera obecnie także podpis zdjęcia dodany przy pomocy elementu figcaption. I ten przykład, który jest pierwszą rzeczą, jaką użytkownik widzi po wejściu na tę stronę, przeczy całemu późniejszemu opisowi elementu figure, sugerując, że każde zdjęcie nadaje się na figure.

Dodatkowo, style pokazywane jako domyślne dla figure są niezgodne z tymi, jakie są opisane w specyfikacji. A to właśnie te ze specyfikacji są używane przez większość przeglądarek, co łatwo sprawdzić w devtools.

Werdykt

Brak poprawy.

Drobny lifting przykładu w niczym nie pomaga.


HTML DOM Figure Object
[Obiekt Figure z HTML DOM]

Nic się nie zmieniło przez te 5 lat, Figure dalej nie istnieje.

Werdykt

Brak poprawy.


HTML Audio/Video DOM play() Method
[Metoda play z HTML Audio/Video DOM]

Tu podobnie. Informacja o tym, że ta metoda nic nie zwraca, była nieprawdą już 5 lat temu. Od tego czasu tego nie poprawiono i nie zanosi się, by to mialo się zmienić w najbliższym czasie. A tego typu rzeczy mogą prowadzić do subtelnych błędów, np. wysypania się aplikacji, jeśli format filmiku jest niewspierany.

Werdykt

Brak poprawy.

Najwidoczniej 5 lat to zbyt krótko, żeby poprawić taką rzecz…


HTML5 Video

Wciąż istnieje tutaj nieprawdziwa informacja o trzech wspieranych formatach. Przez te 5 lat zdeaktualizowała się jeszcze bardziej, bo dodatkowo pojawił się nowy format, AV1, który ma szansę – jako pierwszy – stać się faktycznie uniwersalnym formatem video.

Dodatkowo, strona informuje, że automatyczne odtwarzanie filmików z dźwiękiem jest blokowane na Chrome’ie, ale to nie jest do końca prawda. Praktycznie każda przeglądarka je blokuje i każda ma własny zestaw reguł, które pozwalają niektórym stronom na automatyczne odtwarzanie takich filmików. MDN ma cały poradnik o tym.

Werdykt

Brak poprawy.


HTML !DOCTYPE Declaration

Strona od moich ostatnich odwiedzin została mocno przeredagowana, niemniej nie wpłynęło to ostatecznie na poziom merytoryczny treści. Wciąż zawiera ona podstawowy błąd:

The declaration is not an HTML tag. It is an „information” to the browser about what document type to expect.

[Deklaracja nie jest znacznikiem HTML. To „informacja” dla przeglądarki, jakiego typu dokumentu się spodziewać.]

Jak już wielokrotnie powtarzałem, DOCTYPE służy wyłącznie do wymuszania trybu renderowania zgodnego ze standardami.

Werdykt

Brak poprawy.

Informacje są czytelniej przedstawione, ale wciąż najpoważniejszy błąd merytoryczny pozostał.


HTML !DOCTYPE
[HTML !DOCTYPE]

5 lat temu ta strona nazywała się HTML Elements and Valid DOCTYPES [Elementy HTML oraz prawidłowe DOCTYPE], co, prawdę mówiąc, było sensowniejszym tytułem.

Niemniej ta lekka kosmetyka to jedyne, co się zmieniło. Część elementów dalej jest źle przyporządkowana. Z jakiegoś powodu zniknął też element menu, chociaż dalej jest częścią standardu HTML. Oprócz HTML5 i HTML 4 w tabeli jest też XHTML, ale nie do końca wiadomo, o którą jego wersję chodzi – 1, 1.1 czy może HTML w trybie XML? Sadząc po tym, że w tabeli XHTML różni się zarówno od HTML5, jak i HTML 4, to najprawdopodobniej chodzi o wersję 1.1.

Inna rzecz, że obecnie nie ma za bardzo sensownego powodu, by używać HTML-a innego niż obecny, więc wiedza przedstawiona na tej stronie jest w dużej mierze historyczna.

Werdykt

Brak poprawy.

Powiedziałbym wręcz, że jest minimalnie gorzej, bo część elementów HTML zniknęła…


HTML section tag
[Znacznik HTML section]

Definicja sekcji została uproszczona:

The section tag defines a section in a document.

[Znacznik section definiuje sekcję w dokumencie.]

To zdecydowanie krok w dobrą stronę. Sekcje nie są już dłużej zrównywane z nagłówkami i stopkami. Niemniej brakuje tutaj wspomnienia o tym, że sekcja powinna mieć nagłówek (MDN o tym informuje). Brakuje też jakiegokolwiek wyjaśnienia, czym jest tak naprawdę sekcja.

Werdykt

Minimalna poprawa.

Nie ma już błędu merytorycznego, ale uzyskano to kosztem wycięcia prawie całej treści na stronie.


HTML Editors
[Edytory HTML]

Dalej polecamy jest Notatnik… Przez te 5 lat zmieniło się trochę i Atom wypadł z gry, ale za to pojawiło się Visual Studio Code, a w tle czai się JetBrains Fleet. Nie ma absolutnie żadnego powodu, by utrudniać sobie pracę i korzystać z edytora, który nie jest przystosowany do tworzenia stron WWW.

Werdykt

Brak poprawy.

Polecanie obecnie Notatnika jest jeszcze bardziej żenujące, niż 5 lat temu.


HTML Elements
[Elementy HTML]

Wciąż znajduje się tutaj bzdurna informacja, jakoby W3C zalecało pisanie kodu małymi literami.

Dodatkowo – na co nie zwróciłem uwagi 5 lat temu – znajduje się tutaj informacja, że elementy HTML trzeba zawsze zamykać (nie omijać znaczników zamykających), inaczej mogą występować błędy. I, ogólnie rzecz biorąc, jest to prawda. Problem w tym, że w przykładzie wykorzystano element p, którego nie trzeba zamykać i jest to wyraźnie zaznaczone w standardzie:

A p element’s end tag can be omitted if the p element is immediately followed by an address, article, aside, blockquote, details, div, dl, fieldset, figcaption, figure, footer, form, h1, h2, h3, h4, h5, h6, header, hgroup, hr, main, menu, nav, ol, p, pre, section, table, or ul element, or if there is no more content in the parent element and the parent element is an HTML element that is not an a, audio, del, ins, map, noscript, or video element, or an autonomous custom element.

[Znacznik zamykający elementu p może zostać pominięty, jeśli bezpośrednio po elemencie p następuje element address, article, aside, blockquote, details, div, dl, fieldset, figcaption, figure, footer, form, h1, h2, h3, h4, h5, h6, header, hgroup, hr, main, menu, nav, ol, p, pre, section, table lub ul albo w rodzicu elementu p nie ma już więcej treści i jest on elementem HTML innym niż a, audio, del, ins, map, noscript, video czy autonomiczny element niestandardowy.]

Przykład zaproponowany przez W3Schools jest poprawnym składniowo HTML-em. O wiele lepszym przykładem byłby element a, który faktycznie powoduje błędy w wyświetlaniu strony, jeśli nie zostanie zamknięty.

Werdykt

Brak poprawy.

Strona zawiera dokładnie te same błędy co 5 lat temu.


PHP Form Validation
[Walidacja formularza w PHP]

5 lat temu strona nazywała się PHP 5 Form Validation [Walidacja formularza w PHP 5]. To miło, że ta nieszczęsna piątka zniknęła z tytułu, ale szkoda, że to jedyna widoczna zmiana tutaj… Wszystkie pozostałe uwagi dalej są aplikowalne.

Werdykt

Brak poprawy.

To wciąż poradnik dla PHP 5, sprzedawany jako poradnik dla PHP 8.


JavaScript Tutorial
[Kurs JS]

Zniknęła informacja, że JS to język programowania HTML-a, i zostało tylko stwierdzenie, że to język programowania Sieci.

Werdykt

Poprawa.

Szkoda, że jedyne miejsca, w których W3Schools się poprawia, to te, w których coś usuwa…


JavaScript Versions
[Wersje JS]

Ta strona przeszła poważny lifting i teraz pokazuje inne informacje. Trudno je nazwać bardziej sensownymi, bo od ES6 poszczególne wersje ES wprowadzały poszczególne ficzery, nie zaś – dokonywały rewolucji. Stąd informowanie, kiedy dana wersja ES była w pełni obsługiwana przez daną przeglądarkę, nie ma zbyt wiele sensu. O wiele bardziej developera interesuje, czy może użyć jakiegoś konkretnego ficzera, np. async/await. A tego się z tej strony nie dowie. Zdecydowanie lepszymi źródłami Są w tym wypadku Can I Use? czy choćby MDN, mające przy każdym ficzerze tabelki kompatybilności dla przeglądarek, Node.js i Deno (np. dla wspomnianego async/await).

Pomijam tutaj, że np. w opisie ES6 całkowicie pominięto dodanie składni modułów, co jest bodaj największą zmianą, jaką przyniosła ta wersja języka. No i sam opis wersji kończy się na ES2020 a obecnie (30 października 2022) trwają prace już nad ES2023.

Werdykt

Minimalna poprawa.

Informacje na tej stronie mają obecnie przynajmniej jakiś sens. Ale wciąż są w dużej mierze nieprzydatne do niczego i przestarzałe.


JavaScript JSON

5 lat temu zauważyłem, że strona zawiera nieprawdziwą informację o tym, że JSON ma składnię identyczną z JS-em. I faktycznie, wtedy była to prawda, ale od ES2019 składnie są już identyczne. Innymi słowy: szybciej poprawiony zostanie standard niż informacje na W3Schools.

Werdykt

Brak poprawy.

To, że nagle część informacji na tej stronie stała się prawdziwa, bynajmniej nie jest zasługą W3Schools…


JavaScript Window – The Browser Object Model
[JavaScript Window – Przeglądarkowy Model Obiektowy]

Informacja o tym, że BOM nie jest ustandaryzowany, jest cały czas obecna.

Werdykt

Brak poprawy.


JavaScript Global Reference
[Spis właściwości globalnych w JS]

Lista wciąż jest niekompletna. Są Number i String, ale nie ma innych typów, np. Symbol.

Dodatkowo strona zawiera informacje, że globalne obiekty i funkcje są własnościami obiektu window. To jest prawdą głównie w przeglądarkach, bo inne środowiska JS (jak np. Node.js czy nawet wnętrze Web Workerów) mogą mieć inaczej nazwane obiekty globalne (np. global lub self). Stąd lepiej byłoby wspomnieć o globalThis.

Werdykt

Brak poprawy.


CSS3 Box Sizing

Ta strona nie zmieniła się znacząco przez te 5 lat, ale z kolei moje spojrzenie na nią się zmieniło. Myślę, że te 5 lat temu potraktowałem ją zbyt surowo. Tak, nie ma tutaj informacji, czym jest model pudełkowy, ale jest rozpisany przykład, jak liczone są wymiary elementów. A to w większości przypadków powinno wystarczyć.

Werdykt

Ujdzie.

Strona się, co prawda, nie zmieniła za bardzo, ale za to ja dojrzałem (albo przynajmniej bardziej przymykam oko).


Node.js NPM

5 lat temu jedyne, co wytknąłem na tej stronie, to fakt, że npm zostało błędnie nazwane NPM. Ten mankament do dzisiaj nie jest poprawiony… aczkolwiek nie jest to najpoważniejszy mankament tutaj.

Jest tu bardzo spory problem z nazewnictwem. Spójrzmy na definicję pakietu:

A package in Node.js contains all the files you need for a module.

Modules are JavaScript libraries you can include in your project.

[Pakiet w Node.js zawiera wszystkie pliki potrzebne dla modułu.

Moduły to javascriptowe biblioteki, które możesz dołączyć do swojego projektu.]

Zacznijmy od tego, że pakiety npm to NIEpakiety w Node.js. Od bardzo dawna npm jest managerem pakietów dla całego ekosystemu JS, w tym dla rozwiązań frontendowych, takich jak React czy nieśmiertelne jQuery. Dodatkowo inne środowiska uruchomieniowe JS-a, takie jak Bun czy Deno, również mają wsparcie dla npm.

Co więcej, w obecnym ekosystemie JS moduł jest zdecydowanie mniejszy od pakietu i nie można powiedzieć, że pakiet zawiera rzeczy potrzebne dla modułu. Jest wręcz odwrotnie: pakiet składa się z modułów. Bo od czasów ES6 moduł to nic innego jak plik z importami i eksportami. Można powiedzieć, że moduł to taki pojedynczy klocek LEGO, z którego następnie buduje się całe budowle – czyli właśnie pakiety. Jak podaje oficjalna dokumentacja Node.js, pakiet to katalog, w którym znajduje się plik package.json oraz pliki z kodem JS. Tak, czasami pakiet składa się z pojedynczego modułu (np. pakiet find-up), ale nawet wóczas temu modułowi towarzyszy właśnie plik package.json, często też jakieś testy lub definicje typów. Zatem nawet w najprostszym przypadku pakiet to moduł z dodatkowymi informacjami.

Nieprawdą jest też to, że te dodatkowe informacje są modułowi potrzebne do działania. Dobrze pokazało to swego czasu Deno, które pozwala całkowicie ominąć npm i wczytywać pakiety bezpośrednio przez URL, np. bibliotekę ramda. Jeśli posłużymy się Unpkg (czyli CDN-em, który pozwala używać paczek z npm-a bez potrzeby ich instalowania przy pomocy npm-a) i skorzystamy z pliku eksportującego wszystkie funkcje biblioteki, to wówczas możemy tę bibliotekę użyć w Deno. Przykładowy skrypt:

import * as ramda from 'https://unpkg.com/ramda@0.28.0/es/index.js';

console.log( ramda );

Po zapisaniu tego pliku można go odpalić poprzez wywołanie deno run <ścieżka do pliku>.

Dodatkowe informacje zawarte w package.json są potrzebne głównie samemu npm-owi do sensownego zarządzania pakietami i ich zależnościami. Pozwalają też np. dołączać do kodu dodatkowe informacje o jego autorze czy używanej licencji.

Nieprawdą też jest, że moduł to biblioteka. Tak, w niektórych przypadkach moduły mogą eksportować wiele rzeczy i dzięki temu być de facto bibliotekami, ale znów – nie zawsze. Wróćmy do ramdy – każda funkcja jest tam osobnym modułem, np. funkcja forEach. W takim Deno (czy przeglądarce) nie trzeba wczytywać całej biblioteki ramda, wystarczy wczytać tylko moduły z potrzebnymi nam funkcjami. Biblioteki sugerują coś dużego, a moduły najczęściej są małe, czasami wręcz atomowe. O wiele sensowniej byłoby je nazwać właśnie klockami LEGO.

Te definicje są spójne z innym artykułem o Node.js na stronie W3Schools, Node.js Modules [Moduły Node.js]. Tam pada stwierdzenie o modułach jako bibliotekach w kontekście wbudowanych modułów w Node.js (ang. built-in modules). I tak, w ich kontekście takie uproszczenie ma sens, bo tym są wbudowane moduły – zbiorem funkcji dotyczących wybranych obszarów webdevu, np. operacji na plikach. Ale poza tym kontekstem takie definiowanie modułów i pakietów wprowadza jedynie chaos pojęciowy i nijak się ma do tego, jak funkcjonuje ekosystem JS.

Przykład wykorzystania pakietu npm też jest dość dziwny. Nie bardzo widzę powód, dla którego jest tutaj wykorzystywany serwer HTTP do wyświetlenia jednej linijki tekstu… Równie dobrze można było go wyświetlić w konsoli – zwłaszcza, że przecież skrypt JS jest odpalany w tejże konsoli! Sam kod mógłby też spokojnie używać składni ES6:

const uc = require( 'upper-case' );

console.log( uc.upperCase( 'Hello World!' ) );

Dzięki temu przykład jest zdecydowanie prostszy i pozwala się skupić na tym, co istotne – używaniu zewnętrznych pakietów – zamiast na całym boilerplacie potrzebnym do stworzenia prostego serwera HTTP. Inna rzecz, że mamy rok 2022 i powoli rozpoczyna się migracja całego ekosystemu npm do ESM, więc wypadałoby użyć też nowej składni importów:

import { upperCase } from 'upper-case';

console.log( upperCase( 'Hello World!' ) );

To wymaga, by taki plik został zapisany z rozszerzeniem .mjs lub towarzyszył mu odpowiednio skonfigurowany plik package.json. Więcej o tym mówi dokumentacja Node.js.

Niemniej nawet po takich zmianach ten przykład jest średnio sensowny, bo zamienianie znaków na duże JS ma wbudowane od zawsze, jako String#toUpperCase(), i nie ma absolutnie żadnego powodu, by używać zamiast tego zewnętrznego pakietu. I właśnie tego typu praktyka (wykorzystywanie pakietów npm do wszystkiego) doprowadziła swego czasu do położenia sporej cześci całego ekosystemu. Chociaż, patrząc na to, jak często są aktualizowane materiały na W3Schools, ten przykład mógł równie dobrze powstać przed tą katastrofą…

A jak już się czepiać, to:

www.npmjs.com hosts thousands of free packages to download and use.

[www.npmjs.com zawiera tysiące darmowych pakietów do ściągnięcia i użycia.]

Owszem, 5 lat temu było prawdą, ale w 2019 npm przekroczyło pułap 1 miliona pakietów.

Werdykt

Brak poprawy.

Błąd, który wytknąłem sprzed 5 lat nie został poprawiony, a i cała pozostała treść strony pozostawia wiele do życzenia.

Podsumowanie

Cóż, minimalnie poprawiły się głównie te elementy, w których W3Schools coś usunęło – co chyba tym bardziej dobitnie pokazuje, że ich treść nie jest najwyższej jakości… Najbardziej zastanawia to, jak mało się tutaj zmieniło przez ostatnie 5 lat. A przecież w webdevie w tym czasie działo się naprawdę dużo. W samym CSS-ie mieliśmy kilka trzęsień ziemi. Na W3Schools wciąż jest jak w okolicach 2015 – nie ma grida, za to są floaty. Poradnik PHP wspomina, że konkurentem tego języka jest ASP – technologia martwa od lat. Lista wbudowanych modułów Node.js jest oparta o Node.js 6.10.3 – wersję z maja 2017 roku (obecnie, w październiku 2022 roku, mamy Node 19).

Materiały na W3Schools są dosłownie zamrożone w czasie, od 2017 praktycznie się nie zmieniły. Już wtedy były przestarzałe, a dzisiaj są już tak stare, że wręcz szkodliwe. Cały czas powtarzane są tutaj stare mity i nieprawdziwe informacje (jak choćby o !DOCTYPE), proponowane są przestarzałe techniki (tworzenie układu strony na float), a nowoczesny JS nawet tutaj nie dotarł (gdzie są moduły ES?). Nie spodziewałem się wielkich zmian, ale to, w jakim stanie są treści na W3Schools, było zaskoczeniem nawet dla mnie.

Nie widzę tak po prawdzie sensownego powodu, by używać W3Schools zamiast MDN-u, który jest tak samo darmowy, a do tego zawiera aktualne informacje, poprawiane na bieżąco przez rzeszę ludzi od lat siedzących w branży.

I mam nadzieję, że za 5 lat już nie będzie okazji pisać o W3Schools po raz trzeci.

4 komentarze do “W3Schools.com – runda druga”

    1. Hej,

      nie powiedziałbym, że nie przechodzi. Walidator nie zwraca żadnego błędu, najpoważniejszym zarzutem jest ostrzeżenie związane z brakiem nagłówka w jednej sekcji. Cała reszta komunikatów jest oznaczona jako „Info” i jedynie informuje o pewnej dobrej praktyce, której nie stosuję.

      A głównym powodem jest… WordPress. To on generuje kod w taki sposób, że ten nieszczęsny slash na końcu niektórych elementów jest. Chodzi mi po głowie przesiadka na coś innego (Astro albo Eleventy może), co przy okazji powinno też naprawić ten „problem”.

Skomentuj Comandeer Anuluj pisanie odpowiedzi

Twój adres e-mail nie zostanie opublikowany. Wymagane pola są oznaczone *

Witryna wykorzystuje Akismet, aby ograniczyć spam. Dowiedz się więcej jak przetwarzane są dane komentarzy.