Už je to zase příšerně dlouho co jsem si našel chvíli a navíc jsem měl chuť něco sepsat a protože se mi nahromadilo pár zajímavých čtení o Tapestry, pak je logické, že můj první příspěvek po takové době patří právě Tapetry. Navíc je to pár hodin, co vyšlo Tapestry 5.0.15, které mělo být prvním release candidatem. Bohužel se tak nestalo, kvůli chybičkám objeveným v pozdní stádiu releasu (blíže).
První článek, který vám chci naservírovat, je zajímavý, protože se mu podařilo velmi přehlednou formou shrnout proč je Tapestry zajímavé. Why you should consider Tapestry 5. Bohužel je už malinko starší. Ze stejného blogu pochází i porovnání s Wicket: A glimpse of Wicket 1.4 and Tapestry 5.
Tapestry se vždy hlásilo k následujícím pravidlům: rychlost a škálovatelnost vytvořených aplikací, pohodlný vývoj aplikace bez potřeby speciální podpory v IDE a vysoká produktivita vývojáře. A o produktivitě je Boost Your Productivity Using Apache Tapestry.
Specialitou Tapestry již od verze 4 je vlastní IoC framework. Ve verzi 4 se jednalo o HiveMind, ve verzi 5 jde prostě o Tapestry IoC. Proč má Tapestry vlastní IoC framework, co umí je možné se dočíst ve dvou článcích napsaných přímou autorem Howardem L. Shipem: Tapestry 5 IoC: Binding and Building Services a Tapestry 5 IoC: Introducing Service Configurations.
V neposlední řadě: pozitivní krok je i vznik AppFuse pro Tapestry 5.
22. září 2008
Tapestry - jak dělat webové aplikace konfortně
napsal
Jira
v
21:42
5
komentářů
21. července 2008
Konečně build systém na úrovni - Gradle
Již hodně dlouho se na mě ze všech stran valí, že Ant je překonaný a že bychom měli používat Maven. Jistě Maven přináší spoustu zajímavých myšlenek, především zavedl jednoutnou strukturu projektů a správu závislostí. Ovšem přinesl i spoustu problémů, jako pevně daný build cycle či buildování multi-projektu.
Na trhu open source projektů se objevuje nový hráč, který si řadu těchto nešvarů bere za své a snaží se je napravit. A o jakém projektu, že píši? O projektu Gradle. Gradle je teprve ve verzi 0.2, ale vyvíjí se mílovými kroky.
A co je to převratné, co mě zaujalo. Build skripty se píší v jazyce Groovy. Má to řadu výhod, skript je programován, je možné používat (zavolat) jakýkoliv kód (díky Groovy, jakýkoliv Javovský kód). Navíc je možné opakující se části volat jako funkce (které se dají vytvářet přímo v build scriptu). Bezvadná integrace s Antem. Kolik z nás má v Antu poměrně složité skripty na generování kde čeho. Jejich převod pod Maven je hotovým peklem. Dále build multi-projektu v maven jde pouze z kořenového projektu, díky čemuž se buildu celý multi-projekt. V Gradle je možné multi-projekt build spustit z libovolného projektu a tím se buildují jenom ty podprojekty, které jsou potřeba.
Konvence ohledně build cycle jsou v Gradle definovány pomocí pluginů. Tj. pokud použiji plugin java
, pak je nadefinován konkrétní build cycle. Tento může být dle potřeby modifikován, buď jiným pluginem (např. plugin groovy
) či samotným build skriptem. To znamená konec dvojí pouštění testů, aby mohl vzniknout Cobertura code coverage.
A co zatím chybí. Je toho stále dost, není nativní podpora pro TestNG, Coberturu. Neexistují integrace s IDE.
Zatím jsem lákání Mavenu odolal a doufám, že Gradle dospěje a pomůže mi vyřešit problémy, které s Antem máme. Hrozně nerad bych naše skripty převáděl a ladil v Mavenu.
napsal
Jira
v
20:06
9
komentářů
9. června 2008
On se ještě používá jUnit? Vždyť máme TestNG.
Konečně jsem si poslechl záznam přednášky Jana Novotného Automatické testování v praxi. Jen více takových ...
Ale proč píšu tento příspěvek? Stále mě překvapuje jak velké množství lidí neustále používá jUnit, který mi přijde v porovnání s TestNG jak chudý příbuzný. Proto jsem se rozhodl nastínit 2 hlavní výhody TestNG, alespoň z mého pohledu.
Přecházel jsem na TestNG v době, kdy po jUnit4 nebylo ani vidu ani slechu, takže jsem měl rozhodování o hodně jednodušší. Ale i po uvolnění jUnit4 je TestNG lepší. Ovšem jako jUnit4 vyžaduje Javu 1.5, takže pro vás co běžíte na Javě 1.4 a méně, pak máte smůlu (ovšem testy můžete překládat jinou verzí Javy než produkční kód).
Na úvod porovnání uvedu: jako vývojové nástroje používám Eclipse, builduji Antem nebo Mavenem a necítím se být nijak limitován užíváním TestNG oproti jUnitu.
Nyní k výhodám. Hlavní skutečnost, která mě hnala za změnou jUnitu za něco jiného je skutečnost, kterou se sice podařilo vyřešit, ale neskutečmě se mi nelíbila. Jde o to, že každý test nejenom dostává vlastní novou instanci TestCase
u, ale tato instance je zároveň použita jako objekt nesoucí informaci o výsledku testu (proběhl / neproběhl). Proč mi to vadí? Protože pokud máte hodně testů a u hodně z nich si naplníte instanční proměnné nějakými instancemi, pak vám běh testů sežere hodně paměti (protože se instance TestCase
ů neuvolní pro garbage collection), pokud nespadnou na nedostatek paměti. Takže buď musíte ručně nastavovat hodnotu null
do všech instančních proměnných (pracné a náročné na nezapomenutí) a nebo mít připraveného předka, který bude mít tearDown
s funkcí nastavování hodnoty null
instančním proměnným.
Druhou obrovskou výhodou, kterou jsem dokázal ocenit až po chvíli užívání testNG jsou data-providery. jUnit4 nabízí něco podobného v podobě parametrizovaných testů, ovšem to co nabízí TestNG se to podobá hodně vzdáleně. Když se podíváme na příklad z článku o jUnit4 na devx.com:
@RunWith(Parameterized.class)
public class SquareTest {
private static Calculator calculator = new Calculator();
private int param;
private int result;
@Parameters
public static Collection data() {
return Arrays.asList(new Object[][]{ {0, 0}, {1, 1}, {2, 4}, {4, 16} });
}
public SquareTest(int param, int result) {
this.param = param;
this.result = result;
}
@Test
public void square() {
calculator.square(param);
assertEquals(result, calculator.getResult());
}
}
Z příkladu je zřejmé, že jUnit parametrizuje na úrovní třídy, protože parametry se ze statické metody předávají do konstruktoru třídy. Naproti tomu TestNG:public class SquareTest {
private Calculator calculator = new Calculator();
@DataParameter(name = "square")
protected Object[][] data() {
return new Object[][]{ {0, 0}, {1, 1}, {2, 4}, {4, 16} };
}
@Test(dataProvider = "square")
public void square(int param, int result) {
calculator.square(param);
assertEquals(calculator.getResult(), result);
}
}
Data providerů můžu mít v TestNG víc, dokonce může data provider být z jiné třídy, než test, který jej využívá. Jediné, co si mi nelíbilo, je přehození parametrů metod assert, tj. první je actual
a druhý expected
. Naštěstí existuje třída AssertJUnit
, která zachovává zvyklost z jUnitu.Tyto dvě skutečnosti jsou pro mě tak silnými argumety, že jsem přešel a nelituji. Navíc použití data providerů je tak jednoduché, že dnes je používám možná více než je zdrávo, ale když jsou tak elegantní.
napsal
Jira
v
18:13
7
komentářů
25. května 2008
Test prošel. To je špatně!
Test Driven Development má jednu obrovskou výhodu. Tj. napsat test na neexistující funkcionalitu, pustit jej a ... ano správně ověřit, že test neprošel. Co je to za výhodu?
Přiznám se, že TDD stále není můj šálek kávy. Jestli jsem moc starej a nebo jsem ještě nevyspěl, nevím. Ale stále píšu kód a ten pak testuju a ne obráceně. Stále je moje myšlení tam, že vymýšlím jak věc udělat, když ji tvořím a ne, když vymýšlím test.
No a tady je zakopanej pes, protože pokud chci být korektní, musím manuálně a naprosto proti směru vývoje věcí, nakonec kus kódu pozměnit a zjistit, zda se nestane to co inzeruju v nadpise.
Pokud totiž tento krok neudělám, pak se může stát co se mi už nejednou stalo a to, že testy prošli, ale ne proto, že jsem měl dobře napsanej kód, ale protože test netestoval to co měl.
Stále se přesvědčuji, že Extreme Programming je domyšlené do posledního puntíku a je jenom otázkou času, než to zjistím.
napsal
Jira
v
21:13
0
komentářů
15. května 2008
Na unit testy si vždy čas udělám ...
Přečetl jsem si příspěvek Máte čas na unit testy? od Petra Jůzy a po dlouhé době, mě nějaký text přiměl k reakci (Kde je dagi se svými kontroverzními tematy).
Přiznám se, že s testováním jsem začínal nějakým 8 let zpátky za pomocí jUnit knihovny a měl jsem dobrý pocit. Spíš mě to ale zdržovalo. Postupem času jsem se naučil (alespoň si to myslím) testy psát, začal jsem používat Coberturu a přešel jsem na TestNG.
Nedokážu si představit, že bych neměl unit testy. Proč? Jak píšu kód, píšu testy, kterými ověřím, že to celé funguje ještě předtím, než začnu integrovat komponenty dohromady. Jak to dělají ti, co testy nepíšou netuším. Pokud si vše otestuju, pak v návazných objektech používám mock implementaci téhož (díky EasyMock knihovně) a testuju dál. Nejednou jsem kód měnil, abych ho dokázal otestovat a nejednou jsem se setkal s tím, že se mi taková změna v budoucnu vyplatila.
Psát testy stojí čas, ale i když testy nepíšete, nějak musíte testovat a to také stojí čas. Pokud dojde na nějaké úpravy v budoucnu, pak jsou testy k nezaplacení, protože vzpomenout si, jak jsem to vlastně před půl rokem testoval, to už chce sakra dobrou paměť. Při opravě chyb je to podobné, testy opět pomůžou.
Psát testy až po odladění aplikace je zvěrstvo a plýtvání časem. Má to význam pouze pokud chceme opravit chybu nebo udělat změnu. Pak se může vyplatit napsat na ni testy a teprve poté se pustit do změn.
Nepoužívám TDD a tudíž testy píšu až po napsání výkonného kódu. Nějak na tuto myšlenku nejsem ještě připraven.
A co my testy přinášejí především? Jistotu ...
napsal
Jira
v
12:35
9
komentářů
18. února 2008
Jak nás vypek DateFormat.parse
Tak jsme zase objevili jednu, pro mě překvapivou, skutečnost. Ale vezmu to popořadě. Chceme parsovat datumy s časem reprezentované stringem. Používáme Javu, takže jednoduchý úkol pro DateFormat
:
DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
Date datum = format.parse(retez);
Tento postup má pro mě nelogickou nevýhodu. Tj. pokud si například někdo zplete pořadí měsíce a dne v měsící (u tohoto formátu to není moc pravděpodobné, ale jsou jiné, kde to jde velmi jednoduše), stejně nám to datum vytvoří. Např. parserování textu
2008-24-04 1:30:43
neznamá chybu, ale datum 2009-12-04 1:30:43
.Absolutně tuto vlastnost nechápu, ale třeba se někomu hodí. Proč je ovšem implicitní, to nepochopím nikdy. Naštěstí se dá jednoduše vypnout:
DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
format.setLenient(false);
Date datum = format.parse(retez);
Takže tentokrát už dostaneme, pro mě očekávanou,
ParseException
.A teď se pomalu blížíme k dnešnímu překvapení. Co se stane, pokud na vstupu bude řetěz
2008-04-24 1:30:43 PM
? Možnosti jsou tři: ParseException
, datum 2008-04-24 13:30:43
nebo datum 2008-04-24 1:30:43
? Osobně jsem předpokládal možnost první, přežil bych možnost druhou, ale pravdou je možnost třetí. DateFormat
si i v ne-lenient módu odignoruje část vstupního řetězce. To jsem opravdu nečekal a dost mě to zarazilo. Takže pokud někdo chce skutečně správnou funknci parserování data z řetězce, musí použít:
DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
format.setLenient(false);
ParsePosition p = new ParsePosition(0);
Date datum = format.parse(retez, p);
if (p.getIndex() < retez.length() - 1) {
throw new ParseException(...);
}
Pozor, v případě použití
ParsePosition
metoda parse
nevyhazuje výjimku, musíte si chybu ošetřit sami.Tak a máme konečně, dle mého názoru, správné parserování řetězce na text. Kód je o poznání složitější než ten, se kterým jsme začínali. Škoda, zřejmě chceme to, co není normální pro ostatní.
PS. Díky Luboši ...
napsal
Jira
v
20:30
15
komentářů
štítky: java
1. února 2008
Nová Java: Jak z toho ven ...
Už je to nějaký pátek, co jsem se zabýval vlastnostmi, které bych rád viděl v Javě 7. Něco málo se na mém názoru změnilo: jsem ještě radikálnějsí. Proč? Jsem přesvědčen, že není možné rozšířit Javu tak, aby byla zpětně kompatibilní a zároveň nabízela prvjky, které by moderní jazyk měl mít. Sun se snaží udržen nejen zpětně kompatibilní bytecode, ale i zdroják. A to je ten problém.
A jak z toho ven. Současnou Javu bych nechal takovou jakou je. Cestu ven by nám ukázala nová Java, říkejme jí např. JavaNW (New Way). JavaNW by byla překládána do stejného bytecode, ale byla by nekompatibilní na úrovni zdrojového kódu. Co to znamená? Nepřijdeme o nic z existující infrastruktury: JRE, HotSpot, Terracotta, Tomcat, ... všechno funguje. Ale to není ještě konec seznamu, protože všechny knihovny budou také použitelné: standardní knihovny Javy, Hibernate, Tapestry, FOP, ... vše budeme moci používat i nadále. Takže vlastně skoro o nic nepřijdeme, ale co vlastně získáme? To co získáme je absolutně závislé na tom, jaká bude JavaNW?
Bude JavouNW Scala? Poslední dobu jsem vyplnil studiem tohoto opěvovaného jazyka. Musím přiznat, že jeho prvky jsou opravdu úchvatné (snad se o nich někdy rozepíšu podrobněji), ale je to jiný jazyk. Syntaxe je jiná, pravda kompaktnější (není tolik upovídaná a všechny vlastnosti jsou zakomponovány tak, že do sebe krásně zapadají). Je možné použít stávající knihovny, ale Scala má také vlastní, a ty je potřeba poznat. Je mi to moc líto, protože se mi Scala opravdu moc líbí, ale nemyslím, že se Scala stane JavouNW (nikdy jsem nevěštil, tak spoléhám na to, že to neumím ...).
Tak co třeba některý ze skriptovacích jazyků: Groovy, JRuby, Jython, ... Ne nemyslím si, že budoucnost je v netypových jazycích, Scala nabízí spoustu (netroufám si napsat všechny) vlastnosti, pro které se mi tyto jazyky zamlouvají, ale je typová. Nemyslím, že jsme schopni a ochotni se připravit o výhody typového jazyka: odhalení řady chyb již při překladu, lépe fugující Code Assist, refaktoring, ... Takže JavaNW musí být něco jiného.
Takže kde vzít JavuNW? Za rozumné považuji více vyjít z Javy, aby se syntaxe nového jazyka Javě více podobala a přechod nebyl tak bolestný. Zakomponovat do něj všechny "potřebné" prvky pořádně: generiky, closures, paralelní zpracování a další. Pak by přechod mohl být pozvolný, poklidný a měli bychom nový "nabušený" jazyk.
napsal
Jira
v
20:57
10
komentářů
štítky: budoucnost, java