【发布时间】:2017-08-01 11:03:02
【问题描述】:
我在我的 xamarin 表单项目中使用 Prism。我还使用后台服务在后台推送长时间运行的任务。问题是当应用程序被杀死时,服务也被杀死。并且通过“杀死“我的意思是按下主页按钮 -> 查看所有正在运行的应用程序 -> 将我的应用程序滑到一边 -> 应用程序被杀死。即使应用程序被杀死,我也想保持服务活着。我读过很多帖子说它可以完成.但是我无法让它工作。 这是我尝试过的:-
这是 Android MainActivity.cs
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
try
{
global::Xamarin.Forms.Forms.Init(this, bundle);
LoadApplication(new App(new AndroidInitializer()));
WireUpLongRunningTask();
}
catch(Exception)
{
}
}
public void WireUpLongRunningTask()
{
MessagingCenter.Subscribe<StartSyncBackgroundingTask>(this, "StartSyncBackgroundingTask", message => {
var intent = new Intent(this, typeof(AndroidSyncBackgroundService));
StartService(intent);
});
}
这是 AndroidSyncBackgroundService 类:-
[Service]
public class AndroidSyncBackgroundService : Service
{
CancellationTokenSource _cts;
private ISyncBackgroundService _isyncBackgroundService;
private App _app => (App)Xamarin.Forms.Application.Current;
public override IBinder OnBind(Intent intent)
{
return null;
}
public override StartCommandResult OnStartCommand(Intent intent, StartCommandFlags flags, int startId)
{
_cts = new CancellationTokenSource();
Task.Run(() => {
try {
//INVOKE THE SHARED CODE
_isyncBackgroundService = _app.Container.Resolve<ISyncBackgroundService>();
_isyncBackgroundService.RunBackgroundingCode(_cts.Token).Wait();
}
catch (System.OperationCanceledException) {
}
finally {
if (_cts.IsCancellationRequested) {
var message = new CancelledTask();
Device.BeginInvokeOnMainThread(
() => MessagingCenter.Send(message, "CancelledTask")
);
}
}
}, _cts.Token);
return StartCommandResult.Sticky;
}
public override void OnDestroy()
{
if (_cts != null) {
_cts.Token.ThrowIfCancellationRequested();
_cts.Cancel();
}
StartService(new Intent("com.xamarin.AndroidSyncBackgroundService"));
base.OnDestroy();
}
public override void OnTaskRemoved(Intent rootIntent)
{
Intent restartServiceIntent = new Intent(Xamarin.Forms.Forms.Context, typeof(AndroidSyncBackgroundService));
PendingIntent restartServicePendingIntent = PendingIntent.GetService(Xamarin.Forms.Forms.Context, 1, restartServiceIntent,PendingIntentFlags.OneShot);
AlarmManager alarmService = (AlarmManager)Xamarin.Forms.Forms.Context.GetSystemService(Context.AlarmService);
alarmService.Set(
AlarmType.ElapsedRealtime,
1000,
restartServicePendingIntent);
base.OnTaskRemoved(rootIntent);
}
}
这是 SyncBackgroundService 类:-
public class SyncBackgroundService: ISyncBackgroundService
{
private ISqliteCallsService _iSqliteCallsService;
private IFeedBackSqliteService _feedBackSqliteService;
private ISettingApiService _isettingApiService;
private ISettingSqliteService _isettingSqliteService;
private IWebApiService _iwebApiService;
private App _app => (App)Xamarin.Forms.Application.Current;
public async Task RunBackgroundingCode(CancellationToken token)
{
_iSqliteCallsService= _app.Container.Resolve<ISqliteCallsService>();
await Task.Run(async () => {
token.ThrowIfCancellationRequested();
App.bRunningBackgroundTask = true;
await Task.Run(async () =>
{
await Task.Delay(1);
_iSqliteCallsService.ftnSaveOnlineModeXMLFormat("Offline", 0);
_iSqliteCallsService.SyncEmployeeTableData();
_iSqliteCallsService.SaveOfflineAppCommentData();
_iSqliteCallsService.SaveOfflineAdditionToFlowData();
await Task.Delay(500);
//MessagingCenter.Send<SyncBackgroundService>(this, "StopSyncBackgroundingTask");
});
}, token);
}
}
}
从代码 sn-p 中可以看出,我使用了 StartCommandResult.Sticky,但服务仍然被终止并且不会重新启动。 我还在 OnTaskRemoved 方法中使用了警报管理器,根据其文档,当应用程序被杀死时会触发该方法。但在我的情况下,服务根本没有重新启动。有人能指出我的代码中的错误是什么吗?或者提供一个可行的解决方案,以便我可以在我的应用程序中实现它。 提前致谢!
【问题讨论】:
-
尝试使用 AlarmManager 取消预定的操作系统任务以杀死服务
-
你在什么设备上测试?
-
我已经在 Moto E(第二代)、I-KALL 平板电脑和亚马逊 Kindle 上进行了测试
-
您找到解决方案了吗?
标签: c# xamarin.forms android-service background-service