首页 > 其他分享 >鸿蒙Navigation拦截器实现页面跳转登录鉴权方案

鸿蒙Navigation拦截器实现页面跳转登录鉴权方案

时间:2024-11-15 11:56:31浏览次数:1  
标签:拦截器 登录 data 跳转 Navigation 页面

我们在进行页面跳转时,很多情况下都得考虑登录状态问题,比如进入个人信息页面,下单交易页面等等。在这些场景下,通常在页面跳转前,会先判断下用户是否已经登录,若已登录,则跳转到相应的目标页面,若没有登录,则先跳转到登录页面,然后等着获取登录状态,若登录页面关闭时,能获取到已登录,则继续跳转到目标页,若用户取消了登录,则终止后面的行为。这样的处理通常会存在一些问题,例如很多页面都与登录状态相关,这样需要在大量的入口处增加登录逻辑判断。即使封装成一个方法,也需要关心是否登录成功,增加了逻辑的复杂性,而且登录页面先关闭,再打开新页面,页面切换动画也很不协调。

那么我们有没有一种更好的方案来处理登录鉴权问题呢?首先我们先梳理一下我们想要的效果,我们的目的是要跳转到相应的目标页,目标页是否需要先登录,我们是不太愿意关注的,最好是内部自己处理掉,,若没有登录,就先进行登录,登录成功后,继续后面的行为,外面使用的地方尽量做到无感知。总结一下就是进行页面跳转时,内部先判断一下状态,然后再进行后续的行为,而这恰好是Navigation拦截器的功能。

NavPathStack提供了setInterception方法,用于设置Navigation页面跳转拦截回调。该方法需要传一个NavigationInterception对象,该对象包含三个回调函数willShow,didShow和modeChange,我们在willShow页面即将显示时,进行拦截处理。先判断是否登录,没有登录,就重定向到登录页面,若已登录,则继续后续行为,不做拦截。示例如下

@Entry
@ComponentV2
struct Index {
  nav: NavPathStack = new NavPathStack()
  isLogin: boolean = false

  aboutToAppear(): void {
    this.nav.setInterception({
      willShow: (from: NavDestinationContext | NavBar, to: NavDestinationContext | NavBar,
        operation: NavigationOperation, isAnimated: boolean) => {
        if (typeof to === 'object') {
          if (isLogin) {
            AppRouter.popPage()
            AppRouter.jumpPage('login', undefined)
          }
        }
      }
    })
  }

  build() {
    Navigation(this.nav)
    .hideToolBar(true)
    .hideTitleBar(true)
    .height('100%')
    .width('100%')
  }
}

拦截器细节优化

如何判断是否需要进行拦截

在拦截器中,虽然我们可以进行拦截重定向跳转,但需要考虑的一个问题是什么情况下进行拦截,也就是哪些页面跳转时需要先判断下登录状态。首先想到的是弄一个数组,所有需要登录校验的页面都放到这个数组中。页面跳转时,我们只需要判断下目标页是否在数组中,就可以知道是否需要进行拦截校验登录了。其实思想是对的,只是我们有更简单的实现方式。在系统路由表中,有一个data字段,可以在这个字段中增加一个字段,是否需要登录,在拦截器中先获取目标页中这个参数,只要所有需要登录的页面,都添加了这个字段就可以了。我们以用户信息页为例,配置如下

{
  "routerMap": [
    {
      "name": "login",
      "pageSourceFile": "src/main/ets/pages/login/LoginPage.ets",
      "buildFunction": "loginBuilder"
    },
    {
      "name": "user_info",
      "pageSourceFile": "src/main/ets/pages/user/UserInfoPage.ets",
      "buildFunction": "userInfoBuilder",
      "data": {
        "needLogin": "1"
      }
    }
  ]
}

拦截器中获取该字段的方式如下

this.nav.setInterception({
  willShow: (from: NavDestinationContext | NavBar, to: NavDestinationContext | NavBar,
    operation: NavigationOperation, isAnimated: boolean) => {
    if (typeof to === 'object') {
      const data = (to as NavDestinationContext).getConfigInRouteMap()?.data
      if (data !== undefined && (data as object)['needLogin'] === '1' && !AppConstant.hasLogin) {
        AppRouter.popPage()
        AppRouter.jumpPage(Pages.login, undefined)
      }
    }
  }
})

登录成功后如何获取目标页和页面参数

登录成功后,我们如何知道要跳转到哪个目标页,以及跳转到目标页时所需要的参数呢?我们在跳转到登录页时可以增加2个参数targetPage和targetParam,分别表示要处理的目标页以及相应的参数,若targetPage的值为undefined,则说明登录成功后没有后续操作,若有值,则跳转到这个页面并把相应的参数传过去。在拦截器中,可以通过to.pathInfo.name获取到目标页的名称name以及通过to.pathInfo.param获取到目标页所需要的参数,并把它们赋值给登录页面的targetPage和targetParam就行了。

我们可以发现使用拦截器这种方式,完全符合我们最初的设想,外部调用时不用考虑是否要校验登录状态,由拦截器内部自己处理。登录后也是直接跳转到目标也,没有页面关闭效果。而且是否需要判断登录,只需配置一个字段就行了,非常方便。

标签:拦截器,登录,data,跳转,Navigation,页面
From: https://www.cnblogs.com/zhaloe/p/18547701

相关文章

  • SpringBoot中监听器、过滤器、拦截器和AOP详解
    SpringBoot中监听器、过滤器、拦截器和AOP详解在构建SpringBoot应用程序时,监听器(Listener)、过滤器(Filter)、拦截器(Interceptor)和面向切面编程(AOP)是四种常用的机制,它们各自有不同的用途和执行时机。本文将详细介绍这四种技术的执行时机和区别,并附上示例代码帮助理解。1.......
  • 鸿蒙Navigation入门使用
    Navigation组件适用于模块内和跨模块的路由切换,通过组件级路由能力实现更加自然流畅的转场体验,并提供多种标题栏样式来呈现更好的标题和内容联动效果。一次开发,多端部署场景下,Navigation组件能够自动适配窗口显示大小,在窗口较大的场景下自动切换分栏展示效果。根页面设置我们在E......
  • uniapp路由与页面跳转详解:API调用与Navigator组件实战
    UniApp路由与页面跳转详解:API调用与Navigator组件实战路由uniapp页面路由为框架统一管理,开发者需要在page.json里面配置每个路由页面的路径及页面样式。路由跳转uniapp有两种页面路由跳转方式,调用API跳转和navigator组件跳转。调用API跳转navTo(){ /*跳转到非tabbar......
  • 鸿蒙Navigation知识点详解
    Navigation是路由导航的根视图容器,一般作为页面(@Entry)的根容器,包括单栏(Stack)、分栏(Split)和自适应(Auto)三种显示模式。Navigation组件适用于模块内和跨模块的路由切换,通过组件级路由能力实现更加自然流畅的转场体验,并提供多种标题栏样式来呈现更好的标题和内容联动效果。一次开发,多......
  • 拦截器Filter(过滤器)
    拦截器也叫过滤器,拦截器就是前端和servlet之间的一个东西,可以用拦截器进行编码统一和拦截没登陆就进页面的实现Filter(Servlet包下的)那三个方法是init、doFilter、destroy,它们是生命周期init是初始化,doFilter是内容,destroy是销毁拦截没登陆的1.置web.xml方法这里的配......
  • 插件工厂和AOP拦截器机制
    一.插件工厂基于接口机制的插件工厂是一种设计模式,用于创建和管理插件。插件是独立的模块,可以动态加载和卸载,以扩展应用程序的功能。通过使用接口,插件工厂可以提供一种统一的方式来创建和管理这些插件,而不需要了解插件的具体实现细节。具体实现来说,实现一个插件工厂通过哈希记......
  • C语言设置安全长跳转(setjmp/longjmp)
    #include<stdio.h>#include<stdlib.h>#include<setjmp.h>staticjmp_bufenv;voidd(void){ fprintf(stdout,"%s\n",__func__); fprintf(stdout,"dend\n"); longjmp(env,10);//跳转到设置点}voidc(void){ fprintf(std......
  • linux中使用cd指令跳转路径时带不带“/”
    在Linux中使用`cd`命令跳转目录时,是否需要`/`取决于路径的类型。以下是规则:1.**绝对路径:以`/`开头**-如果路径以`/`开头,表示从根目录开始的**绝对路径**。-使用绝对路径可以精确定位到文件系统中的某个目录,不受当前目录影响。-例如:```bashcd/......
  • 内核源码+vscode+bear+clang实现函数任意跳转,无缝跳转,无缝阅读,无缝开发
    一、准备工作1、内核源码版本选择务必有一份能编译通过的《内核源码》,本次选择5.10版本的。#说明:5.10版本的《内核源码》里,在scripts/clang-tools目录下有《gen_compile_commands.py》文件,这个脚本也能生成《compile_commands.json》文件。已确定4.19版本没有,请尽量选择高版......
  • 鸿蒙Navigation页面生命周期
    Navigation作为路由容器,其生命周期承载在NavDestination组件上,以组件事件的形式开放。其生命周期大致可分为三类,自定义组件生命周期、通用组件生命周期和自有生命周期。其中,aboutToAppear和aboutToDisappear是自定义组件的生命周期(NavDestination外层包含的自定义组件),OnAppear和......