Jump to content
We've recently updated our Privacy Statement, available here ×

sun.misc.InvalidJarIndexException when compiling


actualsystems

Recommended Posts

We wrote a program a while ago using Jasper Reports 3.0.0 that uses ECJ to compile reports. This runs fine on one computer running Vista 32-bit, and a 32-bit JVM (1.6.0 update 10).

We have since recompiled the program and tried to run it under Vista 64-bit, using the same 32-bit JVM. We get an exception compiling the report:

Exception in thread "main" net.sf.jasperreports.engine.JRException: Error compiling report design.
    at net.sf.jasperreports.engine.design.JRAbstractCompiler.compileReport(JRAbstractCompiler.java:233)
    at net.sf.jasperreports.engine.JasperCompileManager.compileReport(JasperCompileManager.java:219)
    at com.actual_systems.p2.client.GUI.ReportPreview.TableReport.TableJasperDesign.compileAndPrintReport(TableJasperDesign.java:534)
    at com.actual_systems.p2.client.GUI.ReportPreview.TableReport.TableJasperDesign.showReport(TableJasperDesign.java:650)
    at com.actual_systems.p2.client.GUI.ReportPreview.TableReport.TableJasperDesign.main(TableJasperDesign.java:608)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:90)
Caused by: sun.misc.InvalidJarIndexException: Invalid index
    at sun.misc.URLClassPath$JarLoader.getResource(URLClassPath.java:854)
    at sun.misc.URLClassPath$JarLoader.getResource(URLClassPath.java:762)
    at sun.misc.URLClassPath$JarLoader.findResource(URLClassPath.java:732)
    at sun.misc.URLClassPath.findResource(URLClassPath.java:145)
    at java.net.URLClassLoader$2.run(URLClassLoader.java:362)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.net.URLClassLoader.findResource(URLClassLoader.java:359)
    at java.lang.ClassLoader.getResource(ClassLoader.java:978)
    at java.lang.ClassLoader.getResourceAsStream(ClassLoader.java:1168)
    at net.sf.jasperreports.engine.design.JRJdtCompiler.getResource(JRJdtCompiler.java:572)
    at net.sf.jasperreports.engine.design.JRJdtCompiler$1.findType(JRJdtCompiler.java:271)
    at net.sf.jasperreports.engine.design.JRJdtCompiler$1.findType(JRJdtCompiler.java:229)
    at org.eclipse.jdt.internal.compiler.lookup.LookupEnvironment.askForType(LookupEnvironment.java:122)
    at org.eclipse.jdt.internal.compiler.lookup.PackageBinding.getTypeOrPackage(PackageBinding.java:183)
    at org.eclipse.jdt.internal.compiler.lookup.BlockScope.getBinding(BlockScope.java:421)
    at org.eclipse.jdt.internal.compiler.ast.QualifiedNameReference.resolveType(QualifiedNameReference.java:989)
    at org.eclipse.jdt.internal.compiler.ast.MessageSend.resolveType(MessageSend.java:341)
    at org.eclipse.jdt.internal.compiler.ast.CastExpression.resolveType(CastExpression.java:490)
    at org.eclipse.jdt.internal.compiler.ast.Assignment.resolveType(Assignment.java:192)
    at org.eclipse.jdt.internal.compiler.ast.Expression.resolve(Expression.java:882)
    at org.eclipse.jdt.internal.compiler.ast.Block.resolve(Block.java:101)
    at org.eclipse.jdt.internal.compiler.ast.Statement.resolveCase(Statement.java:140)
    at org.eclipse.jdt.internal.compiler.ast.SwitchStatement.resolve(SwitchStatement.java:307)
    at org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration.resolveStatements(AbstractMethodDeclaration.java:444)
    at org.eclipse.jdt.internal.compiler.ast.MethodDeclaration.resolveStatements(MethodDeclaration.java:191)
    at org.eclipse.jdt.internal.compiler.ast.AbstractMethodDeclaration.resolve(AbstractMethodDeclaration.java:403)
    at org.eclipse.jdt.internal.compiler.ast.TypeDeclaration.resolve(TypeDeclaration.java:1096)
    at org.eclipse.jdt.internal.compiler.ast.TypeDeclaration.resolve(TypeDeclaration.java:1184)
    at org.eclipse.jdt.internal.compiler.ast.CompilationUnitDeclaration.resolve(CompilationUnitDeclaration.java:537)
    at org.eclipse.jdt.internal.compiler.Compiler.process(Compiler.java:743)
    at org.eclipse.jdt.internal.compiler.Compiler.compile(Compiler.java:444)
    at net.sf.jasperreports.engine.design.JRJdtCompiler.compileUnits(JRJdtCompiler.java:192)
    at net.sf.jasperreports.engine.design.JRAbstractCompiler.compileReport(JRAbstractCompiler.java:192)
    ... 9 more
 

 

Debugging the problem, it looks like an issue with the classloader, which is iterating over the com.actual_systems.... package hierarchy; for each level it tries to load a class and, if that returns null, tries to load a package. "com" loads okay as a package, but the "actual_systems" package throws an exception when trying to load it as a class.

We have tried updating JasperReports to 3.5.1 and ECJ to 3.4.2, but to no avail. I don't know what version of ECJ we were using before (but we have a copy of the JAR file).

If we save the same report as a JRXML file, and compile using ant and JRAntCompileTask, it works okay and generates a .jasper file. This isn't a good solution for us as we don't know the layout of the report until the program is run.

Does anyone have any experience of this issue?

Link to comment
Share on other sites

  • Replies 1
  • Created
  • Last Reply

Top Posters In This Topic

Top Posters In This Topic

We have managed to reduce the problem to a test case. On closer inspection, the problem is not caused by the version of java, the OS or CPU. It seems to be related to a third-party JAR file somehow.

The problem occurs when the test case is in a sub-package at least three levels deep, and when using glazedlists-1.8.0-java15.jar on the classpath. Replacing glazedlists-1.8.0-java15.jar with 1.7.0-java15.jar, or removing it completely, causes the error to go away and the program then works as expected. The program also works as expected when placed in the main package or the "com" package.

The program can also be made to work by changing the text-field expression not to include a reference back to the class (although this isn't a good workaround for us).

We have attached our test case. Does anyone have any idea what could cause this?

Code:
package com.actual_systems.p2.client.GUI.ReportPreview.TableReport;import net.sf.jasperreports.engine.design.*;import net.sf.jasperreports.engine.*;import net.sf.jasperreports.engine.data.JRTableModelDataSource;import net.sf.jasperreports.view.JasperViewer;import javax.swing.*;import javax.swing.table.TableColumnModel;import javax.swing.table.TableModel;import javax.swing.table.DefaultTableModel;import java.text.DateFormat;import java.text.SimpleDateFormat;import java.util.*;import java.sql.Timestamp;/** * JasperDesign to setup a report based on a JTable */public class TableJasperDesign extends JasperDesign {    private static final int LANDSCAPE_TOTAL_PAGE_WIDTH = 791;    private static final int LANDSCAPE_TOTAL_PAGE_HEIGHT = 595;    private static final int LANDSCAPE_MARGIN_HEIGHT = 40;    private static final int LANDSCAPE_MARGIN_WIDTH = 50;    /**     * the printable area of the page (the width of the page minus the right and left margins)     */    public static final int PORTRAIT_PRINTABLE_PAGE_WIDTH = 595 - (2 * 40);    /**     * the printable area of the page (the width of the page minus the right and left margins)     */    public static final int LANDSCAPE_PRINTABLE_PAGE_WIDTH = 791 - (2 * 50);    private static final int SPACE_BETWEEN_COLUMNS = 5;    /**     * Scaling factor from JTable width to report width     */    private final double widthScale;    public static final String REPORT_TITLE_KEY = "ReportTitle";    private static final String REPORT_CLASSNAME = "DynamicReport";    private TableColumnModel columnModel;    private TableModel dataModel;    /**     * Construct the report     *     * @param table      JTable containing data and column models to use     * @throws JRException on error     */    public TableJasperDesign(JTable table) throws JRException {        this.columnModel = table.getColumnModel();        this.dataModel = table.getModel();        widthScale = (double) LANDSCAPE_PRINTABLE_PAGE_WIDTH / (double) columnModel.getTotalColumnWidth();        setOrientation(JasperDesign.ORIENTATION_LANDSCAPE);        setupPage();        setupDetailBand();    }    /**     * Sets up the detail band, which shows the data     */    private void setupDetailBand() {        // Create a band and set the height.        JRDesignBand band = new JRDesignBand();        band.setHeight(14);        for (int col = 0, xPos = 0; col < columnModel.getColumnCount(); ++col) {            // get the column width from the table model            int colWidth = getScaledColWidth(col);            // Create the designTextField and place the field type            // make sure these values can overflow            JRDesignTextField textField = new JRDesignTextField();            textField.setStretchWithOverflow(true);            textField.setX(xPos);            textField.setY(2);            textField.setWidth(colWidth);            textField.setHeight(12);            textField.setPositionType(JRElement.POSITION_TYPE_FLOAT);            JRDesignExpression expression = new JRDesignExpression();            Class type = String.class;            expression.setValueClass(type);            expression.setText(getClass().getName() + ".stripHTML(\"<html><b>TEST</b></html>\")");            textField.setExpression(expression);            band.addElement(textField);            xPos += colWidth + SPACE_BETWEEN_COLUMNS;        }        setDetail(band);    }    /**     * Scale a column from a JTable into the report     *     * @param col Column Index     * @return colWidth     */    private int getScaledColWidth(int col) {        int colWidth = columnModel.getColumn(col).getWidth();        colWidth = (int) (colWidth * widthScale);        colWidth -= SPACE_BETWEEN_COLUMNS;        return colWidth;    }    /**     * Setup the page settings (page height, width, margins etc.)     */    private void setupPage() {        setName(REPORT_CLASSNAME);        setPageWidth(LANDSCAPE_TOTAL_PAGE_WIDTH);        setPageHeight(LANDSCAPE_TOTAL_PAGE_HEIGHT);        setColumnWidth(LANDSCAPE_PRINTABLE_PAGE_WIDTH);        setLeftMargin(LANDSCAPE_MARGIN_WIDTH);        setRightMargin(LANDSCAPE_MARGIN_WIDTH);        setTopMargin(LANDSCAPE_MARGIN_HEIGHT);        setBottomMargin(LANDSCAPE_MARGIN_HEIGHT);        setColumnSpacing(0);    }    /**     * Return the table data     *     * @return rtn     */    public JRTableModelDataSource getTableModel() {        return new JRTableModelDataSource(dataModel) {            private final DateFormat dateFormetter = new SimpleDateFormat("dd/MM");            public Object getFieldValue(JRField jrField) throws JRException {                Object rtn = super.getFieldValue(jrField);                if (rtn == null) {                    rtn = "-";                } else if (rtn instanceof Date) {                    rtn = dateFormetter.format((Date) rtn);                }                return rtn.toString();            }        };    }    /**     * Compile the report and use JasperFillManager to fill the report with the required data.     *     * @return printed - the completed report     * @throws JRException on error     */    public JasperPrint compileAndPrintReport() throws JRException {        JRTableModelDataSource tableModel = getTableModel();        JasperReport report = JasperCompileManager.compileReport(this);        return JasperFillManager.fillReport(report, new HashMap<String, Object>(), tableModel);    }    /*    In Jtables it is easier to render mul;tilines using the HTMLCell renderer.    Unfortunately this does not work for JasperReports printing tables    so we need to translate the HTML into equivalent eg <BR> to "\n"    */    public static String stripHTML(String htmlString) {        String value = htmlString;        if (value.toUpperCase().indexOf("<HTML>") != -1) {            if (value.toUpperCase().indexOf("<BR>") != -1) {                value = htmlString.replaceAll("<[bB][rR]>", "\n");            }            value = value.replaceAll("<.*?>", "");            // if (logger.isDebugEnabled()) logger.debug("value = " + value);        }        return value;    }    // Test methods:    public static void main(String args[]) throws JRException {        // set up the map for testing purposes.        JTable table = makeTestData();        TableJasperDesign jasperDesign = new TableJasperDesign(table);        JasperPrint printed = jasperDesign.compileAndPrintReport();        JasperViewer.viewReport(printed);    }    private static JTable makeTestData() {        Vector<String> colNames = new Vector<String>();        colNames.add("Id");        colNames.add("FirstName");        colNames.add("LastName");        colNames.add("Street Address etc.");        colNames.add("City");        colNames.add("Country");        colNames.add("Telephone Number");        colNames.add("Postcode");        colNames.add("Date");        DateFormat df = new SimpleDateFormat();        Timestamp time = new Timestamp(System.currentTimeMillis());        String date = df.format(time);        TableModel rtn = new DefaultTableModel(colNames, 50);        int i = 1;        for (; i <= rtn.getRowCount(); ++i) {            //data.add(new TestVO(Integer.valueOf(i), "FirstName " + i, "LastName " + i, "Street " + i));            rtn.setValueAt(i, i - 1, 0);            rtn.setValueAt("<html>First Name " + i + "</html>", i - 1, 1);            rtn.setValueAt("<html>Last<br>Name " + i + "</html>", i - 1, 2);            rtn.setValueAt("Street Address " + i, i - 1, 3);            rtn.setValueAt("City " + i, i - 1, 4);            rtn.setValueAt("Country" + i, i - 1, 5);            rtn.setValueAt("Telephone Number" + i, i - 1, 6);            rtn.setValueAt("PCode " + i, i - 1, 7);            rtn.setValueAt(date, i - 1, 8);        }        return new JTable(rtn);    }}
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×
×
  • Create New...