Go Back   vb.org Archive > vBulletin Article Depository > Read An Article > vBulletin 3 Articles

Reply
 
Thread Tools
Function to retrieve the forums a user can access
Admin's Avatar
Admin
Join Date: Oct 2023
Posts: 1

Admin

Server
Show Printable Version Email this Page Subscription
Admin Admin is offline 08-04-2002, 10:00 PM

This is something I once wrote for someone (think it was merk?), and kept it in a file, and finally got around to clean it up and wrap it in a function.

Very useful for some hacks, hope this helps at least some of you.
Here is the full function, along with some basic instructions:

PHP Code:
/***********************************************************************
 * Parameters:
 *    1.    The name of the permission you want to check for.
 *        Alternatively, it can take an array of permissions.
 *        Defaults to 'canview'.
 *    2.    The user ID of the user you are checking permissions for.
 *        Defaults to -1 (i.e current viewer).
 *    3.    The separator for the list of forum ID's.
 * Return:
 *    1.    If the first parameter is a string, the function will
 *        return the list of forum ID's.
 *    2.    If the first parameter is an array, the function will
 *        return an associative array of permission => forum ID's.
 * Example usage:
 *    1.    get_allowed_forums();
 *            Will return the list of forums the current user can view:
 *            1,5,6,8
 *    2.    get_allowed_forums(array('canview', 'canpostnew'), 2);
 *            Will return an array that contains two keys, canview and
 *            canpostnew, each referring to the list of forums user
 *            number 2 can access:
 *            Array
 *            (
 *                [canview] => 3,5,7,8
 *                [canpostnew] => 3,7
 *            )
 **********************************************************************/
function get_allowed_forums ($checkfor 'canview'$userid = -1$separator ',') {
    global 
$permissions$DB_site$bbuserinfo$enableaccess$hideprivateforums;

    if (
$userid == -1) {
        
$userinfo $bbuserinfo;
    } else {
        
$userinfo getuserinfo($userid);
    }

    if (
is_array($checkfor)) {
        
$select implode(', '$checkfor);
    } else {
        
$select $checkfor;
    }
    
$forumpermissions $DB_site->query("
        SELECT forumid, 
$select
        FROM forumpermission
        WHERE usergroupid = 
$userinfo[usergroupid]
    "
);
    while (
$forumpermission $DB_site->fetch_array($forumpermissions)) {
        
$forumpermscache[$forumpermission['forumid']] = $forumpermission;
    }

    if (
$userinfo['userid'] != and $enableaccess) {
        
$accesspermissions $DB_site->query("
            SELECT forumid, accessmask
            FROM access
            WHERE userid = 
$userinfo[userid]
        "
);
        while (
$accesspermission $DB_site->fetch_array($accesspermissions)) {
            
$accesscache[$accesspermission['forumid']] = $accesspermission;
        }

        if (
is_array($checkfor)) {
            foreach (
$checkfor as $permname) {
                
$usergroupdefault[$permname] = $permissions[$permname];
                
$nopermissions[$permname] = 0;
            }
        } else {
            
$usergroupdefault = array(
                
$checkfor => $permissions[$checkfor]
            );
            
$nopermissions = array(
                
$checkfor => 0
            
);
        }
    }

    
// (This is a really really fast query since it only
    //  uses the index and not the actual table.)
    
$forums $DB_site->query('SELECT forumid FROM forum');
    while (
$forum $DB_site->fetch_array($forums)) {
        if (
$enableaccess and is_array($accesscache[$forum['forumid']])) {
            if (
$accesscache[$forum['forumid']]['accessmask'] == 1) {
                
$forumperms $usergroupdefault;
            } else {
                
$forumperms $nopermissions;
            }
        } elseif (
is_array($forumpermscache[$forum['forumid']])) {
            
$forumperms $forumpermscache[$forum['forumid']];
        } else {
            
$forumperms $permissions;
        }

        if (
is_array($checkfor)) {
            foreach (
$checkfor as $permname) {
                if ((!
$hideprivateforums and $permname == 'canview') or $forumperms[$permname]) {
                    if (
$allowedforums[$permname]) {
                        
$allowedforums[$permname] .= $separator;
                    }
                    
$allowedforums[$permname] .= $forum['forumid'];
                }
            }
        } else {
            if ((!
$hideprivateforums and $checkfor == 'canview') or $forumperms[$checkfor]) {
                if (
$allowedforums) {
                    
$allowedforums .= $separator;
                }
                
$allowedforums .= $forum['forumid'];
            }
        }
    }

    return 
$allowedforums;

Reply With Quote
  #12  
Old 08-31-2002, 08:41 AM
tHE DSS's Avatar
tHE DSS tHE DSS is offline
 
Join Date: Jun 2002
Location: UK
Posts: 113
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

As I posted before in this thread - the above function does not return results of forums a user cannot "view", if the forum is using default permissions from it's parent forum.

Our board uses only forum default permissions, inherited from it's parent forum - we rely on usergroup permissions, and this does us absolutely fine.

The other night, I really really needed to make sure I could restrict some queries from returning data that comes from forums any certain usergroup cannot view, so I made the following function - it's a little sloppy in places, but it's not that bad - the main thing is, it works :

PHP Code:
function getForumPermissions($usergroupID) {
    global 
$DB_site;
    
$forumCatPerm_result $DB_site->query("SELECT forumid FROM forumpermission WHERE canview=0 AND usergroupid=$usergroupID");
    if (!
$num_rows $DB_site->num_rows($forumCatPerm_result) <=0) {
        
$arrayIndex 0;
        while (
$row $DB_site->fetch_array($forumCatPerm_resultMYSQL_ASSOC)) {
            
$forumCatPerm_array[$arrayIndex++] = $row[forumid];
        }
    }

    if (isset(
$forumCatPerm_array)) {
        
$forumsCannotView_result $DB_site->query("SELECT forumid,parentlist FROM forum WHERE active=1");
        if (!
$num_rows $DB_site->num_rows($forumsCannotView_result) <=0) {
            
$arrayIndex 0;
            while (
$row $DB_site->fetch_array($forumsCannotView_resultMYSQL_ASSOC)) {
                
$forumParentList_temp explode(','$row[parentlist]);
                if (
$forumParentList_temp[1] != -1) {
                    if (
in_array($forumParentList_temp[1], $forumCatPerm_array)) {
                        
$forumsCannotView_array[$arrayIndex++] = $forumParentList_temp[0];
                    }
                }
            }
        }
        return 
$forumsCannotView_strList implode(","$forumCatPerm_array) . "," implode(","$forumsCannotView_array);
    } else {
        return 
$forumsCannotView_strList "";
    }

.... it's tested, and works.... it checks the 'forumpermission' table, and takes the forumid of parent forums (category forums) that have usergroup permissions set, and then queries the forum table, making a list of forums in that category, that the usergroup cannot view.

As an example, we can take the last 12 posts made, from forums that only the viewers usergroup has 'canview' access to :

PHP Code:
$forumsCannotView_strList getForumPermissions($bbuserinfo[usergroupid]);
$whereClause = ($forumsCannotView_strList != "") ? ("(forumid NOT IN ($forumsCannotView_strList)) AND") : ("");
$latest_discussions_num 12;
if (
$forumsCannotView_strList != "") {
    
$latestThreads_result $DB_site->query("SELECT threadid,title,lastpost,postusername,lastposter 
        FROM thread WHERE 
$whereClause visible=1 AND open=1 
            ORDER BY lastpost DESC 
                LIMIT 
$latest_discussions_num");
} else {
    
$latestThreads_result $DB_site->query("SELECT threadid,title,lastpost,postusername,lastposter 
        FROM thread WHERE visible=1 AND open=1 
            ORDER BY lastpost DESC 
                LIMIT 
$latest_discussions_num");
}
if (!
$num_rows $DB_site->num_rows($latestThreads_result) <=0) {
    while (
$row $DB_site->fetch_array($latestThreads_resultMYSQL_ASSOC)) {
        
$threadTitle "<a href=\"{forumsRoot}/showthread.php?s=$session[sessionhash]&threadid=$row[threadid]\" target=\"_blank\" class=\"smallLinks\">$row[title]</a>";
        
$threadStarter $row[postusername];
        
$lastPoster $row[lastposter];
        
$timezoneoffsetstamp $bbuserinfo[timezoneoffset] * 3600;
        
$timeDate date("$dateformat @ $timeformat"$row[lastpost] + $timezoneoffsetstamp);
        echo 
"$threadTitle | $threadStarter | $lastPoster | $timeDate";
    }

... basically, if the function returns an empty string, there are not restrictions, and the 2nd query is actioned, which returns all forums... obviously, if there are restrictions, then the restricted forums get filtered out of the query.

I find this very handy for some of our non-vB pages.... and I post it simply in-case sombody likes the concept.
Reply With Quote
  #13  
Old 08-31-2002, 08:53 AM
tHE DSS's Avatar
tHE DSS tHE DSS is offline
 
Join Date: Jun 2002
Location: UK
Posts: 113
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

... actually, I think the 2nd query in the example can be left out, cleaning up the example code a little.... basically, the 'else {}' bit in the example (containing the alternate query) can be left out.
Reply With Quote
  #14  
Old 08-31-2002, 09:20 AM
Boofo's Avatar
Boofo Boofo is offline
 
Join Date: Mar 2002
Location: Des Moines, IA (USA)
Posts: 15,776
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

How could I sue this to get the Top thread by replies and the Top Thread by views and only have the right thread show up according to what the user is able to view?

Quote:
Originally posted by tHE DSS
... actually, I think the 2nd query in the example can be left out, cleaning up the example code a little.... basically, the 'else {}' bit in the example (containing the alternate query) can be left out.
Reply With Quote
  #15  
Old 08-31-2002, 12:10 PM
tHE DSS's Avatar
tHE DSS tHE DSS is offline
 
Join Date: Jun 2002
Location: UK
Posts: 113
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

You could use this :

PHP Code:
// generate string list of non-viewable forums, relative to current visitor
$forumsCannotView_strList getForumPermissions($bbuserinfo[usergroupid]);

// generate WHERE clause for non-viewable forums, if any
$whereClause = ($forumsCannotView_strList != "") ? ("(forumid NOT IN ($forumsCannotView_strList)) AND") : ("");

// set return LIMIT
$return_limit 1;

// query THREAD table, for top REPLIED TO thread
if ($forumsCannotView_strList != "") {
    
$topReplyThread_result $DB_site->query("SELECT threadid,title,lastpost,postusername,lastposter 
        FROM thread WHERE 
$whereClause visible=1 AND open=1 
            ORDER BY replycount DESC 
                LIMIT 
$return_limit");
}

// query THREAD table, for top VIEWED thread
if ($forumsCannotView_strList != "") {
    
$topViewedThread_result $DB_site->query("SELECT threadid,title,lastpost,postusername,lastposter 
        FROM thread WHERE 
$whereClause visible=1 AND open=1 
            ORDER BY views DESC 
                LIMIT 
$return_limit");
}

// extract and format top REPLIED TO thread
if (!$num_rows $DB_site->num_rows($topReplyThread_result) <=0) {
    while (
$row $DB_site->fetch_array($topReplyThread_resultMYSQL_ASSOC)) {

        
// put thread title into a link
        
$threadTitle "<a href=\"http://YOUR_FORUMS_PATH/showthread.php?s=$session[sessionhash]&threadid=$row[threadid]\" target=\"_blank\">$row[title]</a>";

        
// get thread starter
        
$threadStarter $row[postusername];

        
// get last poster
        
$lastPoster $row[lastposter];

        
// get time of last post, relative to the current visitor's timezone offset, set in their forum options
        
$timezoneoffsetstamp $bbuserinfo[timezoneoffset] * 3600;
        
$timeDate date("$dateformat @ $timeformat"$row[lastpost] + $timezoneoffsetstamp);

        
// print it out to the browser
        
echo "Top REPLIED TO Thread : $threadTitle | $threadStarter | $lastPoster | $timeDate<br>";

    }
} else {
        echo 
"No data for top REPLIED TO Thread";
}

// extract and format top VIEWED thread
if (!$num_rows $DB_site->num_rows($topViewedThread_result) <=0) {
    while (
$row $DB_site->fetch_array($topViewedThread_resultMYSQL_ASSOC)) {

        
// put thread title into a link
        
$threadTitle "<a href=\"http://YOUR_FORUMS_PATH/showthread.php?s=$session[sessionhash]&threadid=$row[threadid]\" target=\"_blank\">$row[title]</a>";

        
// get thread starter
        
$threadStarter $row[postusername];

        
// get last poster
        
$lastPoster $row[lastposter];

        
// get time of last post, relative to the current visitor's timezone offset, set in their forum options
        
$timezoneoffsetstamp $bbuserinfo[timezoneoffset] * 3600;
        
$timeDate date("$dateformat @ $timeformat"$row[lastpost] + $timezoneoffsetstamp);

        
// print it out to the browser
        
echo "Top VIEWED Thread : $threadTitle | $threadStarter | $lastPoster | $timeDate<br>";

    }
} else {
        echo 
"No data for top VEIWED Thread";

... which will get the stuff you need, for threads that are inside the visitors viewable forums, and that are open... no locked threads will be returned.

As far as i've tested, this only works (and only intended) for forums that have parent forum permissions - it doesn't cater for access masks... I believe that forums using their parent forum permissions show up in BLUE, in the forum permissions panel in the Admin CP... like this :

Code:
Example Forums
    (COPPA) Users Awaiting Moderation
    Administrators
    .... etc ....
    .... etc ....
    Registered
    .... etc ....

    Example Sub Forum, Of Above Category
        (COPPA) Users Awaiting Moderation
        Administrators
        .... etc ....
        .... etc ....
        Registered
        .... etc ....
... i've done abit more testing since, and believe that forums using custom permissions may also be able to benefit from this function... they show up in red in the AdminCP.

Best to test it out yourself though, to be sure in your own mind.

You can simply echo out the returned string list, like this :

PHP Code:
// generate string list of non-viewable forums, relative to current visitor
$forumsCannotView_strList getForumPermissions($bbuserinfo[usergroupid]);
// echo out string list
echo $forumsCannotView_strList
... then check all the comma separated values, against your forum ids.

Play about with forum permissions, and log-in and out as different member groups, and see if the forums that get returned are the only ones viewable by that group.
Reply With Quote
  #16  
Old 08-31-2002, 12:40 PM
Boofo's Avatar
Boofo Boofo is offline
 
Join Date: Mar 2002
Location: Des Moines, IA (USA)
Posts: 15,776
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

I don't mean to sound stupid here, but you are way over my head on this one.

The two queries I need to check permissions for are:

Code:
//Most Popular Thread by Replies
$popularreply=$DB_site->query_first("SELECT * FROM thread ORDER by replycount DESC LIMIT 1");

//Most Popular Thread by Views
$popularview=$DB_site->query_first("SELECT * FROM thread ORDER by views DESC LIMIT 1");
What code do I need to add to for these? I inserted the whole function that Firefly posted in the admin/functions.php file already, so it is there.

I really appreciate your help on this. I am totally lost when it comes to the permissions checking.
Reply With Quote
  #17  
Old 08-31-2002, 12:54 PM
tHE DSS's Avatar
tHE DSS tHE DSS is offline
 
Join Date: Jun 2002
Location: UK
Posts: 113
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

After calling my function, you can use these two queries :

PHP Code:
// query THREAD table, for top REPLIED TO thread
    
$topReplyThread_result $DB_site->query("SELECT * 
        FROM thread WHERE 
$whereClause visible=1 AND open=1 
            ORDER BY replycount DESC 
                LIMIT 
$return_limit");

// query THREAD table, for top VIEWED thread
    
$topViewedThread_result $DB_site->query("SELECT *
        FROM thread WHERE 
$whereClause visible=1 AND open=1 
            ORDER BY views DESC 
                LIMIT 
$return_limit"); 
... those are included in the example I previously gave for your needs... but I chose to only query specific fields.... the two here, i've put the '*' when SELECTing, so that you get all fields returned.

... and i've also taken out the :

PHP Code:
if ($forumsCannotView_strList != "") {... statements ...} 
.... bit, because, as I said previously, it's abit sloppy in places... the WHERE clause that is generated with this :

PHP Code:
// generate WHERE clause for non-viewable forums, if any
$whereClause = ($forumsCannotView_strList != "") ? ("(forumid NOT IN ($forumsCannotView_strList)) AND") : (""); 
.. after calling my function, sorts it out.
Reply With Quote
  #18  
Old 08-31-2002, 01:06 PM
Boofo's Avatar
Boofo Boofo is offline
 
Join Date: Mar 2002
Location: Des Moines, IA (USA)
Posts: 15,776
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

Ok, I think I understand what you are doing here. Where do put the function? In functions.php? And how do I call it in the index.php for the 2 queries?
Reply With Quote
  #19  
Old 08-31-2002, 02:42 PM
tHE DSS's Avatar
tHE DSS tHE DSS is offline
 
Join Date: Jun 2002
Location: UK
Posts: 113
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

I'm going out in a few hours to get p***ed as a fart, but tomorrow, i'll start a new thread for this function, i'll clean up the code and give easy instruction.

But to answer your question here, yeah, you can place it in 'functions.php' if you wish, and you call it like this :

PHP Code:
// generate string list of non-viewable forums, relative to current visitor
$forumsCannotView_strList getForumPermissions($bbuserinfo[usergroupid]); 
You only need to call it the once inside a script, and then you have all the forums IDs the current viewer is allowed to view as a string list, in $forumsCannotView_strList, which you can use however you want.
Reply With Quote
  #20  
Old 08-31-2002, 02:48 PM
Boofo's Avatar
Boofo Boofo is offline
 
Join Date: Mar 2002
Location: Des Moines, IA (USA)
Posts: 15,776
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

Thanks for taking the time and patience with me on this. I really appreciate it. I'll be looking forward to the new thread and your instructions tomorrow then. Have one for me tonight (today, actually for me). I'm home watching the little one.

Quote:
Originally posted by tHE DSS
I'm going out in a few hours to get p***ed as a fart, but tomorrow, i'll start a new thread for this function, i'll clean up the code and give easy instruction.

But to answer your question here, yeah, you can place it in 'functions.php' if you wish, and you call it like this :

PHP Code:
// generate string list of non-viewable forums, relative to current visitor
$forumsCannotView_strList getForumPermissions($bbuserinfo[usergroupid]); 
You only need to call it the once inside a script, and then you have all the forums IDs the current viewer is allowed to view as a string list, in $forumsCannotView_strList, which you can use however you want.
Reply With Quote
  #21  
Old 10-15-2002, 10:09 AM
dwh's Avatar
dwh dwh is offline
 
Join Date: Feb 2002
Posts: 278
Благодарил(а): 0 раз(а)
Поблагодарили: 0 раз(а) в 0 сообщениях
Default

So how could I use this to build a drop down box with a list of forums that the current user has permission to see? Would need the forum name as well as forum id. Here's the part that would have to be built:

Code:
<option value="$forumid">$forumname</option>
Thanks!
Reply With Quote
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump


All times are GMT. The time now is 02:57 PM.


Powered by vBulletin® Version 3.8.12 by vBS
Copyright ©2000 - 2024, vBulletin Solutions Inc.
X vBulletin 3.8.12 by vBS Debug Information
  • Page Generation 0.09840 seconds
  • Memory Usage 2,427KB
  • Queries Executed 25 (?)
More Information
Template Usage:
  • (1)SHOWTHREAD
  • (1)ad_footer_end
  • (1)ad_footer_start
  • (1)ad_header_end
  • (1)ad_header_logo
  • (1)ad_navbar_below
  • (1)ad_showthread_beforeqr
  • (3)bbcode_code
  • (10)bbcode_php
  • (2)bbcode_quote
  • (1)footer
  • (1)forumjump
  • (1)forumrules
  • (1)gobutton
  • (1)header
  • (1)headinclude
  • (1)modsystem_article
  • (1)navbar
  • (4)navbar_link
  • (120)option
  • (1)pagenav
  • (1)pagenav_curpage
  • (2)pagenav_pagelink
  • (11)post_thanks_box
  • (11)post_thanks_button
  • (1)post_thanks_javascript
  • (1)post_thanks_navbar_search
  • (11)post_thanks_postbit_info
  • (10)postbit
  • (11)postbit_onlinestatus
  • (11)postbit_wrapper
  • (1)spacer_close
  • (1)spacer_open
  • (1)tagbit_wrapper 

Phrase Groups Available:
  • global
  • inlinemod
  • postbit
  • posting
  • reputationlevel
  • showthread
Included Files:
  • ./showthread.php
  • ./global.php
  • ./includes/init.php
  • ./includes/class_core.php
  • ./includes/config.php
  • ./includes/functions.php
  • ./includes/class_hook.php
  • ./includes/modsystem_functions.php
  • ./includes/functions_bigthree.php
  • ./includes/class_postbit.php
  • ./includes/class_bbcode.php
  • ./includes/functions_reputation.php
  • ./includes/functions_post_thanks.php 

Hooks Called:
  • init_startup
  • init_startup_session_setup_start
  • init_startup_session_setup_complete
  • cache_permissions
  • fetch_threadinfo_query
  • fetch_threadinfo
  • fetch_foruminfo
  • style_fetch
  • cache_templates
  • global_start
  • parse_templates
  • global_setup_complete
  • showthread_start
  • showthread_getinfo
  • forumjump
  • showthread_post_start
  • showthread_query_postids
  • showthread_query
  • bbcode_fetch_tags
  • bbcode_create
  • showthread_postbit_create
  • postbit_factory
  • postbit_display_start
  • post_thanks_function_post_thanks_off_start
  • post_thanks_function_post_thanks_off_end
  • post_thanks_function_fetch_thanks_start
  • post_thanks_function_fetch_thanks_end
  • post_thanks_function_thanked_already_start
  • post_thanks_function_thanked_already_end
  • fetch_musername
  • postbit_imicons
  • bbcode_parse_start
  • bbcode_parse_complete_precache
  • bbcode_parse_complete
  • postbit_display_complete
  • post_thanks_function_can_thank_this_post_start
  • pagenav_page
  • pagenav_complete
  • tag_fetchbit_complete
  • forumrules
  • navbits
  • navbits_complete
  • showthread_complete