深度分页问题优化方案

问题原因

Mysql使用select * from table limit offset, rows分页在深度分页的情况下, 性能急剧下降。

例如:select * 的情况下直接⽤limit 600000,10 扫描的是约60万条数据,并且是需要回表 60W次,也就是说⼤部分性能都耗在随机访问上,到头来只⽤到10条数据(总共取600010条数据只留10条记录)

优化方案

前端方案:业务层面限制跨度比较大的跳页

提供2种风格分页器供用户选择

  1. 标准分页器,展示最后一页和跳转指定页输入框
    image.png
  2. 简单分页器
    image.png

参考
百度方案: 不展示最后一页和直接跳转指定分页的输入框
image.png
Google方案:只展示查看下一页的按钮
image.png

界面设计器选表格/画廊的属性面板提供分页器风格的属性下拉选择

image.png

xml示例
<!-- 表格使用的标准分页器 --> <view type="TABLE" paginationStyle="SIMPLE"> <!-- fields --> </view> <!-- 画廊使用默认的标准分页器 --> <view type="GALLERY" paginationStyle="STANDARD"> <!-- fields --> </view>

后端方案

  1. 使用索引:确保数据库表中的相关字段上创建了适当的索引。索引可以加快查询速度,特别是在处理大数据量时。

  2. 分批查询:将大数据分成多个较小的批次进行查询,而不是一次性查询全部数据。可以通过限制每次查询的数据量和使用合适的偏移量来实现分批查询,例如使用LIMIT和OFFSET子句。

  3. 基于游标的分页:使用基于游标的分页技术,而不是传统的偏移分页。游标分页是通过记录上一次查询的游标位置,在下一次查询时从该位置开始获取新的数据,避免了大偏移量的影响。这可以通过数据库自身的功能(例如MySQL的CURSOR)或使用第三方库来实现。

  4. 缓存数据:如果数据变化较少,可以考虑将查询结果缓存到内存中,以避免频繁地查询数据库。这样可以提高页面相应速度,并减轻数据库负担。缓存的数据应该根据业务需要及时更新。

  5. 数据预处理:如果查询结果经常需要进行复杂的计算或处理,可以考虑提前对数据进行预处理并缓存结果,以减少每次查询的计算负担。

  6. 数据库优化:针对具体数据库系统,可以根据实际情况进行数据库调优。例如,合理设置数据库连接池大小、调整数据库参数等。

  7. 分布式存储和计算:对于非关系型数据库或分布式存储系统,可以考虑使用分布式存储和计算方案,将数据分散存储在多个节点上,并通过计算节点并行处理查询请求,以提高性能和可伸缩性。

参考链接

MySQL深分页场景下的性能优化

Oinone社区 作者:原创文章,如若转载,请注明出处:https://doc.oinone.top/other/75.html

访问Oinone官网:https://www.oinone.top获取数式Oinone低代码应用平台体验

(0)
的头像
上一篇 2023年6月20日 pm4:07
下一篇 2023年11月2日 pm1:58

相关推荐

  • 正式版发布:Oinone 6.2.0 版本 Oinone 正式开源,邀您体验

    版本号: 6.2.0 版本发布日期:2025.06.09更新要点:Oinone 正式开源 6.2.0 版本 GitHub: 后端: https://github.com/oinone/oinone-pamirs 前端: https://github.com/oinone/oinone-kunlun Gitee: 后端: https://gitee.com/oinone/oinone-pamirs 前端: https://gitee.com/oinone/oinone-kunlun 20250929 升级内容 镜像版本升级: 6.2.16 –> 6.2.17 后端版本升级: 6.2.16 –> 6.2.17 前端版本升级 修复视图加载时未正确设置优先级的问题 修复数据库集成接口无法正确转换为单个对象类型的问题 修复树/级联相关组件在某些情况下无法正常查询的问题 修复eip日志在某些情况下无法正常记录的问题 修复sql_record在指定 id 列名时导致更新失败的问题 20250911 升级内容 镜像版本升级: 6.2.15 –> 6.2.16 后端版本升级: 6.2.15 –> 6.2.16 前端版本升级 无代码模块加载新增自动解析依赖模块的功能 修复环境检查在使用系统变量时未正确解析导致业务工程无法正常启动的问题 修复环境历史记录未正确存储的问题 修复oracle数据库在使用虚拟字段时出现无法空指针的问题 修复使用oracle-12c版本时schedule无法正常插入的问题 修复文件集使用local类型的oss无法正常使用的问题 根据字段导出功能在使用关联关系字段时支持使用界面设计器配置的选项标题进行自动填充 修复数据可视化使用连接器作为数据源时无法正常导出的问题 修复模型设计器专家模式无法正常导入的问题 20250908 升级内容 镜像版本升级: 6.2.14 –> 6.2.15 后端版本升级: 6.2.14 –> 6.2.15 前端版本升级 EIP-JDBC 支持按数据库类型配置连接池参数 修复dubbo配置不生效的问题 修复数据可视化属性面板无法全部折叠或展开的问题 修复集成设计器直接创建开放接口无法正确传参的问题 修复tomcat部署时出现 csrfRefererFilter 不支持异步的问题 修复默认 ScriptEngine 未正确生效的问题 修复 boolean 序列化在使用 NDS 驱动时出现枚举空值的问题 修复数据可视化自定义组件在某些情况下无法正确查询数据的问题 修复数据可视化文件集识别字段类型错误的问题 20250901 升级内容 镜像版本升级: 6.2.12 –> 6.2.14 后端版本升级: 6.2.12 –> 6.2.14 前端版本升级 修复树视图/左树右表在指定列名时查询异常的问题 修复多对多关联关系使用静态常量时无法正常保存的问题 修复集成设计器数据库修改连接数据库时未正确刷新的问题 新增是否使用请求线程池开关,可通过 pamirs.request.thread.deferred=false 设置为禁用,用于跳过 tomcat 部署时用户未登录的问题 修复一对多保存失败的问题 修复单选树选择和级联选择字段组件在指定列名时查询异常的问题 20250822 升级内容 镜像版本升级: 6.2.11 –> 6.2.12 后端版本升级: 6.2.11 –> 6.2.12 修复集成设计器新建或复制API时未正确记录日志的问题 修复发布为开放接口时出入参转换异常的问题 修复开放接口调用集成接口时日志保存异常的问题 20250818 升级内容 镜像版本升级: 6.2.10 –> 6.2.11 后端版本升级: 6.2.10 –> 6.2.11 前端版本升级 集成应用-集成接口新增测试功能 集成设计器集成接口详情页面新增测试功能 集成设计器body参数支持保留空值功能 集成设计器的集成接口发布为开放接口后,删除时进行二次确认提示 集成设计器数据库连接支持断开连接和重新连接功能(支持分布式启停) 集成设计器WebService API支持xml解析功能 修复元数据继承计算未正确处理由界面设计器创建的提交动作的问题 修复界面设计器复制视图到子模型时无法复制提交动作的问题 修复界面设计器复制时切换模型时验证不通过的问题 修复从上游生成的菜单无法正确导出的问题 修复集成设计器导出时出现getDriver序列化异常的问题 修复数据可视化快捷日期选择错误的问题 开放dataflow-api和eip-designer-api包 <pamirs.dataflow.designer.version>6.2.1</pamirs.dataflow.designer.version> <pamirs.eip.designer.version>6.2.7</pamirs.eip.designer.version> <dependencyManagement> <dependency> <groupId>pro.shushi.pamirs.dataflow</groupId> <artifactId>pamirs-dataflow-designer-api</artifactId> <version>${pamirs.dataflow.designer.version}</version> </dependency> <dependency> <groupId>pro.shushi.pamirs.designer</groupId> <artifactId>pamirs-eip-designer-api</artifactId> <version>${pamirs.eip.designer.version}</version> </dependency> </dependencyManagement> 20250807 升级内容 镜像版本升级: 6.2.9 –> 6.2.10 后端版本升级: 6.2.9 –> 6.2.10 前端版本升级 添加复合图表类型,调整坐标轴、下钻、跳转样式 添加计算字段 添加允许用户自定义查询数量 界面设计器图表支持高度配置 集成设计器execl导入数据时允许修改数据类型 集成设计器-连接器-数据库-新增/编辑表单的密码使用密文 20250801 升级内容 镜像版本升级: 6.2.8 –> 6.2.9 后端版本升级:…

    2025年6月9日
    1.9K00
  • 创建与编辑一体化

    在业务操作中,用户通常期望能够在创建页面后立即进行编辑,以减少频繁切换页面的步骤。我们可以充分利用Oinone平台提供的创建与编辑一体化功能,使操作更加高效便捷。 通过拖拽实现表单页面设计 在界面设计器中,我们首先需要设计出对应的页面。完成页面设计后,将需要的动作拖入设计好的页面。这个动作的关键在于支持一个功能,即根据前端传入的数据是否包含id来判断是创建操作还是编辑操作。 动作的属性配置如下: 前端自定义动作 一旦页面配置完成,前端需要对这个动作进行自定义。以下是一个示例的代码: @SPI.ClassFactory( ActionWidget.Token({ actionType: [ActionType.Server], model: '模型', name: '动作的名称' }) ) export class CreateOrUpdateServerActionWidget extends ServerActionWidget { @Widget.Reactive() protected get updateData(): boolean { return true; } } 通过以上步骤,我们实现了一个更智能的操作流程,使用户能够在创建页面的同时进行即时的编辑,从而提高了整体操作效率。这种创建与编辑一体化的功能不仅使操作更加顺畅,同时也为用户提供了更灵活的工作流程。

    2023年11月21日
    1.6K00
  • 5.1.0版本bugfix:修复协同开发界面设计器函数无法正常使用的问题,请升级对应版本

    版本号: 5.1.10 版本发布日期:2024.09.05更新要点:修复协同开发界面设计器函数无法正常使用的问题 5.1.10 版本 升级说明及步骤(已升级为5.0.0版本忽略) 此版本与4.7.8版本的兼容方案如下,请严格参照升级说明及步骤进行1、【重要】升级前备份base库和用户权限模块所在的库 2、【重要】升级过程执行SQL严格按照升级文档中的步骤执行。特别注意:部分SQL是要求【发布前执行】,部分SQL是要求【发布后执行】 5.0.0升级详细说明及步骤 升级内容(5.1.0) 修复协同开发界面设计器函数无法正常使用的问题 修复GQL层级过深导致无法返回的问题 修复LambdaQueryWrapper在使用select时无法正确处理存储的关联关系字段的问题 修复元数据函数变更时缓存无法正确更新的问题 修复在某些情况下无法正常切换语言的问题 修复前端上传下载时使用相对路径错误覆盖文件的问题 修复EIP用户初始化未正确设置用户来源的问题 修复PamirsMessageJsonConverter转换异常的问题 修复短信和邮件节点,模型相关无法通知的问题。 修复自定义通知人,未调用自定义函数的逻辑缺失。 完善短信发送查询,短信手机号先通过员工表查询,员工表查询失败从用户中心查询。 优化邮件和短信节点的报错信息,显示没有联系方式的用户,将阿里云的报错信息展示到节点错误信息中。 修复邮件服务器配置详情页报错。 修改邮件服务器配置SMTP用户名和服务器地址单索引改为联合索引,优化提示信息。 失效的用户/员工不发送通知,并记录节点日志。 修复通过配置文件配置邮箱后,UI修改邮箱名称,系统重启报错的问题。 应用环境的几个菜单添加搜索功能。 修复无代码模型导入部分场景无法添加字段的问题。 修复工作流部分数学公式(加减乘除)无法处理人工输入数据的问题。 修复工作流人工节点抄送时选择创建/更新人无法抄送的问题。 工作流转交/加签支持选择多个用户 请尽可能保证业务工程前后端服务以及设计器同步升级前端服务仅需重新执行npm install即可自动升级到最新版本 版本包信息 Oinone平台部署及依赖说明(v5.0) 未使用到的版本号请忽略,按项目中使用到的进行替换。 <!– 平台基础 –> <pamirs.middleware.version>5.0.3</pamirs.middleware.version> <pamirs.k2.version>5.1.7</pamirs.k2.version> <pamirs.framework.version>5.1.13</pamirs.framework.version> <pamirs.boot.version>5.1.8</pamirs.boot.version> <pamirs.distribution.version>5.1.7</pamirs.distribution.version> <!– 平台功能 –> <pamirs.metadata.manager>5.1.2</pamirs.metadata.manager> <pamirs.designer.metadata.version>5.1.3</pamirs.designer.metadata.version> <pamirs.core.version>5.1.17</pamirs.core.version> <pamirs.workflow.version>5.1.8</pamirs.workflow.version> <pamirs.workbench.version>5.1.0</pamirs.workbench.version> <pamirs.data.visualization.version>5.1.3</pamirs.data.visualization.version> <!– 设计器 –> <pamirs.designer.common.version>5.1.2</pamirs.designer.common.version> <pamirs.flow.designer.base.version>5.1.3</pamirs.flow.designer.base.version> <pamirs.workflow.designer.version>5.1.2</pamirs.workflow.designer.version> <pamirs.model.designer.version>5.1.4</pamirs.model.designer.version> <pamirs.ui.designer.version>5.1.9</pamirs.ui.designer.version> <pamirs.data.designer.version>5.1.2</pamirs.data.designer.version> <pamirs.dataflow.designer.version>5.1.1</pamirs.dataflow.designer.version> <pamirs.eip.designer.version>5.1.2</pamirs.eip.designer.version> 注意镜像名称变化 镜像说明 所有镜像均使用docker manifest支持amd64和arm64架构。如镜像拉取过慢,可在对应镜像Tag添加-amd64、-arm64后缀获取单一架构镜像。 docker pull harbor.oinone.top/oinone/oinone-designer-full-v5.1:5.1.10-amd64 docker pull harbor.oinone.top/oinone/oinone-designer-full-v5.1:5.1.10-arm64 镜像拉取 镜像或JAR版本:5.1.10 体验镜像:(所有中间件及前后端服务,包含全部设计器) docker pull harbor.oinone.top/oinone/oinone-designer-full-v5.1:5.1.10 部署镜像:(包含前后端服务,包含全部设计器) docker pull harbor.oinone.top/oinone/oinone-designer-mini-v5.1:5.1.10 流程设计器镜像:(包含前后端服务,仅包含流程设计器) docker pull harbor.oinone.top/oinone/workflow-designer-v5.1:5.1.10 后端镜像:(仅包含后端服务,包含全部设计器) docker pull harbor.oinone.top/oinone/designer-backend-v5.1:5.1.10 前端镜像:(仅包含前端服务,包含全部设计器) PS:前端镜像版本为独立版本,与其他镜像版本不同。原基础镜像为nginx-1.21.0版本,从5.0.7版本开始使用nginx-1.24.0版为基础镜像 docker pull harbor.oinone.top/oinone/designer-frontend-v5.1:5.1.16 独立部署所有设计器JAR:(后端服务,包含所有设计器)pamirs-designer-boot-v5.1-5.1.10.jarpamirs-designer-boot-v5.1-latest.jar 独立部署流程设计器JAR:(后端服务,仅包含流程设计器)pamirs-workflow-designer-boot-v5.1-5.1.10.jarpamirs-workflow-designer-boot-v5.1-latest.jar 后端无代码设计器Jar包启动方法 如果您有任何问题、建议或反馈,请随时联系我们。为了获得最佳体验,请及时更新至最新版本。我们将继续努力改进产品,提供更好的服务。谢谢!

    2024年9月5日
    1.1K00
  • 用户中心

    1. 创建用户 进入用户中心应用,在用户列表中点击创建。 填写表单中的必填信息。 若未设置昵称,则右上角头像右侧展示名称。若设置了昵称,则右上角头像右侧展示昵称。 是否激活账号选择是,选择否时用户登录会显示“未找到首页”。 角色分组中,选择创建的用户的角色,默认选择了超级管理员(包含所有权限)。 点击确定,用户创建完成。 用户登录时可用登录账号/邮箱/手机号登录。 2. 用户相关操作 表格页中包含常规的搜索、批量删除功能。 冻结:当将“是否有效”状态为“是”时展示,将用户“是否有效”修改为“否”。 解冻:当将“是否有效”状态为“否”时展示,将用户“是否有效”修改为“是”。 修改:进入用户信息修改页面,“编码、登录账号、注册时间”只读。 重置密码:点击后在弹窗“账号确认”中输入账号,点击重置密码后,展示新密码。

    2024年6月20日
    2.0K00
  • 如何通过传输模型完成页面能力

    介绍 在业务中我们经常能遇到这种场景,我们的数据是通过调用第三方接口获取的,在业务系统中没有对应的存储模型,但是我们又需要展示这些数据,这时候可以利用传输模型不建表的特性完成这个功能。 定义传输模型 package pro.shushi.pamirs.demo.api.tmodel; import pro.shushi.pamirs.meta.annotation.Field; import pro.shushi.pamirs.meta.annotation.Model; import pro.shushi.pamirs.meta.base.TransientModel; @Model.model(DemoCreateOrder.MODEL_MODEL) @Model(displayName = "下单页面模型") public class DemoCreateOrder extends TransientModel { public static final String MODEL_MODEL = "demo.DemoCreateOrder"; @Field.Integer @Field(displayName ="下单人uid") private Long userId; } 定义action,由于传输模型用于表现层和应用层之间的数据交互,本身不会存储,没有默认的数据管理器,只有数据构造器,所以需要手动添加所需的queryOne、create、update等方法 注意:传输模型没有数据管理器能力,所以不提供类似queryPage的方法,后续版本考虑支持中 package pro.shushi.pamirs.demo.core.action; import org.springframework.stereotype.Component; import pro.shushi.pamirs.demo.api.tmodel.DemoCreateOrder; import pro.shushi.pamirs.meta.annotation.Action; import pro.shushi.pamirs.meta.annotation.Function; import pro.shushi.pamirs.meta.annotation.Model; import pro.shushi.pamirs.meta.api.dto.condition.Pagination; import pro.shushi.pamirs.meta.api.dto.wrapper.IWrapper; import pro.shushi.pamirs.meta.constant.FunctionConstants; import pro.shushi.pamirs.meta.enmu.FunctionOpenEnum; import pro.shushi.pamirs.meta.enmu.FunctionTypeEnum; import pro.shushi.pamirs.meta.enmu.ViewTypeEnum; import static pro.shushi.pamirs.meta.enmu.FunctionOpenEnum.*; @Component @Model.model(DemoCreateOrder.MODEL_MODEL) public class DemoCreateOrderAction { @Function.Advanced(type = FunctionTypeEnum.QUERY) @Function.fun(FunctionConstants.queryByEntity) @Function(openLevel = {LOCAL, REMOTE, API}) public DemoCreateOrder queryOne(DemoCreateOrder query) { return query; } @Action.Advanced(name = FunctionConstants.create, managed = true) @Action(displayName = "创建", label = "确定", summary = "添加", bindingType = ViewTypeEnum.FORM) @Function(name = FunctionConstants.create) @Function.fun(FunctionConstants.create) public DemoCreateOrder create(DemoCreateOrder data) { return data; } @Action.Advanced(name = FunctionConstants.update, managed = true) @Action(displayName = "确定", summary = "修改", bindingType = ViewTypeEnum.FORM) @Function(name = FunctionConstants.update) @Function.fun(FunctionConstants.update) public DemoCreateOrder update(DemoCreateOrder data) { return data; } }

    2024年5月24日
    1.0K00

Leave a Reply

登录后才能评论