当前位置: 首页 > news >正文

NodeJs 中的 HTML 模板

  • 💂 个人网站:【海拥】【摸鱼游戏】【神级源码资源网】
  • 🤟 前端学习课程:👉【28个案例趣学前端】【400个JS面试题】
  • 💅 想寻找共同学习交流、摸鱼划水的小伙伴,请点击【摸鱼学习交流群】

HTML 模板是一种允许我们创建基本 HTML 结构并使用占位符根据从 JSON 文件或数据库中检索到的数据动态生成内容的技术。

让我们考虑一个假设实例,其中我们的网站包含许多产品卡,每个卡都包含从 JSON 文件中检索到的特定产品详细信息。

现在,如果我们要从 JSON 文件中添加或删除任何产品,我们将如何在前端动态更新相应的卡片?

考虑到我们基于内容的数据存储在 JSON 文件中,我们可以继续从现有的 HTML 代码创建可重用的模板。

第 1 步:构建模板

作为开发人员,您可能熟悉提供动态 Web 内容的概念。实现这一目标的一种方法是使用模板。

我们将创建两个 HTML 模板,一个用于产品概览页面,一个用于单个产品卡片。

第一个模板template-card.html用作单个产品卡片的蓝图,第二个模板template-overview.html用作概览页面的蓝图。这些模板包含占位符,当用户请求页面时,这些占位符将被替换为实际内容。

确保您的占位符不包含任何属于 HTML 代码的符号。占位符的常用语法是{%PLACEHOLDER_NAME%}.

这是template-card.html我们的第一个模板,用作根据需要动态创建尽可能多的卡片的蓝图。

<figure class="card"><div class="card__emoji">{%IMAGE%}{%IMAGE%}</div><div class="card__title-box"><h2 class="card__title">{%PRODUCTNAME%}</h2></div><div class="card__details"><div class="card__detail-box"><h6 class="card__detail card__detail {%NOT_ORGANIC%}"> Organic!</h6></div><div class="card__detail-box"><h6 class="card__detail">{%QUANTITY%} per 📦</h6></div><div class="card__detail-box"><h6 class="card__detail card__detail--price"> {%PRICE%}€</h6></div></div><a class="card__link" href="/product?id={%ID%}"><span>Detail <i class="emoji-right">👉</i></span></a></figure>

由于此卡片将用作模板,因此其中包含的信息也应替换为占位符。添加占位符后,卡片将类似于以下内容:

<figure class="card"><div class="card__emoji">🥦🥦</div><div class="card__title-box"><h2 class="card__title">Apollo Broccoli</h2></div><div class="card__details"><div class="card__detail-box"><h6 class="card__detail card__detail--organic">Organic!</h6></div><div class="card__detail-box"><h6 class="card__detail">3🥦 per 📦</h6></div><div class="card__detail-box"><h6 class="card__detail card__detail- price">5.50</h6></div></div><a class="card__link" href="/product?id="><span>Detail <i class="emoji-right">👉</i></span></a></figure>

锚标记包含一个 href 链接,其中包含一个 ID 的占位符。这表明我们的 JSON 文件中的每张卡或产品都有一个不同的 ID。这些 ID 是唯一的,将用于在路由过程中识别每个产品。

此外,当我们需要根据元素的类别设置元素样式时,CSS 类和 ID 可以用占位符代替,就像在图像示例中所做的那样。这种方法在这种情况下特别有用。

<body><div class="container"><h1>🌽 Node Farm 🥦</h1><div class="cards-container">{%PRODUCT_CARDS%}</div></div>
</body>

在此示例中,我们已将模板卡片替换为占位符。请务必记住,我们将使用这个单一模板卡片动态生成多张卡片。

注意:这是我们的第二张模板卡,template-overview.html

第 2 步:填充模板

有趣的部分来了,通过用实际内容替换我们的占位符来填充我们的模板。

当用户请求 URL 时,代码会同步读取相关模板文件(或者template-overview.htmltemplate-card.html),用 JSON 文件中的内容动态填充它,并将相关内容作为响应发回给用户。

这是通过使用函数实现的replaceTemplate,该函数用实际内容替换模板中的占位符。

// SECOND STEP:
const replaceTemplate = (temp, product) => {let output = temp.replace(/{%PRODUCTNAME%}/g, product.productName);output = output.replace(/{%IMAGE%}/g, product.image);output = output.replace(/{%PRICE%}/g, product.price);output = output.replace(/{%ID%}/g, product.id); // /g is a regex global flagreturn output;
}// FIRST STEP:
const tempOverview = fs.readFileSync(`${__dirname}/templates/template-overview.html`, 'utf-8');
const tempCard = fs.readFileSync(`${__dirname}/templates/template-card.html`, 'utf-8');
const data = fs.readFileSync(`${__dirname}/dev-data/data.json`, 'utf-8');
const dataObj = JSON.parse(data);// THIRD STEP:
const server = http.createServer((req, res) => {const pathName = req.url;//FOURTH STEP://Here is the Overviewif(pathName === '/' || pathName === '/overview') {res.writeHead(200, {'Content-type': 'text/html'});const cardsHtml = dataObj.map(el => replaceTemplate(tempCard, el)).join('');const output = tempOverview.replace('{%PRODUCT_CARDS%', cardsHtml);res.end(output);//API} else if(pathName === '/api') {res.writeHead(200, {'Content-type': 'application/json'});res.end(data);// Not Found} else {res.writeHead(404, {'Content-type': 'text/html', //standard header'my-header': 'hello-world'});res.end('<h1>This page cannot be found.</h1>');}
});server.listen(8000, '127.0.0.1', () => {console.log('Listening to requests on port 8000');
});res.writeHead(404, {'Content-type': 'text/html', //standard header'my-header': 'hello-world'});res.end('<h1>This page cannot be found.</h1>');}
});server.listen(8000, '127.0.0.1', () => {console.log('Listening to requests on port 8000');
});

别担心,我们将仔细研究上面的大块代码,并用更简单的术语弄清楚它的作用。

  • 首先,读取两个 HTML 模板文件和存储在 JSON 文件中的产品数据
  • 其次,定义一个函数,用特定于产品的数据替换模板中的占位符。在这里,我们的函数被命名为replaceTemplate
  • 第三、监听传入的 HTTP 请求并检查请求 URL 的路径名
  • 第四,如果路径名为//overview,则使用replaceTemplatefunction和JSON文件中的产品数据替换tempCard模板中的占位符,为每个产品卡生成HTML代码。
  • 然后连接每张卡片的结果 HTML 以创建字符串cardsHtml。然后修改模板tempOverview以包含 cardsHtml 字符串,并将生成的 HTML 代码作为响应发回。
  • 此外,如果路径名是,/api它会以 JSON 格式发回产品数据作为响应
  • 最后,如果路径名是其他任何内容,则发回 404 错误消息。

哇,那段代码看起来确实很多,但如果我们仔细看,一步一步来,它并没有那么复杂。

它所做的只是用真实信息替换一些特殊词并将其发送回网站,以便人们可以看到它!

HTML 模板的好处

HTML 模板提供了几个好处,使其成为 Web 开发人员的热门选择:

  • 通过使用 HTML 模板,我们将内容与表示分离,允许开发人员生成可重复使用的模板,这些模板可以处理来自多个来源的不同数量的数据,并维护类似代码的多个副本。
  • HTML 模板为呈现数据、改善用户体验和轻松导航站点提供了标准结构。
  • 模板的灵活性使得修改底层数据变得更加容易。这节省了时间和精力,因为开发人员不需要手动更改 HTML 代码。
  • 由于 HTML 模板可重复使用,因此更易于维护和更新。可以在不修改模板代码的情况下对基础数据进行更改,从而降低出错的可能性。
  • HTML 模板可以在不影响性能的情况下处理大量数据。这使其成为具有大量动态内容的网站的理想选择。

总之,HTML 模板是一种高效、一致、灵活且可扩展的技术,可简化动态 Web 内容的开发和维护。

通过将内容与表示分离,HTML 模板使开发人员能够创建可重用的模板,这些模板可以处理不同数量的数据,而无需将内容硬编码到每个页面中。

拓展部分:

Node.js 中还有其他几个可用的模板引擎,例如 EJS、Pug(以前称为 Jade)、Handlebars 和 Mustache 等。

要在 Node.js 中使用模板引擎,您需要通过 npm 安装它,然后在您的代码中需要它。这些引擎提供了一种通过将数据插入模板内的占位符来生成 HTML 的方法。

⭐️ 好书推荐

《特效师手册:影视剪辑与特效制作从入门到精通(剪映版)》

在这里插入图片描述

【内容简介】

本书根据作者多年的特效制作经验,结合目前年轻人喜爱的短视频特效,设计、讲解了 11 章内容,包括影视剪辑与特效基础、画面特效与人物特效、使用蒙版合成画面、混合模式合成效果、用关键帧制作特效、掌握剪映抠图特效、剪辑影视解说视频、制作影视字幕特效,以及制作热门的武侠类特效、仙侠类特效和科幻类特效等,帮助读者在较短的时间内,从新手成为剪映影视剪辑和特效制作高手。本书既讲解了如何在剪映电脑版中进行影视剪辑与特效制作,也讲解了剪映手机版的案例制作步骤,让读者买一本书精通剪映的两个版本,轻松玩转剪映电脑版 + 手机版,随时随地制作出精彩的影视混剪与特效视频。

📚 京东自营购买链接:《特效师手册:影视剪辑与特效制作从入门到精通(剪映版)》

相关文章:

NodeJs 中的 HTML 模板

&#x1f482; 个人网站:【海拥】【摸鱼游戏】【神级源码资源网】&#x1f91f; 前端学习课程&#xff1a;&#x1f449;【28个案例趣学前端】【400个JS面试题】&#x1f485; 想寻找共同学习交流、摸鱼划水的小伙伴&#xff0c;请点击【摸鱼学习交流群】 HTML 模板是一种允许我…...

3.ffmpeg命令行环境搭建、ffmpeg命令行初步了解

在上章,我们讲过: ffmpeg.exe: 主要用于转码或者剪切的应用程序, 也可以从url/现场音频/视频源抓取输入源ffplay.exe: 主要用于播放视频的应用程序,该应用程序源码是开源的,我们后面章节会去源码分析ffprobe.exe: 主要用于分析视频码流的应用程序, 可以获取媒体文件的详细信息,…...

Kubernetes初始化容器

初始化容器 之前了解了容器的健康检查的两个探针&#xff1a;liveness probe&#xff08;存活探针&#xff09;和readiness probe&#xff08;可读性探针&#xff09;的使用方法&#xff0c;我们说在这两个探针是可以影响容器的生命周期的&#xff0c;包括我们之前提到的容器的…...

leetcode: Swapping Nodes in a Linked List

leetcode: Swapping Nodes in a Linked List1. 题目描述2. 题目解答3. 总结1. 题目描述 You are given the head of a linked list, and an integer k.Return the head of the linked list after swapping the values of the kth node from the beginning and the kth node f…...

Nydus 在约苗平台的容器镜像加速实践

文 | 向申 约苗平台运维工程师 关注云原生领域 本文字数 9574阅读时间24分钟 本文是来自向申同学的分享&#xff0c;介绍了其在 K8s 生产环境集群部署 Nydus 的相关实践。 Nydus 是蚂蚁集团&#xff0c;阿里云和字节等共建的开源容器镜像加速项目&#xff0c;是 CNCF Dragon…...

企业对不同形态CRM系统价格需求不同

很多企业在选型时关心CRM客户管理系统的价格&#xff0c;有人对CRM的价格完全没有概念&#xff0c;也有的人先问价格再看其他。CRM价格在系统选型中到底有多重要&#xff1f;不同类型CRM系统的价格是否有所不同&#xff1f; CRM的不同产品形态也会影响价格 通常情况下&#x…...

「JVM 高效并发」线程安全

面向过程编程&#xff0c;把数据和过程分别作为独立的部分考虑&#xff0c;数据代表问题空间中的客体&#xff0c;程序代码则用于处理这些数据&#xff1b;面向对象编程&#xff0c;把数据和行为都看做对象的一部分&#xff0c;以符合现实世界的思维方式来编写和组织程序&#…...

微信扫码登录

一、准备工作 微信开发者平台&#xff1a;https://open.weixin.qq.com 1、注册 2、邮箱激活 3、完善开发者资料 4、开发者资质认证&#xff1a;仅能企业注册&#xff08;后面提供学习的使用渠道&#xff09;准备营业执照&#xff0c;1-2个工作日审批、300元 5、创建网站应用&…...

Unity协程的简单应用

Unity协程是一种特殊的函数&#xff0c;可以让你在Unity中创建一种类似于多线程的异步操作。它可以在需要等待某个操作完成时&#xff0c;暂停执行当前代码&#xff0c;等待某个条件满足后再继续执行。 在一般情况下 unity中调用函数时&#xff0c;函数将运行到完成状态&#x…...

LeetCode 1250. Check If It Is a Good Array【数论】

本文属于「征服LeetCode」系列文章之一&#xff0c;这一系列正式开始于2021/08/12。由于LeetCode上部分题目有锁&#xff0c;本系列将至少持续到刷完所有无锁题之日为止&#xff1b;由于LeetCode还在不断地创建新题&#xff0c;本系列的终止日期可能是永远。在这一系列刷题文章…...

ETHDenver 2023

ETHDenver是全球最大、持续时间最长的以太坊活动之一&#xff0c;今年的活动定于2月24日至3月5日在美国科罗拉多州丹佛市盛大举行。这次活动将面向以太坊和其他区块链协议爱好者、设计者和开发人员。Moonbeam作为ETHDenver 2023的Meta赞助商&#xff0c;将在本次活动中展示令人…...

React架构演变

老版React架构 React 16之前的架构 其实就分为两个部分&#xff1a; Reconciler协调器Render渲染器 Reconciler协调器负责本次更新有什么组件需要被渲染&#xff0c;diff算法就发生在这个步骤中&#xff0c;在diff算法中会将上次更新的组件和本次更新的组件做一个对比&…...

安全认证--JWT介绍及使用

安全认证--JWT介绍及使用1.无状态登录原理1.1.什么是有状态&#xff1f;1.2.什么是无状态1.3.如何实现无状态1.4.JWT1.4.1.简介1.4.2.数据格式2.编写JWT工具2.1.添加JWT依赖2.2.载荷对象2.3.工具2.4.测试2.4.1.配置秘钥2.4.2.测试类1.无状态登录原理 有状态登录和无状态登录详…...

【计算机组成原理】计算机硬件的基础组成、认识各个硬件部件

计算机组成原理&#xff08;一&#xff09; 计算机内部是通过电信号传递数据 电信号&#xff1a;分为高电平和低电平&#xff0c;分别代表1/0 数字、文字、图像如何用二进制表示? CPU如何对二进制数进行加减乘除? 如何存储这些二进制数的? 如何从内存中取出想要的数…...

使用ChIPSeeker进行ChIP-seq, ATAC-seq,cuttag等富集峰的基因组注释

二代测序产生的数据类型 常规的下一代高通量测序&#xff08;next generation sequencing, NGS&#xff09;实验通常产生大量短片段(reads)&#xff0c;通常我们需要将这些reads比对到参考基因组/转录组上&#xff0c;即将它们置于生物学上有意义的基因背景下&#xff0c;才能…...

第九届蓝桥杯省赛——7缩位求和

题目&#xff1a;在电子计算机普及以前&#xff0c;人们经常用一个粗略的方法来验算四则运算是否正确。比如&#xff1a;248 * 15 3720把乘数和被乘数分别逐位求和&#xff0c;如果是多位数再逐位求和&#xff0c;直到是1位数&#xff0c;得2 4 8 14 > 1 4 5;1 5 65…...

【c++】STL常用容器5—list容器

文章目录list基本概念list构造函数list赋值和交换list大小操作list插入和删除list数据存取list反转和排序list基本概念 功能&#xff1a;将数据进行链式存储。 链表&#xff08;list&#xff09;是一种物理存储单元上非连续的存储结构&#xff0c;数据元素的逻辑顺序是通过链…...

【牛客刷题专栏】0x0D:JZ5 替换空格(C语言编程题)

前言 个人推荐在牛客网刷题(点击可以跳转)&#xff0c;它登陆后会保存刷题记录进度&#xff0c;重新登录时写过的题目代码不会丢失。个人刷题练习系列专栏&#xff1a;个人CSDN牛客刷题专栏。 题目来自&#xff1a;牛客/题库 / 在线编程 / 剑指offer&#xff1a; 目录前言问题…...

聚观早报 | 苹果2024年放弃高通;腾讯回应进军类 ChatGPT

今日要闻&#xff1a;苹果2024年放弃高通&#xff1b;腾讯回应进军类 ChatGPT&#xff1b;小米发布无线AR眼镜探索版&#xff1b;50%的美国企业已在使用ChatGPT&#xff1b;Snap推出ChatGPT驱动的聊天机器人 苹果2024年放弃高通 高通公司 CEO 兼总裁克里斯蒂亚诺・安蒙&#xf…...

Elasticsearch:如何正确处理 Elasticsearch 摄取管道故障

在我之前的文章 “Elastic&#xff1a;开发者上手指南” 中的 “Ingest pipeline” 章节中个&#xff0c;我有很多文章是关于 ingest pipeline 的。在今天的文章中&#xff0c;我将重点介绍如何处理在摄取管道中的错误。在我之前的文章 “Elasticsearch&#xff1a;如何处理 in…...

Python:操作 Excel 折叠

💖亲爱的技术爱好者们,热烈欢迎来到 Kant2048 的博客!我是 Thomas Kant,很开心能在CSDN上与你们相遇~💖 本博客的精华专栏: 【自动化测试】 【测试经验】 【人工智能】 【Python】 Python 操作 Excel 系列 读取单元格数据按行写入设置行高和列宽自动调整行高和列宽水平…...

Auto-Coder使用GPT-4o完成:在用TabPFN这个模型构建一个预测未来3天涨跌的分类任务

通过akshare库&#xff0c;获取股票数据&#xff0c;并生成TabPFN这个模型 可以识别、处理的格式&#xff0c;写一个完整的预处理示例&#xff0c;并构建一个预测未来 3 天股价涨跌的分类任务 用TabPFN这个模型构建一个预测未来 3 天股价涨跌的分类任务&#xff0c;进行预测并输…...

页面渲染流程与性能优化

页面渲染流程与性能优化详解&#xff08;完整版&#xff09; 一、现代浏览器渲染流程&#xff08;详细说明&#xff09; 1. 构建DOM树 浏览器接收到HTML文档后&#xff0c;会逐步解析并构建DOM&#xff08;Document Object Model&#xff09;树。具体过程如下&#xff1a; (…...

云原生玩法三问:构建自定义开发环境

云原生玩法三问&#xff1a;构建自定义开发环境 引言 临时运维一个古董项目&#xff0c;无文档&#xff0c;无环境&#xff0c;无交接人&#xff0c;俗称三无。 运行设备的环境老&#xff0c;本地环境版本高&#xff0c;ssh不过去。正好最近对 腾讯出品的云原生 cnb 感兴趣&…...

省略号和可变参数模板

本文主要介绍如何展开可变参数的参数包 1.C语言的va_list展开可变参数 #include <iostream> #include <cstdarg>void printNumbers(int count, ...) {// 声明va_list类型的变量va_list args;// 使用va_start将可变参数写入变量argsva_start(args, count);for (in…...

【学习笔记】erase 删除顺序迭代器后迭代器失效的解决方案

目录 使用 erase 返回值继续迭代使用索引进行遍历 我们知道类似 vector 的顺序迭代器被删除后&#xff0c;迭代器会失效&#xff0c;因为顺序迭代器在内存中是连续存储的&#xff0c;元素删除后&#xff0c;后续元素会前移。 但一些场景中&#xff0c;我们又需要在执行删除操作…...

【Linux系统】Linux环境变量:系统配置的隐形指挥官

。# Linux系列 文章目录 前言一、环境变量的概念二、常见的环境变量三、环境变量特点及其相关指令3.1 环境变量的全局性3.2、环境变量的生命周期 四、环境变量的组织方式五、C语言对环境变量的操作5.1 设置环境变量&#xff1a;setenv5.2 删除环境变量:unsetenv5.3 遍历所有环境…...

「全栈技术解析」推客小程序系统开发:从架构设计到裂变增长的完整解决方案

在移动互联网营销竞争白热化的当下&#xff0c;推客小程序系统凭借其裂变传播、精准营销等特性&#xff0c;成为企业抢占市场的利器。本文将深度解析推客小程序系统开发的核心技术与实现路径&#xff0c;助力开发者打造具有市场竞争力的营销工具。​ 一、系统核心功能架构&…...

Java并发编程实战 Day 11:并发设计模式

【Java并发编程实战 Day 11】并发设计模式 开篇 这是"Java并发编程实战"系列的第11天&#xff0c;今天我们聚焦于并发设计模式。并发设计模式是解决多线程环境下常见问题的经典解决方案&#xff0c;它们不仅提供了优雅的设计思路&#xff0c;还能显著提升系统的性能…...

Qt Quick Controls模块功能及架构

Qt Quick Controls是Qt Quick的一个附加模块&#xff0c;提供了一套用于构建完整用户界面的UI控件。在Qt 6.0中&#xff0c;这个模块经历了重大重构和改进。 一、主要功能和特点 1. 架构重构 完全重写了底层架构&#xff0c;与Qt Quick更紧密集成 移除了对Qt Widgets的依赖&…...