1.这节课向你展示了如何实现一个简单的应用程序连接到网络。它解释了一些最佳实践你甚至应该遵循创建最简单的网络连接的应用程序。
注意,执行网络操作描述在这节课中,你的应用程序清单文件必须包括以下权限:
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
2. 选择一个HTTP客户端
大多数网络连接Android应用程序使用HTTP来发送和接收数据。Android包括两个HTTP客户端:HttpURLConnection和Apache HttpClient。都支持HTTPS,流媒体上传和下载,可配置的超时,IPv6和连接池。我们建议使用HttpURLConnection针对姜饼和更高的应用程序。更多关于该话题的讨论,请参见博文Android的HTTP客户端。
3。检查网络连接
应用程序试图连接到网络之前,应该检查是否使用网络连接可用, using getActiveNetworkInfo() and isConnected()记住,该设备可能范围内的一个网络,或用户可能禁用无线网络和移动数据访问。更多关于该话题的讨论,请参见教训
↳ | android.net.ConnectivityManager Class that answers queries about the state of network connectivity. It also notifies applications when network connectivity changes. Get an instance of this class by calling |
public void myClickHandler(View view) {
...
ConnectivityManager connMgr = (ConnectivityManager)
getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = connMgr.getActiveNetworkInfo();
if (networkInfo != null && networkInfo.isConnected()) {
// fetch data
} else {
// display error
}
...
}
public NetworkInfo getActiveNetworkInfo ()
Added in API level 1
Returns details about the currently active default data network. When connected, this network is the default route for outgoing connections. You should always check isConnected() before initiating network traffic. This may return null when there is no default network.
Returns
a NetworkInfo object for the current default network or null if no network default network is currently active This method requires the call to hold the permission ACCESS_NETWORK_STATE.
4.在一个单独的线程执行操作
网络运营可能涉及不可预测的延迟。为了防止这种造成不良的用户体验,总是在一个单独的线程执行网络操作的UI。AsyncTask类提供了一个最简单的方法来启动一个新任务从UI线程
the myClickHandler() method invokes new DownloadWebpageTask().execute(stringUrl).
The DownloadWebpageTask class is a subclass of AsyncTask.
DownloadWebpageTask implements the following AsyncTask methods:
doInBackground() executes the method downloadUrl(). It passes the web page URL as a parameter.
The method downloadUrl() fetches and processes the web page content.
When it finishes, it passes back a result string.
onPostExecute() takes the returned string and displays it in the UI.
public class HttpExampleActivity extends Activity {
private static final String DEBUG_TAG = "HttpExample";
private EditText urlText;
private TextView textView;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
urlText = (EditText) findViewById(R.id.myUrl);
textView = (TextView) findViewById(R.id.myText);
}
// When user clicks button, calls AsyncTask.
// Before attempting to fetch the URL, makes sure that there is a network connection.
public void myClickHandler(View view) {
// Gets the URL from the UI's text field.
String stringUrl = urlText.getText().toString();
ConnectivityManager connMgr = (ConnectivityManager)
getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = connMgr.getActiveNetworkInfo();
if (networkInfo != null && networkInfo.isConnected()) {
new DownloadWebpageText().execute(stringUrl);
} else {
textView.setText("No network connection available.");
}
}
// Uses AsyncTask to create a task away from the main UI thread. This task takes a
// URL string and uses it to create an HttpUrlConnection. Once the connection
// has been established, the AsyncTask downloads the contents of the webpage as
// an InputStream. Finally, the InputStream is converted into a string, which is
// displayed in the UI by the AsyncTask's onPostExecute method.
private class DownloadWebpageText extends AsyncTask {
@Override
protected String doInBackground(String... urls) {
// params comes from the execute() call: params[0] is the url.
try {
return downloadUrl(urls[0]);
} catch (IOException e) {
return "Unable to retrieve web page. URL may be invalid.";
}
}
// onPostExecute displays the results of the AsyncTask.
@Override
protected void onPostExecute(String result) {
textView.setText(result);
}
}
...
}
The sequence of events in this snippet is as follows:
- When users click the button that invokes myClickHandler(), the app passes the specified URL to the AsyncTasksubclass DownloadWebpageTask.
- The AsyncTask method doInBackground() calls the downloadUrl() method.
- The downloadUrl() method takes a URL string as a parameter and uses it to create a URL object.
- The URL object is used to establish an HttpURLConnection.
- Once the connection has been established, the HttpURLConnection object fetches the web page content as anInputStream.
- The InputStream is passed to the readIt() method, which converts the stream to a string.
- Finally, the AsyncTask's onPostExecute() method displays the string in the main activity's UI.
5.连接并下载数据 In your thread that performs your network transactions, you can use HttpURLConnection to perform a GET and download your data. After you call connect(), you can get an InputStream of the data by calling getInputStream(). In the following snippet, the doInBackground() method calls the method downloadUrl(). The downloadUrl() method takes the given URL and uses it to connect to the network via HttpURLConnection. Once a connection has been established, the app uses the method getInputStream() to retrieve the data as an InputStream.
// Given a URL, establishes an HttpUrlConnection and retrieves
// the web page content as a InputStream, which it returns as
// a string.
private String downloadUrl(String myurl) throws IOException {
InputStream is = null;
// Only display the first 500 characters of the retrieved
// web page content.
int len = 500;
try {
URL url = new URL(myurl);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setReadTimeout(10000 /* milliseconds */);
conn.setConnectTimeout(15000 /* milliseconds */);
conn.setRequestMethod("GET");
conn.setDoInput(true);
// Starts the query
conn.connect();
int response = conn.getResponseCode();
Log.d(DEBUG_TAG, "The response is: " + response);
is = conn.getInputStream();
// Convert the InputStream into a string
String contentAsString = readIt(is, len);
return contentAsString;
// Makes sure that the InputStream is closed after the app is
// finished using it.
} finally {
if (is != null) {
is.close();
}
}
}
注意,方法getResponseCode()返回的状态码的连接。这是一个有用的方法得到额外的信息连接。状态码200表示成功。
InputStream是一个可读的字节。一旦你得到InputStream,常见的解码或转换成一个目标数据类型。举个例子,如果你是下载图像数据,这样你可以解码和显示:
InputStream is = null;
...
Bitmap bitmap = BitmapFactory.decodeStream(is);
ImageView imageView = (ImageView) findViewById(R.id.image_view);
imageView.setImageBitmap(bitmap);
public String readIt(InputStream stream, int len) throws IOException, UnsupportedEncodingException {
Reader reader = null;
reader = new InputStreamReader(stream, "UTF-8");
char[] buffer = new char[len];
reader.read(buffer);
return new String(buffer);