<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:taxo="http://purl.org/rss/1.0/modules/taxonomy/" version="2.0">
  <channel>
    <title>topic Re: Admin API token exchange on Node.js vs Python in ArcGIS REST APIs and Services Questions</title>
    <link>https://community.esri.com/t5/arcgis-rest-apis-and-services-questions/admin-api-token-exchange-on-node-js-vs-python/m-p/1178803#M4167</link>
    <description>&lt;P&gt;Thanks, I'll have a look at this!&lt;/P&gt;</description>
    <pubDate>Tue, 31 May 2022 21:24:19 GMT</pubDate>
    <dc:creator>JVig</dc:creator>
    <dc:date>2022-05-31T21:24:19Z</dc:date>
    <item>
      <title>Admin API token exchange on Node.js vs Python</title>
      <link>https://community.esri.com/t5/arcgis-rest-apis-and-services-questions/admin-api-token-exchange-on-node-js-vs-python/m-p/1176165#M4140</link>
      <description>&lt;P&gt;&lt;STRONG&gt;TL;DR: Why does Node.js have a different response to exchanging a token in the header vs Python when trying to reach an admin endpoint using a standalone ArcGIS for Server architecture?&lt;/STRONG&gt;&lt;BR /&gt;&lt;BR /&gt;Hello fellow GIS Devs! I've been building out a command line interface to help with some of my administrative tasks using ArcGIS Server 10.7.1 (NOT PORTAL just the standalone server) using node.js, as we plan on upgrading our system to Portal in the future. Because I am not using Portal, I believe the Oath2 workflows will not necessarily work for me. Now to my problem: for some reason in when using Node.js I run into an error regarding the clientID:&lt;/P&gt;&lt;LI-CODE lang="javascript"&gt;{
  status: 'error',
  messages: [ 'Invalid token, ClientID does not match.' ],
  code: 498
}&lt;/LI-CODE&gt;&lt;P&gt;I am using Axios to connect to the administration endpoint and using an interceptor to set the token as an Authorization header for the requests. I have verified the successful return of my token along with it being applied to the GET request at the &amp;lt;myarcserver&amp;gt;/arcgis/admin/services/&amp;lt;folder&amp;gt; endpoint. And yet, I still get the error above which appears to be an Oath2.0 error. Below is a snippet of my instance module along with the module calling it. Please don't make fun of me, I'm just starting to learn Node &lt;span class="lia-unicode-emoji" title=":grinning_face_with_smiling_eyes:"&gt;😄&lt;/span&gt;&lt;BR /&gt;&lt;BR /&gt;Instance snippet:&lt;/P&gt;&lt;LI-CODE lang="javascript"&gt;const baseURL = new URL(`${host}/arcgis/admin`).href;

    const headers = {
        'Content-Type': 'application/x-www-form-urlencoded',
        'Accept': 'application/json'
    };
    const payload = new URLSearchParams({
        username: process.env.GDS_USER,
        password: process.env.GDS_PASS,
        client: 'referer',
        referer: baseURL,
        f: 'json'
    });

    let token = null;

    const axiosInstance = axios.create({baseURL: baseURL});

    axiosInstance.interceptors.request.use(async config =&amp;gt; {
        if (!token) {
            const { data } = await axios({
                url: `${baseURL}/generateToken`,
                method: "post",
                data: payload,
                headers: headers
            })
            token = data.token;
        }

        config.headers.Authorization = `Bearer ${token}`;

        return config
    });&lt;/LI-CODE&gt;&lt;P&gt;&amp;nbsp;And here is the function that calls it when the command line command is invoked:&lt;/P&gt;&lt;LI-CODE lang="javascript"&gt;export const listServices = (folder, env) =&amp;gt; {
    const arc = arcServer(env);

    return arc({
        url: `/services/${folder}`,
        method: "get",
        params: {
            f: 'json',
        }
    })
    .then(response =&amp;gt; {
        console.log(response.data)
    })
    .catch(error =&amp;gt; {
        return Promise.reject(error)
    });
    

}&lt;/LI-CODE&gt;&lt;P&gt;And a screenshot of the response:&lt;/P&gt;&lt;P&gt;&lt;span class="lia-inline-image-display-wrapper lia-image-align-inline" image-alt="JVig_0-1653093331795.png" style="width: 400px;"&gt;&lt;img src="https://community.esri.com/t5/image/serverpage/image-id/41877i8600D485B39AE88F/image-size/medium?v=v2&amp;amp;px=400" role="button" title="JVig_0-1653093331795.png" alt="JVig_0-1653093331795.png" /&gt;&lt;/span&gt;&lt;/P&gt;&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;P&gt;Finally, I have written something similar to this in the past using python and have had zero issue connecting to it, even now.&lt;/P&gt;&lt;LI-CODE lang="python"&gt;def get_token(self):
        """
        Acquires the token necessary to access the administration endpoints. Tokens
        are limited to 600 seconds before expiration.
        """
        url = f'{self.server}:6443/arcgis/admin/generateToken'
        headers = {"Content-type": "application/x-www-form-urlencoded", "Accept": "text/plain"}

        params = {
            'username': self.user,
            'password': self.password,
            'client': 'referer',
            'referer': self.referer,
            'f': 'json'
        }

        r = self.session.post(url, data=params, headers=headers)

        if r.status_code == 200:
            response = json.loads(r.text)
            if response.get('token'):
                self.session.headers.update({'Authorization': f'Bearer {response["token"]}'})

                return response['token']
            else:
                if response.get('error'):
                    e = response['error']
                    raise ArcGISServerException('Generate token failed: {}'.format(e))
                else:
                    raise ArcGISServerException('Generate token failed')
        else:
            raise ArcGISServerException('Generate token failed, server response code: {}'.format(r.status_code))&lt;/LI-CODE&gt;&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;P&gt;So what's the difference here? Am I just a node amateur? Why is the admin services directory requesting a client ID when using one language, but not the other?&lt;BR /&gt;&lt;BR /&gt;As always, appreciate y'all's help. &lt;span class="lia-unicode-emoji" title=":red_heart:"&gt;❤️&lt;/span&gt;&lt;/P&gt;&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;P&gt;/Jason&lt;/P&gt;</description>
      <pubDate>Sat, 21 May 2022 00:42:11 GMT</pubDate>
      <guid>https://community.esri.com/t5/arcgis-rest-apis-and-services-questions/admin-api-token-exchange-on-node-js-vs-python/m-p/1176165#M4140</guid>
      <dc:creator>JVig</dc:creator>
      <dc:date>2022-05-21T00:42:11Z</dc:date>
    </item>
    <item>
      <title>Re: Admin API token exchange on Node.js vs Python</title>
      <link>https://community.esri.com/t5/arcgis-rest-apis-and-services-questions/admin-api-token-exchange-on-node-js-vs-python/m-p/1178492#M4157</link>
      <description>&lt;P&gt;Hi Jason,&lt;/P&gt;&lt;P&gt;I'm more a JS developer. I have never sent the token in the header, I have always send the token as another parameter.&lt;/P&gt;&lt;P&gt;It would help to see a copy of both CURL requests (removing the tokens/domains) to better understand what might be happening, but it doesn't make sense to me either.&lt;/P&gt;&lt;P&gt;I'm going to share a few resources that might help you with this:&lt;/P&gt;&lt;UL&gt;&lt;LI&gt;"Security and authentication &amp;gt; &lt;A href="https://developers.arcgis.com/documentation/mapping-apis-and-services/security/#capability-comparison" target="_self"&gt;Capability comparison&lt;/A&gt;" shows a summary table displaying differences between the different authentication methods&lt;/LI&gt;&lt;LI&gt;&lt;A href="https://developers.arcgis.com/arcgis-rest-js/authentication/" target="_self"&gt;ArcGIS REST JS -&amp;gt; Authentication&lt;/A&gt; this open source library aims to help JS developers to work with ArcGIS services (this is a &lt;A href="https://www.youtube.com/watch?v=0pIgQW8ssIw" target="_self"&gt;really good talk about it&lt;/A&gt;); I have noticed there is no example using username and password&lt;/LI&gt;&lt;LI&gt;&lt;A href="https://www.postman.com/arcgis-developer/workspace/arcgis-location-services" target="_self"&gt;ArcGIS Location Services Postman Workspace&lt;/A&gt;&amp;nbsp;&amp;lt;- This only contains examples for ArcGIS Online and Platform, but you can see how all requests send the token as a parameter.&lt;/LI&gt;&lt;/UL&gt;&lt;P&gt;I hope this helps&lt;/P&gt;&lt;P&gt;&amp;nbsp;&lt;/P&gt;&lt;P&gt;&amp;nbsp;&lt;/P&gt;</description>
      <pubDate>Tue, 31 May 2022 10:12:33 GMT</pubDate>
      <guid>https://community.esri.com/t5/arcgis-rest-apis-and-services-questions/admin-api-token-exchange-on-node-js-vs-python/m-p/1178492#M4157</guid>
      <dc:creator>Raul_Jimenez</dc:creator>
      <dc:date>2022-05-31T10:12:33Z</dc:date>
    </item>
    <item>
      <title>Re: Admin API token exchange on Node.js vs Python</title>
      <link>https://community.esri.com/t5/arcgis-rest-apis-and-services-questions/admin-api-token-exchange-on-node-js-vs-python/m-p/1178803#M4167</link>
      <description>&lt;P&gt;Thanks, I'll have a look at this!&lt;/P&gt;</description>
      <pubDate>Tue, 31 May 2022 21:24:19 GMT</pubDate>
      <guid>https://community.esri.com/t5/arcgis-rest-apis-and-services-questions/admin-api-token-exchange-on-node-js-vs-python/m-p/1178803#M4167</guid>
      <dc:creator>JVig</dc:creator>
      <dc:date>2022-05-31T21:24:19Z</dc:date>
    </item>
  </channel>
</rss>

