如何在Spring项目中实现表单或字段集的局部刷新

如何在spring项目中实现表单或字段集的局部刷新

本文档旨在解决Spring项目中,删除数据库条目后,前端页面需要刷新才能显示最新数据的问题。通过修改删除操作后的处理逻辑,利用JavaScript操作DOM,实现对特定表单或字段集的局部刷新,避免整个页面重新加载,提升用户体验。

在Spring项目中,如果删除数据库中的数据后,前端页面需要刷新才能看到更新,这通常是因为删除操作后没有及时更新前端的显示。以下是如何解决这个问题,实现局部刷新的详细步骤和代码示例:

1. 修改 removeTodo 函数

目前的代码在 removeTodo 函数中,仅仅发送了 DELETE 请求,但没有处理请求成功后的前端更新。需要在成功删除后,更新前端的显示。

function removeTodo() {    const d = document.getElementById('idToDel').value;    fetch(`${API_URL_ALL}/${d}`, { method: 'DELETE' })        .then(processOkResponse)        .then(deleteProduct) // 添加这一行        .catch(console.info);}

这里添加了 .then(deleteProduct),表示在 processOkResponse 成功处理响应后,调用 deleteProduct 函数来更新前端。

2. 修改 createNewProduct 函数

为了方便删除特定条目,需要在创建条目时,为每个 label 元素添加一个唯一的 ID,方便后续通过 JavaScript 找到并删除它。

function createNewProduct(product) {    const label = document.createElement('label');    label.setAttribute('id', `pid-${product.id}`); // 添加这一行    const l1 = document.createElement('label');    const l2 = document.createElement('label');    const l3 = document.createElement('label');    const l4 = document.createElement('label');    label.classList.add('label');    l1.appendChild(document.createTextNode(`  ID:${product.id}. `));    l2.appendChild(document.createTextNode(` ${product.name} `));    l3.appendChild(document.createTextNode(` ${product.amount} `));    l4.appendChild(document.createTextNode(` ${product.type} `));    label.appendChild(l1).appendChild(l2).appendChild(l3).appendChild(l4)    document.getElementById('allProducts').appendChild(label);    label.style.display= 'table';    label.style.paddingLeft='40%';    label.style.wordSpacing='30%';}

在 createNewProduct 函数中,添加了 label.setAttribute(‘id’, pid-${product.id}`);,为每个label元素设置了一个唯一的 ID,格式为pid-条目ID`。

3. 创建 deleteProduct 函数

现在需要创建一个 deleteProduct 函数,用于处理删除操作成功后的前端更新。这个函数接收服务器返回的响应,从中提取被删除条目的 ID,然后找到对应的 HTML 元素并将其删除。

function deleteProduct(deleteApiResponse) {    // 确保服务器返回被删除条目的 ID    const { id } = deleteApiResponse;    const idToDel = `pid-${id}`;    const elementToRemove = document.getElementById(idToDel);    if (elementToRemove) {        // 从DOM中移除该元素        elementToRemove.remove();    } else {        console.warn(`Element with id ${idToDel} not found.`);    }}

在这个函数中,首先从 deleteApiResponse 中提取被删除条目的 id。然后,使用 document.getElementById(idToDel) 找到对应的 HTML 元素。如果找到了该元素,就使用 elementToRemove.remove() 将其从 DOM 中移除。如果没有找到该元素,则在控制台输出警告信息。

注意: 服务器端需要确保在删除操作成功后,返回被删除条目的 ID。

4. 修改服务器端代码 (重要)

确保你的 Spring 后端在成功删除数据后,返回被删除数据的 ID。例如,你的Controller应该返回类似如下的JSON:

{  "id": 123 // 被删除的条目ID}

如果没有返回ID,deleteProduct函数将无法工作。修改 processOkResponse 函数以适应可能的非JSON响应。

function processOkResponse(response = {}) {    if (response.ok) {        // 尝试解析 JSON,如果不是 JSON,则直接返回响应文本        return response.text().then(text => {            try {                return JSON.parse(text);            } catch (e) {                return text;            }        });    }    throw new Error(`Status not 200 (${response.status})`);}

5. 完整代码示例

下面是修改后的完整 JavaScript 代码:

    const API_URL = 'http://localhost:8080';    const API_URL_ADD = `${API_URL}/api`;    const API_URL_ALL = `${API_URL_ADD}/list`;    const pName = document.getElementById('name');    const pUom = document.getElementById('uom');    const pAmount = document.getElementById('amount');    AddFunction();    fetch(API_URL_ALL)        .then(processOkResponse)        .then(list => list.forEach(createNewProduct))    document.getElementById('addProduct').addEventListener('click', (event) => {        event.preventDefault();        fetch(API_URL_ALL, {            method: 'POST',            headers: {                'Accept': 'application/json',                'Content-Type': 'application/json'            },            body: JSON.stringify({ name: pName.value, type : pUom.value, amount: pAmount.value })        })            .then(processOkResponse)            .then(createNewProduct)            .then(() => pName.value = '')            .then(() => pAmount.value = '')            .then(() => pUom.value = '')            .catch(console.warn);    });    function createNewProduct(product) {        const label = document.createElement('label');        label.setAttribute('id', `pid-${product.id}`); // 添加这一行        const l1 = document.createElement('label');        const l2 = document.createElement('label');        const l3 = document.createElement('label');        const l4 = document.createElement('label');        label.classList.add('label');        l1.appendChild(document.createTextNode(`  ID:${product.id}. `));        l2.appendChild(document.createTextNode(` ${product.name} `));        l3.appendChild(document.createTextNode(` ${product.amount} `));        l4.appendChild(document.createTextNode(` ${product.type} `));        label.appendChild(l1).appendChild(l2).appendChild(l3).appendChild(l4)        document.getElementById('allProducts').appendChild(label);        label.style.display= 'table';        label.style.paddingLeft='40%';        label.style.wordSpacing='30%';    }    document.getElementById('delProduct').addEventListener('click', (event) => {        event.preventDefault();        removeTodo();    });    function removeTodo() {        const d = document.getElementById('idToDel').value;        fetch(`${API_URL_ALL}/${d}`, { method: 'DELETE' })            .then(processOkResponse)            .then(deleteProduct) // 添加这一行            .catch(console.info);    }    function deleteProduct(deleteApiResponse) {        const { id } = deleteApiResponse;        const idToDel = `pid-${id}`;        const elementToRemove = document.getElementById(idToDel);        if (elementToRemove) {            elementToRemove.remove();        } else {            console.warn(`Element with id ${idToDel} not found.`);        }    }    function AddFunction(){        const welcomeForm = document.getElementById('welcomeForm');        document.getElementById('welcomeFormBtn').addEventListener('click', (event) => {            event.preventDefault();            const formObj = {                name: welcomeForm.elements.name.value,            };            fetch(`${API_URL_ADD}?${new URLSearchParams(formObj)}`)                .then(response => response.text())                .then((text) => {                    document.getElementById('welcome').innerHTML = `                

${text}

`; welcomeForm.remove(); document.getElementById('AddForm').style.display = 'block'; }); }); } document.getElementById('print-btn').addEventListener('click', (event) => { event.preventDefault(); const f = document.getElementById("allProducts").innerHTML; const a = window.open(); a.document.write(document.getElementById('welcome').innerHTML); a.document.write(f); a.print(); }) function processOkResponse(response = {}) { if (response.ok) { return response.json(); } throw new Error(`Status not 200 (${response.status})`); }

6. 总结

通过以上步骤,可以在 Spring 项目中实现删除操作后的局部刷新,避免整个页面重新加载,提升用户体验。 关键在于:

在创建条目时,为每个条目添加唯一的 ID。在删除操作后,通过 JavaScript 找到对应的 HTML 元素并将其删除。确保服务器端返回被删除条目的 ID。

这样,就可以实现高效、流畅的前端更新,提升用户体验。

以上就是如何在Spring项目中实现表单或字段集的局部刷新的详细内容,更多请关注创想鸟其它相关文章!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 chuangxiangniao@163.com 举报,一经查实,本站将立刻删除。
发布者:程序猿,转转请注明出处:https://www.chuangxiangniao.com/p/1582248.html

赞 (0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
WooCommerce 自定义 WP_Query 获取订单详情报错解决方案
上一篇 2025年12月22日 22:59:24
精准控制:如何独立样式化HTML元素的直接文本内容而不影响子元素
下一篇 2025年12月22日 22:59:41

相关推荐

  • 淘宝奥莱折扣商城是正品?怎么取消订单?订单取消全流程解析:从6重资质审核到15天价保,手把手教你破解15%纠纷率与48小时退款陷阱!

    淘宝奥莱折扣商城是正品?怎么取消订单?订单取消全流程解析:从6重资质审核到15天价保,手把手教你破解15%纠纷率与48小时退款陷阱!淘宝奥莱折扣商城是正品?怎么取消订单?订单取消全流程解析:从6重资质审核到15天价保,手把手教你破解15%纠纷率与48小时退款陷阱!淘宝奥莱折扣商城是正品?怎么取消订单?订单取消全流程解析:从6重资质审核到15天价保,手把手教你破解15%纠纷率与48小时退款陷阱!淘宝奥莱折扣商城是正品?怎么取消订单?订单取消全流程解析:从6重资质审核到15天价保,手把手教你破解15%纠纷率与48小时退款陷阱!

    在淘宝搜索“品牌折扣”时,奥莱折扣商城常以极具吸引力的低价赢得消费者关注。然而,“商品是不是正品?”“怎么取消订单?”等问题也让不少买家心存顾虑。本文结合平台规则与实际操作经验,带您全面了解淘宝奥莱折扣商城的真实情况。 一、淘宝奥莱折扣商城卖的是正品吗? 1. 平台准入审核机制 根据淘宝最新规定:未…

    2026年9月26日 • 用户投稿
    000
  • sublime怎么配置graphql语法和自动补全_sublime GraphQL语法与自动补全配置

    sublime怎么配置graphql语法和自动补全_sublime GraphQL语法与自动补全配置sublime怎么配置graphql语法和自动补全_sublime GraphQL语法与自动补全配置sublime怎么配置graphql语法和自动补全_sublime GraphQL语法与自动补全配置sublime怎么配置graphql语法和自动补全_sublime GraphQL语法与自动补全配置

    首先安装GraphQL语法高亮插件,通过Package Control搜索并安装GraphQL或GraphQL Syntax;然后安装LSP插件,配置LSP使用GraphQL Language Service,并在项目根目录创建包含schemaPath和endpoint的.graphqlconfig…

    2026年9月26日 • 用户投稿
    000
  • Java泛型陷阱:Pair中List类型丢失问题及解决方案

    Java泛型陷阱:Pair中List类型丢失问题及解决方案Java泛型陷阱:Pair中List类型丢失问题及解决方案Java泛型陷阱:Pair中List类型丢失问题及解决方案Java泛型陷阱:Pair中List类型丢失问题及解决方案

    本文探讨了在Java中使用包含List的Pair时,若迭代循环中未正确使用泛型,可能导致List类型信息丢失的问题。核心在于,使用裸类型(Raw Type)的Pair会导致其内部泛型参数被擦除为Object,从而无法访问List特有的方法。解决方案是在循环声明中明确指定泛型类型,以确保编译时类型安全…

    2026年9月26日 • 用户投稿
    200
  • win8防火墙怎么关闭_Win8防火墙设置教程

    win8防火墙怎么关闭_Win8防火墙设置教程win8防火墙怎么关闭_Win8防火墙设置教程win8防火墙怎么关闭_Win8防火墙设置教程win8防火墙怎么关闭_Win8防火墙设置教程

    1、可通过控制面板、服务管理器或运行命令关闭Win8防火墙;2、控制面板方法最直观,服务管理器可彻底禁用,运行命令firewall.cpl可快速进入设置。 如果您在使用Windows 8系统时需要访问特定程序或设备,但网络连接受到限制,可能是防火墙阻止了相关通信。以下是关闭Win8防火墙的详细操作步…

    2026年9月26日 • 用户投稿
    200
  • 使用泛型解决Pair中List无法访问的问题

    使用泛型解决Pair中List无法访问的问题使用泛型解决Pair中List无法访问的问题使用泛型解决Pair中List无法访问的问题使用泛型解决Pair中List无法访问的问题

    本文介绍了在使用 javatuples 库中的 Pair 类时,当 Pair 的第二个元素是 List 类型,并且在循环中访问该 List 时,可能遇到的无法访问 List 的 size() 方法或元素的问题。通过在循环中使用泛型来明确 Pair 中 List 的类型,可以有效解决此问题,确保 Li…

    2026年9月26日 • 用户投稿
    000
  • Windows CMD 换肤

    Windows CMD 换肤Windows CMD 换肤Windows CMD 换肤Windows CMD 换肤

    为了在 windows 平台上进行 c 开发更具乐趣,我经常使用 cmd 终端,尤其是在集成了 ubuntu 子系统(wsl)之后。为了更愉快地呼出 wsl,我习惯在 cmd 下操作,但默认皮肤不够吸引人。因此,我搜寻了一些换肤方法,并在此分享我的发现。 首先,你需要准备好换肤工具:ColorToo…

    2026年9月26日 • 用户投稿
    000
  • Java中Pair嵌套List时泛型丢失问题解析与最佳实践

    Java中Pair嵌套List时泛型丢失问题解析与最佳实践Java中Pair嵌套List时泛型丢失问题解析与最佳实践Java中Pair嵌套List时泛型丢失问题解析与最佳实践Java中Pair嵌套List时泛型丢失问题解析与最佳实践

    本文深入探讨了在Java中使用org.javatuples.Pair嵌套List时,因不当使用泛型(即使用原始类型)导致List功能异常的问题。通过分析原始类型Pair在增强型for循环中的行为,揭示了类型擦除如何影响内部List的访问。文章提供了正确的泛型使用方式,确保在迭代过程中List的类型信…

    2026年9月26日 • 用户投稿
    100
  • laravel如何创建自定义的Artisan命令_Laravel自定义Artisan命令教程

    答案:在 Laravel 中创建自定义 Artisan 命令可自动化常用任务,使用 make:command 生成命令类,配置 signature 和 description 属性定义调用方式与描述,于 handle() 方法编写逻辑,通过 argument() 和 option() 获取参数与选项…

    2026年9月26日
    000
  • sublime怎么给vue文件设置高亮_sublime Vue文件语法高亮设置

    sublime怎么给vue文件设置高亮_sublime Vue文件语法高亮设置sublime怎么给vue文件设置高亮_sublime Vue文件语法高亮设置sublime怎么给vue文件设置高亮_sublime Vue文件语法高亮设置sublime怎么给vue文件设置高亮_sublime Vue文件语法高亮设置

    Sublime Text 默认不支持 Vue 文件的语法高亮,但可以通过安装插件来实现。Vue 文件是混合语法(HTML、JavaScript、CSS),需要专门的语法定义才能正确高亮。以下是设置步骤: 1. 安装 Package Control(如未安装) 如果还没安装 Package Contr…

    2026年9月26日 • 用户投稿
    000
  • Java中InterruptedException与线程中断配合使用

    InterruptedException是Java中用于线程中断的检查异常,当线程在阻塞操作中被中断时抛出;调用interrupt()方法仅设置中断状态,线程需自行响应;常见可中断方法包括sleep、wait、join等;捕获该异常后应恢复中断状态或进行清理并退出;错误地忽略异常会导致中断信号丢失,…

    2026年9月26日
    000
  • 百家号动态怎么发布_百家号动态发布的方法与注意事项

    百家号动态怎么发布_百家号动态发布的方法与注意事项百家号动态怎么发布_百家号动态发布的方法与注意事项百家号动态怎么发布_百家号动态发布的方法与注意事项百家号动态怎么发布_百家号动态发布的方法与注意事项

    要成功发布百家号动态,需先完成账号注册与实名认证,确保具备发布权限。通过手机APP或网页后台进入发布页面,撰写200字内简洁内容,可添加9张图或短视频及话题标签以提升推荐。发布前须遵守审核规则:禁发政治敏感、虚假宣传、侵权盗用、低质标题党及夸大医疗效果等内容,避免审核失败或账号限流,保障内容合规与曝…

    2026年9月26日 • 用户投稿
    100
  • 别再浪费纸了!一文掌握“双面打印”的正确姿势

    别再浪费纸了!一文掌握“双面打印”的正确姿势别再浪费纸了!一文掌握“双面打印”的正确姿势别再浪费纸了!一文掌握“双面打印”的正确姿势别再浪费纸了!一文掌握“双面打印”的正确姿势

    你是否也曾为家中或办公室里堆积如山的废纸感到惋惜? 你是否在打印一份几十页的报告时,默默看着打印机“哗哗”吐出厚厚一叠纸张,心里泛起一丝浪费的不安? 其实,你距离成为一位高效、节约又环保的打印高手,只差一个“双面打印”的操作。 别再用“不会设置”、“太麻烦”当作借口,让纸张白白流失。 今天,我们就来…

    2026年9月26日 • 用户投稿
    1500
  • 远程桌面失败:你的凭据不工作

    远程桌面失败:你的凭据不工作远程桌面失败:你的凭据不工作远程桌面失败:你的凭据不工作远程桌面失败:你的凭据不工作

    解决远程桌面连接失败的问题,可以尝试以下几种方法: 方法一: 首先,按Win+R快捷键,输入“secpol.msc”或“gpedit.msc”打开安全策略或组策略编辑器: 然后,找到并更改默认设置,将“仅来宾—本地用户以来宾身份验证”调整为“经典:本地用户以自己的身份验证”。 方法二: 只需调整远程…

    2026年9月26日 • 用户投稿
    100
  • 云原生Java监控全套方案:从Micrometer到Grafana可视化看板

    云原生Java监控全套方案:从Micrometer到Grafana可视化看板云原生Java监控全套方案:从Micrometer到Grafana可视化看板云原生Java监控全套方案:从Micrometer到Grafana可视化看板云原生Java监控全套方案:从Micrometer到Grafana可视化看板

    云原生Java监控方案以Micrometer收集指标,Prometheus存储查询,Grafana实现可视化。Micrometer提供供应商中立的API,与Spring Boot Actuator集成,自动暴露JVM、HTTP等指标;通过micrometer-registry-prometheus依…

    2026年9月26日 • 用户投稿
    000
  • WPS格式文件中的宏如何安全处理_WPS宏安全管理与处理步骤

    WPS格式文件中的宏如何安全处理_WPS宏安全管理与处理步骤WPS格式文件中的宏如何安全处理_WPS宏安全管理与处理步骤WPS格式文件中的宏如何安全处理_WPS宏安全管理与处理步骤WPS格式文件中的宏如何安全处理_WPS宏安全管理与处理步骤

    首先禁用所有宏并启用通知,再检查宏来源与数字签名,对可疑文件使用沙箱环境测试,必要时清除文档宏代码,最后通过受信任位置管理合法宏运行。 如果您在打开WPS格式文件时遇到宏相关提示或安全警告,可能是文档中包含可执行的宏代码。不正确的处理可能导致恶意代码运行,威胁系统安全。以下是针对WPS文件中宏的安全…

    2026年9月26日 • 用户投稿
    100
  • sublime怎么格式化代码_Sublime Text代码格式化设置与快捷键

    sublime怎么格式化代码_Sublime Text代码格式化设置与快捷键sublime怎么格式化代码_Sublime Text代码格式化设置与快捷键sublime怎么格式化代码_Sublime Text代码格式化设置与快捷键sublime怎么格式化代码_Sublime Text代码格式化设置与快捷键

    Sublime Text通过安装HTML-CSS-JS Prettify等插件可实现代码格式化,需先安装Package Control,再通过命令面板搜索并安装插件,随后在Key Bindings中添加快捷键配置,如Ctrl+Alt+F用于格式化JS/HTML/CSS文件,保存后即可使用;注意确保文…

    2026年9月26日 • 用户投稿
    100
  • Node.js spawn 命令参数解析与 shell: true 的应用

    Node.js spawn 命令参数解析与 shell: true 的应用Node.js spawn 命令参数解析与 shell: true 的应用Node.js spawn 命令参数解析与 shell: true 的应用Node.js spawn 命令参数解析与 shell: true 的应用

    本文探讨Node.js child_process.spawn 函数在处理复杂命令行参数时遇到的常见问题,特别是当参数包含路径或需要特殊解释时,可能导致目标程序(如Java)无法正确识别。通过引入 shell: true 选项,并结合正确的参数格式化,可以有效解决此类问题,同时强调了使用此选项时的安…

    2026年9月26日 • 用户投稿
    000
  • Windows Server 2012 Hyper-V群集图文教程

    Windows Server 2012 Hyper-V群集图文教程Windows Server 2012 Hyper-V群集图文教程Windows Server 2012 Hyper-V群集图文教程Windows Server 2012 Hyper-V群集图文教程

    接下来我们将继续测试windows server 2012 hyper-v群集功能,以实现虚拟机的高可用性。 实验环境: 四台服务器均运行Windows Server 2012 DataCenter操作系统。 SRV2012服务器上安装了iSCSI目标服务器角色,并配置了两个虚拟磁盘,供两台群集服务…

    2026年9月26日 • 用户投稿
    100
  • 百度极速版如何查看历史记录_百度极速版浏览历史的查找方法

    百度极速版如何查看历史记录_百度极速版浏览历史的查找方法百度极速版如何查看历史记录_百度极速版浏览历史的查找方法百度极速版如何查看历史记录_百度极速版浏览历史的查找方法百度极速版如何查看历史记录_百度极速版浏览历史的查找方法

    打开百度极速版APP,点击底部“我的”进入个人中心;2. 点击“历史”查看阅读浏览记录;3. 切换至“搜索浏览”查看搜索记录;4. 若无记录需检查设置中历史记录功能是否开启。 在百度极速版里查看历史记录很简单,主要通过“我的”页面进入。下面介绍具体查找方法。 如何进入历史记录页面 打开手机上的百度极…

    2026年9月26日 • 用户投稿
    200
  • 服务发现组件 Eureka 和 Nacos 有什么区别?

    服务发现组件 Eureka 和 Nacos 有什么区别?服务发现组件 Eureka 和 Nacos 有什么区别?服务发现组件 Eureka 和 Nacos 有什么区别?服务发现组件 Eureka 和 Nacos 有什么区别?

    Eureka 侧重服务注册与发现,适合简单场景;Nacos 功能更全,支持配置管理、动态更新与高扩展性,适用于复杂微服务架构。选择需根据技术栈、项目规模及未来扩展需求权衡,Nacos 在大型项目中更具优势。 Eureka 和 Nacos 都是服务发现组件,核心作用都是让服务能够被其他服务找到并调用。…

    2026年9月26日 • 用户投稿
    000

发表回复

登录后才能评论
关注微信