Skip to content

StackRouter.onPopPage() needs to be extended to allow restoring query parameters on back navigation. #2310

@slavap

Description

@slavap

Currently when calling router.maybePop() all query parameters are removed from browser address bar.
It happens because onPopPage() calls

_updateSharedPathData(includeAncestors: true);

and all _pages routes are getting updated with EMPTY query parameters.

The simplest possible fix for this problem is the following:

  /// Called when Page route is popped
  /// this is not called when pageless routes are popped e.g popping a dialog
  /// that does not use [PageRoute] will not trigger this method
  void onPopPage(AutoRoutePage<Object?> page) {
    if (!_pages.remove(page)) return;
    Map<String, dynamic> newQueryParams = {};
    if (_pages.isNotEmpty) {
      newQueryParams = getNewQueryParamsAfterPop(_pages.last, page) ?? {};
    }
    _updateSharedPathData(includeAncestors: true, queryParams: newQueryParams);
    if (isRouteDataActive(page.routeData)) {
      navigationHistory.rebuildUrl();
    }
  }

  Map<String, dynamic>? getNewQueryParamsAfterPop(AutoRoutePage<Object?> newPage, AutoRoutePage<Object?> oldPage) {
    return null;
  }

Then it will be possible to override getNewQueryParamsAfterPop() in the application to restore proper query parameters, something like this:

  @override
  Map<String, dynamic>? getNewQueryParamsAfterPop(AutoRoutePage<Object?> newPage, AutoRoutePage<Object?> oldPage) {
    final match = newPage.routeData.route;
    if (match.args is ProtoRouteArgs) {
      final protoArgs = match.args as ProtoRouteArgs;
      Map<String, dynamic> m = {};
      if (isNotEmpty(protoArgs.strArgs)) m[ProtoPageParams.args] = protoArgs.strArgs;
      if (isNotEmpty(protoArgs.simpleFilter)) m[ProtoPageParams.filter] = protoArgs.simpleFilter;
      if (m.isEmpty) return null;
      return m;
    }
    return null;
  }

Of course such code is kind of "ugly", and better solution will be preserving query parameters the same way as args preserved in AutoRoutePage.routeData.route, so it will be easy to restore them properly in _updateSharedPathData() automatically, without need for manual getNewQueryParamsAfterPop() override.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions