4.配置模板全局变量,配置可修改的后台地址,nestjs扩展模板方法

@TOC[]

一、配置模板全局变量

1.重点

// 1.设置全局变量
res.locals.userinfo = userinfo;

// 2.在任何一个页面中使用
<a>欢迎您 <%=userinfo.username%></a>

2.完整案例

2.1) 在中间件中配置登录者的全局变量

@filename(adminauth.middleware)

import { Injectable, NestMiddleware } from '@nestjs/common';
@Injectable()
export class AdminauthMiddleware implements NestMiddleware {
    use(req: any, res: any, next: () => void) {
        // console.log('中间件', req.baseUrl);
        let pathname = req.baseUrl; // 获取访问的地址 
        // 1.获取session中保存的用户信息
        let userinfo = req.session.userinfo;
        // 判断权限(是否登录)
        if (userinfo && userinfo.username) {
            // 设置全局变量
            res.locals.userinfo = userinfo;
            console.log('res.locals.userinfo: ', res.locals.userinfo);
            next();
        } else {
            // 未登录时跳转到登录页:排除不需要权限判断的页面(登录、注册、验证码)
            if(pathname == '/admin/login' || pathname == '/admin/login/code' || pathname == '/admin/login/doLogin' ) {
                next();
            }else {
                console.log('未登录');
                res.redirect('/admin/login') //重定向
            }
        }
    }
}

2.2 在公共头部展示数据

<nav class="navbar navbar-inverse" role="navigation">
    <div class="container-fluid">
        <div class="navbar-header">
            <img src="/admin/images/node.jpg" height="44px;" />
        </div>
        <div class="collapse navbar-collapse" id="example-navbar-collapse">           
            <ul class="nav navbar-nav navbar-right">
                <li><a>欢迎您 <%=userinfo.username%></a>
                </li>
                <li><a href="/admin/login/loginOut">安全退出</a>
                </li>
            </ul>
        </div>
    </div>
</nav>

二、配置可修改的后台地址

2.1 在config.ts中设置全局变量

export class Config{
    static adminPath = 'adminxxx'
}

2.1.1 在init.middleware中设置成全局变量

注:在这里配置成全局变量,可以在所有的前端页面中使用。

import { Injectable, NestMiddleware } from '@nestjs/common';
import { Config } from '../config/config'
@Injectable()
export class InitMiddleware implements NestMiddleware {
    use(req: any, res: any, next: () => void) {
        res.locals.config = Config;
        next();
    }
}

2.2 在login.controller中使用

重点@Controller(${Config.adminPath}/login)

完整代码如下

import { Controller, Get, Render, Request, Response, Post, Body } from '@nestjs/common';
import { ToolsService } from '../../../service/tools/tools.service';
import { AdminService } from '../../../service/admin/admin.service';
import { Config } from '../../../config/config'

@Controller(`${Config.adminPath}/login`)
export class LoginController {
    constructor(
        private ToolsService: ToolsService,
        private adminService: AdminService
    ) { }

    @Get()
    @Render('admin/login')
    async index() {
        return {}
    }

    // 获取验证码
    @Get('code')
    getCode(@Request() req, @Response() res) {
        let svgCaptcha = this.ToolsService.captcha(); // 服务里面的方法
        req.session.code = svgCaptcha.text;
        res.type('image/svg+xml'); /*指定返回的类型*/
        res.send(svgCaptcha.data); /*给页面返回一张图片*/
    }

    // 登录
    @Post('doLogin')
    async doLogin(@Body() body, @Request() req, @Response() res) {
        console.log('body: ', body);
        console.log('session: ', req.session);
        try {
            let code: string = body.code;
            let username: string = body.username;
            let password: string = body.password;
            if (username == "" || password.length < 6) {
                await this.ToolsService.error(res, '用户名或密码不合法', `/${Config.adminPath}/login`);
            } else {
                // 注:验证码转化为大写方便比较
                if (code.toUpperCase() == req.session.code.toUpperCase()) {
                    password = this.ToolsService.getMd5(password); // 使用md5加密
                    // 去数据库查是否有这个用户
                    let userResult = await this.adminService.find({ 'username': username, 'password': password });
                    console.log('userResult:', userResult);
                    if (userResult.length > 0) {
                        req.session.userinfo = userResult[0];
                        await this.ToolsService.success(res, `/${Config.adminPath}/main`);
                    } else {
                        await this.ToolsService.error(res, '用户名或密码不正确', `/${Config.adminPath}/login`);
                    }
                } else {
                    await this.ToolsService.error(res, '验证码不正确', `/${Config.adminPath}/login`);
                }
            }
        } catch (error) {
            console.log('error', error);
            res.redirect(`/${Config.adminPath}/login`);
        }
    }

    @Get('loginOut')
    loginOut(@Request() req, @Response() res) {
        console.log('退出');
        req.session.userinfo = null;
        res.redirect(`/${Config.adminPath}/login`);
    }

}

注:现在不校验中间件的地方使用

2.3 实验是否成功

浏览器http://localhost:3000/adminxxx/login,看是否正常显示。

2.4 修改app.module

重点:修改鉴权中间件,让’admin/*'下的路由都经过中间件

.apply(AdminauthMiddleware)
.forRoutes(`${Config.adminPath}/*`)

完整例子

import { Module, NestModule, MiddlewareConsumer } from '@nestjs/common';
import { AdminModule } from './module/admin/admin.module';
import { DefaultModule } from './module/default/default.module';
import { ApiModule } from './module/api/api.module';
import { MongooseModule } from '@nestjs/mongoose';
import { AdminauthMiddleware } from './middleware/adminauth.middleware';
import { InitMiddleware } from './middleware/init.middleware';
import { Config } from './config/config';
@Module({
    imports: [AdminModule, DefaultModule, ApiModule,
        // mongoose连接数据库
        MongooseModule.forRoot("mongodb://127.0.0.1:27017/nestxiaomi")
    ],
    controllers: [],
    providers: [],
})
export class AppModule implements NestModule {
    configure(consumer: MiddlewareConsumer) {
        consumer
            // 访问admin下的东西时才用鉴权中间件
            .apply(AdminauthMiddleware)
            .forRoutes(`${Config.adminPath}/*`)
            .apply(InitMiddleware)
            .forRoutes('*')
    }
}

2.5 修改中间件

@filename(adminauth.middleware)

import { Injectable, NestMiddleware } from '@nestjs/common';
import { Config } from '../config/config';

@Injectable()
export class AdminauthMiddleware implements NestMiddleware {
    use(req: any, res: any, next: () => void) {
        // console.log('中间件', req.baseUrl);
        let pathname = req.baseUrl; // 获取访问的地址 
        // 1.获取session中保存的用户信息
        let userinfo:any = req.session.userinfo; // req.session.userinfo
        // 判断权限(是否登录)
        if (userinfo && userinfo.username) {
            // 设置全局变量
            res.locals.userinfo = userinfo;
            next();
        } else {
            // 未登录时跳转到登录页:排除不需要权限判断的页面(登录、注册、验证码)
            if(pathname == `/${Config.adminPath}/login` || pathname == `/${Config.adminPath}/login/code` || pathname == `/${Config.adminPath}/login/doLogin`) {
                next();
            }else {
                console.log('未登录');
                res.redirect(`/${Config.adminPath}/login`) //重定向
            }
        }
    }
}

2.6 修改前端页面中用到的路由

1. login.ejs

重点:验证码处用到路由

1.验证码:
<img id="verify_img" src="/<%=config.adminPath%>/login/code" title="看不清?点击刷新"
   onclick="javascript:this.src='/<%=config.adminPath%>/login/code?mt='+Math.random()">
   
2.登录
<form action="/<%=config.adminPath%>/login/doLogin" method="post" id="myform">

完整例子

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
  <title>用户登录</title>
    <!-- 注css 文件饮用前加'/' -->
	<link rel="stylesheet" href="/admin/css/login.css"> 
   </head>
<body>
    <div class="container">
        <div id="login">
            <form action="/<%=config.adminPath%>/login/doLogin" method="post" id="myform">
                <div class="l_title">通用商城后台管理系统</div>
                <dl>
                    <dd>管理员姓名:<input class="text" type="text" name="username" id="username"></dd>
                    <dd>管理员密码:<input class="text" type="password" name="password" id="password"></dd>
                    <dd>验 证 码:<input id="verify" type="text" name="code">
                        <img id="verify_img" src="/<%=config.adminPath%>/login/code" title="看不清?点击刷新"
                            onclick="javascript:this.src='/<%=config.adminPath%>/login/code?mt='+Math.random()">
                    </dd>
                    <dd><input type="submit" class="submit" name="dosubmit" value=""></dd>
                </dl>
            </form>
        </div>
    </div>
</body>
</html>

2.7 其他

1.controller中使用方法

// 1.引入config
import { Config } from '../../../config/config'

// 2.修改路由
@Controller(`${Config.adminPath}/login`)

// 3.用到路由处用config.adminPath替换admin
this.ToolsService.error(res, '用户名或密码不合法', `/${Config.adminPath}/login`);

2.前端模板中的使用

重点:<a href="/<%=config.adminPath%>/login/loginOut">安全退出</a>

完整例子

<nav class="navbar navbar-inverse" role="navigation">
    <div class="container-fluid">
        <div class="navbar-header">
            <img sr c="/admin/images/node.jpg" height="44px;" />
        </div>
        <div class="collapse navbar-collapse" id="example-navbar-collapse">           
            <ul class="nav navbar-nav navbar-right">
                <li><a>欢迎您 <%=userinfo.username%></a></li>
                <li><a href="/<%=config.adminPath%>/login/loginOut">安全退出</a>
                </li>
            </ul>
        </div>
    </div>
</nav>

三、nestjs扩展模板方法

重点:新建一个类 – 在中间件中处理成全局方法 – 在模板中使用。

需求:在前端模板中处理字符串。

新建helper.ts

export class Helper{
    static title = "我是全局的title";
    static substring(str:string, start:number, end:number) {
        if(end) {
            return str.substring(start, end);
        }else {
            return str.substring(start);
        }
    }
}

配置成全局方法

@filename(init.middleware)

import { Injectable, NestMiddleware } from '@nestjs/common';
import { Config } from '../config/config';
import { Helper } from '../extend/helper';
@Injectable()
export class InitMiddleware implements NestMiddleware {
    use(req: any, res: any, next: () => void) {
        res.locals.config = Config;
        res.locals.helper = Helper;
        next();
    }
}

前端页面中使用

@filename(welcome.ejs)

截取:<%=helper.substring(userinfo.username, 3)%>
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值