Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Generate Postman (pm) code snippets #644

Open
pythoninthegrass opened this issue Oct 18, 2022 · 0 comments
Open

Generate Postman (pm) code snippets #644

pythoninthegrass opened this issue Oct 18, 2022 · 0 comments
Labels

Comments

@pythoninthegrass
Copy link

Is your feature request related to a problem? Please describe.
The built-in pm runtime is sufficiently different than NodeJS and JS requests libraries that I spent more hours than I'd care to admit trying to map request to the pm.sendRequest method to create an OAuth2 pre-request script and gave up.

Describe the solution you'd like
It'd be lovely to generate working pre-request scripts from the GUI config options (e.g., POST OAuth2 token with basic auth), then store the results in the environment collection.

Currently at the mercy of API authors to build tests to do the latter (cf. OneLogin.)

Additional context
This works outside Postman:

// source .env file
const env = require('dotenv').config({path: `${__dirname}/.env`});

// read .env file
const auth_url = env.parsed.AUTH_URL;
const client_id = env.parsed.CLIENT_ID;
const client_secret = env.parsed.CLIENT_SECRET;
var expiration = env.parsed.TOKEN_EXPIRE * 1000;

if (!expiration) { expiration = 300000; }

var request = require('request');

// generate token
var options = {
  'method': 'POST',
  'url': auth_url,
  'headers': {
      'Content-Type': 'application/x-www-form-urlencoded',
      'Accept': 'application/json'
  },
  form: {
    'grant_type': 'client_credentials',
    'client_id': client_id,
    'client_secret': client_secret
  }
};

request(options, function (error, response) {
  if (error) throw new Error(error);

  var json = JSON.parse(response.body);
  var access_token = json.access_token;
  var refresh_token = json.refresh_token;

  console.log("access_token: " + access_token);
  console.log("refresh_token: " + refresh_token);
  console.log(`Access token expires in ${json.expires_in} seconds`)
});

Rewritten for pm.sendRequest:

const auth_url = pm.environment.get("auth_url");
const client_id = pm.environment.get("client_id_ro");
const client_secret = pm.environment.get("client_secret_ro");

// var access_token = pm.environment.get("access_token");
// var access_token_expiry = pm.environment.get("access_token_expiry");
// var refresh_token = pm.environment.get("refresh_token");
// var refresh_token_expiry = pm.environment.get("refresh_token_expiry");

// base64 encode client_id and client_secret
var enc = new Buffer.from(client_id + ':' + client_secret).toString('base64');
var auth = 'Basic ' + enc;

// generate token
var options = {
    'url': auth_url,
    'method': 'POST',
    'headers': {
      'Content-Type': 'application/json',
      'Authorization': auth
    },
    body: JSON.stringify({
      'grant_type': 'client_credentials'
    })
};
console.log(options);

pm.sendRequest(options, function (err, res) {
  var json = res.json();
  console.log(err ? err : json);

  if (err == null && json.error == null) {
    var access_token = json.access_token;
    var refresh_token = json.refresh_token;

    console.log("access_token: " + access_token);
    // console.log("refresh_token: " + refresh_token);
    // console.log(`Access token expires in ${json.expires_in} seconds`)

    pm.environment.set("access_token", access_token);
    pm.environment.set("refresh_token", refresh_token);

    pm.environment.set('access_token_expiry', new Date().getTime() + (json.expires_in * 1000));
    pm.environment.set('refresh_token_expiry', new Date().getTime() + (json.refresh_expires_in * 1000));
}
});

Running the latter would interpolate the environment variables correctly, encode the client creds, and yet, when tied to a downstream request, it would lose the context, submit a null basic auth variable, fail to carry over the content type, and raise a 400 error.

Just going to call the built-in OneLogin collection Generate Tokens POST with a first-party test script to fill out env vars for now.

Redacted console output


17:21:00.306
{url: "https://<SNIP>.onelogin.com/auth/oauth2/v2/token", method: "POST", headers: {…}…}
url: "https://<SNIP>.onelogin.com/auth/oauth2/v2/token"
method: "POST"
headers: {…}
Content-Type: "application/json"
Authorization: "Basic <SNIP>"
body: "{"grant_type":"client_credentials"}"
 
17:21:00.765
POST https://<SNIP>.onelogin.com/auth/oauth2/v2/token
400
444 ms
Network
Request Headers
Content-Type: text/plain
User-Agent: PostmanRuntime/7.29.2
Accept: */*
Cache-Control: no-cache
Postman-Token: e672ddc7-2b98-4f32-8814-578eef9cef00
Host: <SNIP>.onelogin.com
Accept-Encoding: gzip, deflate, br
Connection: keep-alive
Content-Length: 35
Cookie: ol_oapi_canary_13=false; sub_session_onelogin.com=<SNIP>
Request Body
{"grant_type":"client_credentials"}
Response Headers
cache-control: no-cache
content-type: application/json; charset=utf-8
date: Tue, 18 Oct 2022 22:21:00 GMT
status: 400 Bad Request
x-frame-options: SAMEORIGIN
x-request-id: 634F26CC-AC7F28F4-E590-0A0903B6-24E3-502662-46EF
x-runtime: 0.002652
x-xss-protection: 1; mode=block
transfer-encoding: chunked
strict-transport-security: max-age=63072000; includeSubDomains;
x-content-type-options: nosniff
Response Body
{"status":{"error":true,"code":400,"type":"bad request","message":"Content Type is not specified or specified incorrectly. Content-Type header must be set to application/json"}}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants