liberty
[ class tree: liberty ] [ index: liberty ] [ all elements ]

Source for file LibertyContent.php

Documentation is available at LibertyContent.php

  1. <?php
  2. /**
  3. /* Management of Liberty content
  4. *
  5. @package  liberty
  6. @author   spider <spider@steelsun.com>
  7. */
  8.  
  9. // +----------------------------------------------------------------------+
  10. // | Copyright (c) 2004, bitweaver.org
  11. // +----------------------------------------------------------------------+
  12. // | All Rights Reserved. See below for details and a complete list of authors.
  13. // | Licensed under the GNU LESSER GENERAL PUBLIC LICENSE. See http://www.gnu.org/copyleft/lesser.html for details
  14. // |
  15. // | For comments, please use phpdocu.sourceforge.net documentation standards!!!
  16. // | -> see http://phpdocu.sourceforge.net/
  17. // +----------------------------------------------------------------------+
  18. // | Authors: spider <spider@steelsun.com>
  19. // +----------------------------------------------------------------------+
  20.  
  21. /**
  22.  * Maximum lengths for database fields
  23.  */
  24. if!defined'BIT_CONTENT_MAX_TITLE_LEN' ) ) {
  25.     define'BIT_CONTENT_MAX_TITLE_LEN'160);
  26. }
  27. define'BIT_CONTENT_MAX_LANGUAGE_LEN'4);
  28. define'BIT_CONTENT_MAX_IP_LEN'39);
  29. define'BIT_CONTENT_MAX_FORMAT_GUID_LEN'16);
  30.  
  31. if!defined'BIT_CONTENT_DEFAULT_STATUS' ) ) {
  32.     define'BIT_CONTENT_DEFAULT_STATUS'50);
  33. }
  34. //$gBitSystem->getConfig( 'liberty_status_deleted', -999 ) );
  35. //$gBitSystem->getConfig( 'liberty_status_threshold_private', -40 ) );
  36. //$gBitSystem->getConfig( 'liberty_status_threshold_protected', -20 ) );
  37. //$gBitSystem->getConfig( 'liberty_status_threshold_hidden', -10 ) );
  38.  
  39. /**
  40.  * required setup
  41.  */
  42. require_onceLIBERTY_PKG_PATH.'LibertyBase.php' );
  43.  
  44. define'LIBERTY_SPLIT_REGEX'"!\.{3}split\.{3}[\t ]*\n?!" );
  45.  
  46. /**
  47.  * Virtual base class (as much as one can have such things in PHP) for all
  48.  * derived tikiwiki classes that require database access.
  49.  *
  50.  * @package liberty
  51.  */
  52. class LibertyContent extends LibertyBase implements BitCacheable {
  53.     /**
  54.      * Content Id if an object has been loaded
  55.      * @public
  56.      */
  57.     var $mContentId;
  58.  
  59.     /**
  60.      * If this content is being viewed within a structure
  61.      * @public
  62.      */
  63.     var $mStructureId;
  64.  
  65.     /**
  66.      * Content type GUID for this LibertyContent object
  67.      * @public
  68.      */
  69.     var $mContentTypeGuid;
  70.  
  71.     /**
  72.      * Content type hash for this LibertyContent object
  73.      * @public
  74.      */
  75.     var $mType;
  76.  
  77.     /**
  78.      *Permissions hash specific to the user accessing this LibertyContetn object
  79.      * @public
  80.      */
  81.     var $mUserContentPerms;
  82.  
  83.     /**
  84.      * Preferences hash specific to this LibertyContent object - accessed via getPreference/storePreference
  85.      * @private
  86.      */
  87.     var $mPrefs = NULL;
  88.  
  89.     /**
  90.      * Control permission specific to this LibertyContent type
  91.      * @private
  92.      */
  93.     var $mViewContentPerm;
  94.     var $mUpdateContentPerm;
  95.     var $mCreateContentPerm;
  96.     var $mExpungeContentPerm;
  97.     var $mAdminContentPerm;
  98.  
  99.     /**
  100.      * Construct an empty LibertyBase object with a blank permissions array
  101.      */
  102.     function __construct({
  103.         parent::__construct();
  104.         $this->mPrefs = NULL// init to NULL so getPreference can determine if a load is necessary
  105.  
  106.         // NOTE: we are not assigning anything to mViewContentPerm. if this is empty, we will return TRUE in hasViewPermission()
  107.         ifempty$this->mUpdateContentPerm )) {
  108.             $this->mUpdateContentPerm = 'p_admin_content';
  109.         }
  110.  
  111.         ifempty$this->mCreateContentPerm )) {
  112.             $this->mCreateContentPerm = 'p_admin_content';
  113.         }
  114.  
  115.         ifempty$this->mExpungeContentPerm )) {
  116.             $this->mExpungeContentPerm = 'p_admin_content';
  117.         }
  118.  
  119.         ifempty$this->mAdminContentPerm )) {
  120.             $this->mAdminContentPerm = 'p_admin_content';
  121.         }
  122.     }
  123.  
  124.     public static function isCacheableClass({
  125.         global $gBitSystem;
  126.         return !$gBitSystem->isLive();
  127.     }
  128.  
  129.  
  130.     public function isCacheableObject({
  131.         return parent::isCacheableObject(&& !empty$this->mContentId );
  132.     }
  133.  
  134.     public function getCacheKey({
  135.         if$this->isValid() ) {
  136.             return $this->mContentId;
  137.         }
  138.     }
  139.  
  140.     /**
  141.      * load Assume a derived class has joined on the liberty_content table, and loaded it's columns already.
  142.      *
  143.      * @access public
  144.      * @return void 
  145.      */
  146.     function load$pContentId NULL$pPluginParams NULL {
  147.         if!empty$this->mInfo['content_type_guid')) {
  148.             global $gLibertySystem$gBitSystem$gBitUser;
  149.             $this->loadPreferences();
  150.             $this->mInfo['content_type'$gLibertySystem->mContentTypes[$this->mInfo['content_type_guid']];
  151.             $this->invokeServices'content_load_function'$this );
  152.         }
  153.     }
  154.  
  155.     /**
  156.      * Verify the core class data required to update the liberty_content table entries
  157.      *
  158.      * Verify will build an array [content_store] with all of the required values
  159.      * and populate it with the relevent data to create/update the liberty_content
  160.      * table record
  161.      *
  162.      * @param array $pParamHash Array of content data to be stored
  163.      *
  164.      * @param array $pParamHash[content_id] 
  165.      * @param array $pParamHash[user_id] 
  166.      * @param array $pParamHash[modifier_user_id] 
  167.      * @param array $pParamHash[created] 
  168.      * @param array $pParamHash[last_modified] 
  169.      * @param array $pParamHash[content_type_guid] 
  170.      * @param array $pParamHash[format_guid] 
  171.      * @param array $pParamHash[last_hit] 
  172.      * @param array $pParamHash[event_time] 
  173.      * @param array $pParamHash[hits] 
  174.      * @param array $pParamHash[lang_code] 
  175.      * @param array $pParamHash[title] 
  176.      * @param array $pParamHash[ip] 
  177.      * @param array $pParamHash[edit] 
  178.      * @access public
  179.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  180.      */
  181.     function verify&$pParamHash {
  182.         global $gLibertySystem$gBitSystem$gBitLanguage$gBitUser;
  183.  
  184.         // It is possible a derived class set this to something different
  185.         ifempty$pParamHash['content_type_guid') ) {
  186.             $pParamHash['content_type_guid'$this->mContentTypeGuid;
  187.         }
  188.  
  189.         ifempty$pParamHash['user_id') ) {
  190.             $pParamHash['user_id'$gBitUser->getUserId();
  191.         }
  192.  
  193.         if!@$this->verifyId$pParamHash['content_id') ) {
  194.             if!@$this->verifyId$this->mContentId ) ) {
  195.                 // These should never be updated, only inserted
  196.                 $pParamHash['content_store']['created'!empty$pParamHash['created'$pParamHash['created'$gBitSystem->getUTCTime();
  197.                 // This may get overridden by owner set
  198.                 $pParamHash['content_store']['user_id'$pParamHash['user_id'];
  199.                 // Set a default status when creating if none is set
  200.                 // This may get overwritten below
  201.                 ifempty($pParamHash['content_store']['content_status_id') ){
  202.                         $pParamHash['content_store']['content_status_id'$gBitSystem->getConfig('liberty_default_status'BIT_CONTENT_DEFAULT_STATUS);
  203.                 }
  204.             else {
  205.                 $pParamHash['content_id'$this->mContentId;
  206.             }
  207.         }
  208.  
  209.         if@BitBase::verifyId$pParamHash['content_id')) {
  210.             $pParamHash['content_store']['content_id'$pParamHash['content_id'];
  211.         }
  212.  
  213.         // Are we allowed to override owner?
  214.         if!empty($pParamHash['owner_id') ) {
  215.             if$gBitUser->isAdmin(|| ($gBitSystem->isFeatureActive('liberty_allow_change_owner'&& $gBitUser->hasPermission('p_liberty_edit_content_owner'&& !empty($pParamHash['owner_id']&& !empty($pParamHash['current_owner_id']&& $pParamHash['owner_id'!= $pParamHash['current_owner_id']) ) {
  216.                 // If an owner is being set override user_id
  217.                 $pParamHash['content_store']['user_id'$pParamHash['owner_id'];
  218.             }
  219.         }
  220.  
  221.         // Do we need to change the status
  222.         if (!empty($pParamHash['content_status_id'])) {
  223.             if$this->hasUserPermission'p_liberty_edit_content_status' || $gBitUser->hasUserPermission'p_liberty_edit_all_status') ) {
  224.                 $allStatus $this->getAvailableContentStatuses();
  225.                 if (empty($allStatus[$pParamHash['content_status_id']])) {
  226.                     $this->mErrors['content_status_id'"No such status ID or permission denied.";
  227.                 else {
  228.                     $pParamHash['content_store']['content_status_id'$pParamHash['content_status_id'];
  229.                 }
  230.             }
  231.         }
  232.  
  233.         $pParamHash['field_changed'empty$pParamHash['content_id')
  234.                     || (!empty($this->mInfo["data"]&& !empty($pParamHash["edit"]&& (md5($this->mInfo["data"]!= md5($pParamHash["edit"])))
  235.                     || (!empty($pParamHash["title"]&& !empty($this->mInfo["title"]&& (md5($this->mInfo["title"]!= md5($pParamHash["title"])))
  236.                     || (!empty($pParamHash["edit_comment"]&& !empty($this->mInfo["edit_comment"]&& (md5($this->mInfo["edit_comment"]!= md5($pParamHash["edit_comment"])));
  237.         // check some lengths, if too long, then truncate
  238.         if!empty$pParamHash['title') ) {
  239.             $pParamHash['content_store']['title'substrpreg_replace'/:space:+/m'' '$pParamHash['title')0BIT_CONTENT_MAX_TITLE_LEN );
  240.         elseifisset$pParamHash['title') ) {
  241.             $pParamHash['content_store']['title'NULL;
  242.         }
  243.  
  244.         // get the lang code from $_REQUEST if it's not set
  245.         if!empty$pParamHash['lang_code'&& in_array$pParamHash['lang_code']array_keys$gBitLanguage->mLanguageList ) ) ) {
  246.             $pParamHash['content_store']['lang_code'$pParamHash['lang_code'];
  247.         elseif!empty$_REQUEST['i18n']['lang_code'&& in_array$_REQUEST['i18n']['lang_code']array_keys$gBitLanguage->mLanguageList ) ) ) {
  248.             $pParamHash['content_store']['lang_code'$_REQUEST['i18n']['lang_code'];
  249.         }
  250.  
  251.         $pParamHash['content_store']['last_modified'!empty$pParamHash['last_modified'$pParamHash['last_modified'$gBitSystem->getUTCTime();
  252.         if!empty$pParamHash['event_time') ) {
  253.             $pParamHash['content_store']['event_time'$pParamHash['event_time'];
  254.         }
  255.  
  256.         // WARNING: Assume WIKI if t
  257.         if!empty$pParamHash['content_id') ) {
  258.             // do NOT allow changing of content_type_guid in update for safety of overridden secondary classes (like BitBook )
  259.             unset$pParamHash['content_store']['content_type_guid');
  260.         elseifempty$pParamHash['content_type_guid') ) {
  261.             $this->mErrors['content_type'tra'System Error: Unknown content type' );
  262.         else {
  263.             $pParamHash['content_store']['content_type_guid'$pParamHash['content_type_guid'];
  264.         }
  265.  
  266.         // setup some required defaults if not defined
  267.         ifempty$pParamHash['ip') ) {
  268.             ifempty$_SERVER["REMOTE_ADDR") ) {
  269.                 $pParamHash['ip''127.0.0.1';
  270.             else {
  271.                 $pParamHash['ip'$_SERVER["REMOTE_ADDR"];
  272.             }
  273.         }
  274.         $pParamHash['content_store']['ip'$pParamHash['ip'];
  275.  
  276.         if!@$this->verifyId$pParamHash['modifier_user_id') ) {
  277.             $pParamHash['modifier_user_id'$gBitUser->getUserId();
  278.         }
  279.         $pParamHash['content_store']['modifier_user_id'$pParamHash['modifier_user_id'];
  280.  
  281.         ifempty$pParamHash['format_guid') ) {
  282.             $pParamHash['format_guid'$gBitSystem->getConfig'default_format''tikiwiki' );
  283.         }
  284.         $pParamHash['content_store']['format_guid'$pParamHash['format_guid'];
  285.  
  286.         if!empty$pParamHash['hits') ) {
  287.             $pParamHash['content_store']['hits'$pParamHash['hits'1;
  288.             $pParamHash['content_store']['last_hit'$gBitSystem->getUTCTime();
  289.         }
  290.  
  291.         if!empty$pParamHash['edit'&& $func $gLibertySystem->getPluginFunction$pParamHash['format_guid']'verify_function' ) ) {
  292.             $error $func$pParamHash );
  293.             if$error {
  294.                 $this->mErrors['format'$error;
  295.             }
  296.         }
  297.  
  298.         if!empty$pParamHash['content_store']['data')) {
  299.             $this->filterData$pParamHash['content_store']['data']$pParamHash['content_store']'prestore' );
  300.         else {
  301.             // someone has deleted the data entirely - common for fisheye
  302.             $pParamHash['content_store']['data'NULL;
  303.         }
  304.         $pParamHash['content_store']['format_guid'$pParamHash['format_guid'];
  305.  
  306.         if!@BitBase::verifyId$this->mInfo['version') ) {
  307.             $pParamHash['content_store']['version'1;
  308.         else {
  309.             $pParamHash['content_store']['version'$this->mInfo['version'1;
  310.         }
  311.  
  312.         // search related stuff
  313.         if ( ( !(isset($this->mInfo['no_index']and $this->mInfo['no_index'== true ) ) and !isset($this->mInfo['index_data']) ) {
  314.             $this->mInfo['index_data'"";
  315.             if isset($pParamHash["title"]) )       $this->mInfo['index_data'.= $pParamHash["title"' ';
  316.             if isset($pParamHash["author_name"]) ) $this->mInfo['index_data'.= $pParamHash["author_name"' ';
  317.             if isset($pParamHash["edit"]) )        $this->mInfo['index_data'.= $pParamHash["edit"];
  318.         }
  319.  
  320.         // content preferences
  321.         $prefs array();
  322.         if$gBitUser->hasPermission'p_liberty_enter_html' ) ) {
  323.             $prefs['content_enter_html';
  324.         }
  325.  
  326.         foreach$prefs as $pref {
  327.             if!empty$pParamHash['preferences'][$pref) ) {
  328.                 $pParamHash['preferences_store'][$pref$pParamHash['preferences'][$pref];
  329.             else {
  330.                 $pParamHash['preferences_store'][$prefNULL;
  331.             }
  332.         }
  333.         $pParamHash['data_store']['summary'!empty$pParamHash['summary'$pParamHash['summary'NULL ;
  334.  
  335.         // call verify service to see if any services have errors
  336.         $this->invokeServices'content_verify_function'$pParamHash );
  337.  
  338.         returncount$this->mErrors == );
  339.     }
  340.  
  341.     /**
  342.      * Create a new content object or update an existing one
  343.      *
  344.      * @param array Array of content data to be stored <br>
  345.      *  See verify for details of the values required
  346.      */
  347.     function store&$pParamHash {
  348.         global $gLibertySystem;
  349.         ifLibertyContent::verify$pParamHash ) ) {
  350.             $this->mDb->StartTrans();
  351.             $table BIT_DB_PREFIX."liberty_content";
  352.             if!@$this->verifyId$pParamHash['content_id') ) {
  353.                 // make sure some variables are stuff in case services need getObjectType, mContentId, etc...
  354.                 $this->mContentId = $pParamHash['content_id'$pParamHash['content_store']['content_id'$this->mDb->GenID'liberty_content_id_seq' );
  355.                 $this->mContentTypeGuid = $this->mInfo['content_type_guid'$pParamHash['content_type_guid'];
  356.                 $result $this->mDb->associateInsert$table$pParamHash['content_store');
  357.                 $this->mLogs['content_store'"Created";
  358.             else {
  359.                 if!empty$pParamHash['content_store']['title'&& !empty$this->mInfo['title'&& $pParamHash['content_store']['title'!= $this->mInfo['title'{
  360.                     $this->mLogs['rename_page'"Renamed from {$this->mInfo['title']} to {$pParamHash['content_store']['title']}.";
  361.                 }
  362.                 $result $this->mDb->associateUpdate$table$pParamHash['content_store']array("content_id" => $pParamHash['content_id') );
  363.                 $this->mLogs['content_store'"Updated";
  364.             }
  365.  
  366.             if!empty$pParamHash['force_history'|| empty$pParamHash['minor'&& $this->getField'version' && $pParamHash['field_changed')) {
  367.                 ifempty$pParamHash['has_no_history') ) {
  368.                     $this->storeHistory();
  369.                 }
  370.                 //$action = "Created";
  371.                 //$mailEvents = 'wiki_page_changes';
  372.             }
  373.  
  374.             $this->storeAliases$pParamHash );
  375.  
  376.             $this->invokeServices'content_store_function'$pParamHash );
  377.  
  378.             // Call the formatter's save
  379.             if!empty$pParamHash['content_store']['data')) {
  380.                 if$func $gLibertySystem->getPluginFunction$pParamHash['format_guid']'store_function' ) ) {
  381.                     $ret $func$pParamHash );
  382.                 }
  383.  
  384.                 // post store filter - this is needed to deal with filters that need the content_id on the first save
  385.                 $this->filterData$pParamHash['content_store']['data']$pParamHash['content_store']'poststore' );
  386.             }
  387.             LibertyContent::expungeCacheFile$pParamHash['content_id');
  388.  
  389.             // store data
  390.             foreach$pParamHash['data_store'AS $dataType => $data {
  391.                 $this->storeData$data$dataType );
  392.             }
  393.  
  394.             // store content preferences
  395.             if@is_array$pParamHash['preferences_store') ) {
  396.                 foreach$pParamHash['preferences_store'as $pref => $value {
  397.                     $this->storePreference$pref$value );
  398.                 }
  399.             }
  400.  
  401.             // store hits and last hit
  402.             if!empty$pParamHash['content_store']['hits')  ) {
  403.                 $this->setHits($pParamHash['content_store']['hits']$pParamHash['content_store']['last_hit']);
  404.             }
  405.             // store any messages in the logs
  406.             $this->storeActionLog$pParamHash );
  407.  
  408.  
  409.             $this->mDb->CompleteTrans();
  410.         }
  411.         returncount$this->mErrors == );
  412.     }
  413.  
  414.     /**
  415.      * Delete comment entries relating to the content object
  416.      *
  417.      * @access public
  418.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  419.      */
  420.     function expungeComments({
  421.         require_onceLIBERTY_PKG_PATH.'LibertyComment.php' );
  422.         // Delete all comments associated with this piece of content
  423.         $query "SELECT `comment_id` FROM `".BIT_DB_PREFIX."liberty_comments` WHERE `root_id` = ?";
  424.         if$commentIds $this->mDb->getCol($queryarray$this->mContentId ) ) ) {
  425.             foreach ($commentIds as $commentId{
  426.                 $tmpComment new LibertyComment($commentId);
  427.                 $tmpComment->expunge();
  428.             }
  429.         }
  430.         return TRUE;
  431.     }
  432.  
  433.     /**
  434.      * Delete content object and all related records
  435.      *
  436.      * @access public
  437.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  438.      */
  439.     function expunge({
  440.         global $gBitSystem$gLibertySystem;
  441.         $ret FALSE;
  442.         if$this->isValid() ) {
  443.             $this->mDb->StartTrans();
  444.             $this->expungeComments();
  445.  
  446.             // services, filters and cache
  447.             $this->invokeServices'content_expunge_function'$this );
  448.             if(  $this->getField'format_guid' && $func $gLibertySystem->getPluginFunction$this->getField'format_guid' )'expunge_function' ) ) {
  449.                 $func$this->mContentId );
  450.             }
  451.             $this->filterData$this->mInfo['data']$this->mInfo'expunge' );
  452.             LibertyContent::expungeCacheFile$this->mContentId );
  453.  
  454.             // remove favorites - this probably should be a content_expunge_function in users
  455.             $this->mDb->query"DELETE FROM `".BIT_DB_PREFIX."users_favorites_map` WHERE `favorite_content_id`=?"array$this->mContentId ) );
  456.  
  457.             // remove entries in the history
  458.             $this->expungeVersion();
  459.  
  460.             // Remove individual permissions for this object if they exist
  461.             $query "delete from `".BIT_DB_PREFIX."liberty_content_permissions` where `content_id`=?";
  462.             $result $this->mDb->query$queryarray$this->mContentId ) );
  463.  
  464.             // Remove aliases
  465.             $this->mDb->query"DELETE FROM `".BIT_DB_PREFIX."liberty_aliases` WHERE `content_id`=?"array$this->mContentId ) );
  466.  
  467.             // Remove structures
  468.             // it's not this simple. what about orphans? needs real work. :( xoxo - spider
  469. //            $query = "DELETE FROM `".BIT_DB_PREFIX."liberty_structures` WHERE `content_id` = ?";
  470. //            $result = $this->mDb->query( $query, array( $this->mContentId ) );
  471.  
  472.             // Remove any queued data processing (images, movies, etc.)
  473.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_process_queue` WHERE `content_id` = ?";
  474.             $result $this->mDb->query$queryarray$this->mContentId ) );
  475.  
  476.             // Remove data
  477.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_content_data` WHERE `content_id` = ?";
  478.             $result $this->mDb->query$queryarray$this->mContentId ) );
  479.  
  480.             // Remove hits
  481.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_content_hits` WHERE `content_id` = ?";
  482.             $result $this->mDb->query$queryarray$this->mContentId ) );
  483.  
  484.             // Remove content preferences
  485.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_content_prefs` WHERE `content_id` = ?";
  486.             $result $this->mDb->query$queryarray$this->mContentId ) );
  487.  
  488.             // Remove content links
  489.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_content_links` WHERE `to_content_id` = ? or `from_content_id` = ?";
  490.             $result $this->mDb->query$queryarray$this->mContentId$this->mContentId ) );
  491.  
  492.             // Remove content
  493.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_content` WHERE `content_id` = ?";
  494.             $result $this->mDb->query$queryarray$this->mContentId ) );
  495.  
  496.             $this->mLogs['content_expunge'"Deleted";
  497.             $this->storeActionLog();
  498.  
  499.             $this->mDb->CompleteTrans();
  500.             $ret TRUE;
  501.  
  502.             parent::expunge();
  503.         }
  504.         return $ret;
  505.     }
  506.  
  507.     /**
  508.      * storeAliases will store aliases to a given content item
  509.      *
  510.      * @access public
  511.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  512.      */
  513.     function storeAliases$pParamHash {
  514.         $ret FALSE;
  515.         if$this->isValid(&& isset$pParamHash['alias_string']) ) {
  516.             $this->mDb->query"DELETE FROM `".BIT_DB_PREFIX."liberty_aliases` WHERE `content_id`=?"array$this->mContentId ) );
  517.             $trimmedAliases trim$pParamHash['alias_string');
  518.             if!empty$trimmedAliases && $aliases explode"\n"$trimmedAliases ) ) {
  519.                 foreach$aliases as $a {
  520.                     $this->mDb->query"INSERT INTO `".BIT_DB_PREFIX."liberty_aliases` (`content_id`, `alias_title`) VALUES (?,?)"array$this->mContentIdtrim$a ) ) );
  521.                 }
  522.             }
  523.             $ret TRUE;
  524.         }
  525.         return $ret;
  526.     }
  527.  
  528.     /**
  529.      * storeHistory will store the previous data into the history table for reference
  530.      *
  531.      * @access public
  532.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  533.      */
  534.     function storeHistory({
  535.         global $gBitSystem;
  536.  
  537.         $ret FALSE;
  538.         if$this->isValid() ) {
  539.             $storeHash array(
  540.                 "content_id"      => $this->mContentId,
  541.                 "version"         => $this->getField"version" ),
  542.                 "last_modified"   => $this->getField"last_modified" ),
  543.                 "user_id"         => $this->getField"modifier_user_id" ),
  544.                 "ip"              => $this->getField"ip" ),
  545.                 "data"            => $this->getField"data" ),
  546.                 "summary"         => $this->getField"summary" ),
  547.                 "history_comment" => (string)substr$this->getField"edit_comment" )0200 ),
  548.                 "format_guid"     => $this->getField"format_guid"$gBitSystem->getConfig"default_format""tikiwiki" )),
  549.             );
  550.             $this->mDb->associateInsertBIT_DB_PREFIX."liberty_content_history"$storeHash );
  551.             $ret TRUE;
  552.         }
  553.         return$ret );
  554.     }
  555.  
  556.     /**
  557.      * Get count of the number of historic records for the page
  558.      *
  559.      * @access public
  560.      * @return count 
  561.      */
  562.     function getHistoryCount({
  563.         $ret NULL;
  564.         if$this->isValid() ) {
  565.             $query "
  566.                 SELECT COUNT(*) AS `hcount`
  567.                 FROM `".BIT_DB_PREFIX."liberty_content_history`
  568.                 WHERE `content_id` = ?";
  569.             $rs $this->mDb->query($queryarray($this->mContentId));
  570.             $ret $rs->fields['hcount'];
  571.         }
  572.         return $ret;
  573.     }
  574.  
  575.     /**
  576.      * Get complete set of historical data in order to display a given wiki page version
  577.      *
  578.      * @param array $pVersion 
  579.      * @param array $pUserId 
  580.      * @param int $pOffset 
  581.      * @param array $max_records 
  582.      * @access public
  583.      * @return array of mInfo data
  584.      */
  585.     function getHistory$pVersion=NULL$pUserId=NULL$pOffset 0$max_records = -{
  586.         $ret NULL;
  587.         $cant 0;
  588.         if$this->isValid() ) {
  589.             global $gBitSystem;
  590.  
  591.             $selectSql '';
  592.             $joinSql '';
  593.             $whereSql '';
  594.             $bindVars array();
  595.             $this->getServicesSql'content_list_history_sql_function'$selectSql$joinSql$whereSql$bindVars );
  596.  
  597.             $versionSql '';
  598.             if@BitBase::verifyId$pUserId ) ) {
  599.                 $bindVars[$pUserId;
  600.                 $whereSql .= ' th.`user_id`=? ';
  601.             else {
  602.                 $bindVars[$this->mContentId;
  603.                 $whereSql .= ' th.`content_id`=? ';
  604.             }
  605.             if!empty$pVersion ) ) {
  606.                 array_push$bindVars$pVersion );
  607.                 $versionSql ' AND th.`version`=? ';
  608.             }
  609.  
  610.             $query "SELECT COUNT(*) AS `hcount`
  611.                     FROM `".BIT_DB_PREFIX."liberty_content_history`
  612.                     WHERE `content_id` = ?";
  613.             $rs $this->mDb->query($queryarray($this->mContentId));
  614.             $cant $rs->fields['hcount'];
  615.  
  616.             # Check for offset out of range
  617.             if $pOffset {
  618.                 $pOffset 0;
  619.             elseif $pOffset $cant {
  620.                 $lastPageNumber ceil $cant $max_records 1;
  621.                 $pOffset $max_records $lastPageNumber;
  622.             }
  623.  
  624.             $query "SELECT lc.`title`, th.*,
  625.                 uue.`login` AS modifier_user, uue.`real_name` AS modifier_real_name,
  626.                 uuc.`login` AS creator_user, uuc.`real_name` AS creator_real_name
  627.                 $selectSql
  628.                 FROM `".BIT_DB_PREFIX."liberty_content_history` th INNER JOIN `".BIT_DB_PREFIX."liberty_content` lc ON (lc.`content_id` = th.`content_id`)
  629.                 LEFT JOIN `".BIT_DB_PREFIX."users_users` uue ON (uue.`user_id` = th.`user_id`)
  630.                 LEFT JOIN `".BIT_DB_PREFIX."users_users` uuc ON (uuc.`user_id` = lc.`user_id`)
  631.                 $joinSql
  632.                 WHERE $whereSql $versionSql order by th.`version` desc";
  633.  
  634.             $result $this->mDb->query$query$bindVars$max_records$pOffset );
  635.             $data array();
  636.             while!$result->EOF {
  637.                 $aux $result->fields;
  638.                 $aux['creator'(isset$aux['creator_real_name'$aux['creator_real_name'$aux['creator_user');
  639.                 $aux['editor'(isset$aux['modifier_real_name'$aux['modifier_real_name'$aux['modifier_user');
  640.                 $data[$aux;
  641.                 //array_push( $ret, $aux );
  642.                 $result->MoveNext();
  643.             }
  644.         }
  645.         // Temporary patch to get a $pListHash array for the output
  646.         // this needs to be tidied on the input side
  647.         // TODO: update this to work like newer getList methods
  648.         $pListHash array();
  649.         $pListHash["data"$data;
  650.         $pListHash["cant"$cant;
  651.         $pListHash["max_records"$max_records;
  652.         $pListHash["offset"$pOffset;
  653.         $pListHash["find"NULL;
  654.         $pListHash["sort_mode"NULL;
  655.         LibertyContent::postGetList$pListHash );
  656.         return $pListHash;
  657.     }
  658.  
  659.     /**
  660.      * Removes last version of the page (from pages) if theres some
  661.      * version in the liberty_content_history then the last version becomes the actual version
  662.      *
  663.      * @param string $pComment 
  664.      * @access public
  665.      * @return void 
  666.      */
  667.     function removeLastVersion$pComment '' {
  668.         if$this->isValid() ) {
  669.             global $gBitSystem;
  670.             $this->expungeCacheFile($this->mContentId);
  671.             $query "select * from `".BIT_DB_PREFIX."liberty_content_history` where `content_id`=? order by ".$this->convertSortMode("last_modified_desc");
  672.             $result $this->mDb->query($queryarray$this->mContentId ) );
  673.             if ($result->numRows()) {
  674.                 // We have a version
  675.                 $res $result->fetchRow();
  676.                 $this->rollbackVersion$res["version");
  677.                 $this->expungeVersion$res["version");
  678.             else {
  679.                 $this->remove_all_versions($page);
  680.             }
  681.             $action "Removed last version";
  682.             $t $gBitSystem->getUTCTime();
  683.             $query "insert into `".BIT_DB_PREFIX."liberty_action_log`( `log_message`, `content_id`, `last_modified`, `user_id`, `ip`, `error_message`) values( ?, ?, ?, ?, ?, ?)";
  684.             $result $this->mDb->query$queryarray$action$this->mContentId$tROOT_USER_ID$_SERVER["REMOTE_ADDR"]$pComment ));
  685.         }
  686.     }
  687.  
  688.     /**
  689.      * Roll back to a specific version of a page
  690.      * @param pVersion Version number to roll back to
  691.      * @param pComment Comment text to be added to the action log
  692.      * @return TRUE if completed successfully
  693.      */
  694.     function rollbackVersion$pVersion$pComment '' {
  695.         $ret FALSE;
  696.         if$this->isValid() ) {
  697.             global $gBitUser,$gBitSystem;
  698.             $this->mDb->StartTrans();
  699.             // JHT - cache invalidation appears to be handled by store function - so don't need to do it here
  700.             $query "select lch.*, lch.`user_id` AS modifier_user_id, lch.`data` AS `edit` from `".BIT_DB_PREFIX."liberty_content_history` lch where lch.`content_id`=? and lch.`version`=?";
  701.             if$res $this->mDb->getRow($query,array$this->mContentId$pVersion ) ) ) {
  702.                 $res['edit_comment''Rollback to version '.$pVersion.' by '.$gBitUser->getDisplayName();
  703.                 if (!empty($pComment)) {
  704.                     $res['edit_comment'.="$pComment";
  705.                 }
  706.                 // JHT 2005-06-19_15:22:18
  707.                 // set ['force_history'] to
  708.                 // make sure we don't destory current content without leaving a copy in history
  709.                 // if rollback can destroy the current page version, it can be used
  710.                 // maliciously
  711.                 $res['force_history'1;
  712.                 // JHT 2005-10-16_22:21:10
  713.                 // title must be set or store fails
  714.                 // we use current page name
  715.                 $res['title'$this->getTitle();
  716.                 if$this->store$res ) ) {
  717.                     $ret TRUE;
  718.                 }
  719.                 $this->mDb->CompleteTrans();
  720.             else {
  721.                 $this->mDb->RollbackTrans();
  722.             }
  723.         }
  724.         return $ret;
  725.     }
  726.  
  727.     /**
  728.      * Removes a specific version of a page
  729.      *
  730.      * @param pVersion Version number to roll back to
  731.      * @param pComment Comment text to be added to the action log
  732.      * @return TRUE if completed successfully
  733.      */
  734.     function expungeVersion$pVersion=NULL$pComment '' {
  735.         global $gBitUser;
  736.         $ret FALSE;
  737.         if$this->isValid() ) {
  738.             $this->mDb->StartTrans();
  739.             $bindVars array$this->mContentId );
  740.             $versionSql '';
  741.             if$pVersion {
  742.                 $versionSql " and `version`=? ";
  743.                 array_push$bindVars$pVersion );
  744.             }
  745.             $hasRows $this->mDb->getOne"SELECT COUNT(`version`) FROM `".BIT_DB_PREFIX."liberty_content_history` WHERE `content_id`=? $versionSql "$bindVars );
  746.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_content_history` WHERE `content_id`=? $versionSql ";
  747.             $result $this->mDb->query$query$bindVars );
  748.             if$hasRows {
  749.                 global $gBitSystem;
  750.                 $action "Removed version $pVersion";
  751.                 $t $gBitSystem->getUTCTime();
  752.                 $query "INSERT INTO `".BIT_DB_PREFIX."liberty_action_log` (`log_message`,`content_id`,`last_modified`,`user_id`,`ip`,`error_message`) VALUES (?,?,?,?,?,?)";
  753.                 $result $this->mDb->query($query,array($action,$this->mContentId,$t,$gBitUser->mUserId,$_SERVER["REMOTE_ADDR"],$pComment));
  754.                 $ret TRUE;
  755.             }
  756.             $this->mDb->CompleteTrans();
  757.         }
  758.         return $ret;
  759.     }
  760.  
  761.     function exportList$pList {
  762.         $ret array();
  763.         $keys array_mergearray'content_type_guid''title''uri''url''content_id' )$this->invokeServices'content_export_keys_function'$pList ) );
  764.         foreach$pList as $key=>$hash {
  765.             foreach$keys as $field {
  766.                 ifisset$hash[$field) ) {
  767.                     $ret[$key][$field$hash[$field];
  768.                 }
  769.             }
  770.             $ret[$key]['content_id'$hash['content_id'];
  771.             $ret[$key]['date_created'dateDateTime::W3C$hash['created');
  772.             $ret[$key]['date_last_modified'dateDateTime::W3Cstrtotime$hash['last_modified') );
  773.         }
  774.         return $ret;
  775.     }
  776.  
  777.     /**
  778.      * Create an export hash from the data
  779.      *
  780.      * @access public
  781.      * @return export data
  782.      */
  783.     function exportHash({
  784.         $ret array();
  785.         if$this->isValid() ) {
  786.             $ret array(
  787.                 'type' => $this->getContentType(),
  788.                 'title'      => $this->getTitle(),
  789.                 'uri'        => $this->getDisplayUri(),
  790.                 'url'        => $this->getDisplayUrl(),
  791.                 'content_id' => $this->mContentId,
  792.                 'date_created' => dateDateTime::W3C$this->getField('created') ),
  793.                 'date_last_modified' => dateDateTime::W3C$this->getField('last_modified') ),
  794.             );
  795.         }
  796.         return $ret;
  797.     }
  798.  
  799.     /**
  800.      * Check mContentId to establish if the object has been loaded with a valid record
  801.      */
  802.     function isValid({
  803.         returnBitBase::verifyId$this->mContentId ) );
  804.     }
  805.  
  806.     /**
  807.      * Check permissions to establish if user has permission to view the object
  808.      * Should be provided by the decendent package
  809.      */
  810.     function isViewable($pContentId NULL{
  811.         returntrue );
  812.     }
  813.  
  814.     /**
  815.      * Check permissions to establish if user has permission to edit the object
  816.      * Should be provided by the decendent package
  817.      */
  818.     function isEditable($pContentId NULL{
  819.         returnfalse );
  820.     }
  821.  
  822.     /**
  823.      * Check permissions to establish if user has permission to admin the object
  824.      * That would include permission to delete an object or change it's permissions
  825.      * Should be provided by the decendent package
  826.      */
  827.     function isAdminable($pContentId NULL{
  828.         returnfalse );
  829.     }
  830.  
  831.     /**
  832.      * Check user_id to establish if the object that has been loaded was created by the current user
  833.      * @param $pParamHash optionally pass in the hash to check against
  834.      * @return TRUE if user owns the content
  835.      */
  836.     function isOwner$pParamHash NULL {
  837.         global $gBitUser;
  838.         if@BitBase::verifyId$pParamHash['user_id') ) {
  839.             $user_id $pParamHash['user_id'];
  840.         elseif$this->isValid(&& @$this->verifyId$this->mInfo['user_id') ) {
  841.             $user_id $this->mInfo['user_id'];
  842.         }
  843.         return@BitBase::verifyId$user_id && $user_id != ANONYMOUS_USER_ID && $user_id == $gBitUser->mUserId );
  844.     }
  845.  
  846.     /**
  847.      * Check if content matches content type GUID - must also be a valid content object, it will not work for generic content class
  848.      */
  849.     function isContentType$pContentGuid {
  850.         global $gBitUser;
  851.         return$this->isValid(&& !empty$this->mInfo['content_type_guid'&& $this->mInfo['content_type_guid'== $pContentGuid );
  852.     }
  853.  
  854.     /**
  855.      * Check permissions to establish if user has permission to access the object
  856.      */
  857.     function verifyAccessControl({
  858.         if$this->isValid() ) {
  859.             $this->invokeServices'content_verify_access' );
  860.         }
  861.     }
  862.  
  863.     /**
  864.      * Set up access to services used by the object
  865.      */
  866.     function invokeServices$pServiceFunction&$pFunctionParam=NULL {
  867.         global $gLibertySystem;
  868.         $errors array();
  869.         // Invoke any services store functions such as categorization or access control
  870.         if$serviceFunctions $gLibertySystem->getServiceValues$pServiceFunction ) ) {
  871.             foreach $serviceFunctions as $func {
  872.                 iffunction_exists$func ) ) {
  873.                     if$errors $func$this$pFunctionParam ) ) {
  874.                         $this->mErrors = array_merge$this->mErrors$errors );
  875.                     }
  876.                 }
  877.             }
  878.         }
  879.         return $errors;
  880.     }
  881.  
  882.     /**
  883.      * check if a service is active for this content type
  884.      * requires package LCConfig
  885.      * provisional method until LCConfig package is integrated into the core
  886.      */
  887.     function hasService$pServiceGuid ){
  888.         global $gBitSystem;
  889.         $ret TRUE// we return true by default to preserve legacy service opperation which has no content type preferences
  890.  
  891.         if$gBitSystem->isPackageActive'lcconfig' ) ){
  892.             // LCConfig is a singleton class
  893.             $LCConfig LCConfig::getInstance();
  894.             // LCConfig negates services by content type
  895.             // if result is not 'n' then service should apply to this content type
  896.             if$LCConfig->getConfig'service_'.$pServiceGuid$this->mContentTypeGuid == 'n' ){
  897.                 $ret FALSE;
  898.             }
  899.         }
  900.  
  901.         return $ret;
  902.     }
  903.  
  904.  
  905.     /**
  906.      * check if a service is required for this content type
  907.      * requires package LCConfig
  908.      * provisional method until LCConfig package is integrated into the core
  909.      */
  910.     function isServiceRequired$pServiceGuid ){
  911.         global $gBitSystem;
  912.         $ret TRUE// we return true by default to preserve legacy service opperation which has no content type preferences
  913.  
  914.         if$gBitSystem->isPackageActive'lcconfig' ) ){
  915.             // LCConfig is a singleton class
  916.             $LCConfig LCConfig::getInstance();
  917.             return $LCConfig->getConfig'service_'.$pServiceGuid$this->mContentTypeGuid == 'required' );
  918.         }
  919.  
  920.         return $ret;
  921.     }
  922.  
  923.  
  924.     /**
  925.      * Default liberty sql for joining a content object table to liberty.
  926.      * We are proposing a new way of building queries here where we build up everything in a hash with implicit AND over all
  927.      * where clauses and then do an array_merge and concatenation in a single function at the end. See convertQueryHash for details.
  928.      *
  929.      *    This is an example current, and would be invoked in getList
  930.      *   $queryHash = array('summary', 'users', 'hits', 'avatar', 'primary'), array('select' => array('sql' => $selectSql), 'join' => array('sql' => $joinSql), 'where' => array('sql' => $whereSql, 'var' => $bindVars ));
  931.      *    $this->getLibertySql( 'bp.`content_id`', $queryHash);
  932.      */
  933.     function getLibertySql$pJoinColumn&$pQueryHash$pJoins NULL$pServiceFunction NULL$pObject NULL$pParamHash NULL {
  934.         $pQueryHash['select']['sql']["lc.*";
  935.         $pQueryHash['join']['sql']["
  936.                 INNER JOIN `".BIT_DB_PREFIX."liberty_content` lc ON( lc.`content_id` = $pJoinColumn )";
  937.         ifempty$pJoins || in_array'summary'$pJoins )) {
  938.             $pQueryHash['select']['sql']["lcds.`data` AS `summary`";
  939.             $pQueryHash['join']['sql']["
  940.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_data` lcds ON( lc.`content_id` = lcds.`content_id` AND lcds.`data_type` = ? )";
  941.             $pQueryHash['join']['var']['summary';
  942.         }
  943.         ifempty$pJoins || in_array'hits'$pJoins )) {
  944.             $pQueryHash['select']['sql']["lch.`hits`, lch.`last_hit`";
  945.             $pQueryHash['join']['sql']["
  946.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_hits` lch ON( lc.`content_id` = lch.`content_id` )";
  947.         }
  948.         ifempty$pJoins || in_array'users'$pJoins )) {
  949.             $pQueryHash['select']['sql']["
  950.                 uu.`email` AS creator_email, uu.`login` AS creator_user, uu.`real_name` AS creator_real_name,
  951.                 uue.`email` AS modifier_email, uue.`login` AS modifier_user, uue.`real_name` AS modifier_real_name";
  952.             $pQueryHash['join']['sql']["
  953.                 INNER JOIN `".BIT_DB_PREFIX."users_users` uu ON( uu.`user_id` = lc.`user_id` )
  954.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."users_users` uue ON( uue.`user_id` = lc.`modifier_user_id` )";
  955.         }
  956.         ifempty$pJoins || in_array'avatar'$pJoins )) {
  957.             $pQueryHash['select']['sql']["ulf.`file_name` AS `avatar_file_name`, ulf.`mime_type` AS `avatar_mime_type`, ula.`attachment_id` AS `avatar_attachment_id`";
  958.             $pQueryHash['join']['sql']["
  959.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_attachments` ula ON( uu.`user_id` = ula.`user_id` AND ula.`attachment_id` = uu.`avatar_attachment_id` )
  960.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_files` ulf ON( ulf.`file_id` = ula.`foreign_id` )";
  961.         }
  962.         ifempty$pJoins || in_array'primary'$pJoins )) {
  963.             $pQueryHash['select']['sql']["pla.`attachment_id` AS `primary_attachment_id`, plf.`file_name` AS `primary_file_name`, plf.`mime_type` AS `primary_mime_type`";
  964.             $pQueryHash['join']['sql']["
  965.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_attachments` pla ON( pla.`content_id` = lc.`content_id` AND pla.`is_primary` = 'y' )
  966.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_files` plf ON( plf.`file_id` = pla.`foreign_id` )";
  967.         }
  968.  
  969.         if!empty$pServiceFunction )) {
  970.             $this->getServicesSql2$pServiceFunction$pQueryHash$pObject$pParamHash );
  971.         }
  972.     }
  973.  
  974.     /**
  975.      * getServicesSql2
  976.      *
  977.      * @param array $pServiceFunction 
  978.      * @param array $pQueryHash 
  979.      * @param array $pObject 
  980.      * @param array $pParamHash 
  981.      * @access public
  982.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  983.      * @TODO this function still contains legacy code.
  984.      * @TODO rename this function to getServicesSql has been weened out
  985.      */
  986.     function getServicesSql2$pServiceFunction&$pQueryHash$pObject NULL$pParamHash NULL {
  987.         global $gLibertySystem;
  988.         if$loadFuncs $gLibertySystem->getServiceValues$pServiceFunction ) ) {
  989.             // TODO: clear out this legacy code
  990.             $pQueryHash['service_select_sql'$pQueryHash['service_join_sql'$pQueryHash['service_where_sql''';
  991.             foreach$loadFuncs as $func {
  992.                 iffunction_exists$func ) ) {
  993.                     if!empty$pObject && is_object$pObject )) {
  994.                         $queryHash $func$pObject$pParamHash );
  995.                     else {
  996.                         $queryHash $func$this$pParamHash );
  997.                     }
  998.  
  999.                     // work out if we're using the old services sql method or the new one
  1000.                     if!empty$queryHash['select'|| !empty$queryHash['from'|| !empty$queryHash['join'|| !empty$queryHash['where')) {
  1001.                         // we're using the new method
  1002.                         $pQueryHash array_merge_recursive$pQueryHash$queryHash );
  1003.                     else {
  1004.                         // TODO: clean out this legacy code {{{
  1005.                         // old method: warn the developer
  1006.                         //deprecated( 'This service is still using the old LibertyContent::getServicesSql() method. Please update the service to use the new SQL hash method' );
  1007.                         if!empty$queryHash['select_sql')) {
  1008.                             $pQueryHash['service_select_sql'.= $queryHash['select_sql'];
  1009.                         }
  1010.                         if!empty$queryHash['join_sql')) {
  1011.                             $pQueryHash['service_join_sql'.= $queryHash['join_sql'];
  1012.                         }
  1013.                         if!empty$queryHash['where_sql')) {
  1014.                             $pQueryHash['service_where_sql'.= $queryHash['where_sql'];
  1015.                         }
  1016.                         if!empty$queryHash['bind_vars')) {
  1017.                             if is_array$pQueryHash['service_bind_vars')) {
  1018.                                 $pQueryHash ['service_bind_vars']array_merge$pQueryHash['service_bind_vars']$queryHash['bind_vars');
  1019.                             else {
  1020.                                 $pQueryHash['service_bind_vars'$queryHash['bind_vars'];
  1021.                             }
  1022.                         }
  1023.                         // }}}
  1024.                     }
  1025.                 }
  1026.             }
  1027.         }
  1028.     }
  1029.  
  1030.     /**
  1031.      * Convert a built up pQueryHash into a single query string and set of bind variables.
  1032.      *
  1033.      * A pQueryHash is an array with required keys select and from, and optional keys join, where and order.
  1034.      * Each key other than order should be an array with an 'sql' key which points to an array with statements.
  1035.      * Statements should not include the keywords to start them excluding join statements nor should they
  1036.      * include trailing delimeters such as commas as the conversion adds these where required.
  1037.      * All where statments are automatically ANDed together.
  1038.      * Each key other than order can optionally have a 'vars' key which points to an array with bind variables.
  1039.      * The order key can either be an array or a single value. convertSortmode is automatically called on each order
  1040.      * statement and built into the ORDER BY clause with delimeters where required.
  1041.      *
  1042.      * @return Results come back in $pQueryHash['query'] $pQueryHash['bind_vars'] and $pQueryHash['query_count'] if requested
  1043.      * @TODO this function still contains legacy code.
  1044.      */
  1045.     function convertQueryHash&$pQueryHash$pCountQuery FALSE {
  1046.         global $gBitSystem;
  1047.  
  1048.         // initiate some variables
  1049.         ifempty$pQueryHash['query')) {
  1050.             $pQueryHash['query''';
  1051.         }
  1052.  
  1053.         ifempty$pQueryHash['query_count')) {
  1054.             $pQueryHash['query_count''';
  1055.         }
  1056.  
  1057.         ifempty$pQueryHash['bind_vars')) {
  1058.             $pQueryHash['bind_vars'array();
  1059.         }
  1060.  
  1061.         // Build up all the parts of the query
  1062.         $queryParts array'select''from''join''where' );
  1063.         foreach$queryParts as $part {
  1064.             if!empty$pQueryHash[$part&& !empty$pQueryHash[$part]['sql')) {
  1065.                 // Add the required keyword -- joins include their own
  1066.                 if$part != 'join' {
  1067.                     $pQueryHash['query'.= strtoupper" $part );
  1068.                     if$pCountQuery {
  1069.                         $pQueryHash['query_count'.= strtoupper" $part );
  1070.                     }
  1071.                 }
  1072.  
  1073.                 // Add the count for the count query
  1074.                 if$pCountQuery && $part == 'select' {
  1075.                     $pQueryHash['query_count'.= 'COUNT( ';
  1076.                 }
  1077.  
  1078.                 $first TRUE;
  1079.                 foreach$pQueryHash[$part]['sql'as $sql {
  1080.                     if!$first {
  1081.                         // WHERE clauses have an implicit AND over all terms
  1082.                         if$part == 'where' {
  1083.                             $pQueryHash['query'.= " AND ";
  1084.                             if$pCountQuery {
  1085.                                 $pQueryHash['query_count'.= " AND ";
  1086.                             }
  1087.                         elseif$part == 'select' || $part == 'from' {
  1088.                             $pQueryHash['query'.= ", ";
  1089.                             if$pCountQuery {
  1090.                                 $pQueryHash['query_count'.= ", ";
  1091.                             }
  1092.                         }
  1093.                     else {
  1094.                         $first FALSE;
  1095.                     }
  1096.  
  1097.                     $pQueryHash['query'.= $sql;
  1098.                     if$pCountQuery {
  1099.                         $pQueryHash['query_count'.= $sql;
  1100.                     }
  1101.                 }
  1102.  
  1103.                 // Close the count for the count query
  1104.                 if$pCountQuery && $part == 'select' {
  1105.                     $pQueryHash['query_count'.= ' )';
  1106.                 }
  1107.  
  1108.                 if!empty$pQueryHash[$part]['var')) {
  1109.                     $pQueryHash['bind_vars'array_merge$pQueryHash['bind_vars']$pQueryHash[$part]['var');
  1110.                 }
  1111.             }
  1112.  
  1113.             // TODO: clean out this legacy code {{{
  1114.             // append old style serivce sql arguments
  1115.             // since we don't allow bind_vars in the old services style, we can append everything here and then later on add the bind vars
  1116.             if!empty$pQueryHash['service_'.$part.'_sql')) {
  1117.                 $pQueryHash['query'.= $pQueryHash['service_'.$part.'_sql'];
  1118.                 if$pCountQuery {
  1119.                     $pQueryHash['query_count'.= $pQueryHash['service_'.$part.'_sql'];
  1120.                 }
  1121.             }
  1122.             // }}}
  1123.         }
  1124.  
  1125.         // TODO: clean out this legacy code {{{
  1126.         // append legacy service bind vars
  1127.         if!empty$pQueryHash['service_bind_vars')) {
  1128.             $pQueryHash['bind_vars'array_merge$pQueryHash['bind_vars']$pQueryHash['service_bind_vars');
  1129.         }
  1130.         /// }}}
  1131.  
  1132.         // Order can be a single value or an array of values all of which get passed to convertSortmode
  1133.         if!empty$pQueryHash['order')) {
  1134.             ifis_array$pQueryHash['order')) {
  1135.                 $first true;
  1136.                 foreach$pQueryHash['order'as $order {
  1137.                     if!$first {
  1138.                         $pQueryHash['query'.= ', ';
  1139.                     else {
  1140.                         $pQueryHash['query'.= ' ORDER BY ';
  1141.                         $first false;
  1142.                     }
  1143.                     $pQueryHash['query'.= $gBitSystem->mDb->convertSortmode$order );
  1144.                 }
  1145.             else {
  1146.                 $pQueryHash['query'.= ' ORDER BY '.$gBitSystem->mDb->convertSortmode$pQueryHash['order');
  1147.             }
  1148.         }
  1149.     }
  1150.  
  1151.     /**
  1152.     * Set up SQL strings for services used by the object
  1153.     * TODO: set this function deprecated and eventually nuke it
  1154.     */
  1155.     function getServicesSql$pServiceFunction&$pSelectSql&$pJoinSql&$pWhereSql&$pBindVars$pObject NULL&$pParamHash NULL {
  1156.         //deprecated( 'You package is calling the deprecated LibertyContent::getServicesSql() method. Please update your code to use LibertyContent::getLibertySql' );
  1157.         global $gLibertySystem;
  1158.         if$loadFuncs $gLibertySystem->getServiceValues$pServiceFunction ) ) {
  1159.             foreach$loadFuncs as $func {
  1160.                 iffunction_exists$func ) ) {
  1161.                     if!empty$pObject && is_object$pObject ) ) {
  1162.                         $loadHash $func$pObject$pParamHash );
  1163.                     else {
  1164.                         $loadHash $func$this$pParamHash );
  1165.                     }
  1166.                     if!empty$loadHash['select_sql') ) {
  1167.                         $pSelectSql .= $loadHash['select_sql'];
  1168.                     }
  1169.                     if!empty$loadHash['join_sql') ) {
  1170.                         $pJoinSql .= $loadHash['join_sql'];
  1171.                     }
  1172.                     if!empty$loadHash['where_sql') ) {
  1173.                         $pWhereSql .= $loadHash['where_sql'];
  1174.                     }
  1175.                     if!empty$loadHash['bind_vars') ) {
  1176.                         if is_array$pBindVars ) ) {
  1177.                             $pBindVars array_merge$pBindVars$loadHash['bind_vars');
  1178.                         else {
  1179.                             $pBindVars $loadHash['bind_vars'];
  1180.                         }
  1181.                     }
  1182.                 }
  1183.             }
  1184.         }
  1185.     }
  1186.  
  1187.     // -------------------------------- Content Permission Functions
  1188.  
  1189.     /**
  1190.      * Check to see if the loaded content has individually assigned permissions
  1191.      *
  1192.      * @access public
  1193.      * @return Number of custom assigned permissions set for the loaded content item
  1194.      */
  1195.     function hasUserPermissions({
  1196.         $ret FALSE;
  1197.         if$this->isValid() ) {
  1198.             $ret $this->mDb->getOne"SELECT COUNT(`perm_name`) FROM `".BIT_DB_PREFIX."liberty_content_permissions` WHERE `content_id` = ?"array$this->mContentId ));
  1199.         }
  1200.         return $ret;
  1201.     }
  1202.  
  1203.     /**
  1204.      * getContentPermissionsSql
  1205.      *
  1206.      * @param array $pPermName 
  1207.      * @param array $pSelectSql 
  1208.      * @param array $pJoinSql 
  1209.      * @param array $pWhereSql 
  1210.      * @param array $pBindVars 
  1211.      * @access public
  1212.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  1213.      */
  1214.     function getContentPermissionsSql$pPermName&$pSelectSql&$pJoinSql&$pWhereSql&$pBindVars {
  1215.         global $gBitUser;
  1216.         if defined('ROLE_MODEL') ) {
  1217.             $pJoinSql .= "
  1218.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_permissions` lcperm ON (lc.`content_id`=lcperm.`content_id`)
  1219.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."users_roles_map` urm ON (urm.`role_id`=lcperm.`role_id`) ";
  1220.             $pWhereSql .= " OR (lcperm.perm_name=? AND (urm.user_id=? OR urm.user_id=?)) ";
  1221.         else {
  1222.             $pJoinSql .= "
  1223.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_permissions` lcperm ON (lc.`content_id`=lcperm.`content_id`)
  1224.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."users_groups_map` ugm ON (ugm.`group_id`=lcperm.`group_id`) ";
  1225.             $pWhereSql .= " OR (lcperm.perm_name=? AND (ugm.user_id=? OR ugm.user_id=?)) ";
  1226.         }
  1227.         $pBindVars[$pPermName;
  1228.         $pBindVars[$gBitUser->mUserId;
  1229.         $pBindVars[ANONYMOUS_USER_ID;
  1230.     }
  1231.  
  1232.     /**
  1233.      * getContentListPermissionsSql
  1234.      *
  1235.      * @param array $pPermName 
  1236.      * @param array $pSelectSql 
  1237.      * @param array $pJoinSql 
  1238.      * @param array $pWhereSql 
  1239.      * @param array $pBindVars 
  1240.      * @access public
  1241.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  1242.      */
  1243.     function getContentListPermissionsSql$pPermName&$pSelectSql&$pJoinSql&$pWhereSql&$pBindVars {
  1244.         global $gBitUser;
  1245.         if defined('ROLE_MODEL') ) {
  1246.             $pJoinSql .= "
  1247.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_permissions` lcperm ON (lc.`content_id`=lcperm.`content_id`)
  1248.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."users_roles_map` urm ON (urm.`role_id`=lcperm.`role_id`) ";
  1249.             $pWhereSql .= " AND ( lcperm.perm_name IS NULL OR ( lcperm.perm_name=? AND urm.user_id=? AND ( (lcperm.is_revoked !=? OR lcperm.is_revoked IS NULL) OR lc.`user_id`=? ) ) )";
  1250.         else {
  1251.             $pJoinSql .= "
  1252.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_permissions` lcperm ON (lc.`content_id`=lcperm.`content_id`)
  1253.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."users_groups_map` ugsm ON (ugsm.`group_id`=lcperm.`group_id`) ";
  1254.             $pWhereSql .= " AND ( lcperm.perm_name IS NULL OR ( lcperm.perm_name=? AND ugsm.user_id=? AND ( (lcperm.is_revoked !=? OR lcperm.is_revoked IS NULL) OR lc.`user_id`=? ) ) )";
  1255.         }
  1256.         $pBindVars[$pPermName;
  1257.         $pBindVars[$gBitUser->mUserId;
  1258.         $pBindVars["y";
  1259.         $pBindVars[$gBitUser->mUserId;
  1260.     }
  1261.  
  1262.     /**
  1263.      * Check is a user has permission to access the object
  1264.      *
  1265.      * @param integer User Identifier
  1266.      * @param integer Content Itentifier
  1267.      * @param string Content Type GUID
  1268.      * @param string Name of the permission
  1269.      * @return bool true if access is allowed
  1270.      */
  1271.     function checkContentPermission$pParamHash {
  1272.         global $gBitUser;
  1273.  
  1274.         $ret FALSE;
  1275.  
  1276.         if!empty$this->mAdminContentPerm && $gBitUser->hasPermission$this->mAdminContentPerm ) ) {
  1277.             // content admin shortcut
  1278.             $ret TRUE;
  1279.         else {
  1280.             $selectSql ''$joinSql ''$whereSql '';
  1281.             $bindVars array();
  1282.  
  1283.             if!empty$pParamHash['content_id') ) {
  1284.                 $bindVars[$pParamHash['content_id'];
  1285.             elseif$this->isValid() ) {
  1286.                 $bindVars[$this->mContentId;
  1287.             }
  1288.  
  1289.             if@$this->verifyId$pParamHash['user_id') ) {
  1290.                 $whereSql .= " AND lc.`user_id` = ? ";
  1291.                 $bindVars[$pParamHash['user_id'];
  1292.             }
  1293.  
  1294.             if!empty$pParamHash['group_id') ) {
  1295.                 $whereSql .= " AND lcperm.`group_id` = ? ";
  1296.                 $bindVars[$pParamHash['group_id'];
  1297.             }
  1298.  
  1299.             if!empty$pParamHash['role_id') ) {
  1300.                 $whereSql .= " AND lcperm.`role_id` = ? ";
  1301.                 $bindVars[$pParamHash['role_id'];
  1302.             }
  1303.  
  1304.             $permWhereSql '';
  1305.             $this->getContentPermissionsSql$pParamHash['perm_name']$selectSql$joinSql$permWhereSql$bindVars );
  1306.  
  1307.             if!empty$whereSql ) ) {
  1308.                 $whereSql preg_replace'/^[\s]*AND/''  '$whereSql );
  1309.             }
  1310.  
  1311.             $query "SELECT COUNT(*)
  1312.                       FROM `".BIT_DB_PREFIX."liberty_content` lc  $joinSql
  1313.                       WHERE lc.`content_id`=? AND ( $whereSql $permWhereSql ) ";
  1314.             $ret $this->mDb->getOne$query$bindVars );
  1315.         }
  1316.         return!empty$ret ) );
  1317.     }
  1318.  
  1319.     /**
  1320.      * Load all permissions assigned to a given object.
  1321.      * This function is mainly used to fetch a list of custom permissions of a given content item.
  1322.      *
  1323.      * @access public
  1324.      */
  1325.     function getContentPermissionsList({
  1326.         global $gBitUser;
  1327.         $ret FALSE;
  1328.         if$this->isValid() ) {
  1329.             if defined('ROLE_MODEL') ) {
  1330.                 $query "
  1331.                     SELECT lcperm.`perm_name`, lcperm.`is_revoked`, ur.`role_id`, ur.`role_name`, up.`perm_desc`
  1332.                     FROM `".BIT_DB_PREFIX."liberty_content_permissions` lcperm
  1333.                         INNER JOIN `".BIT_DB_PREFIX."users_roles` ur ON( lcperm.`role_id`=ur.`role_id` )
  1334.                         LEFT OUTER JOIN `".BIT_DB_PREFIX."users_permissions` up ON( up.`perm_name`=lcperm.`perm_name` )
  1335.                     WHERE lcperm.`content_id` = ?";
  1336.                 $team 'role_id';
  1337.             else {
  1338.                 $query "
  1339.                     SELECT lcperm.`perm_name`, lcperm.`is_revoked`, ug.`group_id`, ug.`group_name`, up.`perm_desc`
  1340.                     FROM `".BIT_DB_PREFIX."liberty_content_permissions` lcperm
  1341.                         INNER JOIN `".BIT_DB_PREFIX."users_groups` ug ON( lcperm.`group_id`=ug.`group_id` )
  1342.                         LEFT OUTER JOIN `".BIT_DB_PREFIX."users_permissions` up ON( up.`perm_name`=lcperm.`perm_name` )
  1343.                     WHERE lcperm.`content_id` = ?";
  1344.                 $team 'group_id';
  1345.             }
  1346.             $perms $this->mDb->getAll$queryarray$this->mContentId ));
  1347.             foreach$perms as $perm {
  1348.                 $ret[$perm[$team]][$perm['perm_name']] $perm;
  1349.             }
  1350.         }
  1351.         return $ret;
  1352.     }
  1353.  
  1354.     /**
  1355.      * Get a list of content with permissions
  1356.      *
  1357.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  1358.      */
  1359.     public static function getContentWithPermissionsList({
  1360.         global $gBitSystem;
  1361.         $ret array();
  1362.         if defined('ROLE_MODEL') ) {
  1363.             $query "
  1364.                 SELECT lcperm.`perm_name`, lc.`title`, lc.`content_id`, lc.`content_type_guid`, lcperm.`is_revoked`, ur.`role_id`, ur.`role_name`, up.`perm_desc`
  1365.                 FROM `".BIT_DB_PREFIX."liberty_content_permissions` lcperm
  1366.                     INNER JOIN `".BIT_DB_PREFIX."users_roles` ur ON( lcperm.`role_id`=ur.`role_id` )
  1367.                     INNER JOIN `".BIT_DB_PREFIX."liberty_content` lc ON( lcperm.`content_id`=lc.`content_id` )
  1368.                     LEFT OUTER JOIN `".BIT_DB_PREFIX."users_permissions` up ON( up.`perm_name`=lcperm.`perm_name` )
  1369.                 ORDER BY ".$gBitSystem->mDb->convertSortmode'content_type_guid_asc' ).", ".$gBitSystem->mDb->convertSortmode'title_asc' );
  1370.         else {
  1371.             $query "
  1372.                 SELECT lcperm.`perm_name`, lc.`title`, lc.`content_id`, lc.`content_type_guid`, lcperm.`is_revoked`, ug.`group_id`, ug.`group_name`, up.`perm_desc`
  1373.                 FROM `".BIT_DB_PREFIX."liberty_content_permissions` lcperm
  1374.                     INNER JOIN `".BIT_DB_PREFIX."users_groups` ug ON( lcperm.`group_id`=ug.`group_id` )
  1375.                     INNER JOIN `".BIT_DB_PREFIX."liberty_content` lc ON( lcperm.`content_id`=lc.`content_id` )
  1376.                     LEFT OUTER JOIN `".BIT_DB_PREFIX."users_permissions` up ON( up.`perm_name`=lcperm.`perm_name` )
  1377.                 ORDER BY ".$gBitSystem->mDb->convertSortmode'content_type_guid_asc' ).", ".$gBitSystem->mDb->convertSortmode'title_asc' );
  1378.         }
  1379.         $perms $gBitSystem->mDb->getAll$query );
  1380.         foreach$perms as $perm {
  1381.             $ret[$perm['content_type_guid']][$perm['content_id']][$perm;
  1382.         }
  1383.         return $ret;
  1384.     }
  1385.  
  1386.     /**
  1387.      * Expunge Content Permissions
  1388.      *
  1389.      * @access public
  1390.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  1391.      */
  1392.     function expungeContentPermissions({
  1393.         $ret FALSE;
  1394.         if$this->isValid() ) {
  1395.             $query "DELETE FROM `".BIT_DB_PREFIX."liberty_content_permissions` WHERE `content_id` = ?";
  1396.             $ret $this->mDb->query$queryarray$this->mContentId ));
  1397.         }
  1398.         return $ret;
  1399.     }
  1400.  
  1401.     /**
  1402.      * Function that determines if this content specified permission for the current gBitUser, and will throw a fatal error if not.
  1403.      *
  1404.      * @param string Name of the permission to check
  1405.      * @param string Message if permission denigned
  1406.      */
  1407.     function verifyUserPermission$pPermName$pFatalMessage NULL {
  1408.         $ret TRUE;
  1409.         if$this->isValid(&& !$this->hasUserPermission$pPermName ) ) {
  1410.             global $gBitSystem;
  1411.             $gBitSystem->fatalPermission$pPermName$pFatalMessage );
  1412.         }
  1413.         return $ret;
  1414.     }
  1415.  
  1416.     /**
  1417.      * Function that determines if this content specified permission for the current gBitUser.
  1418.      * Assigned content perms override the indvidual global perms, so the result is the union of the global permission set + overridden individual content perms
  1419.      *
  1420.      * @param string Name of the permission to check
  1421.      * @param string Check access control service if available
  1422.      * @param string return default user permission setting when no content perms are set
  1423.      * @return bool true if user has permission to access file
  1424.      */
  1425.     function hasUserPermission$pPermName$pVerifyAccessControl=TRUE {
  1426.         global $gBitUser;
  1427.         $ret FALSE;
  1428.         if!$this->isValid() ) {
  1429.             // return default user permission setting when no content is loaded
  1430.             $ret $gBitUser->hasPermission$pPermName );
  1431.         elseif!$gBitUser->isRegistered(|| !$ret $this->isOwner(|| $ret $gBitUser->isAdmin() )) {
  1432.             if$gBitUser->isAdmin(|| $gBitUser->hasPermission$this->mAdminContentPerm )) {
  1433.                 $ret TRUE;
  1434.             else {
  1435.                 if$pVerifyAccessControl {
  1436.                     $this->verifyAccessControl();
  1437.                 }
  1438.                 $checkPerms $this->getUserPermissions();
  1439.                 if !empty$checkPerms ) ) {
  1440.                     // Do they have the admin permission or the one we want?
  1441.                     if !empty$checkPerms[$this->mAdminContentPerm) ) {
  1442.                         $ret TRUE;
  1443.                     elseif !empty$checkPerms[$pPermName) ) {
  1444.                         $ret TRUE;
  1445.                     }
  1446.                 else {
  1447.                     // return default user permission setting when no content perms are set
  1448.                     $ret $gBitUser->hasPermission$pPermName );
  1449.                 }
  1450.             }
  1451.         }
  1452.         return$ret );
  1453.     }
  1454.  
  1455.     /**
  1456.      * Determine if current user has the ability to administer this type of content
  1457.      *
  1458.      * @return bool True if user has this type of content administration permission
  1459.      */
  1460.     function hasAdminPermission$pVerifyAccessControl=TRUE {
  1461.         return$this->hasUserPermission$this->mAdminContentPerm$pVerifyAccessControl ) );
  1462.     }
  1463.  
  1464.     // === verifyAdminPermission
  1465.     /**
  1466.      * This code was duplicated _EVERYWHERE_ so here is an easy template to cut that down.
  1467.      * It will verify if a given user has a given $permission and if not, it will display the error template and die()
  1468.      * @param $pVerifyAccessControl check access control service if available
  1469.      * @return TRUE if permitted, method will fatal out if not
  1470.      * @access public
  1471.      */
  1472.     function verifyAdminPermission$pVerifyAccessControl=TRUE {
  1473.         global $gBitSystem;
  1474.         if$this->hasAdminPermission$pVerifyAccessControl ) ) {
  1475.             return TRUE;
  1476.         else {
  1477.             $gBitSystem->fatalPermission$this->mAdminContentPerm );
  1478.         }
  1479.     }
  1480.  
  1481.     /**
  1482.      * Determine if current user has the ability to delete/expunge this type of content
  1483.      *
  1484.      * @return bool True if user has this type of content expunge permission
  1485.      */
  1486.     function hasExpungePermission$pVerifyAccessControl=TRUE {
  1487.         return$this->hasUserPermission$this->mExpungeContentPerm$pVerifyAccessControl ) );
  1488.     }
  1489.  
  1490.     // === verifyExpungePermission
  1491.     /**
  1492.      * It will verify if a given user has a given $permission and if not, it will display the error template and die()
  1493.      * @param $pVerifyAccessControl check access control service if available
  1494.      * @return TRUE if permitted, method will fatal out if not
  1495.      * @access public
  1496.      */
  1497.     function verifyExpungePermission$pVerifyAccessControl=TRUE {
  1498.         global $gBitSystem;
  1499.         if$this->hasExpungePermission$pVerifyAccessControl ) ) {
  1500.             return TRUE;
  1501.         else {
  1502.             $gBitSystem->fatalPermission$this->mExpungeContentPerm );
  1503.         }
  1504.     }
  1505.  
  1506.     /**
  1507.      * Determine if current user has the ability to edit this type of content
  1508.      *
  1509.      * @return bool True if user has this type of content administration permission
  1510.      */
  1511.     function hasUpdatePermission$pVerifyAccessControl=TRUE {
  1512.         return$this->hasUserPermission$this->mUpdateContentPerm$pVerifyAccessControl ) );
  1513.     }
  1514.  
  1515.     /**
  1516.      * Deprecated, use hasUpdatePermission
  1517.      *
  1518.      * @return bool True if user has this type of content administration permission
  1519.      */
  1520.     function hasEditPermission$pVerifyAccessControl=TRUE$pCheckGlobalPerm=TRUE {
  1521.         deprecated"LibertyContent::hasEditPermission has been replaced with LibertyContent::hasUpdatePermission and pCheckGlobal has been change to always be the case" );
  1522.         return$this->hasUpdatePermission$pVerifyAccessControl ) );
  1523.     }
  1524.  
  1525.     // === verifyUpdatePermission
  1526.     /**
  1527.      * This code was duplicated _EVERYWHERE_ so here is an easy template to cut that down.
  1528.      * It will verify if a given user has a given $permission and if not, it will display the error template and die()
  1529.      * @param $pVerifyAccessControl check access control service if available
  1530.      * @return TRUE if permitted, method will fatal out if not
  1531.      * @access public
  1532.      */
  1533.     function verifyUpdatePermission$pVerifyAccessControl=TRUE {
  1534.         global $gBitSystem;
  1535.         if$this->hasUpdatePermission$pVerifyAccessControl ) ) {
  1536.             return TRUE;
  1537.         else {
  1538.             $gBitSystem->fatalPermission$this->mUpdateContentPerm );
  1539.         }
  1540.     }
  1541.  
  1542.     // === verifyEditPermission
  1543.     /**
  1544.      * Deprecated, use verifyUpdatePermission
  1545.      */
  1546.     function verifyEditPermission$pVerifyAccessControl=TRUE$pCheckGlobalPerm=TRUE {
  1547.         deprecated"LibertyContent::verifyEditPermission has been replaced with LibertyContent::verifyUpdatePermission and pCheckGlobal has been change to always be the case" );
  1548.         $this->verifyUpdatePermission$pVerifyAccessControl );
  1549.     }
  1550.  
  1551.     /**
  1552.      * Determine if current user has the ability to craete this type of content
  1553.      *
  1554.      * @return bool True if user has this type of content administration permission
  1555.      */
  1556.     function hasCreatePermission$pVerifyAccessControl=TRUE {
  1557.         return$this->hasUserPermission$this->mCreateContentPerm$pVerifyAccessControl ) );
  1558.     }
  1559.  
  1560.     // === verifyCreatePermission
  1561.     /**
  1562.      * Determine if current user has the ability to create this type of content
  1563.      * Note this will always return FALSEif the content isValid
  1564.      *
  1565.      * @return bool True if user has this type of content administration permission
  1566.      ***/
  1567.     function verifyCreatePermission$pVerifyAccessControl=TRUE {
  1568.         global $gBitSystem;
  1569.         if!$this->isValid(&& $this->hasCreatePermission$pVerifyAccessControl ) ) {
  1570.             return TRUE;
  1571.         else {
  1572.             $gBitSystem->fatalPermission$this->mCreateContentPerm );
  1573.         }
  1574.     }
  1575.  
  1576.     /**
  1577.      * Determine if current user has the ability to view this type of content
  1578.      * Note that this will always return TRUE if you haven't set the mViewContentPerm in your class
  1579.      *
  1580.      * @return bool True if user has this type of content administration permission
  1581.      */
  1582.     function hasViewPermission$pVerifyAccessControl=TRUE {
  1583.         return$this->hasUpdatePermission$pVerifyAccessControl || empty$this->mViewContentPerm || $this->hasUserPermission$this->mViewContentPerm$pVerifyAccessControl ));
  1584.     }
  1585.  
  1586.     // === verifyViewPermission
  1587.     /**
  1588.      * This code was duplicated _EVERYWHERE_ so here is an easy template to cut that down.
  1589.      * It will verify if a given user has a given $permission and if not, it will display the error template and die()
  1590.      * @param $pVerifyAccessControl check access control service if available
  1591.      * @return TRUE if permitted, method will fatal out if not
  1592.      * @access public
  1593.      */
  1594.     function verifyViewPermission$pVerifyAccessControl=TRUE {
  1595.         global $gBitSystem;
  1596.         if$this->hasViewPermission$pVerifyAccessControl ) ) {
  1597.             return TRUE;
  1598.         else {
  1599.             $gBitSystem->fatalPermission$this->mViewContentPerm );
  1600.         }
  1601.     }
  1602.  
  1603.     /**
  1604.      * Determine if current user has the ability to post comments to this type of content
  1605.      *
  1606.      * @return bool True if user has this type of content administration permission
  1607.      */
  1608.     function hasPostCommentsPermission$pVerifyAccessControl=TRUE {
  1609.         return$this->hasUserPermission'p_liberty_post_comments'$pVerifyAccessControl ));
  1610.     }
  1611.  
  1612.     // === verifyPostCommentsPermission
  1613.     /**
  1614.      * It will verify if a given user has a given $permission and if not, it will display the error template and die()
  1615.      * @param $pVerifyAccessControl check access control service if available
  1616.      * @return TRUE if permitted, method will fatal out if not
  1617.      * @access public
  1618.      */
  1619.     function verifyPostCommentsPermission$pVerifyAccessControl=TRUE {
  1620.         global $gBitSystem;
  1621.         if$this->hasPostCommentPermission$pVerifyAccessControl ) ) {
  1622.             return TRUE;
  1623.         else {
  1624.             $gBitSystem->fatalPermission'p_liberty_post_comments' );
  1625.         }
  1626.     }
  1627.  
  1628.     /**
  1629.      * Get specific permissions for the specified user for this content
  1630.      *
  1631.      * @return Array of all permissions for the current user joined with perms
  1632.      *          for the current content. This should handle cases where
  1633.      *          non-default permissions is assigned, default permission is
  1634.      *          removed, and duplicate default permissions where one team's perm
  1635.      *          is revoked, but another is still permitted. If the permission is
  1636.      *          revoked, is_revoked will be set to 'y'
  1637.      */
  1638.     function getUserPermissions({
  1639.         global $gBitUser;
  1640.  
  1641.         $userId $gBitUser->mUserId;
  1642.         // Prevent null entires when creating database
  1643.         if!is_numeric$userId ) ) $userId 0;
  1644.         if!is_numeric$this->mContentId ) ) $this->mContentId = 0;
  1645.         if!isset$this->mUserContentPerms )) {
  1646.             // get the default permissions for specified user
  1647.             if defined('ROLE_MODEL') ) {
  1648.                 $query "
  1649.                     SELECT urp.`perm_name` as `hash_key`, 1 as `role_perm`, urp.`perm_name`, urp.`perm_value`, urp.`role_id`
  1650.                     FROM `".BIT_DB_PREFIX."users_roles_map` urm
  1651.                         LEFT JOIN `".BIT_DB_PREFIX."users_role_permissions` urp ON(urm.`role_id`=urp.`role_id`)
  1652.                         LEFT JOIN `".BIT_DB_PREFIX."liberty_content_permissions` lcp ON(lcp.`role_id`=urm.`role_id` AND lcp.`content_id`=? AND urp.`perm_name`=lcp.`perm_name`)
  1653.                     WHERE (urm.`user_id`=? OR urm.`user_id`=?) AND lcp.`perm_name` IS NULL";
  1654.             else {
  1655.                 $query "
  1656.                     SELECT ugp.`perm_name` as `hash_key`, 1 as `group_perm`, ugp.`perm_name`, ugp.`perm_value`, ugp.`group_id`
  1657.                     FROM `".BIT_DB_PREFIX."users_groups_map` ugm
  1658.                         LEFT JOIN `".BIT_DB_PREFIX."users_group_permissions` ugp ON(ugm.`group_id`=ugp.`group_id`)
  1659.                         LEFT JOIN `".BIT_DB_PREFIX."liberty_content_permissions` lcp ON(lcp.`group_id`=ugm.`group_id` AND lcp.`content_id`=? AND ugp.`perm_name`=lcp.`perm_name`)
  1660.                     WHERE (ugm.`user_id`=? OR ugm.`user_id`=?) AND lcp.`perm_name` IS NULL";
  1661.             }
  1662.             if!$defaultPerms $this->mDb->getAssoc$queryarray$this->mContentId$userIdANONYMOUS_USER_ID ) ) ) {
  1663.                 $defaultPerms array();
  1664.             }
  1665.             if defined('ROLE_MODEL') ) {
  1666.                 $query "
  1667.                     SELECT lcp.`perm_name` AS `hash_key`, lcp.*
  1668.                     FROM `".BIT_DB_PREFIX."liberty_content_permissions` lcp
  1669.                         INNER JOIN `".BIT_DB_PREFIX."users_roles_map` urm ON(lcp.role_id=urm.role_id)
  1670.                         LEFT JOIN `".BIT_DB_PREFIX."users_role_permissions` urp ON(urm.role_id=urp.role_id AND urp.role_id!=lcp.role_id AND urp.perm_name=lcp.perm_name)
  1671.                     WHERE lcp.content_id=? AND (urm.user_id=? OR urm.user_id=?) AND lcp.is_revoked IS NULL";
  1672.             else {
  1673.                 $query "
  1674.                     SELECT lcp.`perm_name` AS `hash_key`, lcp.*
  1675.                     FROM `".BIT_DB_PREFIX."liberty_content_permissions` lcp
  1676.                         INNER JOIN `".BIT_DB_PREFIX."users_groups_map` ugm ON(lcp.group_id=ugm.group_id)
  1677.                         LEFT JOIN `".BIT_DB_PREFIX."users_group_permissions` ugp ON(ugm.group_id=ugp.group_id AND ugp.group_id!=lcp.group_id AND ugp.perm_name=lcp.perm_name)
  1678.                     WHERE lcp.content_id=? AND (ugm.user_id=? OR ugm.user_id=?) AND lcp.is_revoked IS NULL";
  1679.             }
  1680.             if!$nonDefaultPerms $this->mDb->getAssoc$queryarray$this->mContentId$userIdANONYMOUS_USER_ID ) ) ) {
  1681.                 $nonDefaultPerms array();
  1682.             }
  1683.  
  1684.             $this->mUserContentPerms = array_merge$defaultPerms$nonDefaultPerms );
  1685.  
  1686.             $this->invokeServices'content_user_perms_function' );
  1687.         }
  1688.  
  1689.         return $this->mUserContentPerms;
  1690.     }
  1691.  
  1692.     /**
  1693.      * Store a permission for the object that has been loaded in the permission database
  1694.      *
  1695.      * Any old copy of the permission is deleted prior to loading the new copy
  1696.      * @param integer Group Identifier
  1697.      * @param string Name of the permission
  1698.      * @param integer Content Itentifier
  1699.      * @return bool true ( will not currently report a failure )
  1700.      */
  1701.     function storePermission$pTeamId$pPermName$pIsRevoked=FALSE$pContentId=NULL ){
  1702.         $ret FALSE;
  1703.         $pContentId $pContentId == NULL?$this->mContentId:$pContentId;
  1704.         if@BitBase::verifyId$pGroupId && !empty$pPermName && @BitBase::verifyId$pContentId ) ) {
  1705.             $this->removePermission$pGroupId$pPermName$pContentId );
  1706.             $storeHash array(
  1707.                 'perm_name' => $pPermName,
  1708.                 'content_id' => $pContentId,
  1709.             );
  1710.             if defined('ROLE_MODEL') ) {
  1711.                 $storeHash['role_id'$pTeamId;
  1712.             else {
  1713.                 $storeHash['group_id'$pTeamId;
  1714.             }
  1715.             // check to see if this is an exclusion
  1716.             if$pIsRevoked {
  1717.                 $storeHash['is_revoked''y';
  1718.             }
  1719.             $ret $this->mDb->associateInsertBIT_DB_PREFIX."liberty_content_permissions"$storeHash );
  1720.         }
  1721.         return $ret;
  1722.     }
  1723.  
  1724.     /**
  1725.      * Remove a permission to access the content
  1726.      *
  1727.      * @param integer Group Identifier
  1728.      * @param string Name of the permission
  1729.      * @return bool true ( will not currently report a failure )
  1730.      */
  1731.     function removePermission$pTeamId$pPermName$pContentId=NULL {
  1732.         $pContentId $pContentId == NULL?$this->mContentId:$pContentId;
  1733.         if@BitBase::verifyId$pTeamId && !empty$pPermName && @BitBase::verifyId$pContentId ) ) {
  1734.             if defined('ROLE_MODEL') ) {
  1735.                 $team 'role_id';
  1736.             else {
  1737.                 $team 'group_id';
  1738.             }
  1739.             $query "
  1740.                 DELETE FROM `".BIT_DB_PREFIX."liberty_content_permissions`
  1741.                 WHERE `$team` = ? and `content_id` = ? and `perm_name` = ?";
  1742.             $bindVars array$pTeamId$pContentId$pPermName );
  1743.             $result $this->mDb->query$query$bindVars );
  1744.         }
  1745.         return TRUE;
  1746.     }
  1747.  
  1748.     /**
  1749.      * Check to see if this permission is already in the global permissions table.
  1750.      *
  1751.      * @param array $pTeamId 
  1752.      * @param array $pPermName 
  1753.      * @access public
  1754.      * @return TRUE if present, FALSE if not
  1755.      */
  1756.     function isExcludedPermission$pTeamId$pPermName {
  1757.         if@BitBase::verifyId$pTeamId && !empty$pPermName )) {
  1758.             if defined('ROLE_MODEL') ) {
  1759.                 $query "SELECT `perm_name` FROM `".BIT_DB_PREFIX."users_role_permissions` WHERE `role_id` = ? AND `perm_name` = ?";
  1760.             else {
  1761.                 $query "SELECT `perm_name` FROM `".BIT_DB_PREFIX."users_group_permissions` WHERE `group_id` = ? AND `perm_name` = ?";
  1762.             }
  1763.             return$this->mDb->getOne$queryarray$pTeamId$pPermName )) == $pPermName );
  1764.         }
  1765.     }
  1766.  
  1767.  
  1768.     // =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-= Preferences Functions
  1769.  
  1770.     /**
  1771.      * Returns the content preferences value for the passed in key.
  1772.      *
  1773.      * @param string Hash key for the mPrefs value
  1774.      * @param string Default value to return if the preference is empty
  1775.      * @param int Optional content_id for arbitrary content preference
  1776.      */
  1777.     function getPreference$pPrefName$pPrefDefault=NULL$pContentId NULL {
  1778.         global $gBitDb;
  1779.         $ret NULL;
  1780.  
  1781.         if$pContentId && !empty$pPrefName )) {
  1782.             // Get a user preference for an arbitrary user
  1783.             $sql "SELECT `pref_value` FROM `".BIT_DB_PREFIX."liberty_content_prefs` WHERE `content_id`=? AND `pref_name`=?";
  1784.  
  1785.             if!$ret $gBitDb->getOne$sqlarray$pContentId$pPrefName ) ) ) {
  1786.                 $ret $pPrefDefault;
  1787.             }
  1788.         else {
  1789.             ifis_null$this->mPrefs ) ) {
  1790.                 $this->loadPreferences();
  1791.             }
  1792.             ifisset$this->mPrefs && isset$this->mPrefs[$pPrefName) ) {
  1793.                 $ret $this->mPrefs[$pPrefName];
  1794.             else {
  1795.                 $ret $pPrefDefault;
  1796.             }
  1797.         }
  1798.         return $ret;
  1799.     }
  1800.  
  1801.     /**
  1802.      * loadPreferences of the currently loaded object or pass in to get preferences of a specific content_id
  1803.      *
  1804.      * @param numeric $pContentId content_id of the item we want the prefs from (optional)
  1805.      * @access public
  1806.      * @return array of preferences if $pContentId is set or pass preferences on to $this->mPrefs
  1807.      */
  1808.     function loadPreferences$pContentId NULL {
  1809.         global $gBitSystem;
  1810.         if@BitBase::verifyId$pContentId )) {
  1811.             return $gBitSystem->mDb->getAssoc"SELECT `pref_name`, `pref_value` FROM `".BIT_DB_PREFIX."liberty_content_prefs` WHERE `content_id`=?"array$pContentId ));
  1812.         elseif$this->isValid() ) {
  1813.             // If no results, getAssoc will return an empty array (ie not a true NULL value) so getPreference can tell we have attempted a load
  1814.             $this->mPrefs = @$this->mDb->getAssoc"SELECT `pref_name`, `pref_value` FROM `".BIT_DB_PREFIX."liberty_content_prefs` WHERE `content_id`=?"array$this->mContentId ));
  1815.         }
  1816.     }
  1817.  
  1818.     /**
  1819.      * Set a hash value in the mPrefs hash. This does *NOT* store the value in the database. It does no checking for existing or duplicate values. the main point of this function is to limit direct accessing of the mPrefs hash. I will probably make mPrefs private one day.
  1820.      *
  1821.      * @param string Hash key for the mPrefs value
  1822.      * @param string Value for the mPrefs hash key
  1823.      */
  1824.     function setPreference$pPrefName$pPrefValue {
  1825.         $this->mPrefs[$pPrefName$pPrefValue;
  1826.     }
  1827.  
  1828.  
  1829.     /**
  1830.      * Saves a preference to the liberty_content_prefs database table with the given pref name and value. If the value is NULL, the existing value will be delete and the value will not be saved. However, a zero will be stored. This will update the mPrefs hash.
  1831.      *
  1832.      * @param string Hash key for the mPrefs value
  1833.      * @param string Value for the mPrefs hash key
  1834.      */
  1835.     function storePreference$pPrefName$pPrefValue NULL {
  1836.         $ret FALSE;
  1837.         ifLibertyContent::isValid() ) {
  1838.             $query    "DELETE FROM `".BIT_DB_PREFIX."liberty_content_prefs` WHERE `content_id`=? AND `pref_name`=?";
  1839.             $bindvars array$this->mContentId$pPrefName );
  1840.             $result   $this->mDb->query($query$bindvars);
  1841.             if!is_null$pPrefValue )) {
  1842.                 $query      "INSERT INTO `".BIT_DB_PREFIX."liberty_content_prefs` (`content_id`,`pref_name`,`pref_value`) VALUES(?, ?, ?)";
  1843.                 $bindvars[substr$pPrefValue0250 );
  1844.                 $result     $this->mDb->query$query$bindvars );
  1845.                 $this->mPrefs[$pPrefName$pPrefValue;
  1846.             }
  1847.             $this->mPrefs[$pPrefName$pPrefValue;
  1848.         }
  1849.         return $ret;
  1850.     }
  1851.  
  1852.     /**
  1853.      * Register the content type for reference
  1854.      *
  1855.      * @param string Content Type GUID
  1856.      * @param array Array of content type data
  1857.      *  Populates the mType array with the following entries
  1858.      *  string    content_type_guid
  1859.      *  string
  1860.      */
  1861.     function registerContentType$pContentGuid$pTypeParams {
  1862.         global $gLibertySystem;
  1863.         $gLibertySystem->registerContentType$pContentGuid$pTypeParams );
  1864.         $this->mType = $pTypeParams;
  1865.     }
  1866.  
  1867.     /**
  1868.      * Increment the content item hit flag by 1
  1869.      *
  1870.      * @return bool true ( will not currently report a failure )
  1871.      */
  1872.     function addHit({
  1873.         global $gBitUser,$gBitSystem;
  1874.         ifempty$_REQUEST['post_comment_submit'&& empty$_REQUEST['post_comment_request') ) {
  1875.             if@BitBase::verifyId$this->mContentId && (( $gBitUser->isRegistered(&& !$this->isOwner() ) || $gBitUser->getField'user_id' == ANONYMOUS_USER_ID )) && $gBitSystem->isFeatureActive'users_count_admin_pageviews' || !$gBitUser->isAdmin() ) ) {
  1876.                 if$this->mDb->getOne"SELECT `content_id` FROM `".BIT_DB_PREFIX."liberty_content_hits` WHERE `content_id`=?"array$this->mContentId ))) {
  1877.                     $query "UPDATE `".BIT_DB_PREFIX."liberty_content_hits` SET `hits`=`hits`+1, `last_hit`= ? WHERE `content_id` = ?";
  1878.                 else {
  1879.                     $query "INSERT INTO `".BIT_DB_PREFIX."liberty_content_hits` ( `hits`, `last_hit`, `content_id` ) VALUES ( ?,?,? )";
  1880.                     $bindVars[1;
  1881.                 }
  1882.                 $bindVars[$gBitSystem->getUTCTime();
  1883.                 $bindVars[$this->mContentId;
  1884.                 $this->mDb->StartTrans();
  1885.                 $result $this->mDb->query$query$bindVars );
  1886.                 $this->mDb->CompleteTrans();
  1887.             }
  1888.         }
  1889.         return TRUE;
  1890.     }
  1891.  
  1892.     /**
  1893.      * Set Hits and Last Hit
  1894.      *
  1895.      * @return bool true ( will not currently report a failure )
  1896.      */
  1897.     function setHits($pHits$pLastHit=0{
  1898.         if$this->mContentId && !empty($pHits) ) {
  1899.             $query "UPDATE `".BIT_DB_PREFIX."liberty_content_hits` SET `hits`= ?, `last_hit`= ? WHERE `content_id` = ?";
  1900.             $result $this->mDb->query$queryarray$pHits$pLastHit$this->mContentId ) );
  1901.             $affected_rows $this->mDb->Affected_Rows();
  1902.             if!$affected_rows {
  1903.                 $query "INSERT INTO `".BIT_DB_PREFIX."liberty_content_hits` ( `hits`, `last_hit`, `content_id` ) VALUES (?,?,?)";
  1904.                 $result $this->mDb->query$queryarray$pHits$pLastHit$this->mContentId ) );
  1905.             }
  1906.         }
  1907.         return TRUE;
  1908.     }
  1909.  
  1910.  
  1911.     /**
  1912.      * Get Hits and Last Hit
  1913.      *
  1914.      * @return bool true ( will not currently report a failure )
  1915.      */
  1916.     function getHits({
  1917.         if$this->mContentId  {
  1918.             $query "SELECT `hits`,`last_hit` FROM `".BIT_DB_PREFIX."liberty_content_hits` where `content_id` = ?";
  1919.             $row $this->mDb->getRow$queryarray$this->mContentId ) );
  1920.             if !empty($row) ) {
  1921.                 $this->mInfo['hits'$row['hits'];
  1922.                 $this->mInfo['last_hit'$row['last_hit'];
  1923.             }
  1924.         }
  1925.         return TRUE;
  1926.     }
  1927.  
  1928.     /**
  1929.      * Create the generic title for a content item
  1930.      *
  1931.      * This will normally be overwriten by extended classes to provide
  1932.      * an appropriate title string
  1933.      * @param array pHash type hash of data to be used to provide base data
  1934.      * @return string Descriptive title for the page
  1935.      */
  1936.     public static function getTitleFromHash&$pHash$pDefault=TRUE {
  1937.         $ret NULL;
  1938.         if!empty$pHash['title') ) {
  1939.             $ret $pHash['title'];
  1940.         elseif$pDefault && !empty$pHash['content_name') ) {
  1941.             $ret $pHash['content_name'];
  1942.         }
  1943.         return $ret;
  1944.     }
  1945.  
  1946.     /**
  1947.      * Create the generic title for a content item
  1948.      *
  1949.      * This will normally be overwriten by extended classes to provide
  1950.      * an appropriate title string
  1951.      * @return string Descriptive title for the page
  1952.      */
  1953.     function getTitle({
  1954.         $ret NULL;
  1955.         if$this->isValid() ) {
  1956.             $ret self::getTitleFromHash$this->mInfo );
  1957.         }
  1958.         return $ret;
  1959.     }
  1960.  
  1961.     /**
  1962.      * Attempt to create a brief description of this object, most useful for <meta name="description" />
  1963.      *
  1964.      * @return array list of aliases
  1965.      */
  1966.     function generateDescription({
  1967.         $ret NULL;
  1968.         if$this->isValid() ) {
  1969.             if$this->getField('summary') ) {
  1970.                 $ret $this->getField('summary');
  1971.             elseif$this->getField('data') ) {
  1972.                 $text preg_replace('/\s+/'' '$this->parseData() );
  1973.                 // 250 to 300 is max description
  1974.                 $ret substr$text0250 );
  1975.             }
  1976.         }
  1977.         ifempty($ret) ) $ret 'Navigation of the site '.$this->getTitle()}
  1978.         return $ret;
  1979.     }
  1980.  
  1981.     /**
  1982.      * Attempt to create a collection of relevant words about this object, most useful for <meta name="keywords" />
  1983.      *
  1984.      * @return array list of aliases
  1985.      */
  1986.     function generateKeywords({
  1987.         $ret array();
  1988.         if$this->isValid() ) {
  1989.         }
  1990.         return $ret;
  1991.     }
  1992.  
  1993.     /**
  1994.      * Get array of aliases for this content object
  1995.      *
  1996.      * @return array list of aliases
  1997.      */
  1998.     function getAliases({
  1999.         $ret array();
  2000.         if$this->isValid() ) {
  2001.             $ret $this->mDb->getCol"SELECT `alias_title` FROM `".BIT_DB_PREFIX."liberty_aliases` lal INNER JOIN `".BIT_DB_PREFIX."liberty_content` lc ON(lal.`content_id`=lc.`content_id`) WHERE lal.`content_id`=? "array$this->mContentId ) );
  2002.         }
  2003.         return $ret;
  2004.     }
  2005.  
  2006.     /**
  2007.      * Access a content item type GUID
  2008.      *
  2009.      * @return string content_type_guid for the content
  2010.      */
  2011.     function getContentType({
  2012.         $ret NULL;
  2013.         ifisset$this->mInfo['content_type_guid') ) {
  2014.             $ret $this->mInfo['content_type_guid'];
  2015.         elseif$this->mContentTypeGuid {
  2016.             // for unloaded classes
  2017.             $ret $this->mContentTypeGuid;
  2018.         elseif$this->mType['content_type_guid'{
  2019.             // unloaded content might have this
  2020.             $ret $this->mType['content_type_guid'];
  2021.         }
  2022.         return $ret;
  2023.     }
  2024.  
  2025.     /**
  2026.      * Get the display name of the content type
  2027.      * @param boolean $pPlural true will return the plural form of the content type display name
  2028.      * @return string the display name of the content type
  2029.       */
  2030.     function getContentTypeName$pPlural=FALSE ){
  2031.         global $gLibertySystem;
  2032.         return $gLibertySystem->getContentTypeName$this->getContentType()$pPlural );
  2033.     }
  2034.  
  2035.  
  2036.     /**
  2037.      * getContentTypeDescription
  2038.      *
  2039.      * @param array $pContentType 
  2040.      * @access public
  2041.      * @return TRUE on success, FALSE on failure
  2042.      */
  2043.     function getContentTypeDescription$pContentType=NULL {
  2044.         deprecated'You are calling the deprecated method getContentTypeDescription, use getContentTypeName( $pPlural )' );
  2045.         return $this->getContentTypeName();
  2046.         /*
  2047.         global $gLibertySystem;
  2048.         if( is_null( $pContentType ) ) {
  2049.             $pContentType = $this->getContentType();
  2050.         }
  2051.         return $gLibertySystem->getContentTypeDescription( $pContentType );
  2052.          */
  2053.     }
  2054.  
  2055.     /**
  2056.      * Access a content item content_id
  2057.      *
  2058.      * @return string content_type_guid for the object
  2059.      */
  2060.     function getContentId({
  2061.         $ret NULL;
  2062.         ifisset$this->mContentId ) ) {
  2063.             $ret $this->mContentId;
  2064.         }
  2065.         return $ret;
  2066.     }
  2067.  
  2068.     /**
  2069.      * Return content type description for this content object.
  2070.      *
  2071.      * @return string content_type_guid description for the object
  2072.      */
  2073.     function getContentDescription({
  2074.         deprecated'You are calling the deprecated method getContentDescription, use getContentTypeName( $pPlural )' );
  2075.         return $this->getContentTypeName();
  2076.     }
  2077.  
  2078.  
  2079.     /**
  2080.      * returns a path to the template type requested
  2081.      * this is intended for package override. while not a requirement please use a naming convention of center_<action>_<content_type_guid>.tpl for new tpls
  2082.      *
  2083.      * @param string $pAction the type of template. common types are view and list
  2084.      */
  2085.     function getViewTemplate$pAction {
  2086.         $ret null;
  2087.         switch $pAction ){
  2088.             case "view":
  2089.             case "list":
  2090.                 $ret "bitpackage:liberty/center_".$pAction."_generic.tpl";
  2091.                 break;
  2092.         }
  2093.         return $ret;
  2094.     }
  2095.  
  2096.     /**
  2097.      * Pure virtual function that returns the include file that should render a page of content of this type
  2098.      * @return the fully specified path to file to be included
  2099.      */
  2100.     function getRenderFile({
  2101.         return LIBERTY_PKG_PATH.'display_content_inc.php';
  2102.     }
  2103.  
  2104.     /**
  2105.      * Pure virtual function that returns link to display a piece of content
  2106.      *
  2107.      * @param string $pLinkText Text for the link unless overriden by object title
  2108.      * @param array $pMixed different possibilities depending on derived class
  2109.      * @param string $pAnchor anchor string e.g.: #comment_123
  2110.      * @return string Formated html the link to display the page.
  2111.      */
  2112.     function getDisplayLink$pLinkText=NULL$pMixed=NULL$pAnchor=NULL {
  2113.         global $gBitSmarty;
  2114.         $ret '';
  2115.         ifempty$pMixed && !empty$this->mInfo )) {
  2116.             $pMixed &$this->mInfo;
  2117.         }
  2118.  
  2119.         ifempty$pLinkText )) {
  2120.             if!empty$pMixed['title')) {
  2121.                 $pLinkText $pMixed['title'];
  2122.             elseif!empty$pMixed['content_name') ) {
  2123.                 $pLinkText "[ ".$pMixed['content_name']." ]";
  2124.             }
  2125.         }
  2126.  
  2127.         ifempty$pLinkText )) {
  2128.             $pLinkText "[ ".tra"No Title" )." ]";
  2129.         }
  2130.  
  2131.         // we add some more info to the title of the link
  2132.         if!empty$pMixed['created')) {
  2133.             $gBitSmarty->loadPlugin'smarty_modifier_bit_short_date' );
  2134.             $linkTitle tra'Created' ).': '.smarty_modifier_bit_short_date$pMixed['created');
  2135.         else {
  2136.             $linkTitle $pLinkText;
  2137.         }
  2138.  
  2139.         // finally we are ready to create the full link
  2140.         if!empty$pMixed['content_id')) {
  2141.             $ret '<a title="'.htmlspecialchars$linkTitle ).'" href="'.LibertyContent::getDisplayUrlFromHash$pMixed ).$pAnchor.'">'.htmlspecialchars$pLinkText ).'</a>';
  2142.         }
  2143.         return $ret;
  2144.     }
  2145.  
  2146.     /**
  2147.      * Not-so-pure virtual function that returns fully qualified URI to a piece of content
  2148.      * @param string Text for DisplayLink function
  2149.      * @param array different possibilities depending on derived class
  2150.      * @return string Formated URL address to display the page.
  2151.      */
  2152.     public function getDisplayUri({
  2153.         if$this->isValid() ) {
  2154.             return BIT_ROOT_URI.substrstatic::getDisplayUrlFromHash$this->mInfo )strlenBIT_ROOT_URL ) );
  2155.         }
  2156.     }
  2157.  
  2158.     /**
  2159.      * Not-so-pure virtual function that returns fully qualified URI to a piece of content
  2160.      * @param string Text for DisplayLink function
  2161.      * @param array different possibilities depending on derived class
  2162.      * @return string Formated URL address to display the page.
  2163.      */
  2164.     public static function getDisplayUriFromHash&$pParamHash {
  2165.         return BIT_ROOT_URI.substrstatic::getDisplayUrlFromHash$pParamHash )strlenBIT_ROOT_URL ) );
  2166.     }
  2167.  
  2168.     /**
  2169.      * Not-so-pure virtual function that returns Request_URI to a piece of content
  2170.      * @param array $pMixed a hash of params to add to the url
  2171.      * @return string Formated URL address to display the page.
  2172.      */
  2173.     public static function getDisplayUrlFromHash&$pParamHash {
  2174.         $ret NULL;
  2175.         if@static::verifyId$pParamHash['content_id') ) {
  2176.             $ret BIT_ROOT_URL.'index.php?content_id='.$pParamHash['content_id'];
  2177.         }
  2178.         return $ret;
  2179.     }
  2180.  
  2181.     /**
  2182.      * Returns Request URL to a piece of content
  2183.      */
  2184.     public function getDisplayUrl({
  2185.         $ret NULL;
  2186.         if!empty$this && $this->isValid() ) {
  2187.             $ret static::getDisplayUrlFromHash$this->mInfo );
  2188.         }
  2189.         return $ret;
  2190.     }
  2191.  
  2192.     /**
  2193.      * Returns the create/edit url to a piece of content
  2194.      * @param number $pContentId a valid content id
  2195.      * @param array $pMixed a hash of params to add to the url
  2196.      */
  2197.     function getEditUrl$pContentId NULL$pMixed NULL ){
  2198.         global $gLibertySystem;
  2199.         $package $gLibertySystem->mContentTypes[$this->mType['content_type_guid']]['handler_package'];
  2200.  
  2201.         $pathConst strtoupper$package ).'_PKG_URL';
  2202.         ifdefined$pathConst ) ) {
  2203.             $packagePath constant$pathConst );
  2204.         }else{
  2205.             $packagePath BIT_ROOT_URL.$package."/";
  2206.         }
  2207.  
  2208.         if@BitBase::verifyId$pContentId ) ) {
  2209.             $ret $packagePath.'edit.php?content_id='.$pContentId;
  2210.         elseif$this->isValid() ) {
  2211.             $ret $packagePath.'edit.php?content_id='.$this->mContentId;
  2212.         else {
  2213.             $ret $packagePath.'edit.php'.(!empty$pMixed )?"?":"");
  2214.         }
  2215.         foreach$pMixed as $key => $value ){
  2216.             if$key != "content_id" || $key == "content_id" && @BitBase::verifyId$value ) ) ) {
  2217.                 $ret .= (isset($amp)?"&":"").$key."=".$value;
  2218.             }
  2219.             $amp TRUE;
  2220.         }
  2221.         return $ret;
  2222.     }
  2223.  
  2224.  
  2225.     /**
  2226.      * Not-so-pure virtual function that returns Request_URI to the preview.
  2227.      * @param string Text for DisplayLink function
  2228.      * @param array different possibilities depending on derived class
  2229.      * @return string Formated URL address to display the page.
  2230.      */
  2231.     function getPreviewUrl$pContentId NULL$pMixed NULL {
  2232.         if@BitBase::verifyId$pContentId ) ) {
  2233.             $ret LIBERTY_PKG_URL.'preview.php?content_id='.$pContentId;
  2234.         elseif@BitBase::verifyId$pMixed['content_id') ) {
  2235.             $ret LIBERTY_PKG_URL.'preview.php?content_id='.$pMixed['content_id'];
  2236.         elseif$this->isValid() ) {
  2237.             $ret LIBERTY_PKG_URL.'preview.php?content_id='.$this->mContentId;
  2238.         else {
  2239.             $ret '#';
  2240.         }
  2241.         return $ret;
  2242.     }
  2243.  
  2244.  
  2245.     /**
  2246.      * Not-so-pure virtual function that returns Request_URI to a content's thumbnail representation. It is up to the derived content what exactly this means
  2247.      * If not implemented in the content's class, this class will return NULL, which is an acceptable case meaning no thumbnail is available.
  2248.      * FisheyeGallery, BitUser might return pictures, BitArticle might return the article topic image, etc.
  2249.      * @param string Size of the url to return - should be a standard thumbnail size such as 'icon', 'avatar', 'small', 'medium', or 'large'
  2250.      * @param int optional contentId tp generate the thumbnail, if empty, the mContentId variable should be used
  2251.      * @param int optional secondary id, such as user_id or products_id, etc
  2252.      * @return string Formated URL address to display the page.
  2253.      */
  2254.     public function getThumbnailUrl$pSize 'small'$pSecondaryId NULL$pDefault=TRUE {
  2255.         if$this->isValid() ) {
  2256.             return $this->getThumbnailUrlFromHash$this->mInfo$pSize );
  2257.         }
  2258.     }
  2259.  
  2260.  
  2261.     public static function getThumbnailUrlFromHash&$pMixed$pSize 'small'$pSecondaryId NULL$pDefault=TRUE {
  2262.         $ret '';
  2263.         if!empty$pMixed['content_type']['handler_package') ) {
  2264.             $pkgName $pMixed['content_type']['handler_package'];
  2265.             if$pkgPath constantstrtoupper$pkgName ).'_PKG_PATH' ) ) {
  2266.                 iffile_exists$pkgPath.'icons/pkg_'.$pkgName.'.png' ) ) {
  2267.                     $ret constantstrtoupper$pkgName ).'_PKG_URL' ).'icons/pkg_'.$pkgName.'.png';
  2268.                 }
  2269.             }
  2270.         }
  2271.         return $ret;
  2272.     }
  2273.  
  2274.  
  2275.     public function getThumbnailUri$pSize='small' {
  2276.         if$this->isValid() ) {
  2277.             return $this->getThumbnailUriFromHash$this->mInfo$pSize );
  2278.         }
  2279.     }
  2280.  
  2281.     public static function getThumbnailUriFromHash&$pMixed$pSize='small' {
  2282.         $ret static::getThumbnailUrlFromHash$pMixed$pSize );
  2283.         // Check to make sure we don't have an absolute URI already, which could be the case for custom classes
  2284.         ifstrpos$ret'http' !== {
  2285.             $ret STORAGE_HOST_URI.substr$retstrlenBIT_ROOT_URL ) );
  2286.         }
  2287.         return$ret );
  2288.     }
  2289.  
  2290.  
  2291.     public function getThumbnailFile$pSize='small' {
  2292.         if$this->isValid() ) {
  2293.             return $this->getThumbnailFileFromHash$this->mInfo$pSize );
  2294.         }
  2295.     }
  2296.  
  2297.     public static function getThumbnailFileFromHash&$pMixed$pSize='small' {
  2298.         $ret static::getThumbnailUrlFromHash$pMixed$pSize );
  2299.         // Check to make sure we don't have an absolute URI already, which could be the case for custom classes
  2300.         ifstrpos$ret'http' !== {
  2301.             $ret substr$retstrlenBIT_ROOT_URL ) );
  2302.         }
  2303.         returnBIT_ROOT_PATH.$ret );
  2304.     }
  2305.  
  2306.  
  2307.     /**
  2308.      * Validate inbound sort_mode parameter
  2309.      * @param pParamHash hash of parameters for any getList() function
  2310.      * @return the link to display the page.
  2311.      */
  2312.     public static function getSortModeFields({
  2313.         return array(
  2314.             'content_id',
  2315.             'modifier_user',
  2316.             'modifier_real_name',
  2317.             'creator_user',
  2318.             'creator_real_name',
  2319.             'title',
  2320.             'content_type_guid',
  2321.             'ip',
  2322.             'last_modified',
  2323.             'created',
  2324.         );
  2325.     }
  2326.  
  2327.     /**
  2328.      * Validate inbound sort_mode parameter
  2329.      * @param pParamHash hash of parameters for any getList() function
  2330.      * @return the link to display the page.
  2331.      */
  2332.     public function convertSortMode&$pSortMode$pDefault='last_modified_desc' {
  2333.  
  2334.         $sortHash static::getSortModeFields();
  2335.  
  2336.         $baseSortMode str_replace'_asc'''str_replace'_desc'''$pSortMode ) );
  2337.  
  2338.         $baseSortMode preg_replace'/^.*\./'''$baseSortMode );
  2339.  
  2340.         if!in_array$baseSortMode$sortHash ) ) {
  2341.             $pSortMode $pDefault;
  2342.         }
  2343.  
  2344.         return $this->mDb->convertSortmode$pSortMode );
  2345.     }
  2346.  
  2347.  
  2348.     /**
  2349.      * Liberty override to stuff content_status_id and prepares parameters with default values for any getList function
  2350.      * @param pParamHash hash of parameters for any getList() function
  2351.      * @return the link to display the page.
  2352.      */
  2353.     public static function prepGetList&$pListHash {
  2354.         global $gBitUser;
  2355.         if$gBitUser->isAdmin() ) {
  2356.             $pListHash['min_content_status_id'= -9999;
  2357.         elseif!empty$this && is_object$this && $this->hasAdminPermission() ) {
  2358.             $pListHash['min_content_status_id'= -999;
  2359.         elseif!empty$this && is_object$this && $this->hasUpdatePermission() ) {
  2360.             $pListHash['min_content_status_id'= -99;
  2361.         else {
  2362.             $pListHash['min_content_status_id'1;
  2363.         }
  2364.  
  2365.         ifempty$pListHash['query_cache_time') ) {
  2366.             $pListHash['query_cache_time'0;
  2367.         }
  2368.  
  2369.         // if sort_mode is not set then use last_modified_desc
  2370.         if!empty$pListHash['sort_mode')) {
  2371.             ifis_string$pListHash['sort_mode'&& strpos$pListHash['sort_mode']'hits_' === {
  2372.                 // if sort mode is hits_*, then assume liberty content
  2373.                 $pListHash['sort_mode''lch.'.$pListHash['sort_mode'];
  2374.             elseifis_array$pListHash['sort_mode')) {
  2375.                 foreach$pListHash['sort_mode'as $key => $mode {
  2376.                     ifstrpos$mode'hits_' === {
  2377.                         $pListHash['sort_mode'][$key'lch.'.$mode;
  2378.                     }
  2379.                 }
  2380.             }
  2381.         else {
  2382.             // if sort_mode is not set then use last_modified_desc
  2383.             $pListHash['sort_mode''last_modified_desc';
  2384.         }
  2385.  
  2386.         return parent::prepGetList$pListHash );
  2387.     }
  2388.  
  2389.     /**
  2390.      * Get a list of users who have created entries in the content table
  2391.      *
  2392.      * @param array hash of parameters ( content_type_guid will limit list to a single content type
  2393.      * @return none the hash is updated via the reference
  2394.      ***/
  2395.     function getAuthorList&$pListHash {
  2396.         $ret NULL;
  2397.         $mid '';
  2398.  
  2399.         $bindVars array();
  2400.         if!empty$pListHash['content_type_guid') ) {
  2401.             $mid .= ' AND lc.`content_type_guid`=? ';
  2402.             $bindVars[$pListHash['content_type_guid'];
  2403.         }
  2404.  
  2405.         LibertyContent::prepGetList$pListHash );
  2406.         $query "SELECT DISTINCT(uu.`user_id`) AS hash_key, uu.`user_id`, SUM( lch.`hits` ) AS `ag_hits`, uu.`login`, uu.`real_name`
  2407.                 FROM `".BIT_DB_PREFIX."liberty_content` lc INNER JOIN `".BIT_DB_PREFIX."users_users` uu ON( uu.`user_id`=lc.`user_id` )
  2408.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_hits` lch
  2409.                     ON (`lc`.`content_id` =  `lch`.`content_id`)
  2410.                 WHERE uu.`user_id` != ".ANONYMOUS_USER_ID." AND lch.`hits` > 0 $mid
  2411.                 GROUP BY uu.`user_id`, uu.`login`, uu.`real_name`
  2412.                 ORDER BY `ag_hits` DESC";
  2413.         $result $this->mDb->query$query$bindVars$pListHash['max_records']$pListHash['offset');
  2414.         while$aux $result->fetchRow() ) {
  2415.             $ret[$aux;
  2416.         }
  2417.         return $ret;
  2418.     }
  2419.  
  2420.     /**
  2421.      * Get a list of content ranked by certain criteria set in $pListHash['sort_mode']
  2422.      *
  2423.      * @param array hash of parameters ( content_type_guid will limit list to a single content type
  2424.      * @return data
  2425.      ***/
  2426.     function getContentRanking$pListHash {
  2427.         $pListHash['sort_mode'!empty$pListHash['sort_mode'$pListHash['sort_mode''hits_desc';
  2428.  
  2429.         if$pListHash['sort_mode'== 'top_authors' {
  2430.             global $gBitUser;
  2431.             $ret['data'$gBitUser->getAuthorList$pListHash );
  2432.         else {
  2433.             include_onceLIBERTY_PKG_PATH.'LibertyContent.php' );
  2434.             $libertyContent new LibertyContent();
  2435.             $ret['data'$libertyContent->getContentList$pListHash );
  2436.         }
  2437.  
  2438.         $ret['title']     !empty$pListHash['title'$pListHash['title'tra"Content Ranking" );
  2439.         $ret['attribute'!empty$pListHash['attribute'$pListHash['attribute'tra"Hits" );
  2440.  
  2441.         return $ret;
  2442.     }
  2443.  
  2444.     /**
  2445.      * Get a list of all content
  2446.      *
  2447.      * @param string $pListHash['content_type_guid'] Content GUID to limit the list to
  2448.      * @param integer $pListHash['max_records'] Number of the first record to access ( used to page the list )
  2449.      * @param integer $pListHash['offset'] Number of records to return
  2450.      * @param string $pListHash['sort_mode'] Name of the field to sort by ( extended by _asc or _desc for sort direction )
  2451.      * @param array $pListHash['find'] List of text elements to filter the results by
  2452.      * @param integer $pListHash[''] User ID - If set, then only the objcets created by that user will be returned
  2453.      *  $pListHash['last_modified'] date - modified since
  2454.      *  $pListHash['end_date'] date - modified before
  2455.      * @return array An array of mInfo type arrays of content objects
  2456.      ***/
  2457.     function getContentList&$pListHash {
  2458.         global $gLibertySystem$gBitSystem$gBitUser$gBitSmarty;
  2459.  
  2460.         LibertyContent::prepGetList$pListHash );
  2461.  
  2462.         $hashSql array('select'=>array()'join'=>array(),'where'=>array() );
  2463.         $hashBindVars array('select'=>array()'where'=>array()'join'=>array());
  2464.         if!empty$pListHash['content_type_guid'&& is_array$pListHash['content_type_guid')) {
  2465.             foreach$pListHash['content_type_guid'as $contentTypeGuid {
  2466.                 $this->getFilter$contentTypeGuid$hashSql$hashBindVars$pListHash );
  2467.             }
  2468.         elseif!empty$pListHash['content_type_guid')) {
  2469.             $this->getFilter$pListHash['content_type_guid']$hashSql$hashBindVars$pListHash );
  2470.         }
  2471.  
  2472.         if!empty$hashSql['select')) {
  2473.             $selectSql ','.implode','$hashSql['select');
  2474.         else {
  2475.             $selectSql '';
  2476.         }
  2477.         $joinSql implode' '$hashSql['join');
  2478.         $whereSql '';
  2479.         ifempty$hashBindVars['join')) {
  2480.             $bindVars array();
  2481.         else {
  2482.             $bindVars $hashBindVars['join'];
  2483.         }
  2484.         $this->getServicesSql'content_list_sql_function'$selectSql$joinSql$whereSql$bindVarsNULL$pListHash );
  2485.  
  2486.         if$pListHash['sort_mode'== 'size_desc' {
  2487.             $pListHash['sort_mode''wiki_page_size_desc';
  2488.         }
  2489.  
  2490.         if$pListHash['sort_mode'== 'size_asc' {
  2491.             $pListHash['sort_mode''wiki_page_size_asc';
  2492.         }
  2493.  
  2494.         $old_sort_mode '';
  2495.  
  2496.         $sortHash array(
  2497.             'versions_desc',
  2498.             'versions_asc',
  2499.             'links_asc',
  2500.             'links_desc',
  2501.             'backlinks_asc',
  2502.             'backlinks_desc'
  2503.         );
  2504.  
  2505.         ifin_array$pListHash['sort_mode']$sortHash ) ) {
  2506.             $old_offset $pListHash['offset'];
  2507.             $old_max_records $pListHash['max_records'];
  2508.             $old_sort_mode $pListHash['sort_mode'];
  2509.             $pListHash['sort_mode''modifier_user_desc';
  2510.             $pListHash['offset'0;
  2511.             $pListHash['max_records'= -1;
  2512.         }
  2513.  
  2514.         ifis_array$pListHash['find') ) // you can use an array of titles
  2515.             $whereSql .= " AND lc.`title` IN ( ".implode',',array_fill0,count$pListHash['find'),'?' ) ).") ";
  2516.             $bindVars array_merge$pListHash['find']$pListHash['find');
  2517.         elseif!empty$pListHash['find'&& is_string$pListHash['find') ) // or a string
  2518.             $whereSql .= " AND UPPER(lc.`title`) like ? ";
  2519.             $bindVars['%' strtoupper$pListHash['find''%' );
  2520.         }
  2521.  
  2522.         if!empty$pListHash['content_id_list') ) // you can use an array of titles
  2523.             $whereSql .= " AND lc.`content_id` IN ( ".implode',',array_fill0,count$pListHash['content_id_list'),'?' ) ).") ";
  2524.             $bindVars array_merge$bindVars$pListHash['content_id_list');
  2525.         }
  2526.  
  2527.         // this is necessary to display useful information in the liberty RSS feed
  2528.         if!empty$pListHash['include_data') ) {
  2529.             $selectSql .= ", lc.`data`, lc.`format_guid`";
  2530.         }
  2531.  
  2532.         // if we want the primary attachment for each object
  2533.         if(  $gBitSystem->isFeatureActive'liberty_display_primary_attach' )  ){
  2534.             $selectSql .= ', lfp.`file_name`, lfp.`mime_type`, la.`attachment_id`, ';
  2535.             $joinSql .= "LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_attachments` la ON( la.`content_id` = lc.`content_id` AND la.`is_primary` = 'y' )
  2536.                          LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_files` lfp ON( lfp.`file_id` = la.`foreign_id` )";
  2537.         }
  2538.  
  2539.         // Allow selection based on arbitrary time limits -- used in calendar
  2540.         // TODO: We should replace usages of from_date and until_date with this generic setup and depricate those
  2541.         if!empty$pListHash['time_limit_column')) {
  2542.             ifempty$pListHash['time_limit_table') ) {
  2543.                 $pListHash['time_limit_table''lc.';
  2544.             }
  2545.             if!empty$pListHash['time_limit_start') ) {
  2546.                 $whereSql .= " AND ".$pListHash['time_limit_table']."`".$pListHash['time_limit_column']."` >= ? ";
  2547.                 $bindVars[$pListHash['time_limit_start'];
  2548.             }
  2549.             if!empty$pListHash['time_limit_stop') ) {
  2550.                 $whereSql .= " AND ".$pListHash['time_limit_table']."`".$pListHash['time_limit_column']."` <= ? ";
  2551.                 $bindVars[$pListHash['time_limit_stop'];
  2552.             }
  2553.         }
  2554.  
  2555.         if@$this->verifyId$pListHash['user_id') ) {
  2556.             $whereSql .= " AND lc.`user_id` = ? ";
  2557.             $bindVars[$pListHash['user_id'];
  2558.         }
  2559.  
  2560.         if@$this->verifyId$pListHash['link_content_id') ){
  2561.             $joinSql .= " INNER JOIN `".BIT_DB_PREFIX."liberty_content_links` lclk ON ( lc.`content_id` = lclk.`to_content_id` )";
  2562.             $whereSql .= " AND lclk.`from_content_id` = ? ";
  2563.             $bindVars[= (int)$pListHash['link_content_id'];
  2564.         }
  2565.  
  2566.         if$gBitSystem->isFeatureActive'liberty_display_status' &&  $gBitUser->hasPermission'p_liberty_view_all_status' )) {
  2567.             $selectSql .= ", lcs.`content_status_id`, lcs.`content_status_name`";
  2568.             $joinSql   .= " LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_status` lcs ON ( lc.`content_status_id` = lcs.`content_status_id` )";
  2569.             if!empty$pListHash['content_status_id')) {
  2570.                 if$pListHash['content_status_id'== 'not_available' {
  2571.                     $whereSql .= " AND lcs.`content_status_id` <> ? ";
  2572.                     $bindVars[50;
  2573.                 else {
  2574.                     $whereSql .= " AND lcs.`content_status_id` = ? ";
  2575.                     $bindVars[= (int)$pListHash['content_status_id'];
  2576.                 }
  2577.             }
  2578.         }
  2579.  
  2580.         // join on specific content_type_guids
  2581.         if!empty$pListHash['content_type_guid'&& is_string$pListHash['content_type_guid') ) {
  2582.             $whereSql .= ' AND lc.`content_type_guid`=? ';
  2583.             $bindVars[$pListHash['content_type_guid'];
  2584.         elseif!empty$pListHash['content_type_guid'&& is_array$pListHash['content_type_guid') ) {
  2585.             $whereSql .= " AND lc.`content_type_guid` IN ( ".implode',',array_fill 0count$pListHash['content_type_guid'),'?' ) )." )";
  2586.             $bindVars array_merge$bindVars$pListHash['content_type_guid');
  2587.         }
  2588.  
  2589.         // exclude by content_type_guids
  2590.         if!empty$pListHash['exclude_content_type_guid'&& is_string$pListHash['exclude_content_type_guid') ) {
  2591.             $whereSql .= " AND lc.`content_type_guid` != ?";
  2592.             $bindVars[$pListHash['exclude_content_type_guid'];
  2593.         elseif!empty$pListHash['exclude_content_type_guid'&& is_array$pListHash['exclude_content_type_guid') ) {
  2594.             $whereSql .= " AND lc.`content_type_guid` NOT IN ( ".implode',',array_fill 0count$pListHash['exclude_content_type_guid'),'?' ) )." )";
  2595.             $bindVars array_merge$bindVars$pListHash['exclude_content_type_guid');
  2596.         }
  2597.  
  2598.         // only display content modified more recently than this (UTC timestamp)
  2599.         if!empty$pListHash['from_date') ) {
  2600.             $whereSql .= ' AND lc.`last_modified` >= ?';
  2601.             $bindVars[$pListHash['from_date'];
  2602.         }
  2603.  
  2604.         // only display content modified before this (UTC timestamp)
  2605.         if!empty$pListHash['until_date') ) {
  2606.             $whereSql .= ' AND lc.`last_modified` <= ?';
  2607.             $bindVars[$pListHash['until_date'];
  2608.         }
  2609.  
  2610.         // Should results be hashed or sequential indexed
  2611.         $hashKeySql '';
  2612.         if!empty$pListHash['hash_key') ) {
  2613.             $hashKeySql $pListHash['hash_key'].' AS `hash_key`, ';
  2614.         }
  2615.  
  2616.         if$gBitSystem->isPackageActive'gatekeeper' ) ) {
  2617.             if$gBitSystem->isPackageActive'fisheye' ) ) {
  2618.                 // This is really ugly to have in here, and really would be better off somewhere else.
  2619.                 // However, because of the specific nature of the current implementation of fisheye galleries, I am afraid
  2620.                 // this is the only place it can go to properly enforce gatekeeper protections. Hopefully a new content generic
  2621.                 // solution will be available in ReleaseTwo - spiderr
  2622.                 if$this->mDb->isAdvancedPostgresEnabled() ) {
  2623. //                     $joinSql .= " LEFT OUTER JOIN  `".BIT_DB_PREFIX."fisheye_gallery_image_map` fgim ON (fgim.`item_content_id`=lc.`content_id`)";
  2624.                     $whereSql .= " AND (SELECT ls.`security_id` FROM connectby('fisheye_gallery_image_map', 'gallery_content_id', 'item_content_id', 'item_content_id', text( lc.`content_id` ), 0, '/')  AS t(`cb_gallery_content_id` int, `cb_item_content_id` int, level int, branch text, pos int), `".BIT_DB_PREFIX."gatekeeper_security_map` cgm,  `".BIT_DB_PREFIX."gatekeeper_security` ls
  2625.                             WHERE ls.`security_id`=cgm.`security_id` AND cgm.`content_id`=`cb_gallery_content_id` LIMIT 1) IS NULL";
  2626.                 }
  2627.             }
  2628.         }
  2629.  
  2630.         $sortHash array(
  2631.             'content_id_desc',
  2632.             'content_id_asc',
  2633.             'modifier_user_desc',
  2634.             'modifier_user_asc',
  2635.             'modifier_real_name_desc',
  2636.             'modifier_real_name_asc',
  2637.             'creator_user_desc',
  2638.             'creator_user_asc',
  2639.             'creator_real_name_desc',
  2640.             'creator_real_name_asc',
  2641.         );
  2642.  
  2643.         ifin_array$pListHash['sort_mode']$sortHash ) ) {
  2644.             $orderTable '';
  2645.         elseif!empty$pListHash['order_table') ) {
  2646.             $orderTable $pListHash['order_table'];
  2647.         elseif!empty$pListHash['sort_mode'&& strtolowersubstr$pListHash['sort_mode']0) ) =='hits' {
  2648.             $orderTable 'lch.';
  2649.         elseifstrpos$pListHash['sort_mode']'.' ) ) {
  2650.             // do not specifiy orderTable of sort_mode already has a . in it
  2651.             $orderTable '';
  2652.         else {
  2653.             $orderTable 'lc.';
  2654.         }
  2655.  
  2656.         if (!empty($hashSql['where'])) {
  2657.             $whereSql .= ' AND '.implode(' '$hashSql['where']);
  2658.         }
  2659.         if (!empty($hashBindVars['where'])) {
  2660.             $bindVars array_merge($bindVars$hashBindVars['where']);
  2661.         }
  2662.  
  2663.         $whereSql preg_replace'/^[\s]*AND\b/i''WHERE '$whereSql );
  2664.  
  2665.         // If sort mode is versions then offset is 0, max_records is -1 (again) and sort_mode is nil
  2666.         // If sort mode is links then offset is 0, max_records is -1 (again) and sort_mode is nil
  2667.         // If sort mode is backlinks then offset is 0, max_records is -1 (again) and sort_mode is nil
  2668.         $query "
  2669.             SELECT
  2670.                 $hashKeySql
  2671.                 uue.`login` AS `modifier_user`,
  2672.                 uue.`real_name` AS `modifier_real_name`,
  2673.                 uue.`user_id` AS `modifier_user_id`,
  2674.                 uuc.`login` AS `creator_user`,
  2675.                 uuc.`real_name` AS `creator_real_name`,
  2676.                 uuc.`user_id` AS `creator_user_id`,
  2677.                 lch.`hits`,
  2678.                 lch.`last_hit`,
  2679.                 lc.`event_time`,
  2680.                 lc.`title`,
  2681.                 lc.`last_modified`,
  2682.                 lc.`content_type_guid`,
  2683.                 lc.`ip`,
  2684.                 lc.`created`,
  2685.                 lc.`content_id`,
  2686.                 lcds.`data` AS `summary`
  2687.                 $selectSql
  2688.             FROM `".BIT_DB_PREFIX."liberty_content` lc
  2689.                 INNER JOIN `".BIT_DB_PREFIX."users_users` uuc ON (lc.`user_id`=uuc.`user_id`)
  2690.                 INNER JOIN `".BIT_DB_PREFIX."users_users` uue ON (lc.`modifier_user_id`=uue.`user_id`)
  2691.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_hits` lch ON( lc.`content_id` =  lch.`content_id`)
  2692.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_data` lcds ON (lc.`content_id` = lcds.`content_id` AND lcds.`data_type`='summary')
  2693.                 $joinSql
  2694.                 $whereSql
  2695.             ORDER BY ".$orderTable.$this->convertSortMode($pListHash['sort_mode']);
  2696.  
  2697.         $query_cant "
  2698.             SELECT
  2699.                 COUNT(lc.`content_id`)
  2700.             FROM `".BIT_DB_PREFIX."liberty_content` lc
  2701.                 INNER JOIN `".BIT_DB_PREFIX."users_users` uu ON (lc.`modifier_user_id`=uu.`user_id`)
  2702.             $joinSql
  2703.             $whereSql";
  2704.  
  2705.         $cant $this->mDb->getOne$query_cant$bindVars );
  2706.         $pListHash["cant"$cant;
  2707.  
  2708.         # Check for offset out of range
  2709.         if$pListHash['offset'{
  2710.             $pListHash['offset'0;
  2711.         elseif $pListHash['offset']    $pListHash["cant"{
  2712.             $lastPageNumber ceil $pListHash["cant"$pListHash['max_records'1;
  2713.             $pListHash['offset'$pListHash['max_records'$lastPageNumber;
  2714.         }
  2715.  
  2716.  
  2717.         if!empty$hashBindVars['select') ) {
  2718.             $bindVars array_merge($hashBindVars['select']$bindVars);
  2719.         }
  2720.         $result $this->mDb->query$query$bindVars$pListHash['max_records']$pListHash['offset');
  2721.  
  2722.         $ret array();
  2723.         $contentTypes $gLibertySystem->mContentTypes;
  2724.         while$aux $result->fetchRow() ) {
  2725.             if!empty$contentTypes[$aux['content_type_guid']] ) ) {
  2726.                 // quick alias for code readability
  2727.                 $type                       &$contentTypes[$aux['content_type_guid']];
  2728.                 $aux['content_name']         $type['content_name'];
  2729.                 $aux['creator']             (isset$aux['creator_real_name'$aux['creator_real_name'$aux['creator_user');
  2730.                 $aux['real_name']           (isset$aux['creator_real_name'$aux['creator_real_name'$aux['creator_user');
  2731.                 $aux['editor']              (isset$aux['modifier_real_name'$aux['modifier_real_name'$aux['modifier_user');
  2732.                 $aux['user']                $aux['creator_user'];
  2733.                 $aux['user_id']             $aux['creator_user_id'];
  2734.                 // create *one* object for each object *type* to  call virtual methods.
  2735.                 ifempty$type['content_object') ) {
  2736.                     include_once$gBitSystem->mPackages[$type['handler_package']]['path'].$type['handler_file');
  2737.                     $type['content_object'new $type['handler_class']();
  2738.                 }
  2739.                 if!empty$gBitSystem->mPackages[$type['handler_package']] ) ) {
  2740.                     if$aux['content_type_guid'== BITUSER_CONTENT_TYPE_GUID {
  2741.                         // here we provide getDisplay(Link|Url) with user-specific information that we get the correct links to display in pages
  2742.                         $userInfo $gBitUser->getUserInfoarray'content_id' => $aux['content_id'));
  2743.                         $aux['title']        $type['content_object']->getTitleFromHash$userInfo );
  2744.                         $aux['display_link'$type['content_object']->getDisplayLink$userInfo['login']$userInfo );
  2745.                         $aux['display_url']  $type['content_object']->getDisplayUrl$userInfo['login');
  2746.                     else {
  2747.                         $aux['title']        $type['content_object']->getTitleFromHash$aux );
  2748.                         $aux['display_link'$type['content_object']->getDisplayLink$aux['title']$aux );
  2749.                         /**
  2750.                          * @TODO standardize getDisplayUrl params
  2751.                          * nice try, but you can't do this because individual classes have gone off the reservation changing the params they accept
  2752.                          * for distributed packages we need to enforce that method overrides all take the same basic params.
  2753.                          **/
  2754.                         // $aux['display_url']  = $type['content_object']->getDisplayUrl( NULL, $aux );
  2755.                         $aux['display_url'BIT_ROOT_URL."index.php?content_id=".$aux['content_id'];
  2756.                     }
  2757.  
  2758.                     if!empty$pListHash['thumbnail_size') ) {
  2759.                         $aux['content_object'new $type['handler_class']NULL$aux['content_id');
  2760.                         if$aux['content_object']->loadFALSE ) ) {
  2761.                             $aux['thumbnail_url'$aux['content_object']->getThumbnailUrl$pListHash['thumbnail_size');
  2762.                         }
  2763.                     }
  2764.  
  2765.                 }
  2766.  
  2767.                 /**
  2768.                  * @TODO standardize use of thumbnail_url and provision for hash of thumbnail sizes
  2769.                  *
  2770.                  * We have a bit of a mess with the use of thumbnail_url where sometimes it is a hash of sizes, and sometimes it is a single size
  2771.                  * we should standardize the param and what kind of value it returns, and if we need both types then have two params.
  2772.                  * This ultimately might need to be more sophisticated to deal with different mime types.
  2773.                  **/
  2774.                 if(  $gBitSystem->isFeatureActive'liberty_display_primary_attach' ) ) {
  2775.                     $aux['thumbnail_urls'liberty_fetch_thumbnails$aux );
  2776.                 }
  2777.  
  2778.                 ifisset$aux['hash_key') ) {
  2779.                     $ret[$aux['hash_key']] $aux;
  2780.                 else {
  2781.                     $ret[$aux;
  2782.                 }
  2783.             }
  2784.         }
  2785.  
  2786.         // If sortmode is versions, links or backlinks sort using the ad-hoc function and reduce using old_offse and old_max_records
  2787.         if$old_sort_mode == 'versions_asc' && !empty$ret['versions') ) {
  2788.             usort$ret'compare_versions' );
  2789.         }
  2790.  
  2791.         if$old_sort_mode == 'versions_desc' && !empty$ret['versions') ) {
  2792.             usort$ret'r_compare_versions' );
  2793.         }
  2794.  
  2795.         if$old_sort_mode == 'links_desc' && !empty$ret['links') ) {
  2796.             usort$ret'compare_links' );
  2797.         }
  2798.  
  2799.         if$old_sort_mode == 'links_asc' && !empty$ret['links') ) {
  2800.             usort$ret'r_compare_links' );
  2801.         }
  2802.  
  2803.         if$old_sort_mode == 'backlinks_desc' && !empty$ret['backlinks') ) {
  2804.             usort$ret'compare_backlinks' );
  2805.         }
  2806.  
  2807.         if$old_sort_mode == 'backlinks_asc' && !empty$ret['backlinks') ) {
  2808.             usort$ret'r_compare_backlinks' );
  2809.         }
  2810.  
  2811.         ifin_array$old_sort_modearray(
  2812.                 'versions_desc',
  2813.                 'versions_asc',
  2814.                 'links_asc',
  2815.                 'links_desc',
  2816.                 'backlinks_asc',
  2817.                 'backlinks_desc'
  2818.             ))) {
  2819.             $ret array_slice$ret$old_offset$old_max_records );
  2820.         }
  2821.  
  2822.         LibertyContent::postGetList$pListHash );
  2823.         return $ret;
  2824.     }
  2825.  
  2826.     /**
  2827.      * Get a list of all structures this content is a member of
  2828.      **/
  2829.  
  2830.     function getStructures({
  2831.         $ret NULL;
  2832.         if$this->isValid() ) {
  2833.             $ret array();
  2834.             $structures_added array();
  2835.             $query 'SELECT ls.*, lc.`title`, tcr.`title` AS `root_title`
  2836.                 FROM `'.BIT_DB_PREFIX.'liberty_content` lc, `'.BIT_DB_PREFIX.'liberty_structures` ls
  2837.                 INNER JOIN  `'.BIT_DB_PREFIX.'liberty_structures` tsr ON( tsr.`structure_id`=ls.`root_structure_id` )
  2838.                 INNER JOIN `'.BIT_DB_PREFIX.'liberty_content` tcr ON( tsr.`content_id`=tcr.`content_id` )
  2839.                 WHERE lc.`content_id`=ls.`content_id` AND ls.`content_id`=?';
  2840.             if$result $this->mDb->query$query,array$this->mContentId ) ) ) {
  2841.                 while ($res $result->fetchRow()) {
  2842.                     $ret[$res;
  2843.                 }
  2844.             }
  2845.         }
  2846.         return $ret;
  2847.     }
  2848.  
  2849.     /*
  2850.      * Splits content either at the ...split... or at the
  2851.      * length specified if no manual split is in the content.
  2852.      *
  2853.      * @param pParseHash a hash with 'data' in it and any
  2854.      *        arguments to the parser as required
  2855.      * @param pLength the length to split at if no ...split... is present
  2856.      * @param pForceLength force split at length (default false)
  2857.      * @return parsed data cut at LIBERTY_SPLIT_REGEX or at $pLength
  2858.      */
  2859.     function parseSplit$pParseHash$pLength 500$pForceLength FALSE {
  2860.         global $gLibertySystem$gBitSystem;
  2861.  
  2862.         if$pForceLength {
  2863.             $res['data'preg_replaceLIBERTY_SPLIT_REGEX''$res['data');
  2864.         }
  2865.  
  2866.         // Indicate that we are parsing split data. This will clean up the HTML better and avoid pre / post filters
  2867.         $pParseHash['split_parse'TRUE;
  2868.  
  2869.         // copy data that we can compare strings later on
  2870.         $res['data'$pParseHash['data'];
  2871.  
  2872.         // allways set the cache extension to description if it's not set manually
  2873.         $pParseHash['cache_extension'!empty$pParseHash['cache_extension'$pParseHash['cache_extension''desc';
  2874.  
  2875.         // split data according to user specifications
  2876.         ifpreg_matchLIBERTY_SPLIT_REGEX$res['data')) {
  2877.             // this has been manually split
  2878.             $res['man_split'TRUE;
  2879.             $parts preg_splitLIBERTY_SPLIT_REGEX$res['data');
  2880.             $pParseHash['data'$parts[0];
  2881.         else {
  2882.             // Include length in cache file
  2883.             $pParseHash['cache_extension'.= '.'.$pLength;
  2884.             $pParseHash['data'substr$res['data']0$pLength );
  2885.             // snip off a broken tag at the end if there is one
  2886.             $pParseHash['data'preg_replace'!<[a-zA-Z/][^>]*?$!'''$pParseHash['data');
  2887.         }
  2888.  
  2889.         // set 'has_more' and remove cache_extension if we don't need it
  2890.         if!$res['has_more'$res['data'!= $pParseHash['data'))) {
  2891.             $pParseHash['cache_extension'NULL;
  2892.         }
  2893.  
  2894.         if!empty$pParseHash['data')) {
  2895.             // parse data and run it through postsplit filter
  2896.             if$parsed $this->parseData$pParseHash )) {
  2897.                 // parsing split content can break stuff so we remove trailing junk
  2898.                 $res['parsed'$res['parsed_description'preg_replace'!((<br\b[^>]*>)*\s*)*$!si'''$parsed );
  2899.  
  2900.                 // we append '...' when the split was generated automagically
  2901.                 ifempty$res['man_split'&& !empty$res['has_more')) {
  2902.                     $res['parsed_description'.= '&hellip;';
  2903.                 }
  2904.             }
  2905.         else {
  2906.             // did we parse an empty page?
  2907.             $res['parsed'$res['parsed_description''';
  2908.             $res['has_more'FALSE;
  2909.         }
  2910.  
  2911.         return $res;
  2912.     }
  2913.  
  2914.     /**
  2915.      * Process the raw content blob using the speified content GUID processor
  2916.      *
  2917.      * This is the "object like" method. It should be more object like,
  2918.      * but for now, we'll just point to the old lib style "parse_data" - XOXO spiderr
  2919.      * @param         pMixed can be a string or a hash - if a string is given, it will be parsed without the use of cache
  2920.      * @param string  pMixed['data'] string to be parsed
  2921.      * @param int     pMixed['content_id'] content_id or the item to be parsed - required for caching and optimal parser performance
  2922.      * @param boolean pMixed['no_cache'] disable caching
  2923.      * @param string  pMixed['cache_extension'] cache to a separate file. useful for truncated displays of parsed content such as article front page
  2924.      * @param string pFormatGuid processor to use
  2925.      * @return string Formated data string
  2926.      */
  2927.     function parseData$pMixed=NULL$pFormatGuid=NULL {
  2928.         global $gLibertySystem$gBitSystem$gBitUser;
  2929.  
  2930.         // get the data into place
  2931.         ifempty$pMixed && !empty$this->mInfo['data') ) {
  2932.             $parseHash $this->mInfo;
  2933.         elseifis_array$pMixed ) ) {
  2934.             $parseHash $pMixed;
  2935.             ifempty$parseHash['data') ) {
  2936.                 $parseHash['data''';
  2937.             }
  2938.         else {
  2939.             $parseHash['data'$pMixed;
  2940.         }
  2941.  
  2942.         // sanitise parseHash a bit
  2943.         $parseHash['content_id']      !empty$parseHash['content_id')      $parseHash['content_id']      NULL;
  2944.         $parseHash['cache_extension'!empty$parseHash['cache_extension'$parseHash['cache_extension'NULL;
  2945.         $parseHash['format_guid']     !empty$parseHash['format_guid')     $parseHash['format_guid']     $pFormatGuid;
  2946.         $parseHash['user_id']         !empty$parseHash['user_id')         $parseHash['user_id']         is_object$gBitUser $gBitUser->mUserId ANONYMOUS_USER_ID;
  2947.  
  2948.         // Ensure we have a format
  2949.         ifempty$parseHash['format_guid')) {
  2950.             $parseHash['format_guid'$gBitSystem->getConfig'default_format''tikiwiki' );
  2951.         }
  2952.  
  2953.         $ret NULL;
  2954.         // Handle caching if it is enabled.
  2955.         if$gBitSystem->isFeatureActive'liberty_cache' && !empty$parseHash['content_id'&& empty$parseHash['no_cache') ) {
  2956.             if$cacheFile LibertyContent::getCacheFile$parseHash['content_id']$parseHash['cache_extension') ) {
  2957.                 // Attempt to read cache file
  2958.                 if!$ret LibertyContent::readCacheFile$cacheFile ))) {
  2959.                     // failed to read from cache.
  2960.                     $parseAndCache TRUE;
  2961.                 else {
  2962.                     // Note that we read from cache.
  2963.                     $this->mInfo['is_cached'TRUE;
  2964.                 }
  2965.             }
  2966.         }
  2967.  
  2968.         // if $ret is empty, we haven't read anything from cache yet - we need to parse the raw data
  2969.         ifempty$ret || !empty$parseAndCache )) {
  2970.             if!empty$parseHash['data'&& $parseHash['format_guid'{
  2971.                 $replace array();
  2972.                 // extract and protect ~pp~...~/pp~ and ~np~...~/np~ sections
  2973.                 parse_protect$parseHash['data']$replace );
  2974.  
  2975.                 // some few filters such as stencils need to be before the data plugins
  2976.                 LibertyContent::filterData$parseHash['data']$parseHash'preplugin' );
  2977.  
  2978.                 // this will handle all liberty data plugins like {code} and {attachment} usage in all formats
  2979.                 parse_data_plugins$parseHash['data']$replace$this$parseHash );
  2980.  
  2981.                 // pre parse filter according to what we're parsing - split or full body
  2982.                 $filter empty$parseHash['split_parse''parse' 'split';
  2983.                 LibertyContent::filterData$parseHash['data']$parseHash'pre'.$filter );
  2984.  
  2985.                 if$func $gLibertySystem->getPluginFunction$parseHash['format_guid']'load_function' ) ) {
  2986.                     // get the beast parsed
  2987.                     if$ret $func$parseHash$this )) {
  2988.                         // post parse filter
  2989.                         LibertyContent::filterData$ret$parseHash'post'.$filter );
  2990.  
  2991.                         // before we cache we insert the protected sections back - currently this is even after the filters.
  2992.                         // this might not be ideal but it allows stuff like ~pp~{maketoc}~/pp~
  2993.                         $replace array_reverse$replace );
  2994.                         foreach$replace as $rep {
  2995.                             $ret str_replace$rep["key"]$rep["data"]$ret );
  2996.                         }
  2997.  
  2998.                         if!empty$parseAndCache )) {
  2999.                             LibertyContent::writeCacheFile$cacheFile$ret );
  3000.                         }
  3001.                     }
  3002.                 }
  3003.             }
  3004.         }
  3005.  
  3006.         return $ret;
  3007.     }
  3008.  
  3009.     /**
  3010.      * filterData will apply one of the specified filter stages to the input data
  3011.      *
  3012.      * @param array $pFilterHash array of data that should be filtered
  3013.      * @param string $pFilterHash[data] is the actual data that needs to be filtered
  3014.      * @param keyword $pFilterStage specify what filter stage the data is at: pre, post, presplit or postsplit
  3015.      * @access public
  3016.      * @return filtered data
  3017.      */
  3018.     function filterData&$pData&$pFilterHash$pFilterStage 'preparse' {
  3019.         global $gLibertySystem;
  3020.         if!empty$pData && $filters $gLibertySystem->getPluginsOfTypeFILTER_PLUGIN )) {
  3021.             foreach$filters as $guid => $filter {
  3022.                 if$gLibertySystem->isPluginActive$guid && $func $gLibertySystem->getPluginFunction$guid$pFilterStage.'_function' )) {
  3023.                     $func$pData$pFilterHash!empty$this $this NULL ));
  3024.                 }
  3025.             }
  3026.         }
  3027.     }
  3028.  
  3029.     /**
  3030.      * Special parsing for multipage articles
  3031.      *
  3032.      * Temporarily remove <pre>...</pre> sections to protect
  3033.      * from broke <pre>pre</pre> tags and leave well known <pre>pre</pre>
  3034.      * behaviour (i.e. type all text inside AS IS w/o
  3035.      * any interpretation)
  3036.      * @param string Data to process
  3037.      * @return string Extracted pages
  3038.      */
  3039.     function getNumberOfPages&$data {
  3040.         $preparsed array();
  3041.  
  3042.         preg_match_all("/(<[Pp][Rr][Ee]>)((.|\n)*?)(<\/[Pp][Rr][Ee]>)/"$data$preparse);
  3043.         $idx 0;
  3044.  
  3045.         foreach (array_unique($preparse[2])as $pp{
  3046.             $key md5(BitSystem::genPass());
  3047.  
  3048.             $aux["key"$key;
  3049.             $aux["data"$pp;
  3050.             $preparsed[$aux;
  3051.             $data str_replace($preparse[1][$idx$pp $preparse[4][$idx]$key$data);
  3052.             $idx $idx 1;
  3053.         }
  3054.  
  3055.         $parts explode(defined('PAGE_SEP'PAGE_SEP "...page..."$data);
  3056.         return count($parts);
  3057.     }
  3058.  
  3059.     /**
  3060.      * Special parsing for a particular page of a multipage article
  3061.      *
  3062.      * Temporary remove &lt;PRE&gt;&lt;/PRE&gt; secions to protect
  3063.      * from broke &lt;PRE&gt; tags and leave well known &lt;PRE&gt;
  3064.      * behaviour (i.e. type all text inside AS IS w/o
  3065.      * any interpretation)
  3066.      * @param string Data to process
  3067.      * @param integer Number of page to extract
  3068.      * @return string Extracted page
  3069.      */
  3070.     function getPage&$data$i {
  3071.         $preparsed array();
  3072.  
  3073.         preg_match_all("/(<[Pp][Rr][Ee]>)((.|\n)*?)(<\/[Pp][Rr][Ee]>)/"$data$preparse);
  3074.         $idx 0;
  3075.  
  3076.         foreach (array_unique($preparse[2])as $pp{
  3077.             $key md5(BitSystem::genPass());
  3078.  
  3079.             $aux["key"$key;
  3080.             $aux["data"$pp;
  3081.             $preparsed[$aux;
  3082.             $data str_replace($preparse[1][$idx$pp $preparse[4][$idx]$key$data);
  3083.             $idx $idx 1;
  3084.         }
  3085.  
  3086.         // Get slides
  3087.         $parts explode(defined('PAGE_SEP'PAGE_SEP "...page..."$data);
  3088.  
  3089.         if (substr($parts[$i 1]15== "<br/>"{
  3090.             $ret substr($parts[$i 1]6);
  3091.         else {
  3092.             $ret $parts[$i 1];
  3093.         }
  3094.  
  3095.         // Replace back <PRE> sections
  3096.         foreach ($preparsed as $pp{
  3097.             $ret str_replace($pp["key"]"<pre>" $pp["data""</pre>"$ret);
  3098.         }
  3099.  
  3100.         return $ret;
  3101.     }
  3102.  
  3103.     /**
  3104.      * convenience function to process a $_REQUEST array
  3105.      **/
  3106.  
  3107.     function decodeAjaxRequest&$pParamHash ){
  3108.         foreach$pParamHash as $key => $value ){
  3109.             ifis_string($value) ){
  3110.                 $pParamHash[$keyhtmlspecialchars_decode$value );
  3111.             }
  3112.         }
  3113.     }
  3114.  
  3115.     /**
  3116.      * Set content related mStructureId
  3117.      *
  3118.      * @param integer Structure ID
  3119.      */
  3120.     function setStructure$pStructureId {
  3121.         if$this->verifyId$pStructureId ) ) {
  3122.             $this->mStructureId = $pStructureId;
  3123.         }
  3124.     }
  3125.  
  3126.     /**
  3127.      * Check the number of structures that the content object is being used in
  3128.      *
  3129.      * @param integer Structure ID ( If NULL or not supplied check all structures )
  3130.      * @return integer Number of structures that this content object is located in
  3131.      */
  3132.     function isInStructure$pStructureId=NULL {
  3133.         if$this->isValid() ) {
  3134.             $whereSql NULL;
  3135.             $bindVars array$this->mContentId );
  3136.             if$pStructureId {
  3137.                 array_push$bindVars$pStructureId );
  3138.                 $whereSql ' AND ls.`root_structure_id`=? ';
  3139.             }
  3140.             $query  "SELECT `structure_id` FROM `".BIT_DB_PREFIX."liberty_structures` ls
  3141.                     WHERE ls.`content_id`=? $whereSql";
  3142.             $cant $this->mDb->getOne$query$bindVars );
  3143.             return $cant;
  3144.         }
  3145.     }
  3146.  
  3147.     /**
  3148.      * This is a generic liberty content function to gather indexable words. Override this function
  3149.      * in your BitPackage.php file if you need to add more indexable words from files other than
  3150.      * tiki_content and users_users.
  3151.      */
  3152.     function setIndexData$pContentId {
  3153.         global $gBitSystem ;
  3154.         if $pContentId == $pContentId $this->mContentId;
  3155.         $sql "SELECT lc.`title`, lc.`data`, lcds.`data` AS `summary`, uu.`login`, uu.`real_name`
  3156.                 FROM `" BIT_DB_PREFIX "liberty_content` lc
  3157.                     INNER JOIN `" BIT_DB_PREFIX "users_users` uu ON uu.`user_id`    = lc.`user_id`
  3158.                     LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_data` lcds ON (lc.`content_id` = lcds.`content_id` AND lcds.`data_type`='summary')
  3159.                 WHERE lc.`content_id` = ?" ;
  3160.         $res $gBitSystem->mDb->getRow($sqlarray($pContentId));
  3161.         if (!(isset($this->mInfo['no_index']and $this->mInfo['no_index'== true)) {
  3162.             $this->mInfo['index_data'$res["title"" " $res["data"" " $res["login"" " $res["real_name";
  3163.         }
  3164.     }
  3165.  
  3166.     // -------------------- Cache Funtions -------------------- //
  3167.  
  3168.     /**
  3169.      * Check if content has a cache file
  3170.      *
  3171.      * @param array $pContentId Content id of cached item
  3172.      * @access public
  3173.      * @return absolute path
  3174.      */
  3175.     function isCached$pContentId NULL {
  3176.         global $gBitSystem;
  3177.         ifempty$pContentId && @BitBase::verifyId$this->mContentId ) ) {
  3178.             $pContentId $this->mContentId;
  3179.         }
  3180.  
  3181.         return$gBitSystem->getConfig'liberty_cache' && is_fileLibertyContent::getCacheFile$pContentId )));
  3182.     }
  3183.  
  3184.     /**
  3185.      * Get the path where we store liberty cached content
  3186.      *
  3187.      * @access public
  3188.      * @return absolute path
  3189.      */
  3190.     function getCacheBasePath({
  3191.         return str_replace'//''/'TEMP_PKG_PATH.LIBERTY_PKG_NAME.'/cache/' );
  3192.     }
  3193.  
  3194.     /**
  3195.      * Get the path to directory where an individual cache item is stored
  3196.      *
  3197.      * @param array $pContentId Content id of cached item
  3198.      * @access public
  3199.      * @return path on success, FALSE on failure
  3200.      */
  3201.     function getCachePath$pContentId NULL {
  3202.         global $gBitSystem;
  3203.         ifempty$pContentId && @BitBase::verifyId$this->mContentId ) ) {
  3204.             $pContentId $this->mContentId;
  3205.         }
  3206.  
  3207.         $ret FALSE;
  3208.         if@BitBase::verifyId$pContentId ) ) {
  3209.             if$gBitSystem->isFeatureActive'liberty_flat_cache' )) {
  3210.                 $subdir floor$pContentId 1000 );
  3211.                 $path LibertyContent::getCacheBasePath().$subdir.'/';
  3212.             else {
  3213.                 $subdir $pContentId 1000;
  3214.                 $path LibertyContent::getCacheBasePath().$subdir.'/'.$pContentId.'/';
  3215.             }
  3216.             ifis_dir$path || mkdir_p$path ) ) {
  3217.                 $ret $path;
  3218.             }
  3219.         }
  3220.  
  3221.         return $ret;
  3222.     }
  3223.  
  3224.     /**
  3225.      * Attempts to read from the specified cache file checking if the
  3226.      * cached data has expired.
  3227.      *
  3228.      * @param the name of the cache file from getCacheFile()
  3229.      * @return the contents of the cache file or NULL
  3230.      */
  3231.     function readCacheFile$pCacheFile {
  3232.         global $gBitSystem;
  3233.         $ret NULL;
  3234.         ifis_file$pCacheFile && time(filemtime$pCacheFile )) $gBitSystem->getConfig('liberty_cache'&& filesize$pCacheFile {
  3235.             // get contents from cache file
  3236.             $h fopen$pCacheFile'r' );
  3237.             $ret fread$hfilesize$pCacheFile ) );
  3238.             fclose$h );
  3239.         }
  3240.         return $ret;
  3241.     }
  3242.  
  3243.     /**
  3244.      * Unconditionally writes data to the cache file.
  3245.      * Does not check for error assuming if write failed that the
  3246.      * read will as well.
  3247.      *
  3248.      * @param the name of the cache file from getCacheFile() to write
  3249.      * @param the contents to write to the file
  3250.      */
  3251.     function writeCacheFile$pCacheFile$pData {
  3252.         // Cowardly refuse to write nothing.
  3253.         if!empty$pData )) {
  3254.             // write parsed contents to cache file
  3255.             $h fopen$pCacheFile'w' );
  3256.             fwrite$h$pData );
  3257.             fclose$h );
  3258.         }
  3259.     }
  3260.  
  3261.     /**
  3262.      * Get the path to file where an individual cache item is stored
  3263.      *
  3264.      * @param array $pContentId Content id of cached item
  3265.      * @access public
  3266.      * @return filename on success, FALSE on failure
  3267.      */
  3268.     function getCacheFile$pContentId NULL$pCacheExtension NULL {
  3269.         if$ret LibertyContent::getCachePath$pContentId ) ) {
  3270.             return$ret.$pContentId.!empty$pCacheExtension '.'.$pCacheExtension '') );
  3271.         else {
  3272.             return FALSE;
  3273.         }
  3274.     }
  3275.  
  3276.     /**
  3277.      * Delete cache files for a given content item
  3278.      *
  3279.      * @param array $pContentId 
  3280.      * @access public
  3281.      * @return TRUE on success, FALSE on failure
  3282.      */
  3283.     function expungeCacheFile$pContentId NULL {
  3284.         global $gBitSystem;
  3285.         if$gBitSystem->isFeatureActive'liberty_cache' && @BitBase::verifyId$pContentId ) ) {
  3286.             // we need to unlink all files with the same id and any extension
  3287.             if$dh opendir$cacheDir LibertyContent::getCachePath$pContentId ) ) ) {
  3288.                 whileFALSE !== $file readdir$dh ) ) ) {
  3289.                     if$file != '.' && $file != '..' && preg_match"/^".$pContentId."$/"$file || preg_match"/^".$pContentId."\..*/"$file ) ) ) {
  3290.                         @unlink$cacheDir.$file );
  3291.                     }
  3292.                 }
  3293.             }
  3294.         }
  3295.  
  3296.         return TRUE;
  3297.     }
  3298.  
  3299.     /**
  3300.      * Delete liberty cache
  3301.      *
  3302.      * @param array $pContentId 
  3303.      * @access public
  3304.      * @return TRUE on success, FALSE on failure
  3305.      */
  3306.     function expungeCache({
  3307.         global $gBitSystem;
  3308.         $ret FALSE;
  3309.         if$gBitSystem->isFeatureActive'liberty_cache' )) {
  3310.             $cacheDir LibertyContent::getCacheBasePath();
  3311.             // make sure that we're in the temp dir at least
  3312.             ifstrstr$cacheDirstr_replace'//''/'TEMP_PKG_PATH ))) {
  3313.                 unlink_r$cacheDir );
  3314.                 // make sure we have a usable cache directory to work with
  3315.                 $ret is_dir$cacheDir || mkdir_p$cacheDir ));
  3316.             }
  3317.         }
  3318.         return $ret;
  3319.     }
  3320.  
  3321.     /**
  3322.      * getFilter
  3323.      *
  3324.      * @param array $pContentTypeGuid 
  3325.      * @param array $pSql 
  3326.      * @param array $pBindVars 
  3327.      * @param array $pHash 
  3328.      * @access public
  3329.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  3330.      * @todo
  3331.      *  - i think this function is not being used and will hopefully be removed soon - xing - Saturday Jul 07, 2007   19:54:02 CEST
  3332.      *  - it is called in getContentList but I think that services can do what it does now - nick - Sunday Sep 30, 2007
  3333.      */
  3334.     function getFilter$pContentTypeGuid&$pSql&$pBindVars$pHash null{
  3335.         global $gLibertySystem$gBitSystem;
  3336.         foreach ($gLibertySystem->mContentTypes as $type{
  3337.             if ($type['content_type_guid'== $pContentTypeGuid{
  3338.                 $path $gBitSystem->mPackages[$type['handler_package']]['path'];//constant(strtoupper($type['handler_package']).'_PKG_PATH');
  3339.                 include_once($path.$type['handler_file']);
  3340.                 $content new $type['handler_class'];
  3341.                 if (method_exists($content'getFilterSql')) {
  3342.                     $content->getFilterSql($pSql$pBindVars$pHash);
  3343.                 }
  3344.             }
  3345.         }
  3346.     }
  3347.  
  3348.     // -------------------- Action Logging Funtions -------------------- //
  3349.  
  3350.     /**
  3351.      * storeActionLog
  3352.      * Note: use $gBitSystem throughout that this function can be called statically if needed
  3353.      *
  3354.      * @param array $pParamHash 
  3355.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  3356.      */
  3357.     public static function storeActionLogFromHash$pParamHash NULL {
  3358.         global $gBitSystem;
  3359.  
  3360.         if$gBitSystem->isFeatureActive'liberty_action_log' && $this->verifyActionLog$pParamHash ) ) {
  3361.             $gBitSystem->mDb->associateInsertBIT_DB_PREFIX."liberty_action_log"$pParamHash['action_log_store');
  3362.         }
  3363.     }
  3364.  
  3365.     /**
  3366.      * storeActionLog
  3367.      * Note: use $gBitSystem throughout that this function can be called statically if needed
  3368.      *
  3369.      * @param array $pParamHash 
  3370.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  3371.      */
  3372.     public function storeActionLog$pParamHash NULL {
  3373.         global $gBitSystem;
  3374.  
  3375.         if!empty$this && @BitBase::verifyId$this->mContentId ) ) {
  3376.             $pParamHash['action_log']['content_id'$this->mContentId;
  3377.         }
  3378.         if!empty$this->mInfo['title') ) {
  3379.             $pParamHash['action_log']['title'$this->mInfo['title'];
  3380.         }
  3381.         $log_message '';
  3382.         ifempty$pParamHash['action_log']['log_message'&& !empty$this->mLogs ) ) {
  3383.             foreach$this->mLogs as $key => $msg {
  3384.                 $log_message .= "$msg";
  3385.             }
  3386.             $pParamHash['action_log']['log_message'$log_message;
  3387.         }
  3388.         $error_message '';
  3389.         ifempty$pParamHash['action_log']['error_message'&& !empty$this->mErrors ) ) {
  3390.             foreach$this->mErrors as $key => $msg {
  3391.                 $error_message .= "$msg\n";
  3392.             }
  3393.             $pParamHash['action_log']['error_message'$error_message;
  3394.         }
  3395.         if$gBitSystem->isFeatureActive'liberty_action_log' && static::verifyActionLog$pParamHash ) ) {
  3396.             $gBitSystem->mDb->associateInsertBIT_DB_PREFIX."liberty_action_log"$pParamHash['action_log_store');
  3397.         }
  3398.     }
  3399.  
  3400.     /**
  3401.      * verify the data in the action log is ready for storing
  3402.      * First checks $pParamHash['action_log'] for information and then the content_store stuff
  3403.      * Note: use $gBitSystem throughout that this function can be called statically if needed
  3404.      *
  3405.      * @param array $pParamHash 
  3406.      * @return TRUE on success, FALSE on failure
  3407.      */
  3408.     public static function verifyActionLog&$pParamHash {
  3409.         global $gBitUser$gBitSystem;
  3410.  
  3411.         // we will set $ret FALSE if there is a problem along the way
  3412.         // we can't populate mErrors since it would defeat the purpose having errors about the logging system
  3413.         $ret TRUE;
  3414.  
  3415.         // content_id isn't strictly needed
  3416.         if@BitBase::verifyId$pParamHash['action_log']['content_id') ) {
  3417.             $pParamHash['action_log_store']['content_id'$pParamHash['action_log']['content_id'];
  3418.         elseif@BitBase::verifyId$pParamHash['content_id') ) {
  3419.             $pParamHash['action_log_store']['content_id'$pParamHash['content_id'];
  3420.         }
  3421.         // generic information needed in log
  3422.         if!empty$pParamHash['action_log']['user_id') ) {
  3423.             $pParamHash['action_log_store']['user_id'$pParamHash['action_log']['user_id'];
  3424.         else {
  3425.             $pParamHash['action_log_store']['user_id'$gBitUser->mUserId;
  3426.         }
  3427.         if!empty$pParamHash['action_log']['title') ) {
  3428.             $pParamHash['action_log_store']['title'$pParamHash['action_log']['title'];
  3429.         elseif!empty$pParamHash['content_store']['title') ) {
  3430.             $pParamHash['action_log_store']['title'$pParamHash['content_store']['title'];
  3431.         else {
  3432.             $ret FALSE;
  3433.         }
  3434.         // IP of the user
  3435.         ifempty$pParamHash['action_log']['ip') ) {
  3436.             if!empty$pParamHash['content_store']['ip') ) {
  3437.                 $pParamHash['action_log']['ip'$pParamHash['content_store']['ip'];
  3438.             elseifempty$_SERVER["REMOTE_ADDR") ) {
  3439.                 $pParamHash['action_log']['ip''127.0.0.1';
  3440.             else {
  3441.                 $pParamHash['action_log']['ip'$_SERVER["REMOTE_ADDR"];
  3442.             }
  3443.         }
  3444.         $pParamHash['action_log_store']['ip'$pParamHash['action_log']['ip'];
  3445.         $pParamHash['action_log_store']['last_modified'$gBitSystem->getUTCTime();
  3446.  
  3447.         // the log message
  3448.         $log_message '';
  3449.         ifempty$pParamHash['action_log']['log_message'&& !empty$this && !empty$this->mLogs ) ) {
  3450.             foreach$this->mLogs as $key => $msg {
  3451.                 $log_message .= "$msg";
  3452.             }
  3453.         elseif!empty$pParamHash['action_log']['log_message') ) {
  3454.             $log_message $pParamHash['action_log']['log_message'];
  3455.         }
  3456.  
  3457.         // trim down log
  3458.         if!empty$log_message ) ) {
  3459.             $pParamHash['action_log_store']['log_message'substr$log_message0250 );
  3460.         }
  3461.         // error message - default is to put in any stuff in mErrors
  3462.         $error_message '';
  3463.         if!empty$pParamHash['action_log']['error_message') ) {
  3464.             $error_message $pParamHash['action_log']['error_message'];
  3465.         }
  3466.  
  3467.         // trim down error message
  3468.         if!empty$error_message ) ) {
  3469.             $pParamHash['action_log_store']['error_message'substr$error_message0250 );
  3470.         }
  3471.  
  3472.         ifempty$pParamHash['action_log_store']['error_message'&& empty$pParamHash['action_log_store']['log_message')) {
  3473.             $ret FALSE;
  3474.         }
  3475.         // if we get as far as here, we can
  3476.         return $ret;
  3477.     }
  3478.  
  3479.     /**
  3480.      * Get a list of action log entries
  3481.      *
  3482.      * @param array $pListHash List options
  3483.      * @access public
  3484.      * @return List of entries on success, FALSE on failure
  3485.      */
  3486.     function getActionLogs&$pListHash {
  3487.         LibertyContent::prepGetList$pListHash );
  3488.  
  3489.         $ret $bindVars array();
  3490.         $selectSql $joinSql $orderSql $whereSql '';
  3491.  
  3492.         if!empty$pListHash['find') ) {
  3493.             $whereSql .= empty$whereSql ' WHERE ' ' AND ';
  3494.             $whereSql .= " UPPER( lal.`log_message` ) LIKE ? ";
  3495.             $bindVars['%'.strtoupper$pListHash['find').'%';
  3496.         }
  3497.  
  3498.         if!empty$pListHash['find_title') ) {
  3499.             $whereSql .= empty$whereSql ' WHERE ' ' AND ';
  3500.             $whereSql .= " UPPER( lal.`title` ) LIKE ? ";
  3501.             $bindVars['%'.strtoupper$pListHash['find_log').'%';
  3502.         }
  3503.  
  3504.         if!empty$pListHash['user_id') ) {
  3505.             $whereSql .= empty$whereSql ' WHERE ' ' AND ';
  3506.             $whereSql .= " lal.`user_id` = ? ";
  3507.             $bindVars[$pListHash['user_id'];
  3508.         }
  3509.  
  3510.         if!empty$pListHash['content_id') ) {
  3511.             $whereSql .= empty$whereSql ' WHERE ' ' AND ';
  3512.             $whereSql .= " lal.`content_id` = ? ";
  3513.             $bindVars[$pListHash['content_id'];
  3514.         }
  3515.  
  3516.         if!empty$pListHash['sort_mode')) {
  3517.             ifpreg_match"/^last_modified|^title/"$pListHash['sort_mode')) {
  3518.                 $pListHash['sort_mode'"lal.".$pListHash['sort_mode'];
  3519.             }
  3520.             $orderSql " ORDER BY ".$this->convertSortMode$pListHash['sort_mode')." ";
  3521.         }
  3522.  
  3523.         $query "
  3524.             SELECT lal.*,
  3525.                 lc.`content_type_guid`, lc.`created`, lct.`content_name`, lct.`content_name_plural`,
  3526.                 uue.`login` AS modifier_user, uue.`real_name` AS modifier_real_name
  3527.             FROM `".BIT_DB_PREFIX."liberty_action_log` lal
  3528.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content` lc ON ( lc.`content_id` = lal.`content_id` )
  3529.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."liberty_content_types` lct ON ( lct.`content_type_guid` = lc.`content_type_guid` )
  3530.                 LEFT OUTER JOIN `".BIT_DB_PREFIX."users_users` uue ON ( uue.`user_id` = lal.`user_id` )
  3531.             $whereSql $orderSql";
  3532.  
  3533.         $result $this->mDb->query$query$bindVars$pListHash['max_records']$pListHash['offset');
  3534.  
  3535.         while$aux $result->fetchRow() ) {
  3536.             $aux['user']         $aux['modifier_user'];
  3537.             $aux['editor']       isset$aux['modifier_real_name'$aux['modifier_real_name'$aux['modifier_user');
  3538.             $aux['display_name'BitUser::getDisplayNameFromHashNULL$aux );
  3539.             $ret[]               $aux;
  3540.         }
  3541.  
  3542.         $query "SELECT COUNT( lal.`user_id` ) FROM `".BIT_DB_PREFIX."liberty_action_log` lal $whereSql";
  3543.         $pListHash['cant'$this->mDb->getOne$query$bindVars );
  3544.         LibertyContent::postGetList$pListHash );
  3545.  
  3546.         return $ret;
  3547.     }
  3548.  
  3549.     /**
  3550.      * expungeActionLog
  3551.      *
  3552.      * @param array $pTimeSpan Anything older than this timespan will be removed
  3553.      * @access public
  3554.      * @return TRUE on success, FALSE on failure - mErrors will contain reason for failure
  3555.      */
  3556.     function expungeActionLog$pTimeSpan NULL {
  3557.         global $gBitSystem;
  3558.         $where '';
  3559.         $bindVars array();
  3560.         if@BitBase::verifyId$pTimeSpan ) ) {
  3561.             $where "WHERE `last_modified` < ?";
  3562.             $bindVars[$gBitSystem->mServerTimestamp->getUTCTime($pTimeSpan;
  3563.         }
  3564.         $this->mDb->query"DELETE FROM `".BIT_DB_PREFIX."liberty_action_log` $where"$bindVars );
  3565.         return TRUE;
  3566.     }
  3567.  
  3568.     /**
  3569.      * getAvailableContentStatus
  3570.      *
  3571.      * @access public
  3572.      * @return an array of content_status_id, content_status_names the current
  3573.      *  user can use on this content. Subclases may easily override with return
  3574.      *  LibertyContent::getAvailableContentStatus(-100, 0) for example to restrict to
  3575.      *  only hidden content types.
  3576.      */
  3577.     function getAvailableContentStatuses$pUserMinimum=-100$pUserMaximum=100 {
  3578.         global $gBitUser;
  3579.         if$gBitUser->hasPermission'p_liberty_edit_all_status' )) {
  3580.             return$this->mDb->getAssoc"SELECT `content_status_id`,`content_status_name` FROM `".BIT_DB_PREFIX."liberty_content_status` ORDER BY `content_status_id`" ) );
  3581.         else {
  3582.             return$this->mDb->getAssoc"SELECT `content_status_id`, `content_status_name` FROM `".BIT_DB_PREFIX."liberty_content_status` WHERE `content_status_id` > ? AND `content_status_id` < ? ORDER BY `content_status_id`"array$pUserMinimum$pUserMaximum )));
  3583.         }
  3584.     }
  3585.  
  3586.     /**
  3587.      * getContentStatus will return the content status of the currently loaded content.
  3588.      *
  3589.      * @param array $pContentId Content ID of the content in question
  3590.      * @access public
  3591.      * @return Status ID
  3592.      */
  3593.     function getContentStatus$pDefault 50$pContentId NULL {
  3594.         $ret NULL;
  3595.         if @!BitBase::verifyId$pContentId && $this->isValid() ){
  3596.             if !$ret $this->getField'content_status_id' ) ) ){
  3597.                 $pContentId $this->mContentId;
  3598.             }
  3599.         }
  3600.         if!is_null$pContentId )) {
  3601.             $ret $this->mDb->getOne"SELECT `content_status_id` FROM `".BIT_DB_PREFIX."liberty_content` WHERE `content_id` = ?"array$pContentId ));
  3602.         }
  3603.         $ret is_null$ret $pDefault $ret;
  3604.         return $ret;
  3605.     }
  3606.  
  3607.     /**
  3608.      * isDeleted status test
  3609.      *
  3610.      * @return true when the content status = -999
  3611.      */
  3612.     function isDeleted({
  3613.         global $gBitSystem;
  3614.         return$this->getField'content_status_id' <= $gBitSystem->getConfig'liberty_status_deleted'-999 ) );
  3615.     }
  3616.  
  3617.     /**
  3618.      * isPrivate status test
  3619.      *
  3620.      * @return true when the content status = -999
  3621.      */
  3622.     function isPrivate({
  3623.         global $gBitSystem;
  3624.         return$this->getField'content_status_id' <= $gBitSystem->getConfig'liberty_status_threshold_private'-40 ) );
  3625.     }
  3626.  
  3627.     /**
  3628.      * isProtected status test
  3629.      *
  3630.      * @return true when the content status = -20 or content has protection flag set
  3631.      */
  3632.     function isProtected({
  3633.         global $gBitSystem;
  3634.         return$this->getField'content_status_id' <= $gBitSystem->getConfig'liberty_status_threshold_protected'-20 ) );
  3635.     }
  3636.  
  3637.     /**
  3638.      * isHidden status test
  3639.      *
  3640.      * @return true when the content status = -10
  3641.      */
  3642.     function isHidden({
  3643.         global $gBitSystem;
  3644.         return$this->getField'content_status_id' <= $gBitSystem->getConfig'liberty_status_threshold_hidden'-10 ) );
  3645.     }
  3646.  
  3647.     /**
  3648.      * getContentStatusName
  3649.      *
  3650.      * @param array $pStatusId Status ID if not available in $this->mInfo['content_status_id']
  3651.      * @access public
  3652.      * @return The name of the content status based on the status id of the content
  3653.      */
  3654.     function getContentStatusName$pStatusId NULL {
  3655.         $ret 'Not a valid content status';
  3656.  
  3657.         // check to see where we can get the status information from
  3658.         if!empty$this && !empty$this->mInfo['content_status_name')) {
  3659.             return$this->mInfo['content_status_name');
  3660.         elseifis_null$pStatusId && !empty$this && !empty$this->mInfo['content_status_id')) {
  3661.             $pStatusId $this->mInfo['content_status_id'];
  3662.         }
  3663.  
  3664.         // fetch from db if needed
  3665.         if!is_null$pStatusId )) {
  3666.             if$ret $this->mDb->getOne"SELECT `content_status_name` FROM `".BIT_DB_PREFIX."liberty_content_status` WHERE `content_status_id` = ?"array$pStatusId ))) {
  3667.             }
  3668.         }
  3669.  
  3670.         return $ret;
  3671.     }
  3672.  
  3673.     /**
  3674.      * Store Data into liberty_content_data
  3675.      *
  3676.      * @return bool true ( will not currently report a failure )
  3677.      */
  3678.     function storeData$pData$pType {
  3679.         if$this->mContentId {
  3680.             $pData trim$pData );
  3681.             ifempty$pData ) ) {
  3682.                 $this->mDb->query"DELETE FROM `".BIT_DB_PREFIX."liberty_content_data` WHERE `content_id`=? AND `data_type`=?"array$this->mContentId$pType ) );
  3683.             else {
  3684.                 if$this->mDb->getOne"SELECT `content_id` FROM `".BIT_DB_PREFIX."liberty_content_data` WHERE `content_id`=? AND `data_type`=?"array$this->mContentId$pType ) ) ) {
  3685.                     $query "UPDATE `".BIT_DB_PREFIX."liberty_content_data` SET `data`= ? WHERE `content_id` = ? AND `data_type`=?";
  3686.                 else {
  3687.                     $query "INSERT INTO `".BIT_DB_PREFIX."liberty_content_data` ( `data`, `content_id`, `data_type` ) VALUES (?,?,?)";
  3688.                 }
  3689.                 $result $this->mDb->query$queryarray$pData$this->mContentId$pType ) );
  3690.             }
  3691.         }
  3692.         return TRUE;
  3693.     }
  3694.  
  3695.     /**
  3696.      * storeStatus store liberty contenet status
  3697.      *
  3698.      * @param array $pContentStatusId 
  3699.      * @access public
  3700.      * @return void 
  3701.      */
  3702.     function storeStatus$pContentStatusId {
  3703.         if$this->isValid(&& $pContentStatusId {
  3704.             return $this->mDb->query"UPDATE `".BIT_DB_PREFIX."liberty_content` SET `content_status_id`=? WHERE `content_id`=?"array$pContentStatusId$this->mContentId ) );
  3705.         }
  3706.     }
  3707.  
  3708.     /**
  3709.      * isCommentable will check allow_comments in mInfo or if it's set as a preference.
  3710.      *
  3711.      * @access public
  3712.      * @return TRUE on success, FALSE on failure
  3713.      */
  3714.     function isCommentable({
  3715.         if$this->getPreference'allow_comments' == 'y' {
  3716.             return TRUE;
  3717.         else {
  3718.             $setting $this->getField'allow_comments' );
  3719.             return$setting == TRUE || $setting == 'y' );
  3720.         }
  3721.     }
  3722.  
  3723.     /**
  3724.      * getListingPreview -- Returns a string with a preview of the content.
  3725.      * @access public
  3726.      * @return the preview string
  3727.      ***/
  3728.     function getListingPreview$pMixed {
  3729.         global $gBitSystem$gContent$gBitSmarty;
  3730.         // TODO!
  3731.         return $ret;
  3732.     }
  3733.  
  3734.     /**
  3735.      * getPreview -- Returns a string with a preview of the content. Default implementation runs getRenderFile() with $liberty_preview set in the context and gBitSystem set to only render the content.
  3736.      *
  3737.      * @access public
  3738.      * @return the preview string
  3739.      ***/
  3740.     function getPreview({
  3741.         global $gBitSystem$gContent$gBitSmarty$gBitThemes;
  3742.         // Tell gBitSystem not to do modules and such
  3743.         $gBitThemes->setFormatHeader"center_only" );
  3744.         // Tell the content we are previewing (in case they care)
  3745.         $gBitSmarty->assign('liberty_preview'true);
  3746.         // Save current gContent
  3747.         $oldGContent $gContent;
  3748.         // Make us the content
  3749.         $gContent $this;
  3750.  
  3751.         $ret get_include_contents($this->getRenderFile());
  3752.  
  3753.         // Return gBitSystem to full render mode
  3754.         $gBitThemes->setFormatHeader"html" );
  3755.         // Clear the preview flag
  3756.         $gBitSmarty->assign('liberty_preview'false);
  3757.         // Restore gContent
  3758.         $gContent $oldGContent;
  3759.  
  3760.         return $ret;
  3761.     }
  3762.  
  3763. }

Documentation generated on Wed, 29 Jul 2015 13:56:53 +0000 by phpDocumentor 1.5.0-lsces