Overview
This guide will walk you through the process of making your first successful API call to the GetBill External API. By the end of this tutorial, you’ll have retrieved your company profile information.
Prerequisites
Before you start, make sure you have:
A GetBill account with API access enabled
Created an OAuth client in your dashboard
Your Client ID and Client Secret ready
Keep your Client Secret secure and never expose it in client-side code or public repositories.
Step 1: Obtain an Access Token
First, you need to get an OAuth 2.0 access token. We’ll use the Client Credentials grant type for this example.
curl -X POST https://getbill.io/oauth/token \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "grant_type=client_credentials" \
-d "client_id=YOUR_CLIENT_ID" \
-d "client_secret=YOUR_CLIENT_SECRET" \
-d "scope=company:read debts:read"
const clientId = 'YOUR_CLIENT_ID' ;
const clientSecret = 'YOUR_CLIENT_SECRET' ;
const response = await fetch ( 'https://getbill.io/oauth/token' , {
method: 'POST' ,
headers: {
'Content-Type' : 'application/x-www-form-urlencoded' ,
},
body: new URLSearchParams ({
grant_type: 'client_credentials' ,
client_id: clientId ,
client_secret: clientSecret ,
scope: 'company:read debts:read'
})
});
const tokenData = await response . json ();
const accessToken = tokenData . access_token ;
import requests
client_id = 'YOUR_CLIENT_ID'
client_secret = 'YOUR_CLIENT_SECRET'
token_data = {
'grant_type' : 'client_credentials' ,
'client_id' : client_id,
'client_secret' : client_secret,
'scope' : 'company:read debts:read'
}
response = requests.post(
'https://getbill.io/oauth/token' ,
data = token_data
)
token_response = response.json()
access_token = token_response[ 'access_token' ]
Expected Response
{
"access_token" : "xxx.yyy.zzz" ,
"token_type" : "Bearer" ,
"expires_in" : 3600 ,
"refresh_token" : "def50200..." ,
"scope" : "company:read debts:read"
}
Save the access_token - you’ll need it for all subsequent API calls. Tokens expire after 1 hour.
Step 2: Make Your First API Call
Now that you have an access token, let’s retrieve your company profile:
curl -X GET https://getbill.io/external-api/v1/company/profile \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN" \
-H "Content-Type: application/json"
const response = await fetch ( 'https://getbill.io/external-api/v1/company/profile' , {
method: 'GET' ,
headers: {
'Authorization' : `Bearer ${ accessToken } ` ,
'Content-Type' : 'application/json'
}
});
if ( ! response . ok ) {
throw new Error ( `HTTP error! status: ${ response . status } ` );
}
const companyProfile = await response . json ();
console . log ( 'Company Profile:' , companyProfile );
headers = {
'Authorization' : f 'Bearer { access_token } ' ,
'Content-Type' : 'application/json'
}
response = requests.get(
'https://getbill.io/external-api/v1/company/profile' ,
headers = headers
)
if response.status_code == 200 :
company_profile = response.json()
print ( 'Company Profile:' , company_profile)
else :
print ( f 'Error: { response.status_code } ' )
print (response.text)
Expected Response
{
"error" : false ,
"message" : "Success" ,
"data" : {
"id" : "hTBN7n6lkmkhMb6LYqEBZw" ,
"name" : "Your Company Name" ,
"email" : "contact@yourcompany.com" ,
"phone" : "+33123456789" ,
"created_at" : "2023-01-15T10:30:00+00:00"
}
}
To get additional company statistics like debt counts and user counts, use the Get Company Statistics endpoint.
Step 3: Understanding the Response
Let’s break down what you received:
Indicates if the request was successful (false) or failed (true)
Human-readable message about the request result
The actual data you requested - in this case, your company profile
Step 4: Error Handling
Always implement proper error handling:
async function getCompanyProfile ( accessToken ) {
try {
const response = await fetch ( 'https://getbill.io/external-api/v1/company/profile' , {
method: 'GET' ,
headers: {
'Authorization' : `Bearer ${ accessToken } ` ,
'Content-Type' : 'application/json'
}
});
if ( ! response . ok ) {
const error = await response . json ();
if ( response . status === 401 ) {
console . error ( 'Authentication failed:' , error . message );
// Refresh token or re-authenticate
} else if ( response . status === 403 ) {
console . error ( 'Insufficient permissions:' , error . message );
// Check your OAuth scopes
} else {
console . error ( 'API error:' , error . message );
}
throw new Error ( error . message );
}
return await response . json ();
} catch ( error ) {
console . error ( 'Network error:' , error );
throw error ;
}
}
def get_company_profile ( access_token ):
headers = {
'Authorization' : f 'Bearer { access_token } ' ,
'Content-Type' : 'application/json'
}
try :
response = requests.get(
'https://getbill.io/external-api/v1/company/profile' ,
headers = headers,
timeout = 30
)
if response.status_code == 200 :
return response.json()
elif response.status_code == 401 :
print ( 'Authentication failed - check your token' )
elif response.status_code == 403 :
print ( 'Insufficient permissions - check your scopes' )
else :
print ( f 'API error: { response.status_code } ' )
print (response.text)
response.raise_for_status()
except requests.RequestException as e:
print ( f 'Network error: { e } ' )
raise
Step 5: Next Steps
Congratulations! You’ve successfully made your first API call. Here’s what you can do next:
List Your Debts Try retrieving your debt collection portfolio: curl -X GET "https://getbill.io/external-api/v1/debts?limit=10" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN"
Get Statistics Fetch company statistics and analytics: curl -X GET "https://getbill.io/external-api/v1/company/statistics" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN"
Create a Debt Add a new debt to your system: curl -X POST "https://getbill.io/external-api/v1/debts" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN" \
-H "Content-Type: application/json" \
-d '{"firstname":"John","lastname":"Doe",...}'
Explore Documentation Browse the complete API reference to discover all available endpoints and features.
Common Issues and Solutions
Problem : Your access token is invalid or expired.Solution :
Check that you’re including the token in the Authorization header
Ensure the token format is Bearer YOUR_TOKEN
If expired, obtain a new token using your refresh token
Problem : Your token doesn’t have the required scopes.Solution :
Check the endpoint documentation for required scopes
Request a new token with the appropriate scopes
Verify your OAuth client has permission for those scopes
Problem : You’ve hit the rate limit.Solution :
Wait before making more requests (check Retry-After header)
Implement exponential backoff in your code
Consider caching responses to reduce API calls
Problem : Connection issues or timeouts.Solution :
Check your internet connection
Implement retry logic with exponential backoff
Set appropriate timeout values
Check our status page for any ongoing issues
Complete Example
Here’s a complete working example that handles authentication and makes several API calls:
class GetBillAPIClient {
constructor ( clientId , clientSecret ) {
this . clientId = clientId ;
this . clientSecret = clientSecret ;
this . accessToken = null ;
this . baseURL = 'https://getbill.io' ;
}
async authenticate () {
const response = await fetch ( ` ${ this . baseURL } /oauth/token` , {
method: 'POST' ,
headers: {
'Content-Type' : 'application/x-www-form-urlencoded' ,
},
body: new URLSearchParams ({
grant_type: 'client_credentials' ,
client_id: this . clientId ,
client_secret: this . clientSecret ,
scope: 'company:read debts:read debts:write followups:read'
})
});
if ( ! response . ok ) {
throw new Error ( 'Authentication failed' );
}
const tokenData = await response . json ();
this . accessToken = tokenData . access_token ;
}
async makeRequest ( endpoint , options = {}) {
if ( ! this . accessToken ) {
await this . authenticate ();
}
const response = await fetch ( ` ${ this . baseURL } /external-api/v1 ${ endpoint } ` , {
... options ,
headers: {
'Authorization' : `Bearer ${ this . accessToken } ` ,
'Content-Type' : 'application/json' ,
... options . headers
}
});
if ( ! response . ok ) {
const error = await response . json ();
throw new Error ( error . message );
}
return response . json ();
}
async getCompanyProfile () {
return this . makeRequest ( '/company/profile' );
}
async getDebts ( params = {}) {
const queryString = new URLSearchParams ( params ). toString ();
return this . makeRequest ( `/debts ${ queryString ? '?' + queryString : '' } ` );
}
async createDebt ( debtData ) {
return this . makeRequest ( '/debts' , {
method: 'POST' ,
body: JSON . stringify ( debtData )
});
}
}
// Usage
async function main () {
const client = new GetBillAPIClient ( 'YOUR_CLIENT_ID' , 'YOUR_CLIENT_SECRET' );
try {
// Get company profile
const profile = await client . getCompanyProfile ();
console . log ( 'Company:' , profile . data . name );
// Get recent debts
const debts = await client . getDebts ({ limit: 5 });
console . log ( `Found ${ debts . pagination . total } debts` );
// Create a new debt
const newDebt = await client . createDebt ({
firstname: 'John' ,
lastname: 'Doe' ,
phone: '+33123456789' ,
amount: 500 ,
currency: 'EUR' ,
object: 'Test debt'
});
console . log ( 'Created debt:' , newDebt . data . id );
} catch ( error ) {
console . error ( 'Error:' , error . message );
}
}
main ();
Resources
Ready to build something amazing? Start exploring the full API capabilities!