0

내 앱에 있습니다. 앱이 백그라운드에서 알림을 수신하도록 서비스를 시작합니다.이 서비스는 앱을 중지 한 후 자동으로 앱이 시작되도록합니다. 보류중인 의도를 사용하여 문제를 해결하려고했지만 여전히 발생합니다. 난 내가 NullPointerException이 얻을 externalreceiver를 통해 서비스를 호출하는 경우안드로이드 실행 서비스가 자동으로 시작됩니다

Intent messageReceivingIntent = new Intent(this, MessageReceivingService.class); 
messageReceivingIntent.putExtra("myUserId", myUserId); 
Pending Inten messagePendingIntent = PendingIntent.getService(this, 0, messageReceivingIntent, PendingIntent.FLAG_UPDATE_CURRENT); 

    try { 
     // Perform the operation associated with our pendingIntent 
     messagePendingIntent.send(); 
    } catch (PendingIntent.CanceledException e) { 
     e.printStackTrace(); 
    } 

:

다음은 서비스를 시작하는 나의 의도이다. 왜 어떤 생각?

이 내 브로드 캐스트 리시버 호출입니다 : 여기

messageReceivingIntent = new Intent(this, MessageReceivingService.class); 
messageReceivingIntent.putExtra("myUserId", myUserId); 
messageReceivingIntent.setAction("com.example.androidtest"); 
sendBroadcast(messageReceivingIntent); 

내 방송 수신기

public class ExternalReceiver extends BroadcastReceiver { 

@Override 
public void onReceive(Context context, Intent intent) { 
    if(intent!=null){ 
     Bundle extras = intent.getExtras(); 
     if(!MapsActivity.inBackground){ 
      MessageReceivingService.sendToApp(extras, context); 
     } 
     else{ 
      MessageReceivingService.saveToLog(extras, context); 
     } 
    } 
} 

}

이이 MessageReceivingService

public class MessageReceivingService extends Service { 
private GoogleCloudMessaging gcm; 
public static SharedPreferences savedValues; 

public static final String INSTANCE_ID_SCOPE = "GCM"; 
final String BASE_URL = "http://www.example.com/"; 

public String myUserId; 
public String registeredUserId; 
public String token; 
static PendingIntent pendingIntent; 


public static void sendToApp(Bundle extras, Context context) { 
    Intent newIntent = new Intent(); 
    newIntent.setClass(context, MapsActivity.class); 
    newIntent.putExtras(extras); 

    ShortcutBadger.applyCount(Content.getAppContext(), 0); 

    newIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 
    context.startActivity(newIntent); 
} 

public void onCreate() { 
    super.onCreate(); 
    final String preferences = getString(R.string.preferences); 
    savedValues = getSharedPreferences(preferences, Context.MODE_PRIVATE); 
    // In later versions multi_process is no longer the default 
    if (VERSION.SDK_INT > 9) { 
     savedValues = getSharedPreferences(preferences, Context.MODE_MULTI_PROCESS); 
    } 
    gcm = GoogleCloudMessaging.getInstance(getBaseContext()); 






    // Let AndroidMobilePushApp know we have just initialized and there may be stored messages 
    sendToApp(new Bundle(), this); 
} 

protected static void saveToLog(Bundle extras, Context context) { 
    SharedPreferences.Editor editor = savedValues.edit(); 
    String numOfMissedMessages = context.getString(R.string.num_of_missed_messages); 
    int linesOfMessageCount = 0; 

    for (String key : extras.keySet()) { 
     String line = String.format("%s=%s", key, extras.getString(key)); 
     editor.putString(key, line); 
     linesOfMessageCount++; 
    } 
    editor.putInt(context.getString(R.string.lines_of_message_count), linesOfMessageCount); 
    editor.putInt(context.getString(R.string.lines_of_message_count), linesOfMessageCount); 
    editor.putInt(numOfMissedMessages, savedValues.getInt(numOfMissedMessages, 0) + 1); 
    editor.commit(); 

    String type = extras.getString("model"); 
    String id = extras.getString("id"); 
    String userId = extras.getString("user_id"); 

    //postNotification(new Intent(context, MapsActivity.class), context); 
    if(type != null) { 
     if (type.equals("content")) { 
      Intent contentIntent = new Intent(context, ContentDetailActivity.class); 

      Log.v("userID", userId); 

      contentIntent.putExtra("contentId", id); 
      if (userId != null) { 
       contentIntent.putExtra("userId", userId); 
      } 

      postNotification(contentIntent, context); 
     } else if (type.equals("user")) { 
      Intent userIntent = new Intent(context, ProfileActivity.class); 
      userIntent.putExtra("userId", id); 

      postNotification(userIntent, context); 
     } 
    } else { 
     postNotification(new Intent(context, NotificationsActivity.class), context); 
    } 

    ShortcutBadger.applyCount(Content.getAppContext(), Integer.valueOf(savedValues.getInt(Content.getAppContext().getString(R.string.num_of_missed_messages), 0))); 
} 

protected static void postNotification(Intent intentAction, Context context) { 
    final NotificationManager mNotificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE); 

    pendingIntent = PendingIntent.getActivity(context, 0, intentAction, PendingIntent.FLAG_UPDATE_CURRENT); 

    int numOfMissedMessages = 0; 
    String missedMessage = ""; 
    if(savedValues != null){ 
     missedMessage = savedValues.getString("message", "nothing there"); 
    } 



    Log.v("NUMOFMISSEDMESSAGES", String.valueOf(numOfMissedMessages)); 

    final Notification notification = new NotificationCompat.Builder(context).setSmallIcon(R.drawable.ic_launcher) 
      .setContentTitle(missedMessage.substring(missedMessage.indexOf("=") + 1, missedMessage.length())) 
      .setContentText("") 
      .setContentIntent(pendingIntent) 
      .setAutoCancel(true) 
      .build(); 
    mNotificationManager.notify(R.string.notification_number, notification); 
} 

private void register() { 
    new AsyncTask() { 
     protected Object doInBackground(final Object... params) { 

      try { 
       String instanceId = InstanceID.getInstance(getApplicationContext()).getId(); 
       //token = gcm.register(getString(R.string.project_number)); 
       token = InstanceID.getInstance(getApplicationContext()).getToken(getString(R.string.project_number), INSTANCE_ID_SCOPE); 
       Log.i("registrationId", token); 
      } catch (IOException e) { 
       Log.i("Registration Error", e.getMessage()); 
      } 
      return true; 
     } 

     @Override 
     protected void onPostExecute(Object o) { 
      super.onPostExecute(o); 
      new SendRegUserId().execute(); 
     } 
    }.execute(); 
} 

public IBinder onBind(Intent arg0) { 
    return null; 
} 
} 
+0

방송 수신자를 사용하고 있습니까? – SQLiteNoob

+0

'서비스'에서 많은 정적 변수를 사용하고 있습니다. 이것은 아마 당신의 문제의 원인 일 것입니다. 'NullPointerException'을 얻는다면 logcat에서 stacktrace를 포함한 에러 메시지를 게시하고 그 시점에서 무슨 일이 벌어 졌는지 설명하십시오. 또한,'Service'의'onStartCommand()'코드를 게시하십시오. –

답변

2

01을 사용하는 것입니다을 클릭하여 알림을 수신 한 다음 Service으로 보내주십시오. 그러면 앱을 시작하지 않고 notification을 사용자에게 보낼 수 있습니다.

=========
편집 1 :

그래서 방송 수신기는 메서드를 호출하는 대신 서비스를 시작해야합니다. 그래서 의도에 대한 검사는 null 이후의 라인을 따라 뭔가 : 또한

ComponentName comp = new ComponentName(context.getPackageName(), YourIntentService.class.getName()); 
    startWakefulService(context, (intent.setComponent(comp)); 
    setResultCode(Activity.RESULT_OK); 

, 당신의 당신은 아직도 전화가 꺼져있어 후 알림을 수신 할 경우 Broadcast ReceiverWakefulBroadcastReceiver를 확장해야합니다.

또한 ServiceIntentService이어야합니다. Android Studio에는 실제로 미리 만들어진 GCM 클래스 또는 GCM 앱이 포함되어있어 실제로 이러한 작은 문제의 90 %를 처리 할 것입니다. 더 나은 출발점입니다.

자세한 내용은 GCM docs을 확인하십시오.

+0

저는 gcm과 오랜 시간 씨름을 해왔고 문제가있었습니다. 나는 자기 출발 문제와 별개로 잘 작동하기 때문에 주어진 코드를 고치고 싶다. 꽤 심오합니다. – rudi

+0

진지하게 https://github.com/googlesamples/google-services/tree/master/android/gcm을 확인하고 유스 케이스를 샘플에 통합하는 것을 고려해보십시오. 가서 두통을 많이 줄 것입니다. GCM은 항상 변경되고 (현재는 Firebase) 매 반복마다 수동으로 코드를 업데이트해야합니다. 일을 수행하는 것이 좋습니다. – SQLiteNoob

0

몇 가지 가능한 솔루션 -

1)를 사용하여 브로드 캐스트 리시버

2) 사용 onPause(), onResume() 메소드

SharedPreferences prefs=PreferenceManager.getDefaultSharedPreferences(getApplicationContext()); 

Intent messageReceivingIntent = new Intent(this,MessageReceivingService.class); 

    onCreate(){ 

    //YOUR OWN CODE 
    prefs.getBoolean("service_started",false); 
} 

onPause(){ 

//YOUR OWN CODE 
prefs.edit().putBoolean("service_started",true).apply(); 
startService(messageReceivingIntent); 
} 

onResume(){ 

//YOUR OWN CODE 
if(prefs.getBoolean("service_started",false)){ 
    stopService(new Intent(this, MessageReceivingService.class)); 
    prefs.edit().putBoolean("service_started",false).apply(); 
} 
} 

3

) 또는 나에게 따라 할 수있는 최선의 일부 알림을 위해 Firebase Cloud Messaging을 구현하는 것입니다.

확인이 밖으로 https://firebase.google.com/docs/cloud-messaging/

그것은 당신의 배터리와 서버 노력을 많이 줄일 수 있습니다. Google의 새로운 서비스.

또는 서비스 코드에 버그가있을 수 있습니다.

관련 문제