Niezalogowany [ logowanie ]
Subskrybuj kanał ATOM Kanał ATOM    Subskrybuj kanał ATOM dla tagu php Kanał ATOM (tag: php)

Autor wpisu: batman, dodany: 14.06.2011 08:00, tagi: php

Pod koniec maja odbyła się konferencja Dutch PHP Conference. Chciałoby się powiedzieć jedna z wielu konferencji na temat PHP, jakie odbywają się w ciągu roku. Dlaczego jednak właśnie tak konferencja mnie zainteresowała? Bynajmniej nie z powodu Zend Frameworka 2, o którym wczoraj zaćwierkałem. Zainteresowała mnie, ponieważ o PHP mówiono w kontekście nowoczesnych rozwiązań, pokazując że język ten nie powiedział jeszcze ostatniego słowa. Pozwala mieć to nadzieję na przyszłość oraz w to, że mimo ciągłych tarć w ekipie odpowiedzialnej za PHP, język nadal będzie się rozwijał.

Przez ostatnie kilka lat PHP utknęło w wersji 5 i nawet wydanie wersji 5.3, wprowadzające szereg zmian do języka, nie jest w stanie zatrzeć negatywnego wrażenia spowodowanego porzuceniem prac na wersją 6 i brakiem jasnej drogi rozwoju. Pół roku temu cieszyłem się na zmiany mające pojawić się w wersji 5.4, a nieco ponad miesiąc temu webhostig.pl zastanawiał się czy uda się wydać najnowszą wersję jeszcze w tym roku. Nie wygląda to za dobrze.

Na szczęście są na świecie programiści wierzący w siłę PHP, co doskonale udowodniła wspomniana konferencja. Do najciekawszych tematów poruszanych podczas jej trwania można zaliczyć między innymi:

Wygląda na to, że PHP ma się dobrze i powoli wyrasta z brzydkiego kaczątka służącego głównie jako zaawansowany system szablonów. Może nadeszła pora aby wymienić ludzi odpowiedzialnych za PHP zasiadających na najwyższych stołkach? Skoro nie potrafią przedstawić żadnej konkretnej wizji rozwoju, powinni ustąpić miejsca osobom, które będą potrafiły to zrobić.

P.S. Listę wszystkich prezentacji znajdziecie pod adresem http://techportal.ibuildings.com/2011/05/31/dpc11-sessions-and-slides/.

Autor wpisu: batman, dodany: 13.06.2011 08:00, tagi: php

Programowanie w PHP najczęściej wiąże się z posiadaniem lokalnej kopii projektu. Pół biedy gdy nad projektem pracujemy sami. Wówczas lokalne środowisko można dopasować do środowiska produkcyjnego, dzięki czemu unikniemy konieczności utrzymywania kilku wersji kodu dla różnych środowisk (wbrew porom jest to częsta praktyka).

Z pomocą przychodzi nam projekt o nazwie Vagrant. Jest to narzędzie stworzone z myślą o tworzeniu wirtualnych środowisk dla deweloperów, bazujące na dobrze znanym i lubianym VirtualBoksie oraz języku Ruby (działa również na Windowsie).

Instalacja Vagranta wbrew pozorom jest banalna (nawet w przypadku systemu operacyjnego Windows). Na początek potrzebujemy dwóch rzeczy – VirtualBox oraz interpretera Ruby. VirtualBox pobierzemy pod adresem www.virtualbox.org, a interpreter języka Ruby – rubyinstaller.org/downloads. Po pobraniu i zainstalowaniu powyższych VirtualBoksa oraz Ruby, możemy przystąpić do instalacji Vagranta. W przypadku Windowsa konieczne może się okazać zainstalowanie DevKita również dostępnego pod adresem rubyinstaller.org/downloads.

Po zainstalowaniu wszystkich niezbędnych aplikacji możemy przejść do instalacji tej właściwej. W tym celu w wierszu poleceń wykonujemy:

gem install vagrant

Po instalacji Vagranta dodajemy nowy box (wirtualne środowisko) oraz je uruchamiamy:

vagrant box add base http://files.vagrantup.com/lucid32.box
vagrant init
vagrant up

Wykonanie pierwszego polecenia może zająć nieco czasu, ponieważ powoduje ono pobranie z sieci pliku o rozmiarze około 250MB. Kolejne polecenia wykonają się o wiele szybciej.

Na koniec wystarczy połączyć się po ssh do maszyny wirtualnej i korzystać z niej jak z każdego innego systemu, do którego łączymy się po ssh (na Windowsie będziemy potrzebować Putty).

Dokładny opis instalacji oraz łączenia się do maszyny wirtualnej znajdziecie na stronie projektu – vagrantup.com. Warto również obejrzeć film, prezentujący możliwości Vagranta.

Vagrant – Getting Started from Mitchell Hashimoto on Vimeo.

Czytaj dalej tutaj (rozwija treść wpisu)
Czytaj dalej na blogu autora...

Autor wpisu: Tomasz Kowalczyk, dodany: 12.06.2011 22:20, tagi: doctrine, framework, php, symfony, symfony2

Nie ukrywam, że symfony jest moim ulubionym frameworkiem, jeśli mówimy o tych napisanych w języku PHP. Fabien Potencier stworzył naprawdę dobre narzędzie wspomagające tworzenie stron i aplikacji internetowych. Od pewnego czasu możemy usłyszeć o nowym przedsięwzięciu SensioLabs - frameworku Symfony2. Sf2 to zupełnie nowe podejście do tworzenia aplikacji internetowych, dlatego warto zapoznać się z możliwościami [...]

Autor wpisu: Zyx, dodany: 12.06.2011 13:06, tagi: php

Dzisiaj wydałem kolejną wersję mojej kolekcji automatycznych ładowarek klas Open Power Autoloader. Obok dodania wsparcia dla mechanizmu cech z nadchodzącego PHP 5.4, głównym powodem jej pojawienia się była chęć udostępnienia przydatnego narzędzia do optymalizacji i analizy procesu ładowania klas. Jednym z głównych powodów stosowania automatycznego ładowania jest chęć wczytania tylko tych plików, z których faktycznie korzystamy. Zauważmy jednak, że w każdej aplikacji mamy pewien zbiór klas ładowanych zawsze. Chciałem znaleźć ich listę i wygenerować zestaw komend require, które wczytają je "ręcznie". Tak powstał CoreTracker.

Autor wpisu: Athlan, dodany: 12.06.2011 00:11, tagi: php

Praktyka cache‘owania danych jest powszechna wśród programistów aplikacji webowych ze względu na optymalizację dostępu do danych bezpośrednio ze źródła ich pochodzenia, a w szczególności:

  • trudność dostępu (np. wykonanie skomplikowanych połączeń),
  • ograniczenia dostępu (np. limit odpytywania),
  • długi czas oczekiwania na dane; powodów jest wiele.

O ile tematyką stworzenia samego mechanizmu cache zajęli się m.in. Nospor, możecie podejrzeć jak to wygląda w Zend_Cache, Symfony, czy Kohana; tak ja chciałbym zwrócić uwagę na jeszcze jedną rzecz.

Zazwyczaj schemat kodu wygląda mniej więcej tak:

< ?php
$oCache = new Cache(); // tworzony jest jakis obiekt cache
 
if($oCache->expired(3600) || !is_array($aData = $oCache->load())) // sprawdzamy, czy jest cache i nie wygasł
{
  $aData = $oModel->GetSomething(); // zbieramy dane z bazy danych
  $oCache->save($aData);
}
 
// $aData przechowuje nasze dane do użytku
?>

Symulacja, parę linijek kodu, a ile nieszczęść.

Wszystko działa pięknie, dopóki nie spotkamy się z sytuacją, gdy setki osób (procesów) jednocześnie zechcą zbierać takie dane z bazy danych. Przeprowadźmy zatem krótką dywagację. Załóżmy, że użytkownik #1 wchodzi na stronę, stwierdza, że nie ma cache, lub jest nieświeży, wówczas przechodzi do połączenia się z bazą danych i zaczyna zbierać dane. W tym samym czasie, zanim użytkownikowi #1 zostaną zwrócone dane wchodzi użytkownik #2, który stwierdza, że nie ma cache, bo użytkownik #1 jeszcze nie zebrał danych, postanawia połączyć się z bazą i zrobić to samo, co użytkownik #1, powtarzając niepotrzebnie czynność i dodatkowo obciążając bazę. Można by iść dalej i wprowadzić n użytkowników, którzy powtarzają czynność, dopóki dane nie pojawią się w cache i kolejni użytkownicy będą z niego korzystać. Co się stanie natomiast, gdy kolejka tak narośnie, że użytkownikowi #1 zabraknie zasobów systemowych, aby ukończyć proces zbierania danych, co spowoduje, że pozostałym też? Kolejka będzie wydłużała się w nieskończoność, póki system operacyjny nie podejmie żadnych działań (np. odłączy bazę danych, lub po prostu wyłączy serwer, np. w IIS7 wyłączy cały application pool). Aby doszło do tej kolizji nie jest potrzebne wcale natężenie użytkowników, serwer może akurat np. zajmować się wysyłką maili lub nieoptymalnie zrobionym procesem, który zajmuje zasoby, a w tym czasie wejdzie tylko pięciu użytkowników.

Parę linijek kodu, a ile nieszczęść.

Pojęcie semafora.

Semafor w informatyce – jest chronioną zmienną lub abstrakcyjnym typem danych, który stanowi klasyczną metodę kontroli dostępu przez wiele procesów do wspólnego zasobu w środowisku programowania równoległego.

Więcej na temat semaforów na Wikipedii, bądź w Podstawy informatyki / Stefan Węgrzyn. – Warszawa : Państwowe Wydawnictwo Naukowe, 1982.

Podejście do problemu.

< ?php
$oCache = new Cache();
 
if($oCache->expired(3600) || !is_array($aData = $oCache->load()))
{
  $oCache->savePrepare(); // stawiamy semafor
 
  $aData = $oModel->GetSomething();
  $oCache->save($aData); // metoda save() może (nie musi) od razu zwolnić semafor, gdy próba zapisu się zakończy
  // jeżeli metoda save() nie zwalnia zasobu, możemy np. użyć:
  // $oCache->saveFinalize();
}
 
// $aData przechowuje nasze dane do użytku
?>

Rozwiązaniem jest zastosowanie semafora blokującego dostęp do zasobu (w tym przypadku abstrakcyjnie “cache”, mniej abstrakcyjnie może być to plik na dysku, przestrzeń w pamięci operacyjnej, rekord w bazie danych, cokolwiek, co cache przerzymuje). Dla wartości semafora = 1 zasób jest wolny (nieużywany, jest 1 cache), gdy jest mniejszy/równy 0 zasób jest zajęty, ktoś z niego “korzysta”. Zajętość zasobu powinna być sprawdzana przy próbie odczytu. Dopóki zasób nie zostanie zwolniony, nie będzie można określić, czy są dane w cache. Jeżeli nie można określić, czy dane są w cache, należy zaczekać na zwolnienie zasobu.

Teraz nasze rozwiązanie nie dopuści do przytoczonej w powyższym przykładzie sytuacji. Zanim cache nie zostanie odblokowany po próbie zapisu, nie uzyskamy odczytu, czekając na niego i nie przechodząc w skrypcie nigdzie dalej.

Gdy save() się nie powiedzie? Można zastosować timeouty odczytu na load(). Wówczas złapalibyśmy wyjątek i przeszli dalej do realizacji zapisu, tak, jakby semafora nie było.

Czytaj dalej tutaj (rozwija treść wpisu)
Czytaj dalej na blogu autora...

Autor wpisu: singles, dodany: 11.06.2011 12:33, tagi: php, zend_framework

Kolejny wpis z serii Zend Framework Quick Tip

Podstawowym elementem sporej liczby aplikacji internetowych jest datagrid – tabela, której zawartość można filtrować, sortować, z pagerem. W ostatnio wykonywanej aplikacji natrafiliśmy na potrzebę wykorzystania tych samych datagridów w kilku miejsach.

Potrzeba

Do stworzenia gridów wykorzystaliśmy do tego celu bibliotekę ZFDataGrid (która wymagała kilkunastu poprawek, ale i tak nie znaleźliśmy niczego lepszego). Utworzyliśmy jedną bazową klasę Grid i po niej dziedziczyły wszystkie gridy zawarte w aplikacji, definiując własne źródła danych, filtry czy też akcje. Do pełni szczęścia brakowało, aby ładowane były na żądanie, wykorzystując domyślny Zendowy autoloader. Okazało się, że jest bardzo prosty sposób na osiągnięcie takiej funkcjonalności.

Implementacja

ZF domyślnie mapuje kilka rodzajów zasobów (resources) na ścieżkę w strukurze plików. Należą do nich:

Zend Framework Base Resources

Lista domyślnie zdefiniowanych ścieżek w ZF - na bazie " Getting Started with Zend Framework 1.11" Roba Allen'a

Nam brakowało jeszcze prefixu Grid, który mapowałby na ścieżkę grids. Szybkie spojrzenie do manuala i mamy rozwiązanie. Wszystko ogranicziło się do dodania następującego kodu do Bootstrap.php:

/**
 * Register 'Grid', so they could be created the same way like forms, models, etc.
 */
protected function _initGridsAutoload()
{
    $this->getResourceLoader()
         ->addResourceType('grid', 'grids', 'Grid');
 
    //or for many custom resources
    /*
    $this->getResourceLoader()->addResourceTypes(array(
        'item' => array(
            'path'      => 'items/',
            'namespace' => 'Item',
        ),
        'task' => array(
            'path'      => 'some/deep/folder/tasks',
            'namespace' => 'Task'
        )
    ));
    */
}

Pierwszy parametr to wewnętrzny klucz dla loadera, drugi to ścieżka, pod jaką mają być szukane pliki – zaczynając od `application/’, a trzeci to prefix jakiego będziemy używać w aplikacji. I tyle :) Od tego momenu w można wykorzystywać konstrukcję:

$grid = new Grid_Users(); // autoload files application/grids/User.php

Podany przykład dla applicationNamespace = ” – w przypadku kiedy wykorzystujecie namespace powiedzmy My, albo App, będzie to oczywście `App_Grid_Users_.

Autor wpisu: Tomasz Kowalczyk, dodany: 10.06.2011 22:38, tagi: symfony, framework, php

Prowadzenie blogu ma, a przynajmniej powinno mieć na celu niesienie pomocy Czytelnikom. Czasem jednak trzeba też pomóc sobie - autorowi. Najlepiej jest wtedy, kiedy przy okazji spełniania tego pierwszego wymagania, spełnia się przy okazji to drugie. Ze względu na to, że tworzenie wpisów pomaga mi w uporządkowaniu wielu informacji kołaczących się nieskładnie w głowie, czasem [...]
Wszystkie wpisy należą do ich twórców. PHP.pl nie ponosi odpowiedzialności za treść wpisów.