What powers Fyle’s NetSuite Integration
Quick guide to understand how our open-source NetSuite Python SDK eases interacting with NetSuite's Web Services
Introduction
NetSuite is a cloud-based ERP solution that offers a suite of business management tools such as financials, CRM, and e-commerce. NetSuite's SuiteTalk API provides a web services interface to access NetSuite data and business processes.
Why does Fyle Integrate with NetSuite?
Spend management is a critical business function that relies heavily on accurate financial data, integrating Fyle with NetSuite makes perfect sense. Fyle can automatically sync the expenses to NetSuite, ensuring accurate and up-to-date financial records. This can help businesses make informed financial decisions based on accurate data and focus on growing their business rather than spending time on manual data entry and reconciliation.
What are the challenges that modern developers face while integrating with NetSuite?
NetSuite SuiteTalk Web Services requires developers to be proficient in SOAP protocol, which can be complex and requires extra effort to master. There is much more to it as compared to calling a simple REST API.
If you’re working with languages like python where generally you would rely on lists and dictionaries working with SOAP makes it a little hard.
The complexities bring maintenance overheads and also might increase quite a bit of time in your development cycles as onboarding new developers and knowledge transfer may become complicated.
Let’s check out how we would interface with NetSuite using python!
Interact with NetSuite using Python
Install the necessary dependencies
To use Python and Zeep to interact with NetSuite API, we'll need to install the following dependencies:
Python 3+
Zeep
requests
You can install these dependencies by running the following commands in your terminal:
$ pip install zeep
$ pip install requests
Setting up Authentication
To access the NetSuite SOAP API, you will need to provide authentication information. NetSuite uses OAuth 1.0a for authentication, which involves generating a signature based on a set of authentication parameters.
To generate the signature, we need the following information:
NetSuite account ID: This is a unique identifier for your NetSuite account.
Consumer key and secret: These are credentials provided by NetSuite that identify the application making the API request.
Token and secret: These are credentials provided by NetSuite that identify the user making the API request.
Once you have these credentials, you can generate a signature using the HMAC-SHA256 algorithm and generate a Token Passport.
import hmac
import hashlib
import base64
import time
import uuid
from zeep import Client
from zeep.exceptions import Fault
# NetSuite account information
NS_ACCOUNT_ID = '1234567_SB1'
CONSUMER_KEY = 'my_consumer_key'
CONSUMER_SECRET = 'my_consumer_secret'
TOKEN = 'my_token_id'
TOKEN_SECRET = 'my_token_secret'
def get_client_passport():
"""
Returns a client passport object containing authentication information for NetSuite web service API
"""
nonce = uuid.uuid4().hex
# Generate the current time in ISO 8601 format
current_time = str(int(time.time()))
base = '&'.join([NS_ACCOUNT_ID, CONSUMER_KEY, TOKEN, nonce, current_time])
key = '&'.join([CONSUMER_SECRET, TOKEN_SECRET])
digest = hmac.new(
str.encode(key),
msg=str.encode(base),
digestmod=hashlib.sha256
).digest()
signature = base64.b64encode(digest).decode()
client_pass = {
'account': NS_ACCOUNT_ID,
'consumerKey': CONSUMER_KEY,
'token': TOKEN,
'nonce': nonce,
'timestamp': current_time,
'signature': {
'_value_1': signature,
'algorithm': 'HMAC-SHA256'
}
}
return client_pass
Initiating the NetSuite Client
Once you have set up authentication, the next step is to create a service proxy. A service proxy is an object that represents the SOAP API endpoint and provides methods for interacting with it.
We will be using the zeep library to create the service proxy. Zeep is a fast and modern SOAP client library for Python that provides a simple and easy-to-use interface for working with SOAP web services.
def initialize_client():
"""
Returns a proxy object for NetSuite web service API using Zeep library
"""
client = Client(WSDL_URL)
# default service points to wrong data center. need to create a new service proxy and replace the default one
service_proxy = client.create_service(
'{urn:platform_2019_1.webservices.netsuite.com}NetSuiteBinding',
DATACENTER_URL
)
return service_proxy
Creating a Function to Search all Employee Records
Now that we have set up authentication and created a service proxy, we can use the NetSuite API to search for employee records.
To search for employee records, we first need to create an employee search object. We can do this using the get_type
method of the service proxy object returns the object type for a given NetSuite record.
Once we have created the employee search object, we can pass it to the search
method of the service proxy object. We also need to include the authentication information in the _soapheaders
parameter of the search
method.
The search method returns a response object that contains the results of the search. We can access the employee records by iterating over the searchRowList attribute of the response object.
def search_employee_records():
"""
Searches for employee records using NetSuite web service API
"""
service_proxy = initialize_client()
# Get the employee search object type
employee_search = service_proxy._client.get_type('ns34:EmployeeSearch')
# Make a search request to the web service API with the employee search object
try:
response = service_proxy.search(
searchRecord=employee_search(),
_soapheaders={"tokenPassport": get_client_passport()}
)
return response
except Fault as error:
print(error.message)
Finally, Search for Employees
if __name__ == '__main__':
employee_records = search_employee_records()
print(employee_records)
Overall, searching employee records in NetSuite using SOAP web services is complex and involves several steps. Developers need to have a strong understanding of NetSuite's web service API and the Zeep library to successfully implement this functionality. And, this was just the search functionality, figuring out all other operations can leave you like
What other options do we have?
Now coming to the original point of this blog post. What powers Fyle’s NetSuite Integration? The answer is very simple.
We have built our own open-source python SDK for NetSuite. It does all the heavy lifting and creates strong abstractions where the developers can easily access NetSuite and don't have to worry about all the rocket science that goes into interfacing with it.
Install the SDK
$ pip install netsuitesdk
Initialize and search for Employee Records
Now let's do the same Employee Search using Fyle’s NetSuite SDK
from netsuitesdk import NetSuiteConnection
# Initialize NetSuite connection with account and authentication information
netsuite = NetSuiteConnection(
account='my_netsuite_account_id',
consumer_key='my_consumer_key',
consumer_secret='my_consumer_secret',
token_key='my_token_key',
token_secret='my_token_secret'
)
# Retrieve all employee records from NetSuite
employee_records = netsuite.employees.get_all()
print(employee_records)
Yes! It’s as simple as that!!! 🙂
Not only search you can do any operations with utmost ease. Here are some examples!
# Use get_all methods to get all objects of certain types
currencies = netsuite.currencies.get_all()
locations = netsuite.locations.get_all()
departments = netsuite.departments.get_all()
classifications = netsuite.classifications.get_all()
# Just as easily you can do post operations
vendor_bill = {...}
netsuite.vendor_bills.post(vendor_bill)
expense_report = {...}
netsuite.expense_reports.post(expense_report)
journal_entry = {...}
netsuite.journal_entries.post(journal_entry)
vendor_payment = {...}
netsuite.vendor_payments.post(vendor_payment)
We’re openly accepting contributions and we’ve already received multiple contributions from folks outside Fyle. Our SDK is helping multiple businesses easily integrate with NetSuite.
Conclusion
In conclusion, integrating with NetSuite's API using Python can seem daunting at first, but it is a manageable process with the right tools and resources. The netsuitesdk
provides a convenient way to interact with NetSuite's API and can help developers get ahead of the huge learning curve while integrating with NetSuite.
Please check out GitHub Repository and you can reach out to me in case you have any doubts, suggestions, or intent to contribute! 😄
Hello, I want to retrieve the information from a saved search from netsuite. Could you give me an example?