1 /* 2 * Copyright (C) 2016 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 android.app.stubs; 18 19 import android.app.Notification; 20 import android.app.NotificationChannel; 21 import android.app.NotificationManager; 22 import android.app.Service; 23 import android.content.Context; 24 import android.content.Intent; 25 import android.os.Bundle; 26 import android.os.IBinder; 27 import android.util.Log; 28 import android.app.stubs.R; 29 30 import com.android.compatibility.common.util.IBinderParcelable; 31 32 public class LocalForegroundService extends LocalService { 33 34 private static final String TAG = "LocalForegroundService"; 35 protected static final String EXTRA_COMMAND = "LocalForegroundService.command"; 36 private static final String NOTIFICATION_CHANNEL_ID = "cts/" + TAG; 37 38 public static final int COMMAND_START_FOREGROUND = 1; 39 public static final int COMMAND_STOP_FOREGROUND_REMOVE_NOTIFICATION = 2; 40 public static final int COMMAND_STOP_FOREGROUND_DONT_REMOVE_NOTIFICATION = 3; 41 public static final int COMMAND_STOP_FOREGROUND_DETACH_NOTIFICATION = 4; 42 public static final int COMMAND_STOP_FOREGROUND_REMOVE_NOTIFICATION_USING_FLAGS = 5; 43 public static final int COMMAND_START_NO_FOREGROUND = 6; 44 45 private int mNotificationId = 0; 46 47 @Override onCreate()48 public void onCreate() { 49 super.onCreate(); 50 Log.d(TAG, "service created: " + this + " in " + android.os.Process.myPid()); 51 } 52 53 /** Returns the channel id for this service */ getNotificationChannelId()54 protected String getNotificationChannelId() { 55 return NOTIFICATION_CHANNEL_ID; 56 } 57 58 @Override onStart(Intent intent, int startId)59 public void onStart(Intent intent, int startId) { 60 String notificationChannelId = getNotificationChannelId(); 61 NotificationManager notificationManager = getSystemService(NotificationManager.class); 62 notificationManager.createNotificationChannel(new NotificationChannel( 63 notificationChannelId, notificationChannelId, 64 NotificationManager.IMPORTANCE_DEFAULT)); 65 66 Context context = getApplicationContext(); 67 int command = intent.getIntExtra(EXTRA_COMMAND, -1); 68 69 Log.d(TAG, "service start cmd " + command + ", intent " + intent); 70 71 switch (command) { 72 case COMMAND_START_FOREGROUND: 73 mNotificationId ++; 74 Log.d(TAG, "Starting foreground using notification " + mNotificationId); 75 Notification notification = 76 new Notification.Builder(context, NOTIFICATION_CHANNEL_ID) 77 .setContentTitle(getNotificationTitle(mNotificationId)) 78 .setSmallIcon(R.drawable.black) 79 .build(); 80 startForeground(mNotificationId, notification); 81 break; 82 case COMMAND_STOP_FOREGROUND_REMOVE_NOTIFICATION: 83 Log.d(TAG, "Stopping foreground removing notification"); 84 stopForeground(true); 85 break; 86 case COMMAND_STOP_FOREGROUND_DONT_REMOVE_NOTIFICATION: 87 Log.d(TAG, "Stopping foreground without removing notification"); 88 stopForeground(false); 89 break; 90 case COMMAND_STOP_FOREGROUND_REMOVE_NOTIFICATION_USING_FLAGS: 91 Log.d(TAG, "Stopping foreground removing notification using flags"); 92 stopForeground(Service.STOP_FOREGROUND_REMOVE | Service.STOP_FOREGROUND_DETACH); 93 break; 94 case COMMAND_STOP_FOREGROUND_DETACH_NOTIFICATION: 95 Log.d(TAG, "Detaching foreground service notification"); 96 stopForeground(Service.STOP_FOREGROUND_DETACH); 97 break; 98 case COMMAND_START_NO_FOREGROUND: 99 Log.d(TAG, "Starting without calling startForeground()"); 100 break; 101 default: 102 Log.e(TAG, "Unknown command: " + command); 103 } 104 105 // Do parent's onStart at the end, so we don't race with the test code waiting for us to 106 // execute. 107 super.onStart(intent, startId); 108 } 109 110 @Override onDestroy()111 public void onDestroy() { 112 Log.d(TAG, "service destroyed: " + this + " in " + android.os.Process.myPid()); 113 super.onDestroy(); 114 } 115 newCommand(IBinder stateReceiver, int command)116 public static Bundle newCommand(IBinder stateReceiver, int command) { 117 Bundle bundle = new Bundle(); 118 bundle.putParcelable(LocalService.REPORT_OBJ_NAME, new IBinderParcelable(stateReceiver)); 119 bundle.putInt(EXTRA_COMMAND, command); 120 return bundle; 121 } 122 getNotificationTitle(int id)123 public static String getNotificationTitle(int id) { 124 return "I AM FOREGROOT #" + id; 125 } 126 } 127