我按照本指南在Xamarin.Android应用程序中设置了Firebase: https://developer.xamarin.com/guides/android/application_fundamentals/notifications/remote-notifications-with-fcm/
它似乎首先工作,接收通知没有问题。然后我尝试更新代码并重新部署到Device,之后什么也没发生。由于我无法从Firebase控制台收到任何通知。
我试过了
当新部署应用程序时,我尝试发送通知,但没有任何反应。更新和重新部署后,我在控制台中收到错误“未注册的注册令牌”。
在设置新的Firebase项目之前,尝试订阅主题时会出现以下错误 “INVALID_PARAMETERS”,但在创建新项目后,这个问题已经消失。现在订阅主题,它会在一段时间后出现在控制台中。但是尝试向主题发送通知,没有结果。
修改 - 添加代码
MainActivity.cs
[Activity(Label = "<<App Label>>", MainLauncher = true, Icon = "@drawable/icon")]
public class MainActivity : Activity
{
private TextView msgText;
private const string Tag = "MainActivity";
private FirebaseAnalytics _analytics;
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
_analytics = FirebaseAnalytics.GetInstance(this);
// Set our view from the "main" layout resource
SetContentView (Resource.Layout.Main);
msgText = FindViewById<TextView>(Resource.Id.msgText);
if (Intent.Extras != null)
{
foreach (var key in Intent.Extras.KeySet())
{
var value = Intent.Extras.GetString(key);
Log.Debug(Tag, "Key: {0} Value: {1}", key, value);
}
}
IsPlayServicesAvailable();
var logTokenButton = FindViewById<Button>(Resource.Id.logTokenButton);
logTokenButton.Click += delegate {
Log.Debug(Tag, "InstanceID token: " + FirebaseInstanceId.Instance.Token);
};
var subButton = FindViewById<Button>(Resource.Id.subscribeButton);
subButton.Click += SubButton_Click;
}
private void SubButton_Click(object sender, System.EventArgs e)
{
FirebaseMessaging.Instance.SubscribeToTopic("A");
Log.Debug(Tag, "Subscribed to A");
}
public bool IsPlayServicesAvailable()
{
int resultCode = GoogleApiAvailability.Instance.IsGooglePlayServicesAvailable(this);
if (resultCode != ConnectionResult.Success)
{
if (GoogleApiAvailability.Instance.IsUserResolvableError(resultCode))
msgText.Text = GoogleApiAvailability.Instance.GetErrorString(resultCode);
else
{
msgText.Text = "This device is not supported";
Finish();
}
return false;
}
else
{
msgText.Text = "Google Play Services is available.";
return true;
}
}
}
StwFirebaseInstanceIdService.cs
[Service]
[IntentFilter(new []{ "com.google.firebase.INSTANCE_ID_EVENT" })]
public class StwFirebaseInstanceIdService : FirebaseInstanceIdService
{
private const string Tag = "StwFirebaseInstanceIdService";
public override void OnTokenRefresh()
{
var refreshedToken = FirebaseInstanceId.Instance.Token;
Log.Debug(Tag, "Refreshed Token: " + refreshedToken);
//SendRegistrationToServer(refreshedToken);
}
private void SendRegistrationToServer(string token)
{
}
}
的AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="<<Package Name>>" android:versionCode="1" android:versionName="1.0" android:installLocation="auto">
<uses-sdk android:minSdkVersion="16" />
<application android:label="<<App Label>>">
<receiver android:name="com.google.firebase.iid.FirebaseInstanceIdInternalReceiver" android:exported="false" />
<receiver android:name="com.google.firebase.iid.FirebaseInstanceIdReceiver" android:exported="true" 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" />
<category android:name="${applicationId}" />
</intent-filter>
</receiver>
</application>
答案 0 :(得分:1)
我碰到了同样的问题。尝试再次卸载应用程序,在获得令牌(旧令牌)之前,请调用刷新令牌以获取刷新的令牌:
public override void OnTokenRefresh()
{
var refreshedToken = FirebaseInstanceId.Instance.Token;
Log.Debug(TAG, "Refreshed token: " + refreshedToken);
SendRegistrationToServer(refreshedToken);
}
void SendRegistrationToServer(string token)
{ // Your custom implementation depends on your server }
有关详细信息,请访问Here
答案 1 :(得分:0)
上面提到的教程相当不错,但遗漏了几点。在我将应用程序的SHA1密钥添加到注册之前,我无法使用它。您可以通过以下命令获取此信息:
"C:\Program Files\Java\jdk1.8.0_161\bin\keytool.exe" -list -v -keystore "%USERPROFILE%\AppData\Local\Xamarin\Mono for Android\debug.keystore" -alias androiddebugkey -storepass android -keypass android
您可能需要编辑一下该命令以匹配您的Java版本。
第二件事是,DEBUG构建似乎存在一些问题。我从某个地方得到了这个方法(不知道现在在哪里)。
private void ConfigureFireBase()
{
#if DEBUG
Task.Run(() =>
{
var instanceId = FirebaseInstanceId.Instance;
instanceId.DeleteInstanceId();
Android.Util.Log.Debug("TAG", "{0} {1}", instanceId?.Token?.ToString(), instanceId.GetToken(GetString(Resource.String.gcm_defaultSenderId), Firebase.Messaging.FirebaseMessaging.InstanceIdScope));
});
// For debug mode only - will accept the HTTPS certificate of Test/Dev server, as the HTTPS certificate is invalid /not trusted
ServicePointManager.ServerCertificateValidationCallback += (o, certificate, chain, errors) => true;
#endif
}
在OnCreate之后调用它,就像OnCreate一样:
base.OnCreate(bundle);
global::Xamarin.Forms.Forms.Init(this, bundle);
ConfigureFireBase();
答案 2 :(得分:0)
我在Visual Studio for Mac(8.3.11)上使用Xamarin.Firebase.Messaging(71.1740.0)。在较旧的(API 21)和较新的(API 28)物理android设备上进行测试。
首次部署可以在两个设备上使用新令牌。对FCM的自定义REST API调用成功:
{"multicast_id":4160565375891761047,"success":1,"failure":0,"canonical_ids":0,"results":[{"message_id":"0:1576702929647400%320d8b4c320d8b4c"}]}
更改代码,然后在“调试”模式下重新部署到相同的设备上可以正常工作。从Firebase控制台发送正常,将通知发送到FCM中同一项目应用中的两个设备。
几个小时后,自定义REST API返回旧设备令牌(无代码更改):
{"multicast_id":565695677811030352,"success":0,"failure":1,"canonical_ids":0,"results":[{"error":"NotRegistered"}]}
然后,再过几个小时,新设备令牌还将从自定义REST API返回“ NotRegistered”(无代码更改)。此外,Firebase控制台不再向设备发送通知。
发生这种情况后,我获得自定义REST API和Firebase控制台正确发送通知的唯一方法是使用Visual Studio手动从设备中删除应用程序:
Visual Studio Menu > Build > Remove from Device
再次部署将安装该应用程序,就像它是设备上的新设备一样,并请求新的令牌。
注意:在Visual Studio首选项中,已经取消选中“在应用程序部署之间保留数据/缓存”,没有重大更改。清除应用程序的数据/缓存也不起作用。
使用了来自GitHub的最新Microsoft代码(2019年12月):https://github.com/xamarin/GooglePlayServicesComponents/tree/master/samples/com.google.firebase/firebase-messaging