Download a Java Application to Connect to NetSuite OAuth TBA Restlet Endpoints

This article is relevant if you wish to connect to NetSuite RESTLET technology using token-based authentication (TBA) using Java as a client.

Background

In general, my team and I perform NetSuite REST and Web Services development using the Postman http test utility. However, we have found that Postman may have challenges with OAuth 1.0 backing NetSuite’s token-based authentication. Even when using Postman, you may find that even after knowing you have your credentials right, it still may be challenging to craft the HTTP oAuth 1.0 headers in the client programming environment.

As discussed in my article, Download a NetSuite OAuth Token Based Authentication Sample Node.js Program, I offered a way to connect and test your Token-Based Authentication client using Node.js. This article offers effectively the same solution but instead uses Java.

Addendum July 21, 2019 and June 17, 2022

The program required some maintenance from the original work.   In addition, NetSuite now requires SHA256 to connect.  We have updated the latest code for these signatures.

The article has been updated to reflect the latest efforts.

NetSuite Java Class to Connect to REST

Here is the Java Class that will connect up to a NetSuite RESTLet service. It leverages the utilities of the scribejava open source framework.  Below, I offer the source code.

package com.prolecto.sample.restlet.client;

import java.io.IOException;
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.net.http.HttpResponse.BodyHandlers;
import java.util.Map;
import java.util.Properties;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.github.scribejava.core.builder.ServiceBuilder;
import com.github.scribejava.core.builder.api.DefaultApi10a;
import com.github.scribejava.core.model.OAuth1AccessToken;
import com.github.scribejava.core.model.OAuth1RequestToken;
import com.github.scribejava.core.model.OAuthRequest;
import com.github.scribejava.core.model.Response;
import com.github.scribejava.core.model.Verb;

public class App {
	
	private static Logger log = LoggerFactory.getLogger(App.class);
	
    private final String CONSUMER_KEY;
	private final String CONSUMER_SECRET;
	private final String TOKEN_KEY;
	private final String TOKEN_SECRET;
	
	private final String ACCOUNT_ID;
	private final String RESTLET_URL;
	private final URI DOMAIN_URI; 
	
	private ObjectMapper mapper = new ObjectMapper();
	
	private HttpClient httpClient = HttpClient.newBuilder().build();
	
	public App() throws IOException {
		Properties nsProp = new Properties();
		nsProp.load(getClass().getClassLoader().getResourceAsStream("ns.properties"));
		
		CONSUMER_KEY = nsProp.getProperty("ns.consumerKey");
		CONSUMER_SECRET = nsProp.getProperty("ns.consumerSecret");
		TOKEN_KEY = nsProp.getProperty("ns.tokenKey");
		TOKEN_SECRET = nsProp.getProperty("ns.tokenSecret");
		ACCOUNT_ID = nsProp.getProperty("ns.accountId");
		RESTLET_URL = nsProp.getProperty("ns.restletUrl");
		
		DOMAIN_URI = URI.create("https://rest.netsuite.com/rest/datacenterurls?account=" + ACCOUNT_ID);
	}
	
	private Domains getDomains(String realm) throws Exception {
		HttpRequest request = HttpRequest.newBuilder().uri(DOMAIN_URI).build();
		HttpResponse<String> response = httpClient.send(request, BodyHandlers.ofString());
		return mapper.readValue(response.body(), Domains.class);
	}
	
	public static void main(String[] args) throws Exception {
		log.info("Test: NetSuite Token Based Authentication...");
		new App().doEcho();
		log.info("Test: Done!");
	}
	
	public String doEcho() throws Exception {
		String dataCenterRest = getDomains(ACCOUNT_ID).getRestDomain();
		log.debug("RestDataCenter: {}", dataCenterRest);
	    
	    try (var auth10aService = new ServiceBuilder(CONSUMER_KEY).apiSecret(CONSUMER_SECRET).build(new NSApi())) {
	    	OAuthRequest request = new OAuthRequest(Verb.POST, dataCenterRest + RESTLET_URL);
	    	request.setRealm(ACCOUNT_ID);
		    request.addHeader("Content-Type", "application/json");
		    request.setPayload(mapper.writeValueAsString(Map.of("greetings", "Hello World")));
		    log.debug("Request : {}", request.getStringPayload());

		    auth10aService.signRequest(new OAuth1AccessToken(TOKEN_KEY, TOKEN_SECRET), request);
		    Response response = auth10aService.execute(request);
		    log.debug("Response : {}", response.getBody());
		    
		    return response.getBody();
	    }
	}	
}

class NSApi extends DefaultApi10a {

	private static Logger log = LoggerFactory.getLogger(App.class);
	
	@Override
	public String getRequestTokenEndpoint() {
		log.debug("getRequestTokenEndpoint");
		return null;
	}

	@Override
	public String getAccessTokenEndpoint() {
		log.debug("getAccessTokenEndpoint");
		return null;
	}

	@Override
	public String getAuthorizationUrl(OAuth1RequestToken requestToken) {
		log.debug("getAuthorizationUrl: " +  requestToken.getRawResponse());
		return null;
	}

	@Override
	protected String getAuthorizationBaseUrl() {
		log.debug("getAuthorizationBaseUrl");
		return null;
	}	
}

class Domains {

	private String webservicesDomain;
	private String restDomain;
	private String systemDomain;

	public String getWebservicesDomain() {
		return webservicesDomain;
	}

	public void setWebservicesDomain(String webservicesDomain) {
		this.webservicesDomain = webservicesDomain;
	}

	public String getRestDomain() {
		return restDomain;
	}

	public void setRestDomain(String restDomain) {
		this.restDomain = restDomain;
	}

	public String getSystemDomain() {
		return systemDomain;
	}

	public void setSystemDomain(String systemDomain) {
		this.systemDomain = systemDomain;
	}
}

Download Java Client TBA Program to Connect to NetSuite REST Services

You can download this program here. To run the program, assuming you have Java 11 SDK installed, change to the base directory of the unzipped program and enter “gradlew run” (linux) or “gradlew.bat run”  (windows) to have the program compile and execute.  If you do not have the gradle framework on your machine, the software should first install and then you can run the program again.  See the related image for what it looks like to succeed.

Work with Fellow NetSuite Experts

My goal in this article was to help fellow NetSuite software developers lower the learning curve to more quickly become productive. If you have perused a number of our articles, you have found that we love inventing with the NetSuite platform. If you have passion for NetSuite as we do, perhaps you can join our team so we can help each other bring innovation to the community.

Be Sociable, Share!

Marty Zigman

Holding all three official certifications, Marty is regarded as the top NetSuite expert and leads a team of senior professionals at Prolecto Resources, Inc. He is a former Deloitte & Touche CPA and has held CTO roles. For over 30 years, Marty has produced leadership in ERP, CRM and eCommerce business systems. Contact Marty to set up a conversation.

More Posts - Website - Twitter - Facebook - LinkedIn - YouTube

| Category: NetSuite, Technical | 12 Comments

12 thoughts on “Download a Java Application to Connect to NetSuite OAuth TBA Restlet Endpoints

  1. Gabriel says:

    Two thumbs up! Thank you for code sharing.
    I wish NetSuite would be implementing OAuth 2.0, but according to enhancement requests, NetSuite is not considering this at present or in the near future.

  2. Robert Paul says:

    Looks the URL has changed, am trying to test your code and am getting below error.

    Test: NetSuite Token Based Authentication…
    PAYLOAD:
    {“message” : “Hello World”}
    RESULT:
    {“error” : {“code” : “INVALID_DATA_CENTER”, “message” : “Incorrect data center requested! The data center you are requesting is not the data center where your account is hosted. To obtain the correct URL for your request, please use the following endpoint: https://rest.netsuite.com/rest/datacenterurls?account=TSTDRV1030358. Then, send your original request to the correct data center.”}}
    Test: Done!

  3. Marty Zigman says:

    Indeed, it looks like the code needs some maintenance. We will look into it.

    Marty

  4. Rohan says:

    When i am using TBA with webservice integration it is working but when I use TBA with above code i am getting below message:
    error code: INVALID_LOGIN_ATTEMPT
    error message: Invalid login attempt.

    Can you please help me in solving this?

    Thanks in Advance!!

  5. Marty Zigman says:

    Hello Rohan,

    We see the issue. We will create a revised version and update the article. Standby. (Marty’s reference PTM3745)

    Marty

  6. Marty Zigman says:

    Hello Rohan,

    We finished the code maintenance and I have updated the article. Thanks for helping us out.

    Marty

  7. Marty Zigman says:

    Robert,

    The code should be working now. We have updated the article.

    Marty

  8. Sara Myers says:

    We were using scribe 1.3.7 in and Android eclipse project. This has version of scribe has stopped working for Android API 28. Do you know if there is a jar file for the newer version of scribe?

  9. voidle0917 says:

    Hello Marty,

    Does this work if I’m trying to connect using SHA256 signature

  10. Marty Zigman says:

    This Java applet will need to be updated to work with SHA256.

    Marty

  11. Logan says:

    Hello Marty,
    I am having the same issue connecting using the SHA256 signature. I know you mentioned the code being updated, just curious if it has been and if it has been if I could get a copy.
    Best, Logan

  12. Marty Zigman says:

    Hello Logan,

    We just updated the article and the latest build now connects with the SHA256 signature. Here is the reference to the code:
    https://blog.prolecto.com/wp-content/uploads/2022/06/java-restlet-client-20220422.zip

    Marty

Leave a Reply

Your email address will not be published. Required fields are marked *