Jak nejlépe na PHP 5.3 a namespaces

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
Ondřej Mirtes
Člen | 1536
+
0
-

Ahoj,
s 5.3kou koketuju od prvního dne vydání stable verze. Těšil jsem se na namespaces, ale v praxi se ukázalo, že spíše přidělávají práci. Jsou už ale skutečně potřeba, i když je považuji za nutné zlo.

Práce s nimi má několik úskalí:

  • V souborech bez namespace (např. bootstrap) můžete psát např. Nette\Environment, ovšem jak má soubor nějakou namespace, musíte začít psát „cestu“ absolutně, tj. \Nette\Environment. Jinak se bude hledat v namespace např. Web\Nette\Environment (v případě presenteru uvnitř WebModule). Když to zjistíte po několikahodinovém přepisování projektu, je vám do pláče :o)
  • Některé exceptions v Nette jsou (z mně neznámého důvodu) bez namespace, je potřeba jejich vyvolávání/zachycování zapisovat s \ (např. \IOException).
  • Neustále je třeba řešit dilema, zda do kódu psát třídu s plnou cestou, nebo na začátek napsat use \namespace\třída a pak všude v kódu psát název tříd už klasicky.
  • Po přepsání projektu do PHP 5.3 se stejně dozvíte, že hosting s novou verzí nebude a tak jdete vše vracet na PHP 5.2 :o)

Podařilo se mi najít řešení (díky inspiraci v Nette zdrojácích), které práci s namespaces minimalizuje a to nutné zlo efektivně zmenšuje. Vzal jsem předposlední bod toho výčtu výše a řekl si, že to udělám po vzoru Javy – tam je dobrým zvykem uvádět na začátku souboru se třídou všechny importy (což je de facto use z PHP) a v kódu třídy se již neodvolávat na třídy přes např. java.sql.Statement. Vidíte tak, jaké všechny třídy daná třída využívá a pro zpětnou kompatibilitu s PHP 5.2 stačí řádky definující namespace a výčty použitých tříd ve všech souborech zakomentovat – zbytek kódu tříd se totiž nemění.

Co na to říkáte?

hrach
Člen | 1834
+
0
-

no mně to zní velmi dobře :)

LM
Člen | 206
+
0
-

LastHunter napsal(a):

  • Některé exceptions v Nette jsou (z mně neznámého důvodu) bez namespace, je potřeba jejich vyvolávání/zachycování zapisovat s \ (např. \IOException).

Některé výjimky používá třeba i Texy!, představ si situaci kdy v aplikaci používáš obě knihovny, Nette vyhazuje Nette\InvalidStateException a Texy jen InvalidStateException, přitom jsou totéž…

Ondřej Mirtes
Člen | 1536
+
0
-

LM napsal(a):

LastHunter napsal(a):

  • Některé exceptions v Nette jsou (z mně neznámého důvodu) bez namespace, je potřeba jejich vyvolávání/zachycování zapisovat s \ (např. \IOException).

Některé výjimky používá třeba i Texy!, představ si situaci kdy v aplikaci používáš obě knihovny, Nette vyhazuje Nette\InvalidStateException a Texy jen InvalidStateException, přitom jsou totéž…

Jasně no, chápu…

Jinak netvrdím, že jsem přišel na něco úžasného, on by k tomu po několika hodinách dospěl asi každý, ale chci tímhle threadem ušetřit práci těm, co se do 5.3 teprv pustí :)

Ještě jsem pozapomněl:

  • Při přechodu mezi 5.2/5.3 a takto upravenými zdrojáky vás čeká ještě přepisování callbacků, protože na ně se use klauzule nevztahují – např. array('\Classes\Helpers', 'timeHelper')array('Helpers', 'timeHelper').
  • Stejně tak nelze nijak elegantně ošetřit presentery v modulech (v PHP 5.3 je třeba použít namespace NázevModulu + běžný název presenteru – třeba DefaultPresenter, kdežto v 5.2 je třeba používat Web_DefaultPresenter). Komentáře uprostřed názvu třídy PHP snáší špatně. (pokoušel jsem se o /*Web_/**/DefaultPresenter apod., bezúspěšně)

Editoval LastHunter (22. 8. 2009 22:24)

kravčo
Člen | 721
+
0
-

LastHunter napsal(a):

  • Některé exceptions v Nette jsou (z mně neznámého důvodu) bez namespace, je potřeba jejich vyvolávání/zachycování zapisovat s \ (např. \IOException).

Výnimky, ktoré sú v namespace Nette sa týkajú len aplikačnej logiky Nette a sú mu vlastné. Ostatné majú zmysel i pri inom použití.

Ještě jsem pozapomněl:

  • Při přechodu mezi 5.2/5.3 a takto upravenými zdrojáky vás čeká ještě přepisování callbacků, protože na ně se use klauzule nevztahují – např. array('\Classes\Helpers', 'timeHelper')array('Helpers', 'timeHelper').

Toto Nette rieši pomocou dvojice funkcií podpory kompatibility fixCallback() a fixNamespace(), ktoré volá pred použitým callbacku/názvu triedy. Nette služby preto aj v PHP < 5.3 zapisujeme aj s namespacom: „Nette\Loaders\RobotLoader“ a pod.

  • Stejně tak nelze nijak elegantně ošetřit presentery v modulech (v PHP 5.3 je třeba použít namespace NázevModulu + běžný název presenteru – třeba DefaultPresenter, kdežto v 5.2 je třeba používat Web_DefaultPresenter). Komentáře uprostřed názvu třídy PHP snáší špatně. (pokoušel jsem se o /*Web_/**/DefaultPresenter apod., bezúspěšně)

Komentár je ekvivalentný whitespace, teda komentár vnútri názvu triedy má PHP rado približne tak, ako medzeru v názve triedy :)

Jan Tvrdík
Nette guru | 2595
+
0
-

Mě na PHP 5.3 nejvíce chybí současná neexistence kvalitního IDE.

Honza Marek
Člen | 1664
+
0
-

Kdo si počká, ten se dočká. Já si počkám na NetBeans 6.8 a PHP 5.3.1…

DocX
Člen | 154
+
0
-

Mě u namespaces v PHP 5.3 docela překvapilo, že se musí do use psát přímo až konkrétní třídy.

Ze začátku jsem docela dlouho hledal v čem je chyba, když jsem na začátek souboru napsal use Nette a stále mi to hlásilo, že třídu Debug nemůže najít. Pak jsem si pořádně přečetl manuál PHP a zjistil, že prostě neumí hledat třídy v „importovaných“ jmenných prostorech :( Přitom ve „velkých“ jazycích (C#, C++, JAVA), ve kterých jsem dělal, to tak všude funguje…

PS: Já jsem teď celkem spokojen s Eclipse + PDT 2.1, ale slintám po KDevelop 4ce (jde jim to akorát dost pomalu :() :)

Editoval DocX (23. 8. 2009 14:43)

Patrik Votoček
Člen | 2221
+
0
-

Jan Tvrdík napsal(a):

Mě na PHP 5.3 nejvíce chybí současná neexistence kvalitního IDE.

A co zend studio 7.0?

v6ak
Člen | 206
+
0
-

Tak tomu nefunkčnímu uses \Namespace\Trida v souboru s namespace nerozumím, funguje mi to. Ale zatím jsem to zkoušel jen z konzole (php.exe i php-cgi.exe).

Proč nejde use Nette; podobně jako Javové import com.nettephp.*? To je celkem jednoduchý:

  1. Java řeší importy při kompilaci. V tuto chvíli má (musí mít) k dispozici všechny potřebné třídy a má podle čeho řešit celý název třídy. V class souborech již importy nejsou poznat, tam je všechno fully qualified. PHP ty to muselo řešit za běhu a s tou koncepcí autoloaderů apod. to nemá jak zjistit – autoloader to musí dostat již fully qualified.
  2. import neco.*; Nezpůsobí jednoznačné určení třídy v kódu a deprecoval bych to. V Javě by to ještě šlo (binárně by to bylo kompatibilní, protože v class souborech jsou názvy fully qualified), ale představte si ten nečekaný mazec v PHP:
    • Máme dvě namespaces: Foo a Goo.
    • V namespace Foo je třída Bar.
    • V jiné třídě (třeba Pug) bude use Foo; use Goo; a tato třída bude používat třídu Foo\Bar.
    • Poté, co již máme třídu Pug odladěnou přidáme třídu Goo\Bar. Tímto se staneodkaz na třídu Bar ve třídě Pug nejednoznačným. Zatímco v Javě jsou takové problémy pouze na úrovni kódu a distribuované class soubory těmito neduhy netrpí, v PHP je potřeba distribuovat celý zdroják, který je tímto problémem postižen.

Jinak Eclipse dělá ty importy v PHP (teda use) poněkud divně, to je pravda.

hurvajs
Člen | 86
+
0
-

Jan Tvrdík napsal(a):

Mě na PHP 5.3 nejvíce chybí současná neexistence kvalitního IDE.

Neexistence? No nevim, osobne jsem to jeste nezkousel, jedu zatim na PHP 5.2, ale Zend Studio, ve kterem programuji, tak ma nativni podporu PHP 5.3. Viz http://www.zend.com/…io-whats-new.

hurvajs
Člen | 86
+
0
-

Honza Marek napsal(a):

Kdo si počká, ten se dočká. Já si počkám na NetBeans 6.8 a PHP 5.3.1…

:) Tak treba ja jsem ted 6.8 zkousel a musim rici, ze je to dost strasne. Nemohl bych v tom pracovat. Osobne si myslim, ze Zend Studio se proste nic nevyrovna. Sice se plati, ale take je to znat. Kdyz se k tomu da Zend Platform (Zend Server / Zend Server CE), tak se moznosti posunou jeste dal. Ale nechci nikomu nic vnucovat – ciste osobni nazor ziskany behem 5 let denniho uzivani Zend Studia… :-D

romansklenar
Člen | 655
+
0
-

Zend Studio má jednu velkou nevýhodu, a to že pro každé PC na kterém ho chci používat, musím zakoupit licenci… což při ceně 2 x $399 dělá docela závratnou sumu :) freelancer tedy raději sáhne po alternativě. Btw není to tak dávno co jsem PDT kvůli rychlosti a stabilitě opustil a migroval na NB, ale to může být subjektivní, ale nedělalo mi žádný problém si převyknout, je to v podstatě to samé.

hurvajs
Člen | 86
+
0
-

Nechci se s Tebou Romane hadat, ale mam plne 64bit Gentoo, pouzivam Zend Studio 7.1 beta a nemam zadne problemy ani s rychlosti, ani se stabilitou. Pouzivam Zend Studio hodne dlohou dobu a nikdy jsem nepocitoval Tebou zminovane problemy. Ja osobne mam dve licence (desktop + ntb), 3-lety support (platil jsem cca $1.500 + VAT) a nijak me to nezatizilo. Je mi jasne, ze pro nejakeho „freelancera“ muze byt $400 hodne, ale to si na druhou stranu neceni sve prace. Musi se umet neco objetovat, aby se neco ziskalo. Nehlede na to, ze „freelancer“ si to muze dat do nakladu. Zkousel jsem strasnou spoustu IDE (PHPEdit, NetBeans apod.), dva roky programoval ve VIMu, ale proste Zend Studio nema konkurenci a ostatni IDE mu nesahaji ani po kotniky. Je sice placene, zase ne tak moc, ma support, pravidelny update, plno vymozenosti a pluginu, ktere jinde nejsou.

crempa
Člen | 198
+
0
-

Do doby, nez preslo Zend Studio na Eclipse tak to bylo asi top IDE. Priserna tezkopadnost „frameworku na IDE“ Eclipse me vsak neustale odrazuje od jeho pouzivani. :-(
Ale kazdemu vyhovuje neco jineho, momentalne funguju na NB 6.8 a maximalni spokojenost.

redhead
Člen | 1313
+
0
-

Dělal jsem na brigádě Javu v Eclipsu, a taky musím říct, že na mě nepůsobil dobře. Když jsem se dostal k Nette (a dělal stále v PSPadu) začal jsem hledat něco lepšího, a zatím NetBeans vedou.

Ondřej Mirtes
Člen | 1536
+
0
-

NetBeans mi kdysi na PHP opravdu nevyhovovaly, ale v poslední době udělaly hodně kroků kupředu a plynulost celého GUI se zlepšila, takže je používám a jsou hodně dobré :)

Oblíbené klávesové zkratky: Ctrl+R (pro refaktoring názvů), Alt+Shift+F (přeformátování zdrojáku podle pravidel) :)

BigCharlie
Člen | 283
+
0
-

Oblíbené klávesové zkratky: Ctrl+R (pro refaktoring názvů), Alt+Shift+F (přeformátování zdrojáku podle pravidel) :)

Mimochodem, jak vypadá v Netbeans po zformátování tenhle kód:

	$form = new Form();
	$form->addText("a", "b")
		->addRule(cosi...);

Zend Studio jsem nedokázal přinutit k tomu, aby tohle nechal bez povšimnutí a nesrovnal mi to do jedné řádky, což nepotěší (obzvlášť při používání dibi fluent). Neporadil si s tím někdo v ZS?

Jsme už ale trochu OT…

Editoval BigCharlie (12. 12. 2009 19:31)

none_
Člen | 16
+
0
-

Pokud jsi to ještě nezjistil, tak to vypadá úplně přesně tak, jak jsi to napsal. Tedy pokud to budeš mít na jednom řádku, tak to tak nechá, ale pokud to máš původně takhle, tak to maximálně srovná počet Tab.

Patrik Votoček
Člen | 2221
+
0
-

Jak řešíte WTF haluz… dibi\dibi::… Nette\Extras\DataGrid\DataGrid::.. ? Na mysli mam zdvojeni…

LM
Člen | 206
+
0
-

Není zbytečný používat pro každou komponentu zvlášť namespace? viz .NET frameworku:

System.Web.UI.WebControls.DataGrid
System.Web.UI.WebControls.DataGridColumn

V PEARu nebo Zendu by to asi bylo:

System.Web.UI.WebControls.DataGrid
System.Web.UI.WebControls.DataGrid.Column

A dibi třída je spíš jen jmenný prostor pro funkce…

Majkl578
Moderator | 1364
+
0
-

LM napsal(a):

A dibi třída je spíš jen jmenný prostor pro funkce…

No, řekl bych, že to není až tak úplně pravda. Třída dibi je spíš takové „skladiště“ všech připojení k databázi a umožňuje jednodušší přístup k databázi. Ale ano, pokud někdo používá jen jedno připojení, tak je to spíš takové namespace.

Teď k tomu na co se ptal vrtak-cz. Jde o to, že dibi nemá v php 5.3 vlastní jmenný prostor. Říkali jsme si , že by nebylo špatné to udělat. Narazili jsme ale na tohle WTF. Kdyby se metody z třídy dibi přesunuly pod namespace, tak by to byly obyčejné funkce a bylo by to zas jiné WTF…

Takže asi jako nejschůdnější řešení mi připadá dibi\dibi… Sice to není moc pěkné, ale zachová to stejnou funkčnost.

Ondřej Mirtes
Člen | 1536
+
0
-

Já jsem přepisování dibi na \dibi na milionu místech vyřešil tím, že to mám jen párkrát v BaseModelu a v jeho potomcích se odkazuji na $this->db, což je instance DibiConnection.

Honza Marek
Člen | 1664
+
0
-

Přemalováváte dibi, aby se třídy místo DibiConnection jmenovaly Dibi\Connection? K čemu je to dobré?

Patrik Votoček
Člen | 2221
+
0
-

Honza Marek napsal(a):

Přemalováváte dibi, aby se třídy místo DibiConnection jmenovaly Dibi\Connection? K čemu je to dobré?

Vypadá to cool…? :-)

Majkl578
Moderator | 1364
+
0
-

Náhodou jsem se k tomuto tématu znovu dostal a přečetl si první příspěvek. Musím nesouhlasit s prvním bodem. Nemusí se psát absolutně. Ukážu na příkladu.

To, co řekl Ondra, by fungovalo takto:

namespace Foo;
Nette\Environment::dump(1);//chyba, Foo\Nette\Environment neexistuje
\Nette\Environment::dump(1);//funkční

Existuje ale i hezčí řešení (už jsem to vysvětloval X lidem):

namespace Foo;
use Nette;
Nette\Environment::dump(1);//funkční
\Nette\Environment::dump(1);//také funkční, ale naprosto zbytečné a ošklivé

Rozhodně neplatí, že z namespace se musí vždy volat s \ na začátku. Možná bych mohl napsat nějaké Best Practice, hrozně často se totiž setkávám s mystyfikujícími názory a WTF použitím.

Editoval Majkl578 (6. 4. 2010 0:11)

wdolek
Člen | 331
+
0
-

Majkl578, cele PHP se zda byt pod WTF faktorem… dnes jsem se jmennymi prostory take narazil. vse sem si naprgal, v domeni, ze to bude fungovat tak, jako to funguje v jinych jazycich. (jenze tomu tak v PHP nebyva, ja na to zapomel a jak sem dopadl)

<?php
namespace A\B\C;
class MyClass { }

namespace X\Y\Z;
use A\B\C;

new MyClass(); // EPIC FAIL...

new \A\B\C\MyClass(); // pouzivam plnou cestu
new C\MyClass(); // pro "uziti" jmenneho prostoru C a vsech trid z nej, stejne ke kazde tride z nej musim napsat, co je to zac
?>

pri kazdem takovemto objevu, nad kterym stravim par hodin casu (dokumentace je skromna, o nicem takovem nehovori – a samozrejme to, ze to tam neni neberu jako ze takova vec neexistuje – koukneme se treba na nezdokumentovane tridy iteratoru v PHP), vzdy premyslim, proc sakra nedelam v Jave!

je tu nejaky blici smajlik?

v6ak
Člen | 206
+
0
-

No, je to lehce OT, ale J2EE podle mých zkušeností (hosting GAE) není až tak super, jak jsem po J2SE a J2ME očekával. Aspoň zpočátku, ještě jsem na ni nezanevřel, ale není to až tak jednoduché. Ale jmenné prostory tím problémem zrovna nebyly.

Majkl578
Moderator | 1364
+
0
-

wdolek napsal(a):

Majkl578, cele PHP se zda byt pod WTF faktorem…

To nepopírám, jen jsem uváděl na pravou míru to, jak to funguje (a s čím jsem se smířil).

pri kazdem takovemto objevu, nad kterym stravim par hodin casu (dokumentace je skromna, o nicem takovem nehovori – a samozrejme to, ze to tam neni neberu jako ze takova vec neexistuje – koukneme se treba na nezdokumentovane tridy iteratoru v PHP), vzdy premyslim, proc sakra nedelam v Jave!

Soucítím s tebou.
Většina věcí v SPL je špatně zdokumentovaná. Naštěstí výjimky dokumentovat nepotřebují (z názvu je jasné k čemu je). Co jsem nikdy nepoužil jsou datové struktury a nějaké iterátory.
Něco víc se dá vyčíst zde.

Editoval Majkl578 (6. 4. 2010 19:49)

romansklenar
Člen | 655
+
0
-

Majkl578 napsal(a):

Rozhodně neplatí, že z namespace se musí vždy volat s \ na začátku. Možná bych mohl napsat nějaké Best Practice, hrozně často se totiž setkávám s mystyfikujícími názory a WTF použitím.

namespace Foo;
use Nette;

class Bar {
	function __construct() {
		try {
			...
		} catch(\Exception $e) { // <-- jde se nějak zbavit úvodního lomítka?
			...
		}
	}
}
Majkl578
Moderator | 1364
+
0
-

romansklenar napsal(a):

Jde, dát Exception do use.

namespace Foo;
use Nette, Exception;

class Bar {
        function __construct() {
                try {
                        ...
                } catch(Exception $e) {
                        ...
                }
        }
}

Bohužel to může ve výsledku vést k hromadě tříd / jmenných prostorů v use.

Editoval Majkl578 (7. 4. 2010 1:18)

despiq
Člen | 320
+
0
-

kdyz to tu resite
napsat

namespace Admin;
use Nette;

a pak pouzit v kodu
Nette\Environment;

tak to mi prijde ujety, to si tam radsi necham lomitko na zacatku a nebudu pak resit jestli sem na zacatku zapomnel nebo nezapomnel napsat use Nette a aspon to bude vsude stejne, osobne me dost trapi ze po use Nette se znova musi psat cesta k presny tride kterou chci vcetne toho namespacu Nette kterej sem uz uvedl

na druhou stranu napsat
use A;
use B;

a volat tridu Ahoj ktera je v obou jmennych prostorech tak to by asi taky nefungovalo,
ale mohlo by to hodit exception ze jich je tam vic at si vyberu, nevi nekdo proc to tak neni?

jak jmenne prostory funguji v jinych jazycich? Ptal sem se na Javu ale tam to je nakonec v podstate stejne ne?

Patrik Votoček
Člen | 2221
+
0
-

Kdysi někdo prohlásil že jsem namespace úchyl. A asi na tom bude něco pravdy. Po cca půl roce co dělám PHP výhradně pro 5.3 s namespace a vším okolo. Jsem dospěl k názoru že nejlépe se namespace používají asi takto:

  1. pokud potřebujete třídu která je v jiné namespace pouze jednou použíjte \
  2. pokud potřebujete třídu která je v jiné namespace více než jednou použíjte use
  3. pokud potřebujete exception použíjte vždy \ (doopravdy je to přehlednější)

Pak je tu pár věcí které jsem si pořád pořádně nesrovnal v hlavě.

  1. jak používat namespace hezky
    1. App\Modules\Foo\Models\Foo
    2. App\FooModule\FooModel
  2. jak zapisovat namespace
    1. namespace App; class Foo {}
    2. namespace App { class Foo {} }

Co se týká toho jak namespace zapisovat někde jsem čelt že varianta b je preferovaná kvuli budoucímu PHP 5.4/6/7 ale už se mě nedaří najít kde to bylo.

Každopádně mohu říct že pokud PHP tak 5.3 s namespace a Nette jinak to nemá smysl.

Editoval vrtak-cz (7. 4. 2010 9:50)

Majkl578
Moderator | 1364
+
0
-

despiq napsal(a):

kdyz to tu resite
napsat

namespace Admin;
use Nette;

a pak pouzit v kodu
Nette\Environment;

tak to mi prijde ujety, to si tam radsi necham lomitko na zacatku a nebudu pak resit jestli sem na zacatku zapomnel nebo nezapomnel napsat use Nette a aspon to bude vsude stejne, osobne me dost trapi ze po use Nette se znova musi psat cesta k presny tride kterou chci vcetne toho namespacu Nette kterej sem uz uvedl

Nesouhlasím, to je naprosto v pořádku (bavíme se o PHP, ne o C++ apod.).
Ty úvodní lomítka kód leda tak znepřehledňují než aby pomáhaly.

na druhou stranu napsat
use A;
use B;

a volat tridu Ahoj ktera je v obou jmennych prostorech tak to by asi taky nefungovalo,
ale mohlo by to hodit exception ze jich je tam vic at si vyberu, nevi nekdo proc to tak neni?

Z tohoto důvodu to zřejmě funguje tak, jak to funguje. :) Je to podobný problém jako řeší RobotLoader když najde ve dvou souborech třídu se stejným názvem. :)


vrtak-cz napsal(a):
Kdysi někdo prohlásil že jsem namespace úchyl. A asi na tom bude něco pravdy. Po cca půl roce co dělám PHP výhradně pro 5.3 s namespace a vším okolo. Jsem dospěl k názoru že nejlépe se namespace používají asi takto:

  1. pokud potřebujete třídu která je v jiné namespace pouze jednou použíjte \
  2. pokud potřebujete třídu která je v jiné namespace více než jednou použíjte use
  3. pokud potřebujete exception použíjte vždy \ (doopravdy je to přehlednější)

I ze mě se stává namespace úchyl. :) S tímhle vesměs souhlasím, až na 3. (\Nette\Application\AbortException je pro mě opravdu nepřijatelné.)

Pak je tu pár věcí které jsem si pořád pořádně nesrovnal v hlavě.

  1. jak používat namespace hezky
    1. App\Module\Foo\Models\Foo
    2. App\FooModule\FooModel

Tohle dilema řeším taky, posledně jsem použil a) a v aplikaci používal use Foo\Bar\Models a new Models\Baz.

  1. jak zapisovat namespace
    1. namespace App; class Foo {}
    2. namespace App { class Foo {} }

Monžost b) slouží zejména ke skládání souboru z více jmenných prostorů. Jde to i způsobem a), ale to se nedoporučuje, proto b). Já volím metodu „co třída, to soubor“, tedy pro namespace se jedná o a).

Každopádně mohu říct že pokud PHP tak 5.3 s namespace a Nette jinak to nemá smysl.

Nelze než souhlasit. Když se ještě přidá Closure (silný pomocník), tak nemůžu o nějakém 5.2 ani slyšet. :)

Editoval Majkl578 (7. 4. 2010 10:08)

Patrik Votoček
Člen | 2221
+
0
-

Majkl578 napsal(a):

S tímhle vesměs souhlasím, až na 3. (\Nette\Application\AbortException je pro mě opravdu nepřijatelné.)

Tohle je asi to nejdůležitější zjištění kterého jsem u namespace nabyl. Proč to řeším tak jak jsem napsal? Jednoduše proto protože mě to k tomu dovedlo. Několikrát se mě stalo že jsem zapoměl nějáké to use uvést. A pořád mě připadá jako menší zlo uvést kompletní namespace než zkrachovat na chybně vyhozené vyjímce (resp. nevyhozené).

Editoval vrtak-cz (7. 4. 2010 10:20)

Majkl578
Moderator | 1364
+
0
-

vrtak-cz napsal(a):

Vyhození neexistující výjimky skončí fatal errorem. Kompletní namespace s úvodním \ akorát znepřehledňuje kód.
Otázkou spíš je, proč zapomínáš use, zapomínáš takhle i napsat názvy tříd? :)

Tudíž 20× zapsané throw new \Nette\Application\AbortException(); místo throw new AbortException(); s use je pro tebe praktičtější, zajímavé.

despiq
Člen | 320
+
0
-

to lomitko indikuje vylet do jineho prostoru, tak moc nerozumim tomu co je na tom neprehledne

<?php
throw new \Nette\Application\AbortException();
?>
<?php
throw new Nette\Application\AbortException();
?>

kde je ten velky rozdil?

Majkl578
Moderator | 1364
+
0
-

despiq: Dost možná je to otázka vkusu a osobního názoru, mně se tam to úvodní lomítko prostě nelíbí (už ten separátor sám o sobě je dost hrozný, ale byly ve hre i hořší varianty jako :) nebo ^^).

Editoval Majkl578 (7. 4. 2010 10:59)

Patrik Votoček
Člen | 2221
+
0
-

Majkl578 napsal(a):

vrtak-cz napsal(a):

Vyhození neexistující výjimky skončí fatal errorem. Kompletní namespace s úvodním \ akorát znepřehledňuje kód.

Znepřehledňuje? Na to jsi přišel jak? Ba naopak hned víš kde se třída hledá.

Otázkou spíš je, proč zapomínáš use, zapomínáš takhle i napsat názvy tříd? :)

Připadá mě trochu že srovnáváš nesrovnatelné…

Tudíž 20× zapsané throw new \Nette\Application\AbortException(); místo throw new AbortException(); s use je pro tebe praktičtější, zajímavé.

Zhlediska přehlednosti a spolehlivosti kódu ano.

v6ak
Člen | 206
+
0
-

Na jmenné prostory (ať už se jmenují jak chtějí) se mi dosti líbí konvence z Javy a možnosti IDE Eclipse. Tedy:

  • co použitá třída, to use (i při jednou použité třídě)
  • jedna třída na soubor ⇒ namespace foo{…} je zbytečně nepřehledné
  • při výběru neexistující třídy pomocí ctrl+space se mi doplní import (use)

Hierarchie namespaces asi není špatná, i když pro Javaře trošku nezvyklá. V zásadě bych se jí nebránil.

Tyto konvence v PHP používat jdou, ale IDE chovající se jako Eclipse u Javy jsem asi nenašel.

LiborM
Člen | 15
+
0
-

Zdravím,

tak jsem si začal zkoušet PHP 5.3 s namespace a mám takovou kosmetickou otázku.

Je lepší používat :

<?php
use Nette\Debug;
....
Debug::enable();
?>

nebo raději :

<?php
use Nette;
....
Nette\Debug::enable();
?>

Dík za jakoukoliv radu

LiborM

Editoval LiborM (21. 4. 2010 9:16)

Majkl578
Moderator | 1364
+
0
-

LiborM napsal(a):

Osobně mám raději tu druhou možnost, pokud nejde o hodně výskytů. Pokud jich hodně je, použiji use. Někdo ale u použití té druhé verze může namítat, že je to delší. Obě verze jsou funkčně totožné (pominu-li případ kolizí názvů).

v6ak
Člen | 206
+
0
-

Dobré IDE by mohlo psaní té první varianty zjednodušit, navíc se asi bude lépe udržovat.

danik
Člen | 56
+
0
-

:o) tak ja napriklad s Namespaces zatim delal jen jednou, takze mluvim spis jako teoretik a ideolog :o) ale myslim si, ze moje oko modrave v cele diskuzi nenarazilo na prenadhernou schopnost PHP – use ... as ... – neboli namespace aliasing. Predstavme si, ze chceme v nasem kodu na dvaceti mistech zachytavat \Nette\Application\AbortException. Nekdo si na to nenapise nic a bude vzdycky psat ...} catch (\Nette\Application\AbortException $e) {..., nekdo si na to napise use \Nette a bude psat ...} catch (Nette\Application\AbortException $e) {...; dalsi moznost je use \Nette\Application a v kodu mit ...} catch (Application\AbortException $e) {... (coz mi pripada semanticky priserne, co kdyz pouzivam vic frameworku a mam tudiz vic ruznych namespacu ktere se jmenujou Application?) a nekdo si ‚jusne‘ primo danou vyjimku a pise jen jeji nazev. Ja bych si treba udelal neco jako use \Nette\Application as NApp a psal bych ...} catch (NApp\AbortException $e) {....

Tohle konkretne ma smysl napriklad kdyz budu mit deset ruznych vyjimek v jednom konkretnim namespace a v jednom ze skriptu se budu met potykat s vice nez jednou z nich; pokud ale v jednom skriptu pracuji jen s jednou vyjimkou z daneho namespace, rad si napisu jeji plnou cestu, protoze mne osobne to prijde prehlednejsi.

Cele je to ale predevsim vec vkusu, protoze funkcne je to pro vsechny prakticke ucely totozne.

Moje vlastni teoreticka pravidla pro pouzivani Namespaces by tedy vypadala zhruba podobne, jako Vrtakova. Rozlisuji tridy a vyjimky – pro tridy bych postupoval takto:

  1. Danou tridu v souboru pouzivam jen na nekolika (dejme tomu max trech) mistech a z jejiho namespace uz jinou tridu nepouzivam ⇒ pisu v kodu absolutni cesty k tride
  2. Danou tridu v souboru pouzivam vicekrat a/nebo z jejiho namespace pouzivam jen nekolik dalsich trid ⇒ pisu use absolutne az ke tride/tridam a v kodu primo nazev tridy bez NS
  3. Danou tridu a dalsi tridy z jejiho namespace pouzivam hojne ⇒ pisu use k namespace, v nemz se tridy vyskytuji; pokud to dava semanticky vetsi smysl, namespace pomoci aliasingu pro tento skript prejmenuji. V kodu pouzivam posledni segment namespace nebo alias pred nazvem tridy.

S vyjimkami potom pracuji takto:

  1. Z daneho namespace pouzivam pouze jednu vyjimku; pokud ji pouzivam na „vice nez malo“ mistech, „jusuji“ primo vyjimku, pokud pouze nekolikrat, pisu absolutni cestu
  2. Pouzivam vic vyjimek z daneho namespace ⇒ pisu use … as … a alias si nejak standardizuji – napriklad dejme tomu use \Library\Gallery\Exceptions as E a ve zbytku kodu pouzivam E\PhotoMissingException a podobne. Pokud si clovek toto ‚E‘ standardizuje a pouziva jej konzistentne vsude kde importuje vyjimky, jeho WTF faktor klesa – protoze tim ze to vidime porad si za chvilku zvykneme to nevnimat