19

Salesforce now allows Apex developers to invoke Asynchronous Callouts. This means that now, developers can initiate callouts from within Salesforce which can respond back in more than 2 minutes (governor limits) and assign a callback mechanism, to handle response for such callouts. The mechanism is called continuation, wherein all such asynchronous requests ...


10

Your request's Accept header is probably going out with the value of */* indicating that you can accept any type of response. This Content-Type header tells the remote endpoint that you're sending them a json request body - it does not indicate anything about the expected response body. req.setHeader('Content-Type', 'application/json'); Try specifying ...


9

You can't call out from a pre-release org, since the security rules are different from our production/developer environments.


9

RestContext.response.statusCode = 400; You can set any status code defined in RestResponse; simply set RestContext.response.statusCode to any value you'd like from the following list: 200 OK 201 CREATED 202 ACCEPTED 204 NO_CONTENT 206 PARTIAL_CONTENT 300 MULTIPLE_CHOICES 301 MOVED_PERMANENTLY 302 FOUND 304 NOT_MODIFIED 400 BAD_REQUEST 401 UNAUTHORIZED 403 ...


8

If the query in your insertFunction returns more than one Account then you wil be performing this sequence: Http request database update HttpRequest database update ... which as the error message reports is not allowed (because it would potentially leave an uncommitted transaction open for many seconds which is expensive for the platform). If you ...


6

Try changing the Content Type Header to req.setHeader('Content-Type', 'application/json'); ----Edit---- So I signed up to their service to see if I could figure it out...although it's no documented anywhere, try adding .json to the end of the endpoint. When I do that, it works for me... e.g. req.setEndpoint('http://www.carrierlookup.com/index.php/api/...


6

We can't increase the timeout more than 120 sec since that is the maximum limit. The only workaround is to modify the query on the external webservice application to respond within 120 secs. Its suggestible to test the HTTP url from any on the REST applications like POSTMAN before making a decision in salesforce.


5

The argument to HttpRequest.setTimout is a millisecond value so for 2 minutes: req.setTimeout(2 * 60 * 1000); PS With the clarification that the desire is to make the web service call after a 2 minute delay I suggest you experiment with this Need System.schedule cron string for run once approach. In your case you would build the cron string to be 2 minutes ...


5

Looking at the Partner WSDL, the soapAction for the login operation is the empty string. <operation name="login"> <soap:operation soapAction=""/> <!-- .... --> </operation> So you would think that it should be added to the request as such: HttpRequest req = new HttpRequest(); // ... req.setHeader('SOAPAction'...


5

You can use response.getHeader('Set-Cookie') to find the cookies set by the responding site. HttpRequest request1 = new HttpRequest(); request1.setMethod('GET'); request1.setEndpoint('http://www.google.com/'); HttpResponse response1 = new Http().send(request1); String cookies = getResponse.getHeader('Set-Cookie'); //semicolon-delimited keys and values ...


5

The content you are receiving is not Base64: it is Base64 inside JSON, which you are asking the server to provide to you. Base64 encoding uses the characters [A-Za-z0-9+/]. The backslash and quote characters shown here are not part of the Base64 encoding but the JSON wrapper around it. You need to deserialize the JSON first, into a String, and then Base64-...


4

If you separate the HTTP callout from the @future method, you can test them individually and get full coverage. make the @future method return void, use Test.startTest() and Test.stopTest() around its invocation in test (so it executes synchronously), use HttpCalloutMock (as you are) to cover the now-separate HTTP caller, Note that you won't receive an SMS ...


4

The previous answer I gave you assumed success, but for robustness, you can certainly iterate through all expected values. For example: Dom.Document doc = new Dom.Document(); doc.load(res.getBody()); Dom.XmlNode root = doc.getRootElement(); if(root.getName()=='rsp') { for(Dom.XmlNode node1: root.getChildElements()) { if(node1.getName()=='err') { ...


4

Using JSON2Apex (here), you can easily generate a class that you can use to deserialize your JSON. JSON2Apex outputs code like this: public class Outer { public List<Ideal> ideal; public List<Ideal> idealFiltered; public List<Ideal> InBudget; public class Ideal { public String product; public String ...


4

So, the response you are receiving is a JSON string. You can parse it like this: String json = response.getBody(); Map<String,Object> responseMap = (Map<String, Object>) JSON.deserializeUntyped(json); Then, you can access it like this: Map<String,Object> dataMap = (Map<String,Object>)responseMap.get('data'); String accountNumber = (...


4

Try it with JSON like: {"stock_prices":[{"code":"AAPL.US","timestamp":1569593940,"gmtoffset":0,"open":220.54,"high":220.96, "low":219.79,"close":220.24,"volume":3397713,"previousClose":219.89, "change":0.35,"change_p":0.159}]} Your code expects an object with a property "stock_prices" that is an array of objects. If that isn't what you want, and you need ...


3

This pattern where you explicitly update the RestContext allows you to set the status value: @HttpPost global static void doPost() { // Do stuff RestResponse res = RestContext.response; if (res == null) { res = new RestResponse(); RestContext.response = res; } // Return something res.responseBody = Blob.valueOf(...


3

A common cause is that the server is responding with a HTML page that contains error information rather than the JSON. Typically the status code in the response res.getStatusCode() would also be some value other than the 2xx success codes. While you could figure this out using debug logging, its worth putting in code to handle problems in the future too ...


3

the shell is interpreting characters in the URL as shell commands, and not part of the URL, you need to quote the URL string in your curl call, e.g. curl -X POST -H "Authorization: Bearer ..." "https://na1.salesforce...."


3

@Anshul provided an Amazing answer on how to handle callouts in async way. But still the question here is"The maximum callout time is 120,000 milliseconds" i.e You can't go beyond 2mins via any async method . Here now you would have to change the architecture of your application. The answer would be to split the transaction into two calls. The endpoint ...


3

Finally after analyzing the request sent by the browser and Hurl.it it seems that I was missing a header called Accept-Encoding whose value was 'gzip'. req.setHeader('Accept-Encoding', 'gzip'); Now it is returning the JSON response it was suppose to.


3

Blob headerValue = Blob.valueOf(username + ':' + password); String authorizationHeader = 'BASIC ' + EncodingUtil.base64Encode(headerValue); This code is not correct. The automatic "toString" method results in a different message than you expect: Blob b = Blob.valueOf('World'); System.debug('Hello '+ b); Output: 11:21:43.1 (2562345)|USER_DEBUG|[2]|DEBUG|...


3

If you use a HEAD request rather than a GET, the server will return all the headers associated with the URL (and so you can tell if it exists, content type etc), but won't return the body. so instead of req.setMethod('GET'); you'd do req.setMethod('HEAD');


3

Use VALUE_NULL token getText() Returns the textual representation of the current token or null if there's no current token. Since you explicitly were calling getText() without checking for null it will convert the null to a text value String jsonString = '{"next_page":null,"per_page":30,"page_count":22,"count":654}'; JSONParser parser = JSON....


3

Firstly, you don't need to print (v) a variable if you are using it inside an AMPscript block. You can change: set @ItemAssetCall = HTTPGet(v(@ItemAsset),true,1,@ItemAssetCallStatus) to: set @ItemAssetCall = HTTPGet(@ItemAsset,true,1,@ItemAssetCallStatus) To answer your question, I've tried requesting different status codes using HTTPGet to httpstat.us ...


3

When you use JSON.deserializeUntyped(data), you need to perform type casting to tell the Apex compiler what kind of object you're working with or you'll get errors because the type Object has no property baseVolume (e.g.). One way to accomplish this would be: for (Object obj : meta.keyset()){ Data d = (Map<String, Object>)meta.get(obj); ...


3

you can do SOQL query on Item__c filtering by ExternalID__c field. If result is not empty, then set statusCode to relevant one. You can find list of all status codes here. do not set RestContext.response.responseBody and use return at same time, as return result will be set as response body. If the method returns void, then Apex REST returns the ...


3

You have <retour> elements without a child <url> element, as for example <retour> <publication>20180917123004</publication> <production>20180917123004</production> <nature>21</nature> <statut>OK</statut> </retour> Your code iterates over all of the child nodes of your <flux&...


3

Simply put, you can't. While is trivial to build a service that returns, say, up to 50,000 rows, there's simply no mechanism for preserving a QueryLocator across Apex Code transactions, and with one exception (Visualforce), you can't query more than 50,000 rows per transaction (and even that limit is still only exactly 1,000,000, no more). The best you'd be ...


2

This is now listed as a known issue.


Only top voted, non community-wiki answers of a minimum length are eligible