Created
May 5, 2015 11:44
-
-
Save vivekgidmare/8f2bcdbf6f7f02696363 to your computer and use it in GitHub Desktop.
Twitter auth
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
var exports = exports || this; | |
exports.Twitter = (function(global) { | |
var K = function() { | |
}, | |
isAndroid = Ti.Platform.osname === "android", | |
jsOAuth = require('/twitter/jsOAuth-1.3.1'); | |
// var utility = require("/utility"); | |
var APP = require('utility'); | |
// APP.Ui.showLoader('Loading...'); | |
// APP.Ui.hideLoader(); | |
/** | |
* Twitter constructor function | |
* | |
* var client = Twitter({ | |
* consumerKey: "INSERT YOUR KEY HERE", | |
* consumerSecret: "INSERT YOUR SECRET HERE" | |
* }); | |
* | |
* Can be used with or without `new` keyword. | |
* | |
* @constructor | |
* @requires jsOAuth: http://github.com/bytespider/jsOAuth | |
* @param options {Object} Configuration object | |
* @param options.consumerKey {String} Application consumer key | |
* @param options.consumerSecret {String} Application consumer secret | |
* @param options.accessTokenKey {String} (optional) The user's access token key | |
* @param options.accessTokenSecret {String} (optional) The user's access token secret | |
* @param [options.windowTitle="Twitter Authorization"] {String} (optional) The title to display in the authentication window | |
*/ | |
var Twitter = function(options) { | |
var self; | |
if (this instanceof Twitter) { | |
self = this; | |
} else { | |
self = new K(); | |
} | |
if (!options) { | |
options = {}; | |
} | |
self.windowTitle = options.windowTitle || "Twitter Authorization"; | |
self.consumerKey = options.consumerKey; | |
self.consumerSecret = options.consumerSecret; | |
self.authorizeUrl = "https://api.twitter.com/oauth/authorize"; | |
self.accessTokenKey = options.accessTokenKey; | |
self.accessTokenSecret = options.accessTokenSecret; | |
self.authorized = false; | |
self.listeners = {}; | |
if (self.accessTokenKey && self.accessTokenSecret) { | |
self.authorized = true; | |
} | |
options.requestTokenUrl = options.requestTokenUrl || "https://api.twitter.com/oauth/request_token"; | |
self.oauthClient = jsOAuth.OAuth(options); | |
return self; | |
}; | |
K.prototype = Twitter.prototype; | |
function createAuthWindow() { | |
var self = this, | |
oauth = this.oauthClient, | |
// webViewWindow = Ti.UI.createWindow({title: this.windowTitle}), | |
webViewWindow = Ti.UI.createWindow({ | |
top : (OS_IOS) ? 20 : 30, | |
navBarHidden : true, | |
backgroundColor : '#7000', | |
orientationModes : [Titanium.UI.PORTRAIT] | |
}), | |
webView = Ti.UI.createWebView({ | |
top : (OS_IOS) ? 10 : 20, | |
bottom : 5, | |
borderColor : 'white', | |
left : 5, | |
right : 5, | |
borderRadius : 5, | |
borderWidth : 3 | |
}), | |
loadingOverlay = Ti.UI.createView({ | |
backgroundColor : 'white', | |
top : (OS_IOS) ? 10 : 20, | |
opacity : (OS_IOS) ? 0.7 : 0.3, | |
left : 5, | |
right : 5, | |
zIndex : 1 | |
}), | |
actInd = Titanium.UI.createActivityIndicator({ | |
message : 'Loading...', | |
left : 30, | |
color : 'white' | |
}), | |
closeButton = Ti.UI.createButton({ | |
backgroundImage : "/images/fb_twitter_close.png", | |
width : (OS_IOS) ? 30 : 40, | |
height : (OS_IOS) ? 30 : 40, | |
top : 0, | |
left : -3, | |
zIndex : 2 | |
}), | |
backButton = Ti.UI.createButton({ | |
title : "Back", | |
top : 20 | |
}); | |
this.webView = webView; | |
webViewWindow.leftNavButton = closeButton; | |
webViewWindow.add(loadingOverlay); | |
webViewWindow.open({ | |
// modal : true | |
}); | |
webViewWindow.add(webView); | |
webViewWindow.add(closeButton); | |
closeButton.addEventListener('click', function(e) { | |
webViewWindow.close(); | |
APP.Ui.hideLoader(); | |
self.fireEvent('cancel', { | |
success : false, | |
error : "The user cancelled.", | |
result : null | |
}); | |
}); | |
backButton.addEventListener('click', function(e) { | |
webView.goBack(); | |
APP.Ui.hideLoader(); | |
}); | |
webView.addEventListener('beforeload', function(e) { | |
if (!isAndroid) { | |
webViewWindow.add(loadingOverlay); | |
} | |
actInd.show(); | |
}); | |
var webViewFirstLoad = true; | |
webView.addEventListener('load', function(event) { | |
// If we're not on the Twitter authorize page | |
if (event.url.indexOf(self.authorizeUrl) === -1) { | |
webViewWindow.remove(loadingOverlay); | |
actInd.hide(); | |
// Required for Android | |
// Switch out close button for back button | |
if (webViewWindow.leftNavButton !== backButton) { | |
webViewWindow.leftNavButton = backButton; | |
} | |
} else { | |
// Switch out back button for close button | |
if (webViewWindow.leftNavButton !== closeButton) { | |
webViewWindow.leftNavButton = closeButton; | |
} | |
// Grab the PIN code out of the DOM | |
//Sort out android with version > 4.4.2 | |
if (isAndroid && Ti.Platform.version >= '4.4.2') { | |
//Need to setup a collection method. | |
webViewWindow.remove(loadingOverlay); | |
actInd.hide(); | |
if (!webViewFirstLoad) { | |
var promptView = Ti.UI.createView({ | |
width : '90%', | |
height : '25%', | |
layout : "vertical", | |
backgroundColor : '#80000000', | |
bottom : "20%" | |
}), | |
pinField = Ti.UI.createTextField({ | |
width : "70%", | |
font : { | |
fontSize : '20dp' | |
}, | |
height : 40, | |
backgroundColor:'white', | |
color:'black', | |
hintText : 'Please Enter PIN' | |
}), | |
pinButton = Ti.UI.createButton({ | |
width : "50%", | |
height :40, | |
top:10, | |
backgroundColor:'#4099FF', | |
color:'white', | |
title : "Authorize" | |
}); | |
promptView.add(pinField); | |
promptView.add(pinButton); | |
webViewWindow.add(promptView); | |
pinButton.addEventListener('click', function() { | |
if (!pinField.value) { | |
alert('Please enter above PIN.'); | |
} else { | |
var pin = pinField.value; | |
Ti.API.info('Pin :' + pin); | |
if (!isAndroid) {// on iOS we can close the modal window right away | |
mainWindow.close(); | |
} | |
oauth.accessTokenUrl = "https://api.twitter.com/oauth/access_token?oauth_verifier=" + pin; | |
oauth.fetchAccessToken(function(data) { | |
var returnedParams = oauth.parseTokenRequest(data.text); | |
self.fireEvent('login', { | |
success : true, | |
error : false, | |
accessTokenKey : returnedParams.oauth_token, | |
accessTokenSecret : returnedParams.oauth_token_secret | |
}); | |
if (isAndroid) {// we have to wait until now to close the modal window on Android: http://developer.appcelerator.com/question/91261/android-probelm-with-httpclient | |
webViewWindow.close(); | |
} | |
}, function(data) { | |
self.fireEvent('login', { | |
success : false, | |
error : "Failure to fetch access token, please try again.", | |
result : data | |
}); | |
}); | |
} | |
}); | |
} else { | |
webViewFirstLoad = false; | |
} | |
} else { | |
var pin = event.source.evalJS("document.getElementById('oauth_pin').getElementsByTagName('code')[0].innerText"); | |
Ti.API.info('Pin :' + pin); | |
if (!pin) { | |
// We're here when: | |
// - "No thanks" button clicked | |
// - Bad username/password | |
webViewWindow.remove(loadingOverlay); | |
actInd.hide(); | |
} else { | |
// if (!isAndroid) {// on iOS we can close the modal window right away | |
// webViewWindow.close(); | |
// } | |
oauth.accessTokenUrl = "https://api.twitter.com/oauth/access_token?oauth_verifier=" + pin; | |
oauth.fetchAccessToken(function(data) { | |
var returnedParams = oauth.parseTokenRequest(data.text); | |
//Added by vivek | |
//Save oauth token and oauth token secret for parse use | |
Ti.App.Properties.setString("twitter_oauthToken", returnedParams.oauth_token); | |
Ti.App.Properties.setString("twitter_oauthTokenSecret", returnedParams.oauth_token_secret); | |
self.accessTokenKey = returnedParams.oauth_token; | |
self.accessTokenSecret = returnedParams.oauth_token_secret; | |
self.fireEvent('login', { | |
success : true, | |
error : false, | |
accessTokenKey : returnedParams.oauth_token, | |
accessTokenSecret : returnedParams.oauth_token_secret | |
}); | |
Ti.API.info('Twitter Web Closed'); | |
webViewWindow.close(); | |
// utility.showIndicator("Authenticating..."); | |
APP.Ui.showLoader('Loading...'); | |
if (isAndroid) {// we have to wait until now to close the modal window on Android: http://developer.appcelerator.com/question/91261/android-probelm-with-httpclient | |
webViewWindow.close(); | |
} | |
}, function(data) { | |
self.fireEvent('login', { | |
success : false, | |
error : "Failure to fetch access token, please try again.", | |
result : data | |
}); | |
}); | |
} | |
} | |
} | |
}); | |
} | |
/* | |
* Requests the user to authorize via Twitter through a modal WebView. | |
*/ | |
Twitter.prototype.authorize = function() { | |
var self = this; | |
if (this.authorized) { | |
// TODO: verify access tokens are still valid? | |
// We're putting this fireEvent call inside setTimeout to allow | |
// a user to add an event listener below the call to authorize. | |
// Not totally sure if the timeout should be greater than 1. It | |
// seems to do the trick on iOS/Android. | |
setTimeout(function() { | |
self.fireEvent('login', { | |
success : true, | |
error : false, | |
accessTokenKey : self.accessTokenKey, | |
accessTokenSecret : self.accessTokenSecret | |
}); | |
}, 1); | |
} else { | |
createAuthWindow.call(this); | |
this.oauthClient.fetchRequestToken(function(requestParams) { | |
var authorizeUrl = self.authorizeUrl + requestParams; | |
self.webView.url = authorizeUrl; | |
}, function(data) { | |
self.fireEvent('login', { | |
success : false, | |
error : "Failure to fetch access token, please try again.", | |
result : data | |
}); | |
}); | |
} | |
}; | |
Twitter.prototype.deauthorize = function(callback) { | |
Ti.API.info('this.authorized :' + (this.authorized)); | |
if (this.authorized) { | |
self.accessTokenKey = ""; | |
self.accessTokenSecret = ""; | |
Ti.App.Properties.setString("twitter_oauthToken", ""); | |
Ti.App.Properties.setString("twitter_oauthTokenSecret", ""); | |
// execute the callback function | |
if ( typeof (callback) == 'function') { | |
callback(!authorized); | |
} | |
} else { | |
// execute the callback function | |
if ( typeof (callback) == 'function') { | |
callback(!authorized); | |
} | |
} | |
return !this.authorized; | |
}; | |
/* | |
* Make an authenticated Twitter API request. | |
* | |
* @param {String} path the Twitter API path without leading forward slash. For example: `1/statuses/home_timeline.json` | |
* @param {Object} params the parameters to send along with the API call | |
* @param {String} [httpVerb="GET"] the HTTP verb to use | |
* @param {Function} callback | |
*/ | |
Twitter.prototype.request = function(path, params, httpVerb, callback) { | |
var self = this, | |
oauth = this.oauthClient, | |
url = "https://api.twitter.com/" + path; | |
oauth.request({ | |
method : httpVerb, | |
url : url, | |
data : params, | |
success : function(data) { | |
callback.call(self, { | |
success : true, | |
error : false, | |
result : data | |
}); | |
}, | |
failure : function(data) { | |
callback.call(self, { | |
success : false, | |
error : "Request failed", | |
result : data | |
}); | |
} | |
}); | |
}; | |
/* | |
* Add an event listener | |
*/ | |
Twitter.prototype.addEventListener = function(eventName, callback) { | |
this.listeners = this.listeners || {}; | |
this.listeners[eventName] = this.listeners[eventName] || []; | |
this.listeners[eventName].push(callback); | |
}; | |
/* | |
* Fire an event | |
*/ | |
Twitter.prototype.fireEvent = function(eventName, data) { | |
var eventListeners = this.listeners[eventName] || []; | |
for (var i = 0; i < eventListeners.length; i++) { | |
eventListeners[i].call(this, data); | |
} | |
}; | |
return Twitter; | |
})(this); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment