This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "FusionForge".
The branch, master has been updated
via 7baa35da028697b1ab2c29858ab06eccffc5833c (commit)
from 4017da328b347f82f4dcbe0962cb7cdb2eff1f21 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
https://scm.fusionforge.org/anonscm/gitweb/?p=fusionforge/fusionforge.git;a=commitdiff;h=7baa35da028697b1ab2c29858ab06eccffc5833c
commit 7baa35da028697b1ab2c29858ab06eccffc5833c
Author: Franck Villaume <[email protected]>
Date: Sun Dec 4 18:53:42 2016 +0100
docman: document review: start implement
diff --git a/src/common/docman/DocumentReview.class.php
b/src/common/docman/DocumentReview.class.php
new file mode 100644
index 0000000..58d64d9
--- /dev/null
+++ b/src/common/docman/DocumentReview.class.php
@@ -0,0 +1,524 @@
+<?php
+/**
+ * FusionForge Documentation Manager
+ *
+ * Copyright 2016, Franck Villaume - TrivialDev
+ * http://fusionforge.org
+ *
+ * This file is part of FusionForge. FusionForge 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 Licence, or (at your option)
+ * any later version.
+ *
+ * FusionForge 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 FusionForge; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+require_once $gfcommon.'docman/DocumentVersion.class.php';
+require_once $gfcommon.'docman/DocumentVersionFactory.class.php';
+require_once $gfcommon.'docman/include/constants.php';
+
+class DocumentReview extends FFError {
+ /**
+ * The Document object.
+ *
+ * @var object $Document.
+ */
+ var $Document;
+
+ /**
+ * The data values
+ *
+ * @var array $data_array
+ */
+ var $data_array = array();
+
+ var $version = null;
+ var $serialid = null;
+
+ function __construct(&$Document, $revid = false, $arr = false) {
+ parent::__construct();
+ if (!$Document || !is_object($Document)) {
+ $this->setError(_('No Valid Document Object'));
+ return false;
+ }
+ if ($Document->isError()) {
+ $this->setError(_('Document')._(':
').$Document->getErrorMessage());
+ return false;
+ }
+ $this->Document =& $Document;
+ if ($revid) {
+ $this->fetchData($revid);
+ }
+ return true;
+ }
+
+ function fetchData($revid) {
+ $res = db_query_params('SELECT revid, created_by,
doc_review.statusid as statusid, startdate, enddate, title,
doc_review.description, doc_review_status.name as statusname
+ FROM doc_review, doc_review_status
WHERE doc_review.statusid = doc_review_status.statusid AND doc_review.revid =
$1', array($revid));
+ $this->data_array = db_fetch_array($res);
+ $this->getVersion();
+ }
+
+ function getID() {
+ return $this->data_array['revid'];
+ }
+
+ function getTitle() {
+ return $this->data_array['title'];
+ }
+
+ function getDescription() {
+ return $this->data_array['description'];
+ }
+
+ function getStatusID() {
+ return $this->data_array['statusid'];
+ }
+
+ function getStatusName() {
+ return $this->data_array['statusname'];
+ }
+
+ function getCreatedBy() {
+ return $this->data_array['created_by'];
+ }
+
+ function getEnddate() {
+ return $this->data_array['enddate'];
+ }
+
+ function getUsers($statusid = array(), $type = false) {
+ $qpa = db_construct_qpa(false, 'SELECT * FROM doc_review_users
WHERE revid = $1', array($this->getID()));
+ if ($statusid && is_array($statusid)) {
+ $qpa = db_construct_qpa($qpa, ' AND statusid = ANY
($1)', array(db_int_array_to_any_clause($statusid)));
+ }
+ if ($type) {
+ $qpa = db_construct_qpa($qpa, ' AND typeid = $1',
array($type));
+ }
+ $res = db_query_qpa($qpa);
+ $users = array();
+ if ($res && (db_numrows($res) > 0)) {
+ while ($arr = db_fetch_array($res)) {
+ $users[] = $arr;
+ }
+ }
+ return $users;
+ }
+
+ function getMandatoryUsers() {
+ return $this->getUsers(false, 1);
+ }
+
+ function getOptionalUsers() {
+ return $this->getUsers(false, 2);
+ }
+
+ function getStatusIcon() {
+ global $HTML;
+ switch ($this->getStatusID()) {
+ case 1:
+ $img = $HTML->getOpenTicketPic(_('Open'),
_('Open'));
+ break;
+ case 2:
+ $img = $HTML->getClosedTicketPic(_('Closed'),
_('Closed'));
+ break;
+ default:
+ $img = $HTML->getErrorPic(_('On error'), _('On
error'));
+ break;
+ }
+ return $img;
+ }
+
+ function getCreateByRealNameLink() {
+ $user = user_get_object($this->getCreatedBy());
+ if (is_object($user) && !$user->isError()) {
+ return util_display_user($user->getUnixName(),
$user->getID(), $user->getRealName());
+ }
+ return _('Unknown user');
+ }
+
+ function getVersion() {
+ if (isset($this->version) && $this->version) {
+ return $this-version;
+ }
+ $res = db_query_params('SELECT version FROM doc_data_version,
doc_review_version WHERE doc_data_version.serial_id =
doc_review_version.serialid AND doc_review_version.revid = $1',
+ array($this->getID()));
+ if ($res) {
+ $this->version = db_result($res, 0, 0);
+ return $this->version;
+ } else {
+ return $this->setError(db_error());
+ }
+ }
+
+ function getSerialID() {
+ if (isset($this->serialid) && $this->serialid) {
+ return $this->serialid;
+ }
+ $res = db_query_params('SELECT serialid FROM doc_review_version
WHERE revid = $1', array($this->getID()));
+ if ($res) {
+ $this->serialid = db_result($res, 0, 0);
+ return $this->serialid;
+ } else {
+ return $this->setError(db_error());
+ }
+ }
+
+
+ function getDeleteAction() {
+ global $HTML;
+ return util_make_link('#', $HTML->getRemovePic(_('Permanently
delete this review'), 'delreview'), array('id' => 'review_action_delete',
'onclick' => 'javascript:controllerListFile.deleteReview({review:
'.$this->getID().'})'), true);
+ }
+
+ function getEditAction() {
+ global $HTML;
+ $enddate = strftime(_('%Y-%m-%d'), $this->getEnddate());
+ $users = $this->getUsers(array(1, 2));
+ $mandatoryUsers = array();
+ $optionalUsers = array();
+ foreach ($users as $user) {
+ if ($user['typeid'] == 1) {
+ $mandatoryUsers[] = $user['userid'];
+ } else {
+ $optionalUsers[] = $user['userid'];
+ }
+ }
+ return util_make_link('#', $HTML->getConfigurePic(_('Edit this
review'), 'editreview'),
+ array('id' => 'review_action_edit',
'onclick' => 'javascript:controllerListFile.toggleEditReviewView({review:
'.$this->getID().', title: \''.addslashes($this->getTitle()).'\',
+
description:
\''.addslashes($this->getDescription()).'\',
+
endreviewdate:
\''.util_html_encode($enddate).'\',
+
serialid:
'.$this->getSerialID().',
+
mandatoryusers:
'.json_encode($mandatoryUsers).',
+
optionalusers:
'.json_encode($optionalUsers).',})'), true);
+ }
+
+ function getReminderAction() {
+ global $HTML;
+ return util_make_link('#', $HTML->getMailNotifyPic(_('Send
reminder to pending reviewers'), 'reminderreview'), array('id' =>
'review_action_reminder', 'onclick' =>
'javascript:controllerListFile.reminderReview({review: '.$this->getID().'})'),
true);
+ }
+
+ function getCompleteAction() {
+ global $HTML;
+ return util_make_link('#',
$HTML->getClosedTicketPic(_('Complete this review'), 'completereview'),
array('id' => 'review_action_complete', 'onclick' =>
'javascript:controllerListFile.toggleCompleteReviewView({review:
'.$this->getID().'})'), true);
+ }
+
+ function getCommentAction() {
+ global $HTML;
+ return util_make_link('#', $HTML->getEditFilePic(_('Comment the
review'), 'remindercomment'), array('id' => 'review_action_comment', 'onclick'
=> 'javascript:controllerListFile.toggleCommentReviewView({review:
'.$this->getID().'})'), true);
+ }
+
+ function showCreateFormHTML() {
+ global $HTML;
+ $dvf = new DocumentVersionFactory($this->Document);
+ $return = '';
+ if (is_object($dvf)) {
+ $userObjects = $this->Document->Group->getUsers();
+ $userNameArray = array();
+ $userIDArray = array();
+ foreach ($userObjects as $userObject) {
+ if (forge_check_perm_for_user($userObject,
'docman', $this->Document->Group->getID(), 'approve')) {
+ $userNameArray[] =
$userObject->getRealName();
+ $userIDArray[] = $userObject->getID();
+ }
+ }
+ $date_format_js = _('yy-mm-dd');
+ $return = html_ao('div', array('style' => 'display:
none;', 'id' => 'editfile-createreview'));
+ $return .= $HTML->listTableTop();
+ $cells = array();
+ $cells[] =
array(_('Title').utils_requiredField()._(':'), 'style' => 'width: 30%;');
+ $cells[][] = html_e('input', array('type' => 'text',
'id' => 'review-title', 'name' => 'review-title', 'style' => 'width: 100%;
box-sizing: border-box;', 'required' => 'required', 'pattern' => '.{5,}',
'placeholder' => _('Title').' '.sprintf(_('(at least %s characters)'),
DOCMAN__REVIEW_TITLE_MIN_SIZE), 'maxlength' => DOCMAN__REVIEW_TITLE_MAX_SIZE));
+ $return .= $HTML->multiTableRow(array(), $cells);
+ $cells = array();
+ $cells[][] =
_('Description').utils_requiredField()._(':');
+ $cells[][] = html_e('textarea', array('id' =>
'review-description', 'name' => 'review-description', 'style' => 'width: 100%;
box-sizing: border-box;', 'rows' => 3, 'required' => 'required', 'pattern' =>
'.{10,}', 'placeholder' => _('Description').' '.sprintf(_('(at least %s
characters)'), DOCMAN__REVIEW_DESCRIPTION_MIN_SIZE), 'maxlength' =>
DOCMAN__REVIEW_DESCRIPTION_MAX_SIZE), '', false);
+ $return .= $HTML->multiTableRow(array(), $cells);
+ $cells = array();
+ $cells[][] = _('Select Version to
review').utils_requiredField()._(':');
+ $cells[][] =
html_build_select_box($dvf->getDBResVersionSerialIDs(), 'review-serialid',
false, false, '', false, '', false, array('id' => 'review-serialid'));
+ $return .= $HTML->multiTableRow(array(), $cells);
+ $cells = array();
+ $cells[][] = _('Select End date of this
review').utils_requiredField()._(':');
+ $cells[][] = html_e('input', array('id' =>
'datepicker_end_review_date', 'name' => 'review-enddate', 'size' => 10,
'maxlength' => 10, 'required' => 'required'));
+ $return .= $HTML->multiTableRow(array(), $cells);
+ $cells = array();
+ $cells[][] =_('Add mandatory
reviewers').utils_requiredField()._(':');
+ $cells[][] = html_e('p', array(),
html_build_multiple_select_box_from_arrays($userIDArray, $userNameArray,
'review-select-mandatory-users[]', array(), 8, false, 'none', false, array('id'
=> 'review-select-mandatory-users')));
+ $return .= $HTML->multiTableRow(array(), $cells);
+ $cells = array();
+ $cells[][] = _('Add optional reviewers')._(':');
+ $cells[][] = html_e('p', array(),
html_build_multiple_select_box_from_arrays($userIDArray, $userNameArray,
'review-select-optional-users[]', array(), 8, false, 'none', false, array('id'
=> 'review-select-optional-users')));
+ $return .= $HTML->multiTableRow(array(), $cells);
+ $return .= $HTML->listTableBottom();
+ $return .= $HTML->addRequiredFieldsInfoBox();
+ $return .= html_e('input', array('type' => 'hidden',
'id' => 'new_review', 'name' => 'new_review', 'value' => 0));
+ $return .= html_e('input', array('type' => 'hidden',
'id' => 'review_id', 'name' => 'review_id', 'value' => 0));
+ $return .= html_ac(html_ap() -1);
+ $javascript =
'jQuery("#datepicker_end_review_date").datepicker({dateFormat:
"'.$date_format_js.'"});';
+ $return .= html_e('script', array(
'type'=>'text/javascript'), '//<![CDATA['."\n".$javascript."\n".'//]]>');
+ } else {
+ $return = $HTML->error_msg(_('Cannot get Document
Versions'));
+ }
+ return $return;
+ }
+
+ function create($reviewversionserialid, $reviewtitle,
$reviewdescription, $reviewenddate, $reviewmandatoryusers, $reviewoptionalusers
= array()) {
+ if (!is_int($reviewversionserialid) && $reviewversionserialid <
1) {
+ $this->setError(_('Missing Version ID to create
review'));
+ return false;
+ }
+ if (strlen($reviewtitle) < DOCMAN__REVIEW_TITLE_MIN_SIZE ||
strlen($reviewtitle) > DOCMAN__REVIEW_TITLE_MAX_SIZE) {
+ $this->setError(sprintf(_('Review Title must be %d
characters minimum and %d characters maximum'), DOCMAN__REVIEW_TITLE_MIN_SIZE,
DOCMAN__REVIEW_TITLE_MAX_SIZE));
+ return false;
+ }
+ if (strlen($reviewdescription) <
DOCMAN__REVIEW_DESCRIPTION_MIN_SIZE || strlen($reviewdescription) >
DOCMAN__REVIEW_DESCRIPTION_MAX_SIZE) {
+ $this->setError(sprintf(_('Review Description must be
%d characters minimum and %d characters maximum'),
DOCMAN__REVIEW_DESCRIPTION_MIN_SIZE, DOCMAN__REVIEW_DESCRIPTION_MAX_SIZE));
+ return false;
+ }
+ if ($reviewenddate < time()) {
+ $this->setError(_('Review End date is in the past.
Please set it the future'));
+ return false;
+ }
+ if ((is_array($reviewmandatoryusers) &&
count($reviewmandatoryusers) == 0) || (!is_array($reviewmandatoryusers))) {
+ $this->setError(_('Missing mandatory
reviewers').$reviewmandatoryusers);
+ return false;
+ }
+ if (!is_array($reviewoptionalusers)) {
+ $this->setError(_('Wrong parameter type for optional
reviewers'));
+ return false;
+ }
+
+ $user = session_get_user();
+ db_begin();
+ $res = db_query_params('INSERT INTO doc_review (created_by,
statusid, docid, startdate, enddate, title, description) VALUES ($1, $2, $3,
$4, $5, $6, $7)',
+ array($user->getID(), 1,
$this->Document->getID(), time(), $reviewenddate, $reviewtitle,
$reviewdescription));
+ if ($res) {
+ $notifyUsers = array();
+ $revid = db_insertid($res, 'doc_review', 'revid');
+ $this->fetchData($revid);
+ db_query_params('INSERT INTO doc_review_version (revid,
serialid) VALUES ($1, $2)', array($revid, $reviewversionserialid));
+ $args = array();
+ foreach ($reviewmandatoryusers as $reviewmandatoryuser)
{
+ $args[] = array($revid, $reviewmandatoryuser,
1, 1);
+ }
+ if (count($reviewoptionalusers) > 0) {
+ foreach ($reviewoptionalusers as
$reviewoptionaluser) {
+ $args[] = array($revid,
$reviewoptionaluser, 2, 1);
+ }
+ }
+ foreach ($args as $arg) {
+ db_query_params('INSERT INTO doc_review_users
(revid, userid, typeid, statusid) VALUES ($1, $2, $3, $4)', $arg);
+ $notifyUsers[] = $arg;
+
+ }
+ $this->sendNotice($notifyUsers, true);
+ db_commit();
+ return true;
+ } else {
+ db_rollback();
+ }
+ $this->setError(_('Unable to create review'));
+ return false;
+ }
+
+ /**
+ * sendNotice - Notifies users of review.
+ *
+ * @param array array of users where IDs to be notify is arr[1].
+ * @param boolean true = new review, false = reminder
+ * @return bool
+ */
+ function sendNotice($users, $new = false) {
+ if (count($users) > 0) {
+ $createdbyuser = user_get_object($this->getCreatedBy());
+ if ($new) {
+ $title = _('New review started');
+ } else {
+ $title = _('Review still open');
+ }
+ $subject =
'['.$this->Document->Group->getPublicName().'] '.$title.' '._('for the
document').' - '.$this->Document->getName().' - '._('version ID')._(':
').$this->getVersion();
+ $body = _('Project')._(':
').$this->Document->Group->getPublicName()."\n";
+ $body .= _('Folder')._(':
').$this->Document->getDocGroupName()."\n";
+ $body .= _('Document version')._(':
').$this->getVersion()."\n";
+ $dv = documentversion_get_object($this->getVersion(),
$this->Document->getID(), $this->Document->Group->getID());
+ $body .= _('Document version title')._(':
').$dv->getTitle()."\n";
+ $body .= _('Document version description')._(':
').util_unconvert_htmlspecialchars($dv->getDescription())."\n";
+ $body .= _('Review submitter')._(':
').$createdbyuser->getRealName().' ('.$createdbyuser->getUnixName().") \n";
+ $body .=
"\n\n-------------------------------------------------------\n".
+ _('Please review, visit')._(':').
+ "\n\n" .
util_make_url('/docman/?group_id='.$this->Document->Group->getID().'&view=listfile&dirid='.$this->Document->getDocGroupID().'&filedetailid='.$this->Document->getID());
+
+ foreach ($users as $user) {
+ $userObject = user_get_object($user[1]);
+ util_send_message($userObject->getEmail(),
$subject, $body, 'noreply@'.forge_get_config('web_host'), '', _('Docman'));
+ }
+ return true;
+ }
+ return false;
+ }
+
+ function sendDeleteNotice($users) {
+ if (count($users) > 0) {
+ $deletedbyuser = session_get_user();
+ $createdbyuser = user_get_object($this->getCreatedBy());
+ $subject =
'['.$this->Document->Group->getPublicName().'] '._('Review deleted for the
document').' - '.$this->Document->getName().' - '._('version ID')._(':
').$this->getVersion();
+ $body = _('Project')._(':
').$this->Document->Group->getPublicName()."\n";
+ $body .= _('Folder')._(':
').$this->Document->getDocGroupName()."\n";
+ $body .= _('Document version')._(':
').$this->getVersion()."\n";
+ $dv = documentversion_get_object($this->getVersion(),
$this->Document->getID(), $this->Document->Group->getID());
+ $body .= _('Document version title')._(':
').$dv->getTitle()."\n";
+ $body .= _('Document version description')._(':
').util_unconvert_htmlspecialchars($dv->getDescription())."\n";
+ $body .= _('Review submitter')._(':
').$createdbyuser->getRealName().' ('.$createdbyuser->getUnixName().") \n";
+ $body .=
"\n\n-------------------------------------------------------\n".
+ sprintf(_('This review ID %d has been deleted
by %s (%s)'), $this->getID(), $deletedbyuser->getRealName(),
$deletedbyuser->getUnixName());
+
+ foreach ($users as $user) {
+ $userObject = user_get_object($user[1]);
+ util_send_message($userObject->getEmail(),
$subject, $body, 'noreply@'.forge_get_config('web_host'), '', _('Docman'));
+ }
+ return true;
+ }
+ return false;
+ }
+
+ function getProgressbar() {
+ $doneMandatoryUsers = array();
+ $mandatoryUsers = $this->getMandatoryUsers();
+ foreach ($mandatoryUsers as $mandarotyUser) {
+ if ($mandarotyUser['statusid'] == 2) {
+ $doneMandatoryUsers[] = $mandarotyUser;
+ }
+ }
+ $percentDoneMandatoryUsers = ((count($doneMandatoryUsers) /
count($mandatoryUsers)) * 100).'%';
+ $doneOptionalUsers = array();
+ $optionalUsers = $this->getOptionalUsers();
+ foreach ($optionalUsers as $optionalUser) {
+ if ($optionalUser['statusid'] == 2) {
+ $doneOptionalUsers[] = $optionalUser;
+ }
+ }
+ if (count($optionalUsers) > 0) {
+ $percentDoneOptionalUsers = ((count($doneOptionalUsers)
/ count($optionalUsers)) * 100).'%';
+ } else {
+ $percentDoneOptionalUsers = _('n/a');
+ }
+ return html_e('span', array('title' => _('% of mandotary users
with status done - % of optional users with status done')),
$percentDoneMandatoryUsers.' - '.$percentDoneOptionalUsers);
+ }
+
+ function delete() {
+ $users = $this->getUsers(array(1));
+ $res = db_query_params('DELETE FROM doc_review WHERE revid =
$1', array($this->getID()));
+ if ($res) {
+ if (count($users) > 0) {
+ $this->sendDeleteNotice($users);
+ }
+ return true;
+ }
+ $this->setError(db_error());
+ return false;
+ }
+
+ function update($reviewversionserialid, $reviewtitle,
$reviewdescription, $reviewenddate, $reviewmandatoryusers, $reviewoptionalusers
= array()) {
+ if (!is_int($reviewversionserialid) && $reviewversionserialid <
1) {
+ $this->setError(_('Missing Version ID to create
review'));
+ return false;
+ }
+ if (strlen($reviewtitle) < DOCMAN__REVIEW_TITLE_MIN_SIZE ||
strlen($reviewtitle) > DOCMAN__REVIEW_TITLE_MAX_SIZE) {
+ $this->setError(sprintf(_('Review Title must be %d
characters minimum and %d characters maximum'), DOCMAN__REVIEW_TITLE_MIN_SIZE,
DOCMAN__REVIEW_TITLE_MAX_SIZE));
+ return false;
+ }
+ if (strlen($reviewdescription) <
DOCMAN__REVIEW_DESCRIPTION_MIN_SIZE || strlen($reviewdescription) >
DOCMAN__REVIEW_DESCRIPTION_MAX_SIZE) {
+ $this->setError(sprintf(_('Review Description must be
%d characters minimum and %d characters maximum'),
DOCMAN__REVIEW_DESCRIPTION_MIN_SIZE, DOCMAN__REVIEW_DESCRIPTION_MAX_SIZE));
+ return false;
+ }
+ if ($reviewenddate < time()) {
+ $this->setError(_('Review End date is in the past.
Please set it the future'));
+ return false;
+ }
+ if ((is_array($reviewmandatoryusers) &&
count($reviewmandatoryusers) == 0) || (!is_array($reviewmandatoryusers))) {
+ $this->setError(_('Missing mandatory
reviewers').$reviewmandatoryusers);
+ return false;
+ }
+ if (!is_array($reviewoptionalusers)) {
+ $this->setError(_('Wrong parameter type for optional
reviewers'));
+ return false;
+ }
+
+ db_begin();
+ $res = db_query_params('UPDATE doc_review SET (enddate, title,
description) = ($1, $2, $3) WHERE revid = $4', array($reviewenddate,
$reviewtitle, $reviewdescription, $this->getID()));
+ if ($res) {
+ if ($reviewversionserialid != $this->getSerialID()) {
+ db_query_params('UPDATE doc_review_version SET
serialid = $1 WHERE revid = $2', array($reviewversionserialid, $this->getID()));
+ }
+ $mandatoryUsers = $this->getMandatoryUsers();
+ $mandarotyUserIDs = array();
+ foreach ($mandatoryUsers as $mandatoryUser) {
+ $mandarotyUserIDs[] = $mandatoryUser['userid'];
+ }
+ $optionalUsers = $this->getOptionalUsers();
+ $optionalUserIDs = array();
+ foreach ($optionalUsers as $optionalUser) {
+ $optionalUserIDs[] = $optionalUser['userid'];
+ }
+ foreach ($reviewmandatoryusers as $reviewmandatoryuser)
{
+ if (in_array($reviewmandatoryuser,
$mandarotyUserIDs)) {
+
unset($mandarotyUserIDs[array_search($reviewmandatoryuser, $mandarotyUserIDs)]);
+ var_dump($mandarotyUserIDs);
+ } elseif (in_array($reviewmandatoryuser,
$optionalUserIDs)) {
+ db_query_params('UPDATE
doc_review_users SET typeid = $1 WHERE userid = $2 AND revid = $3', array(1,
$reviewmandatoryuser, $this->getID()));
+
unset($optionalUserIDs[array_search($reviewmandatoryuser, $optionalUserIDs)]);
+ } else {
+ db_query_params('INSERT INTO
doc_review_users (revid, userid, typeid, statusid) VALUES ($1, $2, $3, $4)',
array($this->getID(), $reviewmandatoryuser, 1, 1));
+ }
+ }
+ foreach ($reviewoptionalusers as $reviewoptionaluser) {
+ if (in_array($reviewoptionaluser,
$mandarotyUserIDs)) {
+ db_query_params('UPDATE
doc_review_users SET typeid = $1 WHERE userid = $2 AND revid = $3', array(2,
$reviewoptionaluser, $this->getID()));
+
unset($mandarotyUserIDs[array_search($reviewoptionaluser, $mandarotyUserIDs)]);
+ } elseif (in_array($reviewoptionaluser,
$optionalUserIDs)) {
+
unset($optionalUserIDs[array_search($reviewoptionaluser, $optionalUserIDs)]);
+ } else {
+ db_query_params('INSERT INTO
doc_review_users (revid, userid, typeid, statusid) VALUES ($1, $2, $3, $4)',
array($this->getID(), $reviewoptionaluser, 2, 1));
+ }
+ }
+ foreach ($mandarotyUserIDs as $mandarotyUserID) {
+ db_query_params('DELETE from doc_review_users
WHERE userid = $1 AND revid = $2', array($mandarotyUserID, $this->getID()));
+ }
+ foreach ($optionalUserIDs as $optionalUserID) {
+ db_query_params('DELETE from doc_review_users
WHERE userid = $1 AND revid = $2', array($optionalUserID, $this->getID()));
+ }
+ db_commit();
+ return true;
+ }
+ db_rollback();
+ $this->setError(db_error());
+ return false;
+ }
+
+ function getNbComments() {
+ $res = db_query_params('SELECT COUNT(commentid) FROM
doc_review_comments WHERE revid = $1', array($this->getID()));
+ if ($res) {
+ return db_result($res, 0, 0);
+ }
+ return null;
+ }
+
+ function getComments() {
+ return array();
+ }
+
+ function isCompleted() {
+ if ($this->getStatusID() == 2) {
+ return true;
+ } else {
+ return false;
+ }
+ }
+}
diff --git a/src/common/docman/DocumentReviewFactory.class.php
b/src/common/docman/DocumentReviewFactory.class.php
new file mode 100644
index 0000000..b825b43
--- /dev/null
+++ b/src/common/docman/DocumentReviewFactory.class.php
@@ -0,0 +1,123 @@
+<?php
+/**
+ * FusionForge Documentation Manager
+ *
+ * Copyright 2016, Franck Villaume - TrivialDev
+ * http://fusionforge.org
+ *
+ * This file is part of FusionForge. FusionForge 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 Licence, or (at your option)
+ * any later version.
+ *
+ * FusionForge 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 FusionForge; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+class DocumentReviewFactory extends FFError {
+ /**
+ * The Document object.
+ *
+ * @var object $Document
+ */
+ var $Document;
+
+ /**
+ * @var array $reviews Reviews of this document
+ */
+ var $reviews;
+
+ /**
+ * @param $Document
+ * @internal param \The $object Document object to which
this review factory is associated.
+ */
+ function __construct(&$Document) {
+ parent::__construct();
+ if (!$Document || !is_object($Document)) {
+ $this->setError(_('No Valid Document Object'));
+ return false;
+ }
+ if ($Document->isError()) {
+ $this->setError(_('Document')._(':
').$Document->getErrorMessage());
+ return false;
+ }
+ $this->Document =& $Document;
+ return true;
+ }
+
+ function getReviews($serialids = array()) {
+ $res = db_query_params('SELECT doc_review.revid as revid,
created_by, statusid, docid, startdate, enddate, title, description,
doc_review_version.serialid as serialid FROM doc_review, doc_review_version
+ WHERE doc_review.revid =
doc_review_version.revid AND doc_review_version.serialid = ANY ($1) AND
doc_review.docid = $2 ORDER BY enddate DESC',
+
array(db_int_array_to_any_clause($serialids), $this->Document->getID()));
+ if ($res) {
+ while ($arr = db_fetch_array($res)) {
+ $serialid = $arr['serialid'];
+ $this->reviews[] = $arr;
+ }
+ }
+ db_free_result($res);
+ return $this->reviews;
+ }
+
+ function getReviewsHTML($serialids = array()) {
+ global $HTML;
+ $return = '';
+ $this->getReviews($serialids);
+ if ($this->getReviewsCounter() > 0) {
+ $titleArr = array('ID', _('Version'), _('Title'),
_('Created By'), _('Status'), _('End date'), _('Progress'), _('Comments'),
_('Actions'));
+ $classth = array('', '', '', '', '', 'unsortable');
+ $return .= $HTML->listTableTop($titleArr, array(),
'full sortable', 'sortable_docman_listreview', $classth);
+ foreach ($this->reviews as $thereview) {
+ $dr = new DocumentReview($this->Document,
$thereview[0]);
+ $cells = array();
+ $cells[][] = $thereview[0];
+ $cells[] = array($dr->getVersion(), 'id' =>
'docversionreview'.$dr->getVersion());
+ $cells[] = array($dr->getTitle(), 'title' =>
$dr->getDescription());
+ $cells[][] = $dr->getCreateByRealNameLink();
+ $cells[][] = $dr->getStatusIcon();
+ $overdue = '';
+ if (time() > $dr->getEnddate()) {
+ $overdue = $HTML->getErrorPic(_('Review
overdue'), 'overdue');
+ }
+ $cells[][] = strftime(_('%Y-%m-%d'),
$dr->getEnddate()).$overdue;
+ $cells[][] = $dr->getProgressbar();
+ $cells[][] = $dr->getNbComments();
+ $actions = '';
+ $user = session_get_user();
+ $users = $dr->getUsers(array(1, 2));
+ if ($user->getID() == $dr->getCreatedBy()) {
+ $actions .=
$dr->getReminderAction().$dr->getEditAction();
+ if ($dr->isCompleted()) {
+ $actions .=
$dr->getCompleteAction();
+ }
+ }
+ if (($dr->getStatusID() == 1) &&
(($user->getID() == $dr->getCreatedBy()) || in_array($user->getID(), $users))) {
+ $actions .= $dr->getCommentAction();
+ }
+ if ($user->getID() == $dr->getCreatedBy()) {
+ $actions .= $dr->getDeleteAction();
+ }
+
+ $cells[][] = $actions;
+ $return .= $HTML->multiTableRow(array('id' =>
'docreview'.$thereview[0]), $cells);
+ }
+ $return .= $HTML->listTableBottom();
+ } else {
+ $return = $HTML->information(_('No Reviews.'));
+ }
+ $return .= html_e('button', array('id' =>
'doc_review_addbutton', 'type' => 'button', 'onclick' =>
'javascript:controllerListFile.toggleAddReviewView()'), _('Add new review'));
+ return $return;
+ }
+
+
+ function getReviewsCounter() {
+ return count($this->reviews);
+ }
+}
diff --git a/src/common/docman/actions/deletereview.php
b/src/common/docman/actions/deletereview.php
new file mode 100644
index 0000000..dfe54fc
--- /dev/null
+++ b/src/common/docman/actions/deletereview.php
@@ -0,0 +1,65 @@
+<?php
+/**
+ * FusionForge Documentation Manager
+ *
+ * Copyright 2016, Franck Villaume - TrivialDev
+ * http://fusionforge.org
+ *
+ * This file is part of FusionForge. FusionForge 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 Licence, or (at your option)
+ * any later version.
+ *
+ * FusionForge 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 FusionForge; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+/* please do not add require here : use www/docman/index.php to add require */
+/* global variables used */
+global $g; // Group object
+global $group_id; // id of group
+global $HTML;
+
+$sysdebug_enable = false;
+$result = array();
+$result['status'] = 0;
+
+if (!forge_check_perm('docman', $group_id, 'approve')) {
+ $result['html'] = $HTML->error_msg(_('Document Manager Action
Denied.'));
+ echo json_encode($result);
+ exit;
+}
+
+$docid = getIntFromRequest('docid');
+$review = getIntFromRequest('review');
+
+if ($docid && $review) {
+ $documentObject = document_get_object($docid, $group_id);
+ if ($documentObject && !$documentObject->isError()) {
+ $dr = new DocumentReview($documentObject, $review);
+ if ($dr && !$dr->isError()) {
+ if ($dr->delete()) {
+ $result['html'] = $HTML->feedback(_('Review
deleted successfully.'));
+ $result['status'] = 1;
+ } else {
+ $result['html'] = $HTML->error_msg(_('Cannot
delete review ID')._(': ').$review.' '.$dr->getErrorMessage());
+ }
+ } else {
+ $result['html'] = $HTML->error_msg(_('Cannot create
object documentreview'));
+ }
+ } else {
+ $result['html'] = $HTML->error_msg(_('Cannot retrieve
document')._(': ').$docid);
+ }
+} else {
+ $result['html'] = $HTML->warning_msg(_('No document ID. Cannot retrieve
review.'));
+}
+
+echo json_encode($result);
+exit;
diff --git a/src/common/docman/actions/editfile.php
b/src/common/docman/actions/editfile.php
index f73827a..3265421 100644
--- a/src/common/docman/actions/editfile.php
+++ b/src/common/docman/actions/editfile.php
@@ -40,145 +40,179 @@ if ($childgroup_id) {
$urlparam .= '&childgroup_id='.$childgroup_id;
}
-$doc_group = getIntFromRequest('doc_group');
-$fromview = getStringFromRequest('fromview');
-
-switch ($fromview) {
- case 'listrashfile': {
- $urlparam .= '&view='.$fromview;
- break;
- }
- default: {
- $urlparam .= '&dirid='.$doc_group;
- break;
- }
-}
-
if (!forge_check_perm('docman', $g->getID(), 'approve')) {
$warning_msg = _('Document Manager Action Denied.');
session_redirect($urlparam);
}
+$subaction = getStringFromRequest('subaction', 'version');
$docid = getIntFromRequest('docid');
-$title = getStringFromRequest('title');
-$description = getStringFromRequest('description');
-$vcomment = getStringFromRequest('vcomment');
-$details = getStringFromRequest('details');
-$file_url = getStringFromRequest('file_url');
-$uploaded_data = getUploadedFile('uploaded_data');
-$stateid = getIntFromRequest('stateid');
-$filetype = getStringFromRequest('filetype');
-$editor = getStringFromRequest('editor');
-$current_version_radio = getIntFromRequest('doc_version_cv_radio');
-$current_version = getIntFromRequest('current_version', 0);
-$version = getIntFromRequest('edit_version', 0);
-$new_version = getIntFromRequest('new_version', 0);
-$newobjectsassociation = getStringFromRequest('newobjectsassociation');
-
if (!$docid) {
$warning_msg = _('No document found to update');
session_redirect($urlparam);
}
-
$d = document_get_object($docid, $g->getID());
if ($d->isError()) {
$error_msg = $d->getErrorMessage();
session_redirect($urlparam);
}
-$sanitizer = new TextSanitizer();
-$details = $sanitizer->SanitizeHtml($details);
-$data = '';
+$doc_group = getIntFromRequest('doc_group');
+$fromview = getStringFromRequest('fromview');
-if ($version) {
- $dv = documentversion_get_object($version, $docid, $group_id);
- if (($editor) && ($dv->getFileData() != $details) &&
(!$uploaded_data['name'])) {
- $filename = $dv->getFileName();
- $datafile = tempnam('/tmp', 'docman');
- $fh = fopen($datafile, 'w');
- fwrite($fh, $details);
- fclose($fh);
- $data = $datafile;
- if (!$filetype)
- $filetype = $dv->getFileType();
+switch ($fromview) {
+ case 'listrashfile': {
+ $urlparam .= '&view='.$fromview;
+ break;
+ }
+ default: {
+ $urlparam .= '&dirid='.$doc_group;
+ break;
+ }
+}
- } elseif (!empty($uploaded_data) && $uploaded_data['name']) {
- if (!is_uploaded_file($uploaded_data['tmp_name'])) {
- $error_msg = sprintf(_('Invalid file attack attempt
%s.'), $uploaded_data['name']);
+switch ($subaction) {
+ case 'version':
+ $title = getStringFromRequest('title');
+ $description = getStringFromRequest('description');
+ $vcomment = getStringFromRequest('vcomment');
+ $details = getStringFromRequest('details');
+ $file_url = getStringFromRequest('file_url');
+ $uploaded_data = getUploadedFile('uploaded_data');
+ $stateid = getIntFromRequest('stateid');
+ $filetype = getStringFromRequest('filetype');
+ $editor = getStringFromRequest('editor');
+ $current_version_radio =
getIntFromRequest('doc_version_cv_radio');
+ $current_version = getIntFromRequest('current_version', 0);
+ $version = getIntFromRequest('edit_version', 0);
+ $new_version = getIntFromRequest('new_version', 0);
+ $sanitizer = new TextSanitizer();
+ $details = $sanitizer->SanitizeHtml($details);
+ $data = '';
+
+ if ($version) {
+ $dv = documentversion_get_object($version, $docid,
$group_id);
+ if (($editor) && ($dv->getFileData() != $details) &&
(!$uploaded_data['name'])) {
+ $filename = $dv->getFileName();
+ $datafile = tempnam('/tmp', 'docman');
+ $fh = fopen($datafile, 'w');
+ fwrite($fh, $details);
+ fclose($fh);
+ $data = $datafile;
+ if (!$filetype) {
+ $filetype = $dv->getFileType();
+ }
+ } elseif (!empty($uploaded_data) &&
$uploaded_data['name']) {
+ if
(!is_uploaded_file($uploaded_data['tmp_name'])) {
+ $error_msg = sprintf(_('Invalid file
attack attempt %s.'), $uploaded_data['name']);
+ session_redirect($urlparam);
+ }
+ $data = $uploaded_data['tmp_name'];
+ $filename = $uploaded_data['name'];
+ if (function_exists('finfo_open')) {
+ $finfo = finfo_open(FILEINFO_MIME_TYPE);
+ $filetype = finfo_file($finfo,
$uploaded_data['tmp_name']);
+ } else {
+ $filetype = $uploaded_data['type'];
+ }
+ } elseif ($file_url) {
+ $filename = $file_url;
+ $filetype = 'URL';
+ } else {
+ $filename = $dv->getFileName();
+ $filetype = $dv->getFileType();
+ }
+ } elseif ($new_version) {
+ if ($editor && $details && $name) {
+ $filename = $name;
+ $datafile = tempnam('/tmp', 'docman');
+ $fh = fopen($datafile, 'w');
+ fwrite($fh, $details);
+ fclose($fh);
+ $data = $datafile;
+ if (!$filetype) {
+ $filetype = 'text/html';
+ }
+ } elseif (!empty($uploaded_data) &&
$uploaded_data['name']) {
+ if
(!is_uploaded_file($uploaded_data['tmp_name'])) {
+ $error_msg = sprintf(_('Invalid file
attack attempt %s.'), $uploaded_data['name']);
+ session_redirect($urlparam);
+ }
+ $data = $uploaded_data['tmp_name'];
+ $filename = $uploaded_data['name'];
+ if (function_exists('finfo_open')) {
+ $finfo = finfo_open(FILEINFO_MIME_TYPE);
+ $filetype = finfo_file($finfo,
$uploaded_data['tmp_name']);
+ } else {
+ $filetype = $uploaded_data['type'];
+ }
+ } elseif ($file_url) {
+ $filename = $file_url;
+ $filetype = 'URL';
+ }
+ } elseif (($d->getDocGroupID() != $doc_group) ||
($d->getStateID() != $stateid)) {
+ // we do the update based on the current version.
+ if (!$current_version_radio) {
+ $current_version_radio = $d->getVersion();
+ }
+ $dv =
documentversion_get_object($current_version_radio, $docid, $group_id);
+ $filename = $dv->getFileName();
+ $filetype = $dv->getFileType();
+ $title = $dv->getTitle();
+ $description = $dv->getDescription();
+ $vcomment = $dv->getComment();
+ $version = $current_version_radio;
+ $current_version = 1;
+ } else {
+ $warning_msg = _('No action to perform');
session_redirect($urlparam);
}
- $data = $uploaded_data['tmp_name'];
- $filename = $uploaded_data['name'];
- if (function_exists('finfo_open')) {
- $finfo = finfo_open(FILEINFO_MIME_TYPE);
- $filetype = finfo_file($finfo,
$uploaded_data['tmp_name']);
+
+ if (!$d->update($filename, $filetype, $data, $doc_group,
$title, $description, $stateid, $version, $current_version, $new_version, null,
$vcomment)) {
+ $error_msg = $d->getErrorMessage();
} else {
- $filetype = $uploaded_data['type'];
+ $feedback = sprintf(_('Document [D%s] updated
successfully.'), $d->getID());
}
- } elseif ($file_url) {
- $filename = $file_url;
- $filetype = 'URL';
- } else {
- $filename = $dv->getFileName();
- $filetype = $dv->getFileType();
- }
-} elseif ($new_version) {
- if ($editor && $details && $name) {
- $filename = $name;
- $datafile = tempnam('/tmp', 'docman');
- $fh = fopen($datafile, 'w');
- fwrite($fh, $details);
- fclose($fh);
- $data = $datafile;
- if (!$filetype)
- $filetype = 'text/html';
-
- } elseif (!empty($uploaded_data) && $uploaded_data['name']) {
- if (!is_uploaded_file($uploaded_data['tmp_name'])) {
- $error_msg = sprintf(_('Invalid file attack attempt
%s.'), $uploaded_data['name']);
- session_redirect($urlparam);
+ break;
+ case 'association':
+ $newobjectsassociation =
getStringFromRequest('newobjectsassociation');
+ if (!$d->addAssociations($newobjectsassociation)) {
+ $error_msg = $d->getErrorMessage();
+ } else {
+ $feedback = sprintf(_('Document [D%s] updated
successfully.'), $d->getID());
}
- $data = $uploaded_data['tmp_name'];
- $filename = $uploaded_data['name'];
- if (function_exists('finfo_open')) {
- $finfo = finfo_open(FILEINFO_MIME_TYPE);
- $filetype = finfo_file($finfo,
$uploaded_data['tmp_name']);
+ break;
+ case 'review':
+ $reviewtitle = getStringFromRequest('review-title');
+ $reviewdescription = getStringFromRequest('review-description');
+ $reviewversionserialid = getIntFromRequest('review-serialid',
null);
+ $reviewenddateraw = getStringFromRequest('review-enddate');
+ $date_format = _('%Y-%m-%d');
+ $tmp = strptime($reviewenddateraw, $date_format);
+ $reviewenddate = mktime(0, 0, 0, $tmp['tm_mon']+1,
$tmp['tm_mday'], $tmp['tm_year'] + 1900);
+ $reviewmandatoryusers =
getArrayFromRequest('review-select-mandatory-users', array());
+ $reviewoptionalusers =
getArrayFromRequest('review-select-optional-users', array());
+ $new_review = getIntFromRequest('new_review');
+ $reviewid = getIntFromRequest('review_id');
+ if ($reviewversionserialid) {
+ if ($new_review) {
+ $dr = new DocumentReview($d);
+ if ($dr->create($reviewversionserialid,
$reviewtitle, $reviewdescription, $reviewenddate, $reviewmandatoryusers,
$reviewoptionalusers)) {
+ $feedback = _('Review created');
+ } else {
+ $error_msg = $dr->getErrorMessage();
+ }
+ } else {
+ $dr = new DocumentReview($d, $reviewid);
+ if ($dr->update($reviewversionserialid,
$reviewtitle, $reviewdescription, $reviewenddate, $reviewmandatoryusers,
$reviewoptionalusers)) {
+ $feedback = _('Review updated');
+ } else {
+ $error_msg = $dr->getErrorMessage();
+ }
+ }
} else {
- $filetype = $uploaded_data['type'];
+ $warning_msg = _('Missing version to create review');
}
- } elseif ($file_url) {
- $filename = $file_url;
- $filetype = 'URL';
- }
-} elseif (($d->getDocGroupID() != $doc_group) || ($d->getStateID() !=
$stateid)) {
- // we do the update based on the current version.
- if (!$current_version_radio) {
- $current_version_radio = $d->getVersion();
- }
- $dv = documentversion_get_object($current_version_radio, $docid,
$group_id);
- $filename = $dv->getFileName();
- $filetype = $dv->getFileType();
- $title = $dv->getTitle();
- $description = $dv->getDescription();
- $vcomment = $dv->getComment();
- $version = $current_version_radio;
- $current_version = 1;
-} elseif ($newobjectsassociation) {
- if (!$d->addAssociations($newobjectsassociation)) {
- $error_msg = $d->getErrorMessage();
- } else {
- $feedback = sprintf(_('Document [D%s] updated successfully.'),
$d->getID());
- }
- session_redirect($urlparam);
-} else {
- $warning_msg = _('No action to perform');
- session_redirect($urlparam);
-}
-
-if (!$d->update($filename, $filetype, $data, $doc_group, $title, $description,
$stateid, $version, $current_version, $new_version, null, $vcomment)) {
- $error_msg = $d->getErrorMessage();
- session_redirect($urlparam);
+ break;
}
-
-$feedback = sprintf(_('Document [D%s] updated successfully.'), $d->getID());
session_redirect($urlparam);
diff --git a/src/common/docman/actions/getdocreviews.php
b/src/common/docman/actions/getdocreviews.php
new file mode 100644
index 0000000..8286584
--- /dev/null
+++ b/src/common/docman/actions/getdocreviews.php
@@ -0,0 +1,61 @@
+<?php
+/**
+ * FusionForge Documentation Manager
+ *
+ * Copyright 2016, Franck Villaume - TrivialDev
+ * http://fusionforge.org
+ *
+ * This file is part of FusionForge. FusionForge 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 Licence, or (at your option)
+ * any later version.
+ *
+ * FusionForge 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 FusionForge; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+/* please do not add require here : use www/docman/index.php to add require */
+/* global variables used */
+global $group_id; // id of group
+global $HTML;
+
+$sysdebug_enable = false;
+$result = array();
+
+if (!forge_check_perm('docman', $group_id, 'approve')) {
+ $result['html'] = $HTML->error_msg(_('Document Manager Action
Denied.'));
+ echo json_encode($result);
+ exit;
+}
+
+$docid = getIntFromRequest('docid');
+if ($docid) {
+ $documentObject = document_get_object($docid, $group_id);
+ if ($documentObject && !$documentObject->isError()) {
+ $drf = new DocumentReviewFactory($documentObject);
+ $dvf = new DocumentVersionFactory($documentObject);
+ $dr = new DocumentReview($documentObject);
+ if ($drf && $dvf && $dr && !$drf->isError() && !$dvf->isError()
&& !$dr->isError()) {
+ $serialIDs = $dvf->getSerialIDs();
+ $result['html'] .= $drf->getReviewsHTML($serialIDs);
+ $result['html'] .= $dr->showCreateFormHTML();
+ $result['htmltab'] = _('Reviews').'
('.$drf->getReviewsCounter().')';
+ } else {
+ $result['html'] = $HTML->warning_msg(_('Cannot retrieve
reviews')._(': ').$docid);
+ }
+ } else {
+ $result['html'] = $HTML->warning_msg(_('Cannot retrieve
document')._(': ').$docid);
+ }
+} else {
+ $result['html'] = $HTML->warning_msg(_('No document ID. Cannot retrieve
reviews.'));
+}
+
+echo json_encode($result);
+exit;
diff --git a/src/common/docman/actions/reminderreview.php
b/src/common/docman/actions/reminderreview.php
new file mode 100644
index 0000000..55118cb
--- /dev/null
+++ b/src/common/docman/actions/reminderreview.php
@@ -0,0 +1,65 @@
+<?php
+/**
+ * FusionForge Documentation Manager
+ *
+ * Copyright 2016, Franck Villaume - TrivialDev
+ * http://fusionforge.org
+ *
+ * This file is part of FusionForge. FusionForge 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 Licence, or (at your option)
+ * any later version.
+ *
+ * FusionForge 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 FusionForge; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+/* please do not add require here : use www/docman/index.php to add require */
+/* global variables used */
+global $g; // Group object
+global $group_id; // id of group
+global $HTML;
+
+$sysdebug_enable = false;
+$result = array();
+$result['status'] = 0;
+
+if (!forge_check_perm('docman', $group_id, 'approve')) {
+ $result['html'] = $HTML->error_msg(_('Document Manager Action
Denied.'));
+ echo json_encode($result);
+ exit;
+}
+
+$docid = getIntFromRequest('docid');
+$review = getIntFromRequest('review');
+
+if ($docid && $review) {
+ $documentObject = document_get_object($docid, $group_id);
+ if ($documentObject && !$documentObject->isError()) {
+ $dr = new DocumentReview($documentObject, $review);
+ if ($dr && !$dr->isError()) {
+ $users = $dr->getUsers(array(1));
+ if ($dr->sendNotice($users)) {
+ $result['html'] = $HTML->feedback(_('Reminder
sent successfully.'));
+ } else {
+ $result['html'] = $HTML->error_msg(_('No
reminder sent for review ID')._(': ').$review);
+ }
+ } else {
+ $result['html'] = $HTML->error_msg(_('Cannot create
object documentreview'));
+ }
+ } else {
+ $result['html'] = $HTML->error_msg(_('Cannot retrieve
document')._(': ').$docid);
+ }
+} else {
+ $result['html'] = $HTML->warning_msg(_('No document ID. Cannot retrieve
review.'));
+}
+
+echo json_encode($result);
+exit;
diff --git a/src/common/docman/include/constants.php
b/src/common/docman/include/constants.php
index 7f9f0cb..36e030e 100644
--- a/src/common/docman/include/constants.php
+++ b/src/common/docman/include/constants.php
@@ -26,3 +26,7 @@ define('DOCMAN__DESCRIPTION_MIN_SIZE', 10);
define('DOCMAN__DESCRIPTION_MAX_SIZE', 255);
define('DOCMAN__COMMENT_MAX_SIZE', 255);
define('DOCMAN__INFAMOUS_USER_ID', 100);
+define('DOCMAN__REVIEW_TITLE_MIN_SIZE', 5);
+define('DOCMAN__REVIEW_DESCRIPTION_MIN_SIZE', 10);
+define('DOCMAN__REVIEW_TITLE_MAX_SIZE', 255);
+define('DOCMAN__REVIEW_DESCRIPTION_MAX_SIZE', 255);
diff --git a/src/common/docman/views/editfile.php
b/src/common/docman/views/editfile.php
index e641504..9b69399 100644
--- a/src/common/docman/views/editfile.php
+++ b/src/common/docman/views/editfile.php
@@ -49,7 +49,8 @@ jQuery(document).ready(function() {
buttonUrl: jQuery('#editButtonUrl'),
buttonManualUpload: jQuery('#editButtonManualUpload'),
buttonEditor: jQuery('#editButtonEditor'),
- divAssociation: jQuery('#tabbereditfile-association')
+ divAssociation: jQuery('#tabbereditfile-association'),
+ divReview: jQuery('#tabbereditfile-review')
});
});
@@ -67,14 +68,18 @@ $cells[] = array(_('State')._(':'), 'class' =>
'docman_editfile_title');
$cells[][] = html_e('select', array('name' => 'stateid', 'id' => 'stateid'),
'', false);
echo $HTML->multiTableRow(array(), $cells);
echo $HTML->listTableBottom();
+echo html_ao('div', array('id' => 'tabbereditfile'));
+$elementsLi = array();
+$elementsLi[] = array('content' => util_make_link('#tabbereditfile-version',
_('Versions'), array('id' => 'versiontab', 'title' => _('View/Add/Remove
document version.')), true));
+if (forge_get_config('use_docman_review')) {
+ $elementsLi[] = array('content' =>
util_make_link('#tabbereditfile-review', _('Reviews'), array('id' =>
'reviewtab', 'title' => _('View/Start/Comment document review.')), true));
+}
if (forge_get_config('use_object_associations')) {
- echo html_ao('div', array('id' => 'tabbereditfile'));
- $elementsLi = array();
- $elementsLi[] = array('content' =>
util_make_link('#tabbereditfile-version', _('Edit Versions'), array('title' =>
_('View/Add/Remove document version.')), true));
$elementsLi[] = array('content' =>
util_make_link('#tabbereditfile-association', _('Associations'), array('id' =>
'associationtab', 'title' => _('Add/Remove associated objects.')), true));
- echo $HTML->html_list($elementsLi);
- echo html_ao('div', array('id' => 'tabbereditfile-version', 'class' =>
'tabbertab'));
}
+echo $HTML->html_list($elementsLi);
+echo html_ao('div', array('id' => 'tabbereditfile-version', 'class' =>
'tabbertab'));
+
$thArr = array(_('ID (x)'), _('Filename'), _('Title'), _('Description'),
_('Comment'), _('Author'), _('Last Time'), _('Size'), _('Actions'));
$thTitle = array(_('x does mark the current version'), '', '', '', '', '', '',
'', '', '', '');
$thSizeCssArr = array(array('style' => 'width: 60px'), array('style' =>
'width: 150px'), array('style' => 'width: 150px'), array('style' => 'width:
150px'), array('style' => 'width: 110px'),
@@ -86,11 +91,11 @@ echo html_e('button', array('id' =>
'doc_version_addbutton', 'type' => 'button',
echo $HTML->listTableTop(array(), array(), 'listing full hide',
'doc_version_edit');
$cells = array();
$cells[] = array(_('Document Title').utils_requiredField()._(':'), 'class' =>
'docman_editfile_title');
-$cells[][] = html_e('input', array('pattern' => '.{5,}', 'title' =>
sprintf(_('(at least %s characters)'), 5), 'id' => 'title', 'type' => 'text',
'name' => 'title', 'size' => '40', 'maxlength' => '255'));
+$cells[][] = html_e('input', array('pattern' => '.{5,}', 'required' =>
'required', 'title' => sprintf(_('(at least %s characters)'), 5), 'id' =>
'title', 'type' => 'text', 'name' => 'title', 'size' => '40', 'maxlength' =>
'255'));
echo $HTML->multiTableRow(array(), $cells);
$cells = array();
$cells[] = array(_('Description').utils_requiredField()._(':'), 'class' =>
'docman_editfile_description');
-$cells[][] = html_e('textarea', array('pattern' => '.{10,}', 'title' =>
_('Editing tips:http,https or ftp: Hyperlinks. [#NNN]: Tracker id NNN. [TNNN]:
Task id NNN. [wiki:<pagename>]: Wiki page. [forum:<msg_id>]: Forum
post. [DNNN]: Document id NNN.').
+$cells[][] = html_e('textarea', array('pattern' => '.{10,}', 'required' =>
'required', 'title' => _('Editing tips:http,https or ftp: Hyperlinks. [#NNN]:
Tracker id NNN. [TNNN]: Task id NNN. [wiki:<pagename>]: Wiki page.
[forum:<msg_id>]: Forum post. [DNNN]: Document id NNN.').
sprintf(_('at least %s characters)'), 10), 'id' => 'description', 'name' =>
'description', 'maxlength' => '255', 'rows' => '5', 'cols' => '50'), '', false);
echo $HTML->multiTableRow(array(), $cells);
$cells = array();
@@ -151,19 +156,26 @@ $cells = array();
$cells[] = array(_('File')._(':'), 'class' => 'docman_editfile_file');
$cells[][] = html_e('input', array('type' => 'file', 'name' =>
'uploaded_data')).html_e('br').'('._('max upload size')._(':
').human_readable_bytes(util_get_maxuploadfilesize()).')';
echo $HTML->multiTableRow(array('id' => 'uploadnewroweditfile', 'class' =>
'hide'), $cells);
+$cells = array();
+$cells[] = array($HTML->addRequiredFieldsInfoBox(), 'colspan' => 2);
+echo $HTML->multiTableRow(array(), $cells);
echo $HTML->listTableBottom();
echo html_e('input', array('type' => 'hidden', 'id' => 'docid', 'name' =>
'docid'));
echo html_e('input', array('type' => 'hidden', 'id' => 'edit_version', 'name'
=> 'edit_version'));
echo html_e('input', array('type' => 'hidden', 'id' => 'new_version', 'name'
=> 'new_version', 'value' => 0));
+echo html_e('input', array('type' => 'hidden', 'id' => 'subaction', 'name' =>
'subaction', 'value' => 'version'));
+echo html_ac(html_ap() -1);
+if (forge_get_config('use_docman_review')) {
+ echo html_e('div', array('id' => 'tabbereditfile-review', 'class' =>
'tabbertab'), '', false);
+}
if (forge_get_config('use_object_associations')) {
- echo html_ac(html_ap() -1);
echo html_e('div', array('id' => 'tabbereditfile-association', 'class'
=> 'tabbertab'), '', false);
- echo '<script type="text/javascript">//<![CDATA[
- jQuery(document).ready(function() {
- jQuery("#tabbereditfile").tabs();
- });
- //]]></script>';
- echo html_ac(html_ap() -1);
}
+echo '<script type="text/javascript">//<![CDATA[
+ jQuery(document).ready(function() {
+ jQuery("#tabbereditfile").tabs();
+ });
+ //]]></script>';
+echo html_ac(html_ap() -1);
echo $HTML->closeForm();
echo html_ac(html_ap() -1);
diff --git a/src/common/include/FFObject.class.php
b/src/common/include/FFObject.class.php
index a9a7037..15e70f1 100644
--- a/src/common/include/FFObject.class.php
+++ b/src/common/include/FFObject.class.php
@@ -177,31 +177,46 @@ class FFObject extends FFError {
if (preg_match('/^[Dd][0-9]+/', $objectRef)) {
//Document Ref.
$documentId = substr($objectRef, 1);
- $documentObject =
document_get_object($documentId, $this->getGroupID($this));
- if (is_object($documentObject)) {
- $statusArr[] =
$this->addAssociationTo($documentObject);
+ if ($documentId != $this->getID()) {
+ $documentObject =
document_get_object($documentId, $this->getGroupID($this));
+ if (is_object($documentObject))
{
+ $statusArr[] =
$this->addAssociationTo($documentObject);
+ } else {
+
$this->setError(_('Unable to retrieve object ref')._(': ').$objectRef);
+ $statusArr[] = false;
+ }
} else {
- $this->setError(_('Unable to
retrieve object ref')._(': ').$objectRef);
+ $this->setError(_('Unable to
associate to itself'));
$statusArr[] = false;
}
} elseif (preg_match('/^#[0-9]+/', $objectRef))
{
//Artifact Ref.
$artifactId = substr($objectRef, 1);
- $artifactObject =
artifact_get_object($artifactId);
- if (is_object($artifactObject)) {
- $statusArr[] =
$this->addAssociationTo($artifactObject);
+ if ($artifactId != $this->getID()) {
+ $artifactObject =
artifact_get_object($artifactId);
+ if (is_object($artifactObject))
{
+ $statusArr[] =
$this->addAssociationTo($artifactObject);
+ } else {
+
$this->setError(_('Unable to retrieve object ref')._(': ').$objectRef);
+ $statusArr[] = false;
+ }
} else {
- $this->setError(_('Unable to
retrieve object ref')._(': ').$objectRef);
+ $this->setError(_('Unable to
associate to itself'));
$statusArr[] = false;
}
} elseif (preg_match('/^[Rr][0-9]+/',
$objectRef)) {
//Artifact Ref.
- $frsreleaseid = substr($objectRef, 1);
- $frsreleaseObject =
frsrelease_get_object($frsreleaseid);
- if (is_object($frsreleaseObject)) {
- $statusArr[] =
$this->addAssociationTo($frsreleaseObject);
+ $frsreleaseId = substr($objectRef, 1);
+ if ($frsreleaseId != $this->getID()) {
+ $frsreleaseObject =
frsrelease_get_object($frsreleaseId);
+ if
(is_object($frsreleaseObject)) {
+ $statusArr[] =
$this->addAssociationTo($frsreleaseObject);
+ } else {
+
$this->setError(_('Unable to retrieve object ref')._(': ').$objectRef);
+ $statusArr[] = false;
+ }
} else {
- $this->setError(_('Unable to
retrieve object ref')._(': ').$objectRef);
+ $this->setError(_('Unable to
associate to itself'));
$statusArr[] = false;
}
} else {
diff --git a/src/db/20161126-document-review.sql
b/src/db/20161126-document-review.sql
new file mode 100644
index 0000000..ef595fe
--- /dev/null
+++ b/src/db/20161126-document-review.sql
@@ -0,0 +1,73 @@
+CREATE SEQUENCE doc_review_pk_seq
+ START WITH 1
+ INCREMENT BY 1
+ MAXVALUE 2147483647
+ NO MINVALUE
+ CACHE 1;
+
+CREATE TABLE doc_review_status (
+ statusid integer NOT NULL UNIQUE,
+ name text,
+ description text
+);
+
+INSERT INTO doc_review_status (statusid, name) VALUES (1, 'open');
+INSERT INTO doc_review_status (statusid, name) VALUES (2, 'close');
+INSERT INTO doc_review_status (statusid, name) VALUES (3, 'error');
+
+CREATE TABLE doc_review (
+ revid integer DEFAULT nextval('doc_review_pk_seq'::text) NOT NULL
UNIQUE,
+ created_by integer REFERENCES users (user_id) ON DELETE CASCADE,
+ statusid integer REFERENCES doc_review_status (statusid),
+ docid integer REFERENCES doc_data (docid) ON DELETE CASCADE,
+ startdate integer,
+ enddate integer,
+ title text,
+ description text
+);
+
+CREATE TABLE doc_review_version (
+ revid integer REFERENCES doc_review (revid) ON DELETE CASCADE,
+ serialid integer REFERENCES doc_data_version (serial_id) ON DELETE
CASCADE
+);
+
+CREATE TABLE doc_review_users_type (
+ typeid integer NOT NULL UNIQUE,
+ name text
+);
+
+INSERT INTO doc_review_users_type (typeid, name) VALUES (1, 'mandatory');
+INSERT INTO doc_review_users_type (typeid, name) VALUES (2, 'optional');
+
+CREATE TABLE doc_review_users_status (
+ statusid integer NOT NULL UNIQUE,
+ name text
+);
+
+INSERT INTO doc_review_users_status (statusid, name) VALUES (1, 'pending');
+INSERT INTO doc_review_users_status (statusid, name) VALUES (2, 'done');
+
+CREATE TABLE doc_review_users (
+ revid integer REFERENCES doc_review (revid) ON DELETE CASCADE,
+ userid integer REFERENCES users (user_id) ON DELETE CASCADE,
+ typeid integer REFERENCES doc_review_users_type (typeid),
+ statusid integer REFERENCES doc_review_users_status (statusid),
+ updatedate integer
+);
+
+CREATE TABLE doc_review_comments (
+ commentid integer NOT NULL UNIQUE,
+ revid integer REFERENCES doc_review (revid) ON DELETE CASCADE,
+ userid integer REFERENCES users (user_id) ON DELETE CASCADE,
+ rcomment text,
+ createdate integer
+);
+
+CREATE TABLE doc_review_attachments (
+ attachid integer,
+ createdate integer,
+ commentid integer REFERENCES doc_review_comments (commentid) ON DELETE
CASCADE,
+ filename text,
+ filetype text,
+ filesize text
+);
diff --git a/src/etc/config.ini.d/defaults.ini
b/src/etc/config.ini.d/defaults.ini
index 8710393..9de0344 100644
--- a/src/etc/config.ini.d/defaults.ini
+++ b/src/etc/config.ini.d/defaults.ini
@@ -93,8 +93,9 @@ use_quicknav_default = yes
use_home = yes
use_my = yes
check_password_strength = no
-use_object_associations = yes
+use_object_associations = no
use_tracker_widget_display = no
+use_docman_review = no
scm_single_host = yes
system_user=fusionforge
diff --git a/src/www/docman/index.php b/src/www/docman/index.php
index 29811e1..e348e55 100644
--- a/src/www/docman/index.php
+++ b/src/www/docman/index.php
@@ -32,8 +32,8 @@ require_once $gfcommon.'docman/Document.class.php';
require_once $gfcommon.'docman/DocumentFactory.class.php';
require_once $gfcommon.'docman/DocumentGroup.class.php';
require_once $gfcommon.'docman/DocumentGroupFactory.class.php';
-// require_once $gfcommon.'docman/DocumentReview.class.php';
-// require_once $gfcommon.'docman/DocumentReviewFactory.class.php';
+require_once $gfcommon.'docman/DocumentReview.class.php';
+require_once $gfcommon.'docman/DocumentReviewFactory.class.php';
require_once $gfcommon.'docman/DocumentVersion.class.php';
require_once $gfcommon.'docman/DocumentVersionFactory.class.php';
require_once $gfcommon.'docman/include/utils.php';
diff --git a/src/www/docman/scripts/DocManController.js
b/src/www/docman/scripts/DocManController.js
index 45532d3..ea482da 100644
--- a/src/www/docman/scripts/DocManController.js
+++ b/src/www/docman/scripts/DocManController.js
@@ -64,6 +64,15 @@ DocManListFileController.prototype =
if (typeof(this.listfileparams.buttonAddItem) != 'undefined') {
this.listfileparams.buttonAddItem.click(jQuery.proxy(this,
"toggleAddItemView"));
}
+ if (typeof(jQuery('#versiontab')) != 'undefined') {
+ jQuery('#versiontab').click(jQuery.proxy(this,
"setRequiredInputs", jQuery('#versiontab')));
+ }
+ if (typeof(jQuery('#reviewtab')) != 'undefined') {
+ jQuery('#reviewtab').click(jQuery.proxy(this,
"setRequiredInputs", jQuery('#reviewtab')));
+ }
+ if (typeof(jQuery('#associationtab')) != 'undefined') {
+ jQuery('#associationtab').click(jQuery.proxy(this,
"setRequiredInputs", jQuery('#associationtab')));
+ }
},
resizableDiv: function() {
@@ -107,7 +116,6 @@ DocManListFileController.prototype =
autoOpen: false,
width: 1000,
modal: true,
- title: this.listfileparams.divEditTitle,
buttons: {
Save: jQuery.proxy(function() {
jQuery('#editdocdata').submit();
@@ -183,14 +191,13 @@ DocManListFileController.prototype =
var modalId = this.listfileparams.divNotifyUsers;
jQuery(modalId).dialog({
autoOpen: false,
- width: 475,
+ width: 600,
modal: true,
- title: this.listfileparams.divNotifyTitle,
buttons: {
Save: { text:
this.listfileparams.divNotifySaveButtonTxt,
click: jQuery.proxy(function() {
jQuery('#notifyusersdoc').submit();
- var id =
jQuery('#notifydocid').attr('value');
+ var id = jQuery('#docid').attr('value');
jQuery.get(this.listfileparams.docManURL+'/', {
group_id:
this.listfileparams.groupId,
action: 'lock',
@@ -212,7 +219,7 @@ DocManListFileController.prototype =
jQuery(modalId).dialog( "close" );
}, this)},
Cancel: jQuery.proxy(function() {
- var id =
jQuery('#notifydocid').attr('value');
+ var id = jQuery('#docid').attr('value');
jQuery.get(this.listfileparams.docManURL+'/', {
group_id:
this.listfileparams.groupId,
action: 'lock',
@@ -236,7 +243,7 @@ DocManListFileController.prototype =
}
});
jQuery(modalId).bind('dialogclose', jQuery.proxy(function() {
- var id = jQuery('#notifydocid').attr('value');
+ var id = jQuery('#docid').attr('value');
jQuery.get(this.listfileparams.docManURL+'/', {
group_id: this.listfileparams.groupId,
action: 'lock',
@@ -457,6 +464,27 @@ DocManListFileController.prototype =
}
}, this));
+ jQuery.getJSON(this.listfileparams.docManURL + '/?group_id=' +
docid_groupid + '&action=getdocreviews&docid='+ this.docparams.id,
jQuery.proxy(function(data){
+ if (typeof data.html != 'undefined') {
+ jQuery('#tabbereditfile-review >
.feedback').remove();
+ jQuery('#tabbereditfile-review >
.error').remove();
+ jQuery('#tabbereditfile-review >
.warning_msg').remove();
+ jQuery('#tabbereditfile-review >
.information').remove();
+ jQuery('#tabbereditfile-review >
table').remove();
+ jQuery('#tabbereditfile-review >
span').remove();
+ jQuery('#tabbereditfile-review >
p').remove();
+
jQuery('#editfile-createreview').remove();
+
jQuery('#doc_review_addbutton').remove();
+
jQuery('#tabbereditfile-review').prepend(data.html);
+
jQuery('#doc_review_addbutton').button();
+ }
+ if (typeof data.htmltab != 'undefined') {
+ jQuery('#reviewtab').text(data.htmltab);
+ }
+
jQuery('#review-select-mandatory-users').gentleSelect({columns: 3, itemWidth:
150});
+
jQuery('#review-select-optional-users').gentleSelect({columns: 3, itemWidth:
150});
+ }, this));
+
jQuery('#editdocdata').attr('action', this.docparams.action);
jQuery.get(this.docparams.docManURL+'/', {
@@ -469,7 +497,9 @@ DocManListFileController.prototype =
});
this.lockInterval[this.docparams.id] =
setInterval("jQuery.get('" + this.docparams.docManURL + "/',
{group_id:"+this.docparams.groupId+", action:'lock', lock:1, type:'file',
itemid:"+this.docparams.id+", childgroup_id:"+this.docparams.childGroupId+"})",
this.docparams.lockIntervalDelay);
this.lockInterval[this.docparams.docgroupId] =
setInterval("jQuery.get('" + this.docparams.docManURL + "/',
{group_id:"+this.docparams.groupId+", action:'lock', lock:1, type: 'dir',
itemid:"+this.docparams.docgroupId+",
childgroup_id:"+this.docparams.childGroupId+"})",
this.docparams.lockIntervalDelay);
- jQuery(this.listfileparams.divEditFile).dialog('open');
+ jQuery('#tabbereditfile').tabs("option", "active", 0);
+ this.setRequiredInputs(jQuery('#versiontab'));
+ jQuery(this.listfileparams.divEditFile).dialog('option',
'title', '[D'+this.docparams.id+']
'+this.listfileparams.divEditTitle).dialog('open');
return false;
},
@@ -490,8 +520,50 @@ DocManListFileController.prototype =
}
},
+ toggleAddReviewView: function() {
+ jQuery('#review-title').val('');
+ jQuery('#review-description').val('');
+ jQuery('#datepicker_end_review_date').val('');
+ jQuery('#review-serialid').val();
+ jQuery('[class^=gentle]').remove();
+ jQuery('#review-select-mandatory-users').val('');
+ jQuery('#review-select-optional-users').val('');
+ jQuery('#review-select-mandatory-users').gentleSelect({columns:
3, itemWidth: 150});
+ jQuery('#review-select-optional-users').gentleSelect({columns:
3, itemWidth: 150});
+ if (jQuery('#editfile-createreview').is(':visible')) {
+ jQuery('#editfile-createreview').hide();
+ jQuery('#new_review').val(0);
+ } else {
+ jQuery('#new_review').val(1);
+ jQuery('#editfile-createreview').show();
+ }
+ },
+
+ toggleEditReviewView: function(params) {
+ this.review = params;
+ if (jQuery('#editfile-createreview').is(':visible')) {
+ jQuery('#editfile-createreview').hide();
+ jQuery('#new_review').val(0);
+ jQuery('#review_id').val(0);
+ } else {
+ jQuery('#review_id').val(this.review.review);
+ jQuery('#review-title').val(this.review.title);
+
jQuery('#review-description').val(this.review.description);
+
jQuery('#datepicker_end_review_date').val(this.review.endreviewdate);
+ jQuery('#review-serialid').val(this.review.serialid);
+ jQuery('[class^=gentle]').remove();
+
jQuery('#review-select-mandatory-users').val(this.review.mandatoryusers);
+
jQuery('#review-select-optional-users').val(this.review.optionalusers);
+
jQuery('#review-select-mandatory-users').gentleSelect({columns: 3, itemWidth:
150});
+
jQuery('#review-select-optional-users').gentleSelect({columns: 3, itemWidth:
150});
+ jQuery('#new_review').val(0);
+ jQuery('#editfile-createreview').show();
+ }
+ },
+
toggleEditVersionView: function(params) {
this.version = params;
+ jQuery('#new_version').val(0);
if (this.version.isHtml) {
jQuery('#defaulteditfiletype').val('text/html');
}
@@ -567,6 +639,10 @@ DocManListFileController.prototype =
if (typeof data.status != 'undefined') {
if (data.status == 1) {
jQuery('#docversion'+this.version).remove();
+ //adjust review tab & version
tab number?
+ if
(jQuery('#docversionreview'+this.version) != 'undefined') {
+
jQuery('#docversionreview'+this.version).parent.remove();
+ }
if
(jQuery('#sortable_doc_version_table tr').length <= 2) {
jQuery('#version_action_delete').remove();
}
@@ -575,6 +651,36 @@ DocManListFileController.prototype =
}, this.delversion));
},
+ deleteReview: function(params) {
+ this.delreview = params;
+ jQuery.getJSON(this.docparams.docManURL + '/?group_id=' +
this.docparams.groupId +
'&action=deletereview&docid='+this.docparams.id+'&review='+this.delreview.review
, jQuery.proxy(function(data){
+ if (typeof data.html != 'undefined') {
+ jQuery('#editFile >
.feedback').remove();
+ jQuery('#editFile > .error').remove();
+ jQuery('#editFile >
.warning_msg').remove();
+ jQuery('#editFile').prepend(data.html);
+ }
+ if (typeof data.status != 'undefined') {
+ if (data.status == 1) {
+
jQuery('#docreview'+this.review).remove();
+ //adjust review tab number?
+ }
+ }
+ }, this.delreview));
+ },
+
+ reminderReview: function(params) {
+ this.reminderreview = params;
+ jQuery.getJSON(this.docparams.docManURL + '/?group_id=' +
this.docparams.groupId +
'&action=reminderreview&docid='+this.docparams.id+'&review='+this.reminderreview.review
, jQuery.proxy(function(data){
+ if (typeof data.html != 'undefined') {
+ jQuery('#editFile >
.feedback').remove();
+ jQuery('#editFile > .error').remove();
+ jQuery('#editFile >
.warning_msg').remove();
+ jQuery('#editFile').prepend(data.html);
+ }
+ }, this.reminderreview));
+ },
+
toggleMoveFileView: function() {
if (!this.listfileparams.divMoveFile.is(':visible')) {
this.listfileparams.divMoveFile.show();
@@ -595,7 +701,7 @@ DocManListFileController.prototype =
toggleNotifyUserView: function(params) {
this.notifyparams = params;
jQuery('#notifytitle').text(this.notifyparams.title);
-
jQuery('#notifydescription').text(this.notifyparams.description);
+
jQuery('#notifydescription').html(this.notifyparams.description);
jQuery('#notifydocid').val(this.notifyparams.id);
jQuery('#notifyfilelink').text(this.notifyparams.filename);
if (this.notifyparams.statusId != 2) {
@@ -617,7 +723,8 @@ DocManListFileController.prototype =
});
this.lockInterval[this.notifyparams.id] =
setInterval("jQuery.get('" + this.notifyparams.docManURL + "/',
{group_id:"+this.notifyparams.groupId+",action:'lock',lock:1,type:'file',itemid:"+this.notifyparams.id+",childgroup_id:"+this.notifyparams.childGroupId+"})",
this.notifyparams.lockIntervalDelay);
this.lockInterval[this.notifyparams.docgroupId] =
setInterval("jQuery.get('" + this.notifyparams.docManURL + "/',
{group_id:"+this.notifyparams.groupId+",action:'lock',lock:1,type:'dir',itemid:"+this.notifyparams.docgroupId+",childgroup_id:"+this.notifyparams.childGroupId+"})",
this.notifyparams.lockIntervalDelay);
- jQuery(this.listfileparams.divNotifyUsers).dialog('open');
+ jQuery('#notify-userids').gentleSelect({columns: 2, itemWidth:
120});
+ jQuery(this.listfileparams.divNotifyUsers).dialog('option',
'title', '[D'+this.notifyparams.id+']
'+this.listfileparams.divNotifyTitle).dialog('open');
return false;
@@ -661,6 +768,25 @@ DocManListFileController.prototype =
break;
}
}
+ },
+
+ setRequiredInputs: function(id) {
+ if (id.attr('id') == 'reviewtab') {
+ jQuery('#tabbereditfile-version
:input').not(':input[type=hidden], :input[type=button]').prop('disabled', true);
+ jQuery('#tabbereditfile-association').prop('disabled',
true);
+ jQuery('#tabbereditfile-review
:input').removeAttr('disabled');
+ jQuery('#subaction').val('review');
+ } else if (id.attr('id') == 'associationtab') {
+ jQuery('#tabbereditfile-version
:input').not(':input[type=hidden], :input[type=button]').prop('disabled', true);
+
jQuery('#tabbereditfile-association').removeAttr('disabled');
+ jQuery('#tabbereditfile-review
:input').prop('disabled', true);
+ jQuery('#subaction').val('association');
+ } else if (id.attr('id') == 'versiontab') {
+ jQuery('#tabbereditfile-version
:input').not(':input[type=hidden], :input[type=button]').removeAttr('disabled');
+ jQuery('#tabbereditfile-association').prop('disabled',
true);
+ jQuery('#tabbereditfile-review
:input').prop('disabled', true);
+ jQuery('#subaction').val('version');
+ }
}
};
-----------------------------------------------------------------------
Summary of changes:
src/common/docman/DocumentReview.class.php | 524 +++++++++++++++++++++
src/common/docman/DocumentReviewFactory.class.php | 123 +++++
.../{deleteversion.php => deletereview.php} | 18 +-
src/common/docman/actions/editfile.php | 264 ++++++-----
.../{getdocversions.php => getdocreviews.php} | 16 +-
.../{deleteversion.php => reminderreview.php} | 20 +-
src/common/docman/include/constants.php | 4 +
src/common/docman/views/editfile.php | 42 +-
src/common/include/FFObject.class.php | 41 +-
src/db/20161126-document-review.sql | 73 +++
src/etc/config.ini.d/defaults.ini | 3 +-
src/www/docman/index.php | 4 +-
src/www/docman/scripts/DocManController.js | 144 +++++-
13 files changed, 1095 insertions(+), 181 deletions(-)
create mode 100644 src/common/docman/DocumentReview.class.php
create mode 100644 src/common/docman/DocumentReviewFactory.class.php
copy src/common/docman/actions/{deleteversion.php => deletereview.php} (81%)
copy src/common/docman/actions/{getdocversions.php => getdocreviews.php} (76%)
copy src/common/docman/actions/{deleteversion.php => reminderreview.php} (80%)
create mode 100644 src/db/20161126-document-review.sql
hooks/post-receive
--
FusionForge
_______________________________________________
Fusionforge-commits mailing list
[email protected]
http://lists.fusionforge.org/cgi-bin/mailman/listinfo/fusionforge-commits