2012-03-18 166 views
6

我想用android作爲前端和django上傳圖片作爲後端。Android-Django圖片上傳

模型

class Photo(models.Model): 
     title = models.CharField(max_length=255,blank=True) 
     photo = models.FileField(upload_to='photos') 
     description = models.TextField(blank=True) 
     uploaded = models.DateTimeField(auto_now_add=True) 
     modified = models.DateTimeField(auto_now=True) 

     class Meta: 
      db_table = 'media_photos' 

     def __unicode__(self): 
      return '%s' % self.title 

視圖以URL URL(R '^照片/上傳/ $', 'upload_photo'):

def upload_photo(request): 
form=PhotoForm(request.POST,request.FILES) 
if request.method=='POST': 
    if form.is_valid(): 
     image = request.FILES['photo'] 
     title1 ='' 
     new_image = Photo(title=title1,photo=image,description='') 
     new_image.save() 
     response_data=[{"success": "1"}] 
     return HttpResponse(simplejson.dumps(response_data), mimetype='application/json') 

我現在想從android訪問此處的視圖。 所以現在我的Android端代碼上傳圖片:

 public void doFileUpload(String path){ 
     HttpURLConnection conn = null; 
     DataOutputStream dos = null; 
     DataInputStream inStream = null; 
     String lineEnd = "\r\n"; 
     int bytesRead, bytesAvailable, bufferSize; 
     byte[] buffer; 
     int maxBufferSize = 1*1024*1024; 
     String urlString = "http://"; // server ip 
     try 
     { 
     //------------------ CLIENT REQUEST 
     FileInputStream fileInputStream = new FileInputStream(new File(path)); 
     // open a URL connection to the Servlet 
     URL url = new URL(urlString); 
     // Open a HTTP connection to the URL 
     conn = (HttpURLConnection) url.openConnection(); 
     // Allow Inputs 
     conn.setDoInput(true); 
     // Allow Outputs 
     conn.setDoOutput(true); 
     // Don't use a cached copy. 
     conn.setUseCaches(false); 
     // Use a post method. 
     conn.setRequestMethod("POST"); 
     conn.setRequestProperty("Connection", "Keep-Alive"); 
     conn.setRequestProperty("Content-Type", "multipart/form-data;boundary="+" "); 
     dos = new DataOutputStream(conn.getOutputStream()); 
     dos.writeBytes(lineEnd); 
     dos.writeBytes("Content-Disposition: form-data; name=\"uploadedfile\";filename=\"" + path + "\"" + lineEnd); 
     dos.writeBytes(lineEnd); 

     // create a buffer of maximum size 
     bytesAvailable = fileInputStream.available(); 
     bufferSize = Math.min(bytesAvailable, maxBufferSize); 
     buffer = new byte[bufferSize]; 

     // read file and write it into form... 
     bytesRead = fileInputStream.read(buffer, 0, bufferSize); 
     while (bytesRead > 0) 
     { 
      dos.write(buffer, 0, bufferSize); 
      bytesAvailable = fileInputStream.available(); 
      bufferSize = Math.min(bytesAvailable, maxBufferSize); 
      bytesRead = fileInputStream.read(buffer, 0, bufferSize); 
     } 

     // send multipart form data necesssary after file data... 
     dos.writeBytes(lineEnd); 
     dos.writeBytes(lineEnd); 

     // close streams 
     Log.e("Debug","File is written"); 
     fileInputStream.close(); 
     dos.flush(); 
     dos.close(); 
     } 
     catch (MalformedURLException ex) 
     { 
      Log.e("Debug", "error: " + ex.getMessage(), ex); 
     } 
     catch (IOException ioe) 
     { 
      Log.e("Debug", "error: " + ioe.getMessage(), ioe); 
     } 

     //------------------ read the SERVER RESPONSE 
     try { 
       inStream = new DataInputStream (conn.getInputStream()); 
       String str; 
       while ((str = inStream.readLine()) != null) 
       { 
        Log.e("Debug","Server Response "+str); 
       } 
       inStream.close(); 
     } 
     catch (IOException ioex){ 
      Log.e("Debug", "error: " + ioex.getMessage(), ioex); 
     } 
     } 
} 

,但它給我一個錯誤:

E/Debug(590): error: java.net.URISyntaxException: Authority expected at index 7: http:// 
+1

也許你應該添加一些真實的URL到'urlString =「http://」' – zapl 2012-03-18 14:23:20

+0

其實我已經添加了「private static String recordURL =」http://192.168.1.2/photos/upload/「;」這是調用這個上傳功能。但它仍然給我上面給出的錯誤 – user1163236 2012-03-18 17:15:03

+0

你使用你定義的字符串嗎? 'URL url = new URL(recordURL);' – zapl 2012-03-18 17:17:29

回答

2

應該urlString = "http://192.168.1.2/photos/upload";

不過,如果它不工作,你會得到一個不同的錯誤,我們可能需要這個錯誤來進一步回答。

此外,它看起來像你沒有一個真正的邊界字符串集,你沒有正確使用它。

http://stunningco.de/2010/04/25/uploading-files-to-http-server-using-post-android-sdk/,請注意他是如何使用唯一的邊界字符串,並將其寫入輸出流?

您應該開始將您的問題標記爲已回答。當你這樣做時,你會有更好的成功。

0

即使在克服了這些困難後,您也會遇到Django的要求,即您提供了一個帶有POST參數的csrfmiddlewaretoken。我不明白你在Android設備上如何獲得這些信息。通過設計該令牌可以防止從除Django前端(即,「模板」)以外的任何其他方面調用Django後端代碼(即「視圖」)。即它旨在阻止你正在做的事情。

您可以禁用特定視圖的csrf功能 - 使用「@csrf_exempt」修飾器。然後你可以決定你是否關心安全性,找出你自己的替代品,以確定csrf的東西給你帶來什麼。或者,而不是從Android應用程序上傳圖片,編寫一個Web應用程序上傳圖片,並讓您的Django項目提供該Web應用程序。您的Android應用可以啓動瀏覽器(作爲意圖)並將其指向該Web應用。這裏有一些代碼會這樣做:https://simpleisbetterthancomplex.com/tutorial/2016/08/01/how-to-upload-files-with-django.html(它不會贏得任何選美比賽,但它確實有效。)