Android 平臺下Cordova FtpClient插件開發

須要引用一個commons-net-3.3.jar,下載地址:http://commons.apache.org/proper/commons-net/download_net.cgijava

創建一個包,名爲:com.JajaCy.FtpClientandroid

package com.JajaCy.FtpClient;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPClientConfig;
import org.apache.commons.net.ftp.FTPFile;
import org.apache.commons.net.ftp.FTPReply;
import org.apache.cordova.CallbackContext;
import org.apache.cordova.CordovaPlugin;
import org.apache.cordova.PluginResult;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import android.util.Log;

public class FtpClientPlugin extends CordovaPlugin {
    public static final String ACTION_LIST ="list";
    public static final String ACTION_GET ="get";
    public static final String ACTION_PUT ="put";
    private String filePath="/sdcard/JajaCy/";//本地存儲地址
    private String username="admin";//用戶名
    private String password="admin";//密碼
    private int port=21;//服務器端口號
    
    
    @Override
    public boolean execute(String action,JSONArray data,final CallbackContext callbackContext){
        PluginResult.Status status = PluginResult.Status.OK;
        JSONArray result = new JSONArray();
        Log.d("FtpClientPlugin", "Hello, this is a native function called from Cordova!");  
        if(action.equals(ACTION_LIST)){//列表
            try{
                final String ip=data.getString(0);///接收到的值
                final String fileDirectory=data.getString(1);///接收到的值
                System.out.println(ip);
                //this.DisplayToast("192.168.1.108", callbackContext);//返回下載列表
                //getFiles("192.168.1.108", callbackContext);
                Log.d("ACTION_LIST",fileDirectory);  
                cordova.getThreadPool().execute(new Runnable(){
                    public void run(){
                        getFiles(ip, fileDirectory,callbackContext);//獲取文件列表
                    }
                });
                //callbackContext.sendPluginResult(new PluginResult(status, result));
                return true;
            }
            catch(Exception ex){
                Log.d("FtpClientPlugin", ex.toString());
            }
        }
        else if(action.equals(ACTION_GET)){//下載
            try {
                final String ip =data.getString(0);
                final String fileName =data.getString(1);
                final String fileDirectory=data.getString(2);
                cordova.getThreadPool().execute(new Runnable(){
                    public void run(){
                        get(ip, fileName,fileDirectory,callbackContext);//下載
                    }
                });
                return true;
            } catch (JSONException e) {
                e.printStackTrace();
            }
        }
        else if(action.equals(ACTION_PUT)){//上傳
            try{
                final String ip =data.getString(0);
                final String fileName =data.getString(1);
                final String fileDirectory=data.getString(2);
                cordova.getThreadPool().execute(new Runnable(){
                    public void run(){
                        put(ip, fileName,fileDirectory,callbackContext);//上傳
                    }
                });
                return true;
            }
            catch(JSONException e){
                e.printStackTrace();
            }
        }
        return false;
    }
    
    /**
     * 獲取文件列表
     * */
    public void getFiles(String ip,String fileDirectory,CallbackContext callbackContext){
        FTPClient ftpClient=createConnection(ip);
        JSONObject obj = new JSONObject();//建立JSON對象
        JSONArray jsonArray = new JSONArray(); //JSON數組
        boolean flag=false;
        try{
            FTPFile[] ftpFiles=ftpClient.listFiles();//獲得目錄的相應文件列表
            for(int i=0; i<ftpFiles.length; i++){
                String fileName=ftpFiles[i].getName();
                int index=fileName.lastIndexOf("\t");//去掉空字符串並返回長度
                jsonArray.put(i,fileName.substring(index+1,fileName.length()));//返回圖片名稱
            }
            flag=true;
        }
        catch(IOException e2){
            e2.printStackTrace();
        }
        catch(JSONException e1){
            e1.printStackTrace();
        }
        finally{
            logOutConnection(ftpClient);
        }
        
        if(flag){
            try {
                obj.put("Message", "success");
                obj.put("data", jsonArray);
                callbackContext.success(obj);
            } catch (JSONException e) {
                e.printStackTrace();
            }
        }
        else{
            try {
                obj.put("Message", "failure");
                callbackContext.error(obj);
            } catch (JSONException e) {
                e.printStackTrace();
            }
        }
    }
    
    /**
     * 將文件上傳到FTPSERVER 服務器上
     * @param ip                 服務地址
     * @param fileName             上傳文件名稱
     * @param fileDirectory     指定上傳的目錄
     * @param callbackContext     返回成功的信息
     * */
    public void put(String ip,String fileName,String fileDirectory,CallbackContext callbackContext){
        FTPClient ftpClient=createConnection(ip);//登陸成功
        boolean flag=false;
        try{
            String path="/"+fileDirectory+"/";//須要切換的目錄
            String remotePath = new String(path.getBytes("GBK"), "ISO-8859-1");//服務器文件路徑
            ftpClient.changeWorkingDirectory(remotePath);//轉到服務器目錄
            ftpClient.setBufferSize(102400);//設置緩衝區大小,直接或者間接影響下載速度
            File file=new File(filePath+fileDirectory);//本地目錄
            File[] files=file.listFiles();
            for(File fs:files){
                InputStream fis=null;
                fis=new FileInputStream(filePath+fileDirectory+"/"+fs.getName());
                ftpClient.storeFile(new String(fs.getName().getBytes("GBK"),"ISO-8859-1"), fis);
                fis.close();
            }
            flag=true;
            ftpClient.logout();
        }
        catch(IOException e){
            e.printStackTrace();
        }
        finally{
            try {
                if(ftpClient.isConnected()){
                    ftpClient.disconnect();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        if(flag){
            callbackContext.success("success");
        }
        else{
            callbackContext.error("failure");
        }
    }
    
    /**
    *從服務下載文件
    *@param ip                 服務器IP地址
    *@param fileName         下載文件名稱
    *@param fileDirectory     指定下載的目錄
    *@param callbackContext 返回成功的信息
    */
    public void get(String ip,String fileName,String fileDirectory,CallbackContext callbackContext){
        FTPClient ftpClient=createConnection(ip);//登陸成功
        boolean flag=false;
        try {
            ftpClient.setBufferSize(102400);//設置緩衝區大小,直接或者間接影響下載速度
            String path="/"+fileDirectory+"/";//須要切換的目錄
            String remotePath = new String(path.getBytes("GBK"), "ISO-8859-1");//服務器文件路徑
            ftpClient.changeWorkingDirectory(remotePath);//轉到服務器目錄
            
            String localPath=filePath+fileDirectory;//本地目錄
            
            FTPFile[] ftpFiles=ftpClient.listFiles();//獲得目錄的相應文件列表
            for(FTPFile ftpFile:ftpFiles){
                int index=ftpFile.getName().lastIndexOf("\t");//去掉空字符串並返回長度
                String name=ftpFile.getName().substring(index+1,ftpFile.getName().length());//返回圖片名稱
                if(fileName.equals(name)){
                    File localFile=new File(this.createDirectory(localPath)+"/"+fileName);//根據絕對路徑初始化文件
                    singleFile(ftpClient,localFile, fileName);//單文件下載
                    flag=true;
                }
                else if(fileName.isEmpty()){//文件名稱爲空的時候將下載整個目錄中的文件
                    System.out.println();
                    File localFile=new File(this.createDirectory(localPath)+"/"+name);//根據絕對路徑初始化文件
                    singleFile(ftpClient,localFile, name);//單文件下載
                    flag=true;
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        finally{
            this.logOutConnection(ftpClient);
            System.out.println(flag);
            //System.exit(flag ? 1 : 0); //退出進程
        }
        
        if(flag){
            callbackContext.success("success");
        }
        else{
            callbackContext.error("failure");
        }
    }
    
    /**
     * 建立目錄
     * @param fileDirectory 路徑
     * */
    public File createDirectory(String fileDirectory){
        File sdcardFile=new File(fileDirectory);//本地目錄
        if(!sdcardFile.exists()){//檢測目錄是否存在
            sdcardFile.mkdirs();//若是不存在就建立目錄-----注意mkdirs()與mkdir()的區別
        }
        return sdcardFile;
    }
    
    /**
     * 單文件下載
     * @param ftpClient 客戶端對象
     * @param localPath 本地存儲目錄
     * @param fileName     文件名稱
     * */
    public void singleFile(FTPClient ftpClient,File localFile,String fileName){
        try{
            OutputStream outputstream=new FileOutputStream(localFile);//輸出流
            ftpClient.retrieveFile(new String(fileName.getBytes("GBK"),"ISO-8859-1"), outputstream);//下載文件
            outputstream.flush();
            outputstream.close();//關閉流 
        }
        catch(IOException e){
            e.printStackTrace();
        }
    }
    
    /**
    * 建立一個FTP SERVER 
    * @param ip   is FTPSERVER URL
    */
    public FTPClient createConnection(String ip){
        FTPClient ftpClient=new FTPClient();//建立一個客戶端對象
        try{
            int reply;
            ftpClient.connect(ip, port);//進行鏈接
            reply=ftpClient.getReplyCode();//獲取響應值
            if(!FTPReply.isPositiveCompletion(reply)){
                ftpClient.disconnect();//斷開鏈接
                System.out.println("鏈接服務器失敗");  
            }
            // 下面三行代碼必需要,並且不能改變編碼格式
            ftpClient.setControlEncoding("GBK");
            
            // 若是採用默認端口,能夠使用ftp.connect(url) 的方式直接鏈接FTP服務器  
            ftpClient.login(username, password);//登陸
            //ftpClient.enterLocalPassiveMode();//使用被動模式
            reply=ftpClient.getReplyCode();//回執碼
            if(!FTPReply.isPositiveCompletion(reply)){
                ftpClient.disconnect();
                 System.out.println("鏈接服務器失敗");  
            }
            else{
                FTPClientConfig conf=new FTPClientConfig(FTPClientConfig.SYST_NT);
                conf.setServerLanguageCode("zh");
                ftpClient.setFileType(FTPClient.BINARY_FILE_TYPE);//設置文件類型
            }
              System.out.println("login");
        }
        catch(IOException e){
            e.printStackTrace();
        }
        return ftpClient;
    }
    
    /**
    *    退出登陸並斷開鏈接
    * @param ftpClient FTP客戶端對象
    */
    public void logOutConnection(FTPClient ftpClient){
        try {
            ftpClient.logout();
        } catch (IOException e1) {
            e1.printStackTrace();
        }
        
        try {
            if(ftpClient.isConnected()){
                ftpClient.disconnect();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

AndroidManifest.xml中設置權限:apache

<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS" />
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
    <uses-permission android:name="android.permission.READ_PHONE_STATE" />
    <uses-permission android:name="android.permission.VIBRATE" />

在res/config.xml中添加:json

<feature name="FtpClient">
        <param name="android-package" value="com.JajaCy.FtpClient.FtpClientPlugin"/>
    </feature>

assets\www\plugins\com.JajaCy.FtpClient這個目錄中建一個名稱爲FtpClientPlugin.js的js文件數組

cordova.define('com.JajaCy.FtpClient.FtpClientPlugin', function(require, exports, module) {
    var exec=require('cordova/exec');
    module.exports={
        /**
        * 獲取文件列表
        * param:data
        */
        getFiles:function(data1,data2,fn){
            /**
            一共五個參數
            第一個 :成功會掉 
            第二個 :失敗回調 
            第三個 :將要調用的類的配置名字(在config.xml中配置 稍後在下面會講解) 
            第四個 :調用的方法名(一個類裏可能有多個方法 靠這個參數區分) 
            第五個 :傳遞的參數  以json的格式 
            */
            exec(function(result){
                console.log(result.Message);
                fn(result);//JSON.parse(result)
            },nativePluginErrorHandler,"FtpClient","list",[data1,data2])
        },
        /**
        * 上傳文件
        * data1:服務器ip地址
        * data2:文件名稱
        * data3:當前目錄名稱
        */
        put:function(data1,data2,data3,fn){
            exec(function(result){
            fn(result);
            },nativePluginErrorHandler,"FtpClient","put",[data1,data2,data3])
        },
        /**
        * 下載文件
        * data1:服務器ip地址
        * data2:文件名稱
        * data3:當前目錄名稱
        */
        get:function(data1,data2,data3,fn){
            exec(function(result){
            fn(result);
            },nativePluginErrorHandler,"FtpClient","get",[data1,data2,data3])
        }
    }
});

 /**
成功時調用的方法
*/
function nativePluginResultHandler (result) {   
   //alert("SUCCESS: \r\n"+result );   
   console.log(result);
} 
/**
失敗時調用的方法
*/  
function nativePluginErrorHandler (error) {   
   alert("ERROR: \r\n"+error );   
}

而後在cordova_plugins.js這個文件中進行插件配置:服務器

{
    "file": "plugins/com.JajaCy.FtpClient/FtpClientPlugin.js",
        "id": "com.JajaCy.FtpClient.FtpClientPlugin",
        "clobbers": [
            "window.ftp"   //調用的方法名
        ]
}

在module.exports.metadata中添加:ide

module.exports.metadata = 
// TOP OF METADATA
{
    "com.JajaCy.FtpClient":"0.0.1"
}

開始進行調用:ui

window.ftp.get("192.168.1.108", '','image', function (data) {//下載指定目錄的文件
            if (data == "success") {
                Ext.Msg.alert("菜品圖片下載完成");
            }
            else{
                Ext.Msg.alert("未鏈接服務器!");
            }
        });
window.ftp.put("192.168.1.108", '','image', function (data) {//上傳指定目錄的文件
            if (data == "success") {
                Ext.Viewport.unmask();
                Ext.Msg.alert("菜品圖片下載完成");
            }
            else{
                Ext.Viewport.unmask();
                Ext.Msg.alert("未鏈接服務器!");
            }
        });
相關文章
相關標籤/搜索