+ Start a Discussion
Ross GoldbergRoss Goldberg 

force:hasRecordId interface doesn't return recordId attribute in Winter '18

In Winter '18 we are not able to retrieve the recordId via the force:hasRecordId interface.  Has anyone else experienced issues with this interface in their Lightning components?  If so, do you know of any workaround?

Thanks,
Ross
Alain CabonAlain Cabon
Hi,

That would be a big issue. You also need  <aura:attribute name="recordId" type="String"/>   in the components.

Could you post your controller and component and try the little lex component below on a record page?
 
<aura:component implements="flexipage:availableForRecordHome,force:hasRecordId,force:hasSObjectName" access="global" >
    <aura:attribute name="recordId" type="String"/>
    <aura:attribute name="sObjectName" type="String" />
    <b>This is recordID {!v.recordId} </b><br/>
    <b>This is SObjectName {!v.sObjectName} </b><br/>
</aura:component>
Ross GoldbergRoss Goldberg
Alain,

Thanks for your reply.  According to the documentation (https://developer.salesforce.com/docs/atlas.en-us.lightning.meta/lightning/ref_interfaces_force_hasrecordid.htm" target="_blank) we should not have to set this attribute in the component:
If your component implements force:hasRecordId, you don’t need to add a recordId attribute to the component yourself. If you do add it, don’t change the access level or type of the attribute or the component will cause a runtime error.
Do you know if this has changed for Winter '18?

Here is the code I am using that reproduces the error (based on your example):
<aura:component implements="force:lightningQuickAction,force:hasRecordId,force:hasSObjectName" access="global" >
    <aura:attribute name="recordId" type="String"/>
    <aura:attribute name="sObjectName" type="String" />
    <b>This is recordID {!v.recordId} </b><br/>
    <b>This is SObjectName {!v.sObjectName} </b><br/>
</aura:component>
This produces the following output:

Generated Output

Thanks,
Ross
Alain CabonAlain Cabon
Without  force:appHostable  that still works for me so you need flexipage:availableForRecordHome

User-added image

What is your result with ?

force:lightningQuickAction,force:hasRecordId +  flexipage:availableForRecordHome

Regards
Ross GoldbergRoss Goldberg
Alain,

After adding these interfaces I still get the same result from my quick action (no record id) :-(  The interfaces I have now implemented are:

flexipage:availableForRecordHome,force:lightningQuickAction,force:hasRecordId,force:hasSObjectName,force:appHostable

I was thinking this might be an org issue, but I can reproduce in more than one org.  Strange.

Thanks,
Ross
Alain CabonAlain Cabon
Adding <aura:attribute name="recordId" type="String" /> is not a good practice finally (possible but useless) and that works also without it, version 41.

force:hasRecordId
Useful for components invoked in a context associated with a specific record, such as record page components or custom object actions. Add this interface if you want your component to receive the ID of the currently displaying record.
The force:hasRecordId interface does two things to a component that implements it.
It adds an attribute named recordId to your component. This attribute is of type String, and its value is an 18-character Salesforce record ID, for example: 001xx000003DGSWAA4.

If you added it yourself, the attribute definition would look like the following markup:
<aura:attribute name="recordId" type="String" />

If your component implements force:hasRecordId, you don’t need to add a recordId attribute to the component yourself. If you do add it, don’t change the access level or type of the attribute or the component will cause a runtime error.

The recordId attribute is set only when you place or invoke the component in an explicit record context. For example, when you place the component directly on a record page layout, or invoke it as an object-specific action from a record page or object home. In all other cases, such as when you invoke the component as a global action, or create the component programmatically inside another componentrecordId isn’t set, and your component shouldn’t depend on it.


Without <aura:attribute name="recordId" type="String" />, that also works.
<aura:component implements="force:lightningQuickAction,force:hasRecordId,force:appHostable,flexipage:availableForRecordHome,force:hasRecordId,force:hasSObjectName" access="global" >
    <!-- aura:attribute name="recordId" type="String"/ -->
    <aura:attribute name="sObjectName" type="String" />
    <aura:handler name="init" value="{!this}" action="{!c.doInit}"/>
    <b>This is recordID {!v.recordId} </b><br/>
    <b>This is myRecordID {!v.myRecordID} </b><br/>
    <b>This is SObjectName {!v.sObjectName} </b><br/>
</aura:component>

https://developer.salesforce.com/docs/atlas.en-us.lightning.meta/lightning/components_config_for_app_builder_record_home.htm

 
Ross GoldbergRoss Goldberg
Interesting.  In Summer '17 we were able to define a global action, and when added to a record page layout the recordId value was passed to our component.  In Winter '18 this no longer works and it seems we must instead define the action at the object level (I have confirmed that works).

This seems to be a change in how the platform functions, but as you note above the documentation does state outside a record context the recordId would not be passed.  This makes sense, except we are adding the global action to our record page layout the same as we would if we define the action at the object level.

For us, it makes more sense to define a global action since our component is designed to work with any object type.  This makes configuration simpler, since we only need to define the action once and then add to any page layout to pass the recordId.  Now, with Winter '18, this no longer works.  Reading the documentation, I guess it can be interpreted either way -- outside a page layout context a global action wouldn't pass the recordId, but when a global action is added to a page layout it inherits the context of the page layout.  At least, that was my understanding :-)

Thanks again for your assistance!  For now we will convert our instructions to require a new action for each object where the component is to be added.  In the future, perhaps, the global action will once again support this interface.

Ross
 
Alain CabonAlain Cabon
Interesting because I didn't test the global actions.

We can expect new answers for new workarounds here (perhaps).

Lex is still a new technology (many beta features for the components above all).

Before Spring 17', using Lex components was highly risky and it's easy to be surprised by these reversals.

For big developements this lack of stability could be a problem so we are still reluctants to use the Lex components (it lacks the component Lookup and a good component for the picklists). The components of the Visualforce page are still easiest and stable.
John Francis ValondaJohn Francis Valonda
This should be working in record/ detail page.
MANJOT SINGH 7MANJOT SINGH 7
I was also facing same problem. So i have posted an idea on success community. You can upvote it..
https://success.salesforce.com/ideaView?id=0873A000000TuumQAC
Nithun GangulaNithun Gangula
I am having issue to get the RecordId from TASK Record Page, while I can get the value from other object Record pages. I am using QuickAction on Record Page  that  calls a component, which implements following interfaces: force:appHostable,flexipage:availableForRecordHome,flexipage:availableForAllPageTypes,force:lightningQuickActionWithoutHeader,force:hasRecordId,force:hasSObjectName. Anyone seen this issue ?
Nithun GangulaNithun Gangula
Issue only seems to be with Task record Page using QuickAction calling component that has force:recordId, If I drag the component on the record page, it works as expected. <bummer/>
Sharif Elkassed 9Sharif Elkassed 9

I know this is an old thread, but I thought I would add my experience with this issue:

I am using force:hasRecordId without declaring a recordId attribute.

Initially, the recordId was not being captured.

I then realized that I was using component.find("v.recordId") instead of component.get("v.recordId")

Hope this heps someone!

Suraj Tripathi 47Suraj Tripathi 47
Hi Ross,

Greetings!

force:hasRecordId return the record id of the current detail page.
By using {!v.recordId} in the lightning component.

If you find your Solution then mark this as the best answer. 

Thank you!

Regards,
Suraj Tripathi