Location: PHPKode > projects > Gallery2flickr > Gallery2Flickr/classes/Gallery2Flickr.class.php
<?php
/*
 * Gallery2Flickr
 *
 * A bridge between your gallery2 installation and flickr.com
 *
 * File:       Gallery2Flickr.class.php
 *
 *             Helper class to interface gallery2 with flickr
 *
 * Copyright:
 *             (c) 2006 - 2008 hide@address.com
 *             Distributed under the terms of the GNU General Public License v2
 *
 * Author(s):
 *             Gunnar Wrobel <hide@address.com>
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as
 * published by the Free Software Foundation; either version 2 of the
 * License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
 * 02110-1301, USA.
 *
 * (Gallery2Flickr is a module for Gallery2 - a web based photo album
 *  viewer and editor - Copyright for Gallery2: (C) 2000-2008 Bharat
 *  Mediratta)
 */

/**
 * @package Gallery2Flickr
 * @version $Id: Gallery2Flickr.class.php 10 2008-01-18 09:39:31Z luciferc $
 * @author Gunnar Wrobel <hide@address.com>
 */
class FlickrToGallery  
{

    var $flickr_api_key = '1ec6e0da9b85ab695169b4cab430562a';
    var $flickr_shared_secret = 'b7a499460670674e';
    var $flickr_bridge_perms = 'write';
    
    var $flickr;

    var $user;
    
    function FlickrToGallery() {
	
	GalleryCoreApi::requireOnce('modules/Gallery2Flickr/classes/phpFlickr/phpFlickr.php');
	
	// We get the token from our db, not the session.
	unset($_SESSION['phpFlickr_auth_token']);

	$this->flickr = new phpFlickr($this->flickr_api_key, 
				      $this->flickr_shared_secret);
	
	// Try to get the token
	list ($ret, $flickr_api_token) = FlickrToGalleryHelper::retrieveToken();
	if ($ret) {
	    return array($ret, null);
	}

	if (!$ret && $flickr_api_token) {
	    $this->flickr->setToken($flickr_api_token);
	    $check_token = $this->flickr->auth_checkToken($flickr_api_token);
	    // valid token?
	    if (!$check_token || $check_token['token'] != $flickr_api_token) {
		// Clear invalid token
		$ret = FlickrToGalleryHelper::setToken('');

		$this->flickr = new phpFlickr($this->flickr_api_key, 
					      $this->flickr_shared_secret);
	    } else {
	      if (isset($check_token['user']) && isset($check_token['user']['nsid'])) {
		$this->user = $this->flickr->people_getInfo($check_token['user']['nsid']);
	      }
	    }
	}

    }

    // Generate a link to flickr that the user can use to give us access
    function auth_link() {

	$error = array();

	// Try to get the frob
	list ($ret, $flickr_api_frob) = FlickrToGalleryHelper::retrieveFrob();
	if ($ret || !$flickr_api_frob) {
	    // Get new frob
	    $flickr_api_frob = $this->flickr->auth_getFrob();
	    if (!$flickr_api_frob) {
		$error['code']    = $this->flickr->error_code;
		$error['message'] = $this->flickr->error_msg;
	    }
	}

	// generate the api signature
	$flickr_api_sig = md5($this->flickr_shared_secret . 
			      "api_key" . $this->flickr_api_key . 
			      "frob" . $flickr_api_frob . 
			      "perms" . $this->flickr_bridge_perms);

	$flickr_auth_link = 'http://flickr.com/services/auth/?' . 
	    'api_key=' . $this->flickr_api_key . 
	    '&perms=' . $this->flickr_bridge_perms .
	    '&frob=' . $flickr_api_frob .
	    '&api_sig=' . $flickr_api_sig;

	return array('frob' => $flickr_api_frob, 
		     'link' => $flickr_auth_link, 
		     'error' => $error);
    }

    function import_set($set_id, $g2id) {

	$set = $this->flickr->photosets_getInfo($set_id);
	$photos = $this->flickr->photosets_getPhotos($set_id);

	$name = 'flickr_owner_' . $set['owner'] . '_id_' . $set['id'];
	$title = $set['title'];
	$description = $set['description'];
	$summary = 'Flickr: ' . $this->flickr->urls_getUserPhotos() . 'sets/' . $set['id'];
	$keywords = '';

	list ($ret, $album) = GalleryCoreApi::createAlbum($g2id, 
							  $name, 
							  $title, 
							  $summary, 
							  $description, 
							  $keywords);

	if ($ret) {
	    return false;
	}

	foreach ($photos['photo'] as $photo) {
	    if (!$this->import_image($photo['id'], $album->getId())) {
		return false;
	    }
	}
	return true;
    }

    function update_set($set_id, $g2id) {

	$set = $this->flickr->photosets_getInfo($set_id);
	$photos = $this->flickr->photosets_getPhotos($set_id);

	$name = 'flickr_owner_' . $set['owner'] . '_id_' . $set['id'];
	$title = $set['title'];
	$description = $set['description'];
	$summary = 'Flickr: ' . $this->flickr->urls_getUserPhotos() . 'sets/' . $set['id'];
	$keywords = '';

    global $gallery;
    $platform =& $gallery->getPlatform();

	/* Find the child set with this name */
    $pathComponent = $platform->legalizePathComponent(trim($name));
	list ($ret, $setId) =
	    GalleryCoreApi::fetchChildIdByPathComponent($g2id, $pathComponent);
    if ($ret) {
	    return false;
	}
	list ($ret, $album) = GalleryCoreApi::loadEntitiesById($g2id);
    if ($ret) {
	    return false;
    }
	list ($ret, $setItem) = GalleryCoreApi::loadEntitiesById($setId);
    if ($ret) {
	    return false;
        }
	/* List of pictures in the set */
    list ($ret, $childIds) = GalleryCoreApi::fetchChildItemIds($setItem);
    if ($ret) {
        return false;
    }
	/* Get Flickr id of every picture already in the gallery set */
	$chunkSize = 200;
	while (!empty($childIds)) {
	    $chunk = array_splice($childIds, 0, $chunkSize);
	    $gallery->guaranteeTimeLimit(60);
	    list ($ret, $childs) = GalleryCoreApi::loadEntitiesById($chunk);
	    if ($ret) {
            return false;
	    }
	    foreach ($childs as $item) {
            $path = $item->getPathComponent();
            $pos = strpos($path, '_');
            $photo_id[] = substr($path, 0, $pos);
	    }
	}
	/* Import pictures from Flickr set which are not yet locally present */
	foreach ($photos['photo'] as $photo) {
	    if (empty($photo_id) || ! in_array ($photo['id'], $photo_id)) {
            if (!$this->import_image($photo['id'], $setId)) {
                return false;
            }
	    }
	}
	return true;
    }

    function import_image($photo_id, $g2id, $import_size = 'Original') {

	global $gallery;

	$g2id = (int)$g2id;

	$photo = $this->flickr->photos_getInfo($photo_id);
    $photo_sizes = $this->flickr->photos_getSizes($photo_id);

    $sizes = array('Square' => 0,
                   'Thumbnail' => 1,
                   'Small' => 2,
                   'Medium' => 3,
                   'Large' => 4,
                   'Original' => 5);

    $sorted_sizes = array();
    foreach ($photo_sizes as $size) {
        $sorted_sizes[$sizes[$size['label']]] = $size;
    }

    $isize = $sizes[$import_size];
    while (!in_array($isize, array_keys($sorted_sizes))) {
        $isize--;
    }
    $photo_url = $sorted_sizes[$isize]['source'];
    /*    var_dump($photo_sizes);
    var_dump($sorted_sizes);
    var_dump($isize);
    var_dump($photo_url);
    die();*/
    

	/* Define basic information */
	$mimeType = 'image/jpeg';
	$title = (isset($photo['title'])) ? $photo['title'] : '';
	$fileName = basename($photo_url);
	$description = (isset($photo['description'])) ? $photo['description'] : '';
	$summary = (isset($photo['urls']['url'][0]['_content'])) ? 'Flickr: ' . $photo['urls']['url'][0]['_content'] : '';

	$tags = '';
	if (isset($photo['tags']['tag'])) {
	    foreach ($photo['tags']['tag'] as $tag) {
		$tags .= $tag['_content'] . ' ';
	    }
	}

	/* Copy the file locally */
	$tmpDir = $gallery->getConfig('data.gallery.tmp');
	$platform =& $gallery->getPlatform();
	$tmpFile = $platform->tempnam($tmpDir, 'add');

	$successfullyCopied = false;
	GalleryUtilities::unsanitizeInputValues($photo_url, false);

	if (empty($extraHeaders)) {
	    $extraHeaders = array('Referer' => str_replace('&amp;', '&', $photo_url));
	}

	// Use the web helper class directly here since we need to specify the
	// redirection depth
	GalleryCoreApi::requireOnce('modules/core/classes/helpers/WebHelper_simple.class');
	list ($successfullyCopied, $response, $headers) =
	    WebHelper_simple::fetchWebFile($photo_url, $tmpFile, $extraHeaders, 2);

	if ($successfullyCopied) {

	    /* Add it */
	    $lock = GalleryCoreApi::acquireWriteLock($g2id);
	    list ($ret, $newItem) = GalleryCoreApi::addItemToAlbum($tmpFile,
								   $fileName,
								   $title,
								   $summary,
								   $description,
								   $mimeType,
								   $g2id);

	    GalleryCoreApi::releaseLocks($lock);

	    $lock = GalleryCoreApi::acquireWriteLock($newItem->getId());

	    $newItem->setKeywords($tags);
	    $newItem->save();

	    GalleryCoreApi::releaseLocks($lock);

	    @$platform->unlink($tmpFile);
	    //      var_dump($newItem->getKeywords());die();

	    if ($ret) {
		return false;
	    }
	} else {
	    return false;
	}
	return true;
    }

    function export($g2id, $set = null, $permissions = 'none') {

	$g2id = (int)$g2id;
	list ($ret, $item) = GalleryCoreApi::loadEntitiesById($g2id);
	if ($ret) {
	    return false;
	}

	if (!$item->getCanContainChildren()) {
	    $pid = $this->export_image($g2id, $permissions);
        if (isset($set)) {
            $result = $this->flickr->photosets_addPhoto($set, $pid);
        }
        return $pid;
	} else {

	    list ($ret, $children) = GalleryCoreApi::fetchChildItemIds($item);
	    if ($ret) {
		return false;
	    }

        $pids = array();
	    foreach ($children as $child) {
            $pid = $this->export($child, $set, $permissions);
            if ($pid) {
                $pids[] = $pid;
            }
        }

        if (!$set) {
            $description = $item->getDescription();
            if (!$description) {
                $description = 'Imported by Gallery2Flickr';
            }
            $new_set = $this->flickr->photosets_create($item->getTitle(),
                                                       $description,
                                                       $pids[0]);
            if ($new_set) {
                $setid = $new_set['id'];
            }
            foreach ($pids as $pid) {
                $this->flickr->photosets_addPhoto($setid, $pid);
            }
        }
        return null;
    }
    }

    function export_image($g2id, $permissions = 'none') {

	global $gallery;

	list ($ret, $item) = GalleryCoreApi::loadEntitiesById($g2id);
	if ($ret) {
	    return false;
	}

	$is_public = "0";
	$is_friend = "0";
	$is_family = "0";

	switch ($permissions) {
	case 'friends':
	    $is_friend = "1";
	    break;
	case 'family':
	    $is_family = "1";
	    break;
	case 'frfa':
	    $is_friend = "1";
	    $is_family = "1";
	    break;
	case 'all':
	    $is_public = "1";
	    break;
	case 'none':
	default:
	    $is_public = "0";
	    $is_friend = "0";
	    $is_family = "0";
	    break;
	}	

	$lock = GalleryCoreApi::acquireReadLock($g2id);

    // Instead of just fetching the file from our disk, we try to
    // ensure that the image gets processed through all filters that
    // might apply to the image

	$platform =& $gallery->getPlatform();
	$path = $platform->tempnam($tmpDir, 'export');

    /* Who is the anonymous user? */
    list ($ret, $anonymousUserId) =
        GalleryCoreApi::getPluginParameter('module', 'core', 'id.anonymousUser');
    if ($ret) {
        return $ret;
    }

    /* Can the current image be accessed by anonymous? */
    list ($ret, $pref) = GalleryCoreApi::fetchPreferredSource($item);
    if ($ret) {
        return $ret;
    }
    $itemId = $pref->getId();

    list ($ret, $permissions) = GalleryCoreApi::getPermissions($itemId);
    if ($ret) {
        return $ret;
    }
    list ($ret, $publicPermissions) =
        GalleryCoreApi::getPermissions($itemId, $anonymousUserId, false);
    if ($ret) {
        return $ret;
    }

    $needSession = !isset($publicPermissions['core.viewSource']);

    if ($needSession) {
		/*
		 * Get G2 session for gallery2flickr to access non-public images.
		 * We can't use this session because hijack protection will prevent access
		 * plus the current user could logout before fotokasten retrieves the images.
		 * Create a new session with the rights of current user for fotokasten to use.
		 */
		$gfSession = new GallerySession();
		$ret = $gfSession->initEmpty(true, $gallery->getActiveUserId());
		if ($ret) {
		    return array($ret, null);
		}
    }
    if ($needSession) {
		$sessionParam = array($gfSession->getKey() => $gfSession->getId());
    } else {
		$sessionParam = array();
    }

	$urlGenerator =& $gallery->getUrlGenerator();
	$src = $urlGenerator->generateUrl(
        array_merge(
            array('view' => 'core.DownloadItem', 'itemId' => $itemId),
            $sessionParam
        ),
        array('forceFullUrl' => true)
    );

	if (isset($gfSession)) {
	    /* Mark this session so that it can be treated specially */
	    $gfSession->put('core.isPrintService', array($itemId));
	    $ret = $gfSession->save();
	    if ($ret) {
            return array($ret, null);
	    }
	}

	list ($success, $response, $headers, $url) = GalleryCoreApi::fetchWebFile($src, $path);
	if (!$success) {
	    return false;
	}

	list($ret, $plugins) = GalleryCoreApi::fetchPluginStatus('module');
	
	$commentsOn = false;
	if (!empty($plugins['comment']) && !empty($plugins['comment']['active']) && $plugins['comment']['active']) {
	    $commentsOn = true;
 	}

	if ($commentsOn) {
	    // get the comments for a photo
	    GalleryCoreApi::requireOnce('modules/comment/classes/GalleryCommentHelper.class');

	    list ($ret, $comments) =
		GalleryCommentHelper::fetchComments($item->getId(), null, ORDER_ASCENDING);
	    if ($ret) {
		return $ret;
	    }
	    
	    // an array of the users who left comments indexed by commenterId
	    $commenters = array();
	    if (!empty($comments)) {
		for ($i = 0; $i < sizeof($comments); $i++) {
		    /* Get the commenter ids */
		    $commenters[$comments[$i]->getCommenterId()] = 1;
		}
		
		/* Load all the commenters user information */
		if (sizeof($commenters) > 0) {
		    list ($ret, $commentersList) =
			GalleryCoreApi::loadEntitiesById(array_keys($commenters));
		    if ($ret) {
			return $ret;
		    }
		}
		
		foreach ($commentersList as $commenter) {
		    $commenters[$commenter->getId()] = $commenter;
		}
	    }
	}

	// disable PHP script timeout feature
	// without this uploads of large images
	// may fail
	set_time_limit(0);

	$pid = $this->flickr->sync_upload ($path, 
					   $item->getTitle(), 
					   $item->getDescription(), 
					   $item->getKeywords() . ' gallery2flickr', 
					   $is_public,
					   $is_friend,
					   $is_family);
    
	GalleryCoreApi::releaseLocks($lock);

	if (!$pid) {
	    return false;
	}
    
	if ($commentsOn) {
	    // set the photo comments in flickr
	    define("FLICKR_COMMENT_DELIMITER", " :: ");
	    if (!empty($comments)) {
		for ($i = 0; $i < sizeof($comments); $i++) {
		    $currentComment = $comments[$i];

		    $flickrCommentText = "Gallery Comment" . FLICKR_COMMENT_DELIMITER;

		    if($commenters[$currentComment->getCommenterId()]->getFullName() != null) {
			$flickrCommentText .= $commenters[$currentComment->getCommenterId()]->getFullName();
		    } else {
			$flickrCommentText .= $commenters[$currentComment->getCommenterId()]->getUserName();
		    }

		    if(null != $currentComment->getSubject()) {
			$flickrCommentText .= FLICKR_COMMENT_DELIMITER . $currentComment->getSubject();
		    }

		    if(null != $currentComment->getComment()) {
			$flickrCommentText .= FLICKR_COMMENT_DELIMITER . $currentComment->getComment();
		    }

		    // TODO error handling on result code
		    $result = $this->flickr->photos_comments_addComment($pid,$flickrCommentText);
		}
	    }
	}

	return $pid;
    }
}

class FlickrToGalleryHelper {

    function accessAllowed() {
	list($ret, $token) = FlickrToGalleryHelper::retrieveToken();
	if ($ret) {
	    return array($ret, false);
	}

        if (!$token) {
	  return array(GalleryCoreApi::error(ERROR_PERMISSION_DENIED, __FILE__, __LINE__, 'No token found!'), false);
        }
	return array(null, true);
    }

    function adminAccessAllowed($user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	/* 
	 * This should be only accessible to registered users
	 */
	list ($ret, $anonymous) =
	    GalleryCoreApi::getPluginParameter('module', 'core', 'id.anonymousUser');
	if ($ret) {
	    return array($ret, null);
	}

	// The next gallery version allows locking
	//list ($ret, $user) = GalleryCoreApi::loadEntitiesById($user);
	//if ($ret) {
	// return array($ret, null);
        //}

	//if ($isAnonymous || $user->isLocked()) {
        if ($user == $anonymous) {
            return array(GalleryCoreApi::error(ERROR_PERMISSION_DENIED, __FILE__, __LINE__, 'Not allowed!'), null);
        }
	return array(null, true);
    }

    function storeFrob($frob, $user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	list($ret, $allowed) = FlickrToGalleryHelper::adminAccessAllowed();
	if ($ret) {
	    return array($ret, null);
	}

	$ret = GalleryCoreApi::setPluginParameter('module', 'Gallery2Flickr', 'ufrob', $frob, $user);
	if ($ret) {
	    return array($ret, null);
	}
    }

    function storeToken($token, $user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	list($ret, $allowed) = FlickrToGalleryHelper::adminAccessAllowed($user);
	if ($ret) {
	    return array($ret, null);
	}

	$ret = GalleryCoreApi::setPluginParameter('module', 'Gallery2Flickr', 'utoken', $token, $user);
	if ($ret) {
	    return array($ret, null);
	}
    }

    function hasFrob($user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	list($ret, $has) = FlickrToGalleryHelper::retrieveFrob($user);
	if ($ret || !$has) {
	  return false;
	}

	return true;
    }

    function hasToken($user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	list($ret, $has) = FlickrToGalleryHelper::retrieveToken($user);
	if ($ret || !$has) {
	  return false;
	}

	return true;
    }

    function deleteFrob($user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	if (FlickrToGalleryHelper::retrieveFrob($user)) {
	  $ret = GalleryCoreApi::removePluginParameter('module', 'Gallery2Flickr', 'ufrob', $user);
	}
	return false;
    }

    function deleteToken($user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	if (FlickrToGalleryHelper::retrieveToken($user)) {
	  $ret = GalleryCoreApi::removePluginParameter('module', 'Gallery2Flickr', 'utoken', $user);
	}
	return false;
    }

    function retrieveFrob($user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	list($ret, $allowed) = FlickrToGalleryHelper::adminAccessAllowed($user);
	if ($ret) {
	    return array($ret, null);
	}

	list ($ret, $frob) = GalleryCoreApi::getPluginParameter('module', 'Gallery2Flickr', 'ufrob', $user);
	if ($ret) {
	    return array($ret, null);
	}
	
	return array(null, $frob);
    }

    function retrieveToken($user = null) {

	if (!$user) {
	    global $gallery;
	    $user = $gallery->getActiveUserId();
	}

	list($ret, $allowed) = FlickrToGalleryHelper::adminAccessAllowed($user);
	if ($ret) {
	    return array($ret, null);
	}

	list ($ret, $token) = GalleryCoreApi::getPluginParameter('module', 'Gallery2Flickr', 'utoken', $user);
	if ($ret) {
	    return array($ret, null);
	}

	return array(null, $token);
    }

}
Return current item: Gallery2flickr