$string['cannotsetvisible'] = 'Cannot set this to visible - the plugin has been completely disabled because of a misconfiguration';
$string['configexport'] = 'Configure exported data';
$string['configplugin'] = 'Configure portfolio plugin';
+$string['confirmcancel'] = 'Are you sure you wish you cancel this export?';
$string['confirmexport'] = 'Please confirm this export';
$string['confirmsummary'] = 'Summary of your export';
$string['configure'] = 'Configure';
$string['nocallbackclass'] = 'Could not find the callback class to use ($a)';
$string['nocommonformats'] = 'No common formats between any available portfolio plugin and the calling location $a';
$string['noclassbeforeformats'] = 'You must set the callback class before calling set_formats in portfolio_button';
+$string['noinstanceyet'] = 'Not yet selected';
+$string['nologs'] = 'There are no logs to display!';
+$string['nomultipleexports'] = 'Sorry, but the portfolio destination ($a->plugin) doesn\'t support multiple exports at the same time. Please <a href=\"$a->link\">finish the current one first</a> and try again';
$string['nopermissions'] = 'Sorry but you do not have the required permissions to export files from this area';
$string['nonprimative'] = 'A non primative value was passed as a callback argument to portfolio_add_button. Refusing to continue. The key was $a->key and the value was $a->value';
$string['notexportable'] = 'Sorry, but the type of content you are trying to export is not exportable';
$string['selectedformat'] = 'Selected export format';
$string['selectedwait'] = 'Selected to wait?';
$string['selectplugin'] = 'Select destination';
+$string['singleinstancenomultiallowed'] = 'Only a single portfolio plugin instance is available, it doesn\'t support multiple exports per session, and there\'s already an active export in the session using this plugin!';
$string['someinstancesdisabled'] = 'Some configured portfolio plugin instances have been disabled either because they are misconfigured or rely on something else that is';
$string['somepluginsdisabled'] = 'Some entire portfolio plugins have been disabled because they are either misconfigured or rely on something else that is:';
$string['sure'] = 'Are you sure you want to delete \'$a\'? This cannot be undone.';
// but I think if there's always an exception, we should clean up
// rather than force the user to resolve the export later.
$exporter->process_stage_cleanup();
- } else {
- global $SESSION;
- if (!empty($SESSION->portfolioexport)) {
- debugging(get_string('exportexceptionnoexporter', 'portfolio'));
- }
}
parent::__construct($errorcode, $module, $continue, $a);
}
*/
private $id;
- /**
- * the session key during the export
- * used to avoid hijacking transfers
- */
- private $sesskey;
-
/**
* array of stages that have had the portfolio plugin already steal control from them
*/
*/
private $format;
+ /**
+ * queued - this is set after the event is triggered
+ */
+ private $queued = false;
+
+ /**
+ * expiry time - set the first time the object is saved out
+ */
+ private $expirytime;
+
/**
* construct a new exporter for use
*
if ($pluginobj || $callerobj || count($formats) > 1 || ($expectedtime != PORTFOLIO_TIME_LOW && $expectedtime != PORTFOLIO_TIME_FORCEQUEUE)) {
$customdata = array(
'instance' => $this->instance,
+ 'id' => $this->id,
'plugin' => $pluginobj,
'caller' => $callerobj,
'userid' => $this->user->id,
return true;
}
$strconfirm = get_string('confirmexport', 'portfolio');
- $yesurl = $CFG->wwwroot . '/portfolio/add.php?stage=' . PORTFOLIO_STAGE_QUEUEORWAIT;
- $nourl = $CFG->wwwroot . '/portfolio/add.php?cancel=1';
+ $baseurl = $CFG->wwwroot . '/portfolio/add.php?sesskey=' . sesskey() . '&id=' . $this->get('id');
+ $yesurl = $baseurl . '&stage=' . PORTFOLIO_STAGE_QUEUEORWAIT;
+ $nourl = $baseurl . '&cancel=1';
$this->print_header('confirmexport');
echo $OUTPUT->box_start();
echo $OUTPUT->heading(get_string('confirmsummary', 'portfolio'), 4);
* @return boolean whether or not to process the next stage. this is important as the control function is called recursively.
*/
public function process_stage_queueorwait() {
- global $SESSION;
$wait = $this->instance->get_export_config('wait');
if (empty($wait)) {
events_trigger('portfolio_send', $this->id);
- unset($SESSION->portfolioexport);
+ $this->queued = true;
return $this->process_stage_finished(true);
}
return true;
* @return boolean whether or not to process the next stage. this is important as the control function is called recursively.
*/
public function process_stage_cleanup($pullok=false) {
- global $CFG, $DB, $SESSION;
+ global $CFG, $DB;
if (!$pullok && $this->get('instance') && !$this->get('instance')->is_push()) {
- unset($SESSION->portfolioexport);
return true;
}
if ($this->get('instance')) {
$DB->delete_records('portfolio_tempdata', array('id' => $this->id));
$fs = get_file_storage();
$fs->delete_area_files(SYSCONTEXTID, 'portfolio_exporter', $this->id);
- unset($SESSION->portfolioexport);
return true;
}
* cancels a potfolio request and cleans up the tempdata
* and redirects the user back to where they started
*/
- public function cancel_request() {
+ public function cancel_request($logreturn=false) {
+ global $CFG;
if (!isset($this)) {
return;
}
$this->process_stage_cleanup(true);
+ if ($logreturn) {
+ redirect($CFG->wwwroot . '/user/portfoliologs.php');
+ }
redirect($this->caller->get_return_url());
exit;
}
'instance' => (empty($this->instance)) ? null : $this->instance->get('id'),
);
$this->id = $DB->insert_record('portfolio_tempdata', $r);
+ $this->expirytime = $r->expirytime;
$this->save(); // call again so that id gets added to the save data.
} else {
$r = $DB->get_record('portfolio_tempdata', array('id' => $this->id));
}
require_once($CFG->dirroot . '/' . $exporter->callerfile);
$exporter = unserialize(serialize($exporter));
+ if (!$exporter->get('id')) {
+ // workaround for weird case
+ // where the id doesn't get saved between a new insert
+ // and the subsequent call that sets this field in the serialised data
+ $exporter->set('id', $id);
+ $exporter->save();
+ }
return $exporter;
}
* @throws portfolio_exception
*/
public function verify_rewaken($readonly=false) {
- global $USER;
- if ($this->get('user')->id != $USER->id) {
+ global $USER, $CFG;
+ if ($this->get('user')->id != $USER->id) { // make sure it belongs to the right user
throw new portfolio_exception('notyours', 'portfolio');
}
- if (!$readonly && !confirm_sesskey($this->get('sesskey'))) {
- throw new portfolio_exception('confirmsesskeybad');
+ if (!$readonly && $this->get('instance') && !$this->get('instance')->allows_multiple_exports()
+ && ($already = portfolio_exporter::existing_exports($this->get('user')->id, $this->get('instance')->get('plugin')))
+ && array_shift(array_keys($already)) != $this->get('id')
+ ) {
+ $a = (object)array(
+ 'plugin' => $this->get('instance')->get('plugin'),
+ 'link' => $CFG->wwwroot . '/user/portfoliologs.php',
+ );
+ throw new portfolio_exception('nomultipleexports', 'portfolio', '', $a);
}
- if (!$this->caller->check_permissions()) {
+ if (!$this->caller->check_permissions()) { // recall the caller permission check
throw new portfolio_caller_exception('nopermissions', 'portfolio', $this->caller->get_return_url());
}
}
exit;
}
+ /**
+ * return a list of current exports for the given user
+ * this will not go through and call rewaken_object, because it's heavy
+ * it's really just used to figure out what exports are currently happening.
+ * this is useful for plugins that don't support multiple exports per session
+ *
+ * @param int $userid the user to check for
+ * @param string $type (optional) the portfolio plugin to filter by
+ *
+ * @return array
+ */
+ public static function existing_exports($userid, $type=null) {
+ global $DB;
+ $sql = 'SELECT t.*,t.instance,i.plugin,i.name FROM {portfolio_tempdata} t JOIN {portfolio_instance} i ON t.instance = i.id WHERE t.userid = ? ';
+ $values = array($userid);
+ if ($type) {
+ $sql .= ' AND i.plugin = ?';
+ $values[] = $type;
+ }
+ return $DB->get_records_sql($sql, $values);
+ }
+
+ /**
+ * Return an array of existing exports by type for a given user.
+ * This is much more lightweight than {@see existing_exports} because it only returns the types, rather than the whole serialised data
+ * so can be used for checking availability of multiple plugins at the same time.
+ */
+ public static function existing_exports_by_plugin($userid) {
+ global $DB;
+ $sql = 'SELECT t.instance,i.plugin FROM {portfolio_tempdata} t JOIN {portfolio_instance} i ON t.instance = i.id WHERE t.userid = ? ';
+ $values = array($userid);
+ return $DB->get_records_sql_menu($sql, $values);
+ }
}
$mform =& $this->_form;
$mform->addElement('hidden', 'stage', PORTFOLIO_STAGE_CONFIG);
- $mform->setType('stage', PARAM_INT);
+ $mform->addElement('hidden', 'id', $this->_customdata['id']);
$mform->addElement('hidden', 'instance', $this->_customdata['instance']->get('id'));
$mform->setType('instance', PARAM_INT);
+ $mform->setType('stage', PARAM_INT);
+ $mform->setType('id', PARAM_INT);
if (array_key_exists('formats', $this->_customdata) && is_array($this->_customdata['formats'])) {
if (count($this->_customdata['formats']) > 1) {
true,
true
);
+ // TODO maybe add on some information to the user if they're already exporting
+ // and some of the options were skipped because they are for plugins that don't support
+ // multiple exports per session
if (empty($options)) {
debugging('noavailableplugins', 'portfolio');
return false;
}
$mform =& $this->_form;
$mform->addElement('select', 'instance', get_string('selectplugin', 'portfolio'), $options);
+ $mform->addElement('hidden', 'id', $this->_customdata['id']);
$this->add_action_buttons(true, get_string('next'));
}
}
public static function mnet_publishes() {
return array();
}
+
+ /**
+ * whether this plugin supports multiple exports in the same session
+ * most plugins should handle this, but some that require a redirect for authentication
+ * and then don't support dynamically constructed urls to return to (eg box.net)
+ * need to override this to return false.
+ * this means that moodle will prevent multiple exports of this *type* of plugin
+ * occurring in the same session.
+ *
+ * @return boolean
+ */
+ public static function allows_multiple_exports() {
+ return true;
+ }
}
/**
*/
class portfolio_add_button {
- private $alreadyexporting;
private $callbackclass;
private $callbackargs;
private $callbackfile;
*/
public function __construct($options=null) {
global $SESSION, $CFG;
- if (isset($SESSION->portfolioexport)) {
- $this->alreadyexporting = true;
- return;
- }
$this->instances = portfolio_instances();
if (empty($options)) {
return true;
}
+ $constructoroptions = array('callbackclass', 'callbackargs', 'callbackfile', 'formats');
foreach ((array)$options as $key => $value) {
if (!in_array($key, $constructoroptions)) {
throw new portfolio_button_exception('invalidbuttonproperty', 'portfolio', $key);
* this path should be relative (ie, not include) dirroot, eg '/mod/forum/lib.php'
*/
public function set_callback_options($class, array $argarray, $file=null) {
- if ($this->alreadyexporting) {
- return;
- }
global $CFG;
if (empty($file)) {
$backtrace = debug_backtrace();
* {@see portfolio_format_from_file} for how to get the appropriate formats to pass here for uploaded files.
*/
public function set_formats($formats=null) {
- if ($this->alreadyexporting) {
- return;
- }
if (is_string($formats)) {
$formats = array($formats);
}
* this is whole string, not key. optional, defaults to 'Add to portfolio';
*/
public function to_html($format=null, $addstr=null) {
- if ($this->alreadyexporting) {
- return $this->already_exporting($format, $addstr);
- }
global $CFG, $COURSE, $OUTPUT;
if (!$this->is_renderable()) {
return;
if (count($this->instances) == 1) {
$tmp = array_values($this->instances);
$instance = $tmp[0];
- //$instance = array_shift($this->instances);
+
$formats = portfolio_supported_formats_intersect($this->formats, $instance->supported_formats());
if (count($formats) == 0) {
// bail. no common formats.
debugging(get_string('instancemisconfigured', 'portfolio', get_string($error[$instance->get('id')], 'portfolio_' . $instance->get('plugin'))));
return;
}
+ if (!$instance->allows_multiple_exports() && $already = portfolio_exporter::existing_exports($USER->id, $instance->get('plugin'))) {
+ debugging(get_string('singleinstancenomultiallowed', 'portfolio'));
+ return;
+ }
$formoutput .= "\n" . '<input type="hidden" name="instance" value="' . $instance->get('id') . '" />';
$linkoutput .= '&instance=' . $instance->get('id');
}
public function get_callbackclass() {
return $this->callbackclass;
}
-
- private function already_exporting($format, $addstr) {
- global $CFG, $OUTPUT;
- $url = $CFG->wwwroot . '/portfolio/already.php';
- $icon = $OUTPUT->old_icon_url('t/portfoliono') . '';
- $alt = get_string('alreadyalt', 'portfolio');
- if (empty($format)) {
- $format = PORTFOLIO_ADD_FULL_FORM;
- }
- if (empty($addstr)) {
- $addstr = get_string('addtoportfolio', 'portfolio');
- }
- switch ($format) {
- case PORTFOLIO_ADD_FULL_FORM:
- return '<form action="' . $url . '">' . "\n"
- . '<input type="submit" value="' . $addstr . '" />' . "\n"
- . '<img src="' . $icon . '" alt="' . $alt . '" />' . "\n"
- . ' </form>';
- case PORTFOLIO_ADD_ICON_FORM:
- case PORTFOLIO_ADD_ICON_LINK:
- return '<a href="' . $url . '"><img src="' . $icon . '" alt="' . $alt . '" /></a>';
- case PORTFOLIO_ADD_TEXT_LINK:
- return '<a href="' . $url . '">' . $addstr . '(!) </a>';
- default:
- debugging(get_string('invalidaddformat', 'portfolio', $format));
- }
- }
}
/**
* @return string the html, from <select> to </select> inclusive.
*/
function portfolio_instance_select($instances, $callerformats, $callbackclass, $selectname='instance', $return=false, $returnarray=false) {
- global $CFG;
+ global $CFG, $USER;
if (empty($CFG->enableportfolios)) {
return;
$count = 0;
$selectoutput = "\n" . '<select name="' . $selectname . '">' . "\n";
+ $existingexports = portfolio_exporter::existing_exports_by_plugin($USER->id);
foreach ($instances as $instance) {
$formats = portfolio_supported_formats_intersect($callerformats, $instance->supported_formats());
if (count($formats) == 0) {
debugging(get_string('pluginismisconfigured', 'portfolio', get_string($pinsane[$instance->get('plugin')], 'portfolio_' . $instance->get('plugin'))));
continue;
}
+ if (!$instance->allows_multiple_exports() && in_array($instance->get('plugin'), $existingexports)) {
+ // bail, already exporting something with this plugin and it doesn't support multiple exports
+ continue;
+ }
+
$count++;
$selectoutput .= "\n" . '<option value="' . $instance->get('id') . '">' . $instance->get('name') . '</option>' . "\n";
$options[$instance->get('id')] = $instance->get('name');
*/
function portfolio_fake_add_url($instanceid, $classname, $classfile, $callbackargs) {
global $CFG;
- $url = $CFG->wwwroot . '/portfolio/add.php?instance=' . $instanceid . '&callbackclass=' . $classname . '&callbackfile=' . $classfile;
+ $url = $CFG->wwwroot . '/portfolio/add.php?instance=' . $instanceid . '&callbackclass=' . $classname . '&callbackfile=' . $classfile . '&sesskey=' . sesskey();
if (is_object($callbackargs)) {
$callbackargs = (array)$callbackargs;
// so plugins don't have to.
require_once($CFG->libdir . '/formslib.php');
+$dataid = optional_param('id', 0, PARAM_INT); // id of partially completed export. corresponds to a record in portfolio_tempdata
+$type = optional_param('type', null, PARAM_SAFEDIR); // if we're returning from an external system (postcontrol) for a single-export only plugin
$cancel = optional_param('cancel', 0, PARAM_RAW); // user has cancelled the request
-$dataid = optional_param('id', 0, PARAM_INT); // id of partially completed export (in session, everything else in portfolio_tempdata
+$cancelsure = optional_param('cancelsure', 0, PARAM_BOOL); // make sure they confirm first
+$logreturn = optional_param('logreturn', 0, PARAM_BOOL); // when cancelling, we can also come from the log page, rather than the caller
$instanceid = optional_param('instance', 0, PARAM_INT); // instanceof of configured portfolio plugin
$courseid = optional_param('course', 0, PARAM_INT); // courseid the data being exported belongs to (caller object should provide this later)
$stage = optional_param('stage', PORTFOLIO_STAGE_CONFIG, PARAM_INT); // stage of the export we're at (stored in the exporter)
$callbackclass = optional_param('callbackclass', null, PARAM_ALPHAEXT); // callback class eg forum_portfolio_caller - the class to handle the exporting content.
require_login(); // this is selectively called again with $course later when we know for sure which one we're in.
-$PAGE->set_url('/portfolio/add.php', array('id' => $dataid));
+$PAGE->set_url('/portfolio/add.php', array('id' => $dataid, 'sesskey' => sesskey()));
$exporter = null;
-// try and find a partial export id in the session if it's not passed explicitly
-if (empty($dataid)) {
- if (isset($SESSION->portfolioexport)) {
- $dataid = $SESSION->portfolioexport;
+if ($postcontrol && $type && !$dataid) {
+ // we're returning from an external system that can't construct dynamic return urls
+ // this is a special "one export of this type only per session" case
+ if (portfolio_static_function($type, 'allows_multiple_exports')) {
+ throw new portfolio_exception('multiplesingleresume', 'portfolio');
}
+
+ if (!$dataid = $DB->get_field('portfolio_tempdata', 'id', array('type' => $type, 'userid' => $USER->id))) {
+ throw new portfolio_exception('invalidtempid', 'portfolio');
+ }
+} else {
+ // we can't do this in the above case, because we're redirecting straight back from an external system
+ // this is not really ideal, but since we're in a "staged" wizard, the session key is checked in other stages.
+ require_sesskey(); // pretty much everything in this page is a write that could be hijacked, so just do this at the top here
}
// if we have a dataid, it means we're in the middle of an export,
// this can happen in some cases, a cancel request is sent when something is already broken
// so process it elegantly and move on.
if ($cancel) {
- unset($SESSION->portfolioexport);
+ if ($logreturn) {
+ redirect($CFG->wwwroot . '/user/portfoliologs.php');
+ }
redirect($CFG->wwwroot);
} else {
- portfolio_exporter::print_expired_export();
+ throw $e;
}
}
// we have to wake it up first before we can cancel it
// so temporary directories etc get cleaned up.
if ($cancel) {
- $exporter->cancel_request();
+ if ($cancelsure) {
+ $exporter->cancel_request($logreturn);
+ } else {
+ $yesurl = $CFG->wwwroot . '/portfolio/add.php?id=' . $dataid . '&cancel=1&cancelsure=1&logreturn=' . $logreturn . '&sesskey=' . sesskey();
+ $nourl = $CFG->wwwroot . '/portfolio/add.php?id=' . $dataid . '&sesskey=' . sesskey();
+ if ($logreturn) {
+ $nourl = $CFG->wwwroot . '/user/portfoliologs.php';
+ }
+ $exporter->print_header('confirmcancel');
+ echo $OUTPUT->box_start();
+ echo $OUTPUT->confirm(get_string('confirmcancel', 'portfolio'), $yesurl, $nourl);
+ echo $OUTPUT->box_end();
+ echo $OUTPUT->footer();
+ exit;
+ }
}
- // verify we still belong to the correct user and session
+ // verify we still belong to the correct user and permissions are still ok
$exporter->verify_rewaken();
// if we don't have an instanceid in the exporter
// it means we've just posted from the 'choose portfolio instance' page
$callbackargs[substr($key, 3)] = $value;
}
}
- if (!confirm_sesskey()) {
- throw new portfolio_caller_exception('confirmsesskeybad', 'error');
- }
// righto, now we have the callback args set up
// load up the caller file and class and tell it to set up all the data
// it needs
// set the export-specific variables, and save.
$exporter->set('user', $USER);
- $exporter->set('sesskey', sesskey());
$exporter->save();
-
- // and finally, put it in the session for waking up again later.
- $SESSION->portfolioexport = $exporter->get('id');
}
if (!$exporter->get('instance')) {
// in this case the exporter object and the caller object have been set up above
// so just make a little form to select the portfolio plugin instance,
// which is the last thing to do before starting the export.
- $mform = new portfolio_instance_select('', array('caller' => $exporter->get('caller')));
+ $mform = new portfolio_instance_select('', array('id' => $exporter->get('id'), 'caller' => $exporter->get('caller')));
if ($mform->is_cancelled()) {
$exporter->cancel_request();
} else if ($fromform = $mform->get_data()){
+++ /dev/null
-<?php
-/**
- * Moodle - Modular Object-Oriented Dynamic Learning Environment
- * http://moodle.org
- * Copyright (C) 1999 onwards Martin Dougiamas http://dougiamas.com
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
- *
- * @package moodle
- * @subpackage portfolio
- * @author Penny Leach <penny@catalyst.net.nz>
- * @license http://www.gnu.org/copyleft/gpl.html GNU GPL
- * @copyright (C) 1999 onwards Martin Dougiamas http://dougiamas.com
- *
- * This file is the handler that gets invoked when there's already an export happening.
- */
-require_once(dirname(dirname(__FILE__)) . '/config.php');
-
-if (empty($CFG->enableportfolios)) {
- print_error('disabled', 'portfolio');
-}
-
-require_once($CFG->libdir . '/portfoliolib.php');
-
-require_login();
-
-$dataid = 0;
-
-// look for the export id in the request, if it's not there, try the session
-if (!$dataid = optional_param('id', '', PARAM_INT) ) {
- if (isset($SESSION->portfolioexport)) {
- $dataid = $SESSION->portfolioexport;
- }
-}
-
-// all we're going to do is print a table with some information
-// about the current export, with a yes/ no option to resume or cancel.
-$table = new html_table();
-$table->head = array(
- get_string('displayarea', 'portfolio'), // the part of moodle exporting content
- get_string('destination', 'portfolio'), // the portfolio plugin instance
- get_string('displayinfo', 'portfolio'), // any extra data about what it is we're exporting from the caller
-);
-$table->data = array();
-if ($dataid) {
- try {
- // try to reawaken it and get any information about it we can
- $exporter = portfolio_exporter::rewaken_object($dataid);
- $exporter->verify_rewaken();
- $table->data[] = array(
- $exporter->get('caller')->display_name(),
- ($exporter->get('instance') ? $exporter->get('instance')->get('name') : get_string('notyetselected', 'portfolio')),
- $exporter->get('caller')->heading_summary(),
- );
- } catch (portfolio_exception $e) { } // maybe in this case we should just kill it and redirect to the new request anyway ?
-}
-
-$strheading = get_string('activeexport', 'portfolio');
-
-$PAGE->set_title($strheading);
-$PAGE->set_heading($strheading);
-echo $OUTPUT->header();
-echo $OUTPUT->confirm(get_string('alreadyexporting', 'portfolio'), $CFG->wwwroot . '/portfolio/add.php', $CFG->wwwroot . '/portfolio/add.php?cancel=1');
-
-if (count($table->data) > 0) {
- echo $OUTPUT->table($table);
-}
-
-echo $OUTPUT->footer();
-
-
$currenttab = 'portfoliologs';
$showroles = 1;
+$somethingprinted = false;
include('tabs.php');
+echo $OUTPUT->box_start();
+
$queued = $DB->get_records('portfolio_tempdata', array('userid' => $USER->id), '', 'id, expirytime');
if (count($queued) > 0) {
$table = new html_table();
get_string('plugin', 'portfolio'),
get_string('displayinfo', 'portfolio'),
get_string('displayexpiry', 'portfolio'),
+ '',
);
$table->data = array();
+ $now = time();
foreach ($queued as $q){
$e = portfolio_exporter::rewaken_object($q->id);
$e->verify_rewaken(true);
+ $queued = $e->get('queued');
+ $base = $CFG->wwwroot . '/portfolio/add.php?id=' . $q->id . '&logreturn=1&sesskey=' . sesskey();
+ $iconstr = '';
+
+ $cancel = new moodle_action_icon();
+ $cancel->link->url = new moodle_url($base . '&cancel=1');
+ $cancel->image->src = $OUTPUT->old_icon_url('t/stop');
+ $cancel->linktext = get_string('cancel');
+
+ $iconstr = $OUTPUT->action_icon($cancel);
+
+ if (!$e->get('queued') && $e->get('expirytime') > $now) {
+ $continue = new moodle_action_icon();
+ $continue->link->url = new moodle_url($base);
+ $continue->image->src = $OUTPUT->old_icon_url('t/go');
+ $continue->linktext = get_string('continue');
+ $iconstr .= ' ' . $OUTPUT->action_icon($continue);
+ }
$table->data[] = array(
$e->get('caller')->display_name(),
- $e->get('instance')->get('name'),
+ (($e->get('instance')) ? $e->get('instance')->get('name') : get_string('noinstanceyet', 'portfolio')),
$e->get('caller')->heading_summary(),
userdate($q->expirytime),
+ $iconstr,
);
unset($e); // this could potentially be quite big, so free it.
}
echo $OUTPUT->heading(get_string('queuesummary', 'portfolio'));
echo $OUTPUT->table($table);
+ $somethingprinted = true;
}
+// paging - get total count separately
$logcount = $DB->count_records('portfolio_log', array('userid' => $USER->id));
if ($logcount > 0) {
$table = new html_table();
echo $OUTPUT->paging_bar($pagingbar);
echo $OUTPUT->table($table);
echo $OUTPUT->paging_bar($pagingbar);
-
+ $somethingprinted = true;
}
-
+if (!$somethingprinted) {
+ echo $OUTPUT->heading($strportfolios);
+ echo get_string('nologs', 'portfolio');
+}
+echo $OUTPUT->box_end();
echo $OUTPUT->footer();