10

We have a rats nest of classes. Some are with sharing, some are without sharing, and some have no declarations.

Salesforce relatively recently introduced "inherited sharing"

How is this different from not having sharing declared on the class?

What happens when a class is declared as "inherited sharing" but is called from a class which never had sharing declared?

3 Answers 3

23

When inherited sharing is used, it means that it will inherit the sharing settings of the caller class.

  • If a class with without sharing is calling the method of class with inherited sharing, then it will run in without sharing mode.
  • If a class with with sharing is calling the method of class with inherited sharing, then it will run in with sharing mode.
  • If a class with omitted sharing (i.e. no sharing is mentioned) is calling the method of class with inherited sharing, then it will run in without sharing mode as the default sharing mode of the omitted sharing is to run in without sharing mode (This is because the calling class is established as a without sharing context). A class declared as inherited sharing runs as without sharing only when explicitly called from an already established without sharing context.
  • If a class with with sharing is calling a method of class with omitted sharing which in turn calls a method of class with inherited sharing, then it will run in with sharing mode, as the calling class is in with sharing mode and omitted class is established as with sharing context.
  • If a class with without sharing is calling a method of class with omitted sharing which in turn calls a method of class with inherited sharing, then it will run in without sharing mode, as the calling class is in without sharing mode and the omitted class is established as without sharing context.
  • If the class is used as the entry point to an Apex transaction, an omitted sharing declaration runs as without sharing.
  • If the class is used as the entry point to an Apex transaction, inherited sharing ensures that the default is to run as with sharing.

Excerpt from the salesforce documentation, Using the with sharing, without sharing, and inherited sharing Keywords

There is a distinct difference between an Apex class that is marked with inherited sharing and one with an omitted sharing declaration. If the class is used as the entry point to an Apex transaction, an omitted sharing declaration runs as without sharing. However, inherited sharing ensures that the default is to run as with sharing. A class declared as inherited sharing runs as without sharing only when explicitly called from an already established without sharing context.

Hope answers for both your questions are covered in the above explanation.

6
  • Great answer! Using bullet points really helps me visualize this in a way that the block of quoted text failed to. Just one point to clarify, what do we mean by "established"? Let's say a class without sharing invokes a class with omitted sharing which then invokes a class with inherited sharing. In this instance, is it a correct understanding that the "without sharing" has established the middle class as also "without sharing"? And the same would be for any number of inherited or omitted sharing between the without and the inherited? Commented Jun 4, 2019 at 7:42
  • Hey @BrianKessler, I updated the answers for your question, made changes in few points in the answer and added couple of points regarding your question in the comments. Commented Jun 4, 2019 at 10:44
  • Corrected a mistake where I said that inherited sharing class will run in with sharing context when called from omitted sharing class, whereas it will run in without sharing context. (Verified it after few tests in dev org) Commented Jun 4, 2019 at 10:46
  • Cheers for further expanding on your already great answer! That said, as clear as the bullet points make things, I'm starting to feel like I really need a table, if StackExchange supports this, :-) Commented Jun 4, 2019 at 14:26
  • Hi @Vijay Ganji, regarding you comment, I must say that is not completly true, inherited sharing class can run in both, with sharin and without sharing, when called from omitted sharing class, depending on if this omitted sharing class ( which is, inherithed sharing too ) is running as with sharing or without sharing. If you have a with sharing class, that calls an omitted sharing class, that calls an inherited sharing class, this last one will be executed as with sharing. This is at least true, when the context of execution is not Trigger context. Commented Jun 29, 2020 at 11:24
7

If you can refer salesforce docs then you observed the difference between inherited sharing and no sharing. Excerpt from salesforce docs:

There is a distinct difference between an Apex class that is marked with inherited sharing and one with an omitted sharing declaration. If the class is used as the entry point to an Apex transaction, an omitted sharing declaration runs as without sharing. However, inherited sharing ensures that the default is to run as with sharing. A class declared as inherited sharing runs as without sharing only when explicitly called from an already established without sharing context.

Please refer below link for more details:

https://developer.salesforce.com/docs/atlas.en-us.apexcode.meta/apexcode/apex_classes_keywords_sharing.htm

0

In addition to the answers, the omitted sharing class behaves as with sharing when it is called from the Lightning Web component. I have tried and tested this with the below code.

public class DefaultSharing {
    @AuraEnabled(cacheable=true)
    public static List<Application__c> getApplications() {
        return [SELECT Name, Owner.Name FROM Application__c];
    }
}
import { LightningElement, wire } from "lwc";
import getApplicationsDefaultSharing from "@salesforce/apex/DefaultSharing.getApplications";

//...
export default class ApexSharingDemo extends LightningElement {

    appsDefaultSharing = [];

    @wire(getApplicationsDefaultSharing, {})
    getApplicationsDefaultSharing({ error, data }) {
        if (error) {
            console.log("Error getting data", error);
        } else if (data) {
            this.appsDefaultSharing = [...data];
        }
    }
}

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .