2

This is, in some sense, a followup to this earlier question:

What is a protected custom setting record?

I got rid of the Apex class that held my config data. Instead, I created a Protected Custom Setting with the data.

This is the API name of the Custom Setting:

PrivateIncInfo__SameDayConfigurationModel__c

And this is the API name of the field:

PrivateIncInfo__xApiKey__c

So I assumed I could replace the old Apex class with the new Custom Setting:

        HttpRequest request = new HttpRequest();

        request.setBody(payLoad);
        request.setEndPoint(endpoint);
        request.setMethod('POST');
        request.setHeader('Accept', 'application/json');
        request.setHeader('Content-Type', 'application/json');
        request.setHeader('x-api-key', PrivateIncInfo__SameDayConfigurationModel__c.PrivateIncInfo__xApiKey__c);

But when I try to add this code to my Salesforce managed package, I get this error:

Failures - 1 PrivcoImportController: Method does not exist or incorrect signature: void setHeader(String, Schema.SObjectField) from the type System.HttpRequest

I defined PrivateIncInfo__xApiKey__c as a text box, and so I assume the value is a string. But apparently I'm not getting a string value when I call it? How do I fix this?

[ [ UPDATE ] ]

I'm sorry I was unclear. I have now tried calling the data like this.

I established that as a Protected Custom Setting, using List format. I'm not sure if that is correct.

This is part of a Managed Package.

I simply need to store an API key that works to access a 3rd party API.

I tried:

        PrivateIncInfo__SameDayConfigurationModel__c pcm;

        try {

                            List<PrivateIncInfo__SameDayConfigurationModel__c> lpcm = PrivateIncInfo__SameDayConfigurationModel__c.getall().values();
                            pcm = lpcm[0];


        request.setBody(payLoad);
        request.setEndPoint(endpoint);
        request.setMethod('POST');
        request.setHeader('Accept', 'application/json');
        request.setHeader('Content-Type', 'application/json');
        request.setHeader('x-api-key', pcm.PrivateIncInfo__xApiKey__c);
        request.setHeader('Authorization', ps.APIAuthorizationKey__c);

But I got an Exception. I was told the list was empty.

I also tried:

pcm = PrivateIncInfo__SameDayConfigurationModel__c.getInstance(); 

But when I do this, then pcm.PrivateIncInfo__xApiKey__c is null.

So what is the right answer?

This also comes says "Second argument can not be null."

        request.setHeader('Content-Type', 'application/json');
        request.setHeader('x-api-key', PrivateIncInfo__SameDayConfigurationModel__c.getOrgDefaults().PrivateIncInfo__xApiKey__c);
  • Have you populated the List custom setting in the clients org after installing the managed package? – Daniel Ballinger Jun 27 '17 at 19:44
  • I don't think I know what that means. I'm in my own developer org. I'm testing the managed package before I upload it. – LRK9 Jun 27 '17 at 19:48
2

You forgot to get the instance of your List. I am not sure what type of CS this is (List or Hierarchy) but one type of example is this. (This can change depending on how you chose to implement it)

PrivateIncInfo__SameDayConfigurationModel__c.getOrgDefaults().PrivateIncInfo__xApiKey__c

or

PrivateIncInfo__SameDayConfigurationModel__c.getValues().PrivateIncInfo__xApiKey__c

Please keep in mind that I haven't added any error handling code. You may want to wrap the function calls in a try-catch to ensure no errors are thrown if the user does not have an instance of the CS created in their org.

== Update ==

You have two options

a) (Better) Turn the Custom Setting into a Hierarchy one, and create an Org-Default record. The use the getOrgDefault() method above.

b) (Less Optimal). Leave it as a list. But create a record so you have something to query against.

You create records by clicking "Manage" next to the Custom Setting record and then using the GUI as you would use the standard SFDC GUI

In either case you must ensure that the application can handle the absence of a record, because you may not have one. In your managed package, in the "Post Install Script" ensure you create an OrgDefaults record (or a list record) so the client will have it when installing.

  • I updated my question. – LRK9 Jun 27 '17 at 19:42
  • Sebastian, I updated my code to use getOrgDefault(), but now I get "variable does not exist" – LRK9 Jun 27 '17 at 21:07
  • What do I need to do to establish one of these records as the Org Default? – LRK9 Jun 27 '17 at 21:08
  • You need to make sure your CS is of hierarchy type – Sebastian Kessel Jun 27 '17 at 21:28
1

See Access Custom Settings

Assuming it is a hierarchy custom setting you will need something like:

PrivateIncInfo__SameDayConfigurationModel__c settings = PrivateIncInfo__SameDayConfigurationModel__c.getInstance();
// TODO: check that the required setting is defined and returns an API Key.
request.setHeader('x-api-key', settings.PrivateIncInfo__xApiKey__c);

An important note form the docs:

If Privacy for a custom setting is Protected and the custom setting is contained in a managed package, the subscribing organization cannot edit the values or access them using Apex.

The code above must be part of your managed package. It won't be possible to access the protected custom setting outside that context.

  • I updated my question. – LRK9 Jun 27 '17 at 19:42
  • Daniel, I just wanted to point out that the privacy comment does not apply if the apex code using the CS is within the same namespace. – Sebastian Kessel Jun 27 '17 at 19:47

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.