简体   繁体   English

使用Jersey客户端向请求正文获取OuputStream?

[英]Get an OuputStream to a request body using Jersey Client?

I wan't to post a CSV file to a web service using the Jersey Client without having to buffer the csv content in memory. 我不想使用Jersey客户端将CSV文件发布到Web服务,而不必在内存中缓冲csv内容。

So I started of with some code similar to this: 所以我开始使用类似于此的一些代码:

String csvContent = [the buffered CSV content];
Client c = Client.create();
WebResource r = c.resouce("http://example.com/services/service");
r.type("text/csv").post(csvContent);

I would like to avoid buffering the entire CSV content in memory before sending to the server, I am aware that I can send a File object using the client and jersey will deal with loading and sending the file, however in this case the CSV content will be generated automatically so what I would really like to do is just simply write it to an OutputStream which goes directly to the server rather than into memory... is there a way I can do this using the Jersey client? 我想避免在发送到服务器之前缓冲内存中的整个CSV内容,我知道我可以使用客户端发送File对象,并且jersey将处理加载和发送文件,但是在这种情况下CSV内容将自动生成所以我真正想做的只是简单地将它写入一个直接进入服务器而不是内存的OutputStream ......有没有办法可以使用Jersey客户端来做到这一点?

It seems Jersey doesn't support writing direct to the OutputStream however after much digging and merging of a few different thinks I learned along the way I managed to come up with this class. 似乎泽西岛并不支持直接写出OutputStream,但经过多次挖掘和合并之后,我学到了很多东西,我设法提出了这个课程。

Jersey supports passing an InputStream into the post method on WebResource which is read and the content written to the request body. Jersey支持将InputStream传递给WebResource上的post方法,该方法被读取并且内容被写入请求主体。

I am producing a CSV file from a ResultSet so I wrote a class that extends InputStream and when read() is called it gets a record from the ResultSet and builds a line of the CSV file and returns just one character from the line. 我正在从ResultSet生成一个CSV文件,所以我编写了一个扩展InputStream的类,当调用read()时,它从ResultSet获取一条记录并构建一行CSV文件并从该行返回一个字符。 Each time read() is called the next character is returned until the whole line is returned at which point the next record is read from the database and the process repeated until there are no records left. 每次调用read()时,都会返回下一个字符,直到返回整行,此时从数据库中读取下一条记录并重复该过程,直到没有记录为止。

I am using a library called OpenCSV to build the lines of the CSV file 我正在使用一个名为OpenCSV的库来构建CSV文件的行

public class ResultSetCsvInputStream extends InputStream {

 private ResultSet rs;
 private int columns;

 private int ch;
 private byte[] line;

 /**
  * Construct a new SchemaInputStream
  * @param rs
  * @throws SQLException 
  */
 public ResultSetCsvInputStream(ResultSet rs) throws SQLException {

  this.rs = rs;

  // write column names
  ResultSetMetaData meta = rs.getMetaData();
  columns = meta.getColumnCount();
  String[] colNames = new String[columns];
  for(int i = 0; i < colNames.length; i++) {
   colNames[i] = meta.getColumnName(i+1);
  }
  writeLine(colNames);

 }

 private void writeLine(String[] ln) {
  StringWriter strWriter = new StringWriter();
  CSVWriter csv = new CSVWriter(strWriter);
  csv.writeNext(ln);
  line = strWriter.toString().getBytes(Charset.forName("UTF8"));
  ch = 0;
 }

 @Override
 public int read() throws IOException {

  if(rs == null)
   return -1;

  // read the next line
  if(line == null || ch >= line.length) {

   // query next line
   try {
    if(rs.next()) {
     String[] record = new String[columns];
     for(int i = 0; i < record.length; i++) {
      record[i] = rs.getString(i+1);
     }
     writeLine(record);
    }
    else {
     rs = null;
     return -1;
    }
   } catch (SQLException e) {
    throw new IOException(e);
   }

  }

  // read next character
  return line[ch++] & 0xFF;

 }

}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM