Seditio Source
Root |
./othercms/b2evolution_7.2.3/inc/collections/model/_category.funcs.php
<?php
/**
 * This file implements Category handling functions.
 *
 * This file is part of the evoCore framework - {@link http://evocore.net/}
 * See also {@link https://github.com/b2evolution/b2evolution}.
 *
 * @license GNU GPL v2 - {@link http://b2evolution.net/about/gnu-gpl-license}
 *
 * @copyright (c)2003-2020 by Francois Planque - {@link http://fplanque.com/}
 * Parts of this file are copyright (c)2004-2006 by Daniel HAHLER - {@link http://thequod.de/contact}.
 * Parts of this file are copyright (c)2004 by The University of North Carolina at Charlotte as
 * contributed by Jason Edgecombe {@link http://tst.uncc.edu/team/members/jason_bio.php}.
 *
 * @package evocore
 *
 * @todo implement CategoryCache based on LinkCache
 */
if( !defined('EVO_MAIN_INIT') ) die( 'Please, do not access this page directly.' );


/**
 * Create a new category
 *
 * This funtion has to handle all needed DB dependencies!
 *
 * @param string Category name
 * @param string Category ID ('NULL' as string(!) for root)
 * @param integer|NULL Blog ID (will be taken from parent cat, if empty)
 * @param string Category description
 * @param boolean Set to true if the new object needs to be added into the ChapterCache after it was created
 * @param integer Category order
 * @param boolean Is meta category?
 * @param string Name of default Item Type
 * @return integer ID of new created Category
 */
function cat_create( $cat_name, $cat_parent_ID, $cat_blog_ID = NULL, $cat_description = NULL, $add_to_cache = false, $cat_order = NULL, $subcat_ordering = NULL, $meta = false, $default_item_type_name = NULL )
{
    global
$DB;

   
load_class('chapters/model/_chapter.class.php', 'Chapter');

    if( !
$cat_blog_ID )
    {
        if( empty(
$cat_parent_ID ) )
        {
           
debug_die ( 'cat_create(-) missing parameters (cat_parent_ID)!' );
        }

       
$ChapterCache = & get_ChapterCache();
       
$Chapter = $ChapterCache->get_by_ID($cat_parent_ID);
       
$cat_blog_ID = $Chapter->blog_ID;
    }

    if(
$cat_parent_ID === 'NULL' )
    {
// fix old use case
       
$cat_parent_ID = NULL;
    }

   
$new_Chapter = new Chapter( NULL, $cat_blog_ID );
   
$new_Chapter->set( 'name', $cat_name );
   
$new_Chapter->set( 'parent_ID', $cat_parent_ID );
    if( !empty(
$cat_description ) )
    {
// Set decription
       
$new_Chapter->set( 'description', $cat_description );
    }
   
$new_Chapter->set( 'order', $cat_order );
   
$new_Chapter->set( 'subcat_ordering', $subcat_ordering );
    if(
$meta )
    {
// Set this category as meta
       
$new_Chapter->set( 'meta', 1 );
    }

    if(
$default_item_type_name !== NULL &&
        (
$ItemTypeCache = & get_ItemTypeCache() ) &&
        (
$ItemType = & $ItemTypeCache->get_by_name( $default_item_type_name, false, false ) ) )
    {    
// Item type exists in DB by requested name, Use it:
       
$new_Chapter->set( 'ityp_ID', $ItemType->ID );
    }

    if( !
$new_Chapter->dbinsert() )
    {
        return
0;
    }

    if(
$add_to_cache )
    {
// add new Category into the Cache
       
$ChapterCache = & get_ChapterCache();
       
$ChapterCache->add( $new_Chapter );
    }

    return
$new_Chapter->ID;
}


/**
 * Get category name+blog_id for specified cat ID
 *
 * fplanque: reused "R. U. Serious" optimization here
 * fplanque: added blog ID stuff
 *
 * @deprecated since 3.1.0-alpha. Use ChapterCache instead.
 * @param integer category ID
 * @param boolean die() if category does not exist? (default: true)
 *
 */
function get_the_category_by_ID( $cat_ID, $die = true )
{
   
// TODO: asimo> Old content was changed, but still the whole function should be removed.
   
$ChapterCache = & get_ChapterCache();
    return
$ChapterCache->get_by_ID( $cat_ID, $die );
}


/**
 * Get blog ID for a given cat.
 * This halts on error.
 * @return integer
 */
function get_catblog( $cat_ID )
{
   
$ChapterCache = & get_ChapterCache();
   
$Chapter = $ChapterCache->get_by_ID($cat_ID);

    return
$Chapter->blog_ID;
}


/**
 * Get category permanent url by category ID
 *
 * @param integer category ID
 */
function get_caturl( $cat_ID )
{
   
$ChapterCache = & get_ChapterCache();
   
$Chapter = $ChapterCache->get_by_ID($cat_ID);

    return
$Chapter->get_permanent_url();
}


/**
 * Get # of posts for each category in a blog
 *
 * @param integer Category ID
 * @param integer Blog ID
 */
function get_postcount_in_category( $cat_ID, $blog_ID = NULL )
{
    if(
is_null( $blog_ID ) )
    {
        global
$blog;
       
$blog_ID = $blog;
    }

    global
$DB, $number_of_posts_in_cat;

    if( !isset(
$number_of_posts_in_cat[ (string) $blog_ID ] ) )
    {
       
$SQL = new SQL( 'Get # of posts for each category in a blog' );
       
$SQL->SELECT( 'cat_ID, count( postcat_post_ID ) c' );
       
$SQL->FROM( 'T_categories' );
       
$SQL->FROM_add( 'INNER JOIN T_postcats ON postcat_cat_ID = cat_id' );
       
$SQL->FROM_add( 'INNER JOIN T_items__item ON postcat_post_ID = post_id' );
       
$SQL->FROM_add( 'LEFT JOIN T_items__type ON post_ityp_ID = ityp_ID' );
       
$SQL->WHERE( 'cat_blog_ID = '.$DB->quote( $blog_ID ) );
       
$SQL->WHERE_and( 'post_ityp_ID IS NULL OR ityp_usage = "post"' );
       
$SQL->WHERE_and( statuses_where_clause( get_inskin_statuses( $blog_ID, 'post' ), 'post_', $blog_ID, 'blog_post!', true ) );
       
$SQL->GROUP_BY( 'cat_ID' );
       
$number_of_posts_in_cat[ (string) $blog_ID ] = $DB->get_assoc( $SQL );
    }

    return isset(
$number_of_posts_in_cat[(string) $blog_ID][$cat_ID] ) ? (int) $number_of_posts_in_cat[(string) $blog_ID][$cat_ID] : 0;
}


/**
 * Get # of comments for each category in a blog
 *
 * @param integer Category ID
 * @param integer Blog ID
 */
function get_commentcount_in_category( $cat_ID, $blog_ID = NULL )
{
    if(
is_null( $blog_ID ) )
    {
        global
$blog;
       
$blog_ID = $blog;
    }

    global
$DB, $number_of_comments_in_cat;

    if( !isset(
$number_of_comments_in_cat[(string) $blog_ID] ) )
    {
       
$SQL = new SQL();
       
$SQL->SELECT( 'cat_ID, COUNT( comment_ID ) c' );
       
$SQL->FROM( 'T_comments' );
       
$SQL->FROM_add( 'LEFT JOIN T_postcats ON comment_item_ID = postcat_post_ID' );
       
$SQL->FROM_add( 'LEFT JOIN T_categories ON postcat_cat_ID = cat_id' );
       
$SQL->FROM_add( 'LEFT JOIN T_items__item ON comment_item_ID = post_id' );
       
$SQL->FROM_add( 'LEFT JOIN T_items__type ON post_ityp_ID = ityp_ID' );
       
$SQL->WHERE( 'cat_blog_ID = '.$DB->quote( $blog_ID ) );
       
$SQL->WHERE_and( 'comment_type IN ( "comment", "trackback", "pingback", "webmention" )' );
       
$SQL->WHERE_and( statuses_where_clause( get_inskin_statuses( $blog_ID, 'comment' ), 'comment_', $blog_ID, 'blog_comment!', true ) );
       
// add where condition to show only those posts commetns which are visible for the current User
       
$SQL->WHERE_and( statuses_where_clause( get_inskin_statuses( $blog_ID, 'post' ), 'post_', $blog_ID, 'blog_post!', true ) );
       
// Get content post types, Exclide pages, intros, sidebar links and ads
       
$SQL->WHERE_and( 'post_ityp_ID IS NULL OR ityp_usage = "post"' );
       
$SQL->GROUP_BY( 'cat_ID' );

       
$number_of_comments_in_cat[(string) $blog_ID] = $DB->get_assoc( $SQL->get() );
    }

    return isset(
$number_of_comments_in_cat[(string) $blog_ID][$cat_ID] ) ? (int) $number_of_comments_in_cat[(string) $blog_ID][$cat_ID] : 0;
}


/**
 * Load category associations for requested items
 *
 * @param array Item IDs
 * @return array Item categories IDs
 */
function postcats_get_by_IDs( $item_IDs )
{
    global
$DB, $cache_postcats;

    if( !
is_array( $cache_postcats ) )
    {    
// Initialize cache array first time:
       
$cache_postcats = array();
    }

   
$not_cached_item_IDs = array_diff( $item_IDs, array_keys( $cache_postcats ) );

    if( empty(
$not_cached_item_IDs ) )
    {    
// The category associations are loaded for all requested items:
       
return;
    }

   
// Load the category associations from DB and cache into global cache array:
   
$SQL = new SQL( 'Load the category associations for items' );
   
$SQL->SELECT( 'postcat_post_ID AS post_ID, postcat_cat_ID AS cat_ID' );
   
$SQL->FROM( 'T_postcats' );
   
$SQL->WHERE( 'postcat_post_ID IN ( '.$DB->quote( $not_cached_item_IDs ).' )' );
   
$SQL->ORDER_BY( 'postcat_post_ID, postcat_cat_ID' );

   
$items_postcats = $DB->get_results( $SQL );

    foreach(
$items_postcats as $item_postcats )
    {
        if( ! isset(
$cache_postcats[ $item_postcats->post_ID ] ) )
        {
           
$cache_postcats[ $item_postcats->post_ID ] = array();
        }

       
$cache_postcats[ $item_postcats->post_ID ][] = $item_postcats->cat_ID;
    }

   
// Set all unexiting associations for requested items in order to don't repeat SQL queries later:
   
foreach( $not_cached_item_IDs as $not_cached_item_ID )
    {
        if( ! isset(
$cache_postcats[ $not_cached_item_ID ] ) )
        {
           
$cache_postcats[ $not_cached_item_ID ] = array();
        }
    }
}


/**
 * Get category associations with given item
 *
 * sam2kb> TODO: Cache item cat IDs into Item::categories property instead of global $cache_postcats
 *
 * @param integer Item ID
 * @return array Item categories IDs
 */
function postcats_get_byID( $post_ID )
{
    global
$DB, $cache_postcats;

    if( empty(
$post_ID ) )
    {
        return array();
    }

    if( !
is_array( $cache_postcats ) )
    {    
// Initialize cache array first time:
       
$cache_postcats = array();
    }

    if( ! isset(
$cache_postcats[ $post_ID ] ) )
    {    
// Get data from DB if it is not still in cache:
       
$SQL = new SQL( 'Get category associations with given item #'.$post_ID );
       
$SQL->SELECT( 'postcat_cat_ID' );
       
$SQL->FROM( 'T_postcats' );
       
$SQL->WHERE( 'postcat_post_ID = '.$DB->quote( $post_ID ) );
       
$SQL->ORDER_BY( 'postcat_cat_ID' );

       
$cache_postcats[ $post_ID ] = $DB->get_col( $SQL );
    }

    return
$cache_postcats[ $post_ID ];
}


/**
 * Does a given blog have categories?
 *
 * @param integer Blog ID
 * @return boolean
 */
function blog_has_cats( $blog_ID )
{
   
$ChapterCache = & get_ChapterCache();
    return
$ChapterCache->has_chapters_in_subset( $blog_ID );
}


/**
 * Compiles the cat array from $cat (recursive + optional modifiers) and $catsel[] (non recursive)
 *
 * @param string
 * @param array
 * @param array by ref, will be modified
 * @param string by ref, will be modified
 * @param integer blog number to restrict to
 */
function compile_cat_array( $cat, $catsel, & $cat_array, & $cat_modifier, $restrict_to_blog = 0  )
{
   
// echo '$cat='.$cat;
    // pre_dump( $catsel );
    // echo '$restrict_to_blog'.$restrict_to_blog;

   
$cat_array = array();
   
$cat_modifier = '';

   
// Check for cat string (which will be handled recursively)
   
if( $cat != 'all' && !empty($cat) )
    {
// specified a category string:
       
$cat_modifier = substr($cat, 0, 1 );
       
// echo 'cats['.$first_char.']';
       
if( ( $cat_modifier == '*' ) ||
            (
$cat_modifier == '-' ) ||
            (
$cat_modifier == '|' ) )
        {
           
$cat = substr( $cat, 1 );
        }
        else
        {
           
$cat_modifier = '';
        }

        if(
strlen( $cat ) )
        {    
// There are some values to explode...
           
$req_cat_array = explode(',', $cat);

           
// Getting required sub-categories:
            // and add everything to cat array
            // ----------------- START RECURSIVE CAT LIST ----------------
           
$ChapterCache = & get_ChapterCache();
            if(
$restrict_to_blog > 0 )
            {
// Load all Chapters from the given blog
               
$ChapterCache->reveal_children( $restrict_to_blog, true );
            }
            else
            {
// Load all chapters
               
$ChapterCache->reveal_children( NULL, true );
            }

            foreach(
$req_cat_array as $cat_ID )
            {
// run recursively through the cats
               
$current_Chapter = $ChapterCache->get_by_ID( $cat_ID, false );
                if( empty(
$current_Chapter ) )
                {
// The requested Chapter doesn't exists in the given context
                   
continue;
                }
                if( !
in_array( $cat_ID, $cat_array ) )
                {
// Not already in list
                   
$cat_array[] = $cat_ID;
                   
$ChapterCache->iterate_through_category_children( $current_Chapter, array( 'line' => 'cat_req' ), true, array( 'sorted' => true ) );
                }
            }
           
// ----------------- END RECURSIVE CAT LIST ----------------
       
}
    }

   
// Add explicit selections:
   
if( ! empty( $catsel ))
    {
       
// echo "Explicit selections!<br />";
       
$cat_array = array_merge( $cat_array, $catsel );
       
$cat_array = array_unique( $cat_array );
    }

   
// echo '$cat_modifier='.$cat_modifier;
    // pre_dump( $cat_array );

}


/**
 * Callback used in compile_cat_array()
 */
function cat_req( $Chapter, $level )
{
    global
$cat_array;

    if( !
in_array( $Chapter->ID, $cat_array ) )
    {
// Not already visited
       
$cat_array[] = $Chapter->ID;
    }
}


/**
 * Get global cross posting settings -- (cross posting = 1 post in multiple blogs)
 *
 * @return int
 *         0 - cross posting disabled
 *         1 - cross posting enabled for extra categories
 *         2 - cross posting enabled for main categories
 *         3 - cross posting enabled for main and extracats
 */
function get_allow_cross_posting()
{
    global
$Settings;
    return
$Settings->get( 'cross_posting' ) + ( 2 *  $Settings->get( 'cross_posting_blogs' ) );
}
?>