HTML
<template>
<lightning-card variant="base">
<div slot="title">
Card Title
</div>
<div>
<!-- Card Body -->
<template if:true={records}>
<div class="table-container">
<lightning-datatable key-field="id" data={records} columns={columns}>
</lightning-datatable>
</div>
<br>
<lightning-layout>
<lightning-layout-item>
<lightning-button label="Previous" icon-name="utility:chevronleft" onclick={handlePrevious}
class="previous" disabled={previousButtonDisabled}>
</lightning-button>
</lightning-layout-item>
<lightning-layout-item flexibility="grow" style="text-align: center;">
<p>{currentPageNum} of {totalPageCount}</p>
</lightning-layout-item>
<lightning-layout-item>
<lightning-button label="Next" icon-name="utility:chevronright" icon-position="right"
onclick={handleNext} class="next" disabled={nextButtonDisabled}>
</lightning-button>
</lightning-layout-item>
</lightning-layout>
</template>
</div>
</lightning-card>
</template>
Js
import { LightningElement, wire } from 'lwc';
import getAccountsPaginated from '@salesforce/apex/PracticePaginationController.getAccountsPaginated';
const COLUMNS = [
{
label: 'Account Name',
fieldName: 'Name',
type: 'text'
},
{ label: 'Type', fieldName: 'Type', type: 'text' },
{
label: 'Phone',
fieldName: 'Phone',
type: 'phone'
}
];
const PAGE_SIZE = 5;
export default class PracticePagination extends LightningElement {
columns = COLUMNS;
error;
records;
currentPageToken = 0;
nextPageToken = PAGE_SIZE;
totalPageCount = 0;
previousButtonDisabled;
nextButtonDisabled;
currentPageNum = 1;
@wire(getAccountsPaginated, {
pageSize: PAGE_SIZE,
pageToken: '$currentPageToken'
})
wiredAccounts({ data, error }) {
if (data) {
this.records = data.records;
this.nextPageToken = data.nextPageToken;
this.totalPageCount = data.totalPageCount;
this.previousButtonDisabled = this.currentPageToken === 0 ? true : false;
this.nextButtonDisabled = this.nextPageToken === undefined ? true : false;
} else if (error) this.error = error;
}
handlePrevious() {
this.currentPageToken = this.currentPageToken - PAGE_SIZE;
this.previousButtonDisabled = this.currentPageToken === 0 ? true : false;
this.nextButtonDisabled = this.nextPageToken === undefined ? true : false;
this.currentPageNum -= 1;
}
handleNext() {
this.currentPageToken = this.currentPageToken + PAGE_SIZE;
this.previousButtonDisabled = this.currentPageToken === 0 ? true : false;
this.nextButtonDisabled = this.nextPageToken === undefined ? true : false;
this.currentPageNum += 1;
}
}
Controller
public with sharing class PracticePaginationController {
@AuraEnabled(cacheable=true)
public static PaginatedAccounts getAccountsPaginated(Integer pageSize,Integer pageToken) {
PaginatedAccounts paginatedAccounts = new PaginatedAccounts();
paginatedAccounts.records = [
SELECT Name, Type, Phone, Owner.Name
FROM Account
WITH SECURITY_ENFORCED
ORDER BY Name
LIMIT :pageSize
OFFSET :pageToken
];
Integer totalCount = [SELECT COUNT() FROM Account];
paginatedAccounts.nextPageToken = (pageToken + pageSize < totalCount)
? pageToken + pageSize
: null;
paginatedAccounts.totalPageCount = Math.ceil(Decimal.valueOf(totalCount).divide(pageSize, 1));
return paginatedAccounts;
}
public class PaginatedAccounts {
@AuraEnabled
public List records;
@AuraEnabled
public Integer nextPageToken;
@AuraEnabled
public Decimal totalPageCount;
}
}