params = $params;
// Start setting up the BDHttp connector
$transport = null;
// Set up our JRegistry object for the BDHttp connector
$options = new JRegistry;
// Set the user agent
$options->set('userAgent', 'TweetDisplayBack/3.0');
// Use a 30 second timeout
$options->set('timeout', 30);
// Include the BabDev library
JLoader::registerPrefix('BD', __DIR__ . '/libraries');
// If the user has forced a specific connector, use it, otherwise allow BDHttpFactory to decide
$connector = $this->params->get('overrideConnector', null);
// If the override is 'no', set to null
if ($connector == 'no')
{
$connector = null;
}
// Instantiate our BDHttp object
$this->connector = BDHttpFactory::getHttp($options, $connector);
// Instantiate the bearer token
$this->bearer = new BDBearer($this->params, $this->connector);
// Store the requested URL scheme
$this->scheme = JUri::getInstance()->getScheme();
}
/**
* Function to compile the data to render a formatted object displaying a Twitter feed
*
* @return object An object with the formatted tweets
*
* @since 1.5
*/
public function compileData()
{
// Load the parameters
$uname = $this->params->get('twitterName', '');
$list = $this->params->get('twitterList', '');
$count = $this->params->get('twitterCount', 3);
$retweet = $this->params->get('tweetRetweets', 1);
$feed = $this->params->get('twitterFeedType', 'user');
// Convert the list name to a usable string for the JSON
if ($list)
{
$flist = static::toAscii($list);
}
// Get the user info
$this->prepareUser();
// Check to see if we have an error
if (isset($this->twitter['error']))
{
return $this->twitter;
}
// Set the include RT's string
$incRT = '';
if ($retweet == 1)
{
$incRT = '&include_rts=1';
}
// Count the number of active filters
$activeFilters = 0;
// Mentions
if ($this->params->get('showMentions', 0) == 0)
{
$activeFilters++;
}
// Replies
if ($this->params->get('showReplies', 0) == 0)
{
$activeFilters++;
}
// Retweets
if ($retweet == 0)
{
$activeFilters++;
}
// Determine whether the feed being returned is a user, favorites, or list feed
if ($feed == 'list')
{
// Get the list feed
$req = 'https://api.twitter.com/1.1/lists/statuses.json?slug=' . $flist . '&owner_screen_name=' . $uname . $incRT . '&include_entities=1';
}
elseif ($feed == 'favorites')
{
// Get the favorites feed
$req = 'https://api.twitter.com/1.1/favorites/list.json?count=' . $count . '&screen_name=' . $uname . '&include_entities=1';
}
else
{
/*
* Get the user feed, we have to manually filter mentions, RTs and replies,
* so get additional tweets by multiplying $count based on the number
* of active filters
*/
if ($activeFilters == 1)
{
$count = $count * 3;
}
elseif ($activeFilters == 2)
{
$count = $count * 4;
}
elseif ($activeFilters == 3)
{
$count = $count * 5;
}
/*
* Determine whether the user has overridden the count parameter with a
* manual number of tweets to retrieve. Override the $count variable
* if this is the case
*/
if ($this->params->get('overrideCount', 1) == 1)
{
$count = $this->params->get('tweetsToScan', 3);
}
$req = 'https://api.twitter.com/1.1/statuses/user_timeline.json?count=' . $count . '&screen_name=' . $uname . '&include_entities=1';
}
// Fetch the decoded JSON
try
{
$obj = $this->getJSON($req);
}
catch (RuntimeException $e)
{
$this->twitter['error'] = '';
return $this->twitter;
}
// Check if we've reached an error
if (isset($obj->errors))
{
$this->twitter['error'] = array();
$this->twitter['error']['messages'] = array();
foreach ($obj->errors as $error)
{
$this->twitter['error']['messages'][] = $error->message;
}
return $this->twitter;
}
// Make sure we've got an array of data
elseif (is_array($obj))
{
// Store the twitter stream response object
static::$tweets = $obj;
// Check if $obj has data; if not, return an error
if (is_null($obj))
{
// Set an error
$this->twitter[0]->tweet->text = JText::_('MOD_TWEETDISPLAYBACK_ERROR_UNABLETOLOAD');
}
else
{
// If caching is enabled and we aren't using cached data, json_encode the object and write it to file
if ($this->params->get('cache') == 1)
{
$data = json_encode($obj);
file_put_contents(JPATH_CACHE . '/tweetdisplayback_tweets-' . $this->moduleId . '.json', $data);
}
// Process the filtering options and render the feed
$this->processFiltering();
// Flag that processing was successful
$this->isProcessed = true;
}
}
else
{
$this->twitter['error'] = '';
}
return $this->twitter;
}
/**
* Function to compile the data from cache and format the object
*
* @return object An object with the formatted tweets
*
* @since 1.5
*/
public function compileFromCache()
{
// Reset the $twitter object in case we errored out previously
$this->twitter = array();
// Get the user info
$this->prepareUser();
// Check to see if we have an error or are out of hits
if (isset($this->twitter['error']) || isset($this->twitter['hits']))
{
return $this->twitter;
}
// Retrieve the cached data and decode it
$obj = file_get_contents(JPATH_CACHE . '/tweetdisplayback_tweets-' . $this->moduleId . '.json');
$obj = json_decode($obj);
// Check if we've reached an error
if (isset($obj->errors))
{
$this->twitter['error'] = array();
$this->twitter['error']['messages'] = array();
foreach ($obj->errors as $error)
{
$this->twitter['error']['messages'][] = $error->message;
}
}
// Make sure we've got an array of data
elseif (is_array($obj))
{
// Store the twitter stream response object
static::$tweets = $obj;
// Check if $obj has data; if not, return an error
if (is_null($obj))
{
// Set an error
$this->twitter[0]->tweet->text = JText::_('MOD_TWEETDISPLAYBACK_ERROR_UNABLETOLOAD');
}
else
{
// Process the filtering options and render the feed
$this->processFiltering();
// Flag that processing was successful
$this->isProcessed = true;
}
}
else
{
$this->twitter['error'] = '';
}
return $this->twitter;
}
/**
* Function to fetch a JSON feed
*
* @param string $req The URL of the feed to load
*
* @return object The fetched JSON query
*
* @since 1.0
* @throws RuntimeException
*/
public function getJSON($req)
{
// Get the data
try
{
$headers = array(
'Authorization' => "Bearer {$this->bearer->token}"
);
$response = $this->connector->get($req, $headers);
}
catch (Exception $e)
{
return null;
}
// Return the decoded response body
return json_decode($response->body);
}
/**
* Function to fetch the user JSON and render it
*
* @return void
*
* @since 1.5
*/
protected function prepareUser()
{
$scheme = $this->scheme . '://';
// Load the parameters
$uname = $this->params->get('twitterName', '');
$list = $this->params->get('twitterList', '');
$feed = $this->params->get('twitterFeedType', 'user');
// Initialize object containers
$this->twitter['header'] = new stdClass;
$this->twitter['footer'] = new stdClass;
$this->twitter['tweets'] = new stdClass;
// Convert the list name to a usable string for the URL
if ($list)
{
$flist = static::toAscii($list);
}
// Retrieve data from Twitter if the header is enabled
if ($this->params->get('headerDisplay', 1) == 1)
{
// Sanity check on user file cache
$cacheFile = JPATH_CACHE . '/tweetdisplayback_user-' . $this->moduleId . '.json';
$cacheTime = $this->params->get('cache_time', 15);
$cacheTime = $cacheTime * 60;
// Get the data
if ($this->isCached && (!file_exists($cacheFile) || time() - @filemtime($cacheFile) > $cacheTime))
{
// Fetch from cache
$obj = file_get_contents(JPATH_CACHE . '/tweetdisplayback_user-' . $this->moduleId . '.json');
$obj = json_decode($obj);
}
else
{
$req = 'https://api.twitter.com/1.1/users/show.json?screen_name=' . $uname;
try
{
$obj = $this->getJSON($req);
}
catch (RuntimeException $e)
{
$this->twitter['error'] = '';
return;
}
// Check if we've reached an error
if (isset($obj->errors))
{
$this->twitter['error'] = array();
$this->twitter['error']['messages'] = array();
foreach ($obj->errors as $error)
{
$this->twitter['error']['messages'][] = $error->message;
}
return;
}
// Check that we have the JSON, otherwise set an error
elseif (!$obj)
{
$this->twitter['error'] = '';
return;
}
// Store the user profile response object so it can be accessed (for advanced use)
static::$user = $obj;
// If caching is enabled and we aren't using cached data, json_encode the object and write it to file
if ($this->params->get('cache') == 1 && !$this->isCached)
{
$data = json_encode($obj);
file_put_contents(JPATH_CACHE . '/tweetdisplayback_user-' . $this->moduleId . '.json', $data);
}
}
/*
* Header info
*/
if ($this->params->get('headerUser', 1) == 1)
{
// Check if the Intents action is bypassed
if ($this->params->get('bypassIntent', '0') == 1)
{
$this->twitter['header']->user = '';
}
else
{
$this->twitter['header']->user = '';
}
// Show the real name or the username
if ($this->params->get('headerName', 1) == 1)
{
$this->twitter['header']->user .= $obj->name . '';
}
else
{
$this->twitter['header']->user .= $uname . '';
}
// Append the list name if being pulled
if ($feed == 'list')
{
$this->twitter['header']->user .= ' - ' . $list . ' list';
}
}
// Show the bio
if ($this->params->get('headerBio', 1) == 1)
{
$this->twitter['header']->bio = $obj->description;
}
// Show the location
if ($this->params->get('headerLocation', 1) == 1)
{
$this->twitter['header']->location = $obj->location;
}
// Show the user's URL
if ($this->params->get('headerWeb', 1) == 1)
{
$this->twitter['header']->web = '' . $obj->url . '';
}
// Get the profile image URL from the object
$avatar = $this->scheme == 'https' ? $obj->profile_image_url_https : $obj->profile_image_url;
// Switch from the normal size avatar (48px) to the large one (73px)
$avatar = str_replace('normal.jpg', 'bigger.jpg', $avatar);
$this->twitter['header']->avatar = '';
}
/*
* Footer info
*/
// Display the Follow button
if ($this->params->get('footerFollowLink', 1) == 1)
{
// Don't display for a list feed
if ($feed != 'list')
{
$followParams = 'screen_name=' . $uname;
$followParams .= '&lang=' . substr(JFactory::getLanguage()->getTag(), 0, 2);
if ($this->params->get('footerFollowCount', '1') == '1')
{
$followParams .= '&show_count=true';
}
else
{
$followParams .= '&show_count=false';
}
$followParams .= '&show_screen_name=' . (bool) $this->params->get('footerFollowUser', 1);
$iframe = '';
$this->twitter['footer']->follow_me = '