Doing HTTP Post with Android

Basic Tutorials concerning: GUI, Views, Activites, XML, Layouts, Intents, ...

Postby aetmos » Fri Jan 18, 2008 12:36 am

Hi All,

I'm trying to use Nanodeath's HTTP_Request class, but I'm getting this error:

PostHandler cannot be resolved to a type

on this line

Code: Select all
request.setHandler(new PostHandler(){


Any ideas why? It's finding HTTP_Request okay.

Thanks,
Tom
aetmos
Junior Developer
Junior Developer
 
Posts: 21
Joined: Fri Jan 18, 2008 12:33 am

Top

Postby Nanodeath » Fri Jan 18, 2008 12:40 am

Might have to qualify it like "new HTTP_Request.PostHandler" (or add an import at the top).
Nanodeath
Junior Developer
Junior Developer
 
Posts: 15
Joined: Tue Jan 15, 2008 6:56 am

Postby aetmos » Fri Jan 18, 2008 12:40 am

Nevermind, I just needed an HTTP_Request. in front of it, I guess.
aetmos
Junior Developer
Junior Developer
 
Posts: 21
Joined: Fri Jan 18, 2008 12:33 am

Postby aetmos » Fri Jan 18, 2008 12:41 am

Nanodeath wrote:Might have to qualify it like "new HTTP_Request.PostHandler" (or add an import at the top).


Thanks ;-) I guess I figured it out a second too late...
aetmos
Junior Developer
Junior Developer
 
Posts: 21
Joined: Fri Jan 18, 2008 12:33 am

Postby aetmos » Fri Jan 18, 2008 12:42 am

And it works! Thanks for this great Class! :D
aetmos
Junior Developer
Junior Developer
 
Posts: 21
Joined: Fri Jan 18, 2008 12:33 am

Postby aetmos » Fri Jan 18, 2008 12:45 am

Now does anybody know how to resolve these warnings in HTTP_Request?

Set is a raw type. References to generic type Set<E> should be parameterized

on

Code: Select all
Set keys = variables.keySet();


and

Iterator is a raw type. References to generic type Iterator<E> should be parameterized

on

Code: Select all
for(Iterator i = keys.iterator(); i.hasNext();){


Sorry if this is obvious...Java and Android are pretty new to me

Thanks,
Tom
aetmos
Junior Developer
Junior Developer
 
Posts: 21
Joined: Fri Jan 18, 2008 12:33 am

Top

Postby Nanodeath » Fri Jan 18, 2008 12:51 am

This is a little off topic, but Java "wants" you to use the Generics version of data structures (and their iterators) whenever possible. Back in Ye Olde Days, data structures only held objects and any objects you put into them had to be cast back into their original types when you pulled them out again. This is annoying and not terribly "safe" (possible ClassCastException). So...you say Set<SomeOtherType> thatThatSet = new Set<SomeOtherType>(); and...that pretty much takes care of all the problems. Hopefully the solution to the iterator question falls out of that somewhere.
Nanodeath
Junior Developer
Junior Developer
 
Posts: 15
Joined: Tue Jan 15, 2008 6:56 am

Postby plusminus » Fri Jan 18, 2008 1:06 am

Hey guys,
To resolve the Warning: "Set is a raw type. References to generic type Set<E> should be parameterized." probably also within the for-loop alter the following:
Syntax: [ Download ] [ Hide ]
Using java Syntax Highlighting
  1.                  Set<String> keys = variables.keySet();
  2.                  
  3.                  for(Iterator<String> i = keys.iterator(); i.hasNext();){
  4.                          // ... saves you this cast.
  5.                          String key = (String)i.next();
  6.                          // ...
  7.                  }
Parsed in 0.030 seconds, using GeSHi 1.0.8.4

This is just done to satisfy the compiler and to get some develop-time type-safety.

Regards,
plusminus
Image
Image | Android Development Community / Tutorials
User avatar
plusminus
Site Admin
Site Admin
 
Posts: 2688
Joined: Wed Nov 14, 2007 8:37 pm
Location: Schriesheim, Germany

Postby Nanodeath » Fri Jan 18, 2008 1:53 am

Okay, I've made another version. Main points, it's now ResponseHandler instead of PostHandler (since it can be GET or POST) and I've moved the variable-handling stuff to the go() function so that you can sorta create a template HTTP_Request in your class and then invoke it from different methods in the class with different variables but the same url. Plus I added some more comments and a couple minor tweaks here and there. Oh, and now you can get by without a ResponseHandler at all (caused null pointer exc before). I think I'm done messing with it now...

Syntax: [ Download ] [ Hide ]
Using java Syntax Highlighting
  1. import java.io.ByteArrayInputStream;
  2.  
  3. import java.io.UnsupportedEncodingException;
  4.  
  5. import java.net.URLEncoder;
  6.  
  7. import java.util.HashMap;
  8.  
  9. import java.util.Iterator;
  10.  
  11. import java.util.Map;
  12.  
  13. import java.util.Set;
  14.  
  15.  
  16.  
  17. import org.apache.http.util.ByteArrayBuffer;
  18.  
  19.  
  20.  
  21. import android.content.Context;
  22.  
  23. import android.net.http.EventHandler;
  24.  
  25. import android.net.http.Headers;
  26.  
  27. import android.net.http.RequestQueue;
  28.  
  29. import android.net.http.SslCertificate;
  30.  
  31. import android.util.Log;
  32.  
  33.  
  34.  
  35. /***
  36.  
  37.  * Perform GET or POST requests easily and handle responses, status checks, and errors.
  38.  
  39.  * Encapsulated in a class by Nanodeath
  40.  
  41.  * @author plusminus
  42.  
  43.  * @author nanodeath
  44.  
  45.  *
  46.  
  47.  */
  48.  
  49. public class HTTP_Request {
  50.  
  51.  
  52.  
  53.         // Fields
  54.  
  55.  
  56.  
  57.         private Context context;
  58.  
  59.         private String url;
  60.  
  61.         private Method method;
  62.  
  63.        
  64.  
  65.         /***
  66.  
  67.          *      Possible modes to make requests
  68.  
  69.          */
  70.  
  71.         public enum Method {
  72.  
  73.                 POST,
  74.  
  75.                 GET
  76.  
  77.         }
  78.  
  79.  
  80.  
  81.         // Constructors
  82.  
  83.        
  84.  
  85.         public HTTP_Request(Context c, String url, Method method) {
  86.  
  87.                 this.context = c;
  88.  
  89.                 this.url = url;
  90.  
  91.                 this.method = method;  
  92.  
  93.         }
  94.  
  95.  
  96.  
  97.         private ResponseHandler handler;
  98.  
  99.  
  100.  
  101.         /***
  102.  
  103.          * Optionally, you can process any output the url generates when accessed.  You can do so here.
  104.  
  105.          * @param h The response handler you want this object to use
  106.  
  107.          */
  108.  
  109.         public void setHandler(ResponseHandler h){
  110.  
  111.                 handler = h;
  112.  
  113.         }
  114.  
  115.  
  116.  
  117.         /***
  118.  
  119.          * Initiates the defined HTTP_Request without any variables
  120.  
  121.          */
  122.  
  123.         public void go(){
  124.  
  125.                 go(null);
  126.  
  127.         }
  128.  
  129.        
  130.  
  131.         /***
  132.  
  133.          * Initiates the defined HTTP_Request with the given variables as arguments
  134.  
  135.          * @param variables Key,value pairs to be sent to the webservice
  136.  
  137.          */
  138.  
  139.         public void go(Map<String,String> variables){
  140.  
  141.                 if(handler == null){
  142.  
  143.                         handler = new ResponseHandler();
  144.  
  145.                 }
  146.  
  147.                
  148.  
  149.                 /* Create a new EventHandler defined above, to handle what gets returned. */
  150.  
  151.                 MyEventHandler myEvH = new MyEventHandler(handler);
  152.  
  153.  
  154.  
  155.                 /* Create a new HTTP-RequestQueue. */
  156.  
  157.                 android.net.http.RequestQueue rQueue = new RequestQueue(context);        
  158.  
  159.  
  160.  
  161.                 /* Create a header-hashmap */
  162.  
  163.                 Map<String, String> headers = new HashMap<String, String>();
  164.  
  165.                 /* and put the Default-Encoding for html-forms to it. */
  166.  
  167.                 headers.put("Content-Type", "application/x-www-form-urlencoded");
  168.  
  169.                
  170.  
  171.                 /* Prepare the variables we are going to send. */
  172.  
  173.                 String variablesURL;
  174.  
  175.                 if(variables != null && variables.size() > 0){
  176.  
  177.                         try {
  178.  
  179.                                 StringBuilder b = new StringBuilder();
  180.  
  181.                                 Set<String> keys = variables.keySet();
  182.  
  183.                                 // Iterate over each variable you want and append it to our variablesURL variable
  184.  
  185.                                 for(Iterator<String> i = keys.iterator();;){
  186.  
  187.                                         String key = i.next();
  188.  
  189.                                         b.append(key);
  190.  
  191.                                         b.append("=");
  192.  
  193.                                         b.append(URLEncoder.encode(variables.get(key), "UTF-8"));
  194.  
  195.                                        
  196.  
  197.                                         // Minor speed optimization so that i.hasNext() is only called once (instead of in the for loop).
  198.  
  199.                                         if(i.hasNext()){
  200.  
  201.                                                 b.append("&");
  202.  
  203.                                         } else {
  204.  
  205.                                                 break;
  206.  
  207.                                         }
  208.  
  209.                                 }
  210.  
  211.                                 variablesURL = b.toString();
  212.  
  213.                         } catch (UnsupportedEncodingException e) {
  214.  
  215.                                 Log.e("HTTP_Request", "Unsupported Encoding Exception");
  216.  
  217.                                 return;
  218.  
  219.                         }
  220.  
  221.                 } else {
  222.  
  223.                         variablesURL = "";
  224.  
  225.                 }
  226.  
  227.                
  228.  
  229.                 if(method == Method.GET){
  230.  
  231.                         // Perform the request with GET
  232.  
  233.                         if(!variablesURL.equals("")){
  234.  
  235.                                 url = url + "?" + variablesURL;
  236.  
  237.                         }
  238.  
  239.                         rQueue.queueRequest(url, "GET", headers, myEvH, null, 0, false);
  240.  
  241.                 } else if(method == Method.POST){
  242.  
  243.                         /* And put the encoded bytes into an BAIS,
  244.  
  245.                          * where a function later can read bytes from. */
  246.  
  247.                         byte[] POSTbytes = variablesURL.getBytes();
  248.  
  249.                         ByteArrayInputStream baos = new ByteArrayInputStream(POSTbytes);
  250.  
  251.                         rQueue.queueRequest(url, "POST", headers, myEvH, baos, POSTbytes.length, false);                       
  252.  
  253.                 } else {
  254.  
  255.                         // Hopefully this could never actually occur
  256.  
  257.                         return;
  258.  
  259.                 }
  260.  
  261.                
  262.  
  263.                 /* Wait until the request is complete.*/
  264.  
  265.                 rQueue.waitUntilComplete();
  266.  
  267.         }
  268.  
  269.  
  270.  
  271.         // ===========================================================
  272.  
  273.         // Worker Class
  274.  
  275.         // ===========================================================
  276.  
  277.  
  278.  
  279.         private class MyEventHandler implements EventHandler {
  280.  
  281.                 private ResponseHandler handler;
  282.  
  283.  
  284.  
  285.                 /** Will hold the data returned by the URLCall. */
  286.  
  287.                 ByteArrayBuffer baf = new ByteArrayBuffer(20);
  288.  
  289.  
  290.  
  291.                 MyEventHandler(ResponseHandler callback) {
  292.  
  293.                         this.handler = callback;
  294.  
  295.                 }
  296.  
  297.  
  298.  
  299.                 public void data(byte[] bytes, int len) {
  300.  
  301.                         baf.append(bytes, 0, len);
  302.  
  303.                 }
  304.  
  305.  
  306.  
  307.                 public void endData() {
  308.  
  309.                         handler.run(new String(baf.toByteArray()));
  310.  
  311.                 }
  312.  
  313.  
  314.  
  315.                 public void status(int arg0, int arg1, int HTTPstatusCode, String status) {
  316.  
  317.                         // HTTPstatusCode can be 200 for OK, 404 for Not Found, etc.
  318.  
  319.                         // Status can be OK, Not Found, others...                      
  320.  
  321.                         handler.status(status);
  322.  
  323.                 }
  324.  
  325.  
  326.  
  327.                 public void error(int i, String s) {
  328.  
  329.                         handler.error(s);
  330.  
  331.                 }
  332.  
  333.  
  334.  
  335.                 public void handleSslErrorRequest(int arg0, String arg1, SslCertificate arg2) { }
  336.  
  337.                 public void headers(Iterator arg0) { }
  338.  
  339.                 public void headers(Headers arg0) { }
  340.  
  341.         }
  342.  
  343.  
  344.  
  345.         public static class ResponseHandler {
  346.  
  347.                 public void run(String response){}
  348.  
  349.                 public void status(String status) {}
  350.  
  351.                 public void error(String error) {}
  352.  
  353.         }
  354.  
  355. }
Parsed in 0.050 seconds, using GeSHi 1.0.8.4
Nanodeath
Junior Developer
Junior Developer
 
Posts: 15
Joined: Tue Jan 15, 2008 6:56 am

Postby aetmos » Fri Jan 18, 2008 3:25 am

Excellent. Thanks for the explanations and the new class. Works great.

One thing I thought I'd mention...if you're using your implementation of the class on the first page, you have to change this:

Code: Select all
                     void run(String response) {
                          Log.d("HTTP_Request", "RESPONSE: " + response);
                     }

                     @Override
                     void error(String error) {
                          Log.e("HTTP_Request", "ERROR: " + error);
                     }

                     @Override
                     void status(String status) {
                          Log.i("HTTP_Request", "STATUS:" + status);
                     }


to this:


Code: Select all
                     public void run(String response) {
                          Log.d("HTTP_Request", "RESPONSE: " + response);
                     }

                     @Override
                     public void error(String error) {
                          Log.e("HTTP_Request", "ERROR: " + error);
                     }

                     @Override
                     public void status(String status) {
                          Log.i("HTTP_Request", "STATUS:" + status);
                     }


for obvious reasons.

Tom
aetmos
Junior Developer
Junior Developer
 
Posts: 21
Joined: Fri Jan 18, 2008 12:33 am

Postby Androider » Thu Jan 24, 2008 1:16 pm

Can we cancel the Request once we issued the request.

Tnx.
Androider
Freshman
Freshman
 
Posts: 7
Joined: Thu Jan 17, 2008 8:03 am

Postby Nanodeath » Thu Jan 24, 2008 4:51 pm

Well, it seems to be me like if one wanted to do that, it would happen in the RequestQueue (rQueue), but the only relevant methods it has are queueRequest and waitUntilComplete. I was hoping for a clearQueue, dequeue, pop, etc, but there doesn't seem to be one. So, to the best of my limited knowledge, and strictly speaking, I don't think there's a way to cancel a request in progress.
Nanodeath
Junior Developer
Junior Developer
 
Posts: 15
Joined: Tue Jan 15, 2008 6:56 am

Postby ramgraph1 » Tue Feb 12, 2008 12:00 am

Using the original code by plusminus above and changing the php file's URL to my own php file's, the app runs in the emulator but I am only getting this in the warning dialog:

Data loaded:
POSTed data:''

It seems like it is working halfway as it is getting the "POSTed data:" part from the php file but for some reason is not getting the message I was trying to send. Right?
I am getting a warning on this line of code:
Code: Select all
     public void headers(Iterator arg0) { }

with Eclipse saying I should "rename in file"...
Any ideas what I am doing wrong? The php file is exactly the same as the one used by plusminus above.
Thanks for any help you can give.
ramgraph1
Experienced Developer
Experienced Developer
 
Posts: 68
Joined: Wed Jan 09, 2008 10:03 pm

Postby cyberrob » Wed Feb 13, 2008 8:07 am

ramgraph1 wrote:Using the original code by plusminus above and changing the php file's URL to my own php file's, the app runs in the emulator but I am only getting this in the warning dialog:

Data loaded:
POSTed data:''

It seems like it is working halfway as it is getting the "POSTed data:" part from the php file but for some reason is not getting the message I was trying to send. Right?


This is a easy one~So I solve this surprisingly! :oops: You have to edit your php file.Its just a little bug.
From
Code: Select all
<?php
    echo "POSTed data: '".$_POST['data']."'";
?>

To
Code: Select all
<?php
    echo "POSTed data: '".$_POST['mydata']."'";
?>

Cos in java we annouce the "mydata", not "data".

I am getting a warning on this line of code:
Code: Select all
     public void headers(Iterator arg0) { }

with Eclipse saying I should "rename in file"...
Any ideas what I am doing wrong? The php file is exactly the same as the one used by plusminus above.
Thanks for any help you can give.


I got the same warning, but it's ok. you dont have to change anything to run this example successfully.

BR,
Robert
User avatar
cyberrob
Junior Developer
Junior Developer
 
Posts: 12
Joined: Thu Dec 13, 2007 3:01 am

Postby plusminus » Wed Feb 13, 2008 9:22 am

Hey guys,

:larrow: :shock:

:cut: :cut: :cut: :cut: :cut: :cut: :cut:
...which will simply echo the 'mydata' variable posted to it:
Syntax: [ Download ] [ Hide ]
Using php Syntax Highlighting
  1.                  <?php
  2.                                 echo "POSTed data: '".$_POST['data']."'";
  3.                  ?>
Parsed in 0.061 seconds, using GeSHi 1.0.8.4

:cut: :cut: :cut: :cut: :cut: :cut: :cut:

Corrected it in the first post...

Regards,
plusminus
Image
Image | Android Development Community / Tutorials
User avatar
plusminus
Site Admin
Site Admin
 
Posts: 2688
Joined: Wed Nov 14, 2007 8:37 pm
Location: Schriesheim, Germany

Top
PreviousNext

Return to Novice Tutorials

Who is online

Users browsing this forum: No registered users and 10 guests