seplus
Contributor
Contributor

REST API call to get Bearer Token

Jump to solution

I connected vra8 as REST Host in vro.(with basic authentication)

And created action to get the Token. (this is on perm)

Getting an error as "Bad Request 400"

if(restHost)

{

   try{

        var url="/csp/gateway/am/api/login";

  

        var request = restHost.createRequest("POST",url);

       request.setHeader("Content-Type", "application/json");

       request.setHeader("Accept", 'application/json');

        System.log("Request url: "+ request.fullUrl);

        var requestResponse = request.execute();


        System.log("Request Response: "+ requestResponse.contentAsString);

        if(requestResponse.statusCode !=200){

             System.log("Bearer Token Request Failed with an error code"+requestResponse.statusCode);

             throw "Error: "+ requestResponse.statusCode;

            }


             var bearerToken = JSON.parse(requestResponse.contentAsString).cspAuthToken;

             System.log("Bearer Token: "+ bearerToken);

             return bearerToken;


  }

   catch(e)

  {

   System.log("An  error : "+e);

  }

}

else

{

   throw "No Rest Host Provided";

}

1 Solution

Accepted Solutions
stevedrummond
Hot Shot
Hot Shot

You cannot set the credential on the REST host connection as it doesn't know how to format the body and send it, or how to parse the result for the token and issue the token in all subsequent requests.

You need to do something like the following:

const body = { username: 'test user', password: 'mypassword', domain: 'mydomain.local' };

const request = restHost.createRequest('POST', '/csp/gateway/am/api/login', JSON.stringify(body));

const response = request.execute();

const accessToken = JSON.parse(response.contentAsString).cspAuthToken;

You will need then to include the accessToken in your auth header for all other requests to vRA 8.

View solution in original post

11 Replies
iiliev
VMware Employee
VMware Employee

I guess the problem is that you are not providing user credentials in the POST request body, which makes the request invalid.

Check the documentation (vRA Programming Guide) for info/examples what should be sent as request body for this particular API call.

seplus
Contributor
Contributor

Thank you for the reply.

The rest Host is already connected in the vRO invetory.

I am creating the request using that Host connection, do we need to pass username and password again for that request ?

0 Kudos
stevedrummond
Hot Shot
Hot Shot

You cannot set the credential on the REST host connection as it doesn't know how to format the body and send it, or how to parse the result for the token and issue the token in all subsequent requests.

You need to do something like the following:

const body = { username: 'test user', password: 'mypassword', domain: 'mydomain.local' };

const request = restHost.createRequest('POST', '/csp/gateway/am/api/login', JSON.stringify(body));

const response = request.execute();

const accessToken = JSON.parse(response.contentAsString).cspAuthToken;

You will need then to include the accessToken in your auth header for all other requests to vRA 8.

seplus
Contributor
Contributor

Thank you!!!

If I am publish this workflow as catalog, how can we give the requesting users credentials ?

Or do we need to save the one api user's user name and password with this workflow?

thanks

0 Kudos
stevedrummond
Hot Shot
Hot Shot

You have two options. "Per User" or "Shared Session"; normally the plug-in objects handle this for you, particularly useful for "Per User" as it passes through their credentials for you.

As you are having to auth "manually" you can either your workflow with a shared service account and if necessary track what user is performing the action in some way (either just the vRA request artifact or some other ledger). Alternatively the catalog item would need to prompt the user for the username/password, or perhaps the presentation layer has some mechanism to "pass through" (I haven't looked), and the workflow uses that data to retrieve an auth token on behalf of the user.

0 Kudos
seplus
Contributor
Contributor

Thanks for the reply.

Getting the current logged on User's auth token, and using that getting the access token is the best method.

So that the request will show under the requester.

trying to find out the method to get current login user's auth token.:smileycry:

0 Kudos
johnbowdre
Enthusiast
Enthusiast

Were you able to get this sorted? I'm struggling to understand how to get vRO8 to talk to vRA8's REST API without resorting to putting the plaintext credentials in the action script.

BrettK1
Enthusiast
Enthusiast

As someone who has never used REST at all, and now hearing that REST is the only way to accomplish some basic vRO - vRA communications, I'll second this question about plaintext credentials.  Having to include credentials at all in a vRO script already seems like a fail point, and using plain text would mean LOTS of bad things (it should be something more akin to a 'secret' in vRA, for security, re-usability, and ease of updating....) if every script with a password needed to be updated every time the password is changed (every year at a minimum), I see LOTS of failure points....

0 Kudos
Ankush11s
VMware Employee
VMware Employee

@BrettK1 I am not sure if you are aware of feature of configuration element and vRO plugin for vRA
on your 2 concerns

1. for vRA-vRO communication , you can use the vRA Plugin and you need to enter the credentials one time and no one can see and it is not in plain text.
Plugin has been in vRO and that is the way to communicate between these 2 products from legacy version .
2. Regarding the plain text password, There are multiple ways , you can use secrets type and you can use configuration element to map 
so if there is any change in password you do not need to change in every places , Just update in configuration element.

Note: Both suggestion has been in system from very long time atleast 4-5 years i can say there is no change in product on these 2 expects.

johnbowdre
Enthusiast
Enthusiast

I did eventually circle back around to this and figure out how to get a vRO action to authenticate against the vRA REST API without storing the creds in the action itself - by leveraging a configuration element like @Ankush11s mentioned.

I put together some notes on what I learned along the way in case they might help anyone else struggling to get started with the vRA API:

https://www.virtuallypotato.com/getting-started-vra-rest-api/ 

BrettK1
Enthusiast
Enthusiast

Thanks, I did as well, will just need to make sure to document this 1 more place to update when passwords expire.
This did require using a 'shared session' and not a 'per user' session (which I believe was the default when adding the vRA plugin?)

0 Kudos