$GLOBALS['pAR'], 'nAR' => $GLOBALS['nAR'], 'rAR' => $GLOBALS['rAR'], 'pInfoAR' => $GLOBALS['pInfoAR'], 'ptot' => $GLOBALS['ptot'], 'rNameAR' => $GLOBALS['rNameAR'], 'pcAR' => $GLOBALS['pcAR'], 'rtot' => $GLOBALS['rtot'], 'reviewersPerPaper' => $GLOBALS['reviewersPerPaper'], 'papersPerReviewer' => $GLOBALS['papersPerReviewer'], 'pprThreshold' => $GLOBALS['pprThreshold'], 'algo' => $GLOBALS['algo'], 'continueFrom' => (isset($GLOBALS['continueVal']) ? $GLOBALS['continueVal'] : 0), 'POST' => array( 'remedy' => (isset($_POST['remedy']) ? $_POST['remedy'] : array()), 'keep' => (isset($_POST['keep']) ? $_POST['keep'] : ''), 'skipaccepted' => (isset($_POST['skipaccepted']) ? $_POST['skipaccepted'] : ''), 'limittype' => (isset($_POST['limittype']) ? $_POST['limittype'] : ''), 'pcrev' => (isset($_POST['pcrev']) ? $_POST['pcrev'] : ''), 'advrev' => (isset($_POST['advrev']) ? $_POST['advrev'] : ''), 'rpp' => (isset($_POST['rpp']) ? $_POST['rpp'] : ''), 'ppr' => (isset($_POST['ppr']) ? $_POST['ppr'] : ''), 'pprt' => (isset($_POST['pprt']) ? $_POST['pprt'] : ''), 'ppa' => (isset($_POST['ppa']) ? $_POST['ppa'] : ''), 'algo' => (isset($_POST['algo']) ? $_POST['algo'] : '') ) ); if (isset($GLOBALS['continueAR'])) { foreach ($GLOBALS['continueAR'] as $k) { $_SESSION['OPENCONFCHAIRVARS']['timeoutAR'][$k] = $GLOBALS[$k]; } } session_write_close(); header("Location: " . $_SERVER['PHP_SELF'] . "?timeout=1"); ob_clean(); exit; } ob_start(); printHeader("Auto Assign Reviewers", 1); // Init algorithm array $OC_algorithmAR = array( array( 'algorithm' => 'Weighted Topic Match', 'description' => 'Assigns based on number of topic matches (high to low) between submissions and reviewers, giving assignment precedence to submissions with the least number of overall matching reviewer/topic pairings', 'include' => 'assign_auto_reviewers_weighted_topic_match.inc' ), array( 'algorithm' => 'Topic Match', 'description' => 'Assigns based on number of topic matches (high to low) between submissions and reviewers', 'include' => 'assign_auto_reviewers_topic_match.inc' ), ); // Check for addt'l (hook) algorithms if (oc_hookSet('assign_auto_reviewers-algorithm')) { foreach ($OC_hooksAR['assign_auto_reviewers-algorithm'] as $k => $v) { $OC_algorithmAR[] = $v; } } // Submit - Commit assignments to database? if (isset($_POST['submit']) && ($_POST['submit'] == "Make Assignments")) { // Check for valid submission if (!validToken('chair')) { warn('Invalid submission'); } if (!isset($_SESSION['OPENCONFCHAIRVARS']['pAssignments'])) { err("No reviewers set"); } // Keep or delete current assignments? $currAR = array(); if ($_POST['keep'] == 'Yes') { $prq = "SELECT `paperid`, `reviewerid` FROM `" . OCC_TABLE_PAPERREVIEWER . "`"; $prr = ocsql_query($prq) or err("Unable to access database"); while ($prl = ocsql_fetch_array($prr)) { $currAR[] = $prl['paperid'] . '-' . $prl['reviewerid']; } } else { oc_deleteAssignments(null, null); } // Add reviewers foreach ($_SESSION['OPENCONFCHAIRVARS']['pAssignments'] as $pid => $rids) { foreach ($rids as $rid) { if (!$rid || in_array($pid . '-' . $rid, $currAR)) { continue; } $q = "INSERT INTO `" . OCC_TABLE_PAPERREVIEWER . "` (`paperid`,`reviewerid`,`assigned`) VALUES ('" . safeSQLstr($pid) . "','" . safeSQLstr($rid) . "','" . safeSQLstr(date('Y-m-d')) . "')"; issueSQL($q); } } // Okey Dokey print '
Assignments have been made
'; unset($_SESSION['OPENCONFCHAIRVARS']['pAssignments']); printFooter(); exit; } // Check whether any reviews assigned yet $prq = "SELECT `paperid`, `reviewerid` FROM `" . OCC_TABLE_PAPERREVIEWER . "`"; $prr = ocsql_query($prq) or err("Unable to access database"); $prtot = ocsql_num_rows($prr); if ($prtot > 0) { print 'Reviews appear to have already been assigned. Existing reviews will be deleted unless you choose Yes to Keep Existing Assignments below.
'; $confirmOverride = true; } else { $confirmOverride = false; } if (isset($_GET['timeout']) && ($_GET['timeout'] == 1) && isset($_SESSION['OPENCONFCHAIRVARS']['timeoutAR']) && is_array($_SESSION['OPENCONFCHAIRVARS']['timeoutAR'])) { foreach($_SESSION['OPENCONFCHAIRVARS']['timeoutAR'] as $k => $v) { if ($k == 'POST') { foreach ($v as $pk => $pv) { $_POST[$pk] = $pv; } } else { $$k = $v; } } unset($_SESSION['OPENCONFCHAIRVARS']['timeoutAR']); } else { // Assign PC members as reviewers? $ppa = ''; if (isset($_POST['pcrev']) && ($_POST['pcrev'] == 'Yes')) { $onpc = ""; // Set a diff max # of subs per advocate reviewer if (isset($_POST['ppa']) && preg_match("/^\d+$/", $_POST['ppa'])) { $ppa = $_POST['ppa']; } } else { $onpc = " AND `" . OCC_TABLE_REVIEWER . "`.`onprogramcommittee`='F'"; } // Get number of papers and initialize paper count array $pAR = array(); // paper reviewers array $pInfoAR = array(); // paper info array $q = "SELECT `paperid`, `title`, `accepted`, `type` FROM `" . OCC_TABLE_PAPER . "` ORDER BY `paperid`"; $r = ocsql_query($q) or err("Unable to get submissions " . ocsql_errno()); if (($ptot = ocsql_num_rows($r)) == 0) { warn('No submissions have been made yet.'); } while ($l=ocsql_fetch_array($r)) { $pAR[$l['paperid']] = array(); $pInfoAR[$l['paperid']] = array( 'title' => $l['title'], 'accepted' => $l['accepted'], 'type' => $l['type'] ); } // Get number of reviewers and initialize reviewer count arrays $rAR = array(); // reviewer papers array $rNameAR = array(); // reviewer name array $pcAR = array(); // program committee array $q = "SELECT `reviewerid`, CONCAT_WS(' ', `name_first`, `name_last`) AS `name`, `onprogramcommittee` FROM `" . OCC_TABLE_REVIEWER . "` ORDER BY `reviewerid`"; $r = ocsql_query($q) or err("Unable to get reviewers ".ocsql_errno()); if (($rtot = ocsql_num_rows($r)) == 0) { warn('No reviewers have signed up yet.'); } while ($l=ocsql_fetch_array($r)) { $rAR[$l['reviewerid']] = array(); $rNameAR[$l['reviewerid']] = $l['name']; if ($l['onprogramcommittee'] == 'T') { $pcAR[] = $l['reviewerid']; } } // Revise rtot based on whether pc members assigned as reviewers if (!isset($_POST['pcrev']) || ($_POST['pcrev'] == 'No')) { $rtot -= count($pcAR); } // Get conflicts $nAR = getConflicts(); // Calculate # of reviewers per paper if (isset($_POST['rpp']) && preg_match("/^\d+$/",$_POST['rpp'])) { $reviewersPerPaper = $_POST['rpp']; } else { if (($rppavg=round($rtot/$ptot)) > $OC_configAR['OC_minReviewersPerPaper']) { $reviewersPerPaper = $rppavg; } else { $reviewersPerPaper = $OC_configAR['OC_minReviewersPerPaper']; } } // Calculate max # of papers each reviewer should get assigned if (isset($_POST['ppr']) && preg_match("/^\d+$/",$_POST['ppr'])) { $papersPerReviewer = $_POST['ppr']; #set below: $pprThreshold = $_POST['pprt']; } else { $totrevs = $rtot; $papersPerReviewer = ceil((($ptot*$reviewersPerPaper)+count($nAR))/$totrevs); # possibly remove +count($nAR) } // Set min # of paper each reviewer should be assigned if (isset($_POST['pprt']) && preg_match("/^\d+$/",$_POST['pprt'])) { $pprThreshold = $_POST['pprt']; } else { $pprThreshold = floor($papersPerReviewer/2); } // Keep assignments already made? if (!isset($_POST['keep']) || ($_POST['keep'] == 'Yes')) { $confirmOverride = false; if ($prtot > 0) { while ($prl = ocsql_fetch_array($prr)) { array_push($pAR[$prl['paperid']], $prl['reviewerid']); array_push($rAR[$prl['reviewerid']], $prl['paperid']); } } } // Add advocates as reviewers? if ($OC_configAR['OC_paperAdvocates'] && (!isset($_POST['advrev']) || empty($_POST['advrev']) || ($_POST['advrev'] == "Yes")) ) { $q = "SELECT `paperid`, `advocateid` FROM `" . OCC_TABLE_PAPERADVOCATE . "`"; $r = ocsql_query($q) or err("Unable to get submissions' advocate " . ocsql_errno()); while ($l=ocsql_fetch_array($r)) { if (oc_skipSubAssignment($l['paperid'])) { continue; } if (!in_array($l['advocateid'], $pAR[$l['paperid']])) { array_push($pAR[$l['paperid']], $l['advocateid']); array_push($rAR[$l['advocateid']], $l['paperid']); } } } // Set max # of papers for advocate reviewers if (empty($ppa)) { $papersPerAdvocate = $papersPerReviewer; } else { $papersPerAdvocate = $ppa; } // Algorithm to use if (isset($_POST['algo']) && ctype_digit($_POST['algo'])) { $algo = $_POST['algo']; } else { $algo = 0; // default to first defined algorithm above } } // Get list of sub. types $OC_activeSubTypeAR = array(); $typer = ocsql_query("SELECT DISTINCT `type` FROM `" . OCC_TABLE_PAPER . "` WHERE `type` IS NOT NULL AND `type`!='' ORDER BY `type`") or err('Unable to retrieve submission types'); while ($typel = ocsql_fetch_assoc($typer)) { $OC_activeSubTypeAR[$typel['type']] = substr($typel['type'], 0, 50); } // Run algo if (isset($OC_algorithmAR[$algo]['include']) && is_file($OC_algorithmAR[$algo]['include'])) { require_once $OC_algorithmAR[$algo]['include']; } else { err("Algorithm choice unknown"); exit; } // Remedy missing reviews by assigning reviewers w/lowest #s (if set) if (isset($_POST['remedy']) && in_array("random", $_POST['remedy'])) { foreach (array_keys($pAR) as $k) { if (oc_skipSubAssignment($k)) { continue; } if (count($pAR[$k]) < $reviewersPerPaper) { // Create an ordered array of reviewers w/least # of reviews $rcountAR = array(); foreach (array_keys($rAR) as $k2) { $rcountAR[$k2] = count($rAR[$k2]); } asort($rcountAR); reset($rcountAR); // Assign reviewers if (!in_array(key($rcountAR),$pAR[$k]) && !in_array($k.'-'.key($rcountAR),$nAR)) { array_push($pAR[$k], key($rcountAR)); array_push($rAR[key($rcountAR)], $k); } while ((count($pAR[$k]) < $reviewersPerPaper) && next($rcountAR)) { if (!in_array(key($rcountAR),$pAR[$k]) && !in_array($k.'-'.key($rcountAR),$nAR)) { array_push($pAR[$k], key($rcountAR)); array_push($rAR[key($rcountAR)], $k); } } } } } // Remember assignments $_SESSION['OPENCONFCHAIRVARS']['pAssignments'] = $pAR; // Display form print 'Below you will find OpenConf\'s suggested review assignments. You may fine tune these automated assignments by changing the following options and clicking Re-Evaluate Assignments. Once you are satisfied, click the Make Assignments button to commit them to the database. You may manually add/delete reviews afterwards through the Assign Reviews Manually and List/Unassign Reviews menus.'; if (oc_moduleValid('oc_auto_assign')) { print ' If instead of using this feature you would like assignments to be made automatically when a new submission is made, use the Auto Assign module.'; } print '
'; function fmtNumSpacing ($n, $dir="l") { $sp = ""; if ($n < 10) { $sp = " "; } elseif ($n < 100) { $sp = " "; } if ($dir=="l") { return($sp.$n); } else { return($n.$sp); } } function fmtStrSpacing ($str, $len) { $a = substr($str,0,$len); for ($i=oc_strlen($a); $i<$len; $i++) { $a .= " "; } return $a; } print '
Suggested Assignments' . ((!isset($_POST['keep']) || ($_POST['keep'] == 'Yes')) ? 'including already assigned' : '') . ' | ||
---|---|---|
* below threshold Place cursor on No. Reviewers for assignments Click title for submission info (new window) No. Reviewers per Submission ID (Title) '; foreach ($pAR as $k => $v) { $titleStr = "Reviewers for Submission $k:\n\n"; foreach ($v as $vv) { $titleStr .= "$vv - " . $rNameAR[$vv] . "\n"; } $tmpStr = '' . fmtNumSpacing(count($v)) . " - " . fmtNumSpacing($k) . '' . safeHTMLstr($titleStr) . ' (' . safeHTMLstr(fmtStrSpacing($pInfoAR[$k]['title'], 28)) . ")"; if (count($v) < $reviewersPerPaper) { print '' . $tmpStr . " *\n"; } else { print $tmpStr."\n"; } } print ' | * below threshold Place cursor on No. Submissions for reviewers Click name for reviewer info (new window) No. Submissions per Reviewer ID (Name) '; foreach ($rAR as $k => $v) { $titleStr = "Submissions for Reviewer $k:\n\n"; foreach ($v as $vv) { $titleStr .= "$vv - " . substr($pInfoAR[$vv]['title'],0,40) . "\n"; } $tmpStr = '' . fmtNumSpacing(count($v)) . " - " . fmtNumSpacing($k) . '' . safeHTMLstr($titleStr) . ' ('; if (in_array($k, $pcAR)) { $tmpStr .= 'PC-'; $len = 21; } else { $len = 24; } $tmpStr .= '' . safeHTMLstr(fmtStrSpacing($rNameAR[$k],$len)).")"; if (count($v) <= $pprThreshold) { print '' . $tmpStr . " *\n"; } else { print $tmpStr . "\n"; } } print ' |