Update: TradeMe has revoked my API access and is refusing to provide me with new credentials. Using it to make these blog posts was denied. As such I cannot check if this code still works. My apologies if it no longer works.
TradeMe has an excellent API that allows users to pull all sorts of data from their site, such as car or real estate listings. As a Python beginner, I was a bit intimidated by Python’s API and the authentication process. However, it turned out to be very easy to use with the help of Python’s “OAuth1Session” library.
Step 1: Register your program with TradeMe
All you need to do to get started is sign into TradeMe and fill out this form on their website: https://www.trademe.co.nz/MyTradeMe/Api/RegisterNewApplication.aspx
TradeMe got back to me within a couple days and approved my application. Once approved, you can see your consumer Key and Secret at: https://www.trademe.co.nz/MyTradeMe/Api/DeveloperOptions.aspx
Step 2: Authenticate yourself
In order to request information from TradeMe, you need to authenticate yourself so TradeMe knows who is asking for data. Although it may be tedious and has to be done manually, I found it easiest to authenticate myself using their web-page: https://developer.trademe.co.nz/api-overview/authentication/
Simply put in your consumer key and token, select “Production” for the environment (so you get data from the real TradeMe, rather than their fake sandbox site for testing purposes), and select the permissions you need. Generate your secret Key and Token and copy them into a Python script.
Keep your consumer and secret Key, Token, and Secrets private! Otherwise, anyone could impersonate you on TradeMe.
Step 3: Using Python to make requests
In order to request data from TradeMe, we need to make authenticated searches to their website. I am using the Python library “requests_oauthlib” to handle all the heavy lifting. TradeMe uses OAuth 1.0 to handle authentication. Since TradeMe uses OAuth1.0, we can use “OAuth1Session” from “requests_oauthlib”. We pass in our consumer key, token, and secrets into “OAuth1Session” and start making some requests!
Example search
I’m interested in buying a new car but don’t want to pay too much. I could manually comb through all of TradeMe’s car listings and get a general idea of the price of cars I’m interested in are. OR I could have Python do it for me and get the exact values of specific makes and models. Here’s example code which uses OAuth1Session to ask for all the current car listings on TradeMe in JSON format then stores them using Pandas. You can make your own TradeMe searches here: https://developer.trademe.co.nz/api-reference/search-methods/
#Import needed libraries from requests_oauthlib import OAuth1Session import time import json import pandas as pd # Keys (found on your TradeMe account page) consumerKey = 'yourConsumerKeyHereAsAString' consumerSecret = 'yourConsumerSecretHereAsAString' # Easy way to get these here: https://developer.trademe.co.nz/api-overview/authentication/ oAuthToken = 'yourTokenHereAsAString' oAuthSecret = 'yourSecretHereAsAString' # Use oAuth to authenticate ourselves with our keys and tokens tradeMe = OAuth1Session(consumerKey,consumerSecret,oAuthToken,oAuthSecret) # Tradme uses HTTP for get requests, meaning you ask for specific data by putting in a long URL searchCars = 'https://api.trademe.co.nz/v1/Search/Motors/Used.json?body_style=NotSpecified&condition=All&listed_as=All&listing_type=All&page=1&photo_size=Thumbnail&rows=500&shipping_method=All&sort_order=Default&transmission=NotSpecified HTTP/1.1' # Get the search page returnedPageAll = tradeMe.get(searchCars) # Parse the data dataRawAll = returnedPageAll.content parsedDataAll = json.loads(dataRawAll) # Total number of listings totalCount = parsedDataAll['TotalCount'] # TradeMe limits to 500 listings per request totalRequests = int(totalCount/500) # For all the requests it takes to get all the data for i in range(0,totalRequests+1): pageNum = str(i) # Set up search for each page searchAll ='https://api.trademe.co.nz/v1/Search/Motors/Used.json?body_style=NotSpecified&condition=All&listed_as=All&listing_type=All&page=' + pageNum + '&photo_size=Thumbnail&rows=500&shipping_method=All&sort_order=Default&transmission=NotSpecified HTTP/1.1' returnedPageAll = tradeMe.get(searchCars) dataRawAll = returnedPageAll.content parsedDataAll = json.loads(dataRawAll) # Get the Listings eachListingAll = parsedDataAll['List'] # Convert to Pandas pandaAll = pd.DataFrame.from_dict(eachListingAll) # Save data if i == 0: # If first search pandaAll.to_pickle('dataCars.pkl') else: # Append existing data # Load from storage pandaAllStorage = pd.read_pickle('dataCars.pkl') # Append storaged with new data pandaAllStorage = pandaAllStorage.append(pandaAll,ignore_index=True) # Save (will overwrite old stored data) pandaAllStorage.to_pickle('dataCars.pkl') time.sleep(0.5) print(i) print('done')
Jaryd Thornton
Hi there,
First off I would like to say that your blog fantastic and is very well written.
I’ve been attempting authentication to TradeMe’s Api using your steps. However it looks as though TradeMe has made changes in May-18 that no-longer support OAuth parameters sent in the URL (link below for reference) https://developer.trademe.co.nz/notifications/upcoming-oauth-changes/
TradeMe now need the OAuth parameters sent in a Header. I’ve attempted to do this but keep receiving a 403 status code. Would you be able to show us how to properly authenticate with a header for TradeMe?
Many thanks
Dr. Blake Porter
Hi Jaryd,
Sorry about that. TradeMe actually revoked my API access and has refused to grant me new credentials. Apparently collecting data for programming tutorials and blog posts like these are against their terms of service. They did this before the API changed over so I have not done anything else in terms of TradeMe API, including their new OAuth changes. Off the top of my head I don’t know the correct way to implement the changes you linked. Sorry I can’t be of my help :/
Cheers,
Blake
Miah Stewart
I’ve successfully managed to authenticate (generate an access token) and receive data from the api using raw HTTP requests. I was having trouble initially when I was using requests_oauthlib
I used this as a guide: https://developer.trademe.co.nz/api-overview/authentication/example-plaintext-workflow/
My steps were:
1.
curl \
–header ‘Authorization: OAuth oauth_consumer_key=”xxx”, oauth_callback=”oob”, oauth_signature_method=”PLAINTEXT”, oauth_signature=”xxx%26″‘ \
“https://secure.tmsandbox.co.nz/Oauth/RequestToken?scope=MyTradeMeRead,MyTradeMeWrite”
You will receive a response like this:
oauth_token=xxx&oauth_token_secret=xxx&oauth_callback_confirmed=true%
2.
Then you feed in the oauth_token from the previous step like this:
https://secure.tmsandbox.co.nz/Oauth/Authorize?oauth_token=xxx
And enter that link into a browser.
You will receive a verification number which you will use as oauth_verifier in the next step.
3.
Run:
curl \
–header ‘Authorization: OAuth oauth_verifier=”xxx”, oauth_consumer_key=”xxx”, oauth_token=”xxx”, oauth_signature_method=”PLAINTEXT”, oauth_signature=”xxx%26xxx”‘ “https://secure.tmsandbox.co.nz/Oauth/AccessToken”
Note that oauth_signature is a combination of two tokens (oauth_token_secret from step 1 and consumer_secret)
You will be returned something like this:
oauth_token=xxx&oauth_token_secret=xxx%
You can use these now to call the api
4.
Call the api like so to view your watchlist items (add something to watchlist to test):
curl \
–header ‘Authorization: OAuth oauth_consumer_key=xxx, oauth_token=xxx, oauth_signature_method=PLAINTEXT, oauth_signature=xxx%26xxx “https://api.tmsandbox.co.nz/v1/MyTradeMe/Watchlist/All.xml.”
Hope this helps!
Raj
Way to call Trademe API using authentication header
trade_access = OAuth1(customerKey, customerSecret, oauthToken, oauthSecret)
Mywatchlist = “https://api.tmsandbox.co.nz/v1/MyTradeMe/Watchlist/all.json”
trademe_Response = requests.get(Mywatchlist, auth=trade_access)
print(trademe_Response.status_code)
pprint(trademe_Response.json())