Java Servlet图像上载已损坏(灰色底部)

Java Servlet图像上载已损坏(灰色底部),java,image,servlets,upload,corruption,Java,Image,Servlets,Upload,Corruption,我们有一个接受图像上传的servlet。有时,当上传源于我们的iPhone客户端(脆弱的连接)时,保存的图像可能会部分或完全变成灰色。我怀疑这是由于连接被提前终止,servlet最终处理的是一个不完整的映像 最好的治疗方法是什么?是否有办法在处理之前查看整个图像是否已上载?我应该使用HTTP内容长度头并将上载的内容与此数字进行比较吗 谢谢 上下文的一些代码: @Path("images/") @POST @Consumes("image/*") @Produces({"application/x

我们有一个接受图像上传的servlet。有时,当上传源于我们的iPhone客户端(脆弱的连接)时,保存的图像可能会部分或完全变成灰色。我怀疑这是由于连接被提前终止,servlet最终处理的是一个不完整的映像

最好的治疗方法是什么?是否有办法在处理之前查看整个图像是否已上载?我应该使用HTTP内容长度头并将上载的内容与此数字进行比较吗

谢谢

上下文的一些代码:

@Path("images/")
@POST
@Consumes("image/*")
@Produces({"application/xml", "application/json"})
public AbstractConverter postImage(byte[] imageData) {

    BufferedImage bufferedImage = null;
    try {
        bufferedImage = ImageIO.read(new ByteArrayInputStream(imageData));
    } catch (Exception e) {
    }
    if (bufferedImage == null) {
        throw new PlacesException("Image data not provided or could not be parsed", Response.Status.BAD_REQUEST);
    }

...

    BufferedImage scaledImage = ImageTool.scale(bufferedImage, imageSize);
    BufferedImage thumbnail = ImageTool.scale(bufferedImage, thumbnailSize);

    //Save image and thumbnail
    File outputfile = new File(path);
    ImageTool.imageToJpegFile(scaledImage, outputfile, 0.9f);
    File tnOutputfile = new File(thumbnailPath);
    ImageTool.imageToJpegFile(thumbnail, tnOutputfile, 0.9f);

...

public static void imageToJpegFile(RenderedImage image, File outFile, float compressionQuality) throws IOException {

    //Find a jpeg writer
    ImageWriter writer = null;
    Iterator<ImageWriter> iterator = ImageIO.getImageWritersByFormatName("jpeg");
    if (iterator.hasNext()) {
        writer = iterator.next();
    } else {
        throw new RuntimeException("No jpeg writer found");
    }


    //Set the compression quality
    ImageWriteParam params = writer.getDefaultWriteParam();
    params.setCompressionMode(ImageWriteParam.MODE_EXPLICIT);
    params.setCompressionQuality(compressionQuality);

    //Write to the out file
    ImageOutputStream ios = null;
    try {
        ios = ImageIO.createImageOutputStream(outFile);
        writer.setOutput(ios);
        writer.write(null, new IIOImage(image, null, null), params);

    } finally {
        writer.dispose();
        if (ios != null) {
            try {
                ios.flush();
            } catch (Exception e) {
            }
            try {
                ios.close();
            } catch (Exception e) {
            }
        }

    }
}
@Path(“images/”)
@职位
@消费(“图像/*”)
@产生({“application/xml”、“application/json”})
公共抽象转换器后映像(字节[]图像数据){
BuffereImage BuffereImage=null;
试一试{
BuffereImage=ImageIO.read(新的ByteArrayInputStream(imageData));
}捕获(例外e){
}
if(buffereImage==null){
抛出新的PlacesException(“未提供图像数据或无法分析图像数据”,Response.Status.BAD_请求);
}
...
BuffereImage ScaleImage=ImageTool.scale(BuffereImage,imageSize);
BuffereImage缩略图=ImageTool.scale(BuffereImage,thumbnailSize);
//保存图像和缩略图
文件输出文件=新文件(路径);
ImageTool.ImageToJPEG文件(ScaleImage,outputfile,0.9f);
File tnOutputfile=新文件(thumbnailPath);
ImageTool.ImageToJPEG文件(缩略图,tnOutputfile,0.9f);
...
公共静态void ImageToJPEG文件(渲染图像、文件输出文件、浮点压缩质量)引发IOException{
//查找jpeg编写器
ImageWriter=null;
迭代器迭代器=ImageIO.getImageWritersByFormatName(“jpeg”);
if(iterator.hasNext()){
writer=iterator.next();
}否则{
抛出新的RuntimeException(“未找到jpeg编写器”);
}
//设置压缩质量
ImageWriteParam参数=writer.getDefaultWriteParam();
参数setCompressionMode(ImageWriteParam.MODE_显式);
参数设置压缩质量(压缩质量);
//写入输出文件
ImageOutputStream ios=null;
试一试{
ios=ImageIO.createImageOutputStream(输出文件);
writer.setOutput(ios);
writer.write(null,新IIOImage(image,null,null),params);
}最后{
writer.dispose();
如果(ios!=null){
试一试{
ios.flush();
}捕获(例外e){
}
试一试{
ios.close();
}捕获(例外e){
}
}
}
}

似乎上载未正确完成


正如您自己指出的,您最好使用HTTP
Content-Length
标题检查是否已收到所有数据。如果未收到,则丢弃图像。

这就是我在写问题时得出的结论(以及我最终所做的)。我想没有切实可行的方法来检查图像的完整性,检查总和或其他。好吧,你可以在手机上生成图像的哈希值,然后先上传,然后在服务器上重新计算哈希值。如果存在差异,那么即使长度正确,图像也会损坏(当然不应该发生这种情况)@Oskar:我想你可以计算一个校验和或其他哈希(例如MD5)在客户端中,将其与映像一起发送,并在服务器端验证。但是,检查内容长度应该更容易——如果您收到的字节数与预期的相同,则可以相信数据是正确的。TCP已经丢弃了校验和错误的包。