编辑:发现我的邮件接收服务有推送通知的问题。如果我停止关闭应用程序的服务问题不再出现,但如果我点击我的手机收到的通知,它会从错误的活动启动我的应用程序... 在我的messagereceivingservice.java中我做了
postNotification(new Intent(context, NotificationsActivity.class), context);
这是问题吗?
我在Android上做一个应用程序,用户可以创建自己的个人资料与朋友互动。应用程序包括谷歌地图和推送通知实施。 我无法找到,因为当发生这种情况但是暂时如果用户停止或关闭应用程序,应用程序会在一段时间后自动重启。 因为我不能在这里发布我的所有代码,有没有人遇到过这个问题并且知道在哪里搜索这个问题的根源?可能是应用程序关闭时运行的任何服务强制应用程序重新启动?我必须说我非常绝望,因为应用程序本身完全可以解决这个问题。
至少这是我的AndroidManifest:
<?xml version="1.0" encoding="utf-8"?>
<!--
The ACCESS_COARSE/FINE_LOCATION permissions are not required to use
Google Maps Android API v2, but you must specify either coarse or fine
location permissions for the 'MyLocation' functionality.
-->
<uses-permission android:name="android.permission.INTERACT_ACROSS_USERS_FULL" />
<uses-permission android:name="com.google.android.providers.gsf.permission.READ_GSERVICES" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<!-- GCM -->
<uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" />
<uses-permission android:name="android.permission.GET_ACCOUNTS" />
<!-- GOOGLE CLOUD MESSAGING -->
<permission
android:name=".permission.C2D_MESSAGE"
android:protectionLevel="signature" />
<uses-permission android:name=".permission.C2D_MESSAGE" />
<!-- if you want to keep processor from sleeping when a message is received -->
<uses-permission android:name="android.permission.WAKE_LOCK" />
<uses-feature
android:glEsVersion="0x00020000"
android:required="true" />
<provider
android:name="com.facebook.FacebookContentProvider"
android:authorities="com.facebook.app.FacebookContentProvider1496945817221747"
android:exported="true" />
<application
android:largeHeap="true"
android:screenOrientation="portrait"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
<meta-data
android:name="com.facebook.sdk.ApplicationId"
android:value="@string/facebook_app_id" />
<activity
android:name=".SplashScreen"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".MainActivity"
android:label="@string/app_name"
android:theme="@style/AppTheme.NoActionBar" >
</activity>
<activity
android:name=".AddActivity"
android:label="@string/title_activity_add"
android:parentActivityName=".MainActivity"
android:theme="@style/AppTheme.NoActionBar" >
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".MainActivity" />
</activity>
<activity
android:name=".DiscoverActivity"
android:label="@string/title_activity_discover"
android:parentActivityName=".MainActivity"
android:theme="@style/AppTheme.NoActionBar" >
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".MainActivity" />
</activity>
<activity
android:name=".DetailActivity"
android:label="@string/title_activity_detail"
android:parentActivityName=".MainActivity"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
</activity>
<activity
android:name=".ProfileActivity"
android:label="@string/title_activity_profile"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
</activity>
<activity
android:name=".EditProfileActivity"
android:label="@string/title_activity_edit_profile"
android:parentActivityName=".ProfileActivity"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".ProfileActivity" />
</activity>
<!--
The API key for Google Maps-based APIs is defined as a string resource.
(See the file "res/values/google_maps_api.xml").
Note that the API key is linked to the encryption key used to sign the APK.
You need a different API key for each encryption key, including the release key that is used to
sign the APK for publishing.
You can define the keys for the debug and release targets in src/debug/ and src/release/.
-->
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="@string/google_maps_key" />
<meta-data
android:name="com.google.android.gms.version"
android:value="@integer/google_play_services_version" />
<activity
android:name=".MapsActivity"
android:label="@string/title_activity_maps"
android:screenOrientation="portrait" >
</activity>
<!-- FACEBOOK ACTIVITY -->
<activity
android:name="com.facebook.FacebookActivity"
android:configChanges="keyboard|keyboardHidden|screenLayout|screenSize|orientation"
android:label="@string/app_name"
android:theme="@android:style/Theme.Translucent.NoTitleBar" />
<activity
android:name=".FriendsActivity"
android:label="@string/title_activity_friends"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
</activity>
<activity
android:name=".RegisterActivity"
android:label="@string/title_activity_register"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
</activity>
<activity
android:name=".NotificationsActivity"
android:label="@string/title_activity_notifications"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
</activity>
<!-- GCM -->
<!-- android:name="com.google.android.gms.gcm.GcmReceiver" -->
<receiver
android:name=".ExternalReceiver"
android:permission="com.google.android.c2dm.permission.SEND" >
<intent-filter>
<action android:name="com.google.android.c2dm.intent.RECEIVE" />
<action android:name="com.google.android.c2dm.intent.REGISTRATION" />
<action android:name="com.google.android.c2dm.intent.REGISTER" />
<category android:name=".androidtest" />
</intent-filter>
</receiver>
<service
android:name=".NotificationService"
android:exported="false" >
</service>
<service
android:name=".LoadImageService"
android:exported="false" >
</service>
<service
android:name=".AddFriendService"
android:exported="false" >
</service>
<service
android:name=".AcceptFriendService"
android:exported="false" >
</service>
<service
android:name=".JoinService"
android:exported="false" >
</service>
<service
android:name=".DeleteService"
android:exported="false" >
</service>
<activity
android:name=".EditActivity"
android:label="@string/title_activity_edit"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
</activity>
<service
android:name=".MessageReceivingService"
android:label=".MessageReceivingService" >
<intent-filter>
<action android:name=".AndroidMobilePushApp" />
<action android:name=".ExternalReceiver" />
<category android:name=".androidtest" />
</intent-filter>
</service>
<activity
android:name=".BasesActivity"
android:label="@string/title_activity_bases"
android:theme="@style/Theme.AppCompat.Light.NoActionBar" >
</activity>
</application>
答案 0 :(得分:1)
检查您是否从服务开始活动。也许当你收到一些gcm推送
答案 1 :(得分:0)
这是我的MessageReceivingService.java
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;
public String myToken;
private final String AUTHORIZATION = "AUTHORIZATION";
public static void sendToApp(Bundle extras, Context context) {
Intent newIntent = new Intent();
newIntent.setClass(context, MapsActivity.class);
newIntent.putExtras(extras);
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());
SharedPreferences sharedPrefMyUserId = getSharedPreferences(getString(R.string.preferences_user_id), Context.MODE_PRIVATE);
String defaultUserId = getResources().getString(R.string.default_user_id);
myUserId = sharedPrefMyUserId.getString(getString(R.string.saved_user_id), defaultUserId);
SharedPreferences sharedPrefRegisteredUserId = getSharedPreferences(getString(R.string.preferences_register_user_id), Context.MODE_PRIVATE);
String defaultRegisteredUserId = getResources().getString(R.string.default_register_user_id);
registeredUserId = sharedPrefRegisteredUserId.getString(getString(R.string.saved_register_user_id), defaultRegisteredUserId);
// Get app authoken and save it in a variable
SharedPreferences sharedPref = getSharedPreferences(getString(R.string.preference_token), Context.MODE_PRIVATE);
String defaultToken = getResources().getString(R.string.default_auth_token);
myToken = sharedPref.getString(getString(R.string.saved_auth_token), defaultToken);
SharedPreferences savedValues = PreferenceManager.getDefaultSharedPreferences(this);
if (savedValues.getBoolean(getString(R.string.first_launch), true) || !myUserId.equals(registeredUserId)) {
register();
SharedPreferences.Editor editorRegisterUserId = sharedPrefMyUserId.edit();
editorRegisterUserId.putString(getString(R.string.default_register_user_id), myUserId);
editorRegisterUserId.commit();
SharedPreferences.Editor editor = savedValues.edit();
editor.putBoolean(getString(R.string.first_launch), false);
editor.commit();
}
// 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("MessageLine" + linesOfMessageCount, 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();
//postNotification(new Intent(context, MapsActivity.class), context);
postNotification(new Intent(context, NotificationsActivity.class), context);
}
protected static void postNotification(Intent intentAction, Context context) {
final NotificationManager mNotificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
final PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intentAction, PendingIntent.FLAG_UPDATE_CURRENT);
int numOfMissedMessages = 0;
String missedMessage = "";
if(savedValues != null){
missedMessage = savedValues.getString("MessageLine2", "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;
}
/* Class to register new user */
public class SendRegUserId extends AsyncTask<Void, Void, String> {
private final String LOG_TAG = SendRegUserId.class.getSimpleName();
String id;
@Override
protected String doInBackground(Void... params) {
Log.v("MYSENDTOKEN", token);
// These two need to be declared outside the try/catch
// so that they can be closed in the finally block.
HttpURLConnection urlConnection = null;
BufferedReader reader = null;
// Will contain the raw JSON response as a string.
String jsonStr = null;
try {
String encoded = URLEncoder.encode(token, "UTF-8");
Log.v("ENCODEDTOKEN", encoded);
String sendDataUrl = BASE_URL + "messages/adddevicetoaws/" + URLEncoder.encode(URLEncoder.encode(token, "UTF-8"), "UTF-8") + "/android";
URL url = new URL(sendDataUrl);
// Create the request to OpenWeatherMap, and open the connection
urlConnection = (HttpURLConnection) url.openConnection();
urlConnection.setRequestProperty(AUTHORIZATION, myToken);
urlConnection.setRequestMethod("GET");
urlConnection.connect();
// Read the input stream into a String
InputStream inputStream = urlConnection.getInputStream();
StringBuffer buffer = new StringBuffer();
if (inputStream == null) {
// Nothing to do.
//jsonStr = null;
return null;
}
reader = new BufferedReader(new InputStreamReader(inputStream));
String line;
while ((line = reader.readLine()) != null) {
// Since it's JSON, adding a newline isn't necessary (it won't affect parsing)
// But it does make debugging a *lot* easier if you print out the completed
// buffer for debugging.
buffer.append(line + "\n");
}
if (buffer.length() == 0) {
// Stream was empty. No point in parsing.
jsonStr = null;
return null;
}
jsonStr = buffer.toString();
} catch (IOException e) {
Log.e("ProfileFragment", "Error ", e);
// If the code didn't successfully get the data, there's no point in attempting
// to parse it.
jsonStr = null;
return null;
} finally {
if (urlConnection != null) {
urlConnection.disconnect();
}
if (reader != null) {
try {
reader.close();
} catch (final IOException e) {
Log.e("ProfileFragment", "Error closing stream", e);
}
}
}
Log.v("JSONSTR", jsonStr);
return jsonStr;
}
@Override
protected void onPostExecute(String result) {
if (result != null) {
}
}
}
}