PrismLibrary/Prism · error · InvalidOperationException

The view type ' ' is not a type of Page.

Error message

The view type '{view.FullName}' is not a type of Page.

What it means

RegisterForNavigation validates that the supplied view Type derives from Microsoft.Maui.Controls.Page and throws InvalidOperationException if it does not. Prism navigation is page-based; registering a non-Page type (a ContentView, a plain class, or a ViewModel) cannot be navigated to, so Prism rejects the registration up front.

Solutions

  1. Ensure the registered type inherits from Microsoft.Maui.Controls.Page (ContentPage, NavigationPage, etc.)
  2. Register the Page class, not its ViewModel or a ContentView
  3. Check for namespace collisions where a same-named non-Page type is picked up

Example fix

// before
services.RegisterForNavigation(typeof(MainView), typeof(MainViewModel)); // MainView : ContentView
// after
public partial class MainView : ContentPage { ... }
services.RegisterForNavigation<MainView, MainViewModel>();
Defensive patterns

Strategy: validation

Validate before calling

if (viewType is null || !typeof(Page).IsAssignableFrom(viewType))
    throw new InvalidOperationException($"{viewType?.FullName} must derive from Microsoft.Maui.Controls.Page");
services.RegisterForNavigation(viewType, viewModelType);

Type guard

bool IsPage(Type t) => t is not null && typeof(Page).IsAssignableFrom(t);

Try / catch

try
{
    services.RegisterForNavigation(viewType, viewModelType);
}
catch (InvalidOperationException ex) when (ex.Message.Contains("not a type of Page"))
{
    logger.LogError(ex, "{Type} is not a Page; fix registration", viewType.FullName);
    throw;
}

Prevention

When it happens

Trigger: Calling services.RegisterForNavigation(typeof(SomeContentViewOrViewModel), ...) with a Type not assignable to Page; using Prism.Forms-style ContentView registrations ported to MAUI.

Common situations: Migrating from Xamarin.Forms/Prism.Forms to .NET MAUI where 'views' were ContentViews; accidentally registering a ViewModel instead of the View; a same-named non-Page class from another namespace being resolved.

Understand the failure class

Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.

Related errors


AI-assisted analysis of PrismLibrary/Prism@358118cd64 (2026-09-15). Data as JSON: /api/errors/332433d59bc21d61. Report an issue: GitHub.

Appendix: source

Thrown at src/Maui/Prism.Maui/Ioc/MicrosoftDependencyInjectionExtensions.cs:28

{
#if !UNO_WINUI
    private static readonly Type PageType = typeof(Page);

    public static IServiceCollection RegisterForNavigation<[DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)] TView>(this IServiceCollection services, string name = null)
            where TView : Page =>
            services.RegisterForNavigation(typeof(TView), null, name);

    public static IServiceCollection RegisterForNavigation<[DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)] TView, [DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicConstructors | DynamicallyAccessedMemberTypes.NonPublicConstructors)] TViewModel>(this IServiceCollection services, string name = null)
        where TView : Page =>
        services.RegisterForNavigation(typeof(TView), typeof(TViewModel), name);

    public static IServiceCollection RegisterForNavigation(this IServiceCollection services, Type view, Type viewModel, string name = null)
    {
        if (view is null)
            throw new ArgumentNullException(nameof(view));

        if (!view.IsAssignableTo(PageType))
            throw new InvalidOperationException($"The view type '{view.FullName}' is not a type of Page.");

        if (string.IsNullOrEmpty(name))
            name = view.Name;

        services.AddSingleton(new ViewRegistration
            {
                Type = ViewType.Page,
                Name = name,
                View = view,
                ViewModel = viewModel
            })
            .AddTransient(view);

        if (viewModel != null)
            services.AddTransient(viewModel);

        return services;
    }

View on GitHub (pinned to 358118cd64)