Search code examples
phpsdkcommentshmacsha1gigya

Gigya PHP Sdk - Comment Notifications


I'm trying to use the Gigya's Comment Notification functionality and I've followed the guidelines at: http://developers.gigya.com/010_Developer_Guide/18_Plugins/022_Comments_Version_2/Comment_Notifications

I've developed the following code:

<?php

    require_once('GSSDK.php');

    $event = $_POST['event'];
    $eventData = $_POST['eventData'];
    $nonce = $_POST['nonce'];
    $timestamp = $_POST['timestamp'];
    $signature = $_POST['signature'];
    $signatureBase = sprintf("%s_%s_%s_%s", $event, $eventData, $nonce, $timestamp);
    $expectedSignature = SigUtils::calcSignature(
        $signatureBase,
        MY_SECRET_KEY);

    if($signature !== $expectedSignature) {
        header('HTTP/1.0 403 Forbidden');
        die();
    }

    //Some other stuff
    exit();

?>

But it never gets to the "//Some other stuff" part. Always the expected signature differs from the signature provided by the Gigya's server. What am I doing wrong?


Solution

  • Try the following code instead:

    <?php
    
      static function calcSignature($baseString,$key)
      {
        $baseString = utf8_encode($baseString);
        $rawHmac = hash_hmac("sha1", utf8_encode($baseString), base64_decode($key), true);
        $sig = base64_encode($rawHmac); 
        return $sig;
      }
    
      function checkSignature() 
      {
        $event = $_POST["event"];
        $eventData = $_POST["eventData"];
        $nonce = $_POST["nonce"];
        $timestamp = $_POST["timestamp"];
        $signature = $_POST["signature"];
    
        $signatureBase = $event . "_" . $eventData . "_" . $nonce . "_" . $timestamp;
        $secret = "[your gigya secret key]";
        $expectedSignature = calcSignature($signatureBase, $secret);        
    
        // Now compare the expectedSignature value to the signature value returned in the callback
        if ($signature !== $expectedSignature) 
        {
          header('HTTP/1.0 403 Forbidden');
          die();
        }
      }
    
      checkSignature();
      //Some other stuff
      exit();
    ?>
    

    This code removes the dependency on GigyaSDK just to check the signature. The method provided is the same method that the GigyaSDK uses, but the advantage here is that this is a much smaller memory footprint since the entire GigyaSDK does not need to be loaded.

    Additionally, I'm not sure if it was intentional, but your comparison has the code:

    if(!$signature !== $expectedSignature) {
    

    Instead of:

    if ($signature !== $expectedSignature) {
    

    I'm not quite sure what the purpose of the extraneous logical-NOT operator on $signature is supposed to accomplish, but it seems like this would cause unexpected behavior.