您的位置:首页 > 理论基础 > 计算机网络

安卓网络-冰山一角之httpurlconnection

2014-03-29 12:11 405 查看
好久没碰见问题解决问题了。前段事件搞网络的东西。一团糟糕。没心情搞了。停了一段时间。反倒是好一些了。网络编程时很大的一块内容。但基本是socket和http这两大块。最开始不太懂。后来一点点的啃。原来安卓中提供的各种类其实就是一层层的继承。一点点将功能加强。将操作简化。怎么说?

httpurlconnection是建立在http之上的连接服务器的方法。是安卓提供的内置类。直接使用。方便快捷。我们知道请求多是post和get两种。而post往往是居多的。跟他的安全性和传输的数据量应该是有分不开的关系。

request。请求

response。响应。

这两个是对立的。有请求就要有响应。这两个好比两个大盒子。客户端要向服务器端发送请求。那就得用到这个盒子。request。有什么话咱里边说。有什么请求都可以往这里边放。当然这是有方法的。具体怎么放。将在下一篇博文中整理介绍一番。

同样的。服务器拿到这个盒子就拆开来看。看看你都发了些什么过来。服务器根据你发的这些东西。用已经写好的一些逻辑例如servlet之类的来处理。处理好的结果装在另外一个箱子response中。又给送回去。

如此这番就完成了和服务器的交互。来看个例子。简单的提交用户名和密码。

首先在myeclipse中新建一个web project命名为FirstServlet再在里边新建一个servlet用来处理从客户端发送过来的用户名和密码。

来看代码

package servlet;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class firstservlet extends HttpServlet {

/**
* Constructor of the object.
*/
public firstservlet() {
super();
}

/**
* Destruction of the servlet. <br>
*/
public void destroy() {
super.destroy(); // Just puts "destroy" string in log
// Put your code here
}

/**
* The doGet method of the servlet. <br>
*
* This method is called when a form has its tag value method equals to get.
*
* @param request the request send by the client to the server
* @param response the response send by the server to the client
* @throws ServletException if an error occurred
* @throws IOException if an error occurred
*/
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {

response.setContentType("text/html");
获取输出流来将要返回的信息放进去
PrintWriter out = response.getWriter();
获取request中的用户名和密码。实际上就是上面所说的箱子里面的内容
String usename=request.getParameter("usename");
String password=request.getParameter("password");
if("usename".equals(usename)&&"password".equals(password)){
out.println("httpurlconnection");
}
else
out.println("sorry!");
out.flush();
out.close();
}

/**
* The doPost method of the servlet. <br>
*
* This method is called when a form has its tag value method equals to post.
*
* @param request the request send by the client to the server
* @param response the response send by the server to the client
* @throws ServletException if an error occurred
* @throws IOException if an error occurred
*/
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {

doGet(request,response);
}

/**
* Initialization of the servlet. <br>
*
* @throws ServletException if an error occurs
*/
public void init() throws ServletException {
// Put your code here
}

}
这个代买很简单。就是判断用户名和密码是否是指定好的。并没有去连接数据库那么复杂的操作。

接下来要在客户端也就是安卓代码了。

布局文件时两个edittext用来输入用户名密码。一个button用来提交。一个textview来显示服务器处理返回的结果。

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity" >

<EditText
android:id="@+id/usename"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />

<EditText
android:id="@+id/password"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />

<Button
android:id="@+id/tijiao"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="提交" />

<TextView
android:id="@+id/textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" />

</LinearLayout>


然后是activity的代码。

package com.example.httpurlconnection;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;

import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.app.Activity;
import android.util.Log;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

public class MainActivity extends Activity {

URL url = null;
String result ="";
String susename = null;
String spassword = null;
TextView textview;

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
final EditText usename = (EditText) findViewById(R.id.usename);
final EditText password = (EditText) findViewById(R.id.password);
final Handler handler=new Handler(){
@Override
public void handleMessage(Message msg) {
if(msg.what==0x1233)
textview.setText(result);
}
};
textview = (TextView) findViewById(R.id.textview);
Button tijiao = (Button) findViewById(R.id.tijiao);
tijiao.setOnClickListener(new OnClickListener() {

@Override
public void onClick(View v) {
result ="";
susename = usename.getText().toString();
spassword = password.getText().toString();
StringBuffer stringBuffer = new StringBuffer();
//post请求中传递参数的格式是 参数名=参数&参数名1=参数1的形式
stringBuffer.append("usename=").append(susename).append("&password=").append(spassword);
final byte[] data = stringBuffer.toString().getBytes();
new Thread() {
@Override
public void run() {
try {
//这个地址就是你的web所在的地址。用控制台的ipconfig去查ip。
url = new URL(
"http://192.168.1.101:8080/FirstServlet/servlet/firstservlet");
} catch (MalformedURLException e) {

e.printStackTrace();
}
try {
Log.d("===========================", "进入了函数体");
//打开连接
HttpURLConnection ction = (HttpURLConnection) url
.openConnection();
ction.setRequestMethod("POST");//设置连接方式。默认是get
ction.connect();
Log.d("===========================", "连接成功");
OutputStream os = ction.getOutputStream();//获取输出流来往请求体request中写入数据
os.write(data);
InputStream is = ction.getInputStream();//获取输入流。也就是响应response的返回数据
Log.d("===========================", "输入流获取成功");
BufferedReader in = new BufferedReader(
new InputStreamReader(is));

String line = null;
while ((line = in.readLine()) != null) {
result += line;
}
Log.d("===========================", "result获取成功");
Log.d("===========================",result );
handler.sendEmptyMessage(0x1233);
Log.d("===========================", "显示成功");
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}.start();
}

});

}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}

}
获取了相应的控件之后。为button增加一个点击事件函数。在函数中可以看到。是创建了一个线程。这个是需要注意的。网络连接的部分最好是用一个新线程来做。因为 如果你的网络不好的情况下。不会一直等待。很影响客户体验。在4.0后的版本如果不新启动一个线程来处理网络编译是无法通过的。

还需要注意的一点是。(这里博主其实也不太清楚原理)如果直接是在setonclick之外新建线程来处理网络。可以直接在线程中用textview。settext来设置文本显示返回数据。但是在setonclick之中新建线程是不行的。报错说要原始线程来改变ui。所以这里新建了一个handler。用来在新建的线程和ui线程也就是主线程来通讯。获得了result之后就通知主线程更新数据。

看下结果。



输入的用户名和指定的一样。返回httourlconnection



提交的数据和指定的不一样返回sorry。和服务器的处理代码完全吻合了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: