I'm working on a canvas app which will allow an existing web app to be viewed through canvas.
I have the app working with Signed Request authentication, which works fine when permitted users is set to Admin approved users are pre-authorized
. I'm trying to implement the second flow, which occurs when the permitted users setting is set to All users may self-authorize
.
The documentation has the following to say:
If the user has previously approved the app and the access hasn’t been revoked or expired, Salesforce performs a POST to the canvas app with a signed request payload.
If the user hasn’t approved the app, or if the access has been revoked or expired, Salesforce performs a GET to the canvas app URL. The canvas app must handle the GET by accepting the call and looking for the URL parameter
_sfdc_canvas_authvalue
. If the canvas app receives this parameter value, the canvas app should initiate the approve or deny OAuth flow.
_sfdc_canvas_authvalue = user_approval_required
After the OAuth flow is initiated and the user approves the app, the canvas app should call the
repost()
method with a parameter of true to retrieve the signed request.
The server recieves the GET request with the correct URL parameter, and then redirects to a page which executes the following:
if (!Sfdc.canvas.oauth.loggedin()) {
var uri = Sfdc.canvas.oauth.loginUrl();
Sfdc.canvas.oauth.login(
{uri : uri,
params: {
response_type : 'token',
client_id: 'XXXXXXXXXXXXXXXXX',
redirect_uri : encodeURIComponent(
'https://localhost:1443/bower_components/SalesforceCanvasJavascriptSDK/callback.html')
}});
}
else {
Sfdc.canvas.client.repost();
}
The first half of this works as I expected: it detects that we're not logged in, and launches a popup which asks the user to allow access to the Salesforce org, with the connected app name displayed correctly.
Once the user clicks allow, the canvas page refreshes, and we're detected as logged in (and if I inspect Sfdc.canvas.oauth.token
there's an OAuth token in there now).
However, when the repost()
call is made, the page seems to simply refresh and we're back to our un-logged in state. No signed request is POSTed to the normal URL, which is what I expected to happen. The server just gets another GET request saying that the user needs to allow access again.
If I try to get the signed request straight to the javascript using Sfdc.canvas.client.refreshSignedRequest()
, the response comes back with a status of 403
.
None of the requests made when I call refreshSignedRequest()
or repost()
seem to include the OAuth token I see in Sfdc.canvas.oauth.token
, which suggests to me that perhaps I'm calling them incorrectly, or perhaps a cookie or header isn't being set somewhere where it should.
Poking into the source code of canvas-all.js
has left me none the wiser. There are some attributes called oauthToken
in the message body sent to the server which are hard-coded to "null"
. I've tried hard coding them to match the token in Sfdc.canvas.oauth.token
instead, but it didn't seem to make any difference.