FIX: Prevent anonymous access from creating user selection collections until an action is performed. Also added cleanup cron task for anonymous collections [t26325] [t26361] [t26422] [t26355] [t26322]

git-svn-id: http://svn.resourcespace.com/svn/rs/trunk@16601 c08608d7-6e46-0410-86ca-f2a6f1370df5
This commit is contained in:
nbraddy 2020-12-07 13:04:21 +00:00
parent bd7c3f9018
commit 9df1b034ae
6 changed files with 131 additions and 84 deletions

View File

@ -0,0 +1,18 @@
<?php
// Clean up old anonymous collections
$last_delete_anonymous_cols = get_sysvar('last_delete_anonymous_collections', '1970-01-01');
# No need to run if already run in last 24 hours.
if (time()-strtotime($last_delete_anonymous_cols) < 24*60*60)
{
if('cli' == PHP_SAPI)
{
echo " - Skipping delete_anonymous_collections job - last run: " . $last_delete_anonymous_cols . $LINE_END;
}
return false;
}
cleanup_anonymous_collections(0);
# Update last run date/time.
set_sysvar("last_delete_anonymous_collections",date("Y-m-d H:i:s"));

View File

@ -455,7 +455,7 @@ function collection_writeable($collection)
global $usercollection,$username,$anonymous_login,$anonymous_user_session_collection, $rs_session;
debug("collection session : " . $collectiondata["session_id"]);
debug("collection user : " . $collectiondata["user"]);
debug("anonymous_login : " . $anonymous_login);
debug("anonymous_login : " . isset($anonymous_login) && is_string($anonymous_login) ? $anonymous_login : "(no)");
debug("userref : " . $userref);
debug("username : " . $username);
debug("anonymous_user_session_collection : " . (($anonymous_user_session_collection)?"TRUE":"FALSE"));
@ -557,16 +557,16 @@ function create_collection($userid,$name,$allowchanges=0,$cant_delete=0,$ref=0,$
{
debug_function_call("create_collection", func_get_args());
global $username,$anonymous_login,$rs_session, $anonymous_user_session_collection;
if($username==$anonymous_login && $anonymous_user_session_collection)
{
// We need to set a collection session_id for the anonymous user. Get session ID to create collection with this set
$rs_session=get_rs_session_id(true);
}
else
{
$rs_session="";
}
global $username,$anonymous_login,$rs_session, $anonymous_user_session_collection;
if($username==$anonymous_login && $anonymous_user_session_collection)
{
// We need to set a collection session_id for the anonymous user. Get session ID to create collection with this set
$rs_session=get_rs_session_id(true);
}
else
{
$rs_session="";
}
$sql = sprintf(
"INSERT INTO collection (%sname, user, created, allow_changes, cant_delete, session_id, type)
@ -4469,7 +4469,6 @@ function featured_collections_permissions_filter_sql(string $prefix, string $col
{
return $CACHE_FC_PERMS_FILTER_SQL[$cache_id];
}
// $prefix & $column are used to generate the right SQL (e.g AND ref IN(list of IDs)). If developer/code, passes empty strings,
// that's not this functions' responsibility. We could error here but the code will error anyway because of the bad SQL so
// we might as well fix the problem at its root (ie. where we call this function with bad input arguments).
@ -5135,3 +5134,28 @@ function compute_featured_collections_access_control()
return $return;
}
/**
* Remove all old anonymous collections
*
* @param int $limit Maximum number of collections to delete - if run from browser this is kept low to avoid delays
* @return void
*/
function cleanup_anonymous_collections(int $limit = 100)
{
global $anonymous_login;
$sql_limit = $limit == 0 ? "" : "LIMIT " . $limit;
if(!is_array($anonymous_login))
{
$anonymous_login = array($anonymous_login);
}
foreach ($anonymous_login as $anonymous_user)
{;
$user = get_user_by_username($anonymous_user);
if(is_int_loose($user))
{
sql_query("DELETE FROM collection WHERE user ='" . $user . "' AND created < (curdate() - interval '2' DAY) ORDER BY created ASC " . $sql_limit);
}
}
}

View File

@ -151,54 +151,62 @@ function setup_user($userdata)
$ip_restrict_group=trim($userdata["ip_restrict_group"]);
$ip_restrict_user=trim($userdata["ip_restrict_user"]);
if(isset($anonymous_login) && $username==$anonymous_login && isset($rs_session) && !checkperm('b')) // This is only required if anonymous user has collection functionality
{
// Get all the collections that relate to this session
$sessioncollections=get_session_collections($rs_session,$userref,true);
if($anonymous_user_session_collection)
{
// Just get the first one if more
$usercollection=$sessioncollections[0];
$collection_allow_creation=false; // Hide all links that allow creation of new collections
}
else
{
// Unlikely scenario, but maybe we do allow anonymous users to change the selected collection for all other anonymous users
$usercollection=$userdata["current_collection"];
}
}
else
{
$usercollection=$userdata["current_collection"];
// Check collection actually exists
$validcollection=$userdata["current_collection_valid"];
if($validcollection==0)
{
// Not a valid collection - switch to user's primary collection if there is one
$usercollection=sql_value("select ref value from collection where user='$userref' and name like 'Default Collection%' order by created asc limit 1",0);
if ($usercollection!=0)
{
# set this to be the user's current collection
sql_query("update user set current_collection='$usercollection' where ref='$userref'");
}
}
if ($usercollection==0 || !is_numeric($usercollection))
{
# Create a collection for this user
# The collection name is translated when displayed!
$usercollection=create_collection($userref,"Default Collection",0,1); # Do not translate this string!
# set this to be the user's current collection
sql_query("update user set current_collection='$usercollection' where ref='$userref'");
}
}
$USER_SELECTION_COLLECTION = get_user_selection_collection($userref);
if(is_null($USER_SELECTION_COLLECTION))
if(isset($anonymous_login) && $username==$anonymous_login && isset($rs_session) && !checkperm('b')) // This is only required if anonymous user has collection functionality
{
$USER_SELECTION_COLLECTION = create_collection($userref, "Selection Collection (for batch edit)", 0, 1);
update_collection_type($USER_SELECTION_COLLECTION, COLLECTION_TYPE_SELECTION);
// Get all the collections that relate to this session
$sessioncollections=get_session_collections($rs_session,$userref,true);
if($anonymous_user_session_collection)
{
// Just get the first one if more
$usercollection=$sessioncollections[0];
$collection_allow_creation=false; // Hide all links that allow creation of new collections
}
else
{
// Unlikely scenario, but maybe we do allow anonymous users to change the selected collection for all other anonymous users
$usercollection=$userdata["current_collection"];
}
}
else
{
$usercollection=$userdata["current_collection"];
// Check collection actually exists
$validcollection=$userdata["current_collection_valid"];
if($validcollection==0)
{
// Not a valid collection - switch to user's primary collection if there is one
$usercollection=sql_value("select ref value from collection where user='$userref' and name like 'Default Collection%' order by created asc limit 1",0);
if ($usercollection!=0)
{
# set this to be the user's current collection
sql_query("update user set current_collection='$usercollection' where ref='$userref'");
}
}
if ($usercollection==0 || !is_numeric($usercollection))
{
# Create a collection for this user
# The collection name is translated when displayed!
$usercollection=create_collection($userref,"Default Collection",0,1); # Do not translate this string!
# set this to be the user's current collection
sql_query("update user set current_collection='$usercollection' where ref='$userref'");
}
}
if($username == $anonymous_login)
{
// Don't create a new collection for every anonymous page load, just use a placeholder
$USER_SELECTION_COLLECTION = "user_selection_collection";
}
else
{
$USER_SELECTION_COLLECTION = get_user_selection_collection($userref);
if(is_null($USER_SELECTION_COLLECTION))
{
$USER_SELECTION_COLLECTION = create_collection($userref, "Selection Collection (for batch edit)", 0, 1);
update_collection_type($USER_SELECTION_COLLECTION, COLLECTION_TYPE_SELECTION);
}
}
$newfilter = false;

View File

@ -587,7 +587,7 @@ function add_resource_to_collection(resource, collection, csrf)
function add_multiple_resources_to_collection(resource_list, collection, csrf)
{
console.log("add_multiple_resource_to_collection: adding resource list #%o to collection #%i", resource_list, collection);
console.log("add_multiple_resource_to_collection: adding resource list %s to collection %s", JSON.stringify(resource_list), JSON.stringify(collection));
// var post_data = {}; // Object.assign({}, csrf);
var post_data = Object.assign({}, csrf);
post_data.resource_list = JSON.stringify(resource_list);

View File

@ -24,6 +24,24 @@ $allowed_actions = array(
"remove_multiple_resources"
);
$collection = getval("collection", "");
if($collection == "user_selection_collection")
{
$USER_SELECTION_COLLECTION = get_user_selection_collection($userref);
if(is_null($USER_SELECTION_COLLECTION))
{
// No selection collection is created for anonymous users until an action is performed by the user so create one now
$USER_SELECTION_COLLECTION = create_collection($userref, "Selection Collection (for batch edit)", 0, 1);
update_collection_type($USER_SELECTION_COLLECTION, COLLECTION_TYPE_SELECTION);
}
$collection = $USER_SELECTION_COLLECTION;
}
$collection = (int)$collection;
if(isset($selection_collection_only) && $collection != $USER_SELECTION_COLLECTION)
{
ajax_unauthorized();
}
$return = array();
$action = trim(getval("action", ""));
@ -93,11 +111,6 @@ if($action == "remove_selected_from_collection")
if($action == "add_resource")
{
$resource = getval("resource", null, true);
$collection = getval("collection", null, true);
if(isset($selection_collection_only) && $collection != $USER_SELECTION_COLLECTION)
{
ajax_unauthorized();
}
$smartadd = getval("smartadd", false);
$size = getval("size", "");
$addtype = getval("addtype", "");
@ -148,12 +161,6 @@ if($action == "add_resource")
if($action == "add_multiple_resources")
{
$resource_list=json_decode(getvalescaped("resource_list",false));
$collection = getval("collection", null, true);
if(isset($selection_collection_only) && $collection != $USER_SELECTION_COLLECTION)
{
ajax_unauthorized();
}
$smartadd = getval("smartadd", false);
$size = getval("size", "");
$addtype = getval("addtype", "");
@ -204,11 +211,6 @@ if($action == "add_multiple_resources")
if($action == "remove_resource")
{
$resource = getval("resource", null, true);
$collection = getval("collection", null, true);
if(isset($selection_collection_only) && $collection != $USER_SELECTION_COLLECTION)
{
ajax_unauthorized();
}
$smartadd = getval("smartadd", false);
$size = getval("size", "");
@ -224,11 +226,6 @@ if($action == "remove_resource")
if($action == "remove_multiple_resources")
{
$resource_list=json_decode(getvalescaped("resource_list",false));
$collection = getval("collection", null, true);
if(isset($selection_collection_only) && $collection != $USER_SELECTION_COLLECTION)
{
ajax_unauthorized();
}
$smartadd = getval("smartadd", false);
$size = getval("size", "");

View File

@ -275,7 +275,7 @@ else
}
$view_selected_request = ($use_selection_collection && mb_strpos($search, "!collection{$USER_SELECTION_COLLECTION}") !== false);
if($use_selection_collection && $clear_selection_collection && !$paging_request && !$thumbtypechange && !$view_selected_request)
if($use_selection_collection && $clear_selection_collection && !$paging_request && !$thumbtypechange && !$view_selected_request && $USER_SELECTION_COLLECTION != "user_selection_collection")
{
remove_all_resources_from_collection($USER_SELECTION_COLLECTION);
}
@ -350,7 +350,7 @@ $allow_reorder=false;
# get current collection resources to pre-fill checkboxes
if($use_selection_collection)
{
$selection_collection_resources = get_collection_resources(get_user_selection_collection($userref));
$selection_collection_resources = $USER_SELECTION_COLLECTION=="user_selection_collection" ? array() : get_collection_resources(get_user_selection_collection($userref));
$selection_collection_resources_count = count($selection_collection_resources);
}
@ -1666,7 +1666,7 @@ if($use_selection_collection)
var csrf_data = '{<?php echo generateAjaxToken("ProcessCollectionResourceSelection"); ?>}';
// Convert token from format {CSRFToken:"data"} to strict JSON format which is {"CSRFToken":"data"} so that it can be parsed
var csrf_data = csrf_data.replace('<?php echo $CSRF_token_identifier; ?>','"<?php echo $CSRF_token_identifier; ?>"');
ProcessCollectionResourceSelection(res_list, primary_action, <?php echo $USER_SELECTION_COLLECTION; ?>, csrf_data);
ProcessCollectionResourceSelection(res_list, primary_action, '<?php echo $USER_SELECTION_COLLECTION; ?>', csrf_data);
// Reset processing points
resource_starting=null;
@ -1688,7 +1688,7 @@ if($use_selection_collection)
var csrf_data = '{<?php echo generateAjaxToken("ProcessCollectionResourceSelection"); ?>}';
// Convert token from format {CSRFToken:"data"} to strict JSON format which is {"CSRFToken":"data"} so that it can be parsed
var csrf_data = csrf_data.replace('<?php echo $CSRF_token_identifier; ?>','"<?php echo $CSRF_token_identifier; ?>"');
ProcessCollectionResourceSelection(res_list, primary_action, <?php echo $USER_SELECTION_COLLECTION; ?>, csrf_data);
ProcessCollectionResourceSelection(res_list, primary_action, '<?php echo $USER_SELECTION_COLLECTION; ?>', csrf_data);
}
else if (resource_ending) {