Jump to content
We've recently updated our Privacy Statement, available here ×
  • This documentation is an older version of Jaspersoft Studio User Guide. View the latest documentation.

    Using Collection of JavaBeans Data Sources

    A JavaBeans set data source allows you to use JavaBeans as data for a report. In this context, a JavaBean is a Java class that exposes its attributes with a series of get methods, with the following syntax:

    public <returnType> getXXX()

    where <returnType> (the return value) is a generic Java class or a primitive type (such as int, double, and so on).

    To create a connection to handle JavaBeans, select Collection of JavaBeans in the list of data source types to bring up the dialog shown in “JavaBeans set data source”.

    javabeans-data-adapter_357x339.png.eedf4b0c9b27f0dfbc49686beb1086a8.png

    JavaBeans set data source

    Once again, the first thing to do is specify the name of the new data source.

    Registering the Fields of a JavaBean Set Data Source

    One peculiarity of a JavaBeans set data source is that the fields are exposed through get methods. This means that if the JavaBean has a getXyz() method, xyz is the name of a record field (the JavaBean represent the record).

    In this example, the PersonBean object shows two fields: name and age. Register them in the fields list as a String and an Integer, respectively.

    Create a new empty report and add the two fields by right-clicking the Fields node in the outline view and selecting Add field. The field names and the types of the fields are: name (java.lang.String) and age (java.lang.Integer).

    Drag the fields into the Detail band and run the report. (Make sure the active connection is the Test Factory.) To refer to an attribute of an attribute, you can separate with periods. For example, to access the street attribute of an Address class contained in the PersonBean, the syntax would be address.street. The real call would be <someBean>.getAddress().getStreet().

    Layout of a JavaBeans-Based Report

    javabeans-layout_302x120.png.15651724f9d9024dfdf136e1475f69f4.png

    If the flag Use field description is set when you're specifying the properties of your JavaBeans set data source, mapping between JavaBean attribute and field value uses the field description instead of the field name. The data source considers only the description to determine the field value, and the field can have any name.

    Jaspersoft Studio provides a visual tool to map JavaBean attributes to report fields. To use it, open the query window, go to the tab JavaBean Data Source, insert the full class name of the bean you want to explore, and click Read attributes. The tab displays the attributes of the specified bean class.

    If an attribute is also a Java object, you can double-click the object to display its other attributes.
    To map a field, select an attribute name and click the Add Selected Field(s) button.

    Using XML Data Adapters

    JasperReports supports XML as a data adapter in three different ways: XML documents, remote XML documents, and XML/A servers.

    An XML document is typically organized as a tree, and doesn't match the table-like form required by JasperReports. For this reason, you have to use an XPath expression to define a node set. The specifications of the XPath language are available at http://www.w3.org/TR/xpath. Some examples can help you understand how to define the nodes.

    The XML file below is an address book in which people are grouped in categories, followed by a second list of favorite objects. In this case, you can define different node set types. First you'll need to decide how you want to organize the data in your report.

    Example XML file

    To select only the people contained in the categories (that is, all the people in the address book), use the following expression:

    /addressbook/category/person

    Four nodes are returned as shown.

    Node set with expression /addressbook/category/person

    If you want to select the people appearing in the favorites node, the expression to use is

    /addressbook/favorites/person

    Two nodes are returned.

    Here's another expression. It's a bit more complex, but it shows all the power of the Xpath language. The idea is to select the person nodes belonging to the work category. The expression to use is the following:

    /addressbook/category[@name = "work"]/person

    The expression returns only one node, the one with an ID equal to 4, as shown here:

    After you've created an expression to select a node set, you can create an XML data source.

    Open the window for creating a new data source and select XML File data source from the list of connection types to display the dialog below.

    xml-data-adapter_357x341.png.f221059e0cbd4710e429a71b53143b06.png

    Configuring an XML Data Adapter

    XML file is the only required field. You have the option to provide a set of nodes, using a pre-defined static XPath expression. Or you can set the XPath expression directly in the report.

    We suggest using a report-defined XPath expression. This enables you to use parameters inside the XPath expression, which acts like a real query on the supplied XML data.

    Optionally, you can specify Java patterns to convert dates and numbers from plain strings to more appropriate Java objects (like Date and Double). For the same purpose, you can define a specific locale and time zone to use when parsing the XML stream.

    Registration of Fields for an XML Data Source

    In addition to the type and name, the definition of a field in a report using an XML data source requires an expression inserted as a field description. As the data source aims always to be one node of the selected node set, the expressions are relative to the current node.

    To select the value of an attribute of the current node, use the following syntax:

    @<name attribute>

    For example, to define a field that must point to the id attribute of a person (attribute id of the node person), it's sufficient to create a new field, name it, and set the description to:

    @id

    It's also possible to get to the child nodes of the current node. For example, if you want to refer to the lastname node, child of person, use the following syntax:

    lastname

    To move to the parent value of the current node (for example, to determine the category to which a person belongs), use a slightly different syntax:

    ancestor::category/@name

    The ancestor keyword indicates that you're referring to a parent node of the current node. Specifically, the first parent of category type, of which you want to know the value of the name attribute.

    Now, let’s see everything in action. Prepare a simple report with the registered fields shown here:

    Field name

    Description

    Type

    id

    @id

    Integer

    lastname

    lastname

    String

    firstname

    firstname

    String

    name of category

    ancestor::category/@name

    String

    Jaspersoft Studio provides a visual tool to map XML nodes to report fields; to use it, open the query window and select XPath as the query language. If the active connection is a valid XML data source, the associated XML document is shown in a tree view. To register the fields, set the record node by right-clicking a Person node and selecting the menu item Set record node. The record nodes are displayed in bold.

    Then one by one, select the nodes or attributes and select the pop-up menu itemAdd node as field to map them to report fields. Jaspersoft Studio determines the correct XPath expression to use and creates the fields for you. You can modify the generated field name and set a more suitable field type after the registration of the field in the report (which happens when you close the query dialog).

    Insert the different fields in the Detail band. The XML file used to fill the report is that shown:

    The XPath expression for the node set selection specified in the query dialog is:

    /addressbook/category/person

    XML Data Source and Subreports

    A node set allows you to identify a series of nodes that represent records from a JRDataSource point of view. However, due to the tree-like nature of an XML document, it may be necessary to see other node sets that are subordinate to the main nodes.

    Consider the XML in Complex XML example. This is a slightly modified version of Example XML file. For each person node, a hobbies node is added which contains a series of hobby nodes and one or more e-mail addresses.

    Complex XML example

    What we want to produce is a document that is more elaborate than those you have seen so far. For each person, we want to present their e-mail addresses, hobbies, and favorite people.

    You can create this document using subreports. You'll need a subreport for the e-mail address list, one for hobbies, and one for favorite people (that is a set of nodes out of the scope of the XPath query we used). To generate these subreports, you need to understand how to produce new data sources to feed them. In this case, you'll use the JRXmlDataSource, which exposes two extremely useful methods:

    public JRXmlDataSource dataSource(String selectExpression)

    public JRXmlDataSource subDataSource(String selectExpression)

    The first method processes the expression by applying it to the whole document, starting from the actual root. The second assumes the current node is the root.

    Both methods can be used in the data source expression of a subreport element to dynamically produce the data source to pass to the element. The most important thing to note is that this mechanism allows you to make both the data source production and the expression of node selection dynamic.

    The expression to create the data source that feeds the subreport of the e-mail addresses is:

    	((net.sf.jasperreports.engine.data.JRXmlDataSource)		$P{REPORT_DATA_SOURCE}).subDataSource("/person/email")

    This code returns all the e-mail nodes that descend directly from the present node (person).

    The expression for the hobbies subreport is similar, except for the node selection:

    ((net.sf.jasperreports.engine.data.JRXmlDataSource)

    $P{REPORT_DATA_SOURCE}).subDataSource("/person/hobbies/hobby")

    Next, declare the master report’s fields. In the subreport, you have to refer to the current node value, so the field expression is simply a dot (.),

    Proceed with building your three reports: xml_addressbook.jasper, xml_addresses.jasper, and xml_hobbies.jasper.

    In the master report, xml_addressbook.jrxml, insert a group named “Name of category,” in which you associate the expression for the category field ($F{name of category}). In the header band for Name of category, insert a field to display the category name. By doing this, the names of the people are grouped by category (as in the XML file).

    In the Detail band, position the id, lastname, and firstname fields. Below these fields, add the two Subreport elements, the first for the e-mail addresses, the second for the hobbies.

    The e-mail and hobby subreports are identical except for the name of the field in each one. The two reports should be as large as the Subreport elements in the master report, so remove the margins and set the report width accordingly.

    Preview both the subreports just to compile them and generate the relative .jasper files. Jaspersoft Studio returns an error during the fill process, but that's expected. We haven't set an Xpath query, so JasperReports can't get any data. You can resolve the problem by setting a simple Xpath query (it isn't used in the final report), or you can preview the subreport using an empty data source (select it from the combo box in the tool bar).

    When the subreports are done, execute the master report. If everything is okay, the report groups people by home and work categories and the subreports associated with each person.

    As this example demonstrates, the real power of the XML data source is the versatility of XPath, which allows navigation of the node selection in a refined manner.

    Using XML/A Data Adapters

    XML/A (XML for Analysis) is an XML standard for accessing remote data in an OLAP schema. Jaspersoft Studio supports an XML/A data adapter that can connect various XML/A providers such as JasperReports Server and Microsoft SQL Server Analytic Services (SSAS). Because Jaspersoft Studio uses OLAP4J (http://www.olap4j.org/), it may also be able to connect to other types of XML/A providers.

    The remote server must also be configured for XML/A. For more information, including instructions for configuring Jaspersoft OLAP, see the Jaspersoft OLAP User Guide .

    To create an XML/A Data Adapter:

    1. Right-click Data Adapters in the Repository Explorer, and select Create Data Adapter.
    2. Select XML/A Server and click Next.
    3. Enter a name for the data adapter.
    4. Enter the URL for your XML/A provider. The type of server determines the value. For example:
         If the XML/A server is JasperReports Server, the URL is something like: http://<hostname>:<port>/jasperserver-pro/xmla
         If the XML/A server is Microsoft SSAS 2012, the URL is something like:

    http://<hostname>/MSSQL_2012/msmdpump.dll

    5. Enter a user name and password of a user that has sufficient access in the report server to return your data.
    6. Click Get Metadata.

    Jaspersoft Studio attempts to connect to the server and return information about its data sources, catalogs, and cubes. If it's successful, default values appear in the drop-downs. If the connection fails, check the URL, ensure that the remote server is available, and try again.

    7. Select the data source, catalog, and cube that stores the data you want for your report.
    8. Click Test.

    Jaspersoft Studio connects to the server and read the cube you selected. If the connection fails, check the URL, ensure that the remote server is available, and try again.

    9. When the test succeeds, click OK to close the message and click Finish to close the New Data Adapter wizard.

    When you create a report using this data adapter, you may see a message indicating that the data adapter doesn't support the ability to retrieve fields. This means Jaspersoft Studio doesn't have enough information to preview your data. After you provide an MDX query, Jaspersoft Studio can automatically read fields and suggest their datatypes.

    Registration of fields in XML/A Providers

    When you create an XML/A data adapter, you define the cube from which to read data. Jaspersoft Studio can then inspect the remote server and suggest datatypes for the fields returned.

    To register fields returned by an XML/A data adapter:

    1. With your report open in the design pane, click dataset-and-query-button.png.8af483fdc114f0c8910e573b8ded026e.png
    2. Select the data adapter that points to your XML/A provider from the drop-down in the upper-left corner.
    3. Select MDX from the Language drop-down.
    4. Enter a valid MDX query in the text field.

    To create a good MDX query, you must be familiar with both the language itself and the data you want to work with. You can also use a tool (such as the Jaspersoft OLAP Workbench) to load your OLAP schema and automatically generate MDX queries from it.

    5. Click Read Fields.

    Jaspersoft Studio returns the XML/A provider's data, including fields and parameters, and populates the window's tabs with information. For more on how these tabs can be used to define the data in your report, see Creating Queries.

    Jaspersoft Studio also sets the class type of each field to an appropriate Java datatype. If Jaspersoft Studio sets an incorrect datatype, you can set the correct type after the fields are added to your report.

    6. When the data in the Data Preview tab looks like the data you want to fill your report, click OK to close the Dataset and Query window.

    Using CSV Data Sources

    To create a connection based on a CSV file, click the New button in the Connections/Datasources dialog and select File CSV data source from the data source types list to display the dialog.

    csv-data-adapter_357x415.png.7086149a45e311e9d031d7f8ef04bb7b.png

    CSV Data Adapter

    Set a name for the connection and choose a CSV file. Then declare the fields in the data source.

    If the first line in your file contains the names of the columns, click Get column names from the first row of the file and select the Skip the first line check box . This forces JasperReports to skip the first line (the one containing your column labels). In any case, the column names read from the file are used instead of the declared ones, so avoid modifying the names found with the Get column names button.
    If the first line of your CSV file doesn’t contain the column names, set a name for each column using the syntax COLUMN_0, COLUMN_1, and so on.

    warning-icon-ns_28x28.png.914d392c474ac3233ec3a7a1a4639a67.png

    If you define more columns than the ones available, you’ll get an exception at report filling time.

    JasperReports assumes that for each row all the columns have a value (even if they are empty).

    If your CSV file uses nonstandard characters to separate fields and rows, you can adjust the default setting for separators using the Separators tab.

    csv-separators_357x415.png.254d0b788bb72a42547f8ae0d0324805.png

    Separators Tab

    Registration of the Fields for a CSV Data Source

    When you create a CSV data source, you must define a set of column names as fields for your report. To add them to the fields list, set your CSV data source as the active connection and open the Report query dialog. Open the Dataset and Query Dialog and click the Read Fields button.

    By default, Jaspersoft Studio sets the class type of all fields to java.lang.String. If you're sure the text of a particular column can be easily converted to a number, a date, or a Boolean value, set the correct field type yourself after the fields are added to your report.

    The pattern used to recognize a timestamp (or date) object can be configured at the data source level by selecting the Use custom date format check box.

    Using JREmptyDataSource

    JasperReports provides a special data source named JREmptyDataSource.

    This source returns true to the next method for the record number (by default only one), and always returns null to every call of the getFieldValue method. It's like having records without fields, that is, an empty data source.

    The two constructors of this class are:

    public JREmptyDataSource(int count)public JREmptyDataSource()

     

    The first constructor indicates how many records to return, and the second sets the number of records to one.

    By default, Jaspersoft Studio provides a pre-configured empty data source that returns a single record.

    To create a new empty data source with more records:

    1. Double-click One Empty Record in the Repository View. The Data Adapter Wizard appears with Empty rows.

    Data Adapter Wizard > Empty Record

    data-adapter-empty-record_357x277.png.d1e7c00c66c208ba5c7ba216d2848324.png

    2. Set the number or empty records you need. Remember, whatever field you add to the report, its value is set to null. Since this data source doesn’t care about field names or types, this is a perfect way to test any report (keeping in mind that the fields are always set to null).
    3. Click Finish.

    Using HQL and Hibernate Connections

    JasperReports provides a way to use HQL directly in your report. To do so, first set up a Hibernate connection. Expand your classpath to include all classes, JARs, and configuration files used by your Hibernate mapping. In other words, Jaspersoft Studio must be able to access all the *.hbm.xml files you plan to use, the JavaBeans declared in those files, the hibernate.cfg.xml file, and any other JARs used (for example, JARs that access the database under Hibernate).

    To add these objects to the classpath:

    1. Right-click Data Adapters in the Repository Explorer, and select Create Data Adapter.
    2. Click the Driver Classpath tab.

    data-adapter-add-jar-files_357x375.png.e996d8bf4d6b993b0afaabdce26398ab.png

    Data Adapter Wizard > Add JAR Files

    3. Click the Add button.
    4. Navigate to your JAR file.
    5. Click Open.
    6. Repeat for any additional files.
    7. Give your data adapter a unique name.
    8. Click the Test button to check the path resolution to be certain that hibernate.cfg.xml is in the classpath.

    Currently Jaspersoft Studio works only with the first hibernate.cfg.xml file found in the classpath.

    9. Click Finish.

    If you use the Spring framework, you can use a Spring configuration file to define your connection. In this case, you’ll need to set the configuration file name and the Session Factory Bean ID.

    Now that a Hibernate connection is available, use an HQL query to select the data to print. You can use HQL in the same way as SQL: open the Report query dialog and choose HQL as the query language.

    When you enter an HQL query, Jaspersoft Studio tries to retrieve the available fields. According to the JasperReports documentation, the field mappings are resolved as follows:

    If the query returns one object per row, a field mapping can be one of the following ways:
         If the object’s type is a Hibernate entity or component type, the field mappings are resolved as the property names of the entity/component. If a select alias is present, it can be used to map a field to the whole entity/component object.
         Otherwise, the object type is considered scalar, and only one field can be mapped to its value.
    If the query returns a tuple (object array) per row, a field mapping can be one of the following:
         A select alias. The field is mapped to the value corresponding to the alias.
         A property name prefixed by a select alias and a period (.). The field is mapped to the value of the property for the object corresponding to the alias. The type corresponding to the select alias has to be an entity or component.

    note-icon-ns_28x28.png.226fdd3cae785348bab54094c2f06740.png

    If you don’t understand this field mapping information, simply accept the fields listed by Jaspersoft Studio when the query is parsed.

    Jaspersoft Studio provides a mapping tool to map objects and attributes to report fields. The objects (or JavaBeans) available in each record are listed in the combo box on top of the object tree.

    To add a field from the tree, select the corresponding node and click the Add selected field(s) button.

    Using a Hadoop Hive Connection

    JasperReports provides a way to use Hive in your reports. Unlike traditional databases, Hadoop systems support huge amounts of data, generally called big data. However, this capability has a cost: high latency with access times between 30 seconds and 2 minutes.

    note-icon-ns_28x28.png.9991c658fd9bac79d788799d32ceff9e.png

    Because of the latency, reports based on Hadoop-Hive data sources are best run in the background or scheduled. For example, the report could be run at 6 a.m. and the HTML or PDF could be exported and stored for anyone wanting to access the report during the day.

    To use Hadoop Hive with Jaspersoft Studio:

    1. Double-click New Data Adapter in the Repository view to display the Data Adapter Wizard.

    data-adapter-hadoop-hive_357x375.png.446263835bcbbae2b8f28457d0e8f805.png

    Hadoop Hive Connection

    2. Choose Hadoop Hive connection as your JDBC driver.
    3. Enter the path to your Hive JDBC. Usually it looks something like jdbc:hive://localhost:10000/default.
    4. Click Test to check the path resolution.
    5. Click Finish.

    Use a HiveQL query to retrieve data for your report. You can use HiveQL the same way that you use SQL. To use a HiveQL query, open the Report Query dialog and choose HiveQL as the query language.

    When you enter a HiveQL query, Jaspersoft Studio retrieves all available fields. on the next two screens, select the fields you want to display in your report, and how you want to group them. After defining your HiveQL query and choosing your fields, your report is configured to receive data from your Hadoop Hive data source.

    warning-icon-ns_28x28.png.8d99d2a5ea69ad678a716a0a81007042.png

    The Hive JDBC driver does not yet fully implement the JDBC specifications, and it does not yet work correctly with the JasperReports Server metadata layer (Data Domains). If you're reporting against a Hive data source using JasperReports Server, use Topics rather than Domains.

    Implementing a New JRDataSource

    If the JRDataSource supplied with JasperReports doesn't meet your requirements, you can write a new JRDataSource. This is not a complex operation. In fact, all you have to do is create a class that implements the JRDataSource interface that exposes two simple methods: next and getFieldValue.

    The JRDataSource interface

    The next method is used to set the current record into the data source. It has to return true if a new record to elaborate exists; otherwise it returns false.

    If the next method has been called positively, the getFieldValue method has to return the value of the requested field or null. Specifically, the requested field name is contained in the JRField object passed as a parameter. Also, JRField is an interface through which you can get information associated with a field—the name, description, and Java type that represents it (as mentioned previously in Understanding the JRDataSource Interface).

    Now try writing your personalized data source. You have to write a data source that explores the directory of a file system and returns the found objects (files or directories). The fields you create to manage your data source are the same as the file name, which should be named FILENAME; a flag that indicates whether the object is a file or a directory, which should be named IS_DIRECTORY; and the file size, if available, which should be named SIZE.

    You data source should have two constructors: the first receives the directory to scan as a parameter; the second has no parameters and uses the current directory to scan.

    Once instantiated, the data source looks for the files and the directories present in the way you indicate and fills the array files.

    The next method increases the index variable you use to keep track of the position reached in the array files, and returns true until you reach the end of the array.

    Sample personalized data source

    The getFieldValue method returns the requested file information. Your implementation doesn't use the information regarding the return type expected by the caller of the method. It assumes the name has to be returned as a string. The flag IS_DIRECTORY as a Boolean object, and the file size as a Long object.

    The next section shows how to use your personalized data source in Jaspersoft Studio and test it.

    Using a Custom JasperReports Data Source with Jaspersoft Studio

    Jaspersoft Studio provides a special connection for your personalized data sources. It's useful for employing whatever JRDataSource you want to use through some kind of factory class that provides an instance of that JRDataSource implementation. The factory is just a simple Java class useful for testing your data source and filling a report in Jaspersoft Studio. The idea is the same as what you have seen for the JavaBeans set data source—You need to write a Java class that creates the data source through a static method and returns it. For example, if you want to test the JRFileSystemDataSource in the previous section, you need to create a simple class like that shown in this code sample:

    Class for testing a custom data source

    This class, and in particular the static method that's called, executes all the necessary code for instancing the data source correctly. In this case, you create a new JRFileSystemDataSource object by specifying a way to scan the directory root ("/").

    Now that you have defined the way to obtain the JRDataSource you prepared and the data source is ready to be used, you can create the connection through which it can be used.

    Create a new connection as you normally would (see Creating and Using Database JDBC Connections), then select Custom implementation of JRDataSource from the list and specify a data source name like TestFileSystemDataSource (or whatever name you want), as shown below

    custom-data-adapter_357x325.png.8864dbc838ee552fa34b10e5f00ac796.png

    Configuring a Custom Data Adapter

    Next, specify the class and method to obtain an instance of your JRFileSystemDataSource, that is, TestFileSystemDataSource and test.

    note-icon-ns_28x28.png.801b060db9264a57ae16867b8c8cf203.png

    There is no automatic method to find the fields managed by a custom data source.

    In this case, you know that the JRFileSystemDataSource provides three fields: FILENAME (String), IS_DIRECTORY (Boolean), and SIZE (Long). After you have created these fields, insert them in the report’s Detail band.

    Divide the report into two columns and in the Column Header band, insert Filename and Size tags. Then add two images, one representing a document and the other an open folder. In the Print when expression setting of the Image element placed in the foreground, insert the expression $F{IS_DIRECTORY}, or use as your image expression a condition like the following:

    ($F{IS_DIRECTORY}) ? “folder.png” : “file.png”

    In this example, the class that instantiated the JRFileSystemDataSource was very simple. But you can use more complex classes, such as one that obtains the data source by calling an Enterprise JavaBean or by calling a web service.


    User Feedback

    Recommended Comments

    There are no comments to display.



    Guest
    This is now closed for further comments

×
×
  • Create New...