My nested string-list template table in LWC is working well, but as a js/LWC noob, I'm struggling with making some enhancements, particularly adding new data points to .
I need to add some information to the top level of data - I currently have a row displaying the map key, but I need to add a couple of links to that row. These links are contained in every row of the list in the map, but I can't figure out how to get that data outside of the iteration template for that map.
Here is the js, with my most recent failure commented out
import { LightningElement, api, wire } from 'lwc';
import getRecords from '@salesforce/apex/CoachPortalHelperClassesEYD.getDeliverables';
export default class CPAssignmentList extends LightningElement {
@api TimeFrame;
displaydata = false;
isreview = false;
deliverables=[];
acceptLinks=[];
declineLinks=[];
@wire(getRecords, { TimeFrame: "$TimeFrame" })
getResults(result) {
if(this.TimeFrame == 'Open'){
this.isreview = true;
}
if (result.data) {
const deliverableMap = result.data;
console.log(JSON.stringify(deliverableMap));
for (const key in deliverableMap) {
this.deliverables.push({value: deliverableMap[key], key}); //Here we are creating the top level array to show on UI.
//this.deliverables.acceptLink = deliverableMap[key][0].acceptLink;
//this.deliverables.declineLink = deliverableMap[key][0].declineLink;
}
this.displaydata = true;
} else {
console.log('Error');
}
}
}
Here is the relevant subsection of the HTML - I'm not sure you need the rest of it since it all displays fine - I just can't figure out how to get the accept and decline links to appear.
<template for:each={deliverables} for:item="sow">
<tr class="sowHeaderRow" key ={sow.key}>
<template lwc:if={isreview}>
<td data-label="SOW Name" colspan="2">
<strong>{sow.key}</strong>
</td>
</template>
<template lwc:else>
<td data-label="SOW Name" colspan="4">
<strong>{sow.key}</strong>
</td>
</template>
<td>
<template lwc:if={isreview}>
<a href='{sow.acceptLink}' >Accept</a>
<a href='{sow.declineLink}' >Decline</a>
</template>
</td>
</tr>
<template for:each={sow.value} for:item="sowli">
Here is the Apex Controller:
global without sharing class CoachPortalHelperClassesEYD {
@AuraEnabled(cacheable = true)
global static map<string,list<Deliverable>> getDeliverables(string TimeFrame){
map<string,list<Deliverable>> Deliverables = new map<string,list<Deliverable>>();
list<Statement_of_Work__c> SOWS = getRecords(TimeFrame);
//Get SOW fulfillments and Engagement Reports to display status
set<string> SOWLI_Ids = new set<string>();
for(Statement_of_Work__c SOW: SOWs){
for(sow_line_item__c SOWLI: SOW.sow_line_items__r){
SOWLI_Ids.add(SOWLI.Id);
}
}
Map<ID, sow_line_item__c> sowli_fulfillment_map = new Map<ID, sow_line_item__c>([SELECT Id,
(select createddate from sow_line_item_fulfillments__r order by createddate desc limit 1),
(select lastmodifieddate from Coach_Engagement_Reports__r order by lastmodifieddate desc limit 1)
from sow_line_item__c
where id in :SOWLI_Ids]);
String currentFiscalYear = [SELECT FiscalYearSettings.Name FROM Period WHERE Type = 'Year' AND StartDate <= TODAY AND EndDate >= TODAY].FiscalYearSettings.Name;
List<String> args = new String[]{'0','number','###,###,##0'};
for(Statement_of_Work__c SOW: SOWS){
for(sow_line_item__c SOWLI: SOW.sow_line_items__r){
deliverable d = new deliverable();
d.name = SOWLI.Title__c != null ? SOWLI.Title__c : SOWLI.Coach_Deliverables__r.Name;
sow_line_item__c related = sowli_fulfillment_map.get(sowli.id);
if(SOWLI.Number_of_Work_Units_Remaining__c == 0){
d.Status = 'Fulfilled';
if(related.sow_line_item_fulfillments__r.size()>0){
d.Status += ' '+ related.sow_line_item_fulfillments__r[0].createddate.Format('MM/dd/yyyy');
}
} else if (related.coach_engagement_reports__r.size()>0){
d.Status = 'Resume report saved on '+ related.coach_engagement_reports__r[0].createddate.Format('MM/dd/yyyy');
} else {
d.Status = 'Click to fulfill';}
d.isOpen = SOWLI.Number_of_Work_Units_Remaining__c == 0 ? False : True;
d.ExpectedDate = SOWLI.Estimated_Completion_Date__c;
d.noDate = d.expectedDate == null ? true : false;
d.SOWLIId = SOWLI.id;
d.FulfillmentLink = 'coach-fulfillment?SOWLI='+SOWLI.id;
d.changeDateLink = 'update-estimated-completion-date?SOWLI='+SOWLI.id;
d.Description = SOWLI.description__c;
d.showECDate = SOWLI.Fulfillment_Type__c == 'Engagement Report' && d.isOpen ? True: False;
d.payRate = '$'+ String.format(SOWLI.Pay_Rate_Unit__c.format(),args);
string MapKey = SOW.College__c != null ? SOW.College__c : 'Training, Institutes & Retreats';
if(TimeFrame == 'Open'){
MapKey = SOW.Name + ' ' + MapKey;
d.acceptLink = 'review-assignment?SOW='+SOW.id+'&accept=Accepted';
d.declineLink = 'review-assignment?SOW='+SOW.id+'&accept=Rejected';
d.isReview = true;
} else {
MapKey += ' - ' + SOWLI.Year__c;
d.isReview = false;
}
if(deliverables.containskey(MapKey)){
deliverables.get(MapKey).add(d);
} else {
list<deliverable> Dlist = new list<deliverable>();
Dlist.add(d);
deliverables.put(MapKey,Dlist);
}
}
}
return Deliverables;
}
global static list<Statement_of_Work__c> getRecords(string TimeFrame){
String currentFiscalYear = [SELECT FiscalYearSettings.Name FROM Period WHERE Type = 'Year' AND StartDate <= TODAY AND EndDate >= TODAY].FiscalYearSettings.Name;
String SOWLIConditions = '';
User u = [SELECT Id, ContactId FROM User WHERE Id =: UserInfo.getUserId()];
//string CoachContactId = '0035500001P8zBGAAZ';
string CoachContactId = u.contactId;
system.debug(CoachContactId);
if(TimeFrame == 'Current'){
SOWLIConditions = ' Year__c = \'' + currentFiscalYear + '\' or Number_of_Work_Units_Remaining__c > 0 ';
} else if (TimeFrame == 'Open'){
SOWLIConditions = ' statement_of_work__r.status__c = \'Pending Execution\' ';
} else {
SOWLIConditions = ' Year__c < \'' + currentFiscalYear + '\'';
}
string SOWQuery = 'Select Id, Name, College__c, (Select Id, Name, Type__c, Estimated_Completion_Date__c, description__c, Number_of_Work_Units_Remaining__c, Pay_Rate_Unit__c, title__c, coach_deliverables__r.name, Year__c, Fulfillment_Type__c From SOW_Line_Items__r where '+ SOWLIConditions + ') from Statement_of_Work__c ';
SOWQuery += 'where Contractor_Contact__c = \'' + CoachContactId + '\' and ';
SOWQuery += 'id in (select statement_of_work__c from SOW_Line_Item__c where '+ SOWLIConditions + ')';
SOWQuery += ' and display_on_portal__c = TRUE and status__c = ';
if(TimeFrame != 'Open'){
SOWQuery += '\'Accepted\' ';
} else {
SOWQuery += '\'Pending Execution\' ';
}
SOWQuery +='order by Institution__r.name asc';
list<Statement_of_Work__c> SOWS = Database.query(SOWQuery);
system.debug(SOWQuery);
system.debug(SOWs);
return SOWS;
}
global class Deliverable{
@AuraEnabled
public string name;
@AuraEnabled
public string status;
@AuraEnabled
public date expectedDate;
@AuraEnabled
public string SOWLIId;
@AuraEnabled
public string fulfillmentLink;
@AuraEnabled
public string changeDateLink;
@AuraEnabled
public string description;
@AuraEnabled
public boolean isOpen;
@AuraEnabled
public boolean noDate;
@AuraEnabled
public string payRate;
@AuraEnabled
public string acceptLink;
@AuraEnabled
public string declineLink;
@AuraEnabled
public boolean isReview;
@AuraEnabled
public boolean showECDate;
}
}
Deliverable
class andgetDeliverables
method to include those link?