Introduction
Google Code: https://code.google.com/p/fitjs/
Fitbit is an awesome device to track daily activities, sleep and etc. However, the website itself provides limited applications to users other than displaying data and some basic diagrams. Third-party developers like you can seize this opportunity to develop awesome apps for this new market by providing application related to gamification or motivation.
Fitbit provides RESTful APIs to access users' data. The benefits is that you can develop apps on a variety of platforms without downloading anything. The downside is that you will need to know write a lot of tedious code to call the APIs.
FitJS is an AJAX library that wrap around Fitbit's RESTful APIs. You can directly call Javascript functions to request tokens, accessing token or even create pop-ups to redirect users to authorize your access.
FitJS is completely open-source under Apache License 2.0. You can help develop the library at:
https://code.google.com/p/fitjs/
The 1.0 version now supports only the OAuth Authorization functionalities. However, accessing resources is on the way in the next update. Your help with the library with be greatly appreciated.
Using the code
Prerequisite
Using the library
Downloading and placing the files
1. go to https://code.google.com/p/fitjs/ and download the ZIP file on Google Drive
2. Unzip this file to your website folder
3. include fitjs.js in your web page
<script src="fitjs/fitjs.js"></script>
4. Make sure your server runs on PHP. If not, you may want to make following changes:
- Open "fitjs.js"
- Find FitJS_OAuth() method. Change following code
this.url={
........
verifier:"fitjs/oauthverifier.php",
signature:'fitjs/oauthsignature.php',
proxy:"fitjs/proxy.php"
};
to reflect your choice of web language such as ASP JSP etc.
5. Replace those files in FitJS folder with your files that accomplish the same functionalities.
"oauthverifier.php" returns the verifier returned by Fitbit after users authorize the access. Note that Fitbit will call a URL you provided once users authorize your access to their data. The URL should write the verifier and token returned by this call to your database. "oauthverifier.php" merely pulls these two variables from your database and print it in following format:
verifier=XXX&token=XXX
"oauthsignature.php" signs a base string with with your consumer secret by using HMAC-SHA1 method. If you wish to use other hash methods, please make sure your constructor of the FitJS Object will reflect that.
"proxy.php" is a proxy for XMLHttpRequest to avoid cross-domain call restrictions by most browsers. Javascript function will first send specific requests to this file and this file then call Fitbit APIs and return the response. The file uses a POST method to intake 1) the header Fitbit required for that request 2) the body request for that request 3) the method such as POST or GET for that particular request to Fitbit. You can read the source code to understand better what it does.
Using the JS methods:
0. Basics of FitJS OAuth
This following diagram demonstrates the FitJS OAuth process.
1. Initializing FitJS
foauth=new FitJS_OAuth("http://example.com/oauthverifier.php",
"999999999999999999999999",
"HMAC-SHA1"
);
2. Requesting token
var baseString=foauth.oauthBaseString("request_token");
var signature=foauth.oauthSignatureString(baseString);
foauth.requestToken(signature, true, readyStateChange);
Please note that "readyStategChange" is a callback function with a standard XMLHttpRequest as an argument. To check whether you receive a valid response you may want to do:
function readyStateChange(xmlhttp)
{
if (xmlhttp.readyState===4 && xmlhttp.status===200)
{
}
else
{
}
}
3. Redirecting users to Fitbit.com for authorization
After you received a valid token from Fitbit.com you should then redirect your users to Fitbit.com for their authorizations on your access to data. In the example below, the redirection is sent out only when token is received. Therefore, the code is placed in "readyStateChange" function (in the last step)
function readyStategChange(xmlhttp)
{
if (xmlhttp.readyState===4 && xmlhttp.status===200)
{
foauth.authorize(true, "en_US", false, 800, 500);
foauth.checkOAuthVerifier(2000, 10000, onTimeOut, onFinished, onFailed);
}
}
In the example above, you can see the constant checking is initiated once the pop-up is generated. The checking will be stopped once it detects "oauthverifier" has already returned verifier after user authorize the access.
onTimeOut, onFinished and onFailed are all callback functions accepting one standard XMLHttpRequest argument. In step 5, you can see how onFinished is implemented
4. Accessing token
function onFinished()
{
var basestring=foauth.oauthBaseString("access_token");
var signature=foauth.oauthSignatureString(basestring);
foauth.accessToken(signature, true, onAccessTokenStateChange);
}
function onAccessTokenStateChange(xmlhttp)
{
if (xmlhttp.readyState===4 && xmlhttp.status===200)
{
alert("token:"+foauth.oauth_token+" token secret:"+foauth.oauth_token_secret+" user id: "+foauth.oauth_token_secret);
}
}
API Reference
For the latest API reference you may want to read: https://code.google.com/p/fitjs/wiki/API_Reference
Before start, you may want to check out http://tools.ietf.org/html/draft-hammer-oauth-10 to understand OAuth protocol 1.0 to understand how Fitbit authorizes your app to access to users' data.
Member Functions
Constructor
FitJS_OAuth(callbackUrl, consumerKey, hashMethod)
Parameters:
Return: A initialized copy of Fitbit instance
callbackUrl | an URL for Fitbit API to callback once the user authorize the access to his/her data. The URL should match what's on record unless no record left on Fitbit.com. This URL should write the token and verifier returned by Fitbit to database |
consumerKey | the consumer key string provided by Fitbit |
hashMethod | FitJS currently ONLY ACCEPTS HMAC-SHA1. However, HMAC-SHA1, RSA-SHA1, PLAINTEXT will be supported in the future |
Example:
foauth=new FitJS_OAuth("http://example.com/oauthcomplete.php",
"7c799999999999e8a149499999",
"HMAC-SHA1"
);
Signing a request
An OAuth request usually involves several headers. But the complex parts are 1) assembling a request base string 2) signing it. 3) assembling a request header
2) needs your secret. For security reasons, it is highly commended to not store your OAuth secret in the javascript. For this sake, you should store your Fitbit OAuth secret in "oauthsignature.php".
For more information about signing OAuth request, please see:
http://tools.ietf.org/html/draft-hammer-oauth-10#section-3.4
Generating a base string
oauthBaseString(stage);
This function will generate a base string for signing based on the type of request.
Parameters:
stage | This is an Enum variable with two possible values: "request_token" and "access_token". |
Return: The function will return a base string for generating signature string based on the type of request provided.
Example:
var baseString=foauth.oauthBaseString("request_token");
var basestring=foauth.oauthBaseString("access_token");
oauthSignatureString (baseString)
This function signs the base string by using HMAC-SHA1. Currently, HMAC-SHA1 is the only method allowed in the 1.0 version of FitJS.
Parameters:
baseString | Oauth request base string to generate signature. This string is generated by oauthBaseString() function |
Return: A signature string by using HMAC-SHA1
Example:
var signature=foauth.oauthSignatureString(baseString);
Requesting a temporary token
requestToken (signature, async, onreadyStateChange)
Parameters:
signature | the signature string based on this request's base string |
async | whether this request is asynchronous |
onreadyStateChange | callback function for ready state change event. Only if the request is asynchronous, this function will called. |
Return: If the request is asynchronous, this function does not have return. If the function is synchronous, the return is a standard XMLHttpRequest
Example:
foauth.requestToken(signature, true, readyStategChange);
Authorizing Access
Through the OAuth authorization process, user has to give your app the permission to access his/her data on Fitbit server. Thus, your app needs to either redirect the user to or use a pop-up window to allow the user access to fitbit.com/authorize.
authorize(usePopUp, locale, mobile, popupWidth, popupHeight)
This function allows both pop-up and redirect, although using pop-up is highly recommended to preserve data in your javascript.
Parameters:
usePopUp | whether the access to fitbit.com is through a pop-up or redirect |
locale | the locale of your pop-up |
mobile | whether the user's access to fitbit.com is on a mobile device |
popupWidth | the width of your pop-up |
popupHeight | the heigh of your pop-up |
Return: None
Example:
foauth.authorize(true, "en_US", false, 800, 500);
checkOAuthVerifier(interval, timeout, onTimedOut, onFinished, onFailed)
This function sends requests to "oauthverifier.php" to check whether your website as acquired OAuth verifier from fitbit.com (this occurs only after user has authorized the access). Thus, the prerequisite is to implement a callback URL that allows fitbit.com to send verifier and token and "oauthverifier.php", which pulls data from your database where the verifier and token are stored.
Note that "oauthverifier.php" MUST RETURN VERIFIER AND TOKEN IN FOLLOWING FORMAT:
"verifier=XXX&token=XXX"
Parameters:
interval | frequency to check on "oauthverifier.php" in milliseconds |
timeout | the threshold to timeout of a single request in milliseconds |
onTimedOut | callback function if it does timeout (return XMLHttpRequest) |
onFinished | callback function when finish (return XMLHttpRequest) |
onFailed | callback function when error occurs (return XMLHttpRequest) |
Return:
None
Example:
foauth.checkOAuthVerifier(2000, 10000, onTimeOut, onFinished, onFailed);
stopCheckingOAuthVerifier()
checkOAuthVerifier() will automatically stop sending requests if it acquires verifier and token from the "oauthverifier". However, should you want to stop the checking manually under certain circumstances, you can call this function.
Parameters:
None
Return: None
Example:
stopCheckingOAuthVerifier();
Accessing a token
accessToken(signature, async, onreadyStateChange)
The last step in the OAuth process is to request and receives token credentials from Fitbit. The return includes token, token secret and the user's user-id. With these credentials, your app can then access user's data.
Parameters:
signature | signature string generated by "oauthSignatureString()" |
async | whether this request is asynchronous |
onreadyStateChange | if the request is asynchronous, the callback function to receive read state change event. The argument will be a standard XMLHttpRequest |
Return: If the request is synchronous, the function returns a standard XMLHttpRequest; if not, it does not return anything.
Example:
foauth.accessToken(signature, true, onAccessTokenFinished);
function onAccessTokenFinished(xmlhttp)
{
if (xmlhttp.readyState===4 && xmlhttp.status===200)
{
alert("token:"+foauth.oauth_token+" token secret:"+foauth.oauth_token_secret+" user id: "+foauth.encoded_user_id);
}
}
Member Variables
url={
request_token:"http://api.fitbit.com/oauth/request_token",
access_token:"http://api.fitbit.com/oauth/access_token",
authorize:"https://www.fitbit.com/oauth/authenticate",
verifier:"fitjs/oauthverifier.php",
signature:'fitjs/oauthsignature.php',
proxy:"fitjs/proxy.php"
}
URLs that FitJS internally uses to complete different parts of the OAuth process.
callbackUrl
Callback URL provided when constructing the FitJS_OAuth object.
consumerKey
Consumer key provide when constructing the FitJS_OAuth object.
hashMethod
Hash method provided when constructing the FitJS_OAuth object. Currently, it uses supports HMAC-SHA1.
verifier
Verifier received from "oauthverifier.php" once user authorizes the access to his/her data and redirect Fitbit.com to the callback URL, that stores the verifier in the database.
Token
Temporary token received from Fitbit.com.
callbackConfirmed
Whether the callback URL is confirmed by Fitbit.com when requesting a token.
request_token_timestamp
Timestamp string when request token. This string will change every time when base string function is called to create base string for requesting a token.
request_token_nonce
Random string when request token. This string will change every time when base string function is called to create base string for requesting a token.
access_token_timestamp
Timestamp string when access token. This string will change every time when base string function is called to create base string for accessing a token.
access_token_nonce
Random string when access token. This string will change every time when base string function is called to create base string for accessing a token.
oauth_token_secret
OAuth token secret received from Fitbit after accessToken() is called successfully.
encoded_user_id
User id received from Fitbit after accessToken() is called successfully.