fb_autopost_entity.module in Facebook Autopost 7
Module implementation file
File
fb_autopost_entity/fb_autopost_entity.moduleView source
<?php
/**
* @file
* Module implementation file
*/
/**
* Implements hook_menu().
*/
function fb_autopost_entity_menu() {
$items['facebook-publication/%facebook_publication'] = array(
'title callback' => 'facebook_publication_title',
'title arguments' => array(
1,
),
'page callback' => 'facebook_publication_view',
'page arguments' => array(
1,
),
'access callback' => 'facebook_publication_access',
'access arguments' => array(
'view',
1,
),
'type' => MENU_CALLBACK,
);
return $items;
}
/**
* Title callback for a Facebook Publication page.
*/
function facebook_publication_title($facebook_publication) {
return $facebook_publication->label;
}
/**
* Implements hook_fb_autopost_publication_publish().
*/
function fb_autopost_entity_fb_autopost_publication_publish($publication, $result) {
// If the publication being published came from an entity, invokes
// hook_fb_autopost_publication_entity_publish.
// Publications that started with entities have an extra 'entity' field.
if (!empty($publication['entity'])) {
$publication_entity = unserialize($publication['entity']);
module_invoke_all('fb_autopost_publication_entity_publish', $publication_entity, $result);
}
}
/**
* Implements hook_entity_info().
*/
function fb_autopost_entity_entity_info() {
$return = array(
'facebook_publication' => array(
'label' => t('Facebook publication'),
'plural label' => t('Facebook publications'),
'description' => t('Facebook publications to be displayed in the configured Facebook page(s).'),
'entity class' => 'FacebookPublicationEntity',
'controller class' => 'EntityAPIController',
'base table' => 'facebook_publication',
'fieldable' => TRUE,
'view modes' => array(
'full' => array(
'label' => t('Full view'),
'custom settings' => FALSE,
),
),
'entity keys' => array(
'id' => 'fbpid',
'bundle' => 'type',
'label' => 'label',
),
'bundles' => array(),
'bundle keys' => array(
'bundle' => 'type',
),
'uri callback' => 'entity_class_uri',
'access callback' => 'facebook_publication_access',
'module' => 'fb_autopost_entity',
'metadata controller class' => 'FacebookPublicationMetadataController',
),
);
// Add bundle info but bypass entity_load() as we cannot use it here.
$types = db_select('facebook_publication_type', 'p')
->fields('p')
->execute()
->fetchAllAssoc('type');
foreach ($types as $type => $info) {
$return['facebook_publication']['bundles'][$type] = array(
'label' => $info->label,
'admin' => array(
'path' => 'admin/structure/facebook-publications/manage/%facebook_publication_type',
'real path' => 'admin/structure/facebook-publications/manage/' . $type,
'bundle argument' => 4,
'access arguments' => array(
'administer facebook publications',
),
),
);
}
// Support entity cache module.
if (module_exists('entitycache')) {
$return['facebook_publication']['field cache'] = FALSE;
$return['facebook_publication']['entity cache'] = TRUE;
}
$return['facebook_publication_type'] = array(
'label' => t('Facebook publication type'),
'plural label' => t('Facebook publication types'),
'description' => t('Facebook publication types of Graph API.'),
'entity class' => 'FacebookPublicationTypeEntity',
'controller class' => 'EntityAPIControllerExportable',
'base table' => 'facebook_publication_type',
'fieldable' => FALSE,
'bundle of' => 'facebook_publication',
'exportable' => TRUE,
'entity keys' => array(
'id' => 'id',
'name' => 'type',
'label' => 'label',
),
'access callback' => 'facebook_publication_type_access',
'module' => 'fb_autopost_entity',
// Enable the entity API's admin UI.
'admin ui' => array(
'path' => 'admin/structure/facebook-publications',
'file' => 'fb_autopost_entity.admin.inc',
'controller class' => 'FacebookPublicationTypeUIController',
),
);
return $return;
}
/**
* Menu argument loader; Load a Facebook publication type by string.
*
* @param string $type
* The machine-readable name of a Facebook publication type to load.
*
* @return array
* A Facebook publication type array or FALSE if $type does not exist.
*/
function facebook_publication_type_load($type) {
return facebook_publication_get_types($type);
}
/**
* Implements hook_permission().
*/
function fb_autopost_entity_permission() {
$permissions = array(
'administer facebook publication types' => array(
'title' => t('Administer Facebook publication types'),
'description' => t('Create and delete fields on Facebook publications, and set their permissions.'),
),
'administer facebook publications' => array(
'title' => t('Administer Facebook publications'),
'description' => t('Edit and view all Facebook publications.'),
),
);
// Generate per Facebook publication type permissions.
foreach (facebook_publication_get_types() as $type) {
$type_name = check_plain($type->type);
$permissions += array(
"edit own {$type_name} facebook publication" => array(
'title' => t('%type_name: Edit own Facebook publication', array(
'%type_name' => $type->label,
)),
),
"edit any {$type_name} facebook publication" => array(
'title' => t('%type_name: Edit any Facebook publication', array(
'%type_name' => $type->label,
)),
),
"view own {$type_name} facebook publication" => array(
'title' => t('%type_name: View own Facebook publication', array(
'%type_name' => $type->label,
)),
),
"view any {$type_name} facebook publication" => array(
'title' => t('%type_name: View any Facebook publication', array(
'%type_name' => $type->label,
)),
),
);
}
return $permissions;
}
/**
* Gets an array of all Facebook publication types, keyed by the type name.
*
* @param string $type_name
* If set, the type with the given name is returned.
*
* @return FacebookPublicationTypeEntity[]
* Depending whether $type isset, an array of Facebook publication types or a
* single one.
*/
function facebook_publication_get_types($type_name = NULL) {
$types = entity_load_multiple_by_name('facebook_publication_type', isset($type_name) ? array(
$type_name,
) : FALSE);
return isset($type_name) ? reset($types) : $types;
}
/**
* Fetch a Facebook publication object.
*
* @param int $fbpid
* Integer specifying the Facebook publication id.
* @param bool $reset
* A boolean indicating that the internal cache should be reset.
*
* @return FacebookPublicationEntity
* A fully-loaded $publications object or FALSE if it cannot be loaded.
*
* @see facebook_publication_load_multiple()
*/
function facebook_publication_load($fbpid, $reset = FALSE) {
$publications = facebook_publication_load_multiple(array(
$fbpid,
), array(), $reset);
return reset($publications);
}
/**
* Load multiple Facebook publications based on certain conditions.
*
* @param array $fbpids
* An array of Facebook publication IDs.
* @param array $conditions
* An array of conditions to match against the {facebook_publication} table.
* @param bool $reset
* A boolean indicating that the internal cache should be reset.
*
* @return array
* An array of Facebook publication objects, indexed by pid.
*
* @see entity_load()
* @see facebook_publication_load()
*/
function facebook_publication_load_multiple($fbpids = array(), $conditions = array(), $reset = FALSE) {
return entity_load('facebook_publication', $fbpids, $conditions, $reset);
}
/**
* Deletes a Facebook publication.
*/
function facebook_publication_delete(FacebookPublicationEntity $publication) {
$publication
->delete();
}
/**
* Delete multiple Facebook publications.
*
* @param array $fbpids
* An array of Facebook publication IDs.
*/
function facebook_publication_delete_multiple(array $fbpids) {
entity_get_controller('facebook_publication')
->delete($fbpids);
}
/**
* Create a new Facebook publication object.
*/
function facebook_publication_create(array $values) {
return new FacebookPublicationEntity($values);
}
/**
* Saves a Facebook publication to the database.
*
* @param FacebookPublicationEntity $publication
* The FacebookPublicationEntity object.
*/
function facebook_publication_save(FacebookPublicationEntity $publication) {
return $publication
->save();
}
/**
* Saves a Facebook publication type to the db.
*/
function facebook_publication_type_save(FacebookPublicationTypeEntity $type) {
$type
->save();
}
/**
* Deletes a Facebook publication type from.
*/
function facebook_publication_type_delete(FacebookPublicationTypeEntity $type) {
$type
->delete();
}
/**
* Implements hook_facebook_publication_type_insert().
*/
function fb_autopost_entity_facebook_publication_type_insert(FacebookPublicationTypeEntity $type) {
// Always rebuild the menu in case a Facebook publication type is inserted or
// changed. In order to avoid possible multiple rebuilds of modules we just do
// it always but once here.
variable_set('menu_rebuild_needed', TRUE);
}
/**
* Implements hook_facebook_publication_type_update().
*/
function fb_autopost_entity_facebook_publication_type_update(FacebookPublicationTypeEntity $type) {
// @see fb_autopost_entity_facebook_publication_type_insert()
variable_set('menu_rebuild_needed', TRUE);
}
/**
* Implements hook_facebook_publication_type_delete().
*/
function fb_autopost_entity_facebook_publication_type_delete($type) {
// Delete all Facebook publications of this type.
if ($fbpids = array_keys(facebook_publication_load_multiple(FALSE, array(
'type' => $type->type,
)))) {
facebook_publication_delete_multiple($fbpids);
}
// @see fb_autopost_entity_facebook_publication_type_insert()
variable_set('menu_rebuild_needed', TRUE);
}
/**
* Determines whether the given user has access to a Facebook publication.
*
* @param string $op
* The operation being performed. One of 'view', 'update', 'create', 'delete'
* or just 'edit' (being the same as 'create' or 'update').
* @param FacebookPublicationEntity $publication
* (optional) A Facebook publication to check access for. If nothing is given,
* access for all publications is determined.
* @param object $account
* The user to check for. Leave it to NULL to check for the global user.
*
* @return bool
* Whether access is allowed or not.
*
* @see hook_facebook_publication_access()
* @see fb_autopost_entity_facebook_publication_access()
*/
function facebook_publication_access($op, $publication = NULL, $account = NULL) {
if (user_access('administer facebook publications', $account)) {
return TRUE;
}
if ($op == 'create' || $op == 'update') {
$op = 'edit';
}
// Allow modules to grant / deny access.
$access = module_invoke_all('facebook_publication_access', $op, $publication, $account);
// Only grant access if at least one module granted access and no one denied
// access.
if (in_array(FALSE, $access, TRUE)) {
return FALSE;
}
elseif (in_array(TRUE, $access, TRUE)) {
return TRUE;
}
return FALSE;
}
/**
* Implements hook_facebook_publication_access().
*/
function fb_autopost_entity_facebook_publication_access($op, $publication = NULL, $account = NULL) {
// Don't grant access for users to delete their Facebook publications.
if (isset($publication) && ($type_name = $publication->type) && $op != 'delete') {
if (user_access("{$op} any {$type_name} facebook publication", $account)) {
return TRUE;
}
$account = isset($account) ? $account : $GLOBALS['user'];
if (isset($publication->uid) && $publication->uid == $account->uid && user_access("{$op} own {$type_name} facebook publication", $account)) {
return TRUE;
}
}
// Do not explicitly deny access so others may still grant access.
}
/**
* Access callback for the entity API.
*/
function facebook_publication_type_access($op, $type = NULL, $account = NULL) {
return user_access('administer facebook publication types', $account);
}
/**
* Renders a FacebookPublicationEntity.
*/
function facebook_publication_view(FacebookPublicationEntity $publication) {
$entities = entity_view('facebook_publication', array(
$publication,
));
return reset($entities);
}
/**
* The class used for Facebook publication entities.
*/
class FacebookPublicationEntity extends Entity {
/**
* The Facebook publication id.
*
* @var integer
*/
public $fbpid;
/**
* The name of the Facebook publication type.
*
* @var string
*/
public $type;
/**
* The Facebook publication label.
*
* @var string
*/
public $label;
/**
* The user id of the Facebook publication owner.
*
* @var integer
*/
public $uid;
/**
* The Unix timestamp when the Facebook publication was created.
*
* @var integer
*/
public $created;
/**
* The Unix timestamp when the Facebook publication was most recently saved.
*
* @var integer
*/
public $changed;
/**
* The ID string returned from Facebook on publication.
*
* @var string
*/
public $facebook_id;
/**
* Entity constructor.
*/
public function __construct($values = array()) {
if (isset($values['user'])) {
$this
->setUser($values['user']);
unset($values['user']);
}
if (isset($values['type']) && is_object($values['type'])) {
$values['type'] = $values['type']->type;
}
if (!isset($values['label']) && isset($values['type']) && ($type = facebook_publication_get_types($values['type']))) {
// Initialize the label with the type label, so newly created publications
// have that as interim label.
$values['label'] = $type->label;
}
parent::__construct($values, 'facebook_publication');
}
/**
* Returns the user owning this Facebook publication.
*/
public function user() {
return user_load($this->uid);
}
/**
* Sets a new user owning this Facebook publication.
*
* @param object $account
* The user account object or the user account id (uid).
*/
public function setUser($account) {
$this->uid = is_object($account) ? $account->uid : $account;
}
/**
* Gets the associated Facebook publication type object.
*
* @return FacebookPublicationTypeEntity
* Returns the type entity.
*/
public function type() {
return facebook_publication_get_types($this->type);
}
/**
* Gets the associated facebook_id.
*
* @return string
* String representing the Facebook ID.
*/
public function facebookid() {
return $this->facebook_id;
}
/**
* Returns the full url() for the Facebook publication.
*/
public function url() {
$uri = $this
->uri();
return url($uri['path'], $uri);
}
/**
* Returns the drupal path to this Facebook publication.
*/
public function path() {
$uri = $this
->uri();
return $uri['path'];
}
/**
* Gets the default URI for the publication.
*/
public function defaultUri() {
return array(
// TODO: Define this URL in hook_menu.
'path' => 'facebook-publication/' . $this->fbpid,
);
}
/**
* Build entity content based on $view_mode and $lagcode.
*/
public function buildContent($view_mode = 'full', $langcode = NULL) {
$content = array();
// Assume newly create objects are still empty.
if (!empty($this->is_new)) {
$content['empty']['#markup'] = '<em class="facebook-pulbication-no-data">' . t('There is no Facebook publication data yet.') . '</em>';
}
return entity_get_controller($this->entityType)
->buildContent($this, $view_mode, $langcode, $content);
}
/**
* Save the entity.
*/
public function save() {
// Care about setting created and changed values. But do not automatically
// set a created values for already existing Facebook publications.
if (empty($this->created) && (!empty($this->is_new) || !$this->fbpid)) {
$this->created = REQUEST_TIME;
}
$this->changed = REQUEST_TIME;
parent::save();
}
/**
* Get the property names out of the field names associated to this entity.
*
* @param array $field_names
* A numeric array containing the field names to translate.
*
* @return array
* A keyed array with field name => property name.
*/
public function getFieldProperties($field_names = NULL) {
if (empty($field_names)) {
// Get all the field names associated with this entity bundle.
$field_names = array_keys(field_info_instances('facebook_publication', $publication->type));
}
$output = array();
foreach ($field_names as $field_name) {
// Remove 'field_facebook_' prefix from field names.
$output[$field_name] = substr($field_name, strlen('field_facebook_'));
}
// Allow other modules to alter this default behavior.
drupal_alter('field_property_data', $output);
return $output;
}
}
/**
* Use a separate class for Facebook publication types so we can specify some
* defaults modules may alter.
*/
class FacebookPublicationTypeEntity extends Entity {
public $type;
public $label;
/**
* Entity type constructor.
*/
public function __construct($values = array()) {
parent::__construct($values, 'facebook_publication_type');
}
/**
* Returns whether the Facebook publication type is locked.
*
* Facebook publication types provided in code are automatically treated as
* locked, as well as any fixed Facebook publication type. Locked may not be
* deleted or renamed.
*/
public function isLocked() {
return isset($this->status) && empty($this->is_new) && ($this->status & ENTITY_IN_CODE || $this->status & ENTITY_FIXED);
}
}
/**
* Helper function to translate from field names to property names for the SDK.
*
* @param FacebookPublicationEntity $publication
* Entity to extract the properties from.
*
* @return array
* An array of property names with their corresponding values
*/
function fb_autopost_entity_get_properties(FacebookPublicationEntity $publication) {
$output = array();
// By default assume the properties are like field names minus
// 'field_facebook_'. Get all the field names associated with this entity
// bundle.
$field_names = array_keys(field_info_instances('facebook_publication', $publication->type));
// We will need a entity wrapper to access the field values.
$wrapper = entity_metadata_wrapper('facebook_publication', $publication);
// Get a keyed array to translate field names into Facebook property names.
$field_properties = $publication
->getFieldProperties($field_names);
// Iterate over each field to fetch the actual value.
foreach ($field_names as $field_name) {
$value = $wrapper->{$field_name}
->value();
if (isset($value)) {
$output[$field_properties[$field_name]] = $value;
}
}
return $output;
}
/**
* Factory method.
*
* @param string $type
* Facebook publication type.
*/
function facebook_autopost_entity($type) {
switch ($type) {
case 'photo':
$fb = new FBAutopostEntityPhoto();
break;
case 'event':
$fb = new FBAutopostEntityEvent();
break;
case 'post':
$fb = new FBAutopostEntityPost();
break;
default:
$fb = new FBAutopostEntity();
break;
}
if ($type) {
$fb
->setType($type);
}
// Allow other modules to alter $fb. Useful for altering the underlying
// BaseFacebook object for things like adding proxy support to curl options
drupal_alter('facebook_autopost_entiy_fb', $fb);
return $fb;
}
/**
* Implements hook_views_api().
*/
function fb_autopost_entity_views_api() {
return array(
'api' => 3,
);
}
Functions
Name | Description |
---|---|
facebook_autopost_entity | Factory method. |
facebook_publication_access | Determines whether the given user has access to a Facebook publication. |
facebook_publication_create | Create a new Facebook publication object. |
facebook_publication_delete | Deletes a Facebook publication. |
facebook_publication_delete_multiple | Delete multiple Facebook publications. |
facebook_publication_get_types | Gets an array of all Facebook publication types, keyed by the type name. |
facebook_publication_load | Fetch a Facebook publication object. |
facebook_publication_load_multiple | Load multiple Facebook publications based on certain conditions. |
facebook_publication_save | Saves a Facebook publication to the database. |
facebook_publication_title | Title callback for a Facebook Publication page. |
facebook_publication_type_access | Access callback for the entity API. |
facebook_publication_type_delete | Deletes a Facebook publication type from. |
facebook_publication_type_load | Menu argument loader; Load a Facebook publication type by string. |
facebook_publication_type_save | Saves a Facebook publication type to the db. |
facebook_publication_view | Renders a FacebookPublicationEntity. |
fb_autopost_entity_entity_info | Implements hook_entity_info(). |
fb_autopost_entity_facebook_publication_access | Implements hook_facebook_publication_access(). |
fb_autopost_entity_facebook_publication_type_delete | Implements hook_facebook_publication_type_delete(). |
fb_autopost_entity_facebook_publication_type_insert | Implements hook_facebook_publication_type_insert(). |
fb_autopost_entity_facebook_publication_type_update | Implements hook_facebook_publication_type_update(). |
fb_autopost_entity_fb_autopost_publication_publish | Implements hook_fb_autopost_publication_publish(). |
fb_autopost_entity_get_properties | Helper function to translate from field names to property names for the SDK. |
fb_autopost_entity_menu | Implements hook_menu(). |
fb_autopost_entity_permission | Implements hook_permission(). |
fb_autopost_entity_views_api | Implements hook_views_api(). |
Classes
Name | Description |
---|---|
FacebookPublicationEntity | The class used for Facebook publication entities. |
FacebookPublicationTypeEntity | Use a separate class for Facebook publication types so we can specify some defaults modules may alter. |