mayubao / KuaiChuan

仿茄子快传的一款文件传输应用

Home Page:http://www.jianshu.com/p/1b0b337829f5

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

android6.0传输异常

hardstruglling opened this issue · comments

两台android6.0真机,开启热点接收文件,发送端点击发送文件,发送端有时会报SocketException,传输就中断了,测试了6次,只有一次传输成功

Opps... 这个库是我 fock 别人的,您可以使用我们滴滴开源的 Socket 库 OkSocket 来完成您的业务需求

@hardstruglling
1.确保是否android 6.0是否未分配权限的问题
2.如果未分配权限,请自行动态申请权限。如果分配了权限,打断点看看具体流程是不是有什么问题,比如说,开启热点方未初始化整个局域网等等

今天debug查看下代码,是接收端接收到发送端通过udp发来的消息调用了关闭socket的方法,致使socket连接中断,不知道您当时为什么会调用关闭socket方法,是担心阻塞下一次的文件传输还是有其它什么左右作用?

1.请贴出代码块==》》接收端接收到发送端通过udp发来的消息调用了关闭socket的方法~
2.而对于文件传输的问题,我每一个文件的传输都是用一个tcp连接去实现的~然而每一次tcp链接的结束肯定是要去关闭对应的tcp链接的socket
@hardstruglling

在等待接收界面ReceiverWaitingActivity中调用startFileReceiverServer()方法
/**
* 开启 文件接收方 通信服务 (必须在子线程执行)
* @param serverPort
* @throws Exception
*/
private void startFileReceiverServer(int serverPort) throws Exception{

    //网络连接上,无法获取IP的问题
    int count = 0;
    String localAddress = WifiMgr.getInstance(getContext()).getHotspotLocalIpAddress();
    while(localAddress.equals(Constant.DEFAULT_UNKOWN_IP) && count <  Constant.DEFAULT_TRY_TIME){
        Thread.sleep(1000);
        localAddress = WifiMgr.getInstance(getContext()).getHotspotLocalIpAddress();
        Log.i(TAG, "receiver get local Ip ----->>>" + localAddress);
        count ++;
    }

    mDatagramSocket = new DatagramSocket(serverPort);
    byte[] receiveData = new byte[1024];
    byte[] sendData = null;
    while(true) {
        DatagramPacket receivePacket = new DatagramPacket(receiveData, receiveData.length);
        mDatagramSocket.receive(receivePacket);
        String msg = new String( receivePacket.getData()).trim();
        InetAddress inetAddress = receivePacket.getAddress();
        int port = receivePacket.getPort();
        Log.i(TAG, "Get the msg from FileReceiver######>>>" + Constant.MSG_FILE_RECEIVER_INIT);
        if(msg != null && msg.startsWith(Constant.MSG_FILE_RECEIVER_INIT)){
          Log.i(TAG, "Get the msg from FileReceiver######>>>" + Constant.MSG_FILE_RECEIVER_INIT);
            // 进入文件接收列表界面 (文件接收列表界面需要 通知 文件发送方发送 文件开始传输UDP通知)
            mHandler.obtainMessage(MSG_TO_FILE_RECEIVER_UI, new IpPortInfo(inetAddress, 
                                              port)).sendToTarget();
           }else{ //接收发送方的 文件列表
            if(msg != null){

// FileInfo fileInfo = FileInfo.toObject(msg);
System.out.println("Get the FileInfo from FileReceiver######>>>" + msg);
parseFileInfo(msg);
}
}
}
如果收到发送端发来的消息通知Constant.MSG_FILE_RECEIVER_INIT)就会跳转到文件接收列表界面
Handler mHandler = new Handler(){
@OverRide
public void handleMessage(Message msg) {
//接收到消息跳转文件列表界面
if(msg.what == MSG_TO_FILE_RECEIVER_UI){
IpPortInfo ipPortInfo = (IpPortInfo) msg.obj;
Bundle bundle = new Bundle();
bundle.putSerializable(Constant.KEY_IP_PORT_INFO, ipPortInfo);
NavigatorUtils.toFileReceiverListUI(getContext(), bundle);
finishNormal();
}
}
};
此时是与发送端建立连接进行数据传输,而在跳转之后却调用了finishNormal()关闭连接的方法
/**
* 成功进入 文件接收列表UI 调用的finishNormal()
*/
private void finishNormal(){
if(mWifiAPBroadcastReceiver != null){
unregisterReceiver(mWifiAPBroadcastReceiver);
mWifiAPBroadcastReceiver = null;
}
//关闭socket
closeSocket();
this.finish();
}
@mayubao 关闭了连接进入文件列表接收界面通信就会断了

按照流程来讲的话,closeSocket()只是关闭了传输文件列表的mDatagramSocket,不管文件实际传输的问题~你再排查一下,先用Android6.0或者其他机型的手机测试一下先
@hardstruglling

@mayubao 在Handler接收的消息处理中如果注释了不调用finishNormal真机测试每次都可以正常传输,如果调用了finishNormal真机测试十几次最多也就一次可以正常传输

这个问题我也没查到什么原因造成的,FileReceiverActivity界面才会开启ServerSocket,FileSenderActivity开启Socket进行数据传输,但是只要ReceiverWaitingActivity中调用了finishNormal或者直接finish界面,FileSender都会报SocketException异常,而ReceiverWaitingActivity跳转界面的时候什么操作都不做,则可以正常传输

@mayubao 担心资源没有及时回收 可以在FileReceiverActivity中当文件接收完后给ReceiverWaitingActivity发送一个广播去关闭socket

可以的,只要逻辑走的通就行~
此项目现在已经没有时间去维护了~
@hardstruglling