经过多次尝试后我解决了它,我用的代码用来发送参数和图像:
public class PurchaseAsync extends AsyncTask<String, Void, Boolean> {
public static final String TAG = PurchaseAsync.class.getSimpleName();
public PurchaseAsync(ArrayList<CustomItem> parameters, String imageAddress, PurchaseListener listener){
this.parameters = parameters;
this.imageAddress = imageAddress;
this.listener = listener;
if(this.parameters == null){
this.parameters = new ArrayList<>();
}
LTH.dLog(WMH.WEBSERVICE, TAG + " -> Image path : " + imageAddress);
}
private String imageAddress = "";
// ========== Use HashMap, it works similar to NameValuePair
ArrayList<CustomItem> parameters = new ArrayList<>();
private PurchaseListener listener;
public interface PurchaseListener {
void execute(int exception, Boolean success, FactorItem msg);
}
private int customException = WMH.NO_EXCEPTION;
private FactorItem msg = new FactorItem();
@Override
protected void onPreExecute() {
progressDialog = ProgressDialog.show(App.getActivity(),
"", App.getContext().getString(R.string.pb_msg_purchase_request), true, false);
progressDialog.setCanceledOnTouchOutside(false);
super.onPreExecute();
}
private ProgressDialog progressDialog;
@Override
protected void onPostExecute(Boolean success) {
super.onPostExecute(success);
if(progressDialog != null){
progressDialog.dismiss();
}
LTH.dLog(WMH.WEBSERVICE, TAG + " -> customException : " + customException + " , Success : " + success);
if(listener != null){
listener.execute(customException, success, msg);
}
}
@Override
protected Boolean doInBackground(String... strings) {
customException = WMH.NO_EXCEPTION;
try{
String strResult = readData(strings[0]);
if(strResult.equals("")){
customException = customException == WMH.NO_EXCEPTION ? WMH.INVALID_EXCEPTION : customException;
return false;
}else{
JSONObject jsonObject = jsonParser(strResult);
if(jsonObject == null){
customException = customException == WMH.NO_EXCEPTION ? WMH.INVALID_EXCEPTION : customException;
return false;
}
pareFactor(jsonObject);
if (jsonObject.has("status")) {
return jsonObject.getBoolean("status");
} else {
customException = customException == WMH.NO_EXCEPTION ? WMH.INVALID_EXCEPTION : customException;
return false;
} // end of else/if
}
}catch (Exception e){
customException = customException == WMH.NO_EXCEPTION ? WMH.INVALID_EXCEPTION : customException;
LTH.eLog(WMH.JSON, TAG + " -> Exception Error In Json: " + e.getMessage(), e);
}
return false;
}
private void pareFactor(JSONObject iJsonObject) throws Exception{
if (iJsonObject.has("result")) {
if(iJsonObject.get("result") == null){
return;
}
if(!(iJsonObject.get("result") instanceof JSONObject)){
return;
}
JSONObject jsonObject = iJsonObject.getJSONObject("result");
if(jsonObject.has("code")){
String code = jsonObject.getString("code");
msg.setCode(code);
int fid;
try {
fid = Integer.parseInt(jsonObject.getString("fid"));
}catch (NumberFormatException nfe){
fid = 0;
// throw new Exception("Factor ID Not Assigned Correctly");
}
msg.setItemId(fid);
if(jsonObject.has("price_number")) {
String price_number = jsonObject.getString("price_number");
msg.setPayment(price_number);
msg.setTotal(price_number);
}
if(jsonObject.has("price")) {
int price;
try {
price = Integer.parseInt(jsonObject.getString("price"));
}catch (NumberFormatException nfe){
price = 0;
// throw new Exception("Factor ID Not Assigned Correctly");
}
msg.setPaymentPrice(price);
msg.setTotalPrice(price);
}
}
} else {
throw new Exception("Factor Information Not Assigned");
}
}
private JSONObject jsonParser(String strData) throws Exception{
if(!strData.equals("")){
JSONObject jsonObject = new JSONObject(strData);
return jsonObject.getJSONObject("posts");
}
return null;
}
private String readData(String strUrl){
LTH.dLog(WMH.WEBSERVICE, TAG + " -> readData, Address : " + strUrl);
// ========== Server Communication part - it's relatively long but uses standard methods
// ========== Encoded String - we will have to encode string by our custom method (Very easy)
String outPut = "";
String attachmentName = "image";
String attachmentFileName = "";
String crlf = "\r\n";
String twoHyphens = "--";
String boundary = "*****";
int bytesRead = 0, bytesAvailable, bufferSize;
int maxBufferSize = WMH.MAX_BUFFER_SIZE;
/*if(imageAddress.contains("/")){
attachmentFileName = imageAddress.substring(imageAddress.lastIndexOf("/")+1, imageAddress.length());
}*/
attachmentFileName = imageAddress;
LTH.dLog(WMH.WEBSERVICE, TAG + " -> Attachment Name : " + attachmentName);
try{
HttpURLConnection httpUrlConnection = null;
URL url = new URL(strUrl);
httpUrlConnection = (HttpURLConnection) url.openConnection();
httpUrlConnection.setUseCaches(false);
httpUrlConnection.setDoInput(true);
httpUrlConnection.setDoOutput(true);
httpUrlConnection.setRequestMethod("POST");
// httpUrlConnection.setRequestProperty("User-Agent", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_10_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/44.0.2403.155 Safari/537.36");
httpUrlConnection.setRequestProperty("Connection", "Keep-Alive");
httpUrlConnection.setRequestProperty("Cache-Control", "no-cache");
httpUrlConnection.setRequestProperty("ENCTYPE", "multipart/form-data");
httpUrlConnection.setRequestProperty("Content-Type", "multipart/form-data;boundary=" + boundary);
if(imageAddress.length() > 4) {
httpUrlConnection.setRequestProperty(attachmentName, attachmentFileName);
}
DataOutputStream request = new DataOutputStream(httpUrlConnection.getOutputStream());
request.writeBytes(twoHyphens + boundary + crlf);
if(imageAddress.length() > 4) {
request.writeBytes("Content-Disposition: form-data; name=\"" + attachmentName + "\";filename=\"" + attachmentFileName + "\"" + crlf);
request.writeBytes("Content-Type: image/*" + crlf);
request.writeBytes(crlf);
/*BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.ARGB_8888;
Bitmap bitmap = BitmapFactory.decodeFile(imageAddress, options);
byte[] pixels = new byte[bitmap.getWidth() * bitmap.getHeight()];
for (int i = 0; i < bitmap.getWidth(); ++i) {
for (int j = 0; j < bitmap.getHeight(); ++j) {
//we're interested only in the MSB of the first byte, since the other 3 bytes are identical for B&W images
pixels[i + j] = (byte) ((bitmap.getPixel(i, j) & 0x80) >> 7);
}
}
request.write(pixels);*/
// Code ...
FileInputStream fileInputStream = new FileInputStream(attachmentFileName);
bytesAvailable = fileInputStream.available();
bufferSize = Math.min(bytesAvailable, maxBufferSize);
byte[] buffer = new byte[bufferSize];
// read file and write it into form...
bytesRead = fileInputStream.read(buffer, 0, bufferSize);
while (bytesRead > 0) {
request.write(buffer, 0, bufferSize);
bytesAvailable = fileInputStream.available();
bufferSize = Math.min(bytesAvailable, maxBufferSize);
bytesRead = fileInputStream.read(buffer, 0, bufferSize);
}
// Code .
request.writeBytes(crlf);
request.writeBytes(twoHyphens + boundary + crlf);
}
// Added To Send Parameters
for(int i=0; i<parameters.size();i++){
String key = parameters.get(i).getTitle();
String value = "";
try {
value = URLEncoder.encode(parameters.get(i).getContent(), "UTF-8");
} catch (UnsupportedEncodingException e) {
LTH.eLog(TAG, e.getMessage(), e);
value = parameters.get(i).getContent();
}
LTH.dLog(WMH.WEBSERVICE, TAG + " -> " + key + " : " + value);
request.writeBytes("Content-Disposition: form-data; name=\""+key+"\"" + crlf);
request.writeBytes(crlf);
request.writeBytes(value);
request.writeBytes(crlf);
request.writeBytes(twoHyphens + boundary + crlf);
}
// request.writeBytes(twoHyphens + boundary + twoHyphens + crlf);
request.flush();
request.close();
int responseCode = httpUrlConnection.getResponseCode();
LTH.dLog(WMH.WEBSERVICE, TAG + " -> Response Code : " + responseCode + " , Response Message : " + httpUrlConnection.getResponseMessage());
if (responseCode == HttpsURLConnection.HTTP_OK) {
InputStream responseStream = new BufferedInputStream(httpUrlConnection.getInputStream());
BufferedReader responseStreamReader = new BufferedReader(new InputStreamReader(responseStream, Charset.forName("UTF-8")));
String line = "";
while ((line = responseStreamReader.readLine()) != null) {
outPut+=line;
}
responseStreamReader.close();
}
httpUrlConnection.disconnect();
} catch (Exception exception){
LTH.dLog(WMH.WEBSERVICE, TAG + " -> Error String OUTPUT Result : " + exception.getMessage(), exception);
return exception.toString();
}
LTH.dLog(WMH.WEBSERVICE, TAG + " -> String OUTPUT Result : " + outPut);
return outPut;
}
}
php:
$item = new stdclass();
$item->image = $_FILES['image'];
$imageFileType = pathinfo($_FILES['image'],PATHINFO_EXTENSION);
$check = getimagesize($_FILES['image']["tmp_name"]);
if($check !== false) {
$item->file_status = "File is an image - " . $check["mime"] . ".";
} else {
$item->file_status = "File is not an image.";
}
$item->imageFileType = $imageFileType;
$item->file_check = $check;
$results_array['msg'] = 'Test';
$results_array['status'] = false;
$results_array['result'] = $item;
echo $ws->unicodeString(json_encode(array('posts'=>($results_array))), 'UTF-8');
参数已成功接收文件,但请记住attachmentFileName
如果full file path
。
答案 0 :(得分:7)
我在Android上写了一篇关于Multipart请求的博客。我已经清楚地解释了多部分请求的结构,正文中每个单独的文本意味着什么,如何在android中自己构建一个(带代码),以及它如何与你在帖子中自动生成的那个相似来自firefox等浏览器的服务,以及如何在JSP和java rest API中使用webrequest。一瞥:) Is Multipart request complicated? Think again.
修改
首先要做的事情:)正如名字所暗示的那样,多部分表单数据只是包含多个部分的单个请求:) 示例:这是由firefox生成的多部分请求:)
------WebKitFormBoundaryQHJL2hsKnlU26Mm3
Content-Disposition: form-data; name="profilePic"; filename="66.jpg"
Content-Type: application/octet-stream
//your image data appears here
------WebKitFormBoundaryQHJL2hsKnlU26Mm3
Content-Disposition: form-data; name="testingName"
Myfile.jpg //file name sent as parameter you can pass whatever parameter you want :)
------WebKitFormBoundaryQHJL2hsKnlU26Mm3--
你能看到吗???有两个部分,一个包含一个jpg文件,另一个包含一个字符串(表单数据):)
在您的情况下,一个部分将包含图像,其他部分将包含其余参数。因此,为了通知服务器哪个部分包含您将以正确格式创建请求的内容:)在您的情况下,第一部分让我们假设图像。
DataOutputStream dos = new DataOutputStream(con.getOutputStream());
dos.writeBytes(twoHyphens + boundary + lineEnd);
dos.writeBytes("Content-Disposition: form-data; name=\"image\";filename=\"" + imageAddress +"\"" + lineEnd);
dos.writeBytes("Content-Type: image/jpeg" + lineEnd);
dos.writeBytes(lineEnd);
dos.write(byteArray);//your image array here buddy
dos.writeBytes(lineEnd);
dos.writeBytes(twoHyphens + boundary + lineEnd);
dos.writeBytes("Content-Disposition: form-data; name=\"your parameter name\"" + crlf);
dos.writeBytes(lineEnd);
dos.writeBytes(testName);//your parameter value
dos.writeBytes(lineEnd); //to add multiple parameters write Content-Disposition: form-data; name=\"your parameter name\"" + crlf again and keep repeating till here :)
dos.writeBytes(twoHyphens + boundary + twoHyphens);
dos.flush();
dos.close();
你有没有看到你缺少的是它的内容类型:)预先指定内容类型你需要输入行结束(你能看到firefox生成的多部分表单请求)
指定图像内容后,您需要启动第二部分,所以再次输入新行:) 然后使用twoHyphens + boundary + crlf指定新节的开头 使用Content-Disposition:form-data再次指定内容类型:) name = \“您的参数名称\
输入新行添加参数并再次输入新行并再次使用换行关闭该行。
重复它,直到你添加所有参数(严重的是我更喜欢创建所有参数的json并将其作为一个部分发送),然后用twoHyphens + boundary + twoHyphens关闭multipart请求
多数民众赞成:)你现在得到了你的错误吗? :)
总结:您必须创建一个multipart-formdata请求,使其与我从fire fox浏览器发布的multipart-formdata的结构完全匹配:)
因此,如果您看到我发布的代码,只是按照模板进行操作并按照模板添加文本:)相信我服务器支持它因为浏览器不会出错你知道:))
仍有疑问问我:)在这里帮助。我粘贴的上面的代码不仅仅是一个逻辑的,它实际上来自工作代码:)