测试开发【Mock平台】09开发:项目管理(五)搜索、删除和Table优化

news2025/1/18 0:42:33

【Mock平台】为系列测试开发教程,从0到1编码带你一步步使用Spring Boot 和 Antd React框架完成搭建一个测试工具平台,希望作为一个实战项目对各位的测试开发学习之路有帮助,大奇一个专注测试技术干货原创与分享的家伙。

Mock平台系统项目基本配置,我们已经完成了展示,增加、修改,这个模块的进度其实已经差不多80%了,在本分享中将收下尾,为数据表格配置分页,实现简单搜索功能,以及删除功能,还会掌握如何自定义格式化列数据。

1.优化Table展示

表格形式的数据,一般未来累计超过20条的非常建议为其增加分页功能,在antd中Table组件有自带这个配置,但在之前的逻辑实现中特意关掉了,内部其实嵌套的也是Pagination分页组件,下边将详细演示内嵌和独立使用两种形式。

1.1 Pagination组件

分页组件在数据量大且加载/渲染所有数据将花费很多时间时,可以利用分页器组件进行页码浏览,要使用它需要导入组件 import{ Pagination }from'antd';其中基础配置属性** **total总数量,会根每页条数 pageSize(默认是10条)计算多少页,另外还有一个重要方法 onChange指页码或 pageSize 改变时回调,function(page, pageSize)参数是改变后的页码及每页条数。

参考官方例子给项目列表Table下方增加此组件,为了先做个演示测试,数据固定给50条,并主动开启

  • showSizeChanger 展示 pageSize 切换器,组件默认 total 大于 50 时为 true
  • pageSizeOptions 数组 指定每页可以显示多少条
import{ Pagination }from'antd';

/* 分页相关 */
const pageChange = (page, pageSize) => {
  console.log(`分页变化值 Page:${page}, PageSize:${pageSize}`);
}

...省略...
</Table>
<br/>  
<Pagination
  total={100}
  onChange={pageChange}
  showSizeChanger={true}
  pageSizeOptions={[5,10,20,30,50]}
/>

当点击切换页,下拉选择改变每页显示的数量时候,可以直观的看到的两个参数数值的变化,如下图:
image.png

因此在实现项目表格分页上,只需要在onChange里请求之前文章后服务分页查询接口,并将统计的总数动态赋值,就能实现优化改造。这里参考代码有些注意的地方:

  • 不要忘记server.js 的接口配置;
export async function searchProducts(params) {
  return request('/api/mock/project/search', {
    method: 'GET',
    params
  });
}
  • 定义了些中间变量存储各类数据;
  • 换了fetchData方法函数替代原有请求列表,并且是参数化请求,避免React闭包问题;
  • 列表查询接口还有一个项目名称模糊查询字段,组合请求参数时不要忘记;
  // const {data:useProjectList, error, loading, run: reloadProjectList} = useRequest(getProductList);
  const [data, setData] = useState();
  const [loading, setLoading] = useState(false);
  const [current, setCurrent] = useState(1);
  const [pageSize, setPageSize] = useState(10);
  const [total, setTotal] = useState();
  const fetchData = (name, current, pageSize) => {
    setLoading(true);
    searchProducts({name:name, current:current, pageSize: pageSize})
      .then(reps => {
        setData(reps.data);
        setTotal(reps.total);
        setLoading(false);
      });
  };

  /* 分页相关 */
  const pageChange = (page, pageSize) => {
    setCurrent(page);
    setPageSize(pageSize);
    fetchData('', page, pageSize);
  }

  // 页面首次请求项目列表数据初始化
  useEffect(() => {
    fetchData('', current, pageSize);
  }, []);


  • 对原有数据来要做变方法和变量替换,核心部分如下,其他根据IDE提示解决或者参考源代码;
<Table
  loading={loading}
  rowKey="id"
  pagination={false}
  columns={projectColumns}
  dataSource={data}
/>
<br/>
<Pagination
  total={total}
  current={current}
  pageSize={pageSize}
  onChange={pageChange}
  showSizeChanger={true}
  pageSizeOptions={[5,10,20,30,50]}
/>

代码开发调试效果如演示GIF

这里其实有个问题,就是当切换每页数量时候,当前选中页面还是之前的,如果条数从小条切到大,就有当前页数超出新的页数量总数情况,解决办法如果pageSize有变更,初始化默认页为第一页。

const pageChange = (page, size) => {
    // 如果改变了size 将其page设置为第一页
    let tmpPage = 1;
    if(size !== pageSize){
      tmpPage = 1
    } else {
      tmpPage = page;
    }
    setCurrent(tmpPage);
    setPageSize(size);
    fetchData('', tmpPage, size);
 }

1.2 Table自带分页

对于Table组件是有内置的分页功能,其实也就是Pagination组件,并对其做了封装得以使用更简单

https://ant.design/components/table-cn/#components-table-demo-ajax

image.png

有了上边1.1基础,改造起来就简单多了,只需将Pagination部分内容以JSON赋值方式赋值给Table中的pagination即可。

<Table
  loading={loading}
  rowKey="id"
  pagination={
    {
      total:total,
      current:current,
      pageSize:pageSize,
      onChange: pageChange,
      showSizeChanger:true,
      pageSizeOptions:[5,10,20,30,50]
    }
  }
  columns={projectColumns}
  dataSource={data}
/>

可以看到包括样式在内,自动展示了分页,并且尝试测试切换也均正常,不过我的例子中单独的变量定义的有点多,你们可以尝试参考官方Table远程加载数据例子再优化一版。
image.png

1.3 列表数据格式化

在表格数据展示中其中我们可以看到类型一栏显示还是数据库里的字段,所以这里说明下如何实现格式展示,方法和操作相似,使用 render 自定义请求一个方法,此方法根据类型判断返回相应文字和组件。

const formatType = (txtType) =>{
    if (txtType === 'public') {
      return <Tag>公共项目</Tag>
    } else if (txtType === 'private') {
      return <Tag>私有项目</Tag>
    } else {
      return <Tag>未知类型</Tag>
    }
  }

  // 表单列
  const projectColumns = [
    ...
    {dataIndex:"type",title:"类型",
      render: (text, _) => (formatType(text)),
    },
    ...
  ]

代码中实现的是将英文关键词转换成对应的中文进行显示,并用Tag标签包裹。
image.png

之后其他想做数据格式化展示,或多列合并一条,再或根据不同值展示不同样式等等,都可以使用此方法,当然后边有一种 ProTable 高级表格的时候,它提供多种类型数据展示提供了内置格式化,后续用到再进行详细说明。

2.搜索功能

在优化Table显示需求中替换带分页查询的接口时,我们预留的一个searchName 参数,对于多数据的展示如果能有个主要信息的搜索功能才比较完美,这里利用 Grid栅格Form行内表单 组件实现。

https://ant.design/components/grid-cn/
https://ant.design/components/form-cn/#components-form-demo-layout

Grid 用于布局,基于行(row)和列(col)来定义信息区块的外部框架,笔者因为对CSS不熟,不能熟练的用于DIV做一些样式布局,所以就常用栅格来控制行和列来达到想要的区域块布局效果。
**Form **行内是表单布局一种,一行的显示样式,常用于搜索、快捷编辑等场景。
参考两个组件官方API说明,最终我们要实现如下的页面效果:
image.png

这里由于之前表单的操作已经实战过Form的用法,所以就直接给出了参考代码,其中style是简单样式,实现右边6个栅格区域按钮靠右对齐。

 <Row>
   <Col span={18}>
     <Form layout="inline"
           onFinish={...todo实现提交代码...}
     >
       <Form.Item name="searchName" label="项目名称">
         <Input></Input>
        </Form.Item>
        <Form.Item>
           <Button htmlType="submit">搜索</Button>
        </Form.Item>
     </Form>
   </Col>
   <Col span={6}>
     <Button
      onClick={addAction}
      type="primary"
      style={{
             marginBottom: 16,
             marginRight: 20,
             float: "right"
            }}
      >
        项目添加
      </Button>
    </Col>
</Row>

最后补充下表单提交的实现代码

// 搜索
const onSearch = (values) => {
  fetchData(values.searchName, current, pageSize)
};

// return 内表单修改部分
<Form layout="inline"
  onFinish={onSearch}
>

输入一个关键点击搜索测试一下OK,但参考代码到这里会有交互缺陷,如果给定的关键词搜索的结果也是多页,那么我在切换页面或者页数量的时候,由于之前代码name都写死的空值,所以又会变成全量查询,这个问题的优化留个思考题吧,看看是你会怎么做?
image.png
ps:项目源代码中有我的优化答案可以进行参考

3.项目删除功能

实现完了编辑功能,操作列里还有一个删除操作,一般为了防止删除这种危险动作是误操作,将会用到上一篇中的确认对话框知识点,不过这里将用到官方例子里的 showPromiseConfirm即确定按钮触发会有等待,明确得到返回成功后关闭对话框。

3.1 删除接口

此接口没在之前的 Mock平台-05开发:项目管理(一)后端接口 准备好,需要现实现,MVC全部的代码如下,不再赘述Springboot API实现知识点,不会或者忘记的翻下系列第五篇回看下。这里需要特别强调下,这里删除是个软删除,所以要对数据库表增加一个字段 is_del (0-默认,1-删除)来做标记,实际删除就是更新此字段为删除状态。

MockProjectMapper.java

/**
* 删除项目,软删除标记is_del=1
* @param id
* @return 影响数量 更新成功默认1
*/
@Update({"UPDATE mock_project SET mp_state=1 WHERE mp_id=#{id}"})
Boolean removeProject(Integer id);

MockProjectService.java

RespResult removeMockProject(Integer id);

MockProjectServiceImpl.java

@Override
public RespResult removeMockProject(Integer id) {

  Boolean markResult = mockProjectMapper.removeProject(id);
  if (markResult){
    return RespResult.success();
  }
  return RespResult.failure(RespCode.DATA_REMOVE_ERROR);
}

MockProjectController.java

@PostMapping(value = "/project/remove")
public RespResult removeProject(@Param("id") Integer id){
  return mockProjectService.removeMockProject(id);
}

3.2 删除交互

对于前度删除功能交互的实现,先按照流程先定义服务请求接口

export async function removeProduct(id) {
  return request('/api/mock/project/remove?id='+id, {
    method: 'POST'
  });
}

动态生成确认对话框需要导入Modal组件里的子项 confirm 主要的三个属性和两个方法

  • title 对话显示的标题
  • icon 引用icon图标组件
  • content 详细的内容,支持ReactNode
  • onOk 点击确定按钮触发
  • onCancel 点击取消按钮触发,不做逻辑处理默认为关闭对话框
const { confirm } = Modal;
import { removeProduct } from "@/pages/Project/service";
....省略...

// 删除操作
const deleteConfirmWithPromise = (record) => {
  confirm({
    title: '删除确认?',
    icon: <ExclamationCircleOutlined />,
    content: `确定要删除【${record?.name}】吗?`,
      async onOk() {
        const result = await removeProduct(record.id);
        if(result.success){
          message.success('删除项目成功!');
          // 成功后刷新
          fetchData(sName, current, pageSize);
        } else{
          message.error('删除项目失败!');
        }
      },
       onCancel() {},
    });
  };

表格操作栏删除按钮添加deleteConfirmWithPromise并把所在行数据传过去。

{dataIndex:"option",title:"操作",
  render: (text, record) => (
  <Space>
    <a onClick={()=>editAction(record)}>编辑</a>
+    <a onClick={()=>deleteConfirmWithPromise(record)}>删除</a>
  </Space>
),},

按例重启前后端服务,进行删除取消/确认/删除成功页面刷新的用例测试。

花了大篇幅在比较简单需求的项目管理上,是为务牢基础为后边核心逻辑更轻松,另外学习是一个过程,尤其是基础知识薄弱的,一定不要是看会,而是动手实战,进而有自己的想法和移花接木的本领,最终从务实角度来讲能在实际工作中业务上应用,哪怕是务虚为了KPI、“钱途“也要做点什么。

最后预告系列分享开发实战部分终于要进入核心部分的实现,比如分类Tree,接口管理,Mock拦截等实战内容,欢迎长期关注哦!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/967343.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【大数据实训】基于Hive的北京市天气系统分析报告(二)

博主介绍&#xff1a;✌全网粉丝6W,csdn特邀作者、博客专家、Java领域优质创作者,博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于大数据技术领域和毕业项目实战✌ &#x1f345;文末获取项目联系&#x1f345; 目录 1. 引言 1.1 项目背景 1 1.2 项目意义 1 2.…

蓝队追踪者工具TrackAttacker,以及免杀马生成工具

蓝队追踪者工具TrackAttacker&#xff0c;以及免杀马生成工具。 做过防守的都知道大HW时的攻击IP量&#xff0c;那么对于这些攻击IP若一个个去溯源则显得效率低下&#xff0c;如果有个工具可以对这些IP做批量初筛是不是更好&#xff1f; 0x2 TrackAttacker获取 https://githu…

[管理与领导-67]:IT基层管理者 - 辅助技能 - 4- 职业发展规划 - 评估你与公司的八字是否相合

目录 前言&#xff1a; 一、概述 二、八字相合的步骤 2.1 企业文化是否相合 2.2.1 企业文化对职业选择的意义 2.2.2 个人与企业三观不合的结果 2.2.3 什么样的企业文化的公司不能加入 2.2 公司的发展前景 2.3 公司所处行业发展 2.4 创始人的三观 2.5 创始人与上司的…

HDMI 输出实验

FPGA教程学习 第十四章 HDMI 输出实验 文章目录 FPGA教程学习前言实验原理实验过程程序设计时钟模块&#xff08;video_pll&#xff09;彩条产生模块&#xff08;color_bar)配置数据查找表模块&#xff08;lut_adv7511&#xff09;I2C Master 寄存器配置模块&#xff08;i2c_c…

692. 前K个高频单词

题目来源&#xff1a;力扣 题目描述&#xff1a; 给定一个单词列表 words 和一个整数 k &#xff0c;返回前 k 个出现次数最多的单词。 返回的答案应该按单词出现频率由高到低排序。如果不同的单词有相同出现频率&#xff0c; 按字典顺序 排序。 示例 1&#xff1a; 输入:…

css transition 指南

css transition 指南 在本文中&#xff0c;我们将深入了解 CSS transition&#xff0c;以及如何使用它们来创建丰富、精美的动画。 基本原理 我们创建动画时通常需要一些动画相关的 CSS。 下面是一个按钮在悬停时移动但没有动画的示例&#xff1a; <button class"…

【斗罗Ⅱ】最强武魂揭秘,98级玄老、95级言少哲神兽级武魂曝光

Hello,小伙伴们&#xff0c;我是小郑继续为大家深度解析【绝世唐门】 在斗罗大陆动画绝世唐门中&#xff0c;98级玄老已经登场&#xff0c;他是一个很随意的老人&#xff0c;乍眼一看&#xff0c;似乎是一个邋里邋遢、好吃懒做的人&#xff0c;但是实际上他却是史莱克学院重量级…

精心整理了优秀的GitHub开源项目,包含前端、后端、AI人工智能、游戏、黑客工具、网络工具、AI医疗等等,空闲的时候方便看看提高自己的视野

精心整理了优秀的GitHub开源项目&#xff0c;包含前端、后端、AI人工智能、游戏、黑客工具、网络工具、AI医疗等等&#xff0c;空闲的时候方便看看提高自己的视野。 刚开源就变成新星的 igl&#xff0c;不仅获得了 2k star&#xff0c;也能提高你开发游戏的效率&#xff0c;摆…

自建音乐服务器Navidrome之二

6 准备音乐资源 可选 Last.fm Lastfm是 Audioscrobbler 音乐引擎设计团队的旗舰产品&#xff0c;以英国为总部的网络电台和音乐社区。有遍布232个国家超过1500万的活跃听众。据说有6亿音乐资源。 docker-compose.yml 配置 Navidrome 可以从 Last.fm 和 Spotify 获取专辑信息和…

性能测试 —— Jmeter 命令行详细

我们在启动Jmeter时 会看见&#xff1a;Don’t use GUI mode for load testing !, only for Test creation and Test debugging.For load testing, use CLI Mode (was NON GUI) 这句话的意思就是说&#xff0c;不要使用gui模式进行负载测试&#xff0c;gui模式仅仅是创建脚本…

涂鸦智能携手亚马逊云科技 共建“联合安全实验室” 为IoT发展护航

2023年8月31日&#xff0c;全球化IoT开发者平台涂鸦智能&#xff08;NYSE: TUYA&#xff0c;HKEX: 2391&#xff09;在“2023亚马逊云科技re:Inforce中国站”大会宣布与全球领先的云计算公司亚马逊云科技共同成立“联合安全实验室”&#xff0c;旨在加强IoT行业的安全合规能力与…

管理类联考——逻辑——形式逻辑——汇总篇——知识点突破——论证逻辑——假设——否定代入

角度——原理 可以用“否定代入法”验证疑似选项 由于假设是使推理成立的一个必要条件&#xff0c;根据必要条件的性质若Р是S的必要条件&#xff0c;那么┐P → ┐S可知&#xff0c;如果一个推理在没有某一条件时&#xff0c;这个推理必然不成立&#xff0c;那么这个条件就是…

41.岛屿数量(第四期模拟笔试)(BFS练习题)

题目&#xff1a; 给定一个 m 行 n 列的二维地图&#xff0c;初始化每个单元格都是海洋&#xff0c;二维地图外也全是海洋。 操作 addLand 会将单元格&#xff08;col, row&#xff09;变为陆地。 定义一系列相连的被海洋包围的陆地为岛屿&#xff0c; 横向相邻或者纵向相连的…

%temp%

C:\Users\ADMINI~1\AppData\Local\Temp

springboot~静态资源配置

springboot~静态资源配置 springboot的静态资源默认路径给静态资源请求加前缀指定静态资源加载的包欢迎页 springboot的静态资源默认路径 请求效果见图 给静态资源请求加前缀 有时需要用拦截器对某些请求进行拦截后再处理相关的业务代码&#xff0c;此时我们就要对请求进行…

2023年智能算法之淘金优化器,MATLAB代码免费获取

今天为大家带来一期淘金优化算法(Gold rush optimizer.,GRO)。 GRO算法是受淘金热启发&#xff0c;模拟了淘金者在淘金热时期如何利用淘金的三个关键概念进行淘金&#xff1a;迁移、协作和淘金。 原理详解 ①金矿勘探阶段&#xff1a; 与大多数智能算法相似&#xff0c;就是随机…

MyBatis学习

一、Mybatis使用 1、新建mybatis配置文件 <?xml version"1.0" encoding"UTF-8" ?> <!DOCTYPE configurationPUBLIC "-//mybatis.org//DTD Config 3.0//EN""http://mybatis.org/dtd/mybatis-3-config.dtd"> <configu…

由于cpu cache line机制在共享原子数据操作上带来的硬件干扰对多线程机制的性能影响

由于cpu cache line机制在共享原子数据操作上带来的硬件干扰会对对多线程性能造成影响。例如不同的原子数据&#xff0c;位于同一个cpu cache line&#xff0c;这时候一个处理器读取这个cpu cache line这段数据的时候&#xff0c;就会控制这段数据的所有权&#xff0c;其他想要…

WorkManager的基本使用

目录 一、WorkManager概述1. WorkManager的作用&#xff1a;2. WorkManager的各个角色 二、依赖库的导入三、WorkManager几种基本使用1. 单一任务的执行2. 数据 互相传递3. 多个任务 顺序执行4. 重复执行后台任务5. 约束条件6. 证明 app被杀掉之后&#xff0c;还在后台执行 四、…

中小企业常用的 IT 项目管理软件有哪些?

越热门&#xff0c;越贵的IT项目管理软件越好用吗&#xff1f;对于预算有限的中小型企业来说&#xff0c;如何选择一款适合自己的项目管理工具着实是个头疼的问题。 首先适用于中小型企业使用的 IT 项目管理软件需要具备哪些特点呢&#xff1f; 1、简单易用&#xff1a;中小企…