服务android中的内存泄漏

时间:2015-01-02 12:08:46

标签: java android node.js sockets memory-leaks

我正在为 bound service 维护实现 socket.io 实施的single socket,以便通过此连接与nodejs服务器连接Gottox library。当我实施此服务时,memory服务的not stable就像启动服务时一样30MB40MB,一段时间之后它也会导致200MB 1}}。所以我认为它可能是 memory leak 。但我找不到任何单一的线索。

代码

DemoActivity.java

import org.json.JSONException;
import org.json.JSONObject;

import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;

import com.actionbarsherlock.app.SherlockActivity;
import com.devspark.appmsg.AppMsg;
import com.devspark.appmsg.AppMsg.Style;
import com.nuappz.Demo.DemoService.MyLocalBinder;
import com.nuappz.Demo.handler.ResponseHandler;
import com.nuappz.Demo.helper.MySharedPreferences;

public class DemoActivity extends SherlockActivity {

    MySharedPreferences pref;
    DemoService socketService;
    boolean isBound;
    EditText name, mobile_no, email, password;
    Button Demo;
    Style style_alert, style_success;
    JSONObject json_Demo;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_Demo);

        isBound = false;

    }

    @Override
    protected void onResume() {
        // TODO Auto-generated method stub
        super.onResume();
        // start the bind service
        if (!isBound) {
            bindService(new Intent(DemoActivity.this,
                    DemoService.class), myConnection,
                    Context.BIND_AUTO_CREATE);
            isBound = true;
            startService(new Intent(this, DemoService.class));
            socketService = DemoService.getInstance();

        }
    }

    public ServiceConnection myConnection = new ServiceConnection() {

        @Override
        public void onServiceDisconnected(ComponentName name) {
            // TODO Auto-generated method stub
            isBound = false;

        }

        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            // TODO Auto-generated method stub
            socketService = ((MyLocalBinder) service).getService();
            isBound = true;
        }
    };

    protected void onDestroy() {
        if (isBound) {
            // Disconnect from an application service. You will no longer
            // receive calls as the service is restarted, and the service is
            // now allowed to stop at any time.
            unbindService(myConnection);
            isBound = false;
        }
        stopService(new Intent(DemoActivity.this, DemoService.class));
        super.onDestroy();
    }

}

DemoService.java

import io.socket.IOAcknowledge;
import io.socket.IOCallback;
import io.socket.SocketIO;
import io.socket.SocketIOException;

import java.net.MalformedURLException;
import java.security.NoSuchAlgorithmException;

import javax.net.ssl.SSLContext;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import android.app.Service;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log;

import com.nuappz.Demo.handler.ResponseHandler;
import com.nuappz.Demo.helper.MySharedPreferences;

/*
 * This class is Background service for the Blood Drop application
 */
public class DemoService extends Service {
    private static final String serverUrl = "http://nuappzdev.hello.com:8080/";
    private static SocketIO socket;
    private static DemoService instance;
    private static ResponseHandler handler;
    public boolean bound;
    JSONObject jobj_in = new JSONObject();

    @Override
    public void onCreate() {
        // TODO Auto-generated method stub
        Log.d("Service", "Started");
        super.onCreate();

        // connecting socket
        try {
            DemoService.initInstance();
        } catch (MalformedURLException e1) {
            // TODO Auto-generated catch block
            e1.printStackTrace();
        }
    }

    public DemoService() {

    }

    public static DemoService getInstance() {
        return instance;
    }

    // start the service to handle the functions
    public int onStartCommand(Intent intent, int flags, int startId) {
        // HandleReceiveRequest();
        return START_STICKY;
    }

    // Stop the services
    public void onDestroy() {
        Log.d("Service", "Stopped");
        getSocket().disconnect();

    }

    // Binder class initialize
    public class MyLocalBinder extends Binder {
        DemoService getService() {
            return DemoService.this;
        }
    }

    private final IBinder myBinder = new MyLocalBinder();

    @Override
    public IBinder onBind(Intent arg0) {
        // TODO Auto-generated method stub
        bound = true;
        return myBinder;
    }

    // initiate the socket connection
    public static void initInstance() throws MalformedURLException {
        if (instance == null) {
            instance = new DemoService();
            if (DemoService.getSocket() == null) {
                DemoService.setSocket(new SocketIO());
            }
            DemoService.connectIO();
        }
    }

    // Method to get socket
    public static SocketIO getSocket() {
        return socket;
    }

    // Method to set socket
    public static void setSocket(SocketIO socket) {
        DemoService.socket = socket;
    }

    // Method to ConnectIO to server
    public static void connectIO() throws MalformedURLException {

        try {
            SocketIO.setDefaultSSLSocketFactory(SSLContext.getDefault());
        } catch (NoSuchAlgorithmException e1) {
            // TODO Auto-generated catch block
            e1.printStackTrace();
        }
        DemoService.getSocket().connect(serverUrl, new IOCallback() {
            @Override
            public void onMessage(JSONObject json, IOAcknowledge ack) {
                // TODO Auto-generated method stub
            }

            @Override
            public void onMessage(String data, IOAcknowledge ack) {

            }

            @Override
            public void onError(SocketIOException socketIOException) {
                Log.d("Connection:", "Error in Connection");

            }

            @Override
            public void onDisconnect() {
                // TODO Auto-generated method stub
                Log.d("Connection:", "disConnected");
            }

            @Override
            public void onConnect() {
                Log.d("Connection:", "Connected");
            }

            @Override
            // Method to getting response from server
            public void on(String event, IOAcknowledge ack, Object... args) {
                JSONArray jarr_args = new JSONArray();
                JSONObject jobj_in = new JSONObject();
                try {
                    jarr_args.put(args[0]);
                    jobj_in = jarr_args.getJSONObject(0);
                    jobj_in.put("event", event);
                    Log.d("jobject: event", jobj_in.getString("event"));
                    try {
                        handler.handleObject(jobj_in);

                    } catch (Exception e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }
                } catch (JSONException e1) {
                    // TODO Auto-generated catch block
                    e1.printStackTrace();
                }

            }

        });

    }

    // Method to send request to server
    public static void emit(String event, Object args,
            ResponseHandler responseHandler) throws MalformedURLException {
        handler = responseHandler;
        if (DemoService.getSocket().isConnected() == false) {
            DemoService.getSocket().reconnect();
        }
        DemoService.getSocket().emit(event, args);
    }

    // Method to send request to server with Acknowledge
    public static void emitWithAcknowledge(String event, Object args)
            throws MalformedURLException {
        if (DemoService.getSocket().isConnected() == false) {
            DemoService.getSocket().reconnect();
        }
        DemoService.getSocket().emit(event, new IOAcknowledge() {

            @Override
            public void ack(Object... args) {
                // TODO Auto-generated method stub

            }
        }, args);
    }


    }

}

此代码中存在内存泄漏的可能性。

1 个答案:

答案 0 :(得分:0)

您需要在活动的onStop中取消绑定服务,并且绝不应该从您的活动中调用stopService。让Android处理您服务的生命周期。