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

accordion组件加载两表关联用户数据重复渲染问题求助

问题原因

你遇到的重复渲染问题核心是渲染逻辑错误,和SQL语句本身无关:

  • 外层while循环每读取一条联表查询的扁平化结果(1个用户对应1条FTP记录为一行结果),就输出一次accordion按钮,当一个用户绑定多条FTP记录时,同一个用户的按钮会被输出多次。
  • 循环过程中持续把当前行追加到$rows数组,再遍历整个数组输出内容,会导致FTP明细随着循环推进不断累积重复。
  • 面板容器内部错误嵌套了第二层.panel标签,会导致原有JS逻辑找错折叠目标,交互失效。
  • 按钮文本硬编码写死为John Doe,没有动态读取查询返回的真实用户名。
  • 单条FTP记录被重复输出了两次,会导致同一条明细显示两遍。
修复方案

原有JS交互、CSS样式代码不需要修改,只需要调整PHP渲染逻辑:先把联表查询的结果按用户ID分组归集,再外层遍历用户输出折叠按钮,内层遍历对应用户的所有FTP明细即可。
修复后的PHP代码如下:

<?php
$stmt = $con->prepare("SELECT customers.customer_id, customers.customer_name, customers.customer_company, customers_details.ftp_host, customers_details.ftp_username, customers_details.ftp_password
FROM customers
LEFT JOIN customers_details ON customers.customer_id = customers_details.customer_id WHERE customers.customer_id > ?
ORDER BY customers.customer_company ASC");
$biggerThan = 0;
$stmt->bind_param("i", $biggerThan);
$stmt->execute();
$result = $stmt->get_result();
$num_rows = mysqli_num_rows($result);

$groupedCustomers = [];
if ($num_rows > 0) {
    while ($row = $result->fetch_assoc()) {
        $cid = $row['customer_id'];
        // 首次遇到该用户时初始化用户基础信息
        if (!isset($groupedCustomers[$cid])) {
            $groupedCustomers[$cid] = [
                'customer_name' => $row['customer_name'],
                'customer_company' => $row['customer_company'],
                'ftp_list' => []
            ];
        }
        // 归集FTP明细,跳过左连接无匹配的空记录
        if (!empty($row['ftp_host'])) {
            $groupedCustomers[$cid]['ftp_list'][] = [
                'ftp_host' => htmlentities($row['ftp_host']),
                'ftp_username' => htmlentities($row['ftp_username']),
                'ftp_password' => htmlentities($row['ftp_password'])
            ];
        }
    }
}

// 统一渲染页面
if (empty($groupedCustomers)) {
    echo '<div class="alert alert-danger" role="alert">No user details found</div>';
} else {
    foreach ($groupedCustomers as $customer) {
?>
<button class="accordion"><?= htmlentities($customer['customer_name']) ?></button>
<div class="panel">
    <?php foreach ($customer['ftp_list'] as $index => $ftp): ?>
    <p>FTP Host: <?= $ftp['ftp_host'] ?></p>
    <p>FTP Username: <?= $ftp['ftp_username'] ?></p>
    <p>FTP Password: <?= $ftp['ftp_password'] ?></p>
    <?php if ($index !== array_key_last($customer['ftp_list'])): ?>
    <hr>
    <?php endif; ?>
    <?php endforeach; ?>
</div>
<?php
    }
}
?>
修复说明
  • 新增数据分组逻辑:联表查询返回的是用户和FTP明细一对一的扁平化结果,先按用户ID归集后,每个用户只会输出一次折叠按钮,从根源解决重复显示问题。
  • 移除了面板内部嵌套的多余.panel标签,保证原有JS逻辑可以正确定位到按钮对应的折叠面板,交互正常生效。
  • 按钮文本动态读取用户名,所有输出到页面的动态内容都做了html转义,避免XSS风险。
  • 去掉了单条FTP记录重复输出的冗余代码,分隔线仅在两条FTP明细中间显示,不会在最后一条明细下方出现多余横线。
  • 兼容左连接场景:如果用户没有绑定任何FTP记录,不会输出空白无效内容。

内容的提问来源于stack exchange,提问作者5admin

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.02 07:51:24