026_Pagination分页

本文详细介绍了Element UI中的Pagination分页组件,包括其属性、事件和插槽的使用方法,并提供了多个实际应用示例,如基础用法、设置最大页码按钮数、带有背景色的分页及小型分页等。通过调整不同属性,可以实现灵活的分页功能,并通过事件监听页面大小和当前页数的变化。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1. Pagination分页

1.1. Pagination分页当数据量过多时,使用分页分解数据。

1.2. Attributes

参数

说明

类型

可选值

默认值

small

是否使用小型分页样式

boolean

false

background

是否为分页按钮添加背景色

boolean

false

page-size

每页显示条目个数, 支持.sync修饰符

number

10

total

总条目数

number

page-count

总页数, total和page-count设置任意一个就可以达到显示页码的功能; 如果要支持page-sizes的更改, 则需要使用total属性

number

pager-count

页码按钮的数量, 当总页数超过该值时会折叠

number

大于等于5且小于等于21的奇数

7

current-page

当前页数, 支持.sync修饰符

number

1

layout

组件布局, 子组件名用逗号分隔

String

sizes, prev, pager, next, jumper, ->, total, slot

'prev, pager, next, jumper, ->, total'

page-sizes

每页显示个数选择器的选项设置

number[]

[10, 20, 30, 40, 50, 100]

popper-class

每页显示个数选择器的下拉框类名

string

prev-text

替代图标显示的上一页文字

string

next-text

替代图标显示的下一页文字

string

disabled

是否禁用

boolean

false

hide-on-single-page

只有一页时是否隐藏

boolean

1.3. Events

事件名称

说明

回调参数

size-change

pageSize改变时会触发

每页条数

current-change

currentPage改变时会触发

当前页

prev-click

用户点击上一页按钮改变当前页后触发

当前页

next-click

用户点击下一页按钮改变当前页后触发

当前页

1.4. Slot

name

说明

自定义内容, 需要在layout中列出slot

2. Pagination分页例子

2.1. 使用脚手架新建一个名为element-ui-pagination的前端项目, 同时安装Element插件。

2.2. 在components在新建Pagination.vue 

<template>
  <div>
    <h1>基础用法</h1>
    <h4>total总条目数。page-size每页显示条目个数, 默认是10。current-page当前页数。hide-on-single-page只有一页时是否隐藏。</h4>
    <div class="block">
      <span>页数较少时的效果</span>
      <el-pagination :total="50"></el-pagination>
    </div>
    <div class="block">
      <span>大于7页时的效果</span>
      <el-pagination :total="1000" :page-size="100" :current-page="2" hide-on-single-page></el-pagination>
    </div>

    <h1>设置最大页码按钮数</h1>
    <h4>默认情况下, 当总页数超过7页时, Pagination会折叠多余的页码按钮。通过pager-count属性可以设置最大页码按钮数。</h4>
    <el-pagination :pager-count="11" :total="1000" :current-page.sync="curPage"></el-pagination>

    <h1>带有背景色的分页</h1>
    <h4>设置background属性可以为分页按钮添加背景色。prev-text替代图标显示的上一页文字。next-text替代图标显示的下一页文字。</h4>
    <el-pagination background :total="1000" prev-text="上一页" next-text="下一页"></el-pagination>

    <h1>小型分页</h1>
    <h4>在空间有限的情况下, 可以使用简单的小型分页。只需要一个small属性, 它接受一个Boolean, 默认为false, 设为true即可启用。</h4>
    <h4>size-change事件, 当pageSize改变时会触发。current-change事件, 当currentPage改变时会触发。</h4>
    <el-pagination small :total="50" @size-change="hdlSizCha" @current-change="hdlCurCha"></el-pagination>

    <h1>布局组件</h1>
    <h4>page-sizes每页显示个数选择器的选项设置。</h4>
    <h4>设置layout, 表示需要显示的内容, 用逗号分隔, 布局元素会依次显示。prev表示上一页, next为下一页, pager表示页码列表, 特殊的布局符号->后的元素会靠右显示, jumper表示跳页元素, total表示总条目数, size用于设置每页显示的页码数量。</h4>
    <el-pagination :total="400" :page-sizes="[100, 200, 300, 400]" :page-size="100" layout="total, sizes, prev, pager, next, jumper"></el-pagination>
  </div>
</template>

<script>
export default {
  methods: {
    hdlSizCha (val) {
      console.log(`每页 ${val} 条`)
    },
    hdlCurCha (val) {
      console.log(`当前页: ${val}`)
    }
  },
  data () {
    return {
      curPage: 5
    }
  }
}
</script>

2.3. 访问http://localhost:8080/#/Pagination

<think>好的,我现在需要解决用户关于FastAPI Pagination库的问题。用户之前遇到了TypeError,具体是“'Query'对象没有len()”,现在他想了解分页查询的实现原理以及如何解决之前的错误。首先,我得回顾之前的对话,确保这次的回答连贯。 用户提到参考站内引用,但之前的引用可能不是用户真实需求,需要更多参考用户的上一次问题和我的回答。用户的上一个问题中,我给出了解决TypeError的步骤,包括检查查询是否执行、导入是否正确等。现在用户想深入理解分页原理,同时巩固解决TypeError的方法。 首先,我需要解释fastapi-pagination的工作原理。这个库如何处理查询?可能是通过解析请求参数生成分页参数,然后应用到数据库查询上。需要区分同步和异步查询,因为不同模式下处理方式可能不同。比如,同步查询可能直接使用limit和offset,而异步可能需要不同的处理方式。 接下来,TypeError的原因。用户之前的问题中,错误是因为传递了未执行的Query对象,而不是结果列表。但根据我的上一次回答,新版本可能支持直接传递查询对象,但用户可能在使用旧版本,或者某些情况下仍然需要执行查询。需要详细说明不同情况下的正确用法,比如同步和异步的不同处理。 然后,需要结合代码示例,说明正确的实现方式。比如,在同步模式下,可能需要调用.all(),而异步模式下使用await session.execute()。此外,分页器的paginate函数如何处理查询,内部如何生成count查询和分页查询。 还需要考虑分页器如何集成到FastAPI路由中,响应模型的使用,以及如何自动生成分页参数(如page和size)。可能涉及到中间件或依赖注入,自动解析请求中的分页参数。 另外,用户可能对分页器如何计算总页数和记录数感兴趣,这部分需要解释SQLAlchemy查询的count方法,以及分页器如何优化这些查询,避免性能问题。 最后,要确保回答结构清晰,分点解释原理和解决步骤,提供代码示例,并生成相关问题。同时,检查是否需要更新库的版本,因为不同版本可能有不同的行为,比如是否支持直接传递查询对象。 总结,我需要组织内容为:分页原理(同步/异步)、TypeError的原因和解决方法、代码示例、常见问题。确保覆盖用户的所有疑问,并引用之前提到的解决方案,保持一致性。</think>### FastAPI分页器原理与TypeError深度解析 --- #### 一、分页查询核心原理(SQLAlchemy同步/异步模式) 1. **参数解析机制** fastapi-pagination通过中间件自动解析请求中的分页参数,默认使用`page`和`size`参数生成分页元数据: ```python # 自动从请求中提取参数示例 # GET /items?page=2&size=20 ``` 2. **双查询执行原理** 分页器执行两个关键查询: ```python # 1. 计算总记录数(自动优化count查询) total = await db.execute(select(func.count()).select_from(query.subquery())) total_count = total.scalar() # 2. 执行分页数据查询(自动添加limit/offset) items = await db.execute(query.limit(params.size).offset((params.page-1)*params.size)) ``` 3. **响应封装** 生成标准化响应结构: ```json { "items": [...], "total": 150, "page": 2, "size": 20 } ``` --- #### 二、TypeError: 'Query' has no len() 根本原因 | 错误场景 | 正确场景 | 原理对比 | |---------|---------|---------| | `paginate(db.query(User))` | `paginate(db.query(User).all())` | SQLAlchemy查询对象需执行后获得可计算长度的结果集 | | `async def`中使用同步查询 | 使用`async_session`+`await`执行 | 异步模式下未执行查询对象同样无法计算长度 | --- #### 三、同步/异步模式下的正确实现 1. **同步模式(SQLAlchemy ORM)** ```python @router.get("/sync-users") def get_sync_users(db: Session = Depends(get_db)): query = db.query(User).filter(User.active == True) return paginate(query) # ✅ 新版本(>=0.12.0)支持自动执行 ``` 2. **异步模式(Async SQLAlchemy)** ```python @router.get("/async-users") async def get_async_users(async_db: AsyncSession = Depends(get_async_db)): query = select(User).where(User.active == True) result = await async_db.execute(query) return paginate(result.scalars().all()) # ✅ 必须显式执行 ``` 3. **自定义分页逻辑** ```python class CustomParams(Params): page: int = Query(1, ge=1, alias="p") size: int = Query(50, ge=1, le=100, alias="s") @router.get("/custom-page") def custom_pagination(params: CustomParams = Depends()): base_query = db.query(Product).filter(Product.price > 100) return paginate(base_query, params) ``` --- #### 四、深度技术解析:分页器内部实现 查看`fastapi_pagination/paginator.py`核心逻辑: ```python def paginate(query: Any, params: Params) -> AbstractPage: # 执行count查询 total = _execute_count_query(query) # 🔍 触发SELECT COUNT(*) # 执行数据查询 items = _execute_data_query( query, limit=params.size, offset=(params.page - 1) * params.size ) return create_page(items, total, params) # 🛠️ 构造响应模型 ``` --- #### 五、常见问题解决方案 1. **性能优化技巧** - 使用窗口函数优化count查询: ```python query = query.options( sa.lambda_stmt(lambda: [with_expression( User.total_count, func.count().over() )]) ) ``` - 避免N+1查询:使用`selectinload`预加载关联数据 2. **复杂查询适配方案** ```python # JOIN查询分页示例 stmt = ( select(Order) .join(User) .where(User.country == "CN") .order_by(Order.created_at.desc()) ) return paginate(db.execute(stmt).scalars().all()) ``` --- #### 六、版本兼容性对照表 | fastapi-pagination | SQLAlchemy | 查询传递方式 | 执行要求 | |--------------------|------------|--------------|----------| | <0.9.0 | 1.3 | 必须`.all()` | 显式执行 | | >=0.9.0 | 1.4+ | 支持原始查询 | 自动执行 | | >=0.12.0 | 2.0+ | 同步/异步统一API | 自动适配 | --- --相关问题-- 1. 如何为分页结果添加额外的元数据字段? 2. 使用fastapi-pagination时如何进行性能监控? 3. 分页查询与GraphQL如何集成? 4. 分页器如何支持游标分页(Cursor-based Pagination)?
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值