结合客户端 jQuery 和服务器端 Express
Posted
技术标签:
【中文标题】结合客户端 jQuery 和服务器端 Express【英文标题】:Combining client-side jQuery and server - side Express 【发布时间】:2021-07-30 18:35:03 【问题描述】:我正在学习 Express / Node。我正在尝试构建一个简单的 html form
来验证客户端(例如,使用 jQuery / AJAX),但我也从服务器端(使用 Express.js)提供服务。需要明确的是,该应用程序现在非常简单,我可以在客户端做所有事情,但我想构建服务器端行为来学习整个管道。
这是表格。注意button
类型为button
的名称为change-color
;这是我用于调试目的的button
,稍后解释。我还包括jquery
v.3.6.0 和我自己的client.js
文件。
<!DOCTYPE html>
<html lang="en" dir="ltr">
<head>
<meta charset="utf-8">
<title>A MWE</title>
<link rel="stylesheet" href="styles.css">
</head>
<body>
<h1>A simple form.</h1>
<form action="/" method="post">
<input type="text" name="num1" placeholder = "First Number" value=""> <br>
<input type="text" name="num2" placeholder = "Second Number" value=""> <br>
<button type="submit" name="submit">Calculate</button>
<button type="button" name="change-color">Change color</button>
</form>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.6.0/jquery.min.js"></script>
<script src="client.js" charset="utf-8"></script>
</body>
</html>
在表单中,用户应该给我两个数字,然后服务器将求和并返回。服务器代码位于名为 server.js
的文件中,概述如下:
const express = require("express");
const bodyParser = require("body-parser");
const app = express();
app.use(bodyParser.urlencoded(extended:true));
app.listen(3000, () =>
console.log("Server spun on port 3000.");
);
app.get("/", (req, res) =>
console.log("Serving a GET request at root route.");
res.sendFile(absoluteDirPath() + "index.html");
);
app.post("/", (req, res) =>
console.log("Serving a POST request at root route.");
const num1 = Number(req.body.num1);
const num2 = Number(req.body.num2);
res.send("<h3>Result: " + (num1 + num2) + "</h3>");
);
function absoluteDirPath()
const path = require('path');
return __dirname + path.sep;
当我们第一次访问根端点(GET 调用)时,服务器使用res.sendFile()
将上述 HTML 文件发送给用户。当用户在form
上输入两个数字并单击form
内的submit
类型的button
时,server.js
方法的app.post()
计算和send()
s 请求的总和。
显然我需要在应用总和之前进行一些验证;如果我没有得到号码怎么办?根据对this post 的回答,为避免复杂和突然的重定向,我似乎必须在客户端执行此操作,例如在单独的.js
文件中。在同一篇文章中,有人建议我编写类似以下函数的内容并将其分配给事件侦听器:
function submitFormWithoutReloading()
$.ajax(
type: "POST",
url: "/",
data:
num1: $('#idOfYourFirstInput').val(),
num2: $('#idOfYourSecondInput').val()
,
success: function(res)
alert(res); // This is what the server returns
);
但是,我似乎在这里偶然发现了一个更大的问题。当我使用app.get()
方法中的 HTML 文件为用户提供服务时,我在运行所有 jQuery 时遇到了一些问题!好像每次我访问http://localhost:3000/
时,HTML 文件都会发送给我,但链接的client.js
文件没有被读取(我猜同样的事情也适用于 jQuery)。
为了确保这是我的问题,我暂时忘记了验证例程,制作了上面提到的change-color
HTML button
并在client.js
中添加了一些虚拟代码:
$(document).ready(function()
alert("Hi!");
);
$('button[name="change-color"]').click(function()
$("body").toggleClass("colored-background");
);
因此,change-color
按钮仅用于切换 body
元素以根据此 CSS 规则将 yellow
作为其背景:
.colored-background
background-color: yellow;
如果我从我的文件系统打开index.html
,一切正常; jQuery
和我的 client.js
文件已加载,alert()
很好,按钮按预期工作。但是当我访问localhost:3000
并且GET
端点为客户端提供HTML 文件时,就好像DOM 扫描没有读取client.js
并且我不能做任何客户端的事情,包括我非常想要的验证!
对我做错了什么有任何想法吗?我知道我可以在这里在客户端做一切,但我想学习如何在客户端和服务器端拆分关注点。服务器端可能要访问数据库,客户端不能做任何事情。
// 编辑:如果有帮助,Chrome 控制台会在我加载 localhost:3000
时说一些有趣的事情:
【问题讨论】:
【参考方案1】:你没有做错任何事。这只是使用 node.js 的每个人的常见问题(包括我!Cant access other files in Node.js)。
您必须告诉 express 客户端可以查看哪些文件。让我们创建一个名为public
的文件夹。在您的文件夹中,放置您的 .js
和 .css
文件,以及您希望客户端访问的其他图片或其他资产。
您网站上的这个公共文件夹将替换为您的域。考虑这些文件/文件夹:
index.js (server)
/ views
- index.html
/ public
- style.css
- client.js
- jquery.min.js
客户端只能访问public
内的文件,例如:http://localhost:3000/style.css
,或http://localhost:3000/client.js
,或http://localhost:3000/jquery.min.js
。但是,我们将无法访问其他文件(不在公共文件夹中),除非服务器明确获取它:
app.get('/index.html', function(req, res)
res.sendFile(path.join(__dirname, '/views/index.html'));
);
解决方案:
// ...
const path = require('path');
const app = express();
app.use(express.static(path.join(__dirname, '/public')));
// You routes here
这样,客户端就可以访问public
目录下的所有文件。你的问题应该已经解决了。
记住:服务器仍然可以访问所有文件。这只会限制客户端。
【讨论】:
哈,是的,我实际上得到了一位朋友的相同解决方案,我回来回答我自己的问题,但最好给别人加分。这工作正常,现在我在一种语言中实现了客户端和服务器端的关注点分离,就像宣传的那样。谢谢! 耶!我很高兴你解决了你的问题。我很乐意帮助您解决其他问题(我可以回答)以上是关于结合客户端 jQuery 和服务器端 Express的主要内容,如果未能解决你的问题,请参考以下文章
如何在github上将客户端和服务器端项目文件夹作为一个项目(api +前端)一起推送?
如何在逻辑上结合 react-router 和 redux 进行客户端和服务器端渲染