Lightning Data Service - Get record value during Component Initialization in Controller

While working with "force:recordData" and if you want to get the values in the lightning controller you have to use the standard attribute of the "force:recordData" i.e; "recordUpdated". Please have a look at this sample code.

<force:recordData aura:id="recordLoader"
  recordId="{!v.recordId}"
  targetFields="{!v.simpleRecord}"
  targetError="{!v.recordError}"
  recordUpdated="{!c.handleRecordUpdated}"
  /> // in Component.

In controller

handleRecordUpdated: function(component, event, helper) {
    var eventParams = event.getParams();
    if(eventParams.changeType === "CHANGED") {
        // get the fields that changed for this record
        var changedFields = eventParams.changedFields;
        console.log('Fields that are changed: ' + JSON.stringify(changedFields));
        // record is changed, so refresh the component (or other component logic)
        var resultsToast = $A.get("e.force:showToast");
        resultsToast.setParams({
            "title": "Saved",
            "message": "The record was updated."
        });
        resultsToast.fire();

    } else if(eventParams.changeType === "LOADED") {
        console.log("account loaded:::::" + component.get("v.simpleRecord"));
        // record is loaded in the cache
    } else if(eventParams.changeType === "REMOVED") {
        // record is deleted and removed from the cache
    } else if(eventParams.changeType === "ERROR") {
        // there’s an error while loading, saving or deleting the record
    }
}

Hope this may help you.

Thanks Ram Agarawal


Any call to the server is inherently asynchronous: the browser issues a request to the network, the request traverses the network, the server processes the request and issues a response, the response traverses the network, and the client processes the response.

In contrast the component init event is fired synchronously when the component is created. This means you must plan for all server responses to not be available when init is fired.

Apex and Lightning Data Service (force:recordData) may trigger a server request; therefore, they are inherently asynchronous in how they provision data.

A declarative approach to handle this asynchronous behavior with force:recordData is to use <aura:if> to display separate UI for loading, error, and success states.

<aura:component implements="flexipage:availableForAllPageTypes,flexipage:availableForRecordHome,force:hasRecordId,force:lightningQuickActionWithoutHeader" access="global">

    <aura:attribute name="isOpen" type="boolean" default="false"/>
    <aura:attribute name="recordId" type="String"/>
    <aura:attribute name="targetFields" type="Object"/>
    <aura:attribute name="targetError" type="String"/>
    <aura:attribute name="curView" type="String" /> 
    <force:recordData aura:id="recordLoaderId"
                    layoutType="FULL"
                    recordId="{!v.recordId}"
                    targetError="{!v.targetError}"
                    targetFields="{!v.targetFields}"
                    mode="VIEW"
                    />
    <!-- LOADING -->
    <aura:if isTrue="{!and(empty(v.targetFields),empty(v.targetErrors))}">
        <!-- loading message --> 
    </aura:if>

    <!-- SUCCESS -->
    <aura:if isTrue="{!not(empty(v.targetFields))}">
        <div class="slds-text-body_regular slds-text-align_center">
            <lightning:formattedText title="text" value="{!v.targetFields.Name}" />
        </div>
    </aura:if>

    <!-- ERROR -->
    <aura:if isTrue="{!not(empty(v.targetError))}">
        <!-- show error -->
    </aura:if>
</aura:component>

If you require running logic when the record data is loaded, use the recordUpdated event. You still can use the <aura:if> approach above but augment the force:recordData tag and implement the handler, like:

    <force:recordData aura:id="recordLoaderId"
                    layoutType="FULL"
                    recordId="{!v.recordId}"
                    targetError="{!v.targetError}"
                    targetFields="{!v.targetFields}"
                    recordUpdated="{!c.recordUpdated}"
                    mode="VIEW"
                    />

And in your controller:

({
    recordUpdated: function(component, event, helper) {

    var changeType = event.getParams().changeType;
    if (changeType === "ERROR") { /* handle error; do this first! */ }
    else if (changeType === "LOADED") { /* handle record load */ }
    else if (changeType === "REMOVED") { /* handle record removal */ }
    else if (changeType === "CHANGED") { /* handle record change */ }
})