I need to load a secured layer using an Esri token. In 3.X I did this:
const url = `${serviceUrl}?token=${esriToken}&f=json`
var featureLayer = new FeatureLayer({
url: url
});
It worked great and would load the secure feature service.
I do the exact same thing in 4.X, and I get the pop-up asking me to sign in. I double-checked the URL, and it provides the JSON, so that's not the issue.
What gives? I already signed in using OAuth2. That's how I got the token. I don't want to have to sign in again. Please help. Thanks!
Solved! Go to Solution.
We strip any URL parameters added to a layer URL to better manage params we need to use for queries and stuff. This is by design. The preferred way is IdentityManager for tokens, but you can use the requestInterceptors for this.
esriConfig.request.interceptors.push({
// set the `urls` property to the URL of the FeatureLayer so that this
// interceptor only applies to requests made to the FeatureLayer URL
urls: "https://services6.arcgis.com/ExtdhXSbhHKK7FFW/arcgis/rest/services/Related_Table_2/FeatureServer/0",
// use the BeforeInterceptorCallback to add token to query
before: function(params) {
params.requestOptions.query = params.requestOptions.query || {};
params.requestOptions.query.token = "my-token";
},
});
You can double check that its appended by checking the network request.
Hope that helps.
There are a couple of options, but if you simply want to append it to the URL, you can use the before() requestInterceptor
https://developers.arcgis.com/javascript/latest/api-reference/esri-config.html#RequestInterceptor
Hi @ReneRubalcava ,
Thanks for the quick response? Yes, I just want to append the token to the URL. Why do I need to use a `requstInterceptor`. Why can't I just append the token to the request as shown in this example? I didn't include the actual token, but you get the idea.
At any rate, that approach doesn't work. I tried looking at before() and I can't wrap my mind around how I would do that. Would you mind updating the example to show how that would work?
We strip any URL parameters added to a layer URL to better manage params we need to use for queries and stuff. This is by design. The preferred way is IdentityManager for tokens, but you can use the requestInterceptors for this.
esriConfig.request.interceptors.push({
// set the `urls` property to the URL of the FeatureLayer so that this
// interceptor only applies to requests made to the FeatureLayer URL
urls: "https://services6.arcgis.com/ExtdhXSbhHKK7FFW/arcgis/rest/services/Related_Table_2/FeatureServer/0",
// use the BeforeInterceptorCallback to add token to query
before: function(params) {
params.requestOptions.query = params.requestOptions.query || {};
params.requestOptions.query.token = "my-token";
},
});
You can double check that its appended by checking the network request.
Hope that helps.
This worked perfectly for me. Thanks @ReneRubalcava !
Are there parameters for Editing? I see your example shows Query Parameters but what about if I need to edit this?
Hi ,
I needed also to change in the security option the support for two options:
"allowHttpPostQueryParams"
"allowHttpGet"
under arcgis server admin -- > security --> tokens
Thank you, it really works and not only for a feature layer. Is it possible to do the same thing for array of layers or I should use this script for each needed layer separately?
Update: solved. I understood that
esriConfig.request.interceptors.push
means that interceptors is array so we can add several elements into it.
@ReneRubalcava Thanks for the reply. I used the same code as provide by you and replace the following:-
Now, my code looks like following:-
const featureLayerUrl = "https://services.slip.wa.gov.au/arcgis/rest/services/Landgate_v2_Subscription_Services/Cadastral/MapServer/35";
esriConfig.request.interceptors.push({
urls: featureLayerUrl,
before: function (params) {
params.requestOptions.query = params.requestOptions.query || {};
params.requestOptions.query.token = "nXKRnEHxxxxxxxxxxxxxxxXXXXxxxxxxxxxxxxxxx.";
},
});
const cadastreLayer = new FeatureLayer({
url: featureLayerUrl,
outfields: ["land_id"]
});
map.add(cadastreLayer);
But, it is still asking for the Username / Password on the page. Do you know what I'm missing? Thanks.
There is probably a request being made to the root of the service to check for capabilities. You can make the request interceptor url to the root of the server.
{
urls: "https://services.slip.wa.gov.au"
}