I have an accordion component that retrieves deal terms records. Each deal term has a payment schedule. My LWC pulls all the deal terms plus related payment schedules and displays on a page like this:
The data for data table is coming from related records. My apex SOQL query looks like this:
public with sharing class MLSE_DealTermsEditor {
public String currentRecordId {get;set;}
public MLSE_DealTermsEditor(ApexPages.StandardController controller) {
currentRecordId = ApexPages.CurrentPage().getparameters().get('id');
}
@AuraEnabled (cacheable=true)
public static List<Deal_Term__c> RetriveDealTerms(Id contract){
return [SELECT Id, Name, (SELECT ID, Name, Amount_Pending__c, Amount_Received__c, Payment_Due_Date__c, Payment_Received_Date__c FROM Payment_Schedules__r) FROM Deal_Term__c WHERE Contract__c =: contract];
}
@AuraEnabled
public static string UpdatePaymentSchedules(Object data) {
List<Payment_Schedule__c> paymentSchedulesUpdate = (List<Payment_Schedule__c>) JSON.deserialize(
JSON.serialize(data),
List<Payment_Schedule__c>.class
);
try {
update paymentSchedulesUpdate;
return 'Success: payment schedules updated successfully';
}
catch (Exception e) {
return 'The following exception has occurred: ' + e.getMessage();
}
}
}
My lightning component looks like this:
<template>
<div class="c-container">
<lightning-card title="Payment Schedule Editor"></lightning-card>
<lightning-accordion allow-multiple-sections-open={multiple}>
<div class="slds-m-around_small">
<template if:true={deal_terms}>
<template for:each={deal_terms} for:item="dt">
<lightning-accordion-section name={dt.Name} label={dt.Name} key={dt.Id}>
<div class="slds-box slds-theme--shade">
<div style="height: 450px;">
<lightning-datatable
key-field="Id"
data={dt.Payment_Schedules__r}
columns={columns}
onsave={handleSave}
draft-values={draftValues}
>
</lightning-datatable>
</div>
</div>
<template if:true={dt.error}>
<!-- handle Apex error -->
</template>
</lightning-accordion-section>
</template>
</template>
</div>
</lightning-accordion>
</div>
</template>
And JS file:
import { LightningElement, wire, api, track } from 'lwc';
import { getRecordNotifyChange } from 'lightning/uiRecordApi';
import { refreshApex } from '@salesforce/apex';
import { ShowToastEvent } from 'lightning/platformShowToastEvent';
import getDealTermDetails from '@salesforce/apex/MLSE_DealTermsEditor.RetriveDealTerms';
import updateSchedules from '@salesforce/apex/MLSE_DealTermsEditor.UpdatePaymentSchedules';
export default class Mlse_dealterms_editor extends LightningElement {
draftValues = [];
@track wiredResults;
@track multiple = true;
@track deal_terms;
@track error;
@track toastVisible;
@api recordId;
@track columns = [
{ label: 'Invoice #', fieldName: 'Name', type: 'text' },
{ label: 'Invoice Date', fieldName: 'Payment_Due_Date__c', type: 'date-local', editable: true },
{ label: 'Payment Received Date', fieldName: 'Payment_Received_Date__c', type: 'date-local', editable: true },
{ label: 'Amount Pending', fieldName: 'Amount_Pending__c', type: 'currency', editable: true },
{ label: 'Amount Received', fieldName: 'Amount_Received__c', type: 'currency', editable: true }
];
@wire(getDealTermDetails, { contract: '$recordId' })
wiredDealTerms(results) {
this.wiredResults = results;
if (results.data) {
this.deal_terms = results.data;
this.error = undefined;
} else if (results.error) {
this.records = undefined;
this.error = 'Unknown error';
}
}
async handleSave(event) {
const updatedFields = event.detail.draftValues;
// Prepare the record IDs for getRecordNotifyChange()
const notifyChangeIds = updatedFields.map(row => { return { "recordId": row.Id } });
// console.log('notifyChangeIds' + JSON.stringify(notifyChangeIds));
await updateSchedules({data: updatedFields})
.then(result => {
// console.log(JSON.stringify("Apex update result: "+ result));
this.dispatchEvent(
new ShowToastEvent({
title: 'Success',
message: 'Records updated',
variant: 'success'
})
);
// Refresh LDS cache and wires
getRecordNotifyChange(notifyChangeIds);
//call refresh to do refreshapex
this.refresh();
})
.catch(error => {
console.log(error);
this.error = error;
});
}
refresh() {
refreshApex(this.wiredResults)
.then(() => {
this.draftValues = [];
// console.log('refresh apex complete');
}).catch();
}
}
I can edit the data in the tables but it's not saving it when i push the save button. What can i do to let can inline edit and save the data?
UPDATE: I added code to save the data (handleSave). However, when i push the SAVE button, i can't get it to disappear and refresh. Here is a screenshot:
When i check if it got saved, it did. But it won't remove the SAVE screen after saving.
FINAL UPDATE: I updated the code so that it now works! The only thing missing is the spinner.