【问题标题】:Reload page that posted data via XMTHTTPRequest object重新加载通过 XMTHTTPRequest 对象发布数据的页面
【发布时间】:2020-06-22 17:32:50
【问题描述】:

我正在学习 Web 开发,刚刚开始学习 AJAX;而这种学习 AJAX 的追求让我发疯了……

我在 stackoverflow 上使用 JQuery 看到了很多类似的帖子,但我希望使用纯 JS 来实现这一点。

我的要求是,我有一个通过 XMLHTTPRequest 对象发布表单数据的 HTML 页面。数据正确发送到服务器(节点)。我想要实现的是使用刚刚发布的数据(Like So)重新加载发送数据的同一页面。

我知道这可以通过 JQuery 来完成(即通过调用 location.reload()),但是我不能仅仅通过使用 XHMHTTPRequest 来实现它。甚至有可能用 XHR 实现这一目标吗?我可以看到 xhr 的 ResponseText 具有所需更新的整个 HTML (See Ref)。然后我怎样才能使用这个 html 来重新加载页面。

非常感谢任何方向。

<!DOCTYPE html>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=Edge, chrome=1"/>

<script>
"use strict";
function submitForm()
{
  var formElement = document.getElementById("myForm");
  var formData = new FormData(formElement);

  var xhr = new XMLHttpRequest();
  xhr.onreadystatechange=function(){
    if (xhr.readyState == 4 && xhr.status == 200)
    {
      alert(xhr.responseText); //xhr.responseText has the entire desired HTML
      window.location.reload; //Does nothing
    }
  }
  xhr.open("POST", "/Test", true);
  xhr.send(formData);
  return false;
}
</script>
</head>

<body>
<form id="myForm" method="POST" action="/Test" onsubmit="return submitForm()">
   <input type="text" value="John" name="name"/>
   <input type="submit" value="Send Data"/>
</form>
<div class="">
  <h4>Name entered was <%= data %></h4>
</div>
</body>
</html>
//Node JS
var express = require('express');
var bodyparser = require('body-parser');
var multer = require('multer'); 

var app = express();
app.use(express.static('./'));
app.set('view engine', 'ejs');
var mydata;

var urlencoded = bodyparser.urlencoded({extended:true});
var mult_handler = multer();

app.get('/Test', function(req, res){
    res.render("Test", {data:mydata});
});

app.post('/Test',mult_handler.none(), function(req, res){
  console.log("In POST");
  console.log(req.body.name);
  mydata = req.body.name;
  res.render("Test", {data:req.body.name});
});

【问题讨论】:

  • 这不是 AJAX 的用途,请使用常规表单重新加载页面。 location.reload() 不是 jQuery,它只是一个纯 DOM 对象及其方法。
  • 旁注:jQuery 是一个用 JavaScript 编写的库,所以用 jQuery 完成的任何事情都可以在 vanilla JavaScript 中完成。如果需要,可以使用Fetch API 代替 XMLHttpRequest。
  • 你没有调用 reload 函数。你没有在window.location.reload之后加上括号
  • window.location.reload 只是重新加载页面,从 XHR 返回的任何内容在该新页面上均不可用。

标签: javascript html node.js xmlhttprequest


【解决方案1】:

这是根据 Teemu 的评论构建的高级答案。我同意这不是 AJAX 的使用方式。使用 AJAX 的全部目的是让您无需刷新页面即可从请求中加载数据。相反,您可以动态显示每个请求的数据/内容。

目前,在您的代码中:

alert(xhr.responseText); //xhr.responseText has the entire desired HTML
window.location.reload; //Does nothing

尝试删除window.location.reload 并以适合您的应用程序的方式解析xhr.responseText。这意味着您应该根据端点返回的内容来解析它。在 /Test 端点中返回 JSON 的快速方法是在 app.post() 语句的末尾写入 res.send({ data: req.body.name });。除了这个问题,还有其他方法可以返回与Express.js更相关的json,所以我不会详细说明。

一旦您从返回到客户端的 XHR 对象中解析了数据,您就可以通过 id 选择页面上的不同元素并更新它们的值。更新值的方法有很多,但这只是其中一种。

例如,您可以这样编写示例 div:

<div>
  <h4 id="some_text"></h4>
</div>

并使用 vanilla JS 将值添加到 statechanged 处理程序中的 h4 标记。也许是这样的: document.getElementById("some_text").innerHtml = JSON.parse(xhr.responseText).data;

【讨论】:

  • @Teemu:感谢您的评论。因为我知道这可以通过 jOquery 来实现,而且 jQuery 在底层基本上是 vanilla JS,所以我对尝试使用 vanilla Js 和 XHR 解决这个问题有点好奇。但是,如果 XHR.responseText 返回需要加载的感兴趣的 HTML,如何使用它?
  • @Domino:我会试一试 FetchAPI,即使在 location.reload() 周围加上括号,我也无法让它工作。
  • 杰克逊,非常感谢您的评论。这为我清除了很多东西。因此,如果我要将 POST 重定向到具有更新数据的另一个页面,那么 res.render("SomeotherPageWithUpdatedData", {data:req.body.name});工作,只要 action 属性也指向同一个页面?
  • @Laavanya 不,jQuery 也不会使用获取的数据加载新页面。如果响应是一个 HTML 字符串,那么你可以直接使用它作为 innerHTML 的值,XHR 的思想就是,只有页面的一部分会被重新填充一些新的内容。如果你真的必须从响应中创建一个全新的页面,here is how to do that,尽管我不建议在任何情况下如此严重地滥用 XHR,因为同样可以通过使用简单的表单提交而不是 AJAX 调用来实现.
  • 再一次,我同意 Teemu 的回应,即只有当你真的必须创建一个全新的页面时,你才应该使用表单提交而不是 XHR。由于我假设您正在创建自己的自定义端点来调用,您可以只返回一个 JSON 对象,这将使您的 xhr.responseText 保存一个 JSON 值。我不认为使用res.render() 会在这里工作,因为根据我的理解,res.render() 用于渲染整个页面/视图。文档:Renders a view and sends the rendered HTML string to the client 但你可以试试res.json()expressjs.com/en/api.html#res.json
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-11-07
  • 2012-02-22
  • 2015-03-09
  • 1970-01-01
  • 2012-08-19
  • 2019-07-20
  • 2013-10-26
相关资源
最近更新 更多