javascript - 是否可以创建全局 Ejs 组件?
问题描述
如您所见,我在 index.ejs 文件中包含了我的导航栏组件,并且我对我拥有的每个其他文件都做同样的事情,例如用户页面。有什么方法可以通过将导航栏组件包含在我的所有 ejs 文件中的某个地方一次来使用它吗?而不是将它单独包含在每个 ejs 文件中?
现在我在我的每个文件中都这样做:
索引.ejs:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
</head>
<body>
<% include components/navbar %>
rest of the code...
</body>
</html>
解决方案
正如您在评论中要求的那样,这是我的方法:
我在项目中有“views”文件夹,其中包括这些文件夹:
- 资产
- 布局
和它们旁边的动态 ejs 文件
假设我们要渲染这个布局,它在每个页面中都有一个标题,但有不同的正文:
布局 :
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<% for (let cssLink of cssLinks) { %>
<link rel="stylesheet" href="<%= cssLink %>" />
<% } %>
<title>home page</title>
</head>
<body>
<h1>THIS IS HEADER!</h1>
<div id="demo">
<%- mainView %>
</div>
</body>
</html>
您可以看到主体中有一个变量mainView
,所以让我们看看如何在其中插入动态主体:
我的实用程序文件夹中有一个函数,可以减少代码的重复:
const ejs = require('ejs');
const path = require('path');
const layoutsPath = path.join(__dirname, "./../views/layouts/");
const assetsPath = path.join(__dirname, "./../views/assets/");
const viewsPath = path.join(__dirname, './../views/');
const load = (basePath, filename, data, cb = null) => {
let route ;
switch (basePath) {
case 'layout': {
route = layoutsPath;
break;
}
case 'asset': {
route = assetsPath;
break;
}
case 'view': {
route = viewsPath;
break;
}
default: {
route = basePath;
}
}
ejs.renderFile(path.join(route, filename), data, (err, str) => {
if (err) {
console.log(err);
return err;
}
if (cb === null) {
return str;
} else {
return cb(str);
}
});
}
module.exports = {
load
}
现在index.js
我想将我的home.ejs
内心输出header.ejs
给客户:
let allUsers = await usersModule.findAll();
let renderedHTML = '';
load('view', 'home.ejs', { allUsers }, (rendered) => {
load('layout', 'header.ejs', { mainView: rendered, cssLinks: ['/css/header.css'] }, (fullView) => {
renderedHTML = fullView;
});
});
res.status(200).send(renderedHTML);
所以在这里我从数据库中获取我身体所需的数据,将其传递给 home.ejs,在那里我循环并渲染我的身体视图,例如 home.ejs:
<div>
<% for (let user of allUsers) { %>
<ul>
<li>email : <%= user.email %></li>
<li>name : <%= user.name %></li>
</ul>
<% } %>
</div>
渲染的主体作为参数传递给我们的回调,我们现在可以使用变量名将它传递给我们的标题mainView
,因此在标题中,整个渲染的主体将插入到我们布局中的正确位置。现在我们的布局和动态主体已经合并,可以发送给客户端了
推荐阅读
- neo4j - 每个顶点有 100 多条边的图
- group-by - Power BI:无代码的表可视化中的 GroupBy 列
- android - Android:当 android 设备进入打盹模式时 SignalR 失败
- azure - 是否建议为您组织中的每个应用程序订阅一个订阅?
- arrays - 如何通过数组获取一列中的所有日期值?
- java - 在单向一对多关系中插入实体对象的问题
- r - 通过排除一系列字符串来处理子集时的空格
- javascript - 需要显示模态直到多个 TinyMCE 初始化完全完成
- python - 如何将表格信息发送到我的个人邮箱?
- swiftui - SwiftUI NavigationLink:成功运行帐户创建代码后导航到目标视图