EDIT: Scroll to the bottom of this post for the working code.
I'm very much a beginner at using SalesForce so please forgive me if this question has a trivial solution 🙁
I have a DataTable filled with movie poster information (title, inventory count). I'm just trying to make an app that adds/deletes and if I have time, edits the entries.
Right now I'm trying to get deleting working. I've tried dissecting the example at https://developer.salesforce.com/docs/atlas.en-us.lightning.meta/lightning/aura_compref_lightning_datatable.htm but I'm having trouble.
Javascript controller code:
deleteTableRow : function(component, row) {
var action = component.get("c.deletePoster");
action.setParams({
"toDelete": row
});
$A.enqueueAction(action);
component.refreshDataTable();
}
Here is how I refresh my DataTable (code from the JS controller):
refreshDataTable : function(component, event, helper) {
var refreshAction = component.get("c.getPosters");
refreshAction.setCallback(this, function(data) {
component.set("v.Poster", data.getReturnValue());
});
$A.enqueueAction(refreshAction);
},
Apex code for deleting and refreshing/populating the table:
@AuraEnabled
public static List<Poster__c> getPosters(){
return [Select ID__c, Count__c, Name From Poster__c];
}
@AuraEnabled
public static void deletePoster(Poster__c toDelete){
delete toDelete;
}
Markup (the relevant delete code is in the 2nd lightning card):
<aura:component controller="PostroApexController" implements="flexipage:availableForRecordHome" access="global">
<aura:attribute name="Poster" type="Poster__c"/>
<aura:attribute name="Posters" type="List"/>
<aura:attribute name="Columns" type="List"/>
<aura:attribute name="newPosterTitle" type="String"/>
<aura:attribute name="newPosterCount" type="Decimal"/>
<aura:method name="refreshDataTable" action="{!c.refreshDataTable}"
description="refreshes datatable when data changes"/>
<aura:handler name="init" value="{!this}" action="{!c.performInit}"/>
<div class="width200">
<lightning:card title="Postro SalesForce Demo" iconName="standard:account" footer="Some footer">
<p>
Postro is an inventory management system for movie theatres, specifically relating to movie poster stock.
</p>
<lightning:datatable data="{! v.Poster }" columns="{! v.Columns }" keyField="ID" hideCheckboxColumn="true"
onrowselection="{! c.getSelectedID}"/>
<hr/>
<lightning:input type="text" label="Poster Title" name="posterTitle" value="{!v.newPosterTitle}"/>
<lightning:input type="number" label="Poster Count" name="posterCount" value="{!v.newPosterCount}"/>
<lightning:button type="submit" label="Add" name="btnAdd" onclick="{! c.addNewPoster}"/>
</lightning:card>
<lightning:card title="Postro Tools" footer="Some footer">
<lightning:button type="button" label="Delete" name="btnDelete" onclick="{! c.deleteTableRow}"/>
</lightning:card>
</div>
</aura:component>
Here are the fields on my Poster object:
If I click "delete", nothing happens. How can I get this to work?
EDIT: Working code
Add new attribute to store selected rows:
<aura:attribute name="selectedRows" type="List"/>
Set DataTable's onrowselection
to a JS component function to store the selected rows in the above attribute. My function is {! c.storeSelectedRows}
.
Here is that function:
storeSelectedRows : function(component, event, helper){
var selectedRows = event.getParam("selectedRows");
component.set("v.selectedRows", selectedRows);
},
Finally the JS for deleting rows, set as the function for a "Delete" button. This function feels pretty hacky and could probably be made more efficient, but this works for my purposes for now:
deleteTableRows : function(component, event, helper) {
var selectedPosters = component.get("v.selectedRows");
var IDs = [];
for (var i = 0; i < selectedPosters.length; i++){
IDs[i] = selectedPosters[i].ID__c;
}
var action = component.get("c.deletePosterListByID");
action.setParams({
"idList": IDs
});
$A.enqueueAction(action);
component.refreshDataTable();
}
The function to refresh is higher in this post. Thank you to everyone who helped me get here!
Best Answer
In addition to what @sfdcfox mentioned, below is how you can modify your code to work. Though the below approach will enable your code to work, but follow a more efficient approach where you don't need to make a server trip after deleting the row, instead update the dataTable values, right in the deleteTableRow function as explained in the documentation.
Declare a variable which will capture the selected row, which you will need to use in deleteTableRow JS function.
Set the value of this attribute in the getSelectedID JS function as:
Additionally, modify your deleteRow JS function as below to align as a JS controller function for the component and use the selectedRow attribute as above: