Gravatar Helper

This article is also available in the following languages:
By predominant
From the Gravatar Website:
A gravatar, or globally recognized avatar, is quite simply an avatar image that follows you from weblog to weblog appearing beside your name when you comment on gravatar enabled sites. Avatars help identify your posts on web forums, so why not on weblogs?

Gravatars are a great addition to any blog, or indeed any user submitted content. This helper is designed to provide gravatar output without the fuss

Introduction

This is my first community posted code. Criticism welcome, but please be kind.

There isn't much to this Helper, so I will jump right in.

The code is available at the end of this article, and is also hosted on Github: http://github.com/predominant/CakePHP-Goodies


Usage

More than likely you just want to use the thing... Well, its as simple as this:


Including the helper in your application

As with any helper, ensure that it is included in the helpers array in your controller. This will allow you access to it when you need it, in your views.


Controller
class MyController extends AppController {
  public $helpers = array('Gravatar');
  // ...
}

View

Basic Gravatar with default settings:

<?php echo $gravatar->image('someone@cakeisawesome.com'); ?>

Altering the default gravatar:

<?php echo $gravatar->image(
  
'someone@cakeisawesome.com',
  array(
    
'default' => 'identicon'
  
); ?>

Altering the default gravatar with a custom image:

<?php echo $gravatar->image(
  
'someone@cakeisawesome.com',
  array(
    
'default' => 'http://mysite.com/defaultavatar.png'
  
)); ?>

Changing the gravatar size:

<?php echo $gravatar->image(
  
'someone@cakeisawesome.com',
  array(
    
'default' => 'identicon',
    
'size' => 120
  
); ?>

Adjusting the gravatar ratings to display:

<?php echo $gravatar->image(
  
'someone@cakeisawesome.com',
  array(
    
'rating' => 'x'
  
); ?>

Including image filename extension on the generated URL:

<?php echo $gravatar->image(
  
'someone@cakeisawesome.com',
  array(
    
'default' => 'identicon',
    
'ext' => true
  
); ?>

Options

The options and their valid values are as follows:


default


size

  • Minimum value 1
  • Maximum value 512
In the event that your Gravatar size is outside these bounds, the helper will adjust it to be size 1 or 512, depending which side of the allowed range your specified value was.


rating

  • 'g'
  • 'pg'
  • 'r'
  • 'x'
If rating is either invalid or not specified, Gravatars will automatically be delivered for the 'g' rating. These ratings should be reasonably self explainatory.


ext

  • true
  • false
If not supplied, an image filename extension will not be included as part of the gravatar generation.


Helper Code

Helper Class:

<?php 
<?php
App
::import(array('Security''Validation'));

/**
 * CakePHP Gravatar Helper
 *
 * A CakePHP View Helper for the display of Gravatar images (http://www.gravatar.com)
 *
 * @copyright Copyright 2010, Graham Weldon
 * @license http://www.opensource.org/licenses/mit-license.php The MIT License
 * @package goodies
 * @subpackage goodies.tests.cases.helpers
 *
 */
class GravatarHelper extends AppHelper {

/**
 * Gravatar avatar image base URL
 *
 * @var string
 * @access private
 */
    
private $__url = array(
        
'http' => 'http://www.gravatar.com/avatar/',
        
'https' => 'https://secure.gravatar.com/avatar/'
    
);

/**
 * Hash type to use for email addresses
 *
 * @var string
 * @access private
 */
    
private $__hashType 'md5';

/**
 * Collection of allowed ratings
 *
 * @var array
 * @access private
 */
    
private $__allowedRatings = array('g''pg''r''x');

/**
 * Default Icon sets
 *
 * @var array
 * @access private
 */
    
private $__defaultIcons = array('none''identicon''monsterid''wavatar''404');

/**
 * Default settings
 *
 * @var array
 * @access private
 */
    
private $__default = array(
        
'default' => null,
        
'size' => null,
        
'rating' => null,
        
'ext' => false);

/**
 * Helpers used by this helper
 *
 * @var array
 * @access public
 */
    
public $helpers = array('Html');

/**
 * Constructor
 *
 * @access public
 */
    
public function __construct() {
        
// Default the secure option to match the current URL.
        
$this->__default['secure'] = env('HTTPS');
    }

/**
 * Show gravatar for the supplied email address
 *
 * @param string $email Email address
 * @param array $options Array of options, keyed from default settings
 * @return string Gravatar image string
 * @access public
 */
    
public function image($email$options = array()) {
        
$imageUrl $this->url($email$options);
        unset(
$options['default'], $options['size'], $options['rating'], $options['ext']);
        return 
$this->Html->image($imageUrl$options);
    }

/**
 * Generate image URL
 *
 * @param string $email Email address
 * @param string $options Array of options, keyed from default settings
 * @return string Gravatar Image URL
 * @access public
 */
    
public function url($email$options = array()) {
        
$options $this->__cleanOptions(array_merge($this->__default$options));
        
$ext $options['ext'];
        
$secure $options['secure'];
        unset(
$options['ext'], $options['secure']);
        
$protocol $secure === true 'https' 'http';

        
$imageUrl $this->__url[$protocol] . $this->__emailHash($email$this->__hashType);
        if (
$ext === true) {
            
// If 'ext' option is supplied and true, append an extension to the generated image URL.
            // This helps systems that don't display images unless they have a specific image extension on the URL.
            
$imageUrl .= '.jpg';
        }
        
$imageUrl .= $this->__buildOptions($options);
        return 
$imageUrl;
    }

/**
 * Sanitize the options array
 *
 * @param array $options Array of options, keyed from default settings
 * @return array Clean options array
 * @access private
 */
    
private function __cleanOptions($options) {
        if (!isset(
$options['size']) || empty($options['size']) || !is_numeric($options['size'])) {
            unset(
$options['size']);
        } else {
            
$options['size'] = min(max($options['size'], 1), 512);
        }

        if (!
$options['rating'] || !in_array(mb_strtolower($options['rating']), $this->__allowedRatings)) {
            unset(
$options['rating']);
        }

        if (!
$options['default']) {
            unset(
$options['default']);
        } else {
            if (!
in_array($options['default'], $this->__defaultIcons) && !Validation::url($options['default'])) {
                unset(
$options['default']);
            }
        }
        return 
$options;
    }

/**
 * Generate email address hash
 *
 * @param string $email Email address
 * @param string $type Hash type to employ
 * @return string Email address hash
 * @access private
 */
    
private function __emailHash($email$type) {
        return 
Security::hash(mb_strtolower($email), $type);
    }

/**
 * Build Options URL string
 *
 * @param array $options Array of options, keyed from default settings
 * @return string URL string of options
 * @access private
 */
    
private function __buildOptions($options = array()) {
        
$gravatarOptions array_intersect(array_keys($options), array_keys($this->__default));
        if (!empty(
$gravatarOptions)) {
            
$optionArray = array();
            foreach (
$gravatarOptions as $key) {
                
$value $options[$key];
                
$optionArray[] = $key '=' mb_strtolower($value);
            }
            return 
'?' implode('&amp;'$optionArray);
        }
        return 
'';
    }
}
?>
?>

Final Note

My final note is with regard to the options provided to the helper. Given that the HTML helper already deals extensively with images, it is used to process the actual image tage and return it. Thus, providing any Html Helper image options will ensure they are passed through the gravatar component and onto the Html component, rendering as you would naturally expect from the core Html helper.

Comments and suggestions are encouraged.

If you are using this on your site, let me know!


Code also available on Github: http://github.com/predominant/CakePHP-Goodies

Comments

  • Posted 05/24/11 02:02:25 AM
    What youre saying is completely true. I know that everybody must say the same thing, but I just think that you put it in a way that everyone can understand. I also love the images you put in here. They fit so well with what youre trying to say. Im sure youll reach so many people with what youve got to say.
    I wait behind the visit … Techno News
  • Posted 08/24/10 11:04:18 PM
    Thank you very much for this useful helper.

    I have integrated into my CakePHP app.


    Regards
    The-Di-Lab
    www.thedilab.com
    www.startutorial.com
  • Posted 02/19/10 12:37:50 PM
    Greate thanks for Author :)
  • Posted 12/28/09 04:18:41 AM
    Thanks for all the great feedback folks.

    If you have any suggestions or improvements, please let me know.
  • Posted 12/14/09 05:02:05 AM
    ^
  • Posted 10/29/09 11:59:31 PM
    This works perfectly. Thanks for packing it nicely in git hub. Just pulled it into my plugins directory and worked like a charm!

    Thanks!
  • Posted 10/06/09 09:39:17 AM
    did anyone build a component yet with the gravatar api?
    you would be able to check on whether an email has an account or get all pics of that account etc

    just wondering
    would be cool to validate that first before a user can add his gravatar
  • Posted 08/29/09 11:21:47 AM
    Hello.


    It struck me that you should send a link to the gravatar team, and hopefully they will add it to their implementation guide on the page.

    Good luck and thanks for a good helper.
  • Posted 08/29/09 11:13:39 AM
    Really nice job.
    Just ask google about 'gravatar cakephp' and what pops up if not the perfect solution.
  • Posted 08/17/09 01:25:10 AM
    Updated to add url() method to generate and return the url for the image without the img tag. Handy if you want to generate your own image tag, or if you need to use the image url in some other manner.

    This doesnt affect the previous functionality at all.
  • Posted 07/30/09 07:14:36 PM
    Updated the helper code, and also mirrored on github: http://github.com/predominant/CakePHP-Goodies/tree/master
    Thanks to Mark Scherer for various updates and contributions.
  • Posted 07/17/09 04:26:45 PM
    Nice one, Graham!
  • Posted 06/21/09 05:09:44 PM
    Clean and simple, just the way we like it.

    Great work Graham!
  • Posted 06/10/09 04:20:18 PM
    Updates applied:
    1. HTML Encoding corrected (Thhanks Tyler)
    2. EMail addresses forced lowercase (Thanks Ben)
    3. Moved to PHP 5 only.
    4. Various code cleanup

    Thanks for the suggestions and help with this helpers code. And enjoy the updates.
  • Posted 06/10/09 12:50:25 PM
    This is a pretty nice helper you wrote!

    You should update your code to reflect Tyler's suggestion about encoding the URL properly.

    Also, your hashing method is not taking into account the fact that Gravatar is expecting the email to be hashed in its lower-case form. Hence, the following change should be applied...

    Change this:

    Helper Class:

    <?php 
    return Security::hash($email$type);
    ?>

    To this:

    Helper Class:

    <?php 
    return Security::hash(strtolower($email), $type);
    ?>

    That's all there is to it. :)
  • Posted 01/07/09 08:07:30 PM
    Hi there.
    I'm a newbe and would like to know how to place this code in a html page?
    Do I need a seperate php page with script for each persons Gravatar?
    Do I place the script like this below directly into the html page??

    image(
    'someone@cakeisawesome.com',
    array(
    'rating' => 'x'
    ); ?>
    • Posted 01/11/09 11:51:24 PM
      Do I need a seperate php page with script for each persons Gravatar?
      Do I place the script like this below directly into the html page??

      image(
      'someone@cakeisawesome.com',
      array(
      'rating' => 'x'
      ); ?>

      You actually spotted an error in the code samples there, as there is a missing close bracket, but you can place this into any view .ctp file in your CakePHP Application / Plugin.

      The simplest and easiest way to display a gravatar is to do:

      View Template:


      echo $gravatar->image('someone@cakeisawesome.com');

      And just ensure you include the Gravatar helper in your controller (or AppController), like this:

      Controller Class:

      <?php 
      public $helpers = array('Html''Gravatar');
      ?>
  • Posted 11/30/08 01:24:36 PM
    Thank you for posting this. I'll offer a small suggestion, as the URL isn't properly encoded. On line 94, change:

    $optionString = implode('&', $optionArray);
    To:

    $optionString = implode('&amp;', $optionArray);

Comments are closed for articles over a year old