Displaying image in Ireports using PostgreSql

2019-01-15 19:48发布

问题:

I am trying to load image from PostgreSQL database into jaspersoft ireports(4.0) but I am receiving an error.

In PostgreSQL image is stored as bytea object. In ireports I have changed the property of image field to java.io.InputStream.

After placing the image in report following properties were set:

Expression class: java.io.InputStream Image expression: image field

I also tried this tutorial to show blob images in ireport.

Following error is displayed:

Error filling print... Image read failed. 
Setting up the file resolver... 
net.sf.jasperreports.engine.JRException: Image read failed. 
    at net.sf.jasperreports.engine.util.JRJdk14ImageReader.readImage(JRJdk14ImageReader.java:73) 
    at net.sf.jasperreports.engine.util.JRImageLoader.loadImage(JRImageLoader.java:245) 
    at net.sf.jasperreports.engine.JRImageRenderer.getImage(JRImageRenderer.java:476) 
    at net.sf.jasperreports.engine.JRImageRenderer.getDimension(JRImageRenderer.java:512) 
    at net.sf.jasperreports.engine.fill.JRFillImage.fitImage(JRFillImage.java:1251) 
    at net.sf.jasperreports.engine.fill.JRFillImage.prepare(JRFillImage.java:1173) 
    at net.sf.jasperreports.engine.fill.JRFillElementContainer.prepareElements(JRFillElementContainer.java:329) 
    at net.sf.jasperreports.engine.fill.JRFillBand.fill(JRFillBand.java:419) 
    at net.sf.jasperreports.engine.fill.JRFillBand.fill(JRFillBand.java:378) 
    at net.sf.jasperreports.engine.fill.JRVerticalFiller.fillColumnBand(JRVerticalFiller.java:2038) 
    at net.sf.jasperreports.engine.fill.JRVerticalFiller.fillDetail(JRVerticalFiller.java:760) 
    at net.sf.jasperreports.engine.fill.JRVerticalFiller.fillReportStart(JRVerticalFiller.java:270) 
    at net.sf.jasperreports.engine.fill.JRVerticalFiller.fillReport(JRVerticalFiller.java:128) 
    at net.sf.jasperreports.engine.fill.JRBaseFiller.fill(JRBaseFiller.java:946) 
    at net.sf.jasperreports.engine.fill.JRBaseFiller.fill(JRBaseFiller.java:845) 
    at net.sf.jasperreports.engine.fill.JRFiller.fillReport(JRFiller.java:58) 
    at net.sf.jasperreports.engine.JasperFillManager.fillReport(JasperFillManager.java:417) 
    at net.sf.jasperreports.engine.JasperFillManager.fillReport(JasperFillManager.java:247) 
    at com.jaspersoft.ireport.designer.compiler.IReportCompiler.run(IReportCompiler.java:877) 
    at org.openide.util.RequestProcessor$Task.run(RequestProcessor.java:572) 
    at org.openide.util.RequestProcessor$Processor.run(RequestProcessor.java:997) 
Print not filled. Try to use an EmptyDataSource...

回答1:

In PostgreSQL the bytea type is not a BLOB, and you can't use a stream. In SQL standard terms it is a byte string. It should be loaded to a byte array in Java.

If you want to use BLOB techniques in PostgreSQL you must use the large objects feature.

http://www.postgresql.org/docs/current/interactive/largeobjects.html



回答2:

spending nearly one day, finally found the solution;

  1. in sql query select convert(your_image,'base64') as img from yourtable
  2. set image expression class to java.io.InputStream
  3. in image expression net.sf.jasperreports.engine.util.JRImageLoader.getInstance(new SimpleJasperReportsContext()).loadAwtImageFromBytes(javax.xml.bind.DatatypeConverter.parseBase64Binary($F{img}))

EDIT:

My Postgresql version is : 9.4,

Thanks to FiruzzZ he stated that in postgresql 9.1 instead of convert function, encode(bytea,'base64') is available.



回答3:

Displaying Image from blob (postgresql) to Image in iReport

In Postgresql image is stored as blob-oid
Code inside ReportController

  1. fetch that oid string from database convert it into byte
  2. convert byte array value in InputStream value
  3. map it to the parameter that will be used inside iReport
  4. take one Image element change its type to java.io.InputStream
  5. Create one parameter of type java.io.InputStream (use the same name as mapped inside ReportController)
  6. Now Build project and Run