You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

FreshMVVM中从推送通知打开页面及后续导航异常问题

问题分析与解决方案

环境信息

  • Xamarin.Forms 5.0.0.2401
  • FreshMVVM 4.0.1
  • 运行平台:Android、iOS

问题现象

尝试通过FreshMVVM打开页面时,若应用已运行则接入现有导航栈,页面能正常打开,但后续调用PushPageModel推送新页面时抛出异常:

FreshTinyIoC.TinyIoCResolutionException: 'Resolve failed: IFreshNavigationService'

异常调用栈

at FreshTinyIoC.FreshTinyIoCContainer.ResolveInternal (FreshTinyIoC.FreshTinyIoCContainer+TypeRegistration registration, FreshTinyIoC.NamedParameterOverloads parameters, FreshTinyIoC.ResolveOptions options) [0x00136] in <244cbb4b2b78473caee762c4138df3f3>:0 
at FreshTinyIoC.FreshTinyIoCContainer.Resolve (System.Type resolveType, System.String name) [0x00013] in <244cbb4b2b78473caee762c4138df3f3>:0 
at FreshTinyIoC.FreshTinyIoCContainer.Resolve[ResolveType] (System.String name) [0x00001] in <244cbb4b2b78473caee762c4138df3f3>:0 
at FreshMvvm.FreshTinyIOCBuiltIn.Resolve[ResolveType] (System.String name) [0x00006] in <c1f1d60a460941bc82899cfb78f0c2ec>:0 
at FreshMvvm.PageModelCoreMethods.PushPageModelWithPage (Xamarin.Forms.Page page, FreshMvvm.FreshBasePageModel pageModel, System.Object data, System.Boolean modal, System.Boolean animate) [0x001ca] in <c1f1d60a460941bc82899cfb78f0c2ec>:0 

触发异常的代码

return new FreshAwaitCommand(async (entryType, tcs) =>
{
    await this.CoreMethods.PushPageModel(typeof(SignalHistoryViewModel), null, false, true);
    tcs.SetResult(true);
});

通知点击处理代码(原实现)

Type viewModelType = Helpers.SignalStateToViewModelHelper.GetSignalDetailViewModelType((State)Enum.Parse(typeof(State), signalState));

var navigationStack = Application.Current.MainPage as NavigationPage;

if (navigationStack != null)
{
    // Navigate within the existing navigation stack
    var pageModel = FreshPageModelResolver.ResolvePageModel(viewModelType, true);

    Device.BeginInvokeOnMainThread(async () =>
    {
        await navigationStack.PushAsync(FreshPageModelResolver.ResolvePageModel(viewModelType, null));
    });
}
else
{
    // Create a new navigation stack
    var pageModel = FreshPageModelResolver.ResolvePageModel(viewModelType, true);
    var navigationContainer = new FreshNavigationContainer(pageModel);

    Device.BeginInvokeOnMainThread(() =>
    {
        Application.Current.MainPage = navigationContainer;
    });
}

问题原因

直接使用原生NavigationPage.PushAsync推送FreshMVVM页面时,页面对应的ViewModel没有被正确注入IFreshNavigationService。FreshMVVM的CoreMethods.PushPageModel依赖该服务完成导航,因此后续调用时会因无法解析服务抛出异常。

解决方案

修改通知点击的处理逻辑,通过FreshMVVM自带的FreshNavigationService来完成页面推送,确保ViewModel与导航服务正确关联。

修改后的代码

Type viewModelType = Helpers.SignalStateToViewModelHelper.GetSignalDetailViewModelType((State)Enum.Parse(typeof(State), signalState));

// 直接获取FreshMVVM的导航容器
var freshNavContainer = Application.Current.MainPage as FreshNavigationContainer;

if (freshNavContainer != null)
{
    Device.BeginInvokeOnMainThread(async () =>
    {
        // 使用FreshNavigationService推送页面
        await freshNavContainer.NavigationService.PushPageModel(viewModelType, null, animate: true);
    });
}
else
{
    // 原有创建新导航容器的逻辑保持不变
    var pageModel = FreshPageModelResolver.ResolvePageModel(viewModelType, true);
    var navigationContainer = new FreshNavigationContainer(pageModel);

    Device.BeginInvokeOnMainThread(() =>
    {
        Application.Current.MainPage = navigationContainer;
    });
}

另一种实现方式(通过IoC解析导航服务)

如果确认IFreshNavigationService已被正确注册(创建FreshNavigationContainer时会自动完成注册),也可以直接从IoC容器解析服务:

Type viewModelType = Helpers.SignalStateToViewModelHelper.GetSignalDetailViewModelType((State)Enum.Parse(typeof(State), signalState));

Device.BeginInvokeOnMainThread(async () =>
{
    var navigationService = FreshTinyIoCContainer.Current.Resolve<IFreshNavigationService>();
    await navigationService.PushPageModel(viewModelType, null, animate: true);
});

内容的提问来源于stack exchange,提问作者Pat Long - Munkii Yebee

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.13 07:10:57