如何在jsp页面中检索和显示数据库中的图像?
yyhrrdl81#
让我们分步看看应该发生什么:jsp基本上是一种生成html输出的视图技术。要用html显示图像,需要html <img> 元素。要让它定位一个图像,您需要指定它的位置 src 属性。这个 src 属性需要指向有效的 http:// 因此不是本地磁盘文件系统路径 file:// 因为当服务器和客户机在物理上不同的机器上运行时,这是行不通的。图像url需要在请求路径(例如。 http://example.com/context/images/foo.png )或作为请求参数(例如。 http://example.com/context/images?id=1 ).在jsp/servlet世界中,您可以让servlet监听特定的url模式,如 /images/* ,这样您就可以在特定的url上执行一些java代码。图像是二进制数据,可以作为 byte[] 或者 InputStream 在数据库中,jdbcapi提供 ResultSet#getBytes() 以及 ResultSet#getBinaryStream() 为此,jpaapi提供了 @Lob 为了这个。在servlet中,您可以编写 byte[] 或者 InputStream 到 OutputStream 通常的javaio方式的响应。需要指示客户端将数据作为图像处理,因此至少 Content-Type 还需要设置响应头。您可以通过 ServletContext#getMimeType() 基于图像文件扩展名,您可以通过 <mime-mapping> 在 web.xml .应该是这样。它几乎自己写代码。让我们从html(在jsp中)开始:
<img>
src
http://
file://
http://example.com/context/images/foo.png
http://example.com/context/images?id=1
/images/*
byte[]
InputStream
ResultSet#getBytes()
ResultSet#getBinaryStream()
@Lob
OutputStream
Content-Type
ServletContext#getMimeType()
<mime-mapping>
web.xml
<img src="${pageContext.request.contextPath}/images/foo.png"> <img src="${pageContext.request.contextPath}/images/bar.png"> <img src="${pageContext.request.contextPath}/images/baz.png">
如果需要,还可以动态设置 src 在使用jstl迭代时使用el:
<c:forEach items="${imagenames}" var="imagename"> <img src="${pageContext.request.contextPath}/images/${imagename}"> </c:forEach>
然后定义/创建一个servlet,该servlet侦听的url模式上的get请求 /images/* ,下面的示例使用普通的jdbc进行作业:
@WebServlet("/images/*") public class ImageServlet extends HttpServlet { // content=blob, name=varchar(255) UNIQUE. private static final String SQL_FIND = "SELECT content FROM Image WHERE name = ?"; @Resource(name="jdbc/yourDB") // For Tomcat, define as <Resource> in context.xml and declare as <resource-ref> in web.xml. private DataSource dataSource; @Override protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { String imageName = request.getPathInfo().substring(1); // Returns "foo.png". try (Connection connection = dataSource.getConnection(); PreparedStatement statement = connection.prepareStatement(SQL_FIND)) { statement.setString(1, imageName); try (ResultSet resultSet = statement.executeQuery()) { if (resultSet.next()) { byte[] content = resultSet.getBytes("content"); response.setContentType(getServletContext().getMimeType(imageName)); response.setContentLength(content.length); response.getOutputStream().write(content); } else { response.sendError(HttpServletResponse.SC_NOT_FOUND); // 404. } } } catch (SQLException e) { throw new ServletException("Something failed at SQL/DB level.", e); } } }
就这样。如果您担心head和缓存头以及对这些请求的正确响应,请将此抽象模板用于静态资源servlet。
在基于servlet的应用程序中,我应该如何连接到jdbc数据库/数据源?如何上传图片并保存到数据库中?在javaweb应用程序中从应用服务器外部提供静态数据的最简单方法
ozxc1zmp2#
我建议你把这当作两个问题来处理。有几个问题和答案都与这两者有关。如何从mysql加载blob例如,请参见检索存储为blob的图像如何动态显示图像例如,请参见动态显示缩略图
eqoofvh93#
如果输出流不显示,请尝试刷新并关闭它。Blob image = rs.getBlob(ImageColName); InputStream in = image.getBinaryStream(); //将blob输出到httpservletresponseresponse.setContentType("image/jpeg"); BufferedOutputStream o = new BufferedOutputStream(response.getOutputStream()); ```byte by[] = new byte[32768];int index = in.read(by, 0, 32768);while (index != -1) {o.write(by, 0, index);index = in.read(by, 0, 32768);}o.flush();o.close();
InputStream in = image.getBinaryStream();
BufferedOutputStream o = new BufferedOutputStream(response.getOutputStream());
wgxvkvu94#
您还可以创建用于显示图像的自定义标记。1) 创建自定义标记java类和tld文件。2) 写入逻辑以显示按base64将字节[]转换为字符串的图像。因此,无论您是在单个jsp页面中仅显示一个图像还是显示多个图像,它都用于每个图像。
sigwle7e5#
我用的是sqlserver数据库,所以答案的代码是一致的。你所要做的就是包括一个 <img> 在jsp页面中添加标签,并从其src属性调用servlet,如下所示
<img width="200" height="180" src="DisplayImage?ID=1">
这里1是数据库中图像的唯一id,id是一个变量。我们在servlet中接收这个变量的值。在servlet代码中,我们从表中正确的列获取二进制流输入。即您的图像存储在哪个列中。在我的代码中,我使用了第三列,因为我的图像作为二进制数据存储在第三列中。从表中检索输入流数据后,我们在输出流中读取它的内容,这样就可以在屏幕上写入了。给你
import java.io.*; import java.sql.Connection; import java.sql.ResultSet; import java.sql.SQLException; import java.sql.Statement; import java.util.logging.Level; import java.util.logging.Logger; import javax.servlet.*; import javax.servlet.http.*; import model.ConnectionManager; public class DisplayImage extends HttpServlet { public void doGet(HttpServletRequest request,HttpServletResponse response) throws IOException { Statement stmt=null; String sql=null; BufferedInputStream bin=null; BufferedOutputStream bout=null; InputStream in =null; response.setContentType("image/jpeg"); ServletOutputStream out; out = response.getOutputStream(); Connection conn = ConnectionManager.getConnection(); int ID = Integer.parseInt(request.getParameter("ID")); try { stmt = conn.createStatement(); sql = "SELECT * FROM IMAGETABLE WHERE ID="+ID+""; ResultSet result = stmt.executeQuery(sql); if(result.next()){ in=result.getBinaryStream(3);//Since my data was in third column of table. } bin = new BufferedInputStream(in); bout = new BufferedOutputStream(out); int ch=0; while((ch=bin.read())!=-1) { bout.write(ch); } } catch (SQLException ex) { Logger.getLogger(DisplayImage.class.getName()).log(Level.SEVERE, null, ex); }finally{ try{ if(bin!=null)bin.close(); if(in!=null)in.close(); if(bout!=null)bout.close(); if(out!=null)out.close(); if(conn!=null)conn.close(); }catch(IOException | SQLException ex){ System.out.println("Error : "+ex.getMessage()); } } } }
在执行jsp或html文件之后,您将看到屏幕上的图像。
5条答案
按热度按时间yyhrrdl81#
让我们分步看看应该发生什么:
jsp基本上是一种生成html输出的视图技术。
要用html显示图像,需要html
<img>
元素。要让它定位一个图像,您需要指定它的位置
src
属性。这个
src
属性需要指向有效的http://
因此不是本地磁盘文件系统路径file://
因为当服务器和客户机在物理上不同的机器上运行时,这是行不通的。图像url需要在请求路径(例如。
http://example.com/context/images/foo.png
)或作为请求参数(例如。http://example.com/context/images?id=1
).在jsp/servlet世界中,您可以让servlet监听特定的url模式,如
/images/*
,这样您就可以在特定的url上执行一些java代码。图像是二进制数据,可以作为
byte[]
或者InputStream
在数据库中,jdbcapi提供ResultSet#getBytes()
以及ResultSet#getBinaryStream()
为此,jpaapi提供了@Lob
为了这个。在servlet中,您可以编写
byte[]
或者InputStream
到OutputStream
通常的javaio方式的响应。需要指示客户端将数据作为图像处理,因此至少
Content-Type
还需要设置响应头。您可以通过ServletContext#getMimeType()
基于图像文件扩展名,您可以通过<mime-mapping>
在web.xml
.应该是这样。它几乎自己写代码。让我们从html(在jsp中)开始:
如果需要,还可以动态设置
src
在使用jstl迭代时使用el:然后定义/创建一个servlet,该servlet侦听的url模式上的get请求
/images/*
,下面的示例使用普通的jdbc进行作业:就这样。如果您担心head和缓存头以及对这些请求的正确响应,请将此抽象模板用于静态资源servlet。
另请参见:
在基于servlet的应用程序中,我应该如何连接到jdbc数据库/数据源?
如何上传图片并保存到数据库中?
在javaweb应用程序中从应用服务器外部提供静态数据的最简单方法
ozxc1zmp2#
我建议你把这当作两个问题来处理。有几个问题和答案都与这两者有关。
如何从mysql加载blob
例如,请参见检索存储为blob的图像
如何动态显示图像
例如,请参见动态显示缩略图
eqoofvh93#
如果输出流不显示,请尝试刷新并关闭它。
Blob image = rs.getBlob(ImageColName);
InputStream in = image.getBinaryStream();
//将blob输出到httpservletresponseresponse.setContentType("image/jpeg");
BufferedOutputStream o = new BufferedOutputStream(response.getOutputStream());
```byte by[] = new byte[32768];
int index = in.read(by, 0, 32768);
while (index != -1) {
o.write(by, 0, index);
index = in.read(by, 0, 32768);
}
o.flush();
o.close();
wgxvkvu94#
您还可以创建用于显示图像的自定义标记。
1) 创建自定义标记java类和tld文件。
2) 写入逻辑以显示按base64将字节[]转换为字符串的图像。
因此,无论您是在单个jsp页面中仅显示一个图像还是显示多个图像,它都用于每个图像。
sigwle7e5#
我用的是sqlserver数据库,所以答案的代码是一致的。你所要做的就是包括一个
<img>
在jsp页面中添加标签,并从其src属性调用servlet,如下所示这里1是数据库中图像的唯一id,id是一个变量。我们在servlet中接收这个变量的值。在servlet代码中,我们从表中正确的列获取二进制流输入。即您的图像存储在哪个列中。在我的代码中,我使用了第三列,因为我的图像作为二进制数据存储在第三列中。从表中检索输入流数据后,我们在输出流中读取它的内容,这样就可以在屏幕上写入了。给你
在执行jsp或html文件之后,您将看到屏幕上的图像。