为什么我在网络慢的时候会收到多个 XHR 请求?
Why do I get multiple XHR requests when network is slow?
当我从家庭网络(缓慢,上传速度低于 1Mb/s)在我的网站上执行操作(上传 post 请求)时,Chrome 开发工具显示多个 XHR 请求:
虽然当我执行相同的操作但这次是从我的 4G phone 网络(更快,大约 10Mb/s 上传)时,chrome 开发工具只显示一个(有时是 2 个)XHR请求:
它是如何以及为什么决定这样分裂的?它 link 是因为它是分块传输编码吗?
或者可能是因为 keepalive 超时 5?
问题是当有那么几个 XHR 请求并且我在所有请求结束到代码 200 之前重新加载页面(有时可能需要几分钟)时,我丢失了一些数据。
谢谢。
编辑:
正如评论中所问,这是我用于这部分的代码(我试图通过删除与问题无关的部分来清理它,希望它有所帮助)
例如,如果我更新或添加“标签”到我的笔记(我的代码是笔记应用程序“Evernote”类型),更改会在我的 index.php 文件中触发:
<div class="name_tags"><span><input onfocus="updateidtags(this);" id="tags'.$row['id'].'" type="text" placeholder="Tags ?" value="'.$row['tags'].'"></input></span></div>
然后我的所有函数所在的 JavaScript 文件被调用:
var editing = 0;
var lastudpdate;
var editingnote=-1;
$( document ).ready(function() {
setInterval(function(){ checkedit(); }, 1000);
});
function updateidtags(el)
{
editingnote = el.id.substr(4);
}
function checkedit(){
if(editingnote==-1) return ;
var curdate = new Date();
var curtime = curdate.getTime();
if(editing==1 && curtime-lastudpdate > 1000){
updatenote();
}
}
function updatenote(){
var headi = document.getElementById("inp"+editingnote).value;
var ent = $("#entry"+editingnote).html();
var entcontent = $("#entry"+editingnote).text();
var doss = document.getElementById("dossier"+editingnote).value;
var sousdoss = document.getElementById("sousdoss"+editingnote).value;
var tags = document.getElementById("tags"+editingnote).value;
$.post( "updatenote.php", {pass: app_pass, id: editingnote, dossier: doss, sousdossier: sousdoss, tags: tags, heading: headi, entry: ent, entrycontent: entcontent, now: (new Date().getTime()/1000)-new Date().getTimezoneOffset()*60})
.done(function(data){
if(data=='1'){
editing = 0;
$('#lastupdated'+editingnote).html('Last Saved Today');
}
else{
editing = 0;
$('#lastupdated'+editingnote).html(data);
}
});
$('#newnotes').hide().show(0);
}
最后调用更新 php 文件(我从中删除了将数据发送到数据库的部分):
<?php
[...]
$id = $_POST['id'];
$heading = $_POST['heading'];
$entry = $_POST['entry'];
$entrycontent = $_POST['entrycontent'];
$now = $_POST['now'];
$seconds = $now;
$dossier = $_POST['dossier'];
$sousdossier = $_POST['sousdossier'];
$tags = $_POST['tags'];
$filename = "entries/".$dossier."/".$id.".html";
[...]
$str = fread($handle, filesize($filename));
if ($entry != ''){
if (!fwrite($handle, $entry)){
die("Error while writing to html file");
}
}
fclose($handle);
?>
如果它有助于查看整个代码的样子,我可以提供 Github 存储库,但我不确定我是否可以在这里这样做。
@Daniel Farrell 是对的,问题出在我每秒发送一个新请求,当网络太慢时,这个请求太短了,前一个请求无法完成。这是有问题的代码部分:
$( document ).ready(function() {
setInterval(function(){ checkedit(); }, 1000);
});
它每 1 秒执行一次 checkedit() 函数并启动 updatenote.php 写入文件但是在慢速网络上,这个操作对于一些大文件需要超过一秒所以 setInterval 函数调用 updatenote.php 在最后一个完成之前再次。然后它创建一个新请求。
当我从家庭网络(缓慢,上传速度低于 1Mb/s)在我的网站上执行操作(上传 post 请求)时,Chrome 开发工具显示多个 XHR 请求:
虽然当我执行相同的操作但这次是从我的 4G phone 网络(更快,大约 10Mb/s 上传)时,chrome 开发工具只显示一个(有时是 2 个)XHR请求:
它是如何以及为什么决定这样分裂的?它 link 是因为它是分块传输编码吗?
或者可能是因为 keepalive 超时 5?
问题是当有那么几个 XHR 请求并且我在所有请求结束到代码 200 之前重新加载页面(有时可能需要几分钟)时,我丢失了一些数据。
谢谢。
编辑:
正如评论中所问,这是我用于这部分的代码(我试图通过删除与问题无关的部分来清理它,希望它有所帮助)
例如,如果我更新或添加“标签”到我的笔记(我的代码是笔记应用程序“Evernote”类型),更改会在我的 index.php 文件中触发:
<div class="name_tags"><span><input onfocus="updateidtags(this);" id="tags'.$row['id'].'" type="text" placeholder="Tags ?" value="'.$row['tags'].'"></input></span></div>
然后我的所有函数所在的 JavaScript 文件被调用:
var editing = 0;
var lastudpdate;
var editingnote=-1;
$( document ).ready(function() {
setInterval(function(){ checkedit(); }, 1000);
});
function updateidtags(el)
{
editingnote = el.id.substr(4);
}
function checkedit(){
if(editingnote==-1) return ;
var curdate = new Date();
var curtime = curdate.getTime();
if(editing==1 && curtime-lastudpdate > 1000){
updatenote();
}
}
function updatenote(){
var headi = document.getElementById("inp"+editingnote).value;
var ent = $("#entry"+editingnote).html();
var entcontent = $("#entry"+editingnote).text();
var doss = document.getElementById("dossier"+editingnote).value;
var sousdoss = document.getElementById("sousdoss"+editingnote).value;
var tags = document.getElementById("tags"+editingnote).value;
$.post( "updatenote.php", {pass: app_pass, id: editingnote, dossier: doss, sousdossier: sousdoss, tags: tags, heading: headi, entry: ent, entrycontent: entcontent, now: (new Date().getTime()/1000)-new Date().getTimezoneOffset()*60})
.done(function(data){
if(data=='1'){
editing = 0;
$('#lastupdated'+editingnote).html('Last Saved Today');
}
else{
editing = 0;
$('#lastupdated'+editingnote).html(data);
}
});
$('#newnotes').hide().show(0);
}
最后调用更新 php 文件(我从中删除了将数据发送到数据库的部分):
<?php
[...]
$id = $_POST['id'];
$heading = $_POST['heading'];
$entry = $_POST['entry'];
$entrycontent = $_POST['entrycontent'];
$now = $_POST['now'];
$seconds = $now;
$dossier = $_POST['dossier'];
$sousdossier = $_POST['sousdossier'];
$tags = $_POST['tags'];
$filename = "entries/".$dossier."/".$id.".html";
[...]
$str = fread($handle, filesize($filename));
if ($entry != ''){
if (!fwrite($handle, $entry)){
die("Error while writing to html file");
}
}
fclose($handle);
?>
如果它有助于查看整个代码的样子,我可以提供 Github 存储库,但我不确定我是否可以在这里这样做。
@Daniel Farrell 是对的,问题出在我每秒发送一个新请求,当网络太慢时,这个请求太短了,前一个请求无法完成。这是有问题的代码部分:
$( document ).ready(function() {
setInterval(function(){ checkedit(); }, 1000);
});
它每 1 秒执行一次 checkedit() 函数并启动 updatenote.php 写入文件但是在慢速网络上,这个操作对于一些大文件需要超过一秒所以 setInterval 函数调用 updatenote.php 在最后一个完成之前再次。然后它创建一个新请求。