Rendezés
Egy adott lista elemeinek sorba rendezését célszerű megoldani már szerver oldalon a generált json fájlban. Ha ez nem lehetséges, akkor a Jasper Studio is kínál erre lehetőséget rendező mezők (Sort Field) formájában. Az Outline-on az adott Dataset alatt (Pl: Issues) a "Sort fields"-re jobb gombbal kattintva adhatunk hozzá új rendezési feltételt. Itt megadhatjuk a mező nevét, majd a hozzáadás után a Properties ablakban a rendezési irányt is lehet változtatni. Az IssueList-en az Issues Dataset-nél a "km" mezőt hozzáadva kilométer állás szerint rendezhetjük a rekordokat (jelenleg a json-ban is így van rendezve).
Sajnos ez a rendezési megoldás nem tökéletes. Ha ugyanis egy rendezett listán belül is használnánk "subDataSource-os" listát (itt a vehicles-en belül az issues), például a Vehicles Dataset "year" mező szerinti rendezésekor, akkor a következő hibát kapjuk:
1 2 3 4 5 6 7 8 9 10 11 12 | net.sf.jasperreports.engine.JRException: net.sf.jasperreports.engine.JRRuntimeException: net.sf.jasperreports.engine.fill.JRExpressionEvalException: Error evaluating expression for source text: ((JsonDataSource)$P{REPORT_DATA_SOURCE}).subDataSource( "issues" ) at com.jaspersoft.studio.editor.preview.view.control.ReportControler.fillReport(ReportControler.java: 530 ) at com.jaspersoft.studio.editor.preview.view.control.ReportControler.access$ 20 (ReportControler.java: 505 ) at com.jaspersoft.studio.editor.preview.view.control.ReportControler$ 5 .run(ReportControler.java: 386 ) at org.eclipse.core.internal.jobs.Worker.run(Worker.java: 55 ) ... Caused by: java.lang.ClassCastException: net.sf.jasperreports.engine.fill.SortedDataSource cannot be cast to net.sf.jasperreports.engine.data.JsonDataSource at Cars_Vehicles_1466103932643_94221.evaluate(Cars_Vehicles_1466103932643_94221: 197 ) at net.sf.jasperreports.engine.fill.JREvaluator.evaluate(JREvaluator.java: 276 ) ... 22 more |
A problémát az okozza, hogy a belső lista elemeinek eléréséhez a JsonDataSource (JDS) subDataSource metódusát használnánk, de a rendezett lista minden adattípus esetén SortedDataSource-ot ad vissza, ami nem cast-olható JDS-ra és nem elérhető a szükséges metódus sem. A problémát a SortedDataSource vagy a JDS bővítésével lehetne feloldani, de erre egyelőre nincs megoldás. Ezért is célszerű már a riportban felhasználás előtt rendezni az adatokat.
Szűrés
- Egyszerű szűrés (subDataSource és attributum)
- Feltételek használata
- Beépített paraméter használata ($V{COLUMN_COUNT})
- Komplex feltétel (&&)
- Saját változó használata (tömb mérete)
Egyszerű szűrés
A List elemben a Dataset-nél van lehetőség egyszerű szűrési feltétel megadására a subDataSource elkérésénél. Itt csak az alap operátorokat használhatjuk és csak egy mezőre. Ha csak azokat az járműveket használnánk, ahol a gyártási év 2006-os (Ford), akkor a következő kifejezést kell használnunk a JRDataSource Expression-ben:
1 | ((JsonDataSource)$P{REPORT_DATA_SOURCE}).subDataSource( "vehicles(year == 2006)" ) |
Feltételek használata
A Vehicles Dataset-nél az "Edit query, filter..." gombra kattintva, a "Filter Expression" fül alatt a Expression editorban tetszőleges feltétel megadható.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | // ha az 1996 és 2010 közötti járművekre szűrnénk: // ha a year mezőt alapértelmezett String-ként hoztuk létre, akkor Integer-re kell alakítanunk $F{year} != null && Integer.valueOf($F{year}) >= 1996 && Integer.valueOf($F{year}) <= 2010 // ha a year mező típusa Integer $F{year} != null && $F{year} >= 1996 && $F{year} <= 2010 // ha csak a lista első két elemét jelenítenénk meg: $V{COLUMN_COUNT} <= 2 // ha csak azokat a járműveket, ahol van bejegyzés: // ekkor az $F{issues} mezőben be kell állítani a "issues.date" értéket a Description részen, // 1. így String-ként kapjuk vissza egy tömb értékét, majd a $V{issuesSize} változóban az // Arrays.asList($F{issues}.replaceAll("\\[","").replaceAll("\\]","").split(",")).size(); értéket kell megadnunk // 2. Object-ként kapjuk vissza, amit a $V{issuesSize} változóban ArrayNode-ra alakítunk // ($F{issues} instanceof ArrayNode) ? ((ArrayNode)$F{issues}).size() : 0; $V{issuesSize} > 0 |
*: Az ArrayNode használatához célszerű importálni a com.fasterxml.jackson.databind.node.ArrayNode osztályt (ahogy korábban a JsonDataSource-t), de az alap projektben nem lehet, így mindig a teljes nevet kellene kiírnunk. Erre megoldás lehet, ha a "MyReport - jobb click - Properties" részen hozzáadjuk a Library-nál a "JasperReports Library Dependecies"-t.
A listák használatának kezdetén már látszott, hogy a Jasper Reports használata nem úszható meg minimális programozási tudás nélkül (alap feltételek, cast-olás és operátorok), de a fenti feltételeknél már többre is szükség lehet. Például a tömbök esetén várt java.util.List helyett visszaadott ArrayNode nincs dokumentálva, csak a forráskódból következtethető ki (JsonDataSource). A Jasper Reports forráskód felhasználásáról a későbbiekben írok. A fenti rendezést és szűréseket tartalmazó videó megtalálható itt, a forrásfájlok pedig itt.
A fenti feltételek mindegyike - a meglévő négy elemből - csak ugyanazt a két járművet adja vissza: Honda és Ford.