You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

AJAX仅页面重载后返回数据,循环重复数据问题求助

Hey,我来帮你解决这两个头疼的问题:

问题1:无法自动获取新内容,必须刷新页面

你的AJAX代码只在页面首次加载时执行了一次,之后就不会再主动请求新数据了。要实现管理员无需刷新就能看到新提交的文章,你需要定时发起AJAX请求来轮询新内容。

问题2:重复渲染相同数据,且数据结构错误

这个问题是前后端配合出了问题:

后端的问题

你在foreach循环里每次都直接覆盖$output的同一组键(title/id/story),导致最终返回的JSON是单个文章对象(如果有多篇未激活文章,只会保留最后一篇),而不是文章列表数组。同时number也被重复赋值了多次,完全没必要。

前端的问题

  1. 你在$.each循环里错误地使用了response.id/response.title,而不是当前循环项的value.id/value.title;
  2. 因为后端返回的是单个对象,$.each会遍历这个对象的所有属性(title/id/story/number),每个属性都会生成一个相同的<li>,自然就出现了重复渲染的情况。

修复后的代码

后端file.php修改:

<?php
require $_SERVER['DOCUMENT_ROOT'].'/config/init.php';
require CLASS_PATH.'article.php';
$article = new Article();
$list = $article->getInactiveArticle();
$number = $article->countInactiveArticle();

// 重新构建输出结构:用articles数组存所有未激活文章,单独存数量
$output = [
    'articles' => [],
    'number' => $number[0]->inactive_articles
];

// 循环把每篇文章加入数组
foreach ($list as $lists) {
    $output['articles'][] = [
        'title' => $lists->title,
        'id' => $lists->id,
        'story' => $lists->story
    ];
}

echo json_encode($output);
?>

前端AJAX修改:

<script>
// 把AJAX逻辑封装成函数,方便重复调用
function fetchInactiveArticles() {
    $.ajax({
        type: "POST",
        url: 'inc/file.php',
        dataType: 'json',
        success: function(response) {
            if (response && response.articles) {
                let html = '';
                // 正确遍历articles数组,用value获取当前文章的属性
                $.each(response.articles, function(key, value){
                    html += `<li><a href="editArticle?id=${value.id}&amp;act="><span>${value.title}</span><span>${value.story}</span></a></li>`;
                });
                // 这里用empty()清空旧内容再添加,避免重复累加
                $('#menu1').empty().prepend(html);
                $('#number').text(response.number);
            }
        },
        // 加上错误处理,方便调试
        error: function(xhr, status, error) {
            console.log('获取未激活文章出错:', error);
        }
    });
}

// 页面加载时先执行一次
fetchInactiveArticles();
// 每隔30秒轮询一次(时间可以根据你的需求调整,比如10秒)
setInterval(fetchInactiveArticles, 30000);
</script>

优化建议(可选)

上面的代码每次都会清空旧内容重新渲染,可能会有轻微闪烁。如果想更高效,你可以:

  1. 前端记录最后一次获取的文章ID(比如let lastArticleId = 0;);
  2. AJAX请求时把这个ID传给后端;
  3. 后端只返回ID大于lastArticleId的新文章;
  4. 前端只把这些新文章prepend到列表里,同时更新lastArticleId。

这样既避免了重复渲染旧内容,也减少了不必要的数据传输。

内容的提问来源于stack exchange,提问作者Alisha Lamichhane

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.11 09:27:38