Я пытаюсь подключиться к службе REST, которая принимает объект json и изображение и возвращает текст с изображения (после OCR).Подключиться к службе REST в Android через многопользовательский запрос с помощью JSON
documentation службы REST утверждает, что запрос должен мне подобное:
-----BOUNDARY
Content-Type: application/json
{"engine":"tesseract"}
-----BOUNDARY
-----BOUNDARY
Content-Disposition: attachment;
Content-Type: image/png
filename="attachment.txt".
PNGDATA.........
-----BOUNDARY
Так я говорил this tutorial и изменил код, когда я запускаю код дает мне следующее сообщение об ошибке:
W/System.err: java.io.IOException: unexpected end of stream on Connection{192.168.0.102:8080, [email protected] hostAddress=192.168.0.102 cipherSuite=none protocol=http/1.1} (recycle count=0)
Ниже приведены содержание моего MultipartUtility.java файл
import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.List;
/**
* For sending Multipart requests: modified for OCR
*http://www.codejava.net/java-se/networking/upload-files-by-sending-multipart-request-programmatically
*
*/
public class MultipartUtility {
private final String boundary;
private static final String LINE_FEED = "\r\n";
private HttpURLConnection httpConn;
private String charset;
private OutputStream outputStream;
private PrintWriter writer;
/**
* This constructor initializes a new HTTP POST request with content type
* is set to multipart/form-data
* @param requestURL
* @param charset
* @throws IOException
*/
public MultipartUtility(String requestURL, String charset)
throws IOException {
this.charset = charset;
boundary = "---BOUNDARY";
URL url = new URL(requestURL);
httpConn = (HttpURLConnection) url.openConnection();
httpConn.setUseCaches(false);
httpConn.setDoOutput(true); // indicates POST method
httpConn.setDoInput(true);
httpConn.setRequestProperty("Content-Type",
"multipart/related; boundary=" + boundary);
// httpConn.setRequestProperty("User-Agent", "CodeJava Agent");
// httpConn.setRequestProperty("Test", "Bonjour");
outputStream = httpConn.getOutputStream();
writer = new PrintWriter(new OutputStreamWriter(outputStream, charset),
true);
}
/**
* Adds a form field to the request
*
*/
public void addFormField() {
writer.append(boundary).append(LINE_FEED);
// writer.append("Content-Disposition: form-data; name=\"" + name + "\"")
// .append(LINE_FEED);
writer.append("Content-Type: application/json").append(LINE_FEED);
writer.append(LINE_FEED);
writer.append("{\"engine\":\"tesseract\"}").append(LINE_FEED);
writer.append(boundary).append(LINE_FEED);
writer.flush();
}
/**
* Adds a upload file section to the request
* @param fieldName name attribute in <input type="file" name="..." />
* @param uploadFile a File to be uploaded
* @throws IOException
*/
public void addFilePart(String fieldName, File uploadFile)
throws IOException {
String fileName = uploadFile.getName();
writer.append(boundary).append(LINE_FEED);
writer.append("Content-Disposition: attachment;")
.append(LINE_FEED);
writer.append("Content-Type: image/png").append(LINE_FEED);
writer.append("filename="+fileName+".").append(LINE_FEED);
writer.append(LINE_FEED);
//adding png data here
FileInputStream inputStream = new FileInputStream(uploadFile);
byte[] buffer = new byte[4096];
int bytesRead = -1;
while ((bytesRead = inputStream.read(buffer)) != -1) {
outputStream.write(buffer, 0, bytesRead);
}
outputStream.flush();
inputStream.close();
writer.append(boundary).append(LINE_FEED);
writer.flush();
}
/**
* Adds a header field to the request.
* @param name - name of the header field
* @param value - value of the header field
*/
public void addHeaderField(String name, String value) {
writer.append(name + ": " + value).append(LINE_FEED);
writer.flush();
}
/**
* Completes the request and receives response from the server.
* @return a list of Strings as response in case the server returned
* status OK, otherwise an exception is thrown.
* @throws IOException
*/
public List<String> finish() throws IOException {
List<String> response = new ArrayList<>();
// writer.append(LINE_FEED).flush();
// writer.append("--" + boundary + "--").append(LINE_FEED);
writer.close();
// checks server's status code first
int status = httpConn.getResponseCode();
if (status == HttpURLConnection.HTTP_OK) {
BufferedReader reader = new BufferedReader(new InputStreamReader(
httpConn.getInputStream()));
String line = null;
while ((line = reader.readLine()) != null) {
response.add(line);
}
reader.close();
httpConn.disconnect();
} else {
throw new IOException("Server returned non-OK status: " + status);
}
return response;
}
}
Я использую этот MultipartUtility в моем MainActivty.java файла:
import android.Manifest;
import android.content.pm.PackageManager;
import android.os.AsyncTask;
import android.os.Build;
import android.os.Environment;
import android.support.v4.app.ActivityCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import java.io.File;
import java.io.IOException;
import java.util.List;
public class MainActivity extends AppCompatActivity {
//OkHttpClient client;
String serverUrl = "http://192.168.0.102:8080/ocr-file-upload";
String imgUrl;
String TAG = "MainAcivity";
TextView tvMain;
File uploadFile1;
String charset = "UTF-8";
Button btn_make_request;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
btn_make_request = (Button) findViewById(R.id.btn_make_request);
tvMain = (TextView) findViewById(R.id.tv_main);
// client = new OkHttpClient();
imgUrl = Environment
.getExternalStorageDirectory().toString()+"/ocr_test.png";
uploadFile1 = new File(imgUrl);
btn_make_request.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if(isStoragePermissionGranted())
new UploadImage().execute();
else
Toast.makeText(MainActivity.this, "PERMISSION PROBLEM", Toast.LENGTH_SHORT).show();
}
});
}//edn oncreate
private class UploadImage extends AsyncTask<String, Void, String> {
@Override
protected String doInBackground(String... strings) {
Log.v(TAG, "IN DO IN BACKGROUND");
// upload(serverUrl);
doMultipartOcr();
//doRequest();
return null;
}
}
public void doMultipartOcr(){
try {
MultipartUtility multipart = new MultipartUtility(serverUrl, charset);
// multipart.addHeaderField("Content-Type", "multipart/related");
// multipart.addHeaderField("boundary=", "---BOUNDARY");
multipart.addFormField();
multipart.addFilePart("fileUpload", uploadFile1);
List<String> response = multipart.finish();
for (String line : response) {
//TODO: display Output
tvMain.setText(tvMain.getText() + "\n" + line);
}
} catch (IOException ex) {
//TODO: display error
Log.v(TAG, ex.getMessage());
ex.printStackTrace();
}
}
public boolean isStoragePermissionGranted() {
if (Build.VERSION.SDK_INT >= 23) {
if (checkSelfPermission(android.Manifest.permission.WRITE_EXTERNAL_STORAGE)
== PackageManager.PERMISSION_GRANTED) {
Log.v(TAG,"Permission is granted");
return true;
} else {
Log.v(TAG,"Permission is revoked");
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, 1);
return false;
}
}
else { //permission is automatically granted on sdk<23 upon installation
Log.v(TAG,"Permission is granted");
return true;
}
}
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
if(grantResults[0]== PackageManager.PERMISSION_GRANTED){
Log.v(TAG,"Permission: "+permissions[0]+ "was "+grantResults[0]);
//resume tasks needing this permission
}
}
}
Я новичок в андроид развития, и я пытаюсь понять, как использовать эту REST веб-сервис в моем приложении формы последние 2-3 дня, но я не могу заставить его работать.
Также, пожалуйста, дайте мне знать, если есть лучший/более простой способ использования this web службы в Android-приложении.
Спасибо.