Injektování aktuálního presenteru do service
- Savannah
- Člen | 30
Ahoj,
zkouším, co se dá udělat s novým Nette (jedu 2.0 (revision 013c8ee released on 2012–02–03) ). Zajímá mě, jestli když mám např. takovouhle konfiguraci:
config.neon
common:
# ...
services:
# ...
auditlogService:
class: AuditlogService
a chtěl bych do služby auditlogService dostat aktuální presenter, tedy ten, který se zrovna vykonává. Může se jednat např. o to, že chci mít v této logovací službě vždy k dispozici httpRequest (loguji url, ip), můžu z toho brát aktuálního uživatele atd. Pochopitelně bych si to mohl nasetovat ručně někde při spuštění BasePresenteru, ale pokud mám takových služeb víc, tak to značně znepřehledňuje.
Lze tohle nějak rozumně udělat?
ŘEŠENÍ
AuditlogService.php
class AuditlogService extends NObject {
/**
* @var NPresenter
*/
private $presenter;
/**
* @param NApplication $application
*/
function __construct($application) {
$this->presenter = $application->getPresenter();
}
// ...
}
config.neon
common:
services:
auditlogService:
class: AuditlogService
arguments: [@application]
Editoval Savannah (9. 2. 2012 21:19)
- Savannah
- Člen | 30
No já toho právě chci obecně víc než jenom ten httpRequest. Chci
uživatele, můžu někdy chtít presenter abych měl metodu
$presenter->link
atd. Prostě by se mi hodil presenter jako
celek. Zkoušel jsem něco jako
services:
auditlogService:
class: AuditlogService
arguments: [@presenter] # popř. @currentPresenter
ale ty @presenter
/@currentPresenter
neexistují.
- mkoubik
- Člen | 728
Vždyť každy servis musí mít vztah ke context a skrz něho se dostanete na aktualni presenter ne?
Služba může být jakýkoliv objekt, tudíž nemůžeme předpokládat že
ví o nějakém contextu, natož presenteru.
>
Ale hlavně mi to přijde divny požadavek podle mne je něco spatne
Přesně tak, presenter by měl mít referenci na modely, ne obráceně. Skus promyslet, jestli by to nešlo zpracovat v presenteru a do modelu pak posílat jenom data.
- Savannah
- Člen | 30
mkoubik napsal(a):
Ale hlavně mi to přijde divny požadavek podle mne je něco spatne
Přesně tak, presenter by měl mít referenci na modely, ne obráceně. Skus promyslet, jestli by to nešlo zpracovat v presenteru a do modelu pak posílat jenom data.
Takhle to dělám, ale je zbytečně složité do každé metody posílat
jako první parametr $this
, případně ve startupu každého
presenteru projít všechny services, které potřebují referenci, a
nastavit ji.
David Grudl napsal(a):
Můžeš si předat
@application
a ten má metodu getPresenter().
To by mělo být to, co potřebuji! :) Dík, jen co dorazím domu, vyzkouším
- Savannah
- Člen | 30
mcmatak napsal(a):
Já teda vytvářím service vždy s prvním parametrem konstruktoru což je context
Jak to myslíš konkrétně? Parametry konstruktoru totiž musím dávat
přímo v config.neon
(servicy mi nevytváří presenter, ty jsou
do něj injectnuté). Což je to, čehož chci dosáhnout – přímo
v configu moct injectovat presenter (nebo context, nevím, jak je přesně
rozdíl/vztah).
Což by mohlo řešit to Davidovo @application
- Filip Procházka
- Moderator | 4668
@**Savannah**: @**mcmatak** to myslí tak, že všechny jeho služby dostávají celý DI Container, čímž ho degradoval na Service Locator :) Což není pěkné.
- Savannah
- Člen | 30
Tak jsem zkusil Davidovu radu a funguje báječně! :)
class AuditlogService extends NObject {
/**
* @param NApplication $application
*/
function __construct($application) {
$this->presenter = $application->getPresenter();
}
// ...
}
common:
services:
auditlogService:
class: AuditlogService
arguments: [@application]
Takhle dostanu do auditlogService aktuální presenter a mám tedy přístup ke všemu, co potřebuji (httprequest, user, parameters, …). Díky!