android -implications of creating an instance of a Service class

1.1k views Asked by At

I inherited some android code and i notice there is a class extending Service but its not declared in the manifest. I find this disturbing. i investigated further and i see that the service is not declared in the manifest yet it still works !

what is occuring is in an activities onResume the developer is calling the following:

@Override
    protected void onResume() {
        super.onResume();
mMyService = new MyService();
}


 @Override
    protected void onStart() {
        super.onStart();
     mMyService = new MyService();
}

i have never seen this practice before. would it cause a memory leak ? android components are declared in the manifest and never instantiated right ? The system takes care of it for you.

The service itself is declared like this

public class MyService extends Service {

    @Nullable
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

    @Override
    public void onCreate() {
        super.onCreate();
    }


    //... a bunch of other methods that do stuff by calling from the "new" instance would be below.

}

Again, nothing is declared in the manifest. is this another pattern, and is it safe ?

2

There are 2 answers

0
Andy Res On BEST ANSWER

i investigated further and i see that the service is not declared in the manifest yet it still works !

It "works" because the class is used as a regular java class - it has fields and public methods that you can call, but this is no longer an Android Service. An Android Service is a component intended to perform long running operations in background, it has a life-cycle, and also a reference to Context.

For example when creating the service instance with: MyService service = new MyService() you will notice that onCreate() method of the class is not called, and if you try to do something that involves the use of the Context, such as showing a Toast, you will get an exception.

0
CommonsWare On

would it cause a memory leak ?

Not intrinsically. MyService would be no more prone to being leaked than would any other Java object.

android components are declared in the manifest and never instantiated right ?

The only Android component that you sometimes instantiate yourself is a BroadcastReceiver, and then only if you are using registerReceiver(). Otherwise, the framework classes instantiate your components.

is this another pattern

One from "developers" with limited experience. Usually, this sort of thing starts from somebody needing a Context for something or another, and so they randomly create some subclass of Activity or Service, thinking that they will be able to create an instance (e.g., new MyService()) and have a working Context. This rarely works, as the Context will not be initialized properly this way. Sometimes, the developer themselves is just copying some code that they saw somewhere else, such as the ridiculous number of Stack Overflow questions and answers revolving around a GPSService that is set up akin to your MyService.

Assuming that this class should exist at all (vs. being part of the activity), I recommend that you:

  • Remove extends Service

  • Remove the do-nothing methods that were marked as @Override, such as the onBind() and onCreate() methods in your code snippet

  • Fix any build errors that result in MyService no longer extending Service, by ensuring that those methods have access to a real Context object (e.g., the `Activity)