Http Post kullanarak görüntü gönderme


129

Http Post kullanarak android istemciden Django sunucusuna bir resim göndermek istiyorum. Resim galeriden seçilmiştir. Şu anda, gerekli verileri sunucuya göndermek ve JSON'da Django'dan yanıtlar almak için liste değeri adı Çiftleri kullanıyorum. Görüntüler için aynı yaklaşım kullanılabilir mi (JSON yanıtlarına gömülü görüntülerin url'leri ile)?

Ayrıca hangisi daha iyi bir yöntemdir: görüntülere sunucudan indirmeden uzaktan erişmek veya bunları bir Bitmap dizisinde indirip depolamak ve bunları yerel olarak kullanmak? Görüntüler sayıca az (<10) ve boyut olarak küçüktür (50 * 50 dip).

Bu sorunların üstesinden gelmek için herhangi bir öğretici çok takdir edilecektir.

Düzenle: Galeriden seçilen resimler istenilen boyuta ölçeklendikten sonra sunucuya gönderilir.

Yanıtlar:


144

Yüklemek istediğiniz görüntünün yolunu ve dosya adını bildiğinizi varsayacağım. Bu dizeyi anahtar adı olarak NameValuePairkullanmanıza ekleyin image.

Görüntü gönderme, HttpComponents kitaplıkları kullanılarak yapılabilir . Son HttpClient (şu anda indirin 4.0.1 bağımlılıkları paketi ile) ikilisini ve kopyalamak apache-mime4j-0.6.jarve httpmime-4.0.1.jarprojenize ve Java inşa yoluna ekleyin.

Aşağıdaki içe aktarmaları sınıfınıza eklemeniz gerekecek.

import org.apache.http.entity.mime.HttpMultipartMode;
import org.apache.http.entity.mime.MultipartEntity;
import org.apache.http.entity.mime.content.FileBody;
import org.apache.http.entity.mime.content.StringBody;

Artık MultipartEntityPOST isteğinize bir resim eklemek için bir oluşturabilirsiniz . Aşağıdaki kod, bunun nasıl yapılacağına dair bir örnek gösterir:

public void post(String url, List<NameValuePair> nameValuePairs) {
    HttpClient httpClient = new DefaultHttpClient();
    HttpContext localContext = new BasicHttpContext();
    HttpPost httpPost = new HttpPost(url);

    try {
        MultipartEntity entity = new MultipartEntity(HttpMultipartMode.BROWSER_COMPATIBLE);

        for(int index=0; index < nameValuePairs.size(); index++) {
            if(nameValuePairs.get(index).getName().equalsIgnoreCase("image")) {
                // If the key equals to "image", we use FileBody to transfer the data
                entity.addPart(nameValuePairs.get(index).getName(), new FileBody(new File (nameValuePairs.get(index).getValue())));
            } else {
                // Normal string data
                entity.addPart(nameValuePairs.get(index).getName(), new StringBody(nameValuePairs.get(index).getValue()));
            }
        }

        httpPost.setEntity(entity);

        HttpResponse response = httpClient.execute(httpPost, localContext);
    } catch (IOException e) {
        e.printStackTrace();
    }
}

Umarım bu size doğru yönde biraz yardımcı olur.


6
Bunu kesinlikle tavsiye ederim. Bu şekilde, muhtemelen görüntüyü almak ve kolayca saklamak için Django özelliklerini kullanabilirsiniz. Diğer bir yol, bayt akışını görüntüden base64 kodlu bir dizeye kodlamak ve sunucu tarafında kodunu çözmek olabilir. Ama bu benim görüşüme göre çok fazla güçlük olur ve gidecek yol değil.
Piro

6
Hey millet, bunu MultipartEntity olmadan yapmanın bir yolu var mı? GERÇEKTEN tüm Apache HC'yi sadece bu 4 sınıf için içe aktarmak istemiyorum. :-(
Neil Traft

6
FileBodyİstediğiniz Mime Tipine 2. bir parametre eklemeniz yeterlidir. Örneğin:new FileBody(new File (nameValuePairs.get(index).getValue()), "image/jpeg")
Piro

4
Görünüşe göre çok partili kullanımdan kaldırılmış mı?
Nanne

1
@Piro Ben de cevabınızı düzenlemeyi düşünüyordum. Çok parçalı varlık, kullandığınız dize gövdesi sürümüyle birlikte amortismana tabi tutulur. Düzenleme yapmamamın nedeni, sizin yaptığınız gibi isim çiftlerindeki tüm verileri bağlayamamam.
Yasadışı Tartışma

15

Sürüm 4.3.5 Güncellenen Kod

  • httpclient-4.3.5.jar
  • httpcore-4.3.2.jar
  • httpmime-4.3.5.jar

O MultipartEntityzamandan beri kullanımdan kaldırıldı . Lütfen aşağıdaki koda bakın.

String responseBody = "failure";
HttpClient client = new DefaultHttpClient();
client.getParams().setParameter(CoreProtocolPNames.PROTOCOL_VERSION, HttpVersion.HTTP_1_1);

String url = WWPApi.URL_USERS;
Map<String, String> map = new HashMap<String, String>();
map.put("user_id", String.valueOf(userId));
map.put("action", "update");
url = addQueryParams(map, url);

HttpPost post = new HttpPost(url);
post.addHeader("Accept", "application/json");

MultipartEntityBuilder builder = MultipartEntityBuilder.create();
builder.setCharset(MIME.UTF8_CHARSET);

if (career != null)
    builder.addTextBody("career", career, ContentType.create("text/plain", MIME.UTF8_CHARSET));
if (gender != null)
    builder.addTextBody("gender", gender, ContentType.create("text/plain", MIME.UTF8_CHARSET));
if (username != null)
    builder.addTextBody("username", username, ContentType.create("text/plain", MIME.UTF8_CHARSET));
if (email != null)
    builder.addTextBody("email", email, ContentType.create("text/plain", MIME.UTF8_CHARSET));
if (password != null)
    builder.addTextBody("password", password, ContentType.create("text/plain", MIME.UTF8_CHARSET));
if (country != null)
    builder.addTextBody("country", country, ContentType.create("text/plain", MIME.UTF8_CHARSET));
if (file != null)
    builder.addBinaryBody("Filedata", file, ContentType.MULTIPART_FORM_DATA, file.getName());

post.setEntity(builder.build());

try {
    responseBody = EntityUtils.toString(client.execute(post).getEntity(), "UTF-8");
//  System.out.println("Response from Server ==> " + responseBody);

    JSONObject object = new JSONObject(responseBody);
    Boolean success = object.optBoolean("success");
    String message = object.optString("error");

    if (!success) {
        responseBody = message;
    } else {
        responseBody = "success";
    }

} catch (Exception e) {
    e.printStackTrace();
} finally {
    client.getConnectionManager().shutdown();
}

Hangi kavanoz paketleri gereklidir?

3
httpclient-4.3.5.jar httpcore-4.3.2.jar httpmime-4.3.5.jar
AZ_

AddQueryParams ne döndürür?
San

11

Loopj kütüphanesi bu amaç için düz ileri kullanılabilir:

SyncHttpClient client = new SyncHttpClient();
RequestParams params = new RequestParams();
params.put("text", "some string");
params.put("image", new File(imagePath));

client.post("http://example.com", params, new TextHttpResponseHandler() {
  @Override
  public void onFailure(int statusCode, Header[] headers, String responseString, Throwable throwable) {
    // error handling
  }

  @Override
  public void onSuccess(int statusCode, Header[] headers, String responseString) {
    // success
  }
});

http://loopj.com/


5

Httpclient-4.3.5.jar, httpcore-4.3.2.jar, httpmime-4.3.5.jar kullanarak Android istemcisinden sunucu uygulamasına bir görüntü göndermeye çalışırken çok uğraştım. Her zaman bir çalışma zamanı hatası aldım. Google, Android'de HttpClient'in eski sürümünü kullandığı için temelde bu kavanozları Android ile kullanamayacağınızı öğrendim. Açıklama burada http://hc.apache.org/httpcomponents-client-4.3.x/android-port.html . Httpclientandroidlib-1.2.1 jar dosyasını android http-istemci kitaplığından almanız gerekir . Ardından or.apache.http.client'ten içe aktarmalarınızı ch.boye.httpclientandroidlib olarak değiştirin. Bu yardımcı olur umarım.


-13

Bunu genellikle json yanıtını işleyen iş parçacığında yaparım:

try {
  Bitmap bitmap = BitmapFactory.decodeStream((InputStream)new URL(imageUrl).getContent());
} catch (MalformedURLException e) {
  e.printStackTrace();
} catch (IOException e) {
  e.printStackTrace();
}

Görüntü üzerinde dönüşümler yapmanız gerekiyorsa, Bitmap yerine bir Drawable oluşturmak isteyeceksiniz.


3
Soru, bir resmin nasıl yayınlanacağı ve nasıl alınacağı değil.
dwbrito
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.