1. 程式人生 > >Android:HttpClient、tomcat支援php、搭建PHP後臺

Android:HttpClient、tomcat支援php、搭建PHP後臺

目的:     建立一個簡單的Android專案,並搭建PHP後臺,實現Android與PHP之間的通訊。 本地環境:     Android Studio3.1.2     Tomcat 7.0.63

一、建立一個簡單的安卓專案

    File->New->New project,寫好專案名稱,選擇好本地儲存路徑後,一直NEXT就可以創建出一個專案。 這裡寫圖片描述 這裡寫圖片描述

二、Http Client

    java中要傳送http請求可通過Http Client實現。接下來是封裝httpclient的get()和post()。下面是個人第一次在網上查閱後嘗試寫的,有些地方可能寫得不好,見諒哈,小白一隻。

1、新建HttpClient類

這裡寫圖片描述

package com.example.zwl.myapplication;

import android.util.Log;

import java.io.BufferedReader;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import
java.net.URLEncoder; import java.util.HashMap; public class HttpClient { private String Url; private int timeout; public String getUrl() { return Url; } public void setUrl(String url) { this.Url = url; } public int getTimeout() { return timeout; } public
void setTimeout(int time) { this.timeout = time; } public HashMap<String, Object> get() { //get請求:存放狀態碼和請求內容 HashMap<String, Object> result = null; //用於存放http狀態碼 int STATUS; try { //建立URL物件 URL geturl = new URL(Url); HttpURLConnection httpURLConnection = (HttpURLConnection) geturl.openConnection(); //設定連線超時(ms) httpURLConnection.setConnectTimeout(timeout); //設定請求方式(預設為get) httpURLConnection.setRequestMethod("GET"); //建立到遠端物件的實際連線 httpURLConnection.connect(); //獲取狀態碼 STATUS = httpURLConnection.getResponseCode(); //返回開啟連線讀取的輸入流,輸入流轉化為StringBuffer型別 BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(httpURLConnection.getInputStream(), "utf-8")); StringBuffer stringBuffer = new StringBuffer(); String line; while ((line = bufferedReader.readLine()) != null) { //轉化為utf-8的編碼格式 line = new String(line.getBytes("utf-8")); stringBuffer.append(line); } bufferedReader.close(); httpURLConnection.disconnect(); result = new HashMap<>(); result.put("status", STATUS); result.put("data", stringBuffer.toString()); } catch (MalformedURLException e) { Log.d("get", "build url failed"); e.printStackTrace(); } catch (IOException e) { Log.d("get", "build failed"); e.printStackTrace(); } return result; } public HashMap<String, Object> post(HashMap<String, String> param) { HashMap result = null; try { URL posturl = new URL(Url); HttpURLConnection httpURLConnection = (HttpURLConnection) posturl.openConnection(); httpURLConnection.setConnectTimeout(timeout); httpURLConnection.setRequestMethod("POST"); //設定是否向httpURLConnection輸出 httpURLConnection.setDoOutput(true); //設定是否從httpURLConnection讀入 httpURLConnection.setDoInput(true); //POST不能使用快取 httpURLConnection.setUseCaches(false); httpURLConnection.setInstanceFollowRedirects(true); //設定請求頭 httpURLConnection.setRequestProperty("Charset", "utf-8"); httpURLConnection.setRequestProperty("contentType", "utf-8"); httpURLConnection.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)"); httpURLConnection.setRequestProperty("Content-type", "application/x-www-form-urlencoded"); //配置需在連線之前完成 httpURLConnection.connect(); //設定請求內容 DataOutputStream out = new DataOutputStream(httpURLConnection.getOutputStream()); String content = ""; //遍歷Map,構造表單引數 //keySet()返回postcontent內所有的關鍵字 for (String key : param.keySet()) { String value = param.get(key); content += key + "=" + URLEncoder.encode(value, "utf-8") + "&"; } if (!content.isEmpty()) { content = content.substring(0, content.length() - 1); } out.writeBytes(content); out.flush(); out.close(); int code = httpURLConnection.getResponseCode(); Log.d("post", "content:" + content); Log.d("post", "out:" + out); //返回開啟連線讀取的輸入流,輸入流轉化為StringBuffer型別 //BufferedReader提供通用的緩衝方式文字讀取 //InputStreamReader()能將位元組流輸出為字元流 BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(httpURLConnection.getInputStream(), "utf-8")); String line; StringBuffer stringBuffer = new StringBuffer(); while ((line = bufferedReader.readLine()) != null) { line = new String(line.getBytes("utf-8")); // Log.d(tag:"post",line); stringBuffer.append(line); } Log.d("post", "data : " + stringBuffer.toString()); bufferedReader.close(); httpURLConnection.disconnect(); result = new HashMap<>(); result.put("status", code); result.put("data", stringBuffer.toString()); } catch (MalformedURLException e) { Log.d("post", "build url failed"); e.printStackTrace(); } catch (IOException e) { Log.d("post", "build failed"); e.printStackTrace(); } return result; } }

2、實現了HttpClient類後就是如何使用這個類來進行http請求。由於android4.0以後不能在主執行緒發起網路請求,所以這裡需要建立一個執行緒用於進行網路請求。 我這裡直接在MainActivity.java中建立執行緒。同時在類MyThread中重寫run()。 這裡貼的是傳送post請求的程式碼。

package com.example.zwl.myapplication;

import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        //建立新執行緒
        MyThread t = new MyThread();
        /* 啟動執行緒 */
        t.start();
    }
}
package com.example.zwl.myapplication;

import android.util.Log;

import java.util.HashMap;

public class MyThread extends Thread{
    @Override
    public  void run(){
        super.run();
        HttpClient http = new HttpClient();
        //此處ip為自己電腦的ip地址
        http.setUrl("http://10.201.220.149:8080/phpbin/index.php");
        http.setTimeout(10000);
        HashMap<String, String> params = new HashMap<String, String>();
        params.put("test","test");
        HashMap<String,Object> result = http.post(params);
        Object code = result.get("status");
        Object data = result.get("data");
        Log.v("post","post資料"+String.valueOf(code));
        Log.v("post","post資料"+String.valueOf(data));
    }
}

這裡可以測試一下,編寫的程式是否可用。為了測試,我將 MyThread類中的run()改成下面這樣,這裡是傳送get請求的程式碼:

package com.example.zwl.myapplication;

import android.util.Log;

import java.util.HashMap;

public class MyThread extends Thread{
    @Override
    public  void run(){
        super.run();
        HttpClient http = new HttpClient();
        http.setUrl("https://www.baidu.com");
        http.setTimeout(10000);
        HashMap<String,Object> result = http.get();
        Object code = result.get("status");
        Object data = result.get("data");
        Log.v("get","get資料"+String.valueOf(code));
        Log.v("get","get資料"+String.valueOf(data));
    }
}

記得配置一下聯網許可權,在AndroidManifest.xml檔案中: 這裡寫圖片描述

執行一下程式:Build -> Buid APK(s),Run ‘app’。

這裡寫圖片描述

從列印的資料來看,請求成功了。

3、檢視本機ip

    win+r,輸入cmd,輸入ipconfig即可看到本機ip。

三、搭建本地PHP伺服器

1、tomcat下載 這裡選擇壓縮包解壓。將壓縮包解壓在自己想要放置的資料夾下,環境配置方面需要在系統環境變數中新建JAVA_HOME變數,其值為本機jdk的安裝目錄。 這裡寫圖片描述 檢視apache-tomcat-7.0.63\bin目錄下catalina.bat檔案 這裡寫圖片描述 出現這個代表tomcat安裝成功。雙擊apache-tomcat-7.0.63\bin目錄下startup.bat檔案。瀏覽器:localhost:8080訪問。 這裡寫圖片描述 這裡寫圖片描述 假如雙擊startup.bat出現閃退,可編輯startup.bat檔案,在末尾加上PAUSE,再次啟動,根據資訊進行除錯。 這裡寫圖片描述

2、tomcat登陸

這裡寫圖片描述 開啟apache-tomcat-7.0.63\webapps\host-manager\WEB-INF下的web.xml檔案。 找到admin-gui,複製紅框內容,增加管理角色manager-gui 這裡寫圖片描述 開啟conf/tomcat-users.xml。 這裡寫圖片描述 目的是為了建立一個使用者名稱和密碼均為tomcat的使用者,此使用者擁有管理員許可權。manager-gui是管理者角色,對於tomcat6,mangaer是管理者角色,不是manager-gui。 重啟tomcat之後再次輸入localhost:8080,點選server status,輸入tomcat,密碼為tomcat,即可登陸。 這裡寫圖片描述

3、配置tomcat支援php執行。

下載好php壓縮包後解壓至apache-tomcat-7.0.63(tomcat安裝目錄)下,進入php目錄。 這裡寫圖片描述 支援php cgi執行,修改php.ini如下:

; Directory in which the loadable extensions (modules) reside.
; http://php.net/extension-dir
; extension_dir = "./"
extension_dir = "ext"
; On windows:
cgi.force_redirect = 0

; Directory where the temporary files should be placed.
; Defaults to the system default (see sys_get_temp_dir)
; sys_temp_dir = "/tmp"

開啟apache-tomcat-7.0.63\conf\context.xml,修改如下:

<!-- The contents of this file will be loaded for each web application -->
<Context privileged = "true" >

    <!-- Default set of monitored resources -->
    <WatchedResource>WEB-INF/web.xml</WatchedResource>
<servlet>
        <servlet-name>default</servlet-name>
        <servlet-class>org.apache.catalina.servlets.DefaultServlet</servlet-class>
        <init-param>
            <param-name>debug</param-name>
            <param-value>0</param-value>
        </init-param>
        <init-param>
            <param-name>listings</param-name>
            <param-value>false</param-value>
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>

    <servlet>
        <servlet-name>php</servlet-name>
        <servlet-class>org.apache.catalina.servlets.CGIServlet</servlet-class>
        <init-param>
            <param-name>clientInputTimeout</param-name>
            <param-value>200</param-value>
        </init-param>
        <init-param>
            <param-name>debug</param-name>
            <param-value>0</param-value>
        </init-param>
        <init-param>
            <param-name>executable</param-name>
            <!-- tomcat安裝目錄下php下的php-cgi.exe -->
            <param-value>C:\apache-tomcat-7.0.63\php7.1.9\php-cgi.exe</param-value>
        </init-param>
        <init-param>
            <param-name>passShellEnvironment</param-name>
            <param-value>true</param-value>
        </init-param>
        <init-param>
            <param-name>cgiPathPrefix</param-name>
            <!--指定php在apache-tomcat-7.0.63\webapps\ROOT\WEB-INF\phpbin下-->
            <param-value>WEB-INF/phpbin</param-value>
        </init-param>
        <load-on-startup>5</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>php</servlet-name>
        <url-pattern>/phpbin/*</url-pattern>
    </servlet-mapping>

重啟tomcat,在apache-tomcat-7.0.63\webapps\ROOT\WEB-INF在新建phpbin,新建index.php,內容如下:

<?php phpinfo() ?>

訪問:localhost:8080/phpbin/index.php,看到下面,搭建成功。 這裡寫圖片描述

4、手機訪問本地伺服器

    保證手機與電腦連線在同一wifi下,使用手機瀏覽器訪問:http://ip(電腦ip):8080即可訪問到tomcat主頁

四、php與android間的互動

    通過上面步驟,Android端已經可以傳送請求,設定url為自己本機ip+php檔案路徑,就可以向php檔案傳送post請求。這裡貼一下php檔案的程式碼。

<?php
    //定義返回資料
    $data = ["code" => "","msg" => ""];
    if (!empty($_POST)) {
        //
        foreach($_POST as $key=>$value){
            //接收資料的鍵對值
            $data = ["code" => $key,"msg" => $value]; //因為post資料只有一對鍵對值,這裡我偷懶直接把返回資料在此迴圈裡填裝

        };
    }
    echo json_encode($data);
?>

注意:

  • 在執行前記得開啟本地tomcat
  • php檔案中echo、var_dump資料將顯示在android端。通過網頁訪問php檔案看不到資料。

    執行: 這裡寫圖片描述 php成功返回資料給android端。