672 lines
19 KiB
C++
672 lines
19 KiB
C++
#include "oauthlib.h"
|
|
#include "HMAC_SHA1.h"
|
|
#include "base64.h"
|
|
#include "urlencode.h"
|
|
|
|
/*++
|
|
* @method: oAuth::oAuth
|
|
*
|
|
* @description: constructor
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
oAuth::oAuth()
|
|
{
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::~oAuth
|
|
*
|
|
* @description: destructor
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
oAuth::~oAuth()
|
|
{
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::clone
|
|
*
|
|
* @description: creates a clone of oAuth object
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: cloned oAuth object
|
|
*
|
|
*--*/
|
|
oAuth oAuth::clone()
|
|
{
|
|
oAuth cloneObj;
|
|
cloneObj.m_consumerKey = m_consumerKey;
|
|
cloneObj.m_consumerSecret = m_consumerSecret;
|
|
cloneObj.m_oAuthTokenKey = m_oAuthTokenKey;
|
|
cloneObj.m_oAuthTokenSecret = m_oAuthTokenSecret;
|
|
cloneObj.m_oAuthPin = m_oAuthPin;
|
|
cloneObj.m_nonce = m_nonce;
|
|
cloneObj.m_timeStamp = m_timeStamp;
|
|
cloneObj.m_oAuthScreenName = m_oAuthScreenName;
|
|
return cloneObj;
|
|
}
|
|
|
|
|
|
/*++
|
|
* @method: oAuth::getConsumerKey
|
|
*
|
|
* @description: this method gives consumer key that is being used currently
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: consumer key
|
|
*
|
|
*--*/
|
|
void oAuth::getConsumerKey( std::string& consumerKey )
|
|
{
|
|
consumerKey = m_consumerKey;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::setConsumerKey
|
|
*
|
|
* @description: this method saves consumer key that should be used
|
|
*
|
|
* @input: consumer key
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
void oAuth::setConsumerKey( const std::string& consumerKey )
|
|
{
|
|
m_consumerKey.assign( consumerKey );
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getConsumerSecret
|
|
*
|
|
* @description: this method gives consumer secret that is being used currently
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: consumer secret
|
|
*
|
|
*--*/
|
|
void oAuth::getConsumerSecret( std::string& consumerSecret )
|
|
{
|
|
consumerSecret = m_consumerSecret;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::setConsumerSecret
|
|
*
|
|
* @description: this method saves consumer secret that should be used
|
|
*
|
|
* @input: consumer secret
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
void oAuth::setConsumerSecret( const std::string& consumerSecret )
|
|
{
|
|
m_consumerSecret = consumerSecret;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getOAuthTokenKey
|
|
*
|
|
* @description: this method gives OAuth token (also called access token) that is being used currently
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: OAuth token
|
|
*
|
|
*--*/
|
|
void oAuth::getOAuthTokenKey( std::string& oAuthTokenKey )
|
|
{
|
|
oAuthTokenKey = m_oAuthTokenKey;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::setOAuthTokenKey
|
|
*
|
|
* @description: this method saves OAuth token that should be used
|
|
*
|
|
* @input: OAuth token
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
void oAuth::setOAuthTokenKey( const std::string& oAuthTokenKey )
|
|
{
|
|
m_oAuthTokenKey = oAuthTokenKey;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getOAuthTokenSecret
|
|
*
|
|
* @description: this method gives OAuth token secret that is being used currently
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: OAuth token secret
|
|
*
|
|
*--*/
|
|
void oAuth::getOAuthTokenSecret( std::string& oAuthTokenSecret )
|
|
{
|
|
oAuthTokenSecret = m_oAuthTokenSecret;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::setOAuthTokenSecret
|
|
*
|
|
* @description: this method saves OAuth token that should be used
|
|
*
|
|
* @input: OAuth token secret
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
void oAuth::setOAuthTokenSecret( const std::string& oAuthTokenSecret )
|
|
{
|
|
m_oAuthTokenSecret = oAuthTokenSecret;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getOAuthScreenName
|
|
*
|
|
* @description: this method gives authorized user's screenname
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: screen name
|
|
*
|
|
*--*/
|
|
void oAuth::getOAuthScreenName( std::string& oAuthScreenName )
|
|
{
|
|
oAuthScreenName = m_oAuthScreenName;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::setOAuthScreenName
|
|
*
|
|
* @description: this method sets authorized user's screenname
|
|
*
|
|
* @input: screen name
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
void oAuth::setOAuthScreenName( const std::string& oAuthScreenName )
|
|
{
|
|
m_oAuthScreenName = oAuthScreenName;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getOAuthPin
|
|
*
|
|
* @description: this method gives OAuth verifier PIN
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: OAuth verifier PIN
|
|
*
|
|
*--*/
|
|
void oAuth::getOAuthPin( std::string& oAuthPin )
|
|
{
|
|
oAuthPin = m_oAuthPin;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::setOAuthPin
|
|
*
|
|
* @description: this method sets OAuth verifier PIN
|
|
*
|
|
* @input: OAuth verifier PIN
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
void oAuth::setOAuthPin( const std::string& oAuthPin )
|
|
{
|
|
m_oAuthPin = oAuthPin;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::generateNonceTimeStamp
|
|
*
|
|
* @description: this method generates nonce and timestamp for OAuth header
|
|
*
|
|
* @input: none
|
|
*
|
|
* @output: none
|
|
*
|
|
* @remarks: internal method
|
|
*
|
|
*--*/
|
|
void oAuth::generateNonceTimeStamp()
|
|
{
|
|
char szTime[oAuthLibDefaults::OAUTHLIB_BUFFSIZE];
|
|
char szRand[oAuthLibDefaults::OAUTHLIB_BUFFSIZE];
|
|
memset( szTime, 0, oAuthLibDefaults::OAUTHLIB_BUFFSIZE );
|
|
memset( szRand, 0, oAuthLibDefaults::OAUTHLIB_BUFFSIZE );
|
|
srand( time( NULL ) );
|
|
sprintf( szRand, "%x", rand()%1000 );
|
|
sprintf( szTime, "%ld", time( NULL ) );
|
|
|
|
m_nonce.assign( szTime );
|
|
m_nonce.append( szRand );
|
|
m_timeStamp.assign( szTime );
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::buildOAuthRawDataKeyValPairs
|
|
*
|
|
* @description: this method prepares key-value pairs from the data part of the URL
|
|
* or from the URL post fields data, as required by OAuth header
|
|
* and signature generation.
|
|
*
|
|
* @input: rawData - Raw data either from the URL itself or from post fields.
|
|
* Should already be url encoded.
|
|
* urlencodeData - If true, string will be urlencoded before converting
|
|
* to key value pairs.
|
|
*
|
|
* @output: rawDataKeyValuePairs - Map in which key-value pairs are populated
|
|
*
|
|
* @remarks: internal method
|
|
*
|
|
*--*/
|
|
void oAuth::buildOAuthRawDataKeyValPairs( const std::string& rawData,
|
|
bool urlencodeData,
|
|
oAuthKeyValuePairs& rawDataKeyValuePairs )
|
|
{
|
|
/* Raw data if it's present. Data should already be urlencoded once */
|
|
if( rawData.length() )
|
|
{
|
|
size_t nSep = std::string::npos;
|
|
size_t nPos = std::string::npos;
|
|
std::string dataKeyVal;
|
|
std::string dataKey;
|
|
std::string dataVal;
|
|
|
|
/* This raw data part can contain many key value pairs: key1=value1&key2=value2&key3=value3 */
|
|
std::string dataPart = rawData;
|
|
while( std::string::npos != ( nSep = dataPart.find_first_of("&") ) )
|
|
{
|
|
/* Extract first key=value pair */
|
|
dataKeyVal = dataPart.substr( 0, nSep );
|
|
|
|
/* Split them */
|
|
nPos = dataKeyVal.find_first_of( "=" );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
dataKey = dataKeyVal.substr( 0, nPos );
|
|
dataVal = dataKeyVal.substr( nPos + 1 );
|
|
|
|
/* Put this key=value pair in map */
|
|
rawDataKeyValuePairs[dataKey] = urlencodeData ? urlencode( dataVal ) : dataVal;
|
|
}
|
|
dataPart = dataPart.substr( nSep + 1 );
|
|
}
|
|
|
|
/* For the last key=value */
|
|
dataKeyVal = dataPart.substr( 0, nSep );
|
|
|
|
/* Split them */
|
|
nPos = dataKeyVal.find_first_of( "=" );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
dataKey = dataKeyVal.substr( 0, nPos );
|
|
dataVal = dataKeyVal.substr( nPos + 1 );
|
|
|
|
/* Put this key=value pair in map */
|
|
rawDataKeyValuePairs[dataKey] = urlencodeData ? urlencode( dataVal ) : dataVal;
|
|
}
|
|
}
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::buildOAuthTokenKeyValuePairs
|
|
*
|
|
* @description: this method prepares key-value pairs required for OAuth header
|
|
* and signature generation.
|
|
*
|
|
* @input: includeOAuthVerifierPin - flag to indicate whether oauth_verifer key-value
|
|
* pair needs to be included. oauth_verifer is only
|
|
* used during exchanging request token with access token.
|
|
* oauthSignature - base64 and url encoded OAuth signature.
|
|
* generateTimestamp - If true, then generate new timestamp for nonce.
|
|
*
|
|
* @output: keyValueMap - map in which key-value pairs are populated
|
|
*
|
|
* @remarks: internal method
|
|
*
|
|
*--*/
|
|
bool oAuth::buildOAuthTokenKeyValuePairs( const bool includeOAuthVerifierPin,
|
|
const std::string& oauthSignature,
|
|
oAuthKeyValuePairs& keyValueMap,
|
|
const bool generateTimestamp )
|
|
{
|
|
/* Generate nonce and timestamp if required */
|
|
if( generateTimestamp )
|
|
{
|
|
generateNonceTimeStamp();
|
|
}
|
|
|
|
/* Consumer key and its value */
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_CONSUMERKEY_KEY] = m_consumerKey;
|
|
|
|
/* Nonce key and its value */
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_NONCE_KEY] = m_nonce;
|
|
|
|
/* Signature if supplied */
|
|
if( oauthSignature.length() )
|
|
{
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_SIGNATURE_KEY] = oauthSignature;
|
|
}
|
|
|
|
/* Signature method, only HMAC-SHA1 as of now */
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_SIGNATUREMETHOD_KEY] = std::string( "HMAC-SHA1" );
|
|
|
|
/* Timestamp */
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_TIMESTAMP_KEY] = m_timeStamp;
|
|
|
|
/* Token */
|
|
if( m_oAuthTokenKey.length() )
|
|
{
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_TOKEN_KEY] = m_oAuthTokenKey;
|
|
}
|
|
|
|
/* Verifier */
|
|
if( includeOAuthVerifierPin && m_oAuthPin.length() )
|
|
{
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_VERIFIER_KEY] = m_oAuthPin;
|
|
}
|
|
|
|
/* Version */
|
|
keyValueMap[oAuthLibDefaults::OAUTHLIB_VERSION_KEY] = std::string( "1.0" );
|
|
|
|
return ( keyValueMap.size() ) ? true : false;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getSignature
|
|
*
|
|
* @description: this method calculates HMAC-SHA1 signature of OAuth header
|
|
*
|
|
* @input: eType - HTTP request type
|
|
* rawUrl - raw url of the HTTP request
|
|
* rawKeyValuePairs - key-value pairs containing OAuth headers and HTTP data
|
|
*
|
|
* @output: oAuthSignature - base64 and url encoded signature
|
|
*
|
|
* @remarks: internal method
|
|
*
|
|
*--*/
|
|
bool oAuth::getSignature( const eOAuthHttpRequestType eType,
|
|
const std::string& rawUrl,
|
|
const oAuthKeyValuePairs& rawKeyValuePairs,
|
|
std::string& oAuthSignature )
|
|
{
|
|
std::string rawParams;
|
|
std::string paramsSeperator;
|
|
std::string sigBase;
|
|
|
|
/* Initially empty signature */
|
|
oAuthSignature.assign( "" );
|
|
|
|
/* Build a string using key-value pairs */
|
|
paramsSeperator = "&";
|
|
getStringFromOAuthKeyValuePairs( rawKeyValuePairs, rawParams, paramsSeperator );
|
|
|
|
/* Start constructing base signature string. Refer http://dev.twitter.com/auth#intro */
|
|
switch( eType )
|
|
{
|
|
case eOAuthHttpGet:
|
|
{
|
|
sigBase.assign( "GET&" );
|
|
}
|
|
break;
|
|
|
|
case eOAuthHttpPost:
|
|
{
|
|
sigBase.assign( "POST&" );
|
|
}
|
|
break;
|
|
|
|
case eOAuthHttpDelete:
|
|
{
|
|
sigBase.assign( "DELETE&" );
|
|
}
|
|
break;
|
|
|
|
default:
|
|
{
|
|
return false;
|
|
}
|
|
break;
|
|
}
|
|
sigBase.append( urlencode( rawUrl ) );
|
|
sigBase.append( "&" );
|
|
sigBase.append( urlencode( rawParams ) );
|
|
|
|
/* Now, hash the signature base string using HMAC_SHA1 class */
|
|
CHMAC_SHA1 objHMACSHA1;
|
|
std::string secretSigningKey;
|
|
unsigned char strDigest[oAuthLibDefaults::OAUTHLIB_BUFFSIZE_LARGE];
|
|
|
|
memset( strDigest, 0, oAuthLibDefaults::OAUTHLIB_BUFFSIZE_LARGE );
|
|
|
|
/* Signing key is composed of consumer_secret&token_secret */
|
|
secretSigningKey.assign( m_consumerSecret );
|
|
secretSigningKey.append( "&" );
|
|
if( m_oAuthTokenSecret.length() )
|
|
{
|
|
secretSigningKey.append( m_oAuthTokenSecret );
|
|
}
|
|
|
|
objHMACSHA1.HMAC_SHA1( (unsigned char*)sigBase.c_str(),
|
|
sigBase.length(),
|
|
(unsigned char*)secretSigningKey.c_str(),
|
|
secretSigningKey.length(),
|
|
strDigest );
|
|
|
|
/* Do a base64 encode of signature */
|
|
std::string base64Str = base64_encode( strDigest, 20 /* SHA 1 digest is 160 bits */ );
|
|
|
|
/* Do an url encode */
|
|
oAuthSignature = urlencode( base64Str );
|
|
|
|
return ( oAuthSignature.length() ) ? true : false;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getOAuthHeader
|
|
*
|
|
* @description: this method builds OAuth header that should be used in HTTP requests to twitter
|
|
*
|
|
* @input: eType - HTTP request type
|
|
* rawUrl - raw url of the HTTP request
|
|
* rawData - HTTP data (post fields)
|
|
* includeOAuthVerifierPin - flag to indicate whether or not oauth_verifier needs to included
|
|
* in OAuth header
|
|
*
|
|
* @output: oAuthHttpHeader - OAuth header
|
|
*
|
|
*--*/
|
|
bool oAuth::getOAuthHeader( const eOAuthHttpRequestType eType,
|
|
const std::string& rawUrl,
|
|
const std::string& rawData,
|
|
std::string& oAuthHttpHeader,
|
|
const bool includeOAuthVerifierPin )
|
|
{
|
|
oAuthKeyValuePairs rawKeyValuePairs;
|
|
std::string rawParams;
|
|
std::string oauthSignature;
|
|
std::string paramsSeperator;
|
|
std::string pureUrl( rawUrl );
|
|
|
|
/* Clear header string initially */
|
|
oAuthHttpHeader.assign( "" );
|
|
rawKeyValuePairs.clear();
|
|
|
|
/* If URL itself contains ?key=value, then extract and put them in map */
|
|
size_t nPos = rawUrl.find_first_of( "?" );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
/* Get only URL */
|
|
pureUrl = rawUrl.substr( 0, nPos );
|
|
|
|
/* Get only key=value data part */
|
|
std::string dataPart = rawUrl.substr( nPos + 1 );
|
|
|
|
/* Split the data in URL as key=value pairs */
|
|
buildOAuthRawDataKeyValPairs( dataPart, true, rawKeyValuePairs );
|
|
}
|
|
|
|
/* Split the raw data if it's present, as key=value pairs. Data should already be urlencoded once */
|
|
buildOAuthRawDataKeyValPairs( rawData, false, rawKeyValuePairs );
|
|
|
|
/* Build key-value pairs needed for OAuth request token, without signature */
|
|
buildOAuthTokenKeyValuePairs( includeOAuthVerifierPin, std::string( "" ), rawKeyValuePairs, true );
|
|
|
|
/* Get url encoded base64 signature using request type, url and parameters */
|
|
getSignature( eType, pureUrl, rawKeyValuePairs, oauthSignature );
|
|
|
|
/* Clear map so that the parameters themselves are not sent along with the OAuth values */
|
|
rawKeyValuePairs.clear();
|
|
|
|
/* Now, again build key-value pairs with signature this time */
|
|
buildOAuthTokenKeyValuePairs( includeOAuthVerifierPin, oauthSignature, rawKeyValuePairs, false );
|
|
|
|
/* Get OAuth header in string format */
|
|
paramsSeperator = ",";
|
|
getStringFromOAuthKeyValuePairs( rawKeyValuePairs, rawParams, paramsSeperator );
|
|
|
|
/* Build authorization header */
|
|
oAuthHttpHeader.assign( oAuthLibDefaults::OAUTHLIB_AUTHHEADER_STRING );
|
|
oAuthHttpHeader.append( rawParams );
|
|
|
|
return ( oAuthHttpHeader.length() ) ? true : false;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::getStringFromOAuthKeyValuePairs
|
|
*
|
|
* @description: this method builds a sorted string from key-value pairs
|
|
*
|
|
* @input: rawParamMap - key-value pairs map
|
|
* paramsSeperator - sepearator, either & or ,
|
|
*
|
|
* @output: rawParams - sorted string of OAuth parameters
|
|
*
|
|
* @remarks: internal method
|
|
*
|
|
*--*/
|
|
bool oAuth::getStringFromOAuthKeyValuePairs( const oAuthKeyValuePairs& rawParamMap,
|
|
std::string& rawParams,
|
|
const std::string& paramsSeperator )
|
|
{
|
|
rawParams.assign( "" );
|
|
if( rawParamMap.size() )
|
|
{
|
|
oAuthKeyValueList keyValueList;
|
|
std::string dummyStr;
|
|
|
|
/* Push key-value pairs to a list of strings */
|
|
keyValueList.clear();
|
|
oAuthKeyValuePairs::const_iterator itMap = rawParamMap.begin();
|
|
for( ; itMap != rawParamMap.end(); itMap++ )
|
|
{
|
|
dummyStr.assign( itMap->first );
|
|
dummyStr.append( "=" );
|
|
if( paramsSeperator == "," )
|
|
{
|
|
dummyStr.append( "\"" );
|
|
}
|
|
dummyStr.append( itMap->second );
|
|
if( paramsSeperator == "," )
|
|
{
|
|
dummyStr.append( "\"" );
|
|
}
|
|
keyValueList.push_back( dummyStr );
|
|
}
|
|
|
|
/* Sort key-value pairs based on key name */
|
|
keyValueList.sort();
|
|
|
|
/* Now, form a string */
|
|
dummyStr.assign( "" );
|
|
oAuthKeyValueList::iterator itKeyValue = keyValueList.begin();
|
|
for( ; itKeyValue != keyValueList.end(); itKeyValue++ )
|
|
{
|
|
if( dummyStr.length() )
|
|
{
|
|
dummyStr.append( paramsSeperator );
|
|
}
|
|
dummyStr.append( itKeyValue->c_str() );
|
|
}
|
|
rawParams.assign( dummyStr );
|
|
}
|
|
return ( rawParams.length() ) ? true : false;
|
|
}
|
|
|
|
/*++
|
|
* @method: oAuth::extractOAuthTokenKeySecret
|
|
*
|
|
* @description: this method extracts oauth token key and secret from
|
|
* twitter's HTTP response
|
|
*
|
|
* @input: requestTokenResponse - response from twitter
|
|
*
|
|
* @output: none
|
|
*
|
|
*--*/
|
|
bool oAuth::extractOAuthTokenKeySecret( const std::string& requestTokenResponse )
|
|
{
|
|
if( requestTokenResponse.length() )
|
|
{
|
|
size_t nPos = std::string::npos;
|
|
std::string strDummy;
|
|
|
|
/* Get oauth_token key */
|
|
nPos = requestTokenResponse.find( oAuthLibDefaults::OAUTHLIB_TOKEN_KEY );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
nPos = nPos + oAuthLibDefaults::OAUTHLIB_TOKEN_KEY.length() + strlen( "=" );
|
|
strDummy = requestTokenResponse.substr( nPos );
|
|
nPos = strDummy.find( "&" );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
m_oAuthTokenKey = strDummy.substr( 0, nPos );
|
|
}
|
|
}
|
|
|
|
/* Get oauth_token_secret */
|
|
nPos = requestTokenResponse.find( oAuthLibDefaults::OAUTHLIB_TOKENSECRET_KEY );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
nPos = nPos + oAuthLibDefaults::OAUTHLIB_TOKENSECRET_KEY.length() + strlen( "=" );
|
|
strDummy = requestTokenResponse.substr( nPos );
|
|
nPos = strDummy.find( "&" );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
m_oAuthTokenSecret = strDummy.substr( 0, nPos );
|
|
}
|
|
}
|
|
|
|
/* Get screen_name */
|
|
nPos = requestTokenResponse.find( oAuthLibDefaults::OAUTHLIB_SCREENNAME_KEY );
|
|
if( std::string::npos != nPos )
|
|
{
|
|
nPos = nPos + oAuthLibDefaults::OAUTHLIB_SCREENNAME_KEY.length() + strlen( "=" );
|
|
strDummy = requestTokenResponse.substr( nPos );
|
|
m_oAuthScreenName = strDummy;
|
|
}
|
|
}
|
|
return true;
|
|
}
|