Skip to content

Commit

Permalink
Fix huge memory consumption for print_user_option_list()
Browse files Browse the repository at this point in the history
Following the implementation of the fix for 0010130, calling this
function when the current project is ALL_PROJECTS causes a massive surge
in memory usage as the code builds a large array containing the list of
all users in all projects accessible to the current user, and then
reduces it to remove duplicates.

This commit reduces the problem by removing calls to array_merge() and
building the consolidated user list in a single pass, using a while
loop. No-longer-used arrays are unset to free up memory.

Fixes #15411
  • Loading branch information
dregad committed Jan 23, 2013
1 parent 5f641fc commit f977b3c
Showing 1 changed file with 12 additions and 7 deletions.
19 changes: 12 additions & 7 deletions core/print_api.php
Expand Up @@ -254,16 +254,20 @@ function print_user_option_list( $p_user_id, $p_project_id = null, $p_access = A
$t_projects = user_get_accessible_projects( $t_current_user );

# Get list of users having access level for all accessible projects
$t_users_temp = array();
$t_users = array();
foreach( $t_projects as $t_project_id ) {
$t_project_users_list = project_get_all_user_rows( $t_project_id, $p_access );
$t_users_temp = array_merge( $t_users_temp, $t_project_users_list );
# Do a 'smart' merge of the project's user list, into an
# associative array (to remove duplicates)
# Use a while loop for better performance
$i = 0;
while( isset( $t_project_users_list[$i] ) ) {
$t_users[ $t_project_users_list[$i]['id'] ] = $t_project_users_list[$i];
$i++;
}

# Build list of users as an associative array (to remove duplicates)
foreach( $t_users_temp as $t_user ) {
$t_users[$t_user['id']] = $t_user;
unset( $t_project_users_list );
}
unset( $t_projects );
} else {
$t_users = project_get_all_user_rows( $p_project_id, $p_access );
}
Expand All @@ -288,7 +292,8 @@ function print_user_option_list( $p_user_id, $p_project_id = null, $p_access = A
$t_sort[] = $t_sort_name;
}
array_multisort( $t_sort, SORT_ASC, SORT_STRING, $t_users, $t_display );
$t_count = count( $t_sort );
unset( $t_sort );
$t_count = count( $t_users );
for( $i = 0;$i < $t_count;$i++ ) {
$t_row = $t_users[$i];
echo '<option value="' . $t_row['id'] . '" ';
Expand Down

0 comments on commit f977b3c

Please sign in to comment.