niedziela, 29 lipca 2007

Kashub Geek za 3625 dolców?!?

Hmm... idąc za linkiem na wykopie zrobiłem sobie teścik.
Pytanka wypełniałem uczciwie i wyszło mi oto coś takiego:
50% Geek
Tylko kto mi powie co to oznacza? Czy 50% Geek to dobrze, czy źle?
Myślę, że ciężko tak po prostu to stwierdzić po jednym "badaniu".
Ale mam plan. Wypełnię sobie ten teścik raz jeszcze, na przykład za kilka miesięcy. Wtedy zobaczymy jak zmienia się moja "Geekowatość" :D
Tylko żeby się nie okazało, że jest już za późno... 0_o

//edit
Widzę, że stronka ma kilka ciekawych testów. Nie wiem czy to, co napiszę nie okaże się dla mnie zagrożeniem, ale wyszło mi, że martwy jestem warty $3625 :
$3625.00The Cadaver Calculator - Find out how much your body is worth. From Mingle2 - Free Online Dating

sobota, 21 lipca 2007

Sposób programisty na blokowanie reklam

Wszystkich nas denerwują natrętne i wszędzie obecne reklamy na stronach internetowych.
Osoby mniej cierpliwe starają się je blokować na różne sposoby, np. używając tworzonych do tego celu programów czy też plug-in'ów do przeglądarek.
Nie wszyscy jednak wiedzą, że istnieje jeszcze sposób, który polega na wskazaniu systemowi operacyjnemu, że w przypadku, gdy przeglądarka łączy się z jakimś adresem (np. z serwerem reklam), to ma zamiast tego łączyć się z wybranym innych adresem. Najczęściej jest to przekierowanie tych wywołań na adres własnego komputera, czyli na adres 127.0.0.1, czyli inaczej localhost.
Blokowanie reklam tym sposobem odbywa się poprzez dopisanie znanych serwerów do pliku hosts w systemie operacyjnym. W porządnych systemach operacyjnych lokalizacja tego pliku to /etc/hosts. W Windows 98 jest to domyślnie c:\windows\hosts, w Windows XP oraz Viście - c:\WINDOWS\system32\drivers\etc\hosts. W tym czymś ostatnim, to AFAIK nie da się tak po prostu mieszać w omawianym pliku, ale tutaj jest na to sposób.
Struktura pliku jest bardzo prosta. W pierwszej kolumnie wpisujemy adres ip, na który mamy zostać przekierowani przy odwołaniu do serwera, którego nazwa podana jest w kolumnie drugiej. Przykładowy wpis wygląda następująco:

127.0.0.1 pagead2.googlesyndication.com
Dzięki dodaniu tej jednej linijki do naszego pliku hosts nie będziemy już na przykład zmuszeni do oglądania reklam z Google'a.
Jak się zapewne domyślasz wystarczy dodać inne serwery z reklamami do naszego pliku hosts i jesteśmy wolni od reklam. Pojawia się tylko pytanie Skąd wziąć te wszystkie adresy, albo choćby większość z nich? Czy trzeba je samemu śledzić i wpisywać ręcznie? Spokojnie, nie trzeba. Można sobie pobrać stąd lub wykorzystać ten, którego ja używam (tu wielkie dzięki dla Vip'a).
No dobra. Mamy adresy, wszystko niby ok, już nie ściągamy znikąd reklam, tylko kierujemy na swój komputer. Ale co dalej? Mi osobiście nie podobał się ani komunikat o błędzie, że nie można załadować strony ani też po odpaleniu Apache'a ładowanie domyślnej stronki z localhost'a.
Postanowiłem wykorzystać moc wirtualnych hostów w Apache'u.
Najpierw do httpd.conf dodałem nowego wirtualnego hosta, na który chciałem przekierowywać wszystko, co mi plik hosts wyłapuje. W sekcji odpowiedzialnej za hosty wirtualne dodałem tych kilka linijek. Oznaczają one tyle, że w katalogu /mnt/lin2/web/v/localhost...
    DocumentRoot /mnt/lin2/web/v/localhost
...mam sobie plik index.php, który jest zarówno domyślnym plikiem, jak również plikiem, który jest wykonywany w przypadku, gdy żądanego obiektu nie można odnaleźć na serwerze:
    DirectoryIndex index.php
ErrorDocument 404 /index.php
Zdecydowana większość wyświetleń będzie się opierać właśnie na błędzie 404.
OK, po restarcie Apache'a doszliśmy więc do tego, że jak chce się gdzieś pokazać reklama, to się nie pokaże, tylko odwoła mi się do pliku /mnt/lin2/web/v/localhost/index.php.
To niestety jeszcze nie wszystko. Jeśli chodzi o jakieś iframe'y, to można by w pliku index.php napisać po prostu [spam] i to by wystarczyło. Dla mnie to jednak za mało.
Chcę, żeby mój skrypt:
  • działał dla
    • stron html,
    • zdjęć, animacji i obrazków,
    • skryptów JavaScript
  • posiadał funkcjonalność, która pozwoli mi określić jaki element został właśnie zablokowany, aby wiedzieć jaki adres usunąć z pliku hosts na wypadek gdyby nie podobało mi się to, że zablokował dany element.

Przechodzimy więc do naszego pliczku index.php.
Aby wiedzieć czego dotyczy dane żądanie i co zostało zablokowane używamy:
$req = $_SERVER['REQUEST_URI'];
Samo to nie wystarczy, bo musimy jeszcze wiedzieć jaki adres odblokować w hosts. Pełną ścieżkę wraz z nazwą serwera pobieramy więc za pomocą:
$full_path = $_SERVER['HTTP_HOST'] . $req;
Mamy już pełny adres pod zmienną
$full_path
. Przechodzimy więc do części właściwej - wypisania w miejscu, gdzie miała być jakaś reklama napisu [SPAM] wraz z pełną ścieżką żądanego elementu. Jeśli zablokowany element to strona HTML, to wystarczy kawałek kodu (już z kolorowaniem):
<div style="width: 98%; height: 98%; overflow: auto;
background-color: #fee; color: #f00;
font-family: courier; font-size: 14px;"
>
[SPAM] <?php echo $full_path; ?>
</div>
Jeśli gdzieś był jakiś iframe z blokowaną przez nas reklamą, to zamiast owej reklamy zobaczymy przewijane okienko z jasnoczerwonym tłem i czerwonym napisem z adresem zablokowanego elementu. Proste? Proste!
Przejdźmy teraz do skryptów JavaScript. Tu sprawa nieco się komplikuje. Najpierw sprawdźmy, czy adres żądanego elementu kończy się na .js:
if (eregi('^(.)+(js)$', $req))
Teraz musimy wypisać nasz komunikat za pomocą JavaScriptu na stronie, która ten skrypt wywołała:
document.write('<span style="overflow: auto;
background-color: #fee; color: #f00;
font-family: courier; font-size: 14px;">'
+
'[SPAM]<?php echo htmlspecialchars($full_path) ?></span>');
Żeby przeglądarki wiedziały, że mają do czynienia ze skryptem JS musimy jeszcze przed wysłaniem w/w treści wpisać:
header('Content-type: text/javascript');

Wszystko niby ładnie i pięknie, jednak w testach się okazało, że tak generowany skrypt nie działa, czyli nie wypisuje treści w referującym dokumencie. Po chwili zastanowienia znalazłem gada. Błąd polegał na tym, że jeśli element nie istnieje (a na ogół nie istnieje), to serwer www wysyła nagłówek 404, który informuje przeglądarki, że tego, co otrzyma za chwilę nie ma interpretować jako skrypt, bo coś nie poszło. Rozwiązaniem jest dodanie przed w/w linią poniższego kodu:
header('HTTP/1.1 200 OK');
Dzięki temu przeglądarka uzna, że plik skryptu istnieje i poprawnie go wykona.
Pozostało nam teraz napisanie kodu, który będzie się wykonywał w przypadku, gdy blokujemy jakiś obrazek. Najpierw sprawdźmy, czy żądany element jest obrazem (na podstawie rozszerzenia oczywiście):
if (eregi('^(.)+(jpg|png|gif|jpeg|svg|bmp)$', $req))
Informujemy przeglądarkę, że będziemy wysyłać np. GIF'a:
header('Content-type: image/gif');
Tworzymy tego GIF'a o wysokości np. 20 px i szerokości równej ilości liter w adresie żądanego elementu razy 10 px + 30 px na napis [SPAM]:
$obrazek = ImageCreate(10*strlen($full_path)+30,20);
Teraz na obrazku piszemy znany już nad pełny adres żądanego elementu:
ImageString($obrazek,4,3,2,'[SPAM] ' .
htmlspecialchars($full_path),$kolor_tekstu);
I na koniec wysyłamy spreparowany obrazek do przeglądarki:
ImageGif($obrazek);

No i to wszystko!
Troszkę pisania, ale bynajmniej nie muszę oglądać reklam, szybciej ładują mi się strony i widzę co zablokowałem na wypadek, gdybym jednak chciał gdzieś tam coś obejrzeć :]
Osoby, którym się nie chce pisać podaję kod źródłowy pliku odpowiedzialnego za przechwytywanie reklam ze stron internetowych. Może nie jest to kod idealny, pewnie można go i ulepszyć i przyspieszyć, dodać obsługę np. flash'a, napisać w OOP, itp, ale podaję go tylko jako przykład i jeden ze sposobów na natrętne reklamy na stronach www.
Na zakończenie screen z zasypanej na ogół reklamami stronki przy użyciu opisanej metody ich blokowania: