1 /* 2 * Copyright 2018 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package androidx.media; 18 19 import static org.junit.Assert.fail; 20 21 import android.os.Handler; 22 23 import androidx.annotation.GuardedBy; 24 import androidx.media.MediaLibraryService2.MediaLibrarySession.MediaLibrarySessionCallback; 25 import androidx.media.TestUtils.SyncHandler; 26 27 /** 28 * Keeps the instance of currently running {@link MockMediaSessionService2}. And also provides 29 * a way to control them in one place. 30 * <p> 31 * It only support only one service at a time. 32 */ 33 public class TestServiceRegistry { 34 @GuardedBy("TestServiceRegistry.class") 35 private static TestServiceRegistry sInstance; 36 @GuardedBy("TestServiceRegistry.class") 37 private MediaSessionService2 mService; 38 @GuardedBy("TestServiceRegistry.class") 39 private SyncHandler mHandler; 40 @GuardedBy("TestServiceRegistry.class") 41 private MediaLibrarySessionCallback mSessionCallback; 42 @GuardedBy("TestServiceRegistry.class") 43 private SessionServiceCallback mSessionServiceCallback; 44 45 /** 46 * Callback for session service's lifecyle (onCreate() / onDestroy()) 47 */ 48 public interface SessionServiceCallback { onCreated()49 void onCreated(); onDestroyed()50 void onDestroyed(); 51 } 52 getInstance()53 public static TestServiceRegistry getInstance() { 54 synchronized (TestServiceRegistry.class) { 55 if (sInstance == null) { 56 sInstance = new TestServiceRegistry(); 57 } 58 return sInstance; 59 } 60 } 61 setHandler(Handler handler)62 public void setHandler(Handler handler) { 63 synchronized (TestServiceRegistry.class) { 64 mHandler = new SyncHandler(handler.getLooper()); 65 } 66 } 67 getHandler()68 public Handler getHandler() { 69 synchronized (TestServiceRegistry.class) { 70 return mHandler; 71 } 72 } 73 setSessionServiceCallback(SessionServiceCallback sessionServiceCallback)74 public void setSessionServiceCallback(SessionServiceCallback sessionServiceCallback) { 75 synchronized (TestServiceRegistry.class) { 76 mSessionServiceCallback = sessionServiceCallback; 77 } 78 } 79 setSessionCallback(MediaLibrarySessionCallback sessionCallback)80 public void setSessionCallback(MediaLibrarySessionCallback sessionCallback) { 81 synchronized (TestServiceRegistry.class) { 82 mSessionCallback = sessionCallback; 83 } 84 } 85 getSessionCallback()86 public MediaLibrarySessionCallback getSessionCallback() { 87 synchronized (TestServiceRegistry.class) { 88 return mSessionCallback; 89 } 90 } 91 setServiceInstance(MediaSessionService2 service)92 public void setServiceInstance(MediaSessionService2 service) { 93 synchronized (TestServiceRegistry.class) { 94 if (mService != null) { 95 fail("Previous service instance is still running. Clean up manually to ensure" 96 + " previoulsy running service doesn't break current test"); 97 } 98 mService = service; 99 if (mSessionServiceCallback != null) { 100 mSessionServiceCallback.onCreated(); 101 } 102 } 103 } 104 getServiceInstance()105 public MediaSessionService2 getServiceInstance() { 106 synchronized (TestServiceRegistry.class) { 107 return mService; 108 } 109 } 110 cleanUp()111 public void cleanUp() { 112 synchronized (TestServiceRegistry.class) { 113 if (mService != null) { 114 // TODO(jaewan): Remove this, and override SessionService#onDestroy() to do this 115 mService.getSession().close(); 116 // stopSelf() would not kill service while the binder connection established by 117 // bindService() exists, and close() above will do the job instead. 118 // So stopSelf() isn't really needed, but just for sure. 119 mService.stopSelf(); 120 mService = null; 121 } 122 if (mHandler != null) { 123 mHandler.removeCallbacksAndMessages(null); 124 } 125 mSessionCallback = null; 126 if (mSessionServiceCallback != null) { 127 mSessionServiceCallback.onDestroyed(); 128 mSessionServiceCallback = null; 129 } 130 } 131 } 132 } 133