Modele w Zend Framework

Jakie są niektóre ze sposobów implementacji modeli w Zend Framework?

Widziałem podstawowe class User extends Zend_Db_Table_Abstract a potem wstawianie wywołań do tego w kontrolerach:

$foo = new User;

$foo->fetchAll()

Ale co z bardziej wyrafinowanymi zastosowaniami? Sekcja Quickstart w dokumentacji oferuje taki przykład, ale nadal czuję, że nie otrzymuję "najlepszego przykładu" dla modeli w Zend Framework. Wszelkie ciekawe realizacje tam?

EDIT: powinienem wyjaśnić (w odpowiedzi na komentarz CMS)... Wiem o bardziej skomplikowanych selekcjach. Interesowało mnie ogólne podejście do koncepcji modelu i konkretne przykłady tego, jak inni je zaimplementowali (zasadniczo rzeczy, które Instrukcja pomija i rzeczy, które Basic how-to ' s gloss over) {]}

Author: Charles, 2008-11-17

11 answers

Osobiście podklasuję zarówno Zend_Db_Table_Abstract jak i Zend_Db_Table_Row_Abstract. Główna różnica między moim kodem a Twoim polega na tym, że jawnie traktujemy podklasę Zend_Db_Table_Abstract jako "tabelę", a Zend_Db_Table_Row_Abstract jako"wiersz". Bardzo Rzadko widuję w kontrolerach bezpośrednie wywołania select objects, SQL lub wbudowanych metod bazodanowych ZF. Staram się ukryć logikę żądania konkretnych rekordów do wywołania za Zend_Db_Table_Abstract w ten sposób:

class Users extends Zend_Db_Table_Abstract {

    protected $_name = 'users';

    protected $_rowClass = 'User'; // <== THIS IS REALLY HELPFUL

    public function getById($id) {
        // RETURNS ONE INSTANCE OF 'User'
    }

    public function getActiveUsers() {
        // RETURNS MULTIPLE 'User' OBJECTS            
    }

}

class User extends Zend_Db_Table_Row_Abstract {

    public function setPassword() {
        // SET THE PASSWORD FOR A SINGLE ROW
    }

}

/* CONTROLLER */
public function setPasswordAction() {

    /* GET YOUR PARAMS */

    $users = new Users();

    $user = $users->getById($id);

    $user->setPassword($password);

    $user->save();
}

Istnieje wiele sposobów, aby podejść do tego. Nie myśl, że to jedyny, ale staram się podążać za założenia projektu ZF. (Oto więcej moich myśli i linków na ten temat.) To podejście robi się trochę ciężkie klasy, ale czuję, że utrzymuje Kontrolery koncentruje się na obsłudze wejścia i koordynacji z widokiem; pozostawiając model do wykonania konkretnej pracy aplikacji.

 23
Author: Barrett Conrad,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 11:48:36

Pracowałem dla Zend i wykonałem sporo pracy nad komponentem Zend_Db_Table.

Zend Framework nie daje zbyt wielu wskazówek na temat koncepcji "modelu" w odniesieniu do wzorca modelu domeny. Nie ma klasy bazowej dla modelu, ponieważ model zawiera pewną część logiki biznesowej specyficzną dla Twojej aplikacji. Napisałem blog na ten temat bardziej szczegółowo.

Trwałość w bazie danych powinna być wewnętrzną implementacją modelu. Na Model zazwyczaj używa jednej lub więcej tabel. Powszechnym, ale niewłaściwym projektem obiektowym jest rozważanie modelu jako rozszerzenia tabeli. Innymi słowy, powinniśmy powiedzieć Model ma-tabelę , a nie Model jest-tabelą.

To jest przykład IS-a:

class MyModel extends Zend_Db_Table_Abstract
{
} 

To jest przykład HAS-a:

class MyModel // extends nothing
{
    protected $some_table;
}

W modelu real domain, użyj $some_table w metodach MyModel.

Możesz również przeczytać podejście Martina Fowlera do modelu domeny design pattern, a jego opis anemicznego modelu domeny antypattern, czyli ilu programistów niestety podchodzi do programowania OO.
 61
Author: Bill Karwin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-01-06 07:52:36

Nigdy nie używaj Zend_Db_Table jako swojego modelu. To tylko wpędza cię w kłopoty. Albo piszesz własne klasy modeli, które używają Zend_Db_Table, aby rozmawiać z Twoją bazą danych, albo możesz przeczytać mój post na blogu tutaj , aby uzyskać hack, który pozwala Ci nieco połączyć klasę "Model" i Zend_Db_Table.

Najważniejsze jest to, że gdy używasz Zend_Db_Table bezpośrednio w kontrolerach, robisz te same rzeczy w wielu miejscach. Jeśli musisz coś zmienić logika, trzeba dokonać zmiany w wielu miejscach. Niedobrze. Mój pierwszy profesjonalny projekt został wykonany w ten sposób, ponieważ to ja byłem w firmie, która musiała nauczyć się korzystać z ZF i to jest totalny bałagan teraz.

Mam również tendencję do pisania funkcji pomocniczych w moich klasach dla zaawansowanych pobrań. Coś jak $table - > doNameFetchAll() lub $table - >doOrderFetchAll ().

 7
Author: smack0007,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2008-11-17 08:43:22

Poszperałem trochę o modelach dla ZF i natknąłem się na ciekawą serię artykułów autorstwa Matthew Weiera O ' Phinneya, które warto sprawdzić:

To nie jest "kod produkcyjny" i wiele pozostaje wyobraźni, ale to dobra lektura i bardzo mi pomogła.

 7
Author: ironkeith,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-01-26 21:40:16

Model nie ma nic wspólnego z bazą danych. Co zrobić, jeśli pobieram dane z kanału RSS lub usługi SOAP lub czytam pliki z FS?

Umieszczam wszystkie tego typu rzeczy w modelach. W takim przypadku moja klasa modelek może niczego nie rozszerzać . Mam zamiar napisać model, który używa metod innych modeli.

 5
Author: d-_-b,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-10-29 11:41:16

Pomiń ZF dla części modeli, są znacznie lepsze rozwiązania. "M" w " MVC " ZF jest prawie nieobecny. Czytając ich dokumenty, w ogóle nie wspominają o modelach - co jest dobrą rzeczą, oznacza to, że możesz użyć prawie wszystkiego, co chcesz, bez pisania dużo kodu adaptera.

Spójrz na Doctrine dla modeli zamiast. Szybko staje się de facto ORM dla PHP.

 3
Author: chroder,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2008-11-17 05:07:14

Możesz wykonywać bardziej skomplikowane zapytania, sprawdź sekcję Advanced usage w Zend_Db_Table strona podręcznika.

$select = $table->select();
$select->from($table,
              array('COUNT(reported_by) as `count`', 'reported_by'))
       ->where('bug_status = ?', 'NEW')
       ->group('reported_by');
 1
Author: Christian C. Salvadó,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2008-11-17 04:39:22

Możesz rozszerzyć klasę Zend_Db_Table_Abstract i dodać do niej kilka użytecznych metod. na przykład możesz dodać metodę changePassword() do swojej klasy użytkownika i manipulować jej danymi. możesz też zmienić domyślną metodę _ _ toString() swojej klasy, więc będziesz mieć dostosowaną metodę _ _ toString (), która, powiedzmy, zwraca całe dane kontaktowe użytkownika (imię i nazwisko, adres, numer telefonu) w dobrze sformatowanym łańcuchu znaków. w Twoim konstruktorze możesz uzupełnić swoje dane do właściwości Twojego obiekt. następnie użyj ich jak:

public function __toString() {
   $data = $this->_name . ', ' . $this->_adderss . ', call: ' . $this->_phone;
   return $data;
}

Twój model rozszerza Zend_Db_Table_Abstract tylko po to, aby ułatwić dostęp do jego danych, ale funkcjonalność, którą możesz mieć na tych danych zależy od twojej kreatywności i potrzeb. Polecam Ci książkę "php / architect' s guide to programming with Zend framework" autorstwa cala Evansa. książka jest bardzo pouczająca i łatwa do odczytania. rozdziały 4 i 6 będą przydatne w tej sprawie.

 1
Author: farzad,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2008-11-17 05:00:45

Jednostka bazy danych nie jest jedynym rodzajem komponentu modelu. W związku z tym nie ma sensu mówić o modelach (w liczbie mnogiej) - Twoja aplikacja ma Jeden model, który zawiera wiele komponentów. Niektóre z tych komponentów mogą być bramkami tabel (a więc rozszerzać się od Zend_Db), podczas gdy inne nie.

Polecam zapoznanie się z książkąDomain Driven Design autorstwa Erica Evansa, która doskonale wyjaśnia, jak skonstruować obiekt model.

 1
Author: troelskn,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2008-11-17 20:55:55

Używam Propel 1.3 zamiast Zend_Db_Table. To trudne do skonfigurowania, ale niesamowite. Może badać bazę danych i automatycznie generować wszystkie modele. W rzeczywistości generuje 2 poziomy i 2 typy modelu.

Przykłady dla tabeli 'user':

Poziom 1: BaseModel & BasePeer: są one nadpisywane za każdym razem, gdy regenerujesz swój ORM. tj. BaseUser.php & BaseUserPeer.php

Poziom 2: StubModel& StubPeer: te nie zostaną nadpisane. To te, które dostosowujesz. tj. użytkownika.php & UserPeer.php

Type 1: Model-dla podstawowych operacji CRUD, a nie zapytań tj. użytkownika.php Type 2: Peer -- For queries. Są to obiekty statyczne. czyli UserPeer.php

Tak aby utworzyć użytkownika:

$derek = new User();
$derek->setFirstName('Derek');
$derek->save();

Aby znaleźć wszystkie dereki:

$c = new Criteria();
$c->add(UserPeer::FIRST_NAME, 'Derek');
$dereks = UserPeer::doSelect($c);
 1
Author: lo_fye,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-01-30 14:52:16

Http://zfsite.andreinikolov.com/2008/08/zend_db_table-time-overhead-about-25-percents/

Bit z paragrafu 22, Zend_Table jest w zasadzie miły, ale generuje pewne ogólne koszty wydajności (bez buforowania)...

 1
Author: sunwukung,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-04-06 14:58:55