system.net.httpPost() throwing error while Postman is not

I’m having trouble using the system.net.httpPost() function to POST a message to an endpoint. I can use Postman and get the response I need but when I try to use httpPost() I get an error message {"error": "unsupported_grant_type"}.

I am wondering what I am doing differently in Postman vs Ignition that it doesn’t work.

Here is my script:

def getAccessToken():
	headers = {"Content-Type": "application/x-www-form-urlencoded","Accept": "*/*","Accept-Encoding": "gzip, deflate, br","Connection": "keep-alive"}
	
	body = {"grant_type": "refresh_token","refresh_token": getRefreshToken()}
	
	contentType = "application/x-www-form-urlencoded"
	
	url = getWebServicesRootUrl() + '/services/rest/auth/oauth2/v1/token'

	res = system.net.httpPost(url, 
				contentType = contentType, 
				postData = body, 
				username = getClientId(), 
				password = getClientSecret(), 
				headerValues = headers, 
				throwOnError = False
			)
	return res

Here is what the headers look like in Postman:
image

Here is what the body looks like in Postman:
image

Here is the Authorization in Postman (that corresponds to username and password in system.net.httpPost(), at least that is what I assumed…):

Here are Postman settings:

Any feedback will be greatly appreciated. I also tried using system.net.httpClient() but got the same response code.

Try using system.net.httpClient() instead. system.net.httpPost() doesn’t know how to encode that dictionary you provide for the body into x-www-form-urlencoded. Or do that encoding to the body yourself and pass the resulting string in as the body.

edit: actually not sure if system.net.httpClient() will do that encoding for you either.

1 Like

Hi Kevin,

Thanks for the quick response… That ended up being the issue.

Quick fix:

  1. Add import statement from urllib import urlencode.
  2. Call function urlencode() on body parameter.

Full function:

def getAccessToken():
	from urllib import urlencode
	headers = {"Content-Type": "application/x-www-form-urlencoded","Accept": "*/*","Accept-Encoding": "gzip, deflate, br","Connection": "keep-alive"}
	
	body = {"grant_type": "refresh_token","refresh_token": getRefreshToken()}
	
	contentType = "application/x-www-form-urlencoded"
	
	url = getWebServicesRootUrl() + '/services/rest/auth/oauth2/v1/token'

	res = system.net.httpPost(url, 
				contentType = contentType, 
				postData = urlencode(body), 
				username = getClientId(), 
				password = getClientSecret(), 
				headerValues = headers, 
				throwOnError = False
			)
	return res
1 Like

From my experience, it didn't. Thank you for your answer, that was the breakthrough I needed.

@Kevin.Herron I should probably open another thread, but I have one last question: I have a follow up HTTP POST that I need to make that has the Authorization type Bearer Token. Is there a way to use system.net.httpPost() to make this request? From the documentation, it isn't immediately clear that system.net.httpClient() would support it either, or that it would be any different than httpPost().

1 Like

I think the only way to make that work would be put all the appropriate headers in yourself.

@PGriffith that sound right?

Yeah, that’s correct. The JDK HttpClient only supports Basic auth for now (with some vague idea of future support for other auth types).

And better support for form encoding in POST submissions is a planned feature, but no timeline on that.

I had to import the urlencode function of the urllib library to encode the data being passed in. The get open cases method of the API was a little more straight forward (no explicit encoded required). Hence I was able to get this working.
Thanks Paul!

1 Like

OOPS! Wrong thread! :slight_smile: