delete multiple records

Delete Multiple Records Using Pagination in Lightning Component

Hello guys, today in this post we are going to learn about how to delete multiple records using pagination using Salesforce Lightning Component.

But before we get started, first we need to make a new button lets say View Contacts on Account standard object in Salesforce.

View Contacts button is made to show all the contact records related to account object.

Let's highlight those we are going to study about:

dont miss out iconDon't forget to check out: Top Salesforce Lightning Components to Improve Functionality

How to write JavaScript Pagination?

Pagination is done because you might have 1000 records which is awkward to show on one page so what did I do by using pagination 

I’m just showing, for example, five records per page, you can change it according to your need.

How to use Checkbox functionality?

I think it’s clear now because we are going to delete multiple records so we need something and that’s the Checkbox. Well it is not surprising but I am going to show you how can retain checkbox while changing the page because it gets unticked when you use checkbox but in this case, it won’t.

How to show the total number of records in that object?

I’m going to show you the total number of records (in my case I have used recordId which fetches records, for example, contact records particular to that Account in Account standard object.

How to select all of the records or none?

There is this thing which selects as per your need, giving selecting all records functionality is given because you might have over 1k records than you do not want to select all manually. So here it helps in this case.

Well, the theoretical part is over so let’s come to our programming part. I’m going to explain it to you through a code. You can understand easily as most of the lines are commented for your real understanding.

Apex Controller : ViewContacts_on_Account

/*
API : 48
Author : Deepak Rajput
Date : 24/04/2020
*/
public class ViewContacts_on_Account {
    @AuraEnabled 
    public static List<contactListWrapper> fetchContactWrapper(Id recordId ){     
        List<contactListWrapper> lstcontactListWrapper = new List<contactListWrapper>();
        // query contact records related to account and create 'contactListWrapper' class instance for each record. 
        for(Contact con : [Select id,FirstName,LastName,Phone from Contact where AccountId =:recordId Limit 100]){
            // by default checkbox should be false 
            lstcontactListWrapper.add(new contactListWrapper(false,con));
        } 
        // return the 'lstcontactListWrapper' list 
        return lstcontactListWrapper; 
    }
    @AuraEnabled
    public static void DelcontactList(list<Contact> lstRecordId) {  
        list<id> ids=new list<id>(); 
        for(Contact c : lstRecordId){
            ids.add(c.id);
        }
        List<contact> contactList = [Select id,FirstName,LastName,Phone from Contact where Id =:ids];
        delete contactList;
    }
    
    /* wrapper class */  
    public class contactListWrapper {
        @AuraEnabled public boolean isChecked {get;set;}
        @AuraEnabled public  contact objContact{get;set;}
        public contactListWrapper(boolean isChecked, contact objContact){
            this.isChecked = isChecked;
            this.objContact = objContact;
        }
    }
}

Lightning Component : ViewContacts_on_Account.cmp

<!--  
API : 48
Author : Deepak Rajput
Date : 24/04/2020
-->

<aura:component implements="force:appHostable,flexipage:availableForAllPageTypes,flexipage:availableForRecordHome,force:hasRecordId,forceCommunity:availableForAllPageTypes,force:lightningQuickAction"
                access="global" 
                controller="ViewContacts_on_Account">
    <!-- call doInit method on component load -->
    <aura:handler name="init" value="{!this}" action="{!c.doInit}"/>
    
    <!-- aura attributes to store data/values --> 
    <aura:attribute name="recordId" type="Id" />
    <aura:attribute name="listOfAllContacts" type="list"/> 
    <aura:attribute name="PaginationList" type="list"/> 
    <aura:attribute name="selectedCount" type="integer" default="0"
                    description="selected Records Count"/>
    <aura:attribute name="startPage" type="Integer" />
    <aura:attribute name="endPage" type="Integer"/>
    <aura:attribute name="totalRecordsCount" type="Integer"/>
    <aura:attribute name="pageSize" type="Integer" default="5"
                    description="number of records to be display on per page"/>
    <aura:attribute name="currentPage" type="integer" default="1"/>
    <aura:attribute name="totalPagesCount" type="integer"/>
    <aura:attribute name="bNoRecordsFound" type="boolean"/>
    
    <aura:if isTrue="{!v.bNoRecordsFound}">   
        <!--display error message if there is no records available -->
        <div class="slds-notify slds-notify_alert slds-theme_alert-texture slds-theme_info" role="alert">
            <span class="slds-assistive-text">error</span>
            <h2>No record found.</h2>
        </div>
            <!-- display total record and selected record count -->    
            <p class="slds-m-around_small">
                <span class="slds-badge slds-badge_lightest" style="display:inline-block">
                    Total Records : {!v.selectedCount > 0 ? v.selectedCount + '/' : ''} {!v.totalRecordsCount} 
                </span>
            </p>
            
            <!-- data table start-->  
            <table class="slds-table slds-table_bordered slds-table_cell-buffer">
                <thead>
                    <tr class="slds-text-title_caps">
                        <!--header checkbox for select all-->
                        <th style="width:3.25rem;" class="slds-text-align_right">
                            <div class="slds-form-element">
                                <div class="slds-form-element__control">
                                    <label class="slds-checkbox">
                                        <ui:inputCheckbox disabled="{!v.totalRecordsCount == 0}"
                                                          aura:id="selectAllId"
                                                          change="{!c.selectAllCheckbox}"/>
                                        <span class="slds-checkbox_faux"></span>
                                        <span class="slds-form-element__label"></span>
                                    </label>
                                </div>
                            </div>
                        </th>
                        <th scope="col">
                            <div class="slds-truncate" title="FirstName">FirstName</div>
                        </th>
                        <th scope="col">
                            <div class="slds-truncate" title="LastName">LastName</div>
                        </th>
                        <th scope="col">
                            <div class="slds-truncate" title="Phone">Phone</div>
                        </th>
                    </tr>
                </thead>
                <tbody>
                    <aura:iteration items="{!v.PaginationList}" var="obj">
                        <tr>
                            <th scope="row" class="slds-text-align_right" style="width:3.25rem;">
                                <div class="slds-form-element">
                                    <div class="slds-form-element__control">
                                        <label class="slds-checkbox">
                                            <ui:inputCheckbox text="{!obj.objContact.Id}"
                                                              value="{!obj.isChecked}"
                                                              change="{!c.checkboxSelect}"
                                                              aura:id="SelectAllIds"/>
                                            <span class="slds-checkbox_faux"></span>
                                            <span class="slds-form-element__label text"></span>
                                        </label>
                                    </div>
                                </div>
                            </th>
                            <th scope="row">
                                <div class="slds-truncate" title="{!obj.objContact.FirstName}">
                                    {!obj.objContact.FirstName}
                                </div>
                            </th>
                            <th scope="row">
                                <div class="slds-truncate" title="{!obj.objContact.LastName}">
                                    {!obj.objContact.LastName}
                                </div>
                            </th>
                            <th scope="row">
                                <div class="slds-truncate" title="{!obj.objContact.Phone}">
                                    <lightning:formattedPhone value="{!obj.objContact.Phone}"/>
                                </div>
                            </th>
                        </tr>
                    </aura:iteration>
                </tbody>
            </table>
            <!-- DataTable End -->
            <br/>
            <!--  Pagination Buttons Start -->
            <div class="slds-align_absolute-center">         
                <lightning:button label="Previous"
                                  disabled="{!v.startPage == 0}"  
                                  onclick="{!c.navigation}"
                                  variant="brand"
                                  iconName="utility:back"
                                  name="previous"/>
                
                <span class="slds-badge slds-badge_lightest"
                      style="margin-right: 10px;margin-left: 10px;">
                    Page {!v.currentPage} out of {!v.totalPagesCount}
                </span>
                
                <lightning:button label="Next"
                                  disabled="{!(v.endPage + 1) >= v.totalRecordsCount}" 
                                  onclick="{!c.navigation}"
                                  variant="brand"
                                  iconName="utility:forward"
                                  iconPosition="right"
                                  name="next"/>
            </div>
            <button class="slds-button slds-button--brand" onclick="{!c.deleteSelected}">Delete Contact</button>
            <!--  Pagination Buttons End -->
    </aura:if>  
</aura:component>

JavaScript Controller : ViewContacts_on_AccountController.js

({
    doInit: function(component, event, helper) {
        helper.doInitHelper(component, event);
    },
    
    /* javaScript function for pagination */
    navigation: function(component, event, helper) {
        var sObjectList = component.get("v.listOfAllContacts");
        var end = component.get("v.endPage");
        var start = component.get("v.startPage");
        var pageSize = component.get("v.pageSize");
        var whichBtn = event.getSource().get("v.name");
        // check if whichBtn value is 'next' then call 'next' helper method
        if (whichBtn == 'next') {
            component.set("v.currentPage", component.get("v.currentPage") + 1);
            helper.next(component, event, sObjectList, end, start, pageSize);
        }
        // check if whichBtn value is 'previous' then call 'previous' helper method
        else if (whichBtn == 'previous') {
            component.set("v.currentPage", component.get("v.currentPage") - 1);
            helper.previous(component, event, sObjectList, end, start, pageSize);
        }
    },
    
    selectAllCheckbox: function(component, event, helper) {
        var selectedHeaderCheck = event.getSource().get("v.value");
        var updatedAllRecords = [];
        var updatedPaginationList = [];
        var listOfAllContacts = component.get("v.listOfAllContacts");
        var PaginationList = component.get("v.PaginationList");
        // play a for loop on all records list 
        for (var i = 0; i < listOfAllContacts.length; i++) {
            // check if header checkbox is 'true' then update all checkbox with true and update selected records count
            // else update all records with false and set selectedCount with 0  
            if (selectedHeaderCheck == true) {
                listOfAllContacts[i].isChecked = true;
                component.set("v.selectedCount", listOfAllContacts.length);
            } else {
                listOfAllContacts[i].isChecked = false;
                component.set("v.selectedCount", 0);
            }
            updatedAllRecords.push(listOfAllContacts[i]);
        }
        // update the checkbox for 'PaginationList' based on header checbox 
        for (var i = 0; i < PaginationList.length; i++) {
            if (selectedHeaderCheck == true) {
                PaginationList[i].isChecked = true;
            } else {
                PaginationList[i].isChecked = false;
            }
            updatedPaginationList.push(PaginationList[i]);
        }
        component.set("v.listOfAllContacts", updatedAllRecords);
        component.set("v.PaginationList", updatedPaginationList);
    },
    
    checkboxSelect: function(component, event, helper) {
        // on each checkbox selection update the selected record count 
        var selectedRec = event.getSource().get("v.value");
        var getSelectedNumber = component.get("v.selectedCount");
        if (selectedRec == true) {
            getSelectedNumber++;
        } else {
            getSelectedNumber--;
            component.find("selectAllId").set("v.value", false);
        }
        component.set("v.selectedCount", getSelectedNumber);
        // if all checkboxes are checked then set header checkbox with true   
        if (getSelectedNumber == component.get("v.totalRecordsCount")) {
            component.find("selectAllId").set("v.value", true);
        }
    },
    
    getSelectedRecords: function(component, event, helper) {
        var allRecords = component.get("v.listOfAllContacts");
        var selectedRecords = [];
        for (var i = 0; i < allRecords.length; i++) {
            if (allRecords[i].isChecked) {
                selectedRecords.push(allRecords[i].objContact);
            }
        }
        
        alert(JSON.stringify(selectedRecords)); 
    },
    
    //For Delete selected records 
    deleteSelected: function(component, event, helper) {
        var allRecords = component.get("v.listOfAllContacts");
        var selectedRecords = [];
        for (var i = 0; i < allRecords.length; i++) {
            if (allRecords[i].isChecked) {
                selectedRecords.push(allRecords[i].objContact);
            }
        }
        
        // call the helper function and pass all selected record id's.    
        helper.deleteSelectedHelper(component, event, selectedRecords);
        console.log("selectedRecords");  
    },
})

dont miss out iconCheck out another amazing blog by Deepak here: Salesforce Ant Migration Tool - The Complete Guide

JavaScript Helper : ViewContacts_on_AccountHelper.js

({
    /* doInitHelper funcation to fetch all records, and set attributes value on component load */
    doInitHelper : function(component,event){ 
        var action = component.get("c.fetchContactWrapper");
        action.setParams
        ({
            recordId: component.get("v.recordId")
        });
        action.setCallback(this, function(response) {
            var state = response.getState();
            if (state === "SUCCESS"){
                var oRes = response.getReturnValue();
                if(oRes.length > 0){
                    component.set('v.listOfAllContacts', oRes);
                    var pageSize = component.get("v.pageSize");
                    var totalRecordsList = oRes;
                    var totalLength = totalRecordsList.length ;
                    component.set("v.totalRecordsCount", totalLength);
                    component.set("v.startPage",0);
                    component.set("v.endPage",pageSize-1);
                //    component.set("")
                    
                    var PaginationLst = [];
                    for(var i=0; i < pageSize; i++){
                        if(component.get("v.listOfAllContacts").length > i){
                            PaginationLst.push(oRes[i]);    
                        } 
                    }
                    component.set('v.PaginationList', PaginationLst);
                    component.set("v.selectedCount" , 0);
                    //use Math.ceil() to Round a number upward to its nearest integer
                    component.set("v.totalPagesCount", Math.ceil(totalLength / pageSize)); 
                    component.set("v.currentPage", 1);
                 //currentPage = ceil(($startIndex - 1) / $itemsPerPage) + 1;
                 //  ((startIndex-1)/itemsPerPage) + 1,                 
                }else{
                    // if there is no records then display message
                    component.set("v.bNoRecordsFound" , true);
                } 
            }
            else{
                alert('Error...');
            }
        });
        $A.enqueueAction(action);  
    },
    // navigate to next pagination record set   
    next : function(component,event,sObjectList,end,start,pageSize){
        var Paginationlist = [];
        var counter = 0;
        for(var i = end + 1; i < end + pageSize + 1; i++){
            if(sObjectList.length > i){ 
                if(component.find("selectAllId").get("v.value")){
                    Paginationlist.push(sObjectList[i]);
                }else{
                    Paginationlist.push(sObjectList[i]);  
                }
            }
            counter ++ ;
        }
        start = start + counter;
        end = end + counter;
        component.set("v.startPage",start);
        component.set("v.endPage",end);
        component.set('v.PaginationList', Paginationlist);
    },
    // navigate to previous pagination record set   
    previous : function(component,event,sObjectList,end,start,pageSize){
        var Paginationlist = [];
        var counter = 0;
        for(var i= start-pageSize; i < start ; i++){
            if(i > -1){
                if(component.find("selectAllId").get("v.value")){
                    Paginationlist.push(sObjectList[i]);
                }else{
                    Paginationlist.push(sObjectList[i]); 
                }
                counter ++;
            }else{
                start++;
            }
        }
        start = start - counter;
        end = end - counter;
        component.set("v.startPage",start);
        component.set("v.endPage",end);
        component.set('v.PaginationList', Paginationlist);
    },
    deleteSelectedHelper: function(component, event, selectedRecords) { 
        //call apex class method
        var action = component.get('c.DelcontactList');
        // pass the all selected record's Id's to apex method 
        action.setParams({
            "lstRecordId": selectedRecords
        });
        action.setCallback(this, function(response) {
            //store state of response
            var state = response.getState();
            if (state === "SUCCESS") {

                console.log(state);
                        $A.get('e.force:refreshView').fire();

                if (response.getReturnValue() != '') {
                    // if getting any error while delete the records , then display a alert msg/
                    //   alert('The following error has occurred. while Delete record-->' + response.getReturnValue());
                } else {
                    console.log('check it--> delete successful');
                }
                // call the onLoad function for refresh the List view    
                    this.doInitHelper(component, event);
            }
        });
        $A.enqueueAction(action);
    },
})

Feel free to ask any questions and don’t forget to share it with your friends.

Related Articles

Responses