Tuesday, August 16, 2016

SOSL in Org with namespace or managed package

When we had some SOSL in managed package


An internal server error has occurred
An error has occurred while processing your request. The salesforce.com support team has been notified of the problem. If you believe you have additional information that may be of help in reproducing or correcting the error, please contact Salesforce Support. Please indicate the URL of the page you were requesting, any error id shown on this page as well as any other related information. We apologize for the inconvenience. 

Thank you again for your patience and assistance. And thanks for using salesforce.com! 

Error ID: 368384005-116910 (1415744368)

If you have namespace prefix for your org, the SOQL issued from APEX already have the prefix assigned e.g. below works just fine and doesn't throw any error

List<Account> accounts = [select id, name from Account limit 5];
List<logMessage__c> logs = [select id from logMessage__c limit 5];
System.debug( accounts );
System.debug( logs );

However, if you have namespace prefix for your org (or managed package), the SOSL issued from APEX doesn't have namespace prefix, e.g. below breaks

List<List<sObject>> soslResults1 = search.query('FIND \'Exception*\' IN ALL FIELDS RETURNING LogMessage__C(Id, name, message__c)');
List<List<sObject>> soslResults2 = [FIND 'Exception*' IN ALL FIELDS RETURNING LogMessage__C(Id, name, message__c)];
logMessage__c [] log1 = ((List<LogMessage__c>)soslResults1[0]);
logMessage__c [] log2 = ((List<LogMessage__c>)soslResults2[0]);
System.debug( log1 );
System.debug( log2 );



The fix would be to add prefix:

List<List<sObject>> soslResults1 = search.query('FIND \'Exception*\' IN ALL FIELDS RETURNING mynamespace__LogMessage__C(Id, name, message__c)');
List<List<sObject>> soslResults2 = [FIND 'Exception*' IN ALL FIELDS RETURNING mynamespace__LogMessage__C(Id, name, message__c)];
logMessage__c [] log1 = ((List<LogMessage__c>)soslResults1[0]);
logMessage__c [] log2 = ((List<LogMessage__c>)soslResults2[0]);
System.debug( log1 );
System.debug( log2 );



And of course, we can add the namespace prefix problematically, hence we don't need to hard code:

ApexClass cs =[select NamespacePrefix from ApexClass where Name = 'TestClass'];
String nameSpacePrefix = cs.NamespacePrefix;
if( nameSpacePrefix != null && nameSpacePrefix != '' ) {
    nameSpacePrefix += '__';
} else {
    nameSpacePrefix = '';
}