init
This commit is contained in:
commit
aabcdbc574
4
.dockerignore
Normal file
4
.dockerignore
Normal file
@ -0,0 +1,4 @@
|
||||
./.git
|
||||
./build
|
||||
./Jenkinsfile
|
||||
./Makefile
|
68
.gitlab-ci.yml
Normal file
68
.gitlab-ci.yml
Normal file
@ -0,0 +1,68 @@
|
||||
stages:
|
||||
- sonarqube
|
||||
- unit-test
|
||||
- ui-test
|
||||
- package
|
||||
- cleanup-packages
|
||||
- notify
|
||||
|
||||
program-static-analysis:
|
||||
stage: sonarqube
|
||||
image:
|
||||
name: sonarsource/sonar-scanner-cli:latest
|
||||
entrypoint: [""]
|
||||
variables:
|
||||
SONAR_USER_HOME: "${CI_PROJECT_DIR}/.sonar" # Defines the location of the analysis task cache
|
||||
GIT_DEPTH: "0" # Tells git to fetch all the branches of the project, required by the analysis task
|
||||
cache:
|
||||
key: "${CI_JOB_NAME}"
|
||||
paths:
|
||||
- .sonar/cache
|
||||
script:
|
||||
- sonar-scanner -Dsonar.inclusions=$(git diff --name-only HEAD~1|tr '\n' ',') -Dsonar.analysis.user=${GITLAB_USER_LOGIN}
|
||||
allow_failure: true
|
||||
only:
|
||||
- master # or the name of your main branch
|
||||
|
||||
unit-test:
|
||||
stage: unit-test
|
||||
script:
|
||||
- "/home/gitlab-runner/bin/zentao-unittest.sh ${CI_PROJECT_DIR}"
|
||||
allow_failure: true
|
||||
only:
|
||||
- master
|
||||
- merge_requests
|
||||
|
||||
ui-test:
|
||||
stage: ui-test
|
||||
script:
|
||||
- "/home/gitlab-runner/bin/zentao-uitest.sh ${CI_PROJECT_DIR}"
|
||||
allow_failure: true
|
||||
only:
|
||||
- master
|
||||
- merge_requests
|
||||
|
||||
package:
|
||||
stage: package
|
||||
script:
|
||||
- make cizip
|
||||
allow_failure: true
|
||||
only:
|
||||
- master
|
||||
|
||||
cleanup-packages:
|
||||
stage: cleanup-packages
|
||||
script:
|
||||
- make clean
|
||||
when: on_failure
|
||||
only:
|
||||
- master
|
||||
|
||||
notify:
|
||||
stage: notify
|
||||
script:
|
||||
- "/home/gitlab-runner/bin/ci-notify.php"
|
||||
when: on_success
|
||||
only:
|
||||
- master
|
||||
- merge_requests
|
0
api/index.html
Normal file
0
api/index.html
Normal file
0
api/v1/config/index.html
Normal file
0
api/v1/config/index.html
Normal file
35
api/v1/config/zdisk.php
Normal file
35
api/v1/config/zdisk.php
Normal file
@ -0,0 +1,35 @@
|
||||
<?php
|
||||
global $lang;
|
||||
|
||||
$config->zdisk = new stdclass();
|
||||
|
||||
$config->zdisk->root = array();
|
||||
$config->zdisk->root['my'] = array('name' => $lang->my->common, 'type' => 'folder');
|
||||
$config->zdisk->root['program'] = array('name' => $lang->program->common, 'type' => 'folder');
|
||||
$config->zdisk->root['product'] = array('name' => $lang->product->common, 'type' => 'folder');
|
||||
$config->zdisk->root['project'] = array('name' => $lang->project->common, 'type' => 'folder');
|
||||
$config->zdisk->root['qa'] = array('name' => $lang->qa->common, 'type' => 'folder');
|
||||
|
||||
$config->zdisk->my = array();
|
||||
$config->zdisk->my['todo'] = array('name' => $lang->user->todo, 'type' => 'file');
|
||||
$config->zdisk->my['work'] = array('name' => $lang->my->work, 'type' => 'folder');
|
||||
$config->zdisk->my['myproject'] = array('name' => $lang->projectCommon, 'type' => 'folder');
|
||||
$config->zdisk->my['myexecution'] = array('name' => $lang->executionCommon, 'type' => 'folder');
|
||||
|
||||
$config->zdisk->work = array();
|
||||
$config->zdisk->work['task'] = array('name' => $lang->user->task, 'type' => 'file');
|
||||
$config->zdisk->work['story'] = array('name' => $lang->user->story, 'type' => 'file');
|
||||
$config->zdisk->work['bug'] = array('name' => $lang->user->bug, 'type' => 'file');
|
||||
$config->zdisk->work['case'] = array('name' => $lang->user->testCase, 'type' => 'file');
|
||||
$config->zdisk->work['testtask'] = array('name' => $lang->user->testTask, 'type' => 'file');
|
||||
|
||||
$config->zdisk->myproject = array();
|
||||
$config->zdisk->myproject['doing'] = array('name' => $lang->zdisk->doing, 'type' => 'file');
|
||||
$config->zdisk->myproject['wait'] = array('name' => $lang->zdisk->wait, 'type' => 'file');
|
||||
$config->zdisk->myproject['suspend'] = array('name' => $lang->zdisk->suspend, 'type' => 'file');
|
||||
$config->zdisk->myproject['closed'] = array('name' => $lang->zdisk->closed, 'type' => 'file');
|
||||
$config->zdisk->myproject['openedbyme'] = array('name' => $lang->zdisk->openedByMe, 'type' => 'file');
|
||||
|
||||
$config->zdisk->myexecution = array();
|
||||
$config->zdisk->myexecution['undone'] = array('name' => $lang->zdisk->undone, 'type' => 'file');
|
||||
$config->zdisk->myexecution['done'] = array('name' => $lang->zdisk->done, 'type' => 'file');
|
127
api/v1/entries/bug.php
Normal file
127
api/v1/entries/bug.php
Normal file
@ -0,0 +1,127 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class bugEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($bugID)
|
||||
{
|
||||
$this->resetOpenApp($this->param('tab', 'product'));
|
||||
|
||||
$control = $this->loadController('bug', 'view');
|
||||
$control->view($bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$bug = $data->data->bug;
|
||||
|
||||
/* Set product name and status */
|
||||
$bug->productName = $data->data->product->name;
|
||||
$bug->productStatus = $data->data->product->status;
|
||||
|
||||
/* Set module title */
|
||||
$moduleTitle = '';
|
||||
if(empty($bug->module)) $moduleTitle = '/';
|
||||
if($bug->module)
|
||||
{
|
||||
$modulePath = $data->data->modulePath;
|
||||
foreach($modulePath as $key => $module)
|
||||
{
|
||||
$moduleTitle .= $module->name;
|
||||
if(isset($modulePath[$key + 1])) $moduleTitle .= '/';
|
||||
}
|
||||
}
|
||||
$bug->moduleTitle = $moduleTitle;
|
||||
|
||||
$openedBuilds = array();
|
||||
foreach(explode(',', $bug->openedBuild) as $buildID)
|
||||
{
|
||||
if(empty($buildID)) continue;
|
||||
|
||||
$openedBuild = new stdclass();
|
||||
$openedBuild->id = $buildID;
|
||||
$openedBuild->title = zget($data->data->builds, $buildID, '');
|
||||
|
||||
$openedBuilds[] = $openedBuild;
|
||||
}
|
||||
$bug->openedBuild = $openedBuilds;
|
||||
|
||||
if($bug->resolvedBuild)
|
||||
{
|
||||
$resolvedBuild = new stdclass();
|
||||
$resolvedBuild->id = $bug->resolvedBuild;
|
||||
$resolvedBuild->title = zget($data->data->builds, $bug->resolvedBuild, '');
|
||||
$bug->resolvedBuild = $resolvedBuild;
|
||||
}
|
||||
|
||||
$bug->actions = $this->loadModel('action')->processActionForAPI($data->data->actions, $data->data->users, $this->lang->bug);
|
||||
|
||||
$preAndNext = $data->data->preAndNext;
|
||||
$bug->preAndNext = array();
|
||||
$bug->preAndNext['pre'] = $preAndNext->pre ? $preAndNext->pre->id : '';
|
||||
$bug->preAndNext['next'] = $preAndNext->next ? $preAndNext->next->id : '';
|
||||
|
||||
return $this->send(200, $this->format($bug, 'activatedDate:time,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,mailto:userList,resolvedBy:user,resolvedDate:time,closedBy:user,closedDate:time,lastEditedBy:user,lastEditedDate:time,deadline:date,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($bugID)
|
||||
{
|
||||
$oldBug = $this->loadModel('bug')->getByID($bugID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'uid,title,project,execution,openedBuild,assignedTo,pri,severity,type,story,resolvedBy,closedBy,resolution,product,plan,task,module,steps,mailto,keywords';
|
||||
$this->batchSetPost($fields, $oldBug);
|
||||
$this->setPost('notifyEmail', implode(',', $this->request('notifyEmail', array())));
|
||||
|
||||
$control = $this->loadController('bug', 'edit');
|
||||
$control->edit($bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
|
||||
$bug = $this->bug->getByID($bugID);
|
||||
return $this->send(200, $this->format($bug, 'activatedDate:time,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,mailto:userList,resolvedBy:user,resolvedDate:time,closedBy:user,closedDate:time,lastEditedBy:user,lastEditedDate:time,deadline:date,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($bugID)
|
||||
{
|
||||
$control = $this->loadController('bug', 'delete');
|
||||
$control->delete($bugID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
38
api/v1/entries/bugactive.php
Normal file
38
api/v1/entries/bugactive.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug active entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
**/
|
||||
class bugActiveEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($bugID)
|
||||
{
|
||||
$fields = 'assignedTo,uid,openedBuild,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('bug', 'activate');
|
||||
$control->activate($bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$bug = $this->loadModel('bug')->getByID($bugID);
|
||||
|
||||
return $this->send(200, $this->format($bug, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
||||
|
38
api/v1/entries/bugassign.php
Normal file
38
api/v1/entries/bugassign.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug assign entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
**/
|
||||
class bugAssignEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($bugID)
|
||||
{
|
||||
$fields = 'assignedTo,mailto,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('bug', 'assignTo');
|
||||
$control->assignTo($bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$bug = $this->loadModel('bug')->getByID($bugID);
|
||||
|
||||
return $this->send(200, $this->format($bug, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
||||
|
37
api/v1/entries/bugclose.php
Normal file
37
api/v1/entries/bugclose.php
Normal file
@ -0,0 +1,37 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug close entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
**/
|
||||
class bugCloseEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($bugID)
|
||||
{
|
||||
$fields = 'comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('bug', 'close');
|
||||
$control->close($bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
$bug = $this->loadModel('bug')->getByID($bugID);
|
||||
|
||||
return $this->send(200, $this->format($bug, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
||||
|
38
api/v1/entries/bugconfirm.php
Normal file
38
api/v1/entries/bugconfirm.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug confirm entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class bugConfirmEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
**/
|
||||
public function post($bugID)
|
||||
{
|
||||
$fields = 'assignedTo,mailto,comment,pri,type';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('bug', 'confirmBug');
|
||||
$control->confirmBug($bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$bug = $this->loadModel('bug')->getById($bugID);
|
||||
|
||||
return $this->send(200, $this->format($bug, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
||||
|
61
api/v1/entries/bugrecordestimate.php
Normal file
61
api/v1/entries/bugrecordestimate.php
Normal file
@ -0,0 +1,61 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug recordEstimate entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class bugRecordEstimateEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($bugID)
|
||||
{
|
||||
if($this->config->edition == 'open') return $this->send400('ZenTaoPMS does not have bug effort function.');
|
||||
|
||||
$control = $this->loadController('effort', 'createForObject');
|
||||
$control->createForObject('bug', $bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->error('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$effort = $data->data->efforts;
|
||||
|
||||
return $this->send(200, array('effort' => $effort));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($bugID)
|
||||
{
|
||||
if($this->config->edition == 'open') return $this->send400('ZenTaoPMS does not have bug effort function.');
|
||||
|
||||
$fields = 'id,dates,consumed,objectType,objectID,work';
|
||||
$this->batchSetPost($fields);
|
||||
$control = $this->loadController('effort', 'createForObject');
|
||||
$control->createForObject('bug', $bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$bug = $this->loadModel('bug')->getByID($bugID);
|
||||
|
||||
return $this->send(200, $this->format($bug, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
38
api/v1/entries/bugresolve.php
Normal file
38
api/v1/entries/bugresolve.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug resolve entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
**/
|
||||
class bugResolveEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $bugID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($bugID)
|
||||
{
|
||||
$fields = 'resolution,resolvedBuild,resolvedDate,duplicateBug,assignedTo,uid,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('bug', 'resolve');
|
||||
$control->resolve($bugID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$bug = $this->loadModel('bug')->getByID($bugID);
|
||||
|
||||
return $this->send(200, $this->format($bug, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,resolvedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
||||
|
116
api/v1/entries/bugs.php
Normal file
116
api/v1/entries/bugs.php
Normal file
@ -0,0 +1,116 @@
|
||||
<?php
|
||||
/**
|
||||
* The bugs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class bugsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($productID = 0)
|
||||
{
|
||||
if(empty($productID)) $productID = $this->param('product', 0);
|
||||
if(empty($productID)) return $this->sendError(400, 'Need product id.');
|
||||
|
||||
$control = $this->loadController('bug', 'browse');
|
||||
$control->browse($productID, $this->param('branch', 'all'), $this->param('status', ''), 0, $this->param('order', 'id_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$bugs = $data->data->bugs;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
$this->loadModel('product');
|
||||
foreach($bugs as $bug)
|
||||
{
|
||||
$status = array('code' => $bug->status, 'name' => $this->lang->bug->statusList[$bug->status]);
|
||||
if($bug->status == 'active' and $bug->confirmed) $status = array('code' => 'confirmed', 'name' => $this->lang->bug->labelConfirmed);
|
||||
if($bug->resolution == 'postponed') $status = array('code' => 'postponed', 'name' => $this->lang->bug->labelPostponed);
|
||||
if(!empty($bug->delay)) $status = array('code' => 'delay', 'name' => $this->lang->bug->overdueBugs);
|
||||
$bug->status = $status['code'];
|
||||
$bug->statusName = $status['name'];
|
||||
|
||||
$product = $this->product->getById($bug->product);
|
||||
$bug->productStatus = $product->status;
|
||||
|
||||
$result[$bug->id] = $this->format($bug, 'activatedDate:time,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,mailto:userList,resolvedBy:user,resolvedDate:time,closedBy:user,closedDate:time,lastEditedBy:user,lastEditedDate:time,deadline:date,deleted:bool');
|
||||
}
|
||||
|
||||
$storyChangeds = $this->dao->select('t1.id')->from(TABLE_BUG)->alias('t1')
|
||||
->leftJoin(TABLE_STORY)->alias('t2')->on('t1.story=t2.id')
|
||||
->where('t1.id')->in(array_keys($result))
|
||||
->andWhere('t1.story')->ne('0')
|
||||
->andWhere('t1.storyVersion != t2.version')
|
||||
->fetchPairs('id', 'id');
|
||||
foreach($storyChangeds as $bugID)
|
||||
{
|
||||
$status = array('code' => 'storyChanged', 'name' => $this->lang->bug->changed);
|
||||
$result[$bugID]->status = $status['code'];
|
||||
$result[$bugID]->statusName = $status['name'];
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'bugs' => array_values($result)));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($productID = 0)
|
||||
{
|
||||
if(!$productID) $productID = $this->param('product');
|
||||
if(!$productID and isset($this->requestBody->product)) $productID = $this->requestBody->product;
|
||||
if(!$productID) return $this->sendError(400, 'Need product id.');
|
||||
|
||||
$fields = 'title,project,execution,openedBuild,assignedTo,pri,module,severity,type,story,task,mailto,keywords,steps,uid';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$caseID = $this->request('case', 0);
|
||||
if($caseID)
|
||||
{
|
||||
$case = $this->loadModel('testcase')->getById($caseID);
|
||||
if($case)
|
||||
{
|
||||
$this->setPost('case', $case->id);
|
||||
$this->setPost('caseVersion', $case->version);
|
||||
}
|
||||
}
|
||||
|
||||
$this->setPost('product', $productID);
|
||||
$this->setPost('notifyEmail', implode(',', $this->request('notifyEmail', array())));
|
||||
|
||||
$control = $this->loadController('bug', 'create');
|
||||
$this->requireFields('title,pri,severity,type,openedBuild');
|
||||
|
||||
$control->create($productID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(isset($data->result) and !isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$bug = $this->loadModel('bug')->getByID($data->id);
|
||||
|
||||
return $this->send(200, $this->format($bug, 'activatedDate:time,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,mailto:userList,resolvedBy:user,resolvedDate:time,closedBy:user,closedDate:time,lastEditedBy:user,lastEditedDate:time,deadline:date,deleted:bool'));
|
||||
}
|
||||
}
|
76
api/v1/entries/build.php
Normal file
76
api/v1/entries/build.php
Normal file
@ -0,0 +1,76 @@
|
||||
<?php
|
||||
/**
|
||||
* The build entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class buildEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $buildID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($buildID)
|
||||
{
|
||||
$control = $this->loadController('build', 'view');
|
||||
$control->view($buildID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'success') return $this->send(200, $this->format($data->data->build, 'builder:user,stories:idList,bugs:idList,deleted:bool'));
|
||||
|
||||
/* Exception handling. */
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $buildID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($buildID)
|
||||
{
|
||||
$oldBuild = $this->loadModel('build')->getByID($buildID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'execution,product,name,builder,date,scmPath,filePath,desc';
|
||||
$this->batchSetPost($fields, $oldBuild);
|
||||
|
||||
$control = $this->loadController('build', 'edit');
|
||||
$control->edit($buildID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or (isset($data->message) and $data->message == '404 Not found')) return $this->send404();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$build = $this->build->getByID($buildID);
|
||||
return $this->send(200, $this->format($build, 'builder:user,stories:idList,bugs:idList,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $buildID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($buildID)
|
||||
{
|
||||
$control = $this->loadController('build', 'delete');
|
||||
$control->delete($buildID, 'true');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
72
api/v1/entries/builds.php
Normal file
72
api/v1/entries/builds.php
Normal file
@ -0,0 +1,72 @@
|
||||
<?php
|
||||
/**
|
||||
* The builds entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class buildsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
if(empty($projectID)) $projectID = $this->param('project', 0);
|
||||
if(empty($projectID)) return $this->sendError(400, "Need project id.");
|
||||
|
||||
$control = $this->loadController('project', 'build');
|
||||
$control->build($projectID, $this->param('type', 'all'), $this->param('param', 0), $this->param('order', 't1.date_desc,t1.id_desc'));
|
||||
$data = $this->getData();
|
||||
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$result = array();
|
||||
foreach($data->data->projectBuilds as $productID => $builds)
|
||||
{
|
||||
foreach($builds as $build) $result[] = $this->format($build, 'bugs:idList,stories:idList,builder:user,deleted:bool');
|
||||
}
|
||||
|
||||
return $this->send(200, array('total' => count($result), 'builds' => $result));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($projectID = 0)
|
||||
{
|
||||
if(!$projectID) $projectID = $this->param('project', 0);
|
||||
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
$fields = 'execution,product,name,builder,date,scmPath,filePath,desc,branch';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('build', 'create');
|
||||
$this->requireFields('execution,product,name,builder,date');
|
||||
|
||||
$control->create(0, 0, $projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(isset($data->result) and !isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$build = $this->loadModel('build')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $build);
|
||||
}
|
||||
}
|
30
api/v1/entries/ciresults.php
Normal file
30
api/v1/entries/ciresults.php
Normal file
@ -0,0 +1,30 @@
|
||||
<?php
|
||||
/**
|
||||
* The ciresults entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class ciresultsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$control = $this->loadController('ci', 'commitResult');
|
||||
$control->commitResult();
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
return $this->send(201, array());
|
||||
}
|
||||
}
|
48
api/v1/entries/config.php
Normal file
48
api/v1/entries/config.php
Normal file
@ -0,0 +1,48 @@
|
||||
<?php
|
||||
/**
|
||||
* The config entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class configEntry extends baseEntry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $name language,version,timezone etc.
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($name)
|
||||
{
|
||||
$config = array('name' => $name);
|
||||
|
||||
switch($name)
|
||||
{
|
||||
case 'language':
|
||||
$config['value'] = $this->config->default->lang;
|
||||
break;
|
||||
case 'version':
|
||||
$config['value'] = $this->config->version;
|
||||
break;
|
||||
case 'charset':
|
||||
$config['value'] = $this->config->charset;
|
||||
break;
|
||||
case 'timezone':
|
||||
$config['value'] = $this->config->timezone;
|
||||
break;
|
||||
case 'systemMode':
|
||||
$config['value'] = $this->config->systemMode;
|
||||
break;
|
||||
default:
|
||||
return $this->sendError(400, 'No configuration.');
|
||||
}
|
||||
|
||||
return $this->send(200, $config);
|
||||
}
|
||||
}
|
35
api/v1/entries/configs.php
Normal file
35
api/v1/entries/configs.php
Normal file
@ -0,0 +1,35 @@
|
||||
<?php
|
||||
/**
|
||||
* The configs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class configsEntry extends baseEntry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$configs = array();
|
||||
|
||||
$configs[] = array('key' => 'language', 'value' => $this->config->default->lang);
|
||||
$configs[] = array('key' => 'version', 'value' => $this->config->version);
|
||||
$configs[] = array('key' => 'charset', 'value' => $this->config->charset);
|
||||
$configs[] = array('key' => 'timezone', 'value' => $this->config->timezone);
|
||||
$configs[] = array('key' => 'systemMode', 'value' => $this->config->systemMode);
|
||||
$configs[] = array('key' => 'hourUnit', 'value' => $this->config->hourUnit);
|
||||
$configs[] = array('key' => 'CRProduct', 'value' => $this->config->CRProduct);
|
||||
$configs[] = array('key' => 'CRExecution', 'value' => $this->config->CRExecution);
|
||||
|
||||
return $this->send(200, $configs);
|
||||
}
|
||||
}
|
70
api/v1/entries/department.php
Normal file
70
api/v1/entries/department.php
Normal file
@ -0,0 +1,70 @@
|
||||
<?php
|
||||
/**
|
||||
* The department entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class departmentEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $departmentID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($departmentID)
|
||||
{
|
||||
$dept = $this->loadModel('dept')->getByID($departmentID);
|
||||
|
||||
if(!$dept) return $this->send404();
|
||||
return $this->send(200, $dept);
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $departmentID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($departmentID)
|
||||
{
|
||||
$oldDept = $this->loadModel('dept')->getByID($departmentID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'parent,name,manager';
|
||||
$this->batchSetPost($fields, $oldDept);
|
||||
|
||||
$this->requireFields('name');
|
||||
$control = $this->loadController('dept', 'edit');
|
||||
$control->edit($departmentID);
|
||||
|
||||
$this->getData();
|
||||
$department = $this->dept->getByID($departmentID);
|
||||
return $this->send(200, $department);
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $departmentID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($departmentID)
|
||||
{
|
||||
$control = $this->loadController('dept', 'delete');
|
||||
$control->delete($departmentID, 'true');
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
20
api/v1/entries/departments.php
Normal file
20
api/v1/entries/departments.php
Normal file
@ -0,0 +1,20 @@
|
||||
<?php
|
||||
/**
|
||||
* The departments entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class departmentsEntry extends entry
|
||||
{
|
||||
public function get()
|
||||
{
|
||||
$depts = $this->loadModel('dept')->getDataStructure();
|
||||
|
||||
return $this->send(200, $depts);
|
||||
}
|
||||
}
|
88
api/v1/entries/doc.php
Normal file
88
api/v1/entries/doc.php
Normal file
@ -0,0 +1,88 @@
|
||||
<?php
|
||||
/**
|
||||
* The doc entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class docEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $docID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($docID)
|
||||
{
|
||||
$this->resetOpenApp($this->param('tab', 'doc'));
|
||||
|
||||
$control = $this->loadController('doc', 'view');
|
||||
$control->view($docID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$doc = $data->data->doc;
|
||||
|
||||
unset($doc->draft);
|
||||
if(!empty($doc->files)) $doc->files = array_values((array)$doc->files);
|
||||
|
||||
/* Set lib name */
|
||||
$doc->libName = $data->data->lib->name;
|
||||
|
||||
$preAndNext = $data->data->preAndNext;
|
||||
$doc->preAndNext = array();
|
||||
$doc->preAndNext['pre'] = $preAndNext->pre ? $preAndNext->pre->id : '';
|
||||
$doc->preAndNext['next'] = $preAndNext->next ? $preAndNext->next->id : '';
|
||||
|
||||
return $this->send(200, $this->format($doc, 'addedBy:user,addedDate:time,assignedTo:user,assignedDate:date,editedBy:user,editedDate:time,mailto:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($storyID)
|
||||
{
|
||||
$oldStory = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'type';
|
||||
$this->batchSetPost($fields, $oldStory);
|
||||
$this->setPost('parent', 0);
|
||||
|
||||
$control = $this->loadController('story', 'edit');
|
||||
$control->edit($storyID);
|
||||
|
||||
$this->getData();
|
||||
$story = $this->story->getByID($storyID);
|
||||
return $this->sendSuccess(200, $this->format($story, 'openedDate:time,assignedDate:time,reviewedDate:time,lastEditedDate:time,closedDate:time,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($storyID)
|
||||
{
|
||||
$control = $this->loadController('story', 'delete');
|
||||
$control->delete($storyID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
38
api/v1/entries/doclibs.php
Normal file
38
api/v1/entries/doclibs.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
/**
|
||||
* The doclibs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class doclibsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$type = $this->param('type', 0);
|
||||
$objectID = $this->param('objectID', 0);
|
||||
|
||||
$libs = $this->loadModel('doc')->getLibs($type, $this->param('extra', ''), $this->param('appendLibs', ''), $objectID);
|
||||
$result = array();
|
||||
foreach($libs as $libID => $libName)
|
||||
{
|
||||
$lib = new stdclass();
|
||||
$lib->id = $libID;
|
||||
$lib->name = $libName;
|
||||
$result[] = $lib;
|
||||
}
|
||||
krsort($result);
|
||||
|
||||
return $this->send(200, array('libs' => array_values($result)));
|
||||
}
|
||||
}
|
38
api/v1/entries/docs.php
Normal file
38
api/v1/entries/docs.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
/**
|
||||
* The docs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class docsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($libID = 0)
|
||||
{
|
||||
if(empty($libID)) $libID = $this->param('lib', 0);
|
||||
if(empty($libID)) return $this->sendError(400, 'Need lib id.');
|
||||
|
||||
$docTree = $this->loadModel('doc')->getDocTree($libID);
|
||||
|
||||
foreach($docTree as $i => $module)
|
||||
{
|
||||
if(empty($module->id))
|
||||
{
|
||||
unset($docTree[$i]);
|
||||
foreach($module->children as $doc) $docTree[] = $doc;
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, array('docs' => array_values($docTree)));
|
||||
}
|
||||
}
|
24
api/v1/entries/error.php
Normal file
24
api/v1/entries/error.php
Normal file
@ -0,0 +1,24 @@
|
||||
<?php
|
||||
/**
|
||||
* The error entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class errorEntry extends entry
|
||||
{
|
||||
/**
|
||||
* 404 Not Found.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function notFound()
|
||||
{
|
||||
return $this->send(404, array('error' => 'not found'));
|
||||
}
|
||||
}
|
157
api/v1/entries/execution.php
Normal file
157
api/v1/entries/execution.php
Normal file
@ -0,0 +1,157 @@
|
||||
<?php
|
||||
/**
|
||||
* The execution entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class executionEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($executionID)
|
||||
{
|
||||
$fields = $this->param('fields');
|
||||
$status = $this->param('status', 'all');
|
||||
|
||||
$control = $this->loadController('execution', 'view');
|
||||
$control->view($executionID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$execution = $this->format($data->data->execution, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,PM:user,PO:user,RD:user,QD:user,whitelist:userList,begin:date,end:date,realBegan:date,realEnd:date,deleted:bool');
|
||||
|
||||
$execution->progress = ($execution->totalConsumed + $execution->totalLeft) ? round($execution->totalConsumed / ($execution->totalConsumed + $execution->totalLeft) * 100, 1) : 0;
|
||||
$execution->teamMembers = array_values((array)$data->data->teamMembers);
|
||||
$execution->products = array();
|
||||
foreach($data->data->products as $productID => $executionProduct)
|
||||
{
|
||||
if($status == 'noclosed' and $executionProduct->status == 'closed') continue;
|
||||
|
||||
$product = new stdclass();
|
||||
$product->id = $executionProduct->id;
|
||||
$product->name = $executionProduct->name;
|
||||
$product->plans = array();
|
||||
foreach($executionProduct->plans as $planID)
|
||||
{
|
||||
$plan = new stdclass();
|
||||
$plan->id = trim($planID, ',');
|
||||
$plan->name = $data->data->planGroups->{$productID}->{$plan->id};
|
||||
$product->plans[] = $plan;
|
||||
}
|
||||
$execution->products[] = $product;
|
||||
}
|
||||
|
||||
$this->loadModel('testcase');
|
||||
$execution->caseReview = ($this->config->testcase->needReview or !empty($this->config->testcase->forceReview));
|
||||
|
||||
if(!$fields) $this->send(200, $execution);
|
||||
|
||||
$users = $data->data->users;
|
||||
|
||||
/* Set other fields. */
|
||||
$fields = explode(',', strtolower($fields));
|
||||
foreach($fields as $field)
|
||||
{
|
||||
switch($field)
|
||||
{
|
||||
case 'modules':
|
||||
$control = $this->loadController('tree', 'browsetask');
|
||||
$control->browsetask($executionID);
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$execution->modules = $data->data->tree;
|
||||
}
|
||||
case 'builds':
|
||||
$execution->builds = $this->loadModel('build')->getBuildPairs($productID, 'all', 'noempty,noterminate,nodone', $executionID, 'execution');
|
||||
break;
|
||||
case 'moduleoptionmenu':
|
||||
$execution->moduleOptionMenu = $this->loadModel('tree')->getTaskOptionMenu($executionID, 0, 0, 'allModule');
|
||||
break;
|
||||
case 'members':
|
||||
$execution->members = $this->loadModel('user')->getTeamMemberPairs($executionID, 'execution', 'nodeleted');;
|
||||
unset($execution->members['']);
|
||||
break;
|
||||
case 'stories':
|
||||
$stories = $this->loadModel('story')->getExecutionStories($executionID);
|
||||
foreach($stories as $storyID => $story) $stories[$storyID] = $this->filterFields($story, 'id,title,module,pri,status,stage,estimate');
|
||||
|
||||
$execution->stories = array_values($stories);
|
||||
break;
|
||||
case 'actions':
|
||||
$actions = $data->data->actions;
|
||||
$execution->actions = $this->loadModel('action')->processActionForAPI($actions, $users, $this->lang->execution);
|
||||
break;
|
||||
case "dynamics":
|
||||
$dynamics = $data->data->dynamics;
|
||||
$execution->dynamics = $this->loadModel('action')->processDynamicForAPI($dynamics);
|
||||
break;
|
||||
case 'chartdata':
|
||||
list($dateList, $interval) = $this->loadModel('execution')->getDateList($execution->begin, $execution->end, 'noweekend', '0', 'Y-m-d');
|
||||
$execution->chartData = $this->execution->buildBurnData($executionID, $dateList, 'noweekend', 'left');
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, $execution);
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($executionID)
|
||||
{
|
||||
$oldExecution = $this->loadModel('execution')->getByID($executionID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'project,code,name,begin,end,lifetime,desc,days,acl,status,PO,PM,QD,RD';
|
||||
$this->batchSetPost($fields, $oldExecution);
|
||||
|
||||
$this->setPost('whitelist', $this->request('whitelist', explode(',', $oldExecution->whitelist)));
|
||||
|
||||
$products = $this->loadModel('product')->getProducts($executionID);
|
||||
$this->setPost('products', $this->request('products', array_keys($products)));
|
||||
|
||||
$control = $this->loadController('execution', 'edit');
|
||||
$control->edit($executionID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(!isset($data->result)) return $this->sendError(400, 'error');
|
||||
|
||||
$execution = $this->execution->getByID($executionID);
|
||||
return $this->send(200, $this->format($execution, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,PM:user,PO:user,RD:user,QD:user,whitelist:userList,begin:date,end:date,realBegan:date,realEnd:date,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($executionID)
|
||||
{
|
||||
$control = $this->loadController('execution', 'delete');
|
||||
$control->delete($executionID, 'true');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
72
api/v1/entries/executionbugs.php
Normal file
72
api/v1/entries/executionbugs.php
Normal file
@ -0,0 +1,72 @@
|
||||
<?php
|
||||
/**
|
||||
* The execution bugs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class executionBugsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($executionID = 0)
|
||||
{
|
||||
if(!$executionID) $executionID = $this->param('execution', 0);
|
||||
if(empty($executionID)) return $this->sendError(400, 'Need execution id.');
|
||||
|
||||
$control = $this->loadController('execution', 'bug');
|
||||
$control->bug($executionID, $this->param('product', 0), $this->param('branch', 0), $this->param('order', 'status,id_desc'), $this->param('build', 0), $this->param('status', 'all'), 0, 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$bugs = $data->data->bugs;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
$this->loadModel('product');
|
||||
foreach($bugs as $bug)
|
||||
{
|
||||
$status = array('code' => $bug->status, 'name' => $this->lang->bug->statusList[$bug->status]);
|
||||
if($bug->status == 'active' and $bug->confirmed) $status = array('code' => 'confirmed', 'name' => $this->lang->bug->labelConfirmed);
|
||||
if($bug->resolution == 'postponed') $status = array('code' => 'postponed', 'name' => $this->lang->bug->labelPostponed);
|
||||
if(!empty($bug->delay)) $status = array('code' => 'delay', 'name' => $this->lang->bug->overdueBugs);
|
||||
$bug->status = $status['code'];
|
||||
$bug->statusName = $status['name'];
|
||||
|
||||
$product = $this->product->getById($bug->product);
|
||||
$bug->productStatus = $product->status;
|
||||
|
||||
$result[$bug->id] = $this->format($bug, 'activatedDate:time,openedDate:time,assignedDate:time,resolvedDate:time,closedDate:time,lastEditedDate:time,deadline:date,deleted:bool');
|
||||
}
|
||||
|
||||
$storyChangeds = $this->dao->select('t1.id')->from(TABLE_BUG)->alias('t1')
|
||||
->leftJoin(TABLE_STORY)->alias('t2')->on('t1.story=t2.id')
|
||||
->where('t1.id')->in(array_keys($result))
|
||||
->andWhere('t1.story')->ne('0')
|
||||
->andWhere('t1.storyVersion != t2.version')
|
||||
->fetchPairs('id', 'id');
|
||||
foreach($storyChangeds as $bugID)
|
||||
{
|
||||
$status = array('code' => 'storyChanged', 'name' => $this->lang->bug->changed);
|
||||
$result[$bugID]->status = $status['code'];
|
||||
$result[$bugID]->statusName = $status['name'];
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'bugs' => array_values($result)));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
41
api/v1/entries/executionbuilds.php
Normal file
41
api/v1/entries/executionbuilds.php
Normal file
@ -0,0 +1,41 @@
|
||||
<?php
|
||||
/**
|
||||
* The execution builds entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class executionBuildsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($executionID = 0)
|
||||
{
|
||||
if(empty($executionID)) $executionID = $this->param('execution', 0);
|
||||
if(empty($executionID)) return $this->sendError(400, "Need execution id.");
|
||||
|
||||
$control = $this->loadController('execution', 'build');
|
||||
$control->build($executionID, $this->param('status', 'all'), $this->param('param', 0), $this->param('order', 't1.date_desc,t1.id_desc'));
|
||||
$data = $this->getData();
|
||||
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$result = array();
|
||||
foreach($data->data->executionBuilds as $builds)
|
||||
{
|
||||
foreach($builds as $build) $result[] = $this->format($build, 'builder:user,bugs:idList,stories:idList,deleted:bool');
|
||||
}
|
||||
|
||||
return $this->send(200, array('total' => count($result), 'builds' => $result));
|
||||
}
|
||||
}
|
49
api/v1/entries/executioncases.php
Normal file
49
api/v1/entries/executioncases.php
Normal file
@ -0,0 +1,49 @@
|
||||
<?php
|
||||
/**
|
||||
* The execution cases entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class executionCasesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($executionID = 0)
|
||||
{
|
||||
if(!$executionID) $executionID = $this->param('execution', 0);
|
||||
if(empty($executionID)) return $this->sendError(400, 'Need execution id.');
|
||||
|
||||
$control = $this->loadController('execution', 'testcase');
|
||||
$control->testcase($executionID, $this->param('product', 0), $this->param('branch', 0), $this->param('status', 'all'), $this->param('module', 0), $this->param('order', 'id_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$cases = $data->data->cases;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
foreach($cases as $case)
|
||||
{
|
||||
$case->statusName = $this->lang->testcase->statusList[$case->status];
|
||||
$result[] = $this->format($case, 'openedDate:time,reviewedDate:date,lastEditedDate:time,lastRunDate:time');
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'cases' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
153
api/v1/entries/executions.php
Normal file
153
api/v1/entries/executions.php
Normal file
@ -0,0 +1,153 @@
|
||||
<?php
|
||||
/**
|
||||
* The executions entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class executionsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
$appendFields = $this->param('fields', '');
|
||||
$withProject = $this->param('withProject', '');
|
||||
if(strpos(strtolower(",{$appendFields},"), ',dropmenu,') !== false) return $this->getDropMenu();
|
||||
|
||||
if($projectID)
|
||||
{
|
||||
$control = $this->loadController('project', 'execution');
|
||||
$control->execution($this->param('status', 'undone'), $projectID, $this->param('order', 'id_desc'), $this->param('product', 0), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$executions = $data->data->executionStats;
|
||||
$pager = $data->data->pager;
|
||||
$projects = $data->data->projects;
|
||||
}
|
||||
else
|
||||
{
|
||||
$control = $this->loadController('execution', 'all');
|
||||
$control->all($this->param('status', 'all'), $this->param('order', 'id_desc'), 0, '', 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$executions = $data->data->executionStats;
|
||||
$pager = $data->data->pager;
|
||||
$projects = $data->data->projects;
|
||||
}
|
||||
|
||||
$result = array();
|
||||
foreach($data->data->executionStats as $execution)
|
||||
{
|
||||
foreach($execution->hours as $field => $value) $execution->$field = $value;
|
||||
|
||||
$execution = $this->filterFields($execution, 'id,name,project,code,type,parent,begin,end,status,openedBy,openedDate,delay,progress,children,' . $appendFields);
|
||||
$result[] = $this->format($execution, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,PM:user,PO:user,RD:user,QD:user,whitelist:userList,begin:date,end:date,realBegan:date,realEnd:date,deleted:bool');
|
||||
}
|
||||
|
||||
$data = array();
|
||||
$data['page'] = $pager->pageID;
|
||||
$data['total'] = $pager->recTotal;
|
||||
$data['limit'] = $pager->recPerPage;
|
||||
$data['executions'] = $result;
|
||||
if(!empty($withProject)) $data['projects'] = $projects;
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($projectID = 0)
|
||||
{
|
||||
$fields = 'project,code,name,begin,end,lifetime,desc,days,percent,parent';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$projectID = $this->param('project', $projectID);
|
||||
$this->setPost('project', $projectID);
|
||||
$this->setPost('acl', $this->request('acl', 'private'));
|
||||
$this->setPost('PO', $this->request('PO', ''));
|
||||
$this->setPost('PM', $this->request('PM', ''));
|
||||
$this->setPost('QD', $this->request('QD', ''));
|
||||
$this->setPost('RD', $this->request('RD', ''));
|
||||
$this->setPost('whitelist', $this->request('whitelist', array()));
|
||||
$this->setPost('products', $this->request('products', array()));
|
||||
$this->setPost('plans', $this->request('plans', array()));
|
||||
|
||||
$control = $this->loadController('execution', 'create'); $this->requireFields('name,code,begin,end,days');
|
||||
$control->create($projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$execution = $this->loadModel('execution')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($execution, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,PM:user,PO:user,RD:user,QD:user,whitelist:userList,begin:date,end:date,realBegan:date,realEnd:date,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get drop menu.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function getDropMenu()
|
||||
{
|
||||
$control = $this->loadController('execution', 'ajaxGetDropMenu');
|
||||
$control->ajaxGetDropMenu($this->request('executionID', 0), $this->request('module', 'execution'), $this->request('method', 'task'), $this->request('extra', ''));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$account = $this->app->user->account;
|
||||
$projects = $data->data->projects;
|
||||
$dropMenu = array('involved' => array(), 'other' => array(), 'closed' => array());
|
||||
foreach($data->data->executions as $projectID => $projectExecutions)
|
||||
{
|
||||
foreach($projectExecutions as $execution)
|
||||
{
|
||||
if(helper::diffDate(date('Y-m-d'), $execution->end) > 0) $execution->delay = true;
|
||||
$teams = $execution->teams;
|
||||
$execution = $this->filterFields($execution, 'id,project,model,type,name,code,status,PM,delay');
|
||||
|
||||
$projectName = zget($projects, $execution->project, '');
|
||||
if($projectName) $execution->name = $projectName . '/' . $execution->name;
|
||||
|
||||
if($execution->status == 'closed')
|
||||
{
|
||||
$dropMenu['closed'][] = $execution;
|
||||
}
|
||||
elseif($execution->status != 'done' and $execution->status != 'closed' and ($execution->PM == $account or isset($teams->$account)))
|
||||
{
|
||||
$dropMenu['involved'][] = $execution;
|
||||
}
|
||||
else
|
||||
{
|
||||
$dropMenu['other'][] = $execution;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, $dropMenu);
|
||||
}
|
||||
}
|
50
api/v1/entries/executionstories.php
Normal file
50
api/v1/entries/executionstories.php
Normal file
@ -0,0 +1,50 @@
|
||||
<?php
|
||||
/**
|
||||
* The execution entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package execution
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class executionStoriesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($executionID)
|
||||
{
|
||||
if(empty($executionID)) $this->param('execution', 0);
|
||||
if(empty($executionID)) return $this->sendError(400, 'Need execution id.');
|
||||
|
||||
$control = $this->loadController('execution', 'story');
|
||||
$control->story($executionID, $this->param('storyType', 'story'), $this->param('order', 'id_desc'), $this->param('status', 'all'), 0, 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$stories = $data->data->stories;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
$this->loadModel('product');
|
||||
foreach($stories as $story)
|
||||
{
|
||||
$product = $this->product->getById($story->product);
|
||||
$story->productStatus = $product->status;
|
||||
|
||||
$result[] = $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList');
|
||||
}
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'stories' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
85
api/v1/entries/feedback.php
Normal file
85
api/v1/entries/feedback.php
Normal file
@ -0,0 +1,85 @@
|
||||
<?php
|
||||
/**
|
||||
* The product entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class feedbackEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $feedbackID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($feedbackID)
|
||||
{
|
||||
$control = $this->loadController('feedback', 'adminView');
|
||||
$control->adminView($feedbackID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
$feedback = $data->data->feedback;
|
||||
|
||||
$feedback->publicStatus = $feedback->public;
|
||||
$feedback->productName = $data->data->product;
|
||||
$feedback->moduleName = isset($data->data->modulePath[0]->name) ? $data->data->modulePath[0]->name : '/';
|
||||
$feedback->resultType = $data->data->type;
|
||||
if(isset($feedback->resultInfo) and $feedback->resultInfo->deleted == 0) $feedback->resultStatus = $this->loadModel('feedback')->processStatus($feedback->resultType, $feedback->resultInfo);
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$feedback->actions = $this->loadModel('action')->processActionForAPI($data->data->actions, $data->data->users, $this->lang->feedback);
|
||||
return $this->send(200, $this->format($feedback, 'activatedDate:time,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,mailto:userList,resolvedBy:user,resolvedDate:time,closedBy:user,closedDate:time,lastEditedBy:user,lastEditedDate:time,deadline:date,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $feedbackID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($feedbackID)
|
||||
{
|
||||
$oldFeedback = $this->loadModel('feedback')->getById($feedbackID);
|
||||
|
||||
$fields = 'module,product,type,title,public,desc,status,feedbackBy,notifyEmail,notify,uid';
|
||||
$this->batchSetPost($fields, $oldFeedback);
|
||||
|
||||
$control = $this->loadController('feedback', 'edit');
|
||||
$control->edit($feedbackID, '');
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(!isset($data->result)) return $this->sendError(400, 'error');
|
||||
|
||||
$feedback = $this->feedback->getByID($feedbackID);
|
||||
|
||||
return $this->send(200, $this->format($feedback, 'openedBy:user,openedDate:time,reviewedBy:user,reviewedDate:time,processedBy:user,processedDate:time,closedBy:user,closedDate:time,editedBy:user,editedDate:time,mailto:userList,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $feedbackID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($feedbackID)
|
||||
{
|
||||
$control = $this->loadController('feedback', 'delete');
|
||||
$control->delete($feedbackID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
||||
|
39
api/v1/entries/feedbackassignto.php
Normal file
39
api/v1/entries/feedbackassignto.php
Normal file
@ -0,0 +1,39 @@
|
||||
<?php
|
||||
/**
|
||||
* The feedback assignto entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class feedbackAssignToEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $feedbackID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($feedbackID)
|
||||
{
|
||||
$feedback = $this->loadModel('feedback')->getById($feedbackID);
|
||||
|
||||
$fields = 'assignedTo,comment,mailto';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('feedback', 'assignTo');
|
||||
$control->assignTo($feedbackID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$feedback = $this->loadModel('feedback')->getById($feedbackID);
|
||||
|
||||
return $this->send(200, $this->format($feedback, 'activatedDate:time,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,mailto:userList,resolvedBy:user,resolvedDate:time,closedBy:user,closedDate:time,lastEditedBy:user,lastEditedDate:time,deadline:date,deleted:bool'));
|
||||
}
|
||||
}
|
41
api/v1/entries/feedbackclose.php
Normal file
41
api/v1/entries/feedbackclose.php
Normal file
@ -0,0 +1,41 @@
|
||||
<?php
|
||||
/**
|
||||
* The feedback close entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class feedbackCloseEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $feedbackID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($feedbackID)
|
||||
{
|
||||
$feedback = $this->loadModel('feedback')->getById($feedbackID);
|
||||
|
||||
$fields = 'closedReason,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
if(empty($_POST)) $this->setPost('status', 'closed');
|
||||
|
||||
$control = $this->loadController('feedback', 'close');
|
||||
$control->close($feedbackID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$feedback = $this->loadModel('feedback')->getById($feedbackID);
|
||||
|
||||
return $this->send(200, $feedback);
|
||||
}
|
||||
}
|
97
api/v1/entries/feedbacks.php
Normal file
97
api/v1/entries/feedbacks.php
Normal file
@ -0,0 +1,97 @@
|
||||
<?php
|
||||
/**
|
||||
* The executions entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class feedbacksEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
if(strpos(strtolower($this->param('fields')), 'moduleandproduct') !== false) return $this->getModuleAndProduct();
|
||||
|
||||
$control = $this->loadController('feedback', 'admin');
|
||||
$control->admin($this->param('status', 'unclosed'), 0, $this->param('orderBy', 'id_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$feedbacks = $data->data->feedbacks;
|
||||
$pager = $data->data->pager;
|
||||
|
||||
$result = array();
|
||||
foreach($feedbacks as $feedback)
|
||||
{
|
||||
$result[] = $this->format($feedback, 'openedBy:user,openedDate:time,reviewedBy:user,reviewedDate:time,processedBy:user,processedDate:time,closedBy:user,closedDate:time,editedBy:user,editedDate:time,assignedTo:user,mailto:userList,deleted:bool');
|
||||
}
|
||||
|
||||
$data = array();
|
||||
$data['page'] = $pager->pageID;
|
||||
$data['total'] = $pager->recTotal;
|
||||
$data['limit'] = $pager->recPerPage;
|
||||
$data['feedbacks'] = $result;
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$fields = 'module,product,type,title,public,desc,status,feedbackBy,notify,uid';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('notifyEmail', $this->request('notifyEmail', ''));
|
||||
|
||||
$control = $this->loadController('feedback', 'create');
|
||||
$this->requireFields('title,product');
|
||||
$control->create();
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$feedback = $this->loadModel('feedback')->getById($data->id);
|
||||
|
||||
return $this->send(201, $this->format($feedback, 'openedBy:user,openedDate:time,reviewedBy:user,reviewedDate:time,processedBy:user,processedDate:time,closedBy:user,closedDate:time,editedBy:user,editedDate:time,assignedTo:user,assignedDate:time,feedbackBy:user,mailto:userList,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function getModuleAndProduct()
|
||||
{
|
||||
$control = $this->loadController('feedback', 'create');
|
||||
$control->create();
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
$modules = $data->data->modules;
|
||||
$products = $data->data->products;
|
||||
|
||||
$data = array();
|
||||
$data['modules'] = $modules;
|
||||
$data['products'] = $products;
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
|
||||
}
|
45
api/v1/entries/file.php
Normal file
45
api/v1/entries/file.php
Normal file
@ -0,0 +1,45 @@
|
||||
<?php
|
||||
/**
|
||||
* The file entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class fileEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($fileID)
|
||||
{
|
||||
$control = $this->loadController('file', 'download');
|
||||
$control->download($fileID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($fileID)
|
||||
{
|
||||
$uid = $this->param('uid', '');
|
||||
$action = $this->param('action', '');
|
||||
if($action == 'remove') unset($_SESSION['album']['used'][$uid][$fileID]);
|
||||
|
||||
return $this->send(200, array('id' => $fileID));
|
||||
}
|
||||
}
|
34
api/v1/entries/files.php
Normal file
34
api/v1/entries/files.php
Normal file
@ -0,0 +1,34 @@
|
||||
<?php
|
||||
/**
|
||||
* The files entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class filesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$uid = $this->param('uid', '');
|
||||
|
||||
$control = $this->loadController('file', 'ajaxUpload');
|
||||
$control->ajaxUpload($uid);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->send(200, array('id' => $data->id, 'url' => $data->url));
|
||||
}
|
||||
}
|
39
api/v1/entries/gitlabwebhook.php
Normal file
39
api/v1/entries/gitlabwebhook.php
Normal file
@ -0,0 +1,39 @@
|
||||
<?php
|
||||
/**
|
||||
* The repo entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author xiawenlong <xiawenlong@cnezsoft.com>
|
||||
* @package repo
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class gitlabWebhookEntry extends baseEntry
|
||||
{
|
||||
|
||||
/**
|
||||
* Repo webhook.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$repoID = $this->param('repoID');
|
||||
if(empty($repoID)) return;
|
||||
|
||||
$this->loadModel('repo');
|
||||
|
||||
$repo = $this->repo->getRepoByID($repoID);
|
||||
if(empty($repo)) return;
|
||||
|
||||
$headers = getallheaders(); /* Fetch all HTTP request headers. */
|
||||
$event = isset($headers['X-Gitlab-Event']) ? $headers['X-Gitlab-Event'] : '';
|
||||
$token = isset($headers['X-Gitlab-Token']) ? $headers['X-Gitlab-Token'] : '';
|
||||
if(empty($event) || empty($token)) return;
|
||||
|
||||
$this->repo->handleWebhook($event, $token, $this->requestBody, $repo);
|
||||
}
|
||||
|
||||
}
|
49
api/v1/entries/groups.php
Normal file
49
api/v1/entries/groups.php
Normal file
@ -0,0 +1,49 @@
|
||||
<?php
|
||||
/**
|
||||
* The groups entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class groupsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$groups = $this->loadModel('group')->getList();
|
||||
$privsGroup = $this->dao->select('`group`,module, method')->from(TABLE_GROUPPRIV)->orderBy('module')->fetchGroup('group');
|
||||
$usersGroup = $this->dao->select('t1.`group`,t1.account,t2.realname')->from(TABLE_USERGROUP)->alias('t1')
|
||||
->leftJoin(TABLE_USER)->alias('t2')->on('t1.account=t2.account')
|
||||
->fetchGroup('group');
|
||||
|
||||
foreach($groups as $i => $group)
|
||||
{
|
||||
if($group->acl)
|
||||
{
|
||||
$acl = json_decode($group->acl, true);
|
||||
$group->acl = array();
|
||||
$group->acl['views'] = $acl['views'];
|
||||
}
|
||||
$privs = zget($privsGroup, $group->id, array());
|
||||
$group->privs = array();
|
||||
foreach($privs as $priv) $group->privs[$priv->module][$priv->method] = true;
|
||||
|
||||
$accounts = zget($usersGroup, $group->id, array());
|
||||
$group->accounts = array();
|
||||
foreach($accounts as $account) $group->accounts[$account->account] = $account->realname;
|
||||
|
||||
$groups[$i] = $group;
|
||||
}
|
||||
|
||||
return $this->send(200, $groups);
|
||||
}
|
||||
}
|
111
api/v1/entries/hostheartbeat.php
Normal file
111
api/v1/entries/hostheartbeat.php
Normal file
@ -0,0 +1,111 @@
|
||||
<?php
|
||||
/**
|
||||
* The host entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2022 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Yuchun Li <liyuchun@easycorp.ltd>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class hostHeartbeatEntry extends baseEntry
|
||||
{
|
||||
/**
|
||||
* Listen host heartbeat.
|
||||
*
|
||||
* @param int|string $userID
|
||||
* @access public
|
||||
* @return void
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
/* Check authorize. */
|
||||
$header = getallheaders();
|
||||
$token = isset($header['Authorization']) ? substr($header['Authorization'], 7) : '';
|
||||
$secret = isset($this->requestBody->secret) ? $this->requestBody->secret : '';
|
||||
if(!$secret and !$token) return $this->sendError(401, 'Unauthorized');
|
||||
|
||||
/* Check param. */
|
||||
$status = $this->requestBody->status;
|
||||
$vms = $this->requestBody->Vms;
|
||||
$zap = $this->requestBody->port;
|
||||
$now = helper::now();
|
||||
if(!$status) return $this->sendError(400, 'Params error.');
|
||||
|
||||
$conditionField = $secret ? 'secret' : 'tokenSN';
|
||||
$conditionValue = $secret ? $secret : $token;
|
||||
|
||||
$this->dao = $this->loadModel('common')->dao;
|
||||
$hostInfo = $this->dao->select('id,tokenSN')->from(TABLE_ZAHOST)
|
||||
->beginIF($secret)->where('secret')->eq($secret)->fi()
|
||||
->beginIF(!$secret)->where('tokenSN')->eq($token)
|
||||
->andWhere('tokenTime')->gt($now)->fi()
|
||||
->fetch();
|
||||
if(empty($hostInfo->id))
|
||||
{
|
||||
if(empty($token)) return $this->sendError(400, 'Secret error.');
|
||||
$hostInfo = $this->dao->select('id,tokenSN')->from(TABLE_ZAHOST)
|
||||
->where('oldTokenSN')->eq($token)
|
||||
->andWhere('tokenTime')->gt(date(DT_DATETIME1, strtotime($now) - 30))->fi()
|
||||
->fetch();
|
||||
if(empty($hostInfo->id)) return $this->sendError(400, 'Secret error.');
|
||||
}
|
||||
|
||||
$host = new stdclass();
|
||||
$host->status = $status;
|
||||
if($secret)
|
||||
{
|
||||
$host->tokenSN = md5($secret . $now);
|
||||
$host->tokenTime = date('Y-m-d H:i:s', time() + 7200);
|
||||
$host->oldTokenSN = $hostInfo->tokenSN;
|
||||
}
|
||||
$host->heartbeat = $now;
|
||||
$host->zap = $zap;
|
||||
$this->dao->update(TABLE_ZAHOST)->data($host)->where($conditionField)->eq($conditionValue)->exec();
|
||||
|
||||
if($vms)
|
||||
{
|
||||
foreach($vms as $vm)
|
||||
{
|
||||
$heartbeat = strtotime(substr($vm->heartbeat, 0, 19));
|
||||
$vmData = array(
|
||||
'vnc' => $vm->vncPortOnHost,
|
||||
'zap' => $vm->agentPortOnHost,
|
||||
'ztf' => $vm->ztfPortOnHost,
|
||||
'zd' => $vm->zdPortOnHost,
|
||||
'ssh' => $vm->sshPortOnHost,
|
||||
'status' => $vm->status,
|
||||
'extranet' => $vm->ip,
|
||||
);
|
||||
|
||||
if(!$vm->sshPortOnHost) unset($vmData['ssh']);
|
||||
|
||||
if($heartbeat > 0) $vmData['heartbeat'] = date("Y-m-d H:i:s", $heartbeat);
|
||||
|
||||
$this->dao->update(TABLE_ZAHOST)->data($vmData)->where('mac')->eq($vm->macAddress)->exec();
|
||||
|
||||
if($vm->status == 'running')
|
||||
{
|
||||
$node = $this->loadModel('zanode')->getNodeByMac($vm->macAddress);
|
||||
if(!empty($node))
|
||||
{
|
||||
$snaps = $this->loadModel('zanode')->getSnapshotList($node->id);
|
||||
if(empty($snaps))
|
||||
{
|
||||
if($vm->status == 'running') $this->loadModel('zanode')->createDefaultSnapshot($node->id);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(!$secret) return $this->sendSuccess(200, 'success');
|
||||
|
||||
$host->tokenTimeUnix = strtotime($host->tokenTime);
|
||||
unset($host->status);
|
||||
unset($host->tokenTime);
|
||||
unset($host->oldTokenSN);
|
||||
return $this->send(200, $host);
|
||||
}
|
||||
}
|
64
api/v1/entries/hostsubmit.php
Normal file
64
api/v1/entries/hostsubmit.php
Normal file
@ -0,0 +1,64 @@
|
||||
<?php
|
||||
/**
|
||||
* The host entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2022 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Ke Zhao <zhaoke@easycorp.ltd>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class hostSubmitEntry extends baseEntry
|
||||
{
|
||||
/**
|
||||
* Listen host task finish submit.
|
||||
*
|
||||
* @param int|string $userID
|
||||
* @access public
|
||||
* @return void
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
/* Check authorize. */
|
||||
$header = getallheaders();
|
||||
$token = isset($header['Authorization']) ? substr($header['Authorization'], 7) : '';
|
||||
if(!$token) return $this->sendError(401, 'Unauthorized');
|
||||
|
||||
$now = helper::now();
|
||||
|
||||
/* Check param. */
|
||||
$image = new stdclass();
|
||||
$task = $this->requestBody->task;
|
||||
$image->status = $this->requestBody->status;
|
||||
|
||||
$this->dao = $this->loadModel('common')->dao;
|
||||
$id = $this->dao->select('id')->from(TABLE_ZAHOST)
|
||||
->where('tokenSN')->eq($token)
|
||||
->andWhere('tokenTime')->gt($now)->fi()
|
||||
->fetch('id');
|
||||
|
||||
if(!$id) return $this->sendError(400, 'Secret error.');
|
||||
|
||||
$imageInfo = $this->dao->select('`status`,`from`', 'name')->from(TABLE_IMAGE)
|
||||
->where('id')->eq($task)
|
||||
->fetch();
|
||||
if(empty($imageInfo)) return $this->sendSuccess(200, 'success');
|
||||
if($imageInfo->from == 'snapshot' && $imageInfo->status == 'restoring')
|
||||
{
|
||||
if(in_array($image->status, array('failed', 'completed'))) $image->status = $image->status == 'completed' ? 'restore_completed' : 'restore_failed';
|
||||
}
|
||||
else if($imageInfo->from == 'snapshot')
|
||||
{
|
||||
if($image->status == 'failed')
|
||||
{
|
||||
$this->dao->delete()->from(TABLE_IMAGE)->where("id")->eq($task)->exec();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
||||
|
||||
$this->dao->update(TABLE_IMAGE)->data($image)->where("id")->eq($task)->exec();
|
||||
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
0
api/v1/entries/index.html
Normal file
0
api/v1/entries/index.html
Normal file
79
api/v1/entries/issue.php
Normal file
79
api/v1/entries/issue.php
Normal file
@ -0,0 +1,79 @@
|
||||
<?php
|
||||
/**
|
||||
* The issue entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class issueEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int|string $issueID. Issues id for Gitlab has '-', such as task-1, bug-1.
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($issueID)
|
||||
{
|
||||
/* If $issueID has '-', go to productIssue entry point for Gitlab. */
|
||||
if(strpos($issueID, '-') !== FALSE) return $this->fetch('productIssue', 'get', array('issueID' => $issueID));
|
||||
|
||||
/* Otherwise, get issue of project. */
|
||||
$control = $this->loadController('issue', 'view');
|
||||
$control->view($issueID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or (isset($data->message) and $data->message == '404 Not found')) return $this->send404();
|
||||
if(isset($data->status) and $data->status == 'success') return $this->send(200, $this->format($data->data->issue, 'createdDate:time,editedDate:time,assignedDate:time'));
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $issueID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($issueID)
|
||||
{
|
||||
$oldIssue = $this->loadModel('issue')->getByID($issueID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'type,title,severity,pri,assignedTo,deadline,desc';
|
||||
$this->batchSetPost($fields, $oldIssue);
|
||||
|
||||
$control = $this->loadController('issue', 'edit');
|
||||
$control->edit($issueID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or (isset($data->message) and $data->message == '404 Not found')) return $this->send404();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$issue = $this->issue->getByID($issueID);
|
||||
return $this->send(200, $this->format($issue, 'createdDate:time,editedDate:time,assignedDate:time'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $issueID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($issueID)
|
||||
{
|
||||
$control = $this->loadController('issue', 'delete');
|
||||
$control->delete($issueID, 'true');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
100
api/v1/entries/issues.php
Normal file
100
api/v1/entries/issues.php
Normal file
@ -0,0 +1,100 @@
|
||||
<?php
|
||||
/**
|
||||
* The issues entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class issuesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
if($projectID) return $this->getProjectIssues($projectID);
|
||||
|
||||
/* Get my issues defaultly. */
|
||||
$control = $this->loadController('my', 'issue');
|
||||
$control->issue($this->param('type', 'assignedTo'), $this->param('order', 'id_desc'), $this->param('total', 0), $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
foreach($data->data->issues as $issue)
|
||||
{
|
||||
$result[] = $this->format($issue, 'createdDate:time,editedDate:time,assignedDate:time');
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'issues' => $result));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get issues of project.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
private function getProjectIssues($projectID)
|
||||
{
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
$control = $this->loadController('issue', 'browse');
|
||||
$control->browse($projectID, $this->param('type', 'all'), 0, $this->param('order', ''), $this->param('total', 0), $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
foreach($data->data->issueList as $issue)
|
||||
{
|
||||
$result[] = $this->format($issue, 'createdDate:time,editedDate:time,assignedDate:time');
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'issues' => $result));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($projectID = 0)
|
||||
{
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
$fields = 'type,title,severity,pri,assignedTo,deadline,desc';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('issue', 'create');
|
||||
$this->requireFields('type,title,severity');
|
||||
|
||||
$control->create($projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(isset($data->result) and!isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$issue = $this->loadModel('issue')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($issue, 'createdDate:time,editedDate:time,assignedDate:time'));
|
||||
}
|
||||
}
|
52
api/v1/entries/jobs.php
Normal file
52
api/v1/entries/jobs.php
Normal file
@ -0,0 +1,52 @@
|
||||
<?php
|
||||
/**
|
||||
* The jobs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2022 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Yanyi Cao <caoyanyi@easycorp.ltd>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class jobsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$control = $this->loadController('job', 'browse');
|
||||
$pipeline = $this->param('pipeline', '');
|
||||
$orderBy = $this->param('order', 'id_desc');
|
||||
|
||||
if(empty($pipeline))
|
||||
{
|
||||
$control->browse($orderBy, 0, $this->param('limit', 100), $this->param('page', 1));
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$result = array();
|
||||
$pager = $data->data->pager;
|
||||
$jobs = $data->data->jobList;
|
||||
foreach($jobs as $job) $result[] = $this->format($job, 'deleted:bool,lastSync:datetime,synced:bool,product:idList');
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'jobs' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
}
|
||||
else
|
||||
{
|
||||
$jobs = $this->loadModel('job')->getList($orderBy, null, $this->param('engine', 'jenkins'), $pipeline);
|
||||
return $this->send(200, array('jobs' => array_values($jobs)));
|
||||
}
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
83
api/v1/entries/langs.php
Normal file
83
api/v1/entries/langs.php
Normal file
@ -0,0 +1,83 @@
|
||||
<?php
|
||||
/**
|
||||
* The langs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class langsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$modules = $this->param('modules', '');
|
||||
$language = $this->param('lang', '');
|
||||
|
||||
if($language and !isset($this->config->langs[$language])) return $this->sendError(400, 'Error lang parameter');
|
||||
if(empty($modules)) return $this->sendError(400, 'Need modules');
|
||||
|
||||
if(empty($language)) $language = 'zh-cn';
|
||||
$this->app->setClientLang($language);
|
||||
|
||||
global $filter;
|
||||
$rule = $filter->default->moduleName;
|
||||
$modules = explode(',', $modules);
|
||||
foreach($modules as $module)
|
||||
{
|
||||
if($module == 'all')
|
||||
{
|
||||
$loadedModule = array();
|
||||
foreach(glob($this->app->getModuleRoot() . '*') as $modulePath)
|
||||
{
|
||||
if(!is_dir($modulePath)) continue;
|
||||
|
||||
$moduleName = basename($modulePath);
|
||||
if(!validater::checkByRule($moduleName, $rule)) continue;
|
||||
$this->app->loadLang($moduleName);
|
||||
|
||||
$loadedModule[$moduleName] = $moduleName;
|
||||
}
|
||||
|
||||
foreach(glob($this->app->getExtensionRoot() . '*') as $extensionPath)
|
||||
{
|
||||
if(!is_dir($extensionPath)) continue;
|
||||
|
||||
$edition = basename($extensionPath);
|
||||
if($edition == 'lite') continue;
|
||||
if($edition == 'biz' or $edition == 'max')
|
||||
{
|
||||
if($this->config->edition == 'open') continue;
|
||||
if($this->config->edition != 'open' and $this->config->edition != $edition) continue;
|
||||
}
|
||||
|
||||
foreach(glob($extensionPath . '/*') as $modulePath)
|
||||
{
|
||||
if(!is_dir($modulePath)) continue;
|
||||
|
||||
$moduleName = basename($modulePath);
|
||||
if(!validater::checkByRule($moduleName, $rule)) continue;
|
||||
if(isset($loadedModule[$moduleName])) continue;
|
||||
|
||||
$this->app->loadLang($moduleName);
|
||||
|
||||
$loadedModule[$moduleName] = $moduleName;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if(validater::checkByRule($module, $rule)) $this->app->loadLang($module);
|
||||
}
|
||||
|
||||
return $this->send(200, $this->lang);
|
||||
}
|
||||
}
|
80
api/v1/entries/meetings.php
Normal file
80
api/v1/entries/meetings.php
Normal file
@ -0,0 +1,80 @@
|
||||
<?php
|
||||
/**
|
||||
* The meetings entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class meetingsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
if(empty($projectID)) $projectID = $this->param('project', 0);
|
||||
if(empty($projectID)) return $this->sendError(400, 'Need project id.');
|
||||
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
/* Get meetings by project. */
|
||||
$control = $this->loadController('meeting', 'browse');
|
||||
$control->browse($projectID, $this->param('status', 'all'), '', $this->param('order', 'id_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
foreach($data->data->meetings as $risk)
|
||||
{
|
||||
$result[] = $this->format($risk, 'createdDate:time,editedDate:time');
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'meetings' => $result));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($projectID = 0)
|
||||
{
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
$fields = 'source,name,category,strategy,status,impact,probability,rate,identifiedDate,plannedClosedDate,actualClosedDate,resolvedBy,assignedTo,prevention,remedy,resolution';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('impact', $this->request('impact', 3));
|
||||
$this->setPost('probability', $this->request('probability', 3));
|
||||
$this->setPost('rate', $this->request('rate', 9));
|
||||
$this->setPost('pri', 'middle');
|
||||
|
||||
$control = $this->loadController('risk', 'create');
|
||||
$this->requireFields('name');
|
||||
|
||||
$control->create($projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(isset($data->result) and !isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$risk = $this->loadModel('risk')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($risk, 'createdDate:time,editedDate:time'));
|
||||
}
|
||||
}
|
43
api/v1/entries/modules.php
Normal file
43
api/v1/entries/modules.php
Normal file
@ -0,0 +1,43 @@
|
||||
<?php
|
||||
/**
|
||||
* The modules entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class modulesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* Get method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$objectType = $this->param('type', '');
|
||||
$objectID = $this->param('id', '');
|
||||
|
||||
if(!$objectType or !$objectID) return $this->sendError(400, 'Need id and type.');
|
||||
if(!in_array($objectType, array('story', 'task', 'bug', 'case'))) return $this->sendError(400, 'Type is not allowed');
|
||||
|
||||
if($objectType == 'task')
|
||||
{
|
||||
$control = $this->loadController('tree', 'browsetask');
|
||||
$control->browseTask($objectID);
|
||||
}
|
||||
else
|
||||
{
|
||||
$control = $this->loadController('tree', 'browse');
|
||||
$control->browse($objectID, $objectType);
|
||||
}
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'success') return $this->send(200, array('modules' => $data->data->tree));
|
||||
|
||||
return $this->send400(isset($data->message) ? $data->message: 'error');
|
||||
}
|
||||
}
|
33
api/v1/entries/mr.php
Normal file
33
api/v1/entries/mr.php
Normal file
@ -0,0 +1,33 @@
|
||||
<?php
|
||||
/**
|
||||
* The mr entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2022 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author liyuchun <liyuchun@easysoft.ltd>
|
||||
* @package repo
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class mrEntry extends baseEntry
|
||||
{
|
||||
/**
|
||||
* Create mr.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$fields = 'repoID,jobID,sourceBranch,targetBranch,diffs,mergeStatus';
|
||||
$this->batchSetPost($fields);
|
||||
$postData = fixer::input('post')->get();
|
||||
|
||||
$this->loadController('mr', 'create');
|
||||
$MRID = $this->loadModel('mr')->apiCreate();
|
||||
if(dao::isError()) $this->sendError(400, dao::getError());
|
||||
|
||||
$MR = $this->mr->getByID($MRID);
|
||||
return $this->send(201, $MR);
|
||||
}
|
||||
}
|
46
api/v1/entries/options.php
Normal file
46
api/v1/entries/options.php
Normal file
@ -0,0 +1,46 @@
|
||||
<?php
|
||||
/**
|
||||
* The options entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class optionsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param string $type
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($type = '')
|
||||
{
|
||||
if(!$type) return $this->sendError(400, 'error');
|
||||
|
||||
$options = array();
|
||||
switch($type)
|
||||
{
|
||||
case 'bug':
|
||||
$this->app->loadLang('bug');
|
||||
$options['type'] = $this->lang->bug->typeList;
|
||||
$options['pri'] = $this->lang->bug->priList;
|
||||
$options['severity'] = $this->lang->bug->severityList;
|
||||
|
||||
$options['modules'] = new stdclass();
|
||||
$product = $this->param('product', 0);
|
||||
if($product) $options['modules'] = $this->loadModel('tree')->getOptionMenu($product, 'bug');
|
||||
|
||||
$execution = $this->param('execution', 0);
|
||||
$options['build'] = $this->loadModel('build')->getBuildPairs($product, 'all', '', $execution, 'execution');
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
return $this->send(200, array('options' => $options));
|
||||
}
|
||||
}
|
24
api/v1/entries/ping.php
Normal file
24
api/v1/entries/ping.php
Normal file
@ -0,0 +1,24 @@
|
||||
<?php
|
||||
/**
|
||||
* The ping entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class pingEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
return $this->send(200, array('token' => session_id(), 'tokenLife' => ini_get('session.gc_maxlifetime')));
|
||||
}
|
||||
}
|
33
api/v1/entries/pipelines.php
Normal file
33
api/v1/entries/pipelines.php
Normal file
@ -0,0 +1,33 @@
|
||||
<?php
|
||||
/**
|
||||
* The pipeline entry point of ZenTaoPMS.
|
||||
* It is only used by Zcli.
|
||||
*
|
||||
* @copyright Copyright 2009-2022 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Yanyi Cao <caoyanyi@easycorp.ltd>
|
||||
* @package pipeline
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class pipelinesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
|
||||
$pipeline = $this->param('pipeline', '');
|
||||
$repoUrl = $this->param('repoUrl', '');
|
||||
if(empty($pipeline) and empty($repoUrl)) return $this->sendError(400, 'The parameter is incorrect!');
|
||||
|
||||
$repo = $this->loadModel('repo')->getRepoByUrl($repoUrl, $pipeline);
|
||||
if(empty($repo['data'])) return $this->sendError(400, $repo['message']);
|
||||
|
||||
return $this->send(200, array('status' => 'success', 'repo' => $repo['data']));
|
||||
}
|
||||
}
|
141
api/v1/entries/product.php
Normal file
141
api/v1/entries/product.php
Normal file
@ -0,0 +1,141 @@
|
||||
<?php
|
||||
/**
|
||||
* The product entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($productID)
|
||||
{
|
||||
$fields = $this->param('fields');
|
||||
|
||||
$control = $this->loadController('product', 'view');
|
||||
$control->view($productID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$product = $this->format($data->data->product, 'createdDate:time,whitelist:userList,createdBy:user,PO:user,RD:user,QD:user,feedback:user');
|
||||
|
||||
$this->loadModel('testcase');
|
||||
$product->caseReview = ($this->config->testcase->needReview or !empty($this->config->testcase->forceReview));
|
||||
|
||||
if(!$fields) return $this->send(200, $product);
|
||||
|
||||
/* Set other fields. */
|
||||
$fields = explode(',', strtolower($fields));
|
||||
foreach($fields as $field)
|
||||
{
|
||||
switch($field)
|
||||
{
|
||||
case 'modules':
|
||||
$control = $this->loadController('tree', 'browse');
|
||||
$control->browse($productID, 'story');
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$product->modules = $data->data->tree;
|
||||
}
|
||||
break;
|
||||
case 'execution':
|
||||
$product->execution = $this->loadModel('product')->getExecutionPairsByProduct($productID);
|
||||
break;
|
||||
case 'bugstatistic':
|
||||
$product->bugStatistic = $this->loadModel('bug')->getStatistic($productID);
|
||||
break;
|
||||
case 'moduleoptionmenu':
|
||||
$modules = $this->loadModel('tree')->getOptionMenu($productID, $this->param('moduleType', 'story'));
|
||||
$product->moduleOptionMenu = array();
|
||||
foreach($modules as $id => $name) $product->moduleOptionMenu[] = array('id' => $id, 'name' => $name);
|
||||
break;
|
||||
case 'parentstories':
|
||||
$product->parentstories= $this->loadModel('story')->getParentStoryPairs($productID);
|
||||
break;
|
||||
case 'builds':
|
||||
$product->builds = $this->loadModel('build')->getBuildPairs($productID, 'all', 'noempty,noterminate,nodone,withbranch', $this->param('object', 0), $this->param('objectType', 'execution'));
|
||||
break;
|
||||
case 'actions':
|
||||
$product->addComment = common::hasPriv('action', 'comment') ? true : false;
|
||||
|
||||
$users = $this->loadModel('user')->getPairs();
|
||||
$actions = $data->data->actions;
|
||||
$product->actions = $this->loadModel('action')->processActionForAPI($actions, $users, $this->lang->product);
|
||||
break;
|
||||
case 'lastexecution':
|
||||
$execution = $this->dao->select('t2.id,t2.name,t2.type')->from(TABLE_PROJECTPRODUCT)->alias('t1')
|
||||
->leftJoin(TABLE_PROJECT)->alias('t2')->on('t1.project = t2.id')
|
||||
->where('t2.deleted')->eq(0)
|
||||
->andWhere('t1.product')->eq($productID)
|
||||
->andWhere('t2.type')->in('sprint,stage')
|
||||
->orderBy('t2.id desc')
|
||||
->limit(1)
|
||||
->fetch();
|
||||
if($execution)
|
||||
{
|
||||
$workhour = $this->loadModel('project')->computerProgress(array($execution->id => $execution));
|
||||
if(isset($workhour[$execution->id])) $execution->progress = $workhour[$execution->id]->progress;
|
||||
}
|
||||
|
||||
$product->lastExecution = $execution;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, $product);
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($productID)
|
||||
{
|
||||
$oldProduct = $this->loadModel('product')->getByID($productID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'program,line,name,PO,QD,RD,type,desc,whitelist,status,acl';
|
||||
$this->batchSetPost($fields, $oldProduct);
|
||||
|
||||
$control = $this->loadController('product', 'edit');
|
||||
$control->edit($productID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$product = $this->product->getByID($productID);
|
||||
return $this->send(200, $this->format($product, 'createdDate:time,whitelist:userList,createdBy:user,PO:user,RD:user,QD:user'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($productID)
|
||||
{
|
||||
$control = $this->loadController('product', 'delete');
|
||||
$control->delete($productID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
205
api/v1/entries/productissue.php
Normal file
205
api/v1/entries/productissue.php
Normal file
@ -0,0 +1,205 @@
|
||||
<?php
|
||||
/**
|
||||
* The productissue entry point of ZenTaoPMS.
|
||||
* It is only used by Gitlab.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productIssueEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param string $issueID, such as task-1, story-1, bug-1
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($issueID)
|
||||
{
|
||||
$this->loadModel('entry');
|
||||
|
||||
$idParams = explode('-', $issueID);
|
||||
if(count($idParams) < 2) $this->sendError(400, 'The id of issue is wrong.');
|
||||
|
||||
$type = $idParams[0];
|
||||
$id = intval($idParams[1]);
|
||||
|
||||
$issue = new stdclass();
|
||||
switch($type)
|
||||
{
|
||||
case 'story':
|
||||
$this->app->loadLang('story');
|
||||
$storyStatus = array('' => '', 'draft' => 'opened', 'reviewing' => 'opened', 'active' => 'opened', 'changing' => 'opened', 'closed' => 'closed');
|
||||
|
||||
$story = $this->dao->select('*')->from(TABLE_STORY)->where('id')->eq($id)->fetch();
|
||||
if(!$story) $this->send404();
|
||||
|
||||
$issue->id = $issueID;
|
||||
$issue->title = $story->title;
|
||||
$issue->labels = array($this->app->lang->story->common, zget($this->app->lang->story->categoryList, $story->category));
|
||||
$issue->pri = $story->pri;
|
||||
$issue->openedDate = $story->openedDate;
|
||||
$issue->openedBy = $story->openedBy;
|
||||
$issue->lastEditedDate = $story->lastEditedDate < '1970-01-01 01:01:01' ? $story->openedDate : $story->lastEditedDate;
|
||||
$issue->lastEditedBy = $story->lastEditedDate < '1970-01-01 01:01:01' ? $story->openedBy : $story->lastEditedBy;
|
||||
$issue->status = $storyStatus[$story->status];
|
||||
$issue->url = helper::createLink('story', 'view', "storyID=$id");
|
||||
|
||||
$storySpec = $this->dao->select('*')->from(TABLE_STORYSPEC)->where('story')->eq($id)->andWhere('version')->eq($story->version)->fetch();
|
||||
$issue->desc = $storySpec->spec;
|
||||
|
||||
$issue->assignedTo = $story->assignedTo == "" ? array() : array($story->assignedTo);
|
||||
|
||||
break;
|
||||
|
||||
case 'bug':
|
||||
$this->app->loadLang('bug');
|
||||
$bugStatus = array('' => '', 'active' => 'opened', 'resolved' => 'opened', 'closed' => 'closed');
|
||||
|
||||
$bug = $this->dao->select('*')->from(TABLE_BUG)->where('id')->eq($id)->fetch();
|
||||
if(!$bug) $this->send404();
|
||||
|
||||
$issue->id = $issueID;
|
||||
$issue->title = $bug->title;
|
||||
$issue->labels = array($this->app->lang->bug->common, zget($this->app->lang->bug->typeList, $bug->type));
|
||||
$issue->pri = $bug->pri;
|
||||
$issue->openedDate = $bug->openedDate;
|
||||
$issue->openedBy = $bug->openedBy;
|
||||
$issue->lastEditedDate = helper::isZeroDate($bug->lastEditedDate) ? $bug->openedDate : $bug->lastEditedDate;
|
||||
$issue->lastEditedBy = helper::isZeroDate($bug->lastEditedDate) ? $bug->openedBy : $bug->lastEditedBy;
|
||||
$issue->status = $bugStatus[$bug->status];
|
||||
$issue->url = helper::createLink('bug', 'view', "bugID=$id");
|
||||
$issue->desc = $bug->steps;
|
||||
|
||||
$issue->assignedTo = $bug->assignedTo == "" ? array() : array($bug->assignedTo);
|
||||
break;
|
||||
|
||||
case 'task':
|
||||
$this->app->loadLang('task');
|
||||
$taskStatus = array('' => '', 'wait' => 'opened', 'doing' => 'opened', 'done' => 'opened', 'pause' => 'opened', 'cancel' => 'opened', 'closed' => 'closed');
|
||||
|
||||
$task = $this->dao->select('*')->from(TABLE_TASK)->where('id')->eq($id)->fetch();
|
||||
if(!$task) $this->send404();
|
||||
|
||||
$issue->id = $issueID;
|
||||
$issue->title = $task->name;
|
||||
$issue->labels = array($this->app->lang->task->common, zget($this->app->lang->task->typeList, $task->type));
|
||||
$issue->pri = $task->pri;
|
||||
$issue->openedDate = $task->openedDate;
|
||||
$issue->openedBy = $task->openedBy;
|
||||
$issue->lastEditedDate = $task->lastEditedDate < '1970-01-01 01:01:01' ? $task->openedDate : $task->lastEditedDate;
|
||||
$issue->lastEditedBy = $task->lastEditedDate < '1970-01-01 01:01:01' ? $task->openedBy : $task->lastEditedBy;
|
||||
$issue->status = $taskStatus[$task->status];
|
||||
$issue->url = helper::createLink('task', 'view', "taskID=$id");
|
||||
$issue->desc = $task->desc;
|
||||
|
||||
/* Get assignees for task, the task object has the type of multiple assign only so far. */
|
||||
$users = $this->dao->select('account')->from(TABLE_TEAM)
|
||||
->where('type')->eq('task')
|
||||
->andWhere('root')->eq($task->id)
|
||||
->fetchAll();
|
||||
if($users)
|
||||
{
|
||||
foreach($users as $user) $issue->assignedTo[] = $user->account;
|
||||
}
|
||||
else
|
||||
{
|
||||
$issue->assignedTo = $task->assignedTo == "" ? array() : array($task->assignedTo);
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
$this->send404();
|
||||
}
|
||||
|
||||
$actions = $this->loadModel('action')->getList($type, $id);
|
||||
|
||||
$issue->comments = array_values($this->processActions($type, $actions));
|
||||
|
||||
/* Get all users in issues so that we can get user detail later in batch. */
|
||||
$accountList = array();
|
||||
foreach($issue->assignedTo as $account) $accountList[] = $account;
|
||||
$accountList[] = $issue->openedBy;
|
||||
$accountList = array_unique($accountList);
|
||||
$profileList = $this->loadModel('user')->getUserDetailsForAPI($accountList);
|
||||
|
||||
/* Set the user detail to assignedTo and openedBy. */
|
||||
foreach($issue->assignedTo as $key => $account)
|
||||
{
|
||||
if($account == 'closed')
|
||||
{
|
||||
$issue->assignedTo = array();
|
||||
break;
|
||||
}
|
||||
|
||||
$issue->assignedTo[$key] = $profileList[$account];
|
||||
}
|
||||
$issue->openedBy = $profileList[$issue->openedBy];
|
||||
|
||||
return $this->send(200, array('issue' => $this->format($issue, 'openedDate:time,lastEditedDate:time')));
|
||||
}
|
||||
|
||||
/**
|
||||
* Process actions of one issue.
|
||||
*
|
||||
* @param string $type bug|task|story
|
||||
* @param array $actions
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function processActions($type, $actions)
|
||||
{
|
||||
$accountList = array();
|
||||
foreach($actions as $action)
|
||||
{
|
||||
$accountList[] = $action->actor;
|
||||
ob_start();
|
||||
if(method_exists($this->action, "printActionForGitLab"))
|
||||
{
|
||||
$this->action->printActionForGitLab($action);
|
||||
}
|
||||
else
|
||||
{
|
||||
$this->action->printAction($action);
|
||||
}
|
||||
$action->title = ob_get_contents();
|
||||
ob_clean();
|
||||
|
||||
$action->body_html = '';
|
||||
|
||||
if(!empty($action->history))
|
||||
{
|
||||
ob_start();
|
||||
$this->action->printChanges($action->objectType, $action->history);
|
||||
$action->body_html = ob_get_contents();
|
||||
ob_clean();
|
||||
}
|
||||
|
||||
if(!empty($action->comment))
|
||||
{
|
||||
$comment = strip_tags($action->comment) == $action->comment ? nl2br($action->comment) : $action->comment;
|
||||
$action->body_html = "{$comment}";
|
||||
}
|
||||
}
|
||||
|
||||
/* Format user detail and date. */
|
||||
$accountList = array_unique($accountList);
|
||||
$profileList = $this->loadModel('user')->getUserDetailsForAPI($accountList);
|
||||
foreach($actions as $key => $action)
|
||||
{
|
||||
$action->actor = isset($profileList[$action->actor]) ? $profileList[$action->actor] : array();
|
||||
$action->date = gmdate("Y-m-d\TH:i:s\Z", strtotime($action->date));
|
||||
|
||||
/* Unset this action when actor is System. */
|
||||
if(empty($action->actor)) unset($actions[$key]);
|
||||
}
|
||||
|
||||
return $actions;
|
||||
}
|
||||
}
|
353
api/v1/entries/productissues.php
Normal file
353
api/v1/entries/productissues.php
Normal file
@ -0,0 +1,353 @@
|
||||
<?php
|
||||
/**
|
||||
* The productissue entry point of ZenTaoPMS.
|
||||
* It is only used by Gitlab.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productIssuesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($productID)
|
||||
{
|
||||
if(!is_numeric($productID)) $this->sendError(400, 'The product_id is not supported');
|
||||
|
||||
$taskFields = 'id,status';
|
||||
$taskStatus = array('' => '');
|
||||
$taskStatus['opened'] = 'wait,doing,done,pause';
|
||||
$taskStatus['closed'] = 'closed';
|
||||
|
||||
$storyFields = 'id,status';
|
||||
$storyStatus = array('' => '');
|
||||
$storyStatus['opened'] = 'draft,reviewing,active,changing';
|
||||
$storyStatus['closed'] = 'closed';
|
||||
|
||||
$bugFields = 'id,status';
|
||||
$bugStatus = array('' => '');
|
||||
$bugStatus['opened'] = 'active,resolved';
|
||||
$bugStatus['closed'] = 'closed';
|
||||
|
||||
$productID = (int)$productID;
|
||||
$status = $this->param('status', '');
|
||||
$search = $this->param('search', '');
|
||||
$page = intval($this->param('page', 1));
|
||||
$limit = intval($this->param('limit', 20));
|
||||
$order = $this->param('order', 'openedDate_desc');
|
||||
|
||||
$labels = $this->param('labels', '');
|
||||
$labels = $labels ? explode(',', $labels) : array();
|
||||
|
||||
$orderParams = explode('_', $order);
|
||||
$order = $orderParams[0];
|
||||
$sort = (isset($orderParams[1]) and strtolower($orderParams[1]) == 'asc') ? 'asc' : 'desc';
|
||||
|
||||
if($status == 'all') $status = '';
|
||||
if(!in_array($status, array('opened', 'closed', ''))) $this->sendError(400, 'The status is not supported');
|
||||
|
||||
switch($order)
|
||||
{
|
||||
case 'openedDate':
|
||||
$taskFields .= ',openedDate';
|
||||
$storyFields .= ',openedDate';
|
||||
$bugFields .= ',openedDate';
|
||||
break;
|
||||
case 'title':
|
||||
$taskFields .= ',name as title';
|
||||
$storyFields .= ',title';
|
||||
$bugFields .= ',title';
|
||||
break;
|
||||
case 'lastEditedDate':
|
||||
$taskFields .= ",if(lastEditedDate < '1970-01-01 01-01-01', openedDate, lastEditedDate) as lastEditedDate";
|
||||
$storyFields .= ",if(lastEditedDate < '1970-01-01 01-01-01', openedDate, lastEditedDate) as lastEditedDate";
|
||||
$bugFields .= ",if(lastEditedDate < '1970-01-01 01-01-01', openedDate, lastEditedDate) as lastEditedDate";
|
||||
break;
|
||||
default:
|
||||
$this->sendError(400, 'The order is not supported');
|
||||
}
|
||||
|
||||
$issues = array();
|
||||
$storyFilter = array();
|
||||
$bugFilter = array();
|
||||
$taskFilter = array();
|
||||
$labelTypes = array();
|
||||
|
||||
if(!empty($labels))
|
||||
{
|
||||
$this->app->loadLang('story');
|
||||
$this->app->loadLang('task');
|
||||
$this->app->loadLang('bug');
|
||||
|
||||
$storyTypeMap = array_flip($this->app->lang->story->categoryList);
|
||||
$taskTypeMap = array_flip($this->app->lang->task->typeList);
|
||||
$bugTypeMap = array_flip($this->app->lang->bug->typeList);
|
||||
|
||||
$allValidLabels = array_merge(array_keys(array_merge($storyTypeMap, $taskTypeMap, $bugTypeMap)), array($this->app->lang->story->common, $this->app->lang->task->common, $this->app->lang->bug->common));
|
||||
foreach($labels as $label)
|
||||
{
|
||||
/* Return empty result if label is not exists.*/
|
||||
if(!in_array($label, $allValidLabels)) $this->send(200, array('page' => $page, 'total' => 0, 'limit' => $limit, 'issues' => array()));
|
||||
|
||||
if($label == $this->app->lang->story->common) $storyFilter[] = 'all';
|
||||
if(isset($storyTypeMap[$label])) $storyFilter[] = $storyTypeMap[$label];
|
||||
|
||||
if($label == $this->app->lang->task->common) $taskFilter[] = 'all';
|
||||
if(isset($taskTypeMap[$label])) $taskFilter[] = $taskTypeMap[$label];
|
||||
|
||||
if($label == $this->app->lang->bug->common) $bugFilter[] = 'all';
|
||||
if(isset($bugTypeMap[$label])) $bugFilter[] = $bugTypeMap[$label];
|
||||
}
|
||||
}
|
||||
|
||||
if(!empty($storyFilter)) $labelTypes[] = 'story';
|
||||
if(!empty($taskFilter)) $labelTypes[] = 'task';
|
||||
if(!empty($bugFilter)) $labelTypes[] = 'bug';
|
||||
|
||||
/* If posted labels are not conflictive. */
|
||||
if(count($labelTypes) < 2)
|
||||
{
|
||||
$storyFilter = array_unique($storyFilter);
|
||||
$taskFilter = array_unique($taskFilter);
|
||||
$bugFilter = array_unique($bugFilter);
|
||||
|
||||
$executions = $this->dao->select('project')->from(TABLE_PROJECTPRODUCT)->where('product')->eq($productID)->fetchPairs();
|
||||
|
||||
/* Get tasks. */
|
||||
if(empty($labelTypes) or in_array('task', $labelTypes))
|
||||
{
|
||||
$query = $this->dao->select($taskFields)->from(TABLE_TASK)->where('execution')->in(array_values($executions))
|
||||
->beginIF($search)->andWhere('name')->like("%$search%")->fi()
|
||||
->beginIF($status)->andWhere('status')->in($taskStatus[$status])->fi()
|
||||
->andWhere('deleted')->eq(0);
|
||||
foreach($taskFilter as $filter) if($filter != 'all') $query->andWhere('type')->eq($filter);
|
||||
$tasks = $query->fetchAll();
|
||||
foreach($tasks as $task) $issues[] = array('id' => $task->id, 'type' => 'task', 'order' => $task->$order, 'status' => $this->getKey($task->status, $taskStatus));
|
||||
}
|
||||
|
||||
/* Get stories. */
|
||||
if(empty($labelTypes) or in_array('story', $labelTypes))
|
||||
{
|
||||
$query = $this->dao->select($storyFields)->from(TABLE_STORY)
|
||||
->where('product')->eq($productID)
|
||||
->beginIF($search)->andWhere('title')->like("%$search%")->fi()
|
||||
->beginIF($status)->andWhere('status')->in($storyStatus[$status])->fi()
|
||||
->andWhere('deleted')->eq(0);
|
||||
foreach($storyFilter as $filter) if($filter != 'all') $query->andWhere('category')->eq($filter);
|
||||
$stories = $query->fetchAll();
|
||||
foreach($stories as $story) $issues[] = array('id' => $story->id, 'type' => 'story', 'order' => $story->$order, 'status' => $this->getKey($story->status, $storyStatus));
|
||||
}
|
||||
|
||||
/* Get bugs. */
|
||||
if(empty($labelTypes) or in_array('bug', $labelTypes))
|
||||
{
|
||||
$query = $this->dao->select($bugFields)->from(TABLE_BUG)
|
||||
->where('product')->eq($productID)
|
||||
->beginIF($search)->andWhere('title')->like("%$search%")->fi()
|
||||
->beginIF($status)->andWhere('status')->in($bugStatus[$status])->fi()
|
||||
->andWhere('deleted')->eq(0);
|
||||
foreach($bugFilter as $filter) if($filter != 'all') $query->andWhere('type')->eq($filter);
|
||||
$bugs = $query->fetchAll();
|
||||
foreach($bugs as $bug) $issues[] = array('id' => $bug->id, 'type' => 'bug', 'order' => $bug->$order, 'status' => $this->getKey($bug->status, $bugStatus));
|
||||
}
|
||||
}
|
||||
|
||||
array_multisort(array_column($issues, 'order'), $sort == 'asc' ? SORT_ASC : SORT_DESC, $issues);
|
||||
$total = count($issues);
|
||||
$issues = $page < 1 ? array() : array_slice($issues, ($page-1) * $limit, $limit);
|
||||
|
||||
$result = $this->processIssues($issues);
|
||||
return $this->send(200, array('page' => $page, 'total' => $total, 'limit' => $limit, 'issues' => $result));
|
||||
}
|
||||
|
||||
/**
|
||||
* Process issues, format fields.
|
||||
*
|
||||
* @param array $issues
|
||||
* @param int $page
|
||||
* @param int $limit
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function processIssues($issues)
|
||||
{
|
||||
$this->app->loadLang('story');
|
||||
$this->app->loadLang('task');
|
||||
$this->app->loadLang('bug');
|
||||
|
||||
$this->loadModel('entry');
|
||||
|
||||
$tasks = array();
|
||||
$stories = array();
|
||||
$bugs = array();
|
||||
foreach($issues as $issue)
|
||||
{
|
||||
if($issue['type'] == 'story') $stories[] = $issue['id'];
|
||||
if($issue['type'] == 'task') $tasks[] = $issue['id'];
|
||||
if($issue['type'] == 'bug') $bugs[] = $issue['id'];
|
||||
}
|
||||
|
||||
if(!empty($tasks)) $tasks = $this->dao->select('*')->from(TABLE_TASK)->where('id')->in($tasks)->fetchAll('id');
|
||||
if(!empty($stories)) $stories = $this->dao->select('*')->from(TABLE_STORY)->where('id')->in($stories)->fetchAll('id');
|
||||
if(!empty($bugs)) $bugs = $this->dao->select('*')->from(TABLE_BUG)->where('id')->in($bugs)->fetchAll('id');
|
||||
|
||||
$result = array();
|
||||
foreach($issues as $issue)
|
||||
{
|
||||
$r = new stdclass();
|
||||
if($issue['type'] == 'task')
|
||||
{
|
||||
$task = $tasks[$issue['id']];
|
||||
|
||||
$r->id = 'task-' . $task->id;
|
||||
$r->title = $task->name;
|
||||
$r->labels = array($this->app->lang->task->common, zget($this->app->lang->task->typeList, $task->type));
|
||||
$r->pri = $task->pri;
|
||||
$r->openedDate = $task->openedDate;
|
||||
$r->openedBy = $task->openedBy;
|
||||
$r->lastEditedDate = $task->lastEditedDate < '1970-01-01 01:01:01' ? $task->openedDate : $task->lastEditedDate;
|
||||
$r->lastEditedBy = $task->lastEditedDate < '1970-01-01 01:01:01' ? $task->openedBy : $task->lastEditedBy;
|
||||
$r->status = $issue['status'];
|
||||
$r->url = helper::createLink('task', 'view', "taskID=$task->id");
|
||||
$r->assignedTo = array();
|
||||
|
||||
/* Get assignees for task, the task object has the type of multiple assign only so far. */
|
||||
$users = $this->dao->select('account')->from(TABLE_TEAM)
|
||||
->where('type')->eq('task')
|
||||
->andWhere('root')->eq($task->id)
|
||||
->fetchAll();
|
||||
if($users)
|
||||
{
|
||||
foreach($users as $user)
|
||||
{
|
||||
$r->assignedTo[] = $user->account;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if($task->assignedTo == "")
|
||||
{
|
||||
$r->assignedTo = array();
|
||||
}
|
||||
else
|
||||
{
|
||||
$r->assignedTo = array($task->assignedTo);
|
||||
}
|
||||
}
|
||||
}
|
||||
elseif($issue['type'] == 'story')
|
||||
{
|
||||
$story = $stories[$issue['id']];
|
||||
|
||||
$r->id = 'story-' . $story->id;
|
||||
$r->title = $story->title;
|
||||
$r->labels = array($this->app->lang->story->common, zget($this->app->lang->story->categoryList, $story->category));
|
||||
$r->pri = $story->pri;
|
||||
$r->openedDate = $story->openedDate;
|
||||
$r->openedBy = $story->openedBy;
|
||||
$r->lastEditedDate = $story->lastEditedDate < '1970-01-01 01:01:01' ? $story->openedDate : $story->lastEditedDate;
|
||||
$r->lastEditedBy = $story->lastEditedDate < '1970-01-01 01:01:01' ? $story->openedBy : $story->lastEditedBy;
|
||||
$r->status = $issue['status'];
|
||||
$r->url = helper::createLink('story', 'view', "storyID=$story->id");
|
||||
|
||||
if($story->assignedTo == "")
|
||||
{
|
||||
$r->assignedTo = array();
|
||||
}
|
||||
else
|
||||
{
|
||||
$r->assignedTo = array($story->assignedTo);
|
||||
}
|
||||
}
|
||||
elseif($issue['type'] == 'bug')
|
||||
{
|
||||
$bug = $bugs[$issue['id']];
|
||||
|
||||
$r->id = 'bug-' . $bug->id;
|
||||
$r->title = $bug->title;
|
||||
$r->labels = array($this->app->lang->bug->common, zget($this->app->lang->bug->typeList, $bug->type));
|
||||
$r->pri = $bug->pri;
|
||||
$r->openedDate = $bug->openedDate;
|
||||
$r->openedBy = $bug->openedBy;
|
||||
$r->lastEditedDate = $bug->lastEditedDate < '1970-01-01 01:01:01' ? $bug->openedDate : $bug->lastEditedDate;
|
||||
$r->lastEditedBy = $bug->lastEditedDate < '1970-01-01 01:01:01' ? $bug->openedBy : $bug->lastEditedBy;
|
||||
$r->status = $issue['status'];
|
||||
$r->url = helper::createLink('bug', 'view', "bugID=$bug->id");
|
||||
|
||||
if($bug->assignedTo == "")
|
||||
{
|
||||
$r->assignedTo = array();
|
||||
}
|
||||
else
|
||||
{
|
||||
$r->assignedTo = array($bug->assignedTo);
|
||||
}
|
||||
}
|
||||
|
||||
$result[] = $this->format($r, 'openedDate:time,lastEditedDate:time');
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all users in issues so that we can bulk get user detail later.
|
||||
*
|
||||
*/
|
||||
$userList = array();
|
||||
foreach($result as $issue)
|
||||
{
|
||||
foreach($issue->assignedTo as $account)
|
||||
{
|
||||
$userList[] = $account;
|
||||
}
|
||||
$userList[] = $issue->openedBy;
|
||||
}
|
||||
$userList = array_unique($userList);
|
||||
$userDetails = $this->loadModel('user')->getUserDetailsForAPI($userList);
|
||||
|
||||
/**
|
||||
* Set the user detail to assignedTo and openedBy.
|
||||
*
|
||||
*/
|
||||
foreach($result as $issue)
|
||||
{
|
||||
foreach($issue->assignedTo as $key => $account)
|
||||
{
|
||||
if($account == 'closed')
|
||||
{
|
||||
$issue->assignedTo = array();
|
||||
break;
|
||||
}
|
||||
$issue->assignedTo[$key] = $userDetails[$account];
|
||||
}
|
||||
$issue->openedBy = $userDetails[$issue->openedBy];
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get key in array by value.
|
||||
*
|
||||
* @param string $value
|
||||
* @param array $array
|
||||
* @access private
|
||||
* @return string
|
||||
*/
|
||||
private function getKey($value, $array)
|
||||
{
|
||||
foreach($array as $key => $values)
|
||||
{
|
||||
if($values and strpos($values, $value) !== FALSE) return $key;
|
||||
}
|
||||
|
||||
return '';
|
||||
}
|
||||
}
|
92
api/v1/entries/productplan.php
Normal file
92
api/v1/entries/productplan.php
Normal file
@ -0,0 +1,92 @@
|
||||
<?php
|
||||
/**
|
||||
* The productplan entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productplanEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $planID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($planID)
|
||||
{
|
||||
$fields = $this->param('fields');
|
||||
|
||||
$control = $this->loadController('productplan', 'view');
|
||||
$control->view($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$plan = $data->data->plan;
|
||||
$plan->stories = $data->data->planStories;
|
||||
$plan->bugs = $data->data->planBugs;
|
||||
|
||||
$plan = $this->format($plan, 'begin:date,end:date,deleted:bool,stories:array,bugs:array');
|
||||
|
||||
return $this->send(200, $plan);
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $planID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($planID)
|
||||
{
|
||||
$oldPlan = $this->loadModel('productplan')->getByID($planID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'title,begin,end,desc';
|
||||
$this->batchSetPost($fields, $oldPlan);
|
||||
|
||||
$control = $this->loadController('productplan', 'edit');
|
||||
$control->edit($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
/* Get plan info. */
|
||||
$control = $this->loadController('productplan', 'view');
|
||||
$control->view($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$plan = $data->data->plan;
|
||||
$plan->stories = $data->data->planStories;
|
||||
$plan->bugs = $data->data->planBugs;
|
||||
|
||||
return $this->send(200, $this->format($plan, 'begin:date,end:date,deleted:bool,stories:array,bugs:array'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($planID)
|
||||
{
|
||||
$control = $this->loadController('productplan', 'delete');
|
||||
$control->delete($planID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
50
api/v1/entries/productplanlinkbugs.php
Normal file
50
api/v1/entries/productplanlinkbugs.php
Normal file
@ -0,0 +1,50 @@
|
||||
<?php
|
||||
/**
|
||||
* The productplanlinkbugs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productplanLinkBugsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $planID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($planID)
|
||||
{
|
||||
$fields = 'bugs';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('productplan', 'linkBug');
|
||||
$control->linkBug($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'success')
|
||||
{
|
||||
$control = $this->loadController('productplan', 'view');
|
||||
$control->view($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$plan = $data->data->plan;
|
||||
$plan->stories = $data->data->planStories;
|
||||
$plan->bugs = $data->data->planBugs;
|
||||
|
||||
$plan = $this->format($plan, 'begin:date,end:date,deleted:bool,stories:array,bugs:array');
|
||||
|
||||
return $this->send(200, $plan);
|
||||
}
|
||||
|
||||
$this->sendError(400, array('message' => isset($data->message) ? $data->message : 'error'));
|
||||
}
|
||||
}
|
50
api/v1/entries/productplanlinkstories.php
Normal file
50
api/v1/entries/productplanlinkstories.php
Normal file
@ -0,0 +1,50 @@
|
||||
<?php
|
||||
/**
|
||||
* The productplanlinkstories entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productplanLinkStoriesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $planID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($planID)
|
||||
{
|
||||
$fields = 'stories';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('productplan', 'linkStory');
|
||||
$control->linkStory($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'success')
|
||||
{
|
||||
$control = $this->loadController('productplan', 'view');
|
||||
$control->view($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$plan = $data->data->plan;
|
||||
$plan->stories = $data->data->planStories;
|
||||
$plan->bugs = $data->data->planBugs;
|
||||
|
||||
$plan = $this->format($plan, 'begin:date,end:date,deleted:bool,stories:array,bugs:array');
|
||||
|
||||
return $this->send(200, $plan);
|
||||
}
|
||||
|
||||
$this->sendError(400, array('message' => isset($data->message) ? $data->message : 'error'));
|
||||
}
|
||||
}
|
93
api/v1/entries/productplans.php
Normal file
93
api/v1/entries/productplans.php
Normal file
@ -0,0 +1,93 @@
|
||||
<?php
|
||||
/**
|
||||
* The productplans entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productplansEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($productID = 0)
|
||||
{
|
||||
if(!$productID) $productID = $this->param('product', 0);
|
||||
if(!$productID) return $this->sendError(400, 'No product id.');
|
||||
|
||||
$control = $this->loadController('productplan', 'browse');
|
||||
$control->browse($productID, $this->param('branch', 0), $this->param('status', 'all'), $this->param('query', 0), $this->param('order', 'begin_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$result = array();
|
||||
$plans = $data->data->plans;
|
||||
$pager = $data->data->pager;
|
||||
|
||||
foreach($plans as $plan)
|
||||
{
|
||||
if($plan->parent > 0 and isset($result[$plan->parent]))
|
||||
{
|
||||
$parentPlan = $result[$plan->parent];
|
||||
|
||||
if(!isset($parentPlan->children) or !is_array($parentPlan->children)) $parentPlan->children = array();
|
||||
$parentPlan->children[] = $plan;
|
||||
$result[$plan->parent] = $parentPlan;
|
||||
}
|
||||
else
|
||||
{
|
||||
$result[$plan->id] = $this->format($plan, 'begin:date,end:date,deleted:bool,project:int');
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'plans' => array_values($result)));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($productID = 0)
|
||||
{
|
||||
if(!$productID) $productID = $this->param('product', 0);
|
||||
if(!$productID) return $this->sendError(400, 'No product id.');
|
||||
|
||||
$fields = 'branch,begin,end,title,desc';
|
||||
$this->batchSetPost($fields);
|
||||
$this->setPost('product', $productID);
|
||||
$this->setPost('parent', $this->request('parent', 0));
|
||||
$this->setPost('branch', $this->request('branch', 0));
|
||||
|
||||
$control = $this->loadController('productplan', 'create');
|
||||
$control->create($productID, $this->param('branch', 0), $this->param('parent', 0));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'success')
|
||||
{
|
||||
$plan = $this->loadModel('productplan')->getByID($data->id);
|
||||
$plan->stories = array();
|
||||
$plan->bugs = array();
|
||||
return $this->send(200, $this->format($plan, 'begin:date,end:date,deleted:bool,project:int'));
|
||||
}
|
||||
|
||||
$this->sendError(400, array('message' => isset($data->message) ? $data->message : 'error'));
|
||||
}
|
||||
}
|
45
api/v1/entries/productplanunlinkbugs.php
Normal file
45
api/v1/entries/productplanunlinkbugs.php
Normal file
@ -0,0 +1,45 @@
|
||||
<?php
|
||||
/**
|
||||
* The productplanunlinkbugs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productplanUnlinkBugsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $planID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($planID)
|
||||
{
|
||||
$productplan = $this->loadModel('productplan');
|
||||
foreach($this->request('bugs', array()) as $bugID)
|
||||
{
|
||||
$productplan->unlinkBug($bugID, $planID);
|
||||
if(dao::isError()) return $this->sendError('error');
|
||||
}
|
||||
|
||||
$control = $this->loadController('productplan', 'view');
|
||||
$control->view($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$plan = $data->data->plan;
|
||||
$plan->stories = $data->data->planStories;
|
||||
$plan->bugs = $data->data->planBugs;
|
||||
|
||||
$plan = $this->format($plan, 'begin:date,end:date,deleted:bool,stories:array,bugs:array');
|
||||
|
||||
return $this->send(200, $plan);
|
||||
}
|
||||
}
|
45
api/v1/entries/productplanunlinkstories.php
Normal file
45
api/v1/entries/productplanunlinkstories.php
Normal file
@ -0,0 +1,45 @@
|
||||
<?php
|
||||
/**
|
||||
* The productplanunlinkstories entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productplanUnlinkStoriesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $planID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($planID)
|
||||
{
|
||||
$productplan = $this->loadModel('productplan');
|
||||
foreach($this->request('stories', array()) as $storyID)
|
||||
{
|
||||
$productplan->unlinkStory($storyID, $planID);
|
||||
if(dao::isError()) return $this->sendError('error');
|
||||
}
|
||||
|
||||
$control = $this->loadController('productplan', 'view');
|
||||
$control->view($planID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$plan = $data->data->plan;
|
||||
$plan->stories = $data->data->planStories;
|
||||
$plan->bugs = $data->data->planBugs;
|
||||
|
||||
$plan = $this->format($plan, 'begin:date,end:date,deleted:bool,stories:array,bugs:array');
|
||||
|
||||
return $this->send(200, $plan);
|
||||
}
|
||||
}
|
128
api/v1/entries/productprojects.php
Normal file
128
api/v1/entries/productprojects.php
Normal file
@ -0,0 +1,128 @@
|
||||
<?php
|
||||
/**
|
||||
* The product projects entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productProjectsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($productID = 0)
|
||||
{
|
||||
if(empty($productID)) $productID = $this->param('product', 0);
|
||||
if(empty($productID)) return $this->sendError('400', "Need product id");
|
||||
$appendFields = $this->param('fields', '');
|
||||
|
||||
$control = $this->loadController('product', 'project');
|
||||
$control->project($this->param('status', 'all'), $productID, $this->param('branch', 0), $this->param('involved', 0), $this->param('order', 'order_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$result = array();
|
||||
foreach($data->data->projectStats as $project)
|
||||
{
|
||||
foreach($project->hours as $field => $value) $project->$field = $value;
|
||||
|
||||
$project = $this->filterFields($project, 'id,name,code,model,type,budget,budgetUnit,parent,begin,end,status,openedBy,openedDate,PM,delay,progress,' . $appendFields);
|
||||
$result[] = $this->format($project, 'openedDate:time,lastEditedDate:time,closedDate:time,canceledDate:time');
|
||||
}
|
||||
|
||||
$data = array();
|
||||
$data['total'] = count($result);
|
||||
$data['projects'] = $result;
|
||||
|
||||
$withUser = $this->param('withUser', '');
|
||||
if(!empty($withUser)) $data['users'] = $users;
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
// TODO There is no handle for 401.
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$fields = 'name,begin,end,products';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('code', $this->request('code', ''));
|
||||
$this->setPost('acl', $this->request('acl', 'private'));
|
||||
$this->setPost('parent', $this->request('program', 0));
|
||||
$this->setPost('whitelist', $this->request('whitelist', array()));
|
||||
$this->setPost('PM', $this->request('PM', ''));
|
||||
$this->setPost('model', $this->request('model', 'scrum'));
|
||||
|
||||
$control = $this->loadController('project', 'create');
|
||||
$this->requireFields('name,code,begin,end,products');
|
||||
|
||||
$control->create($this->request('model', 'scrum'));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(!isset($data->result)) return $this->sendError(400, 'error');
|
||||
|
||||
$project = $this->loadModel('project')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($project, 'openedDate:time,lastEditedDate:time,closedDate:time,canceledDate:time'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get drop menu.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function getDropMenu()
|
||||
{
|
||||
$control = $this->loadController('project', 'ajaxGetDropMenu');
|
||||
$control->ajaxGetDropMenu($this->request('projectID', 0), $this->request('module', 'project'), $this->request('method', 'browse'));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$dropMenu = array('owner' => array(), 'other' => array(), 'closed' => array());
|
||||
foreach($data->data->projects as $programID => $projects)
|
||||
{
|
||||
foreach($projects as $project)
|
||||
{
|
||||
if(helper::diffDate(date('Y-m-d'), $project->end) > 0) $project->delay = true;
|
||||
$project = $this->filterFields($project, 'id,model,type,name,code,parent,status,PM,delay');
|
||||
|
||||
if($project->status == 'closed')
|
||||
{
|
||||
$dropMenu['closed'][] = $project;
|
||||
}
|
||||
elseif($project->PM == $this->app->user->account)
|
||||
{
|
||||
$dropMenu['owner'][] = $project;
|
||||
}
|
||||
else
|
||||
{
|
||||
$dropMenu['other'][] = $project;
|
||||
}
|
||||
}
|
||||
}
|
||||
return $this->send(200, $dropMenu);
|
||||
}
|
||||
}
|
245
api/v1/entries/products.php
Normal file
245
api/v1/entries/products.php
Normal file
@ -0,0 +1,245 @@
|
||||
<?php
|
||||
/**
|
||||
* The products entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class productsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($programID = 0)
|
||||
{
|
||||
$fields = $this->param('fields', '');
|
||||
if(strpos(strtolower(",{$fields},"), ',dropmenu,') !== false) return $this->getDropMenu();
|
||||
|
||||
if(!$programID) $programID = $this->param('program', 0);
|
||||
$projectID = $this->param('project', 0);
|
||||
$mergeChildren = $this->param('mergeChildren', '');
|
||||
|
||||
if($programID)
|
||||
{
|
||||
$control = $this->loadController('program', 'product');
|
||||
$control->product($programID, $this->param('status', 'all'), $this->param('order', 'order_asc'), 0, $this->param('limit', '20'), $this->param('page', '1'));
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$products = $data->data->products;
|
||||
|
||||
}
|
||||
elseif($projectID)
|
||||
{
|
||||
$control = $this->loadController('project', 'manageProducts');
|
||||
$control->manageProducts($projectID);
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$products = $data->data->linkedProducts;
|
||||
}
|
||||
else
|
||||
{
|
||||
$control = $this->loadController('product', 'all');
|
||||
$control->all($this->param('status', 'all'), $this->param('order', 'program_asc'), 0, 0, $this->param('limit', 100), $this->param('page', 1));
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$products = $data->data->productStats;
|
||||
if($mergeChildren) $products = $data->data->productStructure;
|
||||
}
|
||||
$pager = $data->data->pager;
|
||||
|
||||
$result = array();
|
||||
if($mergeChildren)
|
||||
{
|
||||
$programs = $this->mergeChildren($products);
|
||||
return $this->send(200, $programs);
|
||||
}
|
||||
else
|
||||
{
|
||||
$accounts = array();
|
||||
foreach($products as $product)
|
||||
{
|
||||
$accounts[$product->PO] = $product->PO;
|
||||
$accounts[$product->QD] = $product->QD;
|
||||
$accounts[$product->RD] = $product->RD;
|
||||
$accounts[$product->createdBy] = $product->createdBy;
|
||||
if(isset($product->feedback)) $accounts[$product->feedback] = $product->feedback;
|
||||
if(!empty($product->mailto))
|
||||
{
|
||||
foreach(explode(',', $product->mailto) as $account)
|
||||
{
|
||||
$account = trim($account);
|
||||
if(empty($account)) continue;
|
||||
$accounts[$account] = $account;
|
||||
}
|
||||
}
|
||||
|
||||
$result[] = $this->format($product, 'createdDate:time,whitelist:userList,createdBy:user,PO:user,RD:user,QD:user');
|
||||
}
|
||||
|
||||
$data = array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'products' => $result);
|
||||
$withUser = $this->param('withUser', '');
|
||||
if(!empty($withUser)) $data['users'] = $this->loadModel('user')->getListByAccounts($accounts, 'account');
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$fields = 'program,code,line,name,PO,QD,RD,type,desc,whitelist';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('acl', $this->request('acl', 'private'));
|
||||
$this->setPost('whitelist', $this->request('whitelist', array()));
|
||||
|
||||
$control = $this->loadController('product', 'create');
|
||||
$this->requireFields('name,code');
|
||||
|
||||
$control->create($this->request('program', 0));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
/* Response */
|
||||
$product = $this->loadModel('product')->getByID($data->id);
|
||||
$product = $this->format($product, 'createdDate:time,whitelist:userList,createdBy:user,PO:user,RD:user,QD:user');
|
||||
|
||||
return $this->send(200, $product);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get dropmenu.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function getDropMenu()
|
||||
{
|
||||
$control = $this->loadController('product', 'ajaxGetDropMenu');
|
||||
$control->ajaxGetDropMenu($this->request('productID', 0), $this->request('module', 'product'), $this->request('method', 'browse'), $this->request('extra', ''), $this->request('from', ''));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$dropMenu = array('owner' => array(), 'other' => array(), 'closed' => array());
|
||||
foreach($data->data->products as $programID => $products)
|
||||
{
|
||||
foreach($products as $product)
|
||||
{
|
||||
$product = $this->filterFields($product, 'id,program,name,code,status,PO');
|
||||
|
||||
if($product->status == 'closed')
|
||||
{
|
||||
$dropMenu['closed'][] = $product;
|
||||
}
|
||||
elseif($product->PO == $this->app->user->account)
|
||||
{
|
||||
$dropMenu['owner'][] = $product;
|
||||
}
|
||||
else
|
||||
{
|
||||
$dropMenu['other'][] = $product;
|
||||
}
|
||||
}
|
||||
}
|
||||
return $this->send(200, $dropMenu);
|
||||
}
|
||||
|
||||
/**
|
||||
* Merge children products.
|
||||
*
|
||||
* @param array $products
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function mergeChildren($products)
|
||||
{
|
||||
$programs = array();
|
||||
foreach($products as $programID => $program)
|
||||
{
|
||||
$programs[$programID] = new stdclass();
|
||||
if(!empty($programID))
|
||||
{
|
||||
$programs[$programID]->id = $programID;
|
||||
$programs[$programID]->name = $program->programName;
|
||||
$programs[$programID]->type = 'program';
|
||||
}
|
||||
|
||||
$unclosedTotal = 0;
|
||||
foreach($program as $lineID => $value)
|
||||
{
|
||||
if(!isset($programs[$programID]->children)) $programs[$programID]->children = array();
|
||||
if(isset($value->products))
|
||||
{
|
||||
if(empty($lineID))
|
||||
{
|
||||
foreach($value->products as $product)
|
||||
{
|
||||
unset($product->desc);
|
||||
$programs[$programID]->children[$product->id] = $product;
|
||||
if($product->status != 'closed') $unclosedTotal += 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
$line = new stdclass();
|
||||
$line->id = $lineID;
|
||||
$line->name = $value->lineName;
|
||||
$line->type = 'line';
|
||||
|
||||
$line->children = array();
|
||||
foreach($value->products as $product)
|
||||
{
|
||||
unset($product->desc);
|
||||
$line->children[$product->id] = $product;
|
||||
if($product->status != 'closed') $unclosedTotal += 1;
|
||||
}
|
||||
if(isset($line->children)) $line->children = array_values($line->children);
|
||||
|
||||
$programs[$programID]->children[$lineID] = $line;
|
||||
}
|
||||
if(isset($programs[$programID]->children)) $programs[$programID]->children = array_values($programs[$programID]->children);
|
||||
$programs[$programID]->unclosedTotal = $unclosedTotal;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$topProducts = array();
|
||||
if(isset($programs[0]))
|
||||
{
|
||||
$topProducts = $programs[0]->children;
|
||||
unset($programs[0]);
|
||||
}
|
||||
|
||||
$programs = array_values($programs);
|
||||
foreach($topProducts as $product) $programs[] = $product;
|
||||
|
||||
return $programs;
|
||||
}
|
||||
}
|
70
api/v1/entries/program.php
Normal file
70
api/v1/entries/program.php
Normal file
@ -0,0 +1,70 @@
|
||||
<?php
|
||||
/**
|
||||
* The program entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class programEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $programID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($programID)
|
||||
{
|
||||
$program = $this->loadModel('program')->getByID($programID);
|
||||
if(!$program) return $this->send404();
|
||||
|
||||
return $this->send(200, $this->format($program, 'begin:date,end:date,PO:user,PM:user,QD:user,RD:user,realBegan:date,realEnd:date,openedBy:user,openedDate:time,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,deleted:bool,whitelist:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $programID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($programID)
|
||||
{
|
||||
$oldProgram = $this->loadModel('program')->getByID($programID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'name,PM,budget,budgetUnit,desc,parent,begin,end,realBegan,realEnd,acl,whitelist';
|
||||
$this->batchSetPost($fields, $oldProgram);
|
||||
$this->setPost('parent', $this->request('parent', 0));
|
||||
|
||||
$control = $this->loadController('program', 'edit');
|
||||
$control->edit($programID);
|
||||
|
||||
$this->getData();
|
||||
$program = $this->program->getByID($programID);
|
||||
return $this->send(200, $this->format($program, 'begin:date,end:date,PO:user,PM:user,QD:user,RD:user,realBegan:date,realEnd:date,openedBy:user,openedDate:time,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,deleted:bool,whitelist:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $programID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($programID)
|
||||
{
|
||||
$control = $this->loadController('program', 'delete');
|
||||
$control->delete($programID, 'true');
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
127
api/v1/entries/programs.php
Normal file
127
api/v1/entries/programs.php
Normal file
@ -0,0 +1,127 @@
|
||||
<?php
|
||||
/**
|
||||
* The programs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class programsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$_COOKIE['showClosed'] = $this->param('showClosed', 0);
|
||||
$mergeChildren = $this->param('mergeChildren', 0);
|
||||
|
||||
$this->config->systemMode = 'ALM';
|
||||
|
||||
$fields = $this->param('fields', '');
|
||||
if(stripos(strtolower(",{$fields},"), ",dropmenu,") !== false) return $this->getDropMenu();
|
||||
|
||||
$program = $this->loadController('program', 'browse');
|
||||
$program->browse($this->param('status', 'all'), $this->param('order', 'order_asc'));
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$programs = $data->data->programs;
|
||||
$progressList = $data->data->progressList;
|
||||
$users = $data->data->users;
|
||||
$result = array();
|
||||
foreach($programs as $program)
|
||||
{
|
||||
if(isset($progressList->{$program->id})) $program->progress = $progressList->{$program->id};
|
||||
$program = $this->format($program, 'begin:date,end:date,PO:user,PM:user,QD:user,RD:user,realBegan:date,realEnd:date,openedBy:user,openedDate:time,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,deleted:bool,whitelist:userList');
|
||||
|
||||
if($mergeChildren)
|
||||
{
|
||||
unset($program->desc);
|
||||
$program->end = $program->end == LONG_TIME ? $this->lang->program->longTime : $program->end;
|
||||
|
||||
$programBudget = $this->loadModel('project')->getBudgetWithUnit($program->budget);
|
||||
$program->labelBudget = $program->budget != 0 ? zget($this->lang->project->currencySymbol, $program->budgetUnit) . ' ' . $programBudget : $this->lang->project->future;
|
||||
|
||||
if(empty($program->parent)) $result[$program->id] = $program;
|
||||
if(isset($programs->{$program->parent}))
|
||||
{
|
||||
$parentProgram = $programs->{$program->parent};
|
||||
if(!isset($parentProgram->children)) $parentProgram->children = array();
|
||||
$parentProgram->children[] = $program;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
$result[] = $program;
|
||||
}
|
||||
}
|
||||
return $this->send(200, array('programs' => array_values($result)));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$fields = 'name,PM,budget,budgetUnit,desc,begin,end';
|
||||
$this->batchSetPost($fields);
|
||||
$this->setPost('acl', $this->request('acl', 'open'));
|
||||
$this->setPost('whitelist', $this->request('whitelist', array()));
|
||||
|
||||
$control = $this->loadController('program', 'create');
|
||||
$this->requireFields('name,begin,end');
|
||||
|
||||
$control->create($this->request('parent', 0));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$program = $this->loadModel('program')->getByID($data->id);
|
||||
return $this->send(201, $this->format($program, 'begin:date,end:date,PO:user,PM:user,QD:user,RD:user,realBegan:date,realEnd:date,openedBy:user,openedDate:time,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,deleted:bool,whitelist:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get drop menu.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function getDropMenu()
|
||||
{
|
||||
$programs = $this->dao->select('id,name,parent,path,grade,`order`')->from(TABLE_PROJECT)
|
||||
->where('deleted')->eq('0')
|
||||
->andWhere('type')->eq('program')
|
||||
->andWhere('id')->in($this->app->user->view->programs)
|
||||
->beginIF(empty($_COOKIE['showClosed']))->andWhere('status')->ne('closed')->fi()
|
||||
->orderBy('grade desc, `order`')
|
||||
->fetchAll('id');
|
||||
|
||||
$dropMenu = array();
|
||||
foreach($programs as $programID => $program)
|
||||
{
|
||||
if(empty($program->parent))
|
||||
{
|
||||
$dropMenu[] = $program;
|
||||
}
|
||||
elseif(isset($programs[$program->parent]))
|
||||
{
|
||||
if(!isset($programs[$program->parent]->children)) $programs[$program->parent]->children = array();
|
||||
$programs[$program->parent]->children[] = $program;
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, $dropMenu);
|
||||
}
|
||||
}
|
144
api/v1/entries/project.php
Normal file
144
api/v1/entries/project.php
Normal file
@ -0,0 +1,144 @@
|
||||
<?php
|
||||
/**
|
||||
* The project entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class projectEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID)
|
||||
{
|
||||
$fields = strtolower($this->param('fields'));
|
||||
|
||||
$control = $this->loadController('project', 'view');
|
||||
$control->view($projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$project = $this->format($data->data->project, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,realBegan:date,realEnd:date,PM:user,whitelist:userList,deleted:bool');
|
||||
|
||||
$this->loadModel('testcase');
|
||||
$project->caseReview = ($this->config->testcase->needReview or !empty($this->config->testcase->forceReview));
|
||||
|
||||
if(empty($fields)) return $this->send(200, $project);
|
||||
|
||||
/* Set other fields. */
|
||||
$fields = explode(',', $fields);
|
||||
foreach($fields as $field)
|
||||
{
|
||||
switch($field)
|
||||
{
|
||||
case 'team':
|
||||
$teams = array();
|
||||
$accounts = array();
|
||||
foreach($data->data->teamMembers as $account => $team)
|
||||
{
|
||||
$team = $this->filterFields($team, "account,role,join,realname");
|
||||
|
||||
$teams[$account] = $team;
|
||||
$accounts[$account] = $account;
|
||||
}
|
||||
$users = $this->loadModel('user')->getListByAccounts($accounts, 'account');
|
||||
foreach($teams as $account => $team)
|
||||
{
|
||||
$user = zget($users, $account, '');
|
||||
$team->avatar = $user->avatar;
|
||||
}
|
||||
|
||||
$project->teams = $teams;
|
||||
break;
|
||||
case "products":
|
||||
$project->products = array();
|
||||
$productList = $this->loadModel('product')->getProducts($projectID, $this->param('status', 'all'));
|
||||
foreach($productList as $product) $project->products[] = $product;
|
||||
break;
|
||||
case "stat":
|
||||
$project->stat = $data->data->statData;
|
||||
break;
|
||||
case "workhour":
|
||||
$workhour = $data->data->workhour;
|
||||
$workhour->progress = ($workhour->totalConsumed + $workhour->totalLeft) ? floor($workhour->totalConsumed / ($workhour->totalConsumed + $workhour->totalLeft) * 1000) / 1000 * 100 : 0;
|
||||
$project->workhour = $workhour;
|
||||
break;
|
||||
case "actions":
|
||||
$actions = $data->data->actions;
|
||||
$project->actions = $this->loadModel('action')->processActionForAPI($actions, (array)$data->data->users, $this->lang->project);
|
||||
break;
|
||||
case "dynamics":
|
||||
$dynamics = $data->data->dynamics;
|
||||
$project->dynamics = $this->loadModel('action')->processDynamicForAPI($dynamics);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, $project);
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($projectID)
|
||||
{
|
||||
$oldProject = $this->loadModel('project')->getByID($projectID);
|
||||
$linkedProducts = $this->loadModel('product')->getProducts($projectID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'name,code,begin,end,acl,parent,desc,PM,whitelist,model';
|
||||
$this->batchSetPost($fields, $oldProject);
|
||||
|
||||
$products = array();
|
||||
$plans = array();
|
||||
foreach($linkedProducts as $product)
|
||||
{
|
||||
$products[] = $product->id;
|
||||
foreach($product->plans as $planID) $plans[] = $planID;
|
||||
}
|
||||
$this->setPost('products', $products);
|
||||
$this->setPost('plans', $plans);
|
||||
|
||||
$control = $this->loadController('project', 'edit');
|
||||
$control->edit($projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
if(!isset($data->result)) return $this->sendError(400, 'error');
|
||||
|
||||
$project = $this->project->getByID($projectID);
|
||||
return $this->send(200, $this->format($project, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,realBegan:date,realEnd:date,PM:user,whitelist:userList,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($projectID)
|
||||
{
|
||||
$control = $this->loadController('project', 'delete');
|
||||
$control->delete($projectID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
72
api/v1/entries/projectbugs.php
Normal file
72
api/v1/entries/projectbugs.php
Normal file
@ -0,0 +1,72 @@
|
||||
<?php
|
||||
/**
|
||||
* The project bugs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class projectBugsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
if(empty($projectID)) $projectID = $this->param('project', 0);
|
||||
if(empty($projectID)) return $this->sendError(400, 'Need project id.');
|
||||
|
||||
$control = $this->loadController('project', 'bug');
|
||||
$control->bug($projectID, $this->param('product', 0), $this->param('branch', 0), $this->param('order', 'status,id_desc'), $this->param('build', 0), $this->param('status', 'all'), 0, 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$bugs = $data->data->bugs;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
$this->loadModel('product');
|
||||
foreach($bugs as $bug)
|
||||
{
|
||||
$status = array('code' => $bug->status, 'name' => $this->lang->bug->statusList[$bug->status]);
|
||||
if($bug->status == 'active' and $bug->confirmed) $status = array('code' => 'confirmed', 'name' => $this->lang->bug->labelConfirmed);
|
||||
if($bug->resolution == 'postponed') $status = array('code' => 'postponed', 'name' => $this->lang->bug->labelPostponed);
|
||||
if(!empty($bug->delay)) $status = array('code' => 'delay', 'name' => $this->lang->bug->overdueBugs);
|
||||
$bug->status = $status['code'];
|
||||
$bug->statusName = $status['name'];
|
||||
|
||||
$product = $this->product->getById($bug->product);
|
||||
$bug->productStatus = $product->status;
|
||||
|
||||
$result[$bug->id] = $this->format($bug, 'activatedDate:time,openedDate:time,assignedDate:time,resolvedDate:time,closedDate:time,lastEditedDate:time,deadline:date,deleted:bool');
|
||||
}
|
||||
|
||||
$storyChangeds = $this->dao->select('t1.id')->from(TABLE_BUG)->alias('t1')
|
||||
->leftJoin(TABLE_STORY)->alias('t2')->on('t1.story=t2.id')
|
||||
->where('t1.id')->in(array_keys($result))
|
||||
->andWhere('t1.story')->ne('0')
|
||||
->andWhere('t1.storyVersion != t2.version')
|
||||
->fetchPairs('id', 'id');
|
||||
foreach($storyChangeds as $bugID)
|
||||
{
|
||||
$status = array('code' => 'storyChanged', 'name' => $this->lang->bug->changed);
|
||||
$result[$bugID]->status = $status['code'];
|
||||
$result[$bugID]->statusName = $status['name'];
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'bugs' => array_values($result)));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
51
api/v1/entries/projectcases.php
Normal file
51
api/v1/entries/projectcases.php
Normal file
@ -0,0 +1,51 @@
|
||||
<?php
|
||||
/**
|
||||
* The project cases entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class projectCasesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
if(!$projectID) $projectID = $this->param('project', 0);
|
||||
if(empty($projectID)) return $this->sendError(400, 'Need project id.');
|
||||
|
||||
$this->resetOpenApp('project');
|
||||
$this->app->session->set('project', $projectID, $this->app->tab);
|
||||
|
||||
$control = $this->loadController('project', 'testcase');
|
||||
$control->testcase($projectID, $this->param('product', 0), $this->param('branch', 0), $this->param('status', 'all'), 0, $this->param('order', 'id_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$cases = $data->data->cases;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
foreach($cases as $case)
|
||||
{
|
||||
$case->statusName = $this->lang->testcase->statusList[$case->status];
|
||||
$result[] = $this->format($case, 'openedDate:time,reviewedDate:date,lastEditedDate:time,lastRunDate:time');
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'cases' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
77
api/v1/entries/projectreleases.php
Normal file
77
api/v1/entries/projectreleases.php
Normal file
@ -0,0 +1,77 @@
|
||||
<?php
|
||||
/**
|
||||
* The projectreleases entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class projectReleasesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
if(empty($projectID)) $projectID = $this->param('project');
|
||||
if(empty($projectID)) return $this->sendError(400, 'Need project id.');
|
||||
|
||||
$page = intval($this->param('page', 1));
|
||||
$limit = intval($this->param('limit', 20));
|
||||
$control = $this->loadController('projectrelease', 'browse');
|
||||
$control->browse($projectID, $this->param('execution', 0), $this->param('status', 'all'), $this->param('order', 't1.date_desc'), 0, $limit, $page);
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$result = array();
|
||||
$releases = $data->data->releases;
|
||||
foreach($releases as $release) $result[] = $this->format($release, 'deleted:bool,date:date,mailto:userList');
|
||||
|
||||
return $this->send(200, array('total' => count($result), 'releases' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($projectID = 0)
|
||||
{
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
$fields = 'name,build,product,date,notify,mailto';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('desc', $this->request('desc', ''));
|
||||
|
||||
$control = $this->loadController('projectrelease', 'create');
|
||||
$this->requireFields('name,date');
|
||||
|
||||
$control->create($projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(isset($data->result) and!isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$release = $this->loadModel('projectrelease')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $release);
|
||||
}
|
||||
}
|
143
api/v1/entries/projects.php
Normal file
143
api/v1/entries/projects.php
Normal file
@ -0,0 +1,143 @@
|
||||
<?php
|
||||
/**
|
||||
* The project entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class projectsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $programID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($programID = 0)
|
||||
{
|
||||
if(!$programID) $programID = $this->param('program', 0);
|
||||
$appendFields = $this->param('fields', '');
|
||||
if(stripos(strtolower(",{$appendFields},"), ',dropmenu,') !== false) return $this->getDropMenu();
|
||||
|
||||
$_COOKIE['involved'] = $this->param('involved', 0);
|
||||
|
||||
$this->config->systemMode = 'ALM';
|
||||
|
||||
if($programID)
|
||||
{
|
||||
$control = $this->loadController('program', 'project');
|
||||
$control->project($programID, $this->param('status', 'all'), $this->param('order', 'order_asc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
}
|
||||
else
|
||||
{
|
||||
$control = $this->loadController('project', 'browse');
|
||||
$control->browse($programID, $this->param('status', 'all'), 0, $this->param('order', 'order_asc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$pager = $data->data->pager;
|
||||
$users = $data->data->users;
|
||||
$result = array();
|
||||
foreach($data->data->projectStats as $project)
|
||||
{
|
||||
foreach($project->hours as $field => $value) $project->$field = $value;
|
||||
|
||||
$result[] = $this->format($project, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,realBegan:date,realEnd:date,PM:user,whitelist:userList,deleted:bool');
|
||||
}
|
||||
|
||||
$data = array();
|
||||
$data['page'] = $pager->pageID;
|
||||
$data['total'] = $pager->recTotal;
|
||||
$data['limit'] = (int)$pager->recPerPage;
|
||||
$data['projects'] = $result;
|
||||
|
||||
$withUser = $this->param('withUser', '');
|
||||
if(!empty($withUser)) $data['users'] = $users;
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$fields = 'name,begin,end,products';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('code', $this->request('code', ''));
|
||||
$this->setPost('acl', $this->request('acl', 'private'));
|
||||
$this->setPost('parent', $this->request('program', 0));
|
||||
$this->setPost('whitelist', $this->request('whitelist', array()));
|
||||
$this->setPost('PM', $this->request('PM', ''));
|
||||
$this->setPost('model', $this->request('model', 'scrum'));
|
||||
$this->setPost('parent', $this->request('parent', 0));
|
||||
|
||||
$control = $this->loadController('project', 'create');
|
||||
$this->requireFields('name,code,begin,end,products');
|
||||
|
||||
$control->create($this->request('model', 'scrum'));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(!isset($data->result)) return $this->sendError(400, 'error');
|
||||
|
||||
$project = $this->loadModel('project')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($project, 'openedBy:user,openedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,realBegan:date,realEnd:date,PM:user,whitelist:userList,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get drop menu.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function getDropMenu()
|
||||
{
|
||||
$control = $this->loadController('project', 'ajaxGetDropMenu');
|
||||
$control->ajaxGetDropMenu($this->request('projectID', 0), $this->request('module', 'project'), $this->request('method', 'browse'));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$dropMenu = array('owner' => array(), 'other' => array(), 'closed' => array());
|
||||
foreach($data->data->projects as $programID => $projects)
|
||||
{
|
||||
foreach($projects as $project)
|
||||
{
|
||||
if(helper::diffDate(date('Y-m-d'), $project->end) > 0) $project->delay = true;
|
||||
$project = $this->filterFields($project, 'id,model,type,name,code,parent,status,PM,delay');
|
||||
|
||||
if($project->status == 'closed')
|
||||
{
|
||||
$dropMenu['closed'][] = $project;
|
||||
}
|
||||
elseif($project->PM == $this->app->user->account)
|
||||
{
|
||||
$dropMenu['owner'][] = $project;
|
||||
}
|
||||
else
|
||||
{
|
||||
$dropMenu['other'][] = $project;
|
||||
}
|
||||
}
|
||||
}
|
||||
return $this->send(200, $dropMenu);
|
||||
}
|
||||
}
|
49
api/v1/entries/projectstories.php
Normal file
49
api/v1/entries/projectstories.php
Normal file
@ -0,0 +1,49 @@
|
||||
<?php
|
||||
/**
|
||||
* The project entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package project
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class projectStoriesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID)
|
||||
{
|
||||
if(!$projectID) $projectID = $this->param('project');
|
||||
if(!$projectID) return $this->sendError(400, 'Need product id.');
|
||||
|
||||
$control = $this->loadController('projectstory', 'story');
|
||||
$control->story($projectID, $this->param('product', 0), $this->param('branch', ''), $this->param('status', 'unclosed'), 0, 'story', $this->param('order', 'id_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$stories = $data->data->stories;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
$this->loadModel('product');
|
||||
foreach($stories as $story)
|
||||
{
|
||||
$product = $this->product->getById($story->product);
|
||||
$story->productStatus = $product->status;
|
||||
|
||||
$result[] = $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList');
|
||||
}
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'stories' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
75
api/v1/entries/release.php
Normal file
75
api/v1/entries/release.php
Normal file
@ -0,0 +1,75 @@
|
||||
<?php
|
||||
/**
|
||||
* The release entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class releaseEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $planID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($releaseID)
|
||||
{
|
||||
$control = $this->loadController('release', 'view');
|
||||
$control->view($releaseID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$release = $this->format($data->data->release, 'date:date,deleted:bool');
|
||||
|
||||
return $this->send(200, $release);
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $releaseID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($releaseID)
|
||||
{
|
||||
$oldRelease = $this->loadModel('release')->getByID($releaseID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'name,build,status,desc';
|
||||
$this->batchSetPost($fields, $oldRelease);
|
||||
|
||||
$control = $this->loadController('release', 'edit');
|
||||
$control->edit($releaseID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$release = $this->release->getByID($releaseID);
|
||||
return $this->sendSuccess(200, $this->format($release, 'date:date,deleted:bool'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $releaseID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($releaseID)
|
||||
{
|
||||
$control = $this->loadController('release', 'delete');
|
||||
$control->delete($releaseID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
43
api/v1/entries/releases.php
Normal file
43
api/v1/entries/releases.php
Normal file
@ -0,0 +1,43 @@
|
||||
<?php
|
||||
/**
|
||||
* The productplans entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class releasesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($productID = 0)
|
||||
{
|
||||
if(empty($productID)) $productID = $this->param('product');
|
||||
if(empty($productID)) return $this->sendError(400, 'Need product id.');
|
||||
|
||||
$control = $this->loadController('release', 'browse');
|
||||
$control->browse($productID, $this->param('branch', 0), $this->param('status', 'all'), $this->param('order', 't1.date_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$result = array();
|
||||
$releases = $data->data->releases;
|
||||
foreach($releases as $release) $result[] = $this->format($release, 'deleted:bool,date:date,mailto:userList');
|
||||
|
||||
return $this->send(200, array('total' => count($result), 'releases' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
374
api/v1/entries/reports.php
Normal file
374
api/v1/entries/reports.php
Normal file
@ -0,0 +1,374 @@
|
||||
<?php
|
||||
/**
|
||||
* The reports entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class reportsEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$fields = $this->param('fields', '');
|
||||
$dept = $this->param('dept', 0);
|
||||
$account = $this->param('account', '');
|
||||
$year = $this->param('year', date('Y'));
|
||||
if(empty($fields)) return $this->send(400, 'Need fields param for report.');
|
||||
|
||||
$accounts = array();
|
||||
if($account) $accounts = array($account => $account);
|
||||
if(empty($accounts) and $dept) $accounts = array_keys($this->loadModel('dept')->getDeptUserPairs($dept));
|
||||
if(empty($accounts) and empty($dept)) $accounts = array_keys($this->loadModel('user')->getPairs('noclosed'));
|
||||
|
||||
$fields = explode(',', strtolower($fields));
|
||||
$report = array();
|
||||
foreach($fields as $field)
|
||||
{
|
||||
$field = trim($field);
|
||||
if(empty($field)) continue;
|
||||
|
||||
if($field == 'projectoverview')
|
||||
{
|
||||
$report['projectOverview'] = $this->projectOverview($accounts);
|
||||
}
|
||||
elseif($field == 'radar')
|
||||
{
|
||||
$report['radar'] = $this->radar($accounts, $year);
|
||||
}
|
||||
elseif($field == 'projectprogress')
|
||||
{
|
||||
$report['projectProgress'] = $this->projectProgress();
|
||||
}
|
||||
elseif($field == 'executionprogress')
|
||||
{
|
||||
$report['executionProgress'] = $this->executionProgress();
|
||||
}
|
||||
elseif($field == 'productprogress')
|
||||
{
|
||||
$report['productProgress'] = $this->productProgress();
|
||||
}
|
||||
elseif($field == 'bugprogress')
|
||||
{
|
||||
$report['bugProgress'] = $this->bugProgress();
|
||||
}
|
||||
elseif($field == 'bugprogress')
|
||||
{
|
||||
$report['bugProgress'] = $this->bugProgress();
|
||||
}
|
||||
elseif($field == 'output')
|
||||
{
|
||||
$report['output'] = $this->loadModel('report')->getOutput4API($accounts, $year);
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, $report);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get project overview by status.
|
||||
*
|
||||
* @param array $accounts
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function projectOverview($accounts)
|
||||
{
|
||||
$statusOverview = $this->loadModel('report')->getProjectStatusOverview($accounts);
|
||||
|
||||
$this->app->loadLang('project');
|
||||
$total = 0;
|
||||
$overview = array();
|
||||
foreach($statusOverview as $status => $count)
|
||||
{
|
||||
$total += $count;
|
||||
$statusName = zget($this->lang->project->statusList, $status);
|
||||
|
||||
$overview[$status] = array();
|
||||
$overview[$status]['code'] = $status;
|
||||
$overview[$status]['name'] = $statusName;
|
||||
$overview[$status]['total'] = $count;
|
||||
}
|
||||
|
||||
$projectOverview = array();
|
||||
$projectOverview['total'] = $total;
|
||||
$projectOverview['overview'] = array_values($overview);
|
||||
|
||||
return $projectOverview;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get radar data. include product, execution, qa, devel and other.
|
||||
*
|
||||
* @param array $accounts
|
||||
* @param string $year
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function radar($accounts, $year)
|
||||
{
|
||||
$contributions = $this->loadModel('report')->getUserYearContributions($accounts, $year);
|
||||
$annualDataConfig = $this->config->report->annualData;
|
||||
|
||||
$radarData = array('product' => 0, 'execution' => 0, 'devel' => 0, 'qa' => 0, 'other' => 0);
|
||||
foreach($contributions as $objectType => $objectContributions)
|
||||
{
|
||||
foreach($objectContributions as $actionName => $count)
|
||||
{
|
||||
$radarTypes = isset($annualDataConfig['radar'][$objectType][$actionName]) ? $annualDataConfig['radar'][$objectType][$actionName] : array('other');
|
||||
foreach($radarTypes as $radarType) $radarData[$radarType] += $count;
|
||||
}
|
||||
}
|
||||
|
||||
$radar = array();
|
||||
foreach($radarData as $radarType => $total)
|
||||
{
|
||||
$radar[$radarType]['code'] = $radarType;
|
||||
$radar[$radarType]['name'] = $this->lang->report->annualData->radarItems[$radarType];
|
||||
$radar[$radarType]['total'] = $total;
|
||||
}
|
||||
|
||||
return array_values($radar);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get project progress.
|
||||
*
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function projectProgress()
|
||||
{
|
||||
$projects = $this->loadModel('program')->getProjectStats(0, 'all');
|
||||
$this->app->loadLang('project');
|
||||
|
||||
$processedProjects = array();
|
||||
$statusList['all']['total'] = 0;
|
||||
$statusList['doing']['total'] = 0;
|
||||
$statusList['wait']['total'] = 0;
|
||||
$statusList['closed']['total'] = 0;
|
||||
foreach($projects as $project)
|
||||
{
|
||||
$newProject = new stdclass();
|
||||
$newProject->id = $project->id;
|
||||
$newProject->name = $project->name;
|
||||
$newProject->status = $project->status;
|
||||
$newProject->progress = round($project->hours->progress, 1);
|
||||
$newProject->totalConsumed = round($project->hours->totalConsumed, 1);
|
||||
$newProject->totalLeft = round($project->hours->totalLeft, 1);
|
||||
if(isset($project->delay)) $newProject->delay = $project->delay;
|
||||
|
||||
$statusList['all']['total'] += 1;
|
||||
if(isset($statusList[$project->status])) $statusList[$project->status]['total'] += 1;
|
||||
|
||||
$processedProjects[$project->id] = $newProject;
|
||||
}
|
||||
|
||||
foreach(array_keys($statusList) as $status)
|
||||
{
|
||||
$statusName = zget($this->lang->project->statusList, $status);
|
||||
if($status == 'all') $statusName = $this->lang->project->featureBar['browse']['all'];
|
||||
|
||||
$statusList[$status]['code'] = $status;
|
||||
$statusList[$status]['name'] = $statusName;
|
||||
}
|
||||
|
||||
return array('statusList' => $statusList, 'projects' => array_values($processedProjects));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get execution progress.
|
||||
*
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function executionProgress()
|
||||
{
|
||||
$executions = $this->loadModel('execution')->getStatData(0, 'all', 0, 0, false, '', 'id_desc');
|
||||
|
||||
$processedExecutions = array();
|
||||
$statusList['all']['total'] = 0;
|
||||
$statusList['doing']['total'] = 0;
|
||||
$statusList['wait']['total'] = 0;
|
||||
$statusList['closed']['total'] = 0;
|
||||
foreach($executions as $execution)
|
||||
{
|
||||
$newExecution = new stdclass();
|
||||
$newExecution->id = $execution->id;
|
||||
$newExecution->name = $execution->name;
|
||||
$newExecution->status = $execution->status;
|
||||
$newExecution->progress = round($execution->hours->progress, 1);
|
||||
$newExecution->totalConsumed = round($execution->hours->totalConsumed, 1);
|
||||
$newExecution->totalLeft = round($execution->hours->totalLeft, 1);
|
||||
if(isset($execution->delay)) $newExecution->delay = $execution->delay;
|
||||
|
||||
$statusList['all']['total'] += 1;
|
||||
if(isset($statusList[$execution->status])) $statusList[$execution->status]['total'] += 1;
|
||||
|
||||
$processedExecutions[$execution->id] = $newExecution;
|
||||
}
|
||||
|
||||
foreach(array_keys($statusList) as $status)
|
||||
{
|
||||
$statusName = zget($this->lang->execution->statusList, $status);
|
||||
if($status == 'all') $statusName = $this->lang->execution->allTasks;
|
||||
|
||||
$statusList[$status]['code'] = $status;
|
||||
$statusList[$status]['name'] = $statusName;
|
||||
}
|
||||
|
||||
return array('statusList' => $statusList, 'executions' => array_values($processedExecutions));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get product progress with story.
|
||||
*
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function productProgress()
|
||||
{
|
||||
$this->app->loadLang('product');
|
||||
$this->app->loadLang('story');
|
||||
|
||||
$storyStatusStat = $this->dao->select('t1.product,t2.name,t2.status,t1.status as storyStatus,count(*) as storyCount')->from(TABLE_STORY)->alias('t1')
|
||||
->leftJoin(TABLE_PRODUCT)->alias('t2')->on('t1.product=t2.id')
|
||||
->where('t2.deleted')->eq(0)
|
||||
->andWhere('t1.deleted')->eq(0)
|
||||
->beginIF(!$this->app->user->admin)->andWhere('t2.id')->in($this->app->user->view->products)->fi()
|
||||
->groupBy('t1.product,t1.status')
|
||||
->orderBy('t1.product_desc,t1.status')
|
||||
->fetchAll();
|
||||
|
||||
$productStatusList['all']['total'] = 0;
|
||||
$productStatusList['normal']['total'] = 0;
|
||||
$productStatusList['closed']['total'] = 0;
|
||||
|
||||
$processedProducts = array();
|
||||
$productStoryStat = array();
|
||||
foreach($storyStatusStat as $product)
|
||||
{
|
||||
$productStoryStat[$product->product][$product->storyStatus] = $product->storyCount;
|
||||
|
||||
if(isset($processedProducts[$product->product])) continue;
|
||||
|
||||
$newProduct = new stdclass();
|
||||
$newProduct->id = $product->product;
|
||||
$newProduct->name = $product->name;
|
||||
$newProduct->status = $product->status;
|
||||
|
||||
$processedProducts[$product->product] = $newProduct;
|
||||
$productStatusList['all']['total'] += 1;
|
||||
if(isset($productStatusList[$product->status])) $productStatusList[$product->status]['total'] += 1;
|
||||
}
|
||||
|
||||
/* Set story status statistics integrate into product. */
|
||||
$storyStatusList = array('draft' => array(), 'reviewing' => array(), 'active' => array(), 'changing' => array(), 'closed' => array());
|
||||
foreach($processedProducts as $productID => $product)
|
||||
{
|
||||
$product->storyStat = array();
|
||||
foreach(array_keys($storyStatusList) as $storyStatus) $product->storyStat[$storyStatus] = isset($productStoryStat[$productID][$storyStatus]) ? $productStoryStat[$productID][$storyStatus] : 0;
|
||||
$product->progress = $product->storyStat['closed'] == 0 ? 0 : round($product->storyStat['closed'] / array_sum($product->storyStat) * 100, 1);
|
||||
}
|
||||
|
||||
foreach(array_keys($productStatusList) as $status)
|
||||
{
|
||||
$statusName = zget($this->lang->product->statusList, $status);
|
||||
if($status == 'all') $statusName = $this->lang->product->allStory;
|
||||
if($status == 'normal') $statusName = $this->lang->product->unclosed;
|
||||
|
||||
$productStatusList[$status]['code'] = $status;
|
||||
$productStatusList[$status]['name'] = $statusName;
|
||||
}
|
||||
|
||||
foreach(array_keys($storyStatusList) as $status)
|
||||
{
|
||||
$statusName = zget($this->lang->story->statusList, $status);
|
||||
|
||||
$storyStatusList[$status]['code'] = $status;
|
||||
$storyStatusList[$status]['name'] = $statusName;
|
||||
}
|
||||
|
||||
return array('productStatusList' => $productStatusList, 'products' => array_values($processedProducts), 'storyStatusList' => $storyStatusList);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get bug progress by product.
|
||||
*
|
||||
* @access public
|
||||
* @return array
|
||||
*/
|
||||
public function bugProgress()
|
||||
{
|
||||
$this->app->loadLang('product');
|
||||
$this->app->loadLang('bug');
|
||||
|
||||
$bugStatusStat = $this->dao->select('t1.product,t2.name,t2.status,t1.status as bugStatus,count(*) as bugCount')->from(TABLE_BUG)->alias('t1')
|
||||
->leftJoin(TABLE_PRODUCT)->alias('t2')->on('t1.product=t2.id')
|
||||
->where('t2.deleted')->eq(0)
|
||||
->andWhere('t1.deleted')->eq(0)
|
||||
->beginIF(!$this->app->user->admin)->andWhere('t2.id')->in($this->app->user->view->products)->fi()
|
||||
->groupBy('t1.product,t1.status')
|
||||
->orderBy('t1.product_desc,t1.status')
|
||||
->fetchAll();
|
||||
|
||||
$productStatusList['all']['total'] = 0;
|
||||
$productStatusList['normal']['total'] = 0;
|
||||
$productStatusList['closed']['total'] = 0;
|
||||
|
||||
$processedProducts = array();
|
||||
$productBugStat = array();
|
||||
foreach($bugStatusStat as $product)
|
||||
{
|
||||
$productBugStat[$product->product][$product->bugStatus] = $product->bugCount;
|
||||
|
||||
if(isset($processedProducts[$product->product])) continue;
|
||||
|
||||
$newProduct = new stdclass();
|
||||
$newProduct->id = $product->product;
|
||||
$newProduct->name = $product->name;
|
||||
$newProduct->status = $product->status;
|
||||
|
||||
$processedProducts[$product->product] = $newProduct;
|
||||
$productStatusList['all']['total'] += 1;
|
||||
if(isset($productStatusList[$product->status])) $productStatusList[$product->status]['total'] += 1;
|
||||
}
|
||||
|
||||
/* Set bug status statistics integrate into product. */
|
||||
$bugStatusList = array('active' => array(), 'resolved' => array(), 'closed' => array());
|
||||
foreach($processedProducts as $productID => $product)
|
||||
{
|
||||
$product->bugStat = array();
|
||||
foreach(array_keys($bugStatusList) as $bugStatus) $product->bugStat[$bugStatus] = isset($productBugStat[$productID][$bugStatus]) ? $productBugStat[$productID][$bugStatus] : 0;
|
||||
}
|
||||
|
||||
foreach(array_keys($productStatusList) as $status)
|
||||
{
|
||||
$statusName = zget($this->lang->product->statusList, $status);
|
||||
if($status == 'all') $statusName = $this->lang->product->allStory;
|
||||
if($status == 'normal') $statusName = $this->lang->product->unclosed;
|
||||
|
||||
$productStatusList[$status]['code'] = $status;
|
||||
$productStatusList[$status]['name'] = $statusName;
|
||||
}
|
||||
|
||||
foreach(array_keys($bugStatusList) as $status)
|
||||
{
|
||||
$statusName = zget($this->lang->bug->statusList, $status);
|
||||
|
||||
$bugStatusList[$status]['code'] = $status;
|
||||
$bugStatusList[$status]['name'] = $statusName;
|
||||
}
|
||||
|
||||
return array('productStatusList' => $productStatusList, 'bugs' => array_values($processedProducts), 'bugStatusList' => $bugStatusList);
|
||||
}
|
||||
}
|
32
api/v1/entries/reporules.php
Normal file
32
api/v1/entries/reporules.php
Normal file
@ -0,0 +1,32 @@
|
||||
<?php
|
||||
/**
|
||||
* The reporules entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Yidong Wang <yidong@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class repoRulesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$control = $this->loadController('repo', 'ajaxGetRules');
|
||||
$control->ajaxGetRules();
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
return $this->send(200, $data->rules);
|
||||
}
|
||||
}
|
56
api/v1/entries/repos.php
Normal file
56
api/v1/entries/repos.php
Normal file
@ -0,0 +1,56 @@
|
||||
<?php
|
||||
/**
|
||||
* The repos entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class reposEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get()
|
||||
{
|
||||
$control = $this->loadController('repo', 'maintain');
|
||||
$repoUrl = $this->param('repoUrl', '');
|
||||
|
||||
if(empty($repoUrl))
|
||||
{
|
||||
$control->maintain(0, $this->param('order', 'id_desc'), 0, $this->param('limit', 100), $this->param('page', 1));
|
||||
/* Response */
|
||||
$data = $this->getData();
|
||||
}
|
||||
else
|
||||
{
|
||||
$data = (object)$this->loadModel('repo')->getRepoListByUrl($repoUrl);
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
if(empty($repoUrl))
|
||||
{
|
||||
$result = array();
|
||||
$pager = $data->data->pager;
|
||||
$repos = $data->data->repoList;
|
||||
foreach($repos as $repo) $result[] = $this->format($repo, 'deleted:bool,lastSync:datetime,synced:bool,product:idList');
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'repos' => $result));
|
||||
}
|
||||
else
|
||||
{
|
||||
return $this->send(200, array('repos' => $data->repos));
|
||||
}
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
}
|
75
api/v1/entries/risk.php
Normal file
75
api/v1/entries/risk.php
Normal file
@ -0,0 +1,75 @@
|
||||
<?php
|
||||
/**
|
||||
* The risk entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class riskEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $riskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($riskID)
|
||||
{
|
||||
$control = $this->loadController('risk', 'view');
|
||||
$control->view($riskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or (isset($data->message) and $data->message == '404 Not found')) return $this->send404();
|
||||
if(isset($data->status) and $data->status == 'success') return $this->send(200, $this->format($data->data->risk, 'createdDate:time,editedDate:time'));
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $riskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($riskID)
|
||||
{
|
||||
$oldRisk = $this->loadModel('risk')->getByID($riskID);
|
||||
if(!$oldRisk) return $this->send404();
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'source,name,category,strategy,status,impact,probability,rate,identifiedDate,plannedClosedDate,actualClosedDate,resolvedBy,assignedTo,prevention,remedy,resolution';
|
||||
$this->batchSetPost($fields, $oldRisk);
|
||||
|
||||
$control = $this->loadController('risk', 'edit');
|
||||
$control->edit($riskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$risk = $this->risk->getByID($riskID);
|
||||
return $this->send(200, $this->format($risk, 'createdDate:time,editedDate:time'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $riskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($riskID)
|
||||
{
|
||||
$control = $this->loadController('risk', 'delete');
|
||||
$control->delete($riskID, 'true');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
87
api/v1/entries/risks.php
Normal file
87
api/v1/entries/risks.php
Normal file
@ -0,0 +1,87 @@
|
||||
<?php
|
||||
/**
|
||||
* The risks entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class risksEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($projectID = 0)
|
||||
{
|
||||
if(!$projectID)
|
||||
{
|
||||
/* Get my risks defaultly. */
|
||||
$control = $this->loadController('my', 'risk');
|
||||
$control->risk($this->param('type', 'assignedTo'), $this->param('order', 'id_desc'), $this->param('total', 0), $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
}
|
||||
else
|
||||
{
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
/* Get risks by project. */
|
||||
$control = $this->loadController('risk', 'browse');
|
||||
$control->browse($projectID, $this->param('type', 'all'), '', $this->param('order', ''), $this->param('total', 0), $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
}
|
||||
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
foreach($data->data->risks as $risk)
|
||||
{
|
||||
$result[] = $this->format($risk, 'createdDate:time,editedDate:time');
|
||||
}
|
||||
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'risks' => $result));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $projectID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($projectID = 0)
|
||||
{
|
||||
$project = $this->loadModel('project')->getByID($projectID);
|
||||
if(!$project) return $this->send404();
|
||||
|
||||
$fields = 'source,name,category,strategy,status,impact,probability,rate,identifiedDate,plannedClosedDate,actualClosedDate,resolvedBy,assignedTo,prevention,remedy,resolution';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('impact', $this->request('impact', 3));
|
||||
$this->setPost('probability', $this->request('probability', 3));
|
||||
$this->setPost('rate', $this->request('rate', 9));
|
||||
$this->setPost('pri', 'middle');
|
||||
|
||||
$control = $this->loadController('risk', 'create');
|
||||
$this->requireFields('name');
|
||||
|
||||
$control->create($projectID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(isset($data->result) and !isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$risk = $this->loadModel('risk')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($risk, 'createdDate:time,editedDate:time'));
|
||||
}
|
||||
}
|
132
api/v1/entries/stakeholders.php
Normal file
132
api/v1/entries/stakeholders.php
Normal file
@ -0,0 +1,132 @@
|
||||
<?php
|
||||
/**
|
||||
* The stakeholder entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class stakeholdersEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $programID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($programID = 0)
|
||||
{
|
||||
if(!$programID) $programID = $this->param('program', 0);
|
||||
|
||||
if($programID)
|
||||
{
|
||||
$control = $this->loadController('program', 'stakeholder');
|
||||
$control->stakeholder($programID, $this->param('order', 't1.id_desc'), 0, $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$this->app->loadLang('stakeholder');
|
||||
$pager = $data->data->pager;
|
||||
$users = $data->data->users;
|
||||
$result = array();
|
||||
foreach($data->data->stakeholders as $stakeholder)
|
||||
{
|
||||
$stakeholder->roleName = zget($this->lang->user->roleList, $stakeholder->role, '');
|
||||
$stakeholder->typeName = zget($this->lang->stakeholder->fromList, $stakeholder->from, '');
|
||||
|
||||
$result[] = $stakeholder;
|
||||
}
|
||||
|
||||
$data = array();
|
||||
$data['page'] = $pager->pageID;
|
||||
$data['total'] = $pager->recTotal;
|
||||
$data['limit'] = (int)$pager->recPerPage;
|
||||
$data['stakeholders'] = $result;
|
||||
|
||||
$withUser = $this->param('withUser', '');
|
||||
if(!empty($withUser)) $data['users'] = $users;
|
||||
|
||||
return $this->send(200, $data);
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post()
|
||||
{
|
||||
$fields = 'name,begin,end,products';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('code', $this->request('code', ''));
|
||||
$this->setPost('acl', $this->request('acl', 'private'));
|
||||
$this->setPost('parent', $this->request('program', 0));
|
||||
$this->setPost('whitelist', $this->request('whitelist', array()));
|
||||
$this->setPost('PM', $this->request('PM', ''));
|
||||
$this->setPost('model', $this->request('model', 'scrum'));
|
||||
|
||||
$control = $this->loadController('project', 'create');
|
||||
$this->requireFields('name,code,begin,end,products');
|
||||
|
||||
$control->create($this->request('model', 'scrum'));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
if(!isset($data->result)) return $this->sendError(400, 'error');
|
||||
|
||||
$project = $this->loadModel('project')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($project, 'openedDate:time,lastEditedDate:time,closedDate:time,canceledDate:time'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get drop menu.
|
||||
*
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function getDropMenu()
|
||||
{
|
||||
$control = $this->loadController('project', 'ajaxGetDropMenu');
|
||||
$control->ajaxGetDropMenu($this->request('projectID', 0), $this->request('module', 'project'), $this->request('method', 'browse'));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(400, $data->message);
|
||||
|
||||
$dropMenu = array('owner' => array(), 'other' => array(), 'closed' => array());
|
||||
foreach($data->data->projects as $programID => $projects)
|
||||
{
|
||||
foreach($projects as $project)
|
||||
{
|
||||
if(helper::diffDate(date('Y-m-d'), $project->end) > 0) $project->delay = true;
|
||||
$project = $this->filterFields($project, 'id,model,type,name,code,parent,status,PM,delay');
|
||||
|
||||
if($project->status == 'closed')
|
||||
{
|
||||
$dropMenu['closed'][] = $project;
|
||||
}
|
||||
elseif($project->PM == $this->app->user->account)
|
||||
{
|
||||
$dropMenu['owner'][] = $project;
|
||||
}
|
||||
else
|
||||
{
|
||||
$dropMenu['other'][] = $project;
|
||||
}
|
||||
}
|
||||
}
|
||||
return $this->send(200, $dropMenu);
|
||||
}
|
||||
}
|
93
api/v1/entries/stories.php
Normal file
93
api/v1/entries/stories.php
Normal file
@ -0,0 +1,93 @@
|
||||
<?php
|
||||
/**
|
||||
* The stories entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class storiesEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($productID = 0)
|
||||
{
|
||||
if(!$productID) $productID = $this->param('product');
|
||||
if(!$productID) return $this->sendError(400, 'Need product id.');
|
||||
|
||||
$control = $this->loadController('product', 'browse');
|
||||
$control->browse($productID, $this->param('branch', ''), $this->param('status', 'unclosed'), 0, $this->param('type', 'story'), $this->param('order', 'id_desc'), 0, $this->param('limit', 500), $this->param('page', 1));
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->sendError(400, 'error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$stories = $data->data->stories;
|
||||
$pager = $data->data->pager;
|
||||
$requirements = $this->loadModel('story')->getRequirements($productID);
|
||||
|
||||
$result = array();
|
||||
$this->loadModel('product');
|
||||
foreach($stories as $story)
|
||||
{
|
||||
$product = $this->product->getById($story->product);
|
||||
$story->productStatus = $product->status;
|
||||
if(isset($story->children))
|
||||
{
|
||||
$story->children = array_values((array)$story->children);
|
||||
foreach($story->children as $id => $children)
|
||||
{
|
||||
$childrenProduct = $this->product->getById($children->product);
|
||||
$story->children[$id]->productStatus = $childrenProduct->status;
|
||||
}
|
||||
}
|
||||
|
||||
$result[] = $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList');
|
||||
}
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'stories' => $result, 'requirements' => $requirements));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $productID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($productID = 0)
|
||||
{
|
||||
if(!$productID) $productID = $this->param('product', 0);
|
||||
if(!$productID and isset($this->requestBody->product)) $productID = $this->requestBody->product;
|
||||
if(!$productID) return $this->sendError(400, 'Need product id.');
|
||||
|
||||
$fields = 'title,spec,verify,reviewer,type,parent,plan,module,moduleOptionMenu,source,sourceNote,category,pri,estimate,mailto,keywords,notifyemail,uid,URS,status';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
/* If reviewer is not post, set needNotReview. */
|
||||
$reviewer = $this->request('reviewer');
|
||||
if(empty($reviewer)) $this->setPost('needNotReview', 1);
|
||||
$this->setPost('product', $productID);
|
||||
$this->setPost('type', $this->param('type', 'story'));
|
||||
$this->setPost('status', $this->param('status', 'draft'));
|
||||
|
||||
$control = $this->loadController('story', 'create');
|
||||
$this->requireFields('title,spec,pri,category');
|
||||
|
||||
$control->create($productID, $this->param('branch', 0), $this->param('moduleID', 0), $this->param('storyID', 0), $this->param('objectID', 0), $this->param('bugID', 0));
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
if(isset($data->result) and !isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$story = $this->loadModel('story')->getByID($data->id);
|
||||
return $this->send(200, $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
129
api/v1/entries/story.php
Normal file
129
api/v1/entries/story.php
Normal file
@ -0,0 +1,129 @@
|
||||
<?php
|
||||
/**
|
||||
* The story entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class storyEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($storyID)
|
||||
{
|
||||
$this->resetOpenApp($this->param('tab', 'product'));
|
||||
|
||||
$control = $this->loadController('story', 'view');
|
||||
$control->view($storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$story = $data->data->story;
|
||||
|
||||
if(!empty($story->children)) $story->children = array_values((array)$story->children);
|
||||
if(isset($story->planTitle)) $story->planTitle = array_values((array)$story->planTitle);
|
||||
if($story->parent > 0) $story->parentPri = $this->dao->select('pri')->from(TABLE_STORY)->where('id')->eq($story->parent)->fetch('pri');
|
||||
|
||||
/* Set product name and status*/
|
||||
$story->productName = $data->data->product->name;
|
||||
$story->productStatus = $data->data->product->status;
|
||||
|
||||
/* Set module title */
|
||||
$moduleTitle = '';
|
||||
if(empty($story->module)) $moduleTitle = '/';
|
||||
if($story->module)
|
||||
{
|
||||
$modulePath = $data->data->modulePath;
|
||||
foreach($modulePath as $key => $module)
|
||||
{
|
||||
$moduleTitle .= $module->name;
|
||||
if(isset($modulePath[$key + 1])) $moduleTitle .= '/';
|
||||
}
|
||||
}
|
||||
$story->moduleTitle = $moduleTitle;
|
||||
|
||||
$storyTasks = array();
|
||||
foreach($story->tasks as $executionTasks)
|
||||
{
|
||||
foreach($executionTasks as $task)
|
||||
{
|
||||
if(!isset($data->data->executions->{$task->execution})) continue;
|
||||
$storyTasks[] = $this->filterFields($task, 'id,name,type,status,assignedTo');
|
||||
}
|
||||
}
|
||||
$story->tasks = $this->format($storyTasks, 'assignedTo:user');
|
||||
|
||||
$story->bugs = array();
|
||||
foreach($data->data->bugs as $bug) $story->bugs[] = $this->filterFields($bug, 'id,title,status,pri,severity');
|
||||
|
||||
$story->cases = array();
|
||||
foreach($data->data->cases as $case) $story->cases[] = $this->filterFields($case, 'id,title,pri,status');
|
||||
|
||||
$story->requirements = array();
|
||||
foreach($data->data->relations as $relation) $story->requirements[] = $this->filterFields($relation, 'id,title');
|
||||
|
||||
$story->actions = $this->loadModel('action')->processActionForAPI($data->data->actions, $data->data->users, $this->lang->story);
|
||||
|
||||
$preAndNext = $data->data->preAndNext;
|
||||
$story->preAndNext = array();
|
||||
$story->preAndNext['pre'] = $preAndNext->pre ? $preAndNext->pre->id : '';
|
||||
$story->preAndNext['next'] = $preAndNext->next ? $preAndNext->next->id : '';
|
||||
|
||||
return $this->send(200, $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($storyID)
|
||||
{
|
||||
$oldStory = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'title,product,parent,reviewer,type,plan,module,source,sourceNote,category,pri,estimate,mailto,keywords,uid,stage,notifyEmail';
|
||||
$this->batchSetPost($fields, $oldStory);
|
||||
|
||||
$control = $this->loadController('story', 'edit');
|
||||
$control->edit($storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(400, $data->message);
|
||||
if(!isset($data->status)) return $this->sendError(400, 'error');
|
||||
|
||||
$story = $this->story->getByID($storyID);
|
||||
return $this->send(200, $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($storyID)
|
||||
{
|
||||
$control = $this->loadController('story', 'delete');
|
||||
$control->delete($storyID, 'yes');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
40
api/v1/entries/storyactive.php
Normal file
40
api/v1/entries/storyactive.php
Normal file
@ -0,0 +1,40 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug change point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
**/
|
||||
|
||||
class storyActiveEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($storyID)
|
||||
{
|
||||
$fields = 'assignedTo,status,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('story', 'activate');
|
||||
|
||||
$control->activate($storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$story = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
return $this->send(200, $story);
|
||||
}
|
||||
}
|
||||
|
37
api/v1/entries/storyassignto.php
Normal file
37
api/v1/entries/storyassignto.php
Normal file
@ -0,0 +1,37 @@
|
||||
<?php
|
||||
/**
|
||||
* The story assignto entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class storyAssignToEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($storyID)
|
||||
{
|
||||
$fields = 'assignedTo,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('story', 'assignTo');
|
||||
$control->assignTo($storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$story = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
return $this->send(200, $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
50
api/v1/entries/storychange.php
Normal file
50
api/v1/entries/storychange.php
Normal file
@ -0,0 +1,50 @@
|
||||
<?php
|
||||
/**
|
||||
* The bug change point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class storyChangeEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($storyID)
|
||||
{
|
||||
$oldStory = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
$fields = 'reviewer,comment,executions,bugs,cases,tasks,reviewedBy,uid';
|
||||
$this->batchSetPost($fields);
|
||||
$fields = 'title,spec,verify';
|
||||
$this->batchSetPost($fields, $oldStory);
|
||||
|
||||
/* If reviewer is not post, set needNotReview. */
|
||||
if(!$this->request('reviewer'))
|
||||
{
|
||||
$this->setPost('reviewer', array());
|
||||
$this->setPost('needNotReview', 1);
|
||||
}
|
||||
|
||||
$control = $this->loadController('story', 'change');
|
||||
$this->requireFields('title');
|
||||
|
||||
$control->change($storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$story = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
return $this->send(200, $this->format($story, 'openedDate:time,assignedDate:time,reviewedDate:time,lastEditedDate:time,closedDate:time'));
|
||||
}
|
||||
}
|
37
api/v1/entries/storyclose.php
Normal file
37
api/v1/entries/storyclose.php
Normal file
@ -0,0 +1,37 @@
|
||||
<?php
|
||||
/**
|
||||
* The story close entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class storyCloseEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($storyID)
|
||||
{
|
||||
$fields = 'closedReason,duplicateStory,childStories,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('story', 'close');
|
||||
$control->close($storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$story = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
return $this->send(200, $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
30
api/v1/entries/storyrecall.php
Normal file
30
api/v1/entries/storyrecall.php
Normal file
@ -0,0 +1,30 @@
|
||||
<?php
|
||||
/**
|
||||
* The story recall entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class storyRecallEntry extends entry
|
||||
{
|
||||
/**
|
||||
* Delete method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($storyID)
|
||||
{
|
||||
$control = $this->loadController('story', 'recall');
|
||||
$control->recall($storyID);
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
||||
|
61
api/v1/entries/storyrecordestimate.php
Normal file
61
api/v1/entries/storyrecordestimate.php
Normal file
@ -0,0 +1,61 @@
|
||||
<?php
|
||||
/**
|
||||
* The story recordEstimate entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class storyRecordEstimateEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($storyID)
|
||||
{
|
||||
if($this->config->edition == 'open') return $this->send400('ZenTaoPMS does not have story effort function.');
|
||||
|
||||
$control = $this->loadController('effort', 'createForObject');
|
||||
$control->createForObject('story', $storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->error('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$effort = $data->data->efforts;
|
||||
|
||||
return $this->send(200, array('effort' => $effort));
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($storyID)
|
||||
{
|
||||
if($this->config->edition == 'open') return $this->send400('ZenTaoPMS does not have story effort function.');
|
||||
|
||||
$fields = 'id,dates,consumed,objectType,objectID,work';
|
||||
$this->batchSetPost($fields);
|
||||
$control = $this->loadController('effort', 'createForObject');
|
||||
$control->createForObject('story', $storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$story = $this->loadModel('story')->getById($storyID);
|
||||
|
||||
return $this->send(200, $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
40
api/v1/entries/storyreview.php
Normal file
40
api/v1/entries/storyreview.php
Normal file
@ -0,0 +1,40 @@
|
||||
<?php
|
||||
/**
|
||||
* The story review of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
**/
|
||||
|
||||
class storyReviewEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $storyID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($storyID)
|
||||
{
|
||||
$fields = 'reviewedDate,result,closedReason,pri,estimate,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('story', 'review');
|
||||
|
||||
$control->review($storyID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$story = $this->loadModel('story')->getByID($storyID);
|
||||
|
||||
return $this->send(200, $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
||||
|
81
api/v1/entries/tabs.php
Normal file
81
api/v1/entries/tabs.php
Normal file
@ -0,0 +1,81 @@
|
||||
<?php
|
||||
/**
|
||||
* The tabs entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class tabsEntry extends baseEntry
|
||||
{
|
||||
/**
|
||||
* Get tabs.
|
||||
*
|
||||
* @param string $moduleName work|
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($moduleName)
|
||||
{
|
||||
$menus = array();
|
||||
if($moduleName == 'work')
|
||||
{
|
||||
$this->app->loadLang('my');
|
||||
$tabs = array('calendar', 'task', 'bug', 'story', 'issue', 'risk', 'myMeeting');
|
||||
|
||||
foreach($tabs as $menuKey)
|
||||
{
|
||||
if(!isset($this->lang->my->$menuKey)) continue;
|
||||
if(!common::hasPriv('my', 'work')) continue;
|
||||
$label = $this->lang->my->$menuKey;
|
||||
if($menuKey == 'calendar') $label = $this->lang->my->calendarAction;
|
||||
|
||||
$menu = new stdclass();
|
||||
$menu->code = $menuKey;
|
||||
$menu->name = $label;
|
||||
|
||||
$menus[] = $menu;
|
||||
}
|
||||
}
|
||||
elseif($moduleName == 'product')
|
||||
{
|
||||
$this->app->loadLang('product');
|
||||
$tabs = array('story', 'plan', 'project', 'release', 'requirement', 'doc', 'view');
|
||||
|
||||
foreach($tabs as $menuKey)
|
||||
{
|
||||
if($menuKey == 'requirement' and empty($this->config->URAndSR)) continue;
|
||||
if(isset($this->lang->product->menu->$menuKey))
|
||||
{
|
||||
$menuName = $this->lang->product->menu->$menuKey;
|
||||
if(!isset($menuName['link'])) continue;
|
||||
|
||||
list($label, $module, $method) = explode('|', $menuName['link']);
|
||||
if(!common::hasPriv($module, $method)) continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
if(!common::hasPriv('product', $menuKey)) continue;
|
||||
}
|
||||
|
||||
$label = zget($this->lang->product, $menuKey, '');
|
||||
if($menuKey == 'view') $label = $this->lang->overview;
|
||||
if($menuKey == 'doc') $label = $this->lang->doc->common;
|
||||
if($menuKey == 'project') $label = $this->lang->project->common;
|
||||
if($menuKey == 'story') $label = $this->lang->createObjects['story'];
|
||||
if($menuKey == 'requirement') $label = $this->lang->URCommon;
|
||||
|
||||
$menu = new stdclass();
|
||||
$menu->code = $menuKey;
|
||||
$menu->name = $label;
|
||||
|
||||
$menus[] = $menu;
|
||||
}
|
||||
}
|
||||
|
||||
return $this->send(200, array('tabs' => $menus));
|
||||
}
|
||||
}
|
135
api/v1/entries/task.php
Normal file
135
api/v1/entries/task.php
Normal file
@ -0,0 +1,135 @@
|
||||
<?php
|
||||
/**
|
||||
* The task entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($taskID)
|
||||
{
|
||||
$this->resetOpenApp($this->param('tab', 'execution'));
|
||||
|
||||
$control = $this->loadController('task', 'view');
|
||||
$control->view($taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
|
||||
if(!$data or !isset($data->status)) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $data->data->task;
|
||||
|
||||
if(!empty($task->children)) $task->children = array_values((array)$task->children);
|
||||
if($task->parent > 0) $task->parentPri = $this->dao->select('pri')->from(TABLE_TASK)->where('id')->eq($task->parent)->fetch('pri');
|
||||
|
||||
/* Set execution name */
|
||||
$task->executionName = $data->data->execution->name;
|
||||
|
||||
/* Set module title */
|
||||
$moduleTitle = '';
|
||||
if(empty($task->module)) $moduleTitle = '/';
|
||||
if($task->module)
|
||||
{
|
||||
$modulePath = $data->data->modulePath;
|
||||
foreach($modulePath as $key => $module)
|
||||
{
|
||||
$moduleTitle .= $module->name;
|
||||
if(isset($modulePath[$key + 1])) $moduleTitle .= '/';
|
||||
}
|
||||
}
|
||||
$task->moduleTitle = $moduleTitle;
|
||||
|
||||
$queryAccounts = array();
|
||||
if($task->assignedTo) $queryAccounts[$task->assignedTo] = $task->assignedTo;
|
||||
if(!empty($task->team))
|
||||
{
|
||||
foreach($task->team as $account => $team) $queryAccounts[$account] = $account;
|
||||
}
|
||||
$usersWithAvatar = $this->loadModel('user')->getListByAccounts($queryAccounts, 'account');
|
||||
|
||||
if(!empty($task->team))
|
||||
{
|
||||
$teams = array();
|
||||
foreach($task->team as $account => $team)
|
||||
{
|
||||
$user = zget($usersWithAvatar, $account, '');
|
||||
$team->realname = $user ? $user->realname : $account;
|
||||
$team->avatar = $user ? $user->avatar : '';
|
||||
$team->estimate = round($team->estimate, 1);
|
||||
$team->consumed = round($team->consumed, 1);
|
||||
$team->left = round($team->left, 1);
|
||||
|
||||
$allHours = $team->consumed + $team->left;
|
||||
$team->progress = empty($allHours) ? 0 : round($team->consumed / $allHours * 100, 1);
|
||||
|
||||
$teams[] = $team;
|
||||
}
|
||||
$task->team = $teams;
|
||||
}
|
||||
|
||||
$task->actions = $this->loadModel('action')->processActionForAPI($data->data->actions, $data->data->users, $this->lang->task);
|
||||
|
||||
$preAndNext = $data->data->preAndNext;
|
||||
$task->preAndNext = array();
|
||||
$task->preAndNext['pre'] = $preAndNext->pre ? $preAndNext->pre->id : '';
|
||||
$task->preAndNext['next'] = $preAndNext->next ? $preAndNext->next->id : '';
|
||||
|
||||
$execution = $this->loadModel('project')->getByID($task->execution, 'execution,sprint');
|
||||
$task->executionStatus = $execution->status;
|
||||
|
||||
return $this->send(200, $this->format($task, 'deadline:date,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,realStarted:time,finishedBy:user,finishedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,lastEditedBy:user,lastEditedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* PUT method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function put($taskID)
|
||||
{
|
||||
$oldTask = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
/* Set $_POST variables. */
|
||||
$fields = 'name,type,desc,assignedTo,pri,estimate,left,consumed,story,parent,execution,module,closedReason,status,estStarted,deadline,team,teamEstimate,teamConsumed,teamLeft,multiple,mailto,uid';
|
||||
$this->batchSetPost($fields, $oldTask);
|
||||
|
||||
$control = $this->loadController('task', 'edit');
|
||||
$control->edit($taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
$task = $this->task->getByID($taskID);
|
||||
return $this->send(200, $this->format($task, 'deadline:date,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,realStarted:time,finishedBy:user,finishedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,lastEditedBy:user,lastEditedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
|
||||
/**
|
||||
* DELETE method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function delete($taskID)
|
||||
{
|
||||
$control = $this->loadController('task', 'delete');
|
||||
$control->delete(0, $taskID, 'true');
|
||||
|
||||
$this->getData();
|
||||
return $this->sendSuccess(200, 'success');
|
||||
}
|
||||
}
|
38
api/v1/entries/taskactive.php
Normal file
38
api/v1/entries/taskactive.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?php
|
||||
/**
|
||||
* The task active entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
**/
|
||||
class taskActiveEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
$fields = 'assignedTo,left,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('task', 'activate');
|
||||
$control->activate($taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
return $this->send(200, $this->format($task, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
||||
|
41
api/v1/entries/taskassignto.php
Normal file
41
api/v1/entries/taskassignto.php
Normal file
@ -0,0 +1,41 @@
|
||||
<?php
|
||||
/**
|
||||
* The task assignto entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskAssignToEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
$fields = 'assignedTo,comment,left';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('task', 'assignTo');
|
||||
$this->requireFields('assignedTo');
|
||||
|
||||
$control->assignTo($task->execution, $taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
return $this->send(200, $this->format($task, 'openedDate:time,assignedDate:time,realStarted:time,finishedDate:time,canceledDate:time,closedDate:time,lastEditedDate:time'));
|
||||
}
|
||||
}
|
86
api/v1/entries/taskbatchcreate.php
Normal file
86
api/v1/entries/taskbatchcreate.php
Normal file
@ -0,0 +1,86 @@
|
||||
<?php
|
||||
/**
|
||||
* The task batch create entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskBatchCreateEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($executionID = 0)
|
||||
{
|
||||
if(!$executionID) $executionID = $this->param('execution', 0);
|
||||
if(!$executionID) return $this->send400('Need execution id.');
|
||||
|
||||
$storyID = $this->param('story', 0);
|
||||
$moduleID = $this->param('module', 0);
|
||||
$taskID = $this->param('task', 0);
|
||||
|
||||
if(!isset($this->requestBody->tasks))
|
||||
{
|
||||
return $this->send400('Need tasks.');
|
||||
}
|
||||
|
||||
$modules = array();
|
||||
$parents = array();
|
||||
$names = array();
|
||||
$colors = array();
|
||||
$types = array();
|
||||
$estimates = array();
|
||||
$estStarted = array();
|
||||
$deadlines = array();
|
||||
$desc = array();
|
||||
$pri = array();
|
||||
$stories = array();
|
||||
foreach($this->request('tasks') as $key => $task)
|
||||
{
|
||||
$number = $key + 1;
|
||||
if(!isset($task->name) or !isset($task->type)) return $this->send400('Task must have name and type.');
|
||||
|
||||
$modules[$number] = isset($task->module) ? $task->module : $moduleID;
|
||||
$parents[$number] = isset($task->parent) ? $task->parent : $taskID;
|
||||
$names[$number] = $task->name;
|
||||
$colors[$number] = isset($task->color) ? $task->color : '';
|
||||
$types[$number] = $task->type;
|
||||
$estimates[$number] = isset($task->estimate) ? $task->estimate : 0;
|
||||
$estStarted[$number] = isset($task->estStarted) ? $task->estStarted : 0;
|
||||
$deadlines[$number] = isset($task->deadline) ? $task->deadline : null;
|
||||
$desc[$number] = isset($task->desc) ? $task->desc : '';
|
||||
$pri[$number] = isset($task->pri) ? $task->pri : 0;
|
||||
$stories[$number] = isset($task->story) ? $task->story : $storyID;
|
||||
}
|
||||
$this->setPost('module', $modules);
|
||||
$this->setPost('parent', $parents);
|
||||
$this->setPost('name', $names);
|
||||
$this->setPost('color', $colors);
|
||||
$this->setPost('type', $types);
|
||||
$this->setPost('estimate', $estimates);
|
||||
$this->setPost('estStarted', $estStarted);
|
||||
$this->setPost('deadline', $deadlines);
|
||||
$this->setPost('desc', $desc);
|
||||
$this->setPost('pri', $pri);
|
||||
$this->setPost('story', $stories);
|
||||
|
||||
$control = $this->loadController('task', 'batchCreate');
|
||||
$control->batchCreate($executionID, $storyID, $moduleID, $taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
if(!$taskID) return $this->send(200, array());
|
||||
$task = $this->loadModel('task')->getById($taskID);
|
||||
return $this->send(200, array('task' => $task));
|
||||
}
|
||||
}
|
39
api/v1/entries/taskclose.php
Normal file
39
api/v1/entries/taskclose.php
Normal file
@ -0,0 +1,39 @@
|
||||
<?php
|
||||
/**
|
||||
* The task close entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskCloseEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
$fields = 'comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('task', 'close');
|
||||
$control->close($taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
return $this->send(200, $task);
|
||||
}
|
||||
}
|
45
api/v1/entries/taskcomponent.php
Normal file
45
api/v1/entries/taskcomponent.php
Normal file
@ -0,0 +1,45 @@
|
||||
<?php
|
||||
/**
|
||||
* The task component entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskComponentEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
$fields = 'name,color,type,assignedTo,parent,estimate,story,module,pri,desc,estStarted,deadline';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$fields = explode(',', $fields);
|
||||
foreach($fields as $field) $this->setArrayPost($field);
|
||||
$task = $this->loadModel('task')->getById($taskID);
|
||||
|
||||
$control = $this->loadController('task', 'batchCreate');
|
||||
$control->batchCreate($task->execution, 0, 0, $taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->task->getById($data->idList[0]);
|
||||
return $this->send(200, $this->format($task, 'deadline:date,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,realStarted:time,finishedBy:user,finishedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,lastEditedBy:user,lastEditedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
|
||||
public function setArrayPost($field)
|
||||
{
|
||||
$_POST[$field] = array('0' => $_POST[$field]);
|
||||
}
|
||||
}
|
47
api/v1/entries/taskfinish.php
Normal file
47
api/v1/entries/taskfinish.php
Normal file
@ -0,0 +1,47 @@
|
||||
<?php
|
||||
/**
|
||||
* The task finish entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskFinishEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
$fields = 'assignedTo,realStarted';
|
||||
$this->batchSetPost($fields, $task);
|
||||
|
||||
$fields = 'finishedDate,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$this->setPost('currentConsumed', $this->request('currentConsumed', 0));
|
||||
$this->setPost('consumed', $this->request('currentConsumed', 0) + $task->consumed);
|
||||
|
||||
$control = $this->loadController('task', 'finish');
|
||||
$this->requireFields('assignedTo,currentConsumed,realStarted,finishedDate');
|
||||
$control->finish($taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
return $this->send(200, $this->format($task, 'openedDate:time,assignedDate:time,realStarted:time,finishedDate:time,canceledDate:time,closedDate:time,lastEditedDate:time'));
|
||||
}
|
||||
}
|
39
api/v1/entries/taskpause.php
Normal file
39
api/v1/entries/taskpause.php
Normal file
@ -0,0 +1,39 @@
|
||||
<?php
|
||||
/**
|
||||
* The task pause entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskPauseEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
$fields = 'comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('task', 'pause');
|
||||
$control->pause($taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
return $this->send(200, $task);
|
||||
}
|
||||
}
|
76
api/v1/entries/taskrecordestimate.php
Normal file
76
api/v1/entries/taskrecordestimate.php
Normal file
@ -0,0 +1,76 @@
|
||||
<?php
|
||||
/**
|
||||
* The task recordEstimate entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskRecordEstimateEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($taskID)
|
||||
{
|
||||
$issetEffort = $this->loadModel('effort') ? true : false;
|
||||
if($issetEffort)
|
||||
{
|
||||
$control = $this->loadController('effort', 'createForObject');
|
||||
$control->createForObject('task', $taskID);
|
||||
}
|
||||
else
|
||||
{
|
||||
$control = $this->loadController('task', 'recordEstimate');
|
||||
$control->recordEstimate($taskID);
|
||||
}
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->error('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$effort = $data->data->efforts ? $data->data->efforts : new stdclass();
|
||||
return $this->send(200, array('effort' => $effort));
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
if($this->loadModel('effort'))
|
||||
{
|
||||
$fields = 'id,dates,consumed,left,objectType,objectID,work';
|
||||
$this->batchSetPost($fields);
|
||||
$control = $this->loadController('effort', 'createForObject');
|
||||
$control->createForObject('task', $taskID);
|
||||
}
|
||||
else
|
||||
{
|
||||
$fields = 'id,dates,consumed,left,work';
|
||||
$this->batchSetPost($fields);
|
||||
$control = $this->loadController('task', 'recordEstimate');
|
||||
$control->recordEstimate($taskID);
|
||||
}
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getById($taskID);
|
||||
|
||||
return $this->send(200, $this->format($task, 'deadline:date,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,realStarted:time,finishedBy:user,finishedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,lastEditedBy:user,lastEditedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
43
api/v1/entries/taskrestart.php
Normal file
43
api/v1/entries/taskrestart.php
Normal file
@ -0,0 +1,43 @@
|
||||
<?php
|
||||
/**
|
||||
* The task start entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2022 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Lu Fei <lufei@easycorp.ltd>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class taskRestartEntry extends entry
|
||||
{
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $taskID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($taskID)
|
||||
{
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
$fields = 'assignedTo,realStarted';
|
||||
$this->batchSetPost($fields, $task);
|
||||
|
||||
$fields = 'consumed,left,comment';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$control = $this->loadController('task', 'restart');
|
||||
$this->requireFields('consumed,left');
|
||||
$control->restart($taskID);
|
||||
|
||||
$data = $this->getData();
|
||||
if(!$data) return $this->send400('error');
|
||||
if(isset($data->result) and $data->result == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getByID($taskID);
|
||||
|
||||
return $this->send(200, $task);
|
||||
}
|
||||
}
|
115
api/v1/entries/tasks.php
Normal file
115
api/v1/entries/tasks.php
Normal file
@ -0,0 +1,115 @@
|
||||
<?php
|
||||
/**
|
||||
* The tasks entry point of ZenTaoPMS.
|
||||
*
|
||||
* @copyright Copyright 2009-2021 禅道软件(青岛)有限公司(ZenTao Software (Qingdao) Co., Ltd. www.cnezsoft.com)
|
||||
* @license ZPL(http://zpl.pub/page/zplv12.html) or AGPL(https://www.gnu.org/licenses/agpl-3.0.en.html)
|
||||
* @author Chunsheng Wang <chunsheng@cnezsoft.com>
|
||||
* @package entries
|
||||
* @version 1
|
||||
* @link http://www.zentao.net
|
||||
*/
|
||||
class tasksEntry extends entry
|
||||
{
|
||||
/**
|
||||
* GET method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function get($executionID = 0)
|
||||
{
|
||||
/* Get tasks by search, search arguments available: pri, assignedTo, status, id, name. Pager arguments will be utilized as well. */
|
||||
if($this->param('search', 0) == 1) // TODO: document this api.
|
||||
{
|
||||
$this->loadModel('task');
|
||||
$searchParams = array();
|
||||
foreach(array('pri' => 'priList', 'assignedTo' => 'assignedToList', 'status' => 'statusList', 'id' => 'idList', 'name' => 'taskName') as $field => $condName)
|
||||
{
|
||||
if($this->param($field, false))
|
||||
{
|
||||
$searchParams[$condName] = $this->param($field);
|
||||
continue;
|
||||
}
|
||||
if($this->param($condName, false)) $searchParams[$condName] = $this->param($condName);
|
||||
}
|
||||
|
||||
$this->app->loadClass('pager', $static = true);
|
||||
$pager = pager::init($this->param('total', 0), $this->param('limit', 20), $this->param('page', 1));
|
||||
$tasks = $this->task->getListByConds((object)$searchParams, $this->param('order', 'id_desc'), $pager);
|
||||
|
||||
$data = new stdclass();
|
||||
$data->status = 'success';
|
||||
$data->data = new stdclass();
|
||||
$data->data->tasks = array_values($tasks);
|
||||
$data->data->pager = (object)$pager;
|
||||
}
|
||||
elseif(!$executionID)
|
||||
{
|
||||
/* Get my tasks defaultly. */
|
||||
$control = $this->loadController('my', 'task');
|
||||
$control->task($this->param('type', 'assignedTo'), $this->param('order', 'id_desc'), $this->param('total', 0), $this->param('limit', 20), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Get tasks by execution. */
|
||||
$control = $this->loadController('execution', 'task');
|
||||
$control->task($executionID, $this->param('status', 'all'), 0, $this->param('order', 'id_desc'), 0, $this->param('limit', 100), $this->param('page', 1));
|
||||
$data = $this->getData();
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'success')
|
||||
{
|
||||
$tasks = $data->data->tasks;
|
||||
$pager = $data->data->pager;
|
||||
$result = array();
|
||||
foreach($tasks as $task)
|
||||
{
|
||||
if(isset($task->children)) $task->children = array_values((array)$task->children);
|
||||
$result[] = $this->format($task, 'deadline:date,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,realStarted:time,finishedBy:user,finishedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,lastEditedBy:user,lastEditedDate:time,deleted:bool,mailto:userList');
|
||||
}
|
||||
return $this->send(200, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'tasks' => $result));
|
||||
}
|
||||
|
||||
if(isset($data->status) and $data->status == 'fail') return $this->sendError(zget($data, 'code', 400), $data->message);
|
||||
return $this->sendError(400, 'error');
|
||||
}
|
||||
|
||||
/**
|
||||
* POST method.
|
||||
*
|
||||
* @param int $executionID
|
||||
* @access public
|
||||
* @return string
|
||||
*/
|
||||
public function post($executionID)
|
||||
{
|
||||
$fields = 'name,type,assignedTo,estimate,story,execution,project,module,pri,desc,estStarted,deadline,mailto,team,teamEstimate,multiple,uid';
|
||||
$this->batchSetPost($fields);
|
||||
|
||||
$assignedTo = $this->request('assignedTo');
|
||||
if($assignedTo and !is_array($assignedTo)) $this->setPost('assignedTo', array($assignedTo));
|
||||
if($this->request('multiple'))
|
||||
{
|
||||
if(count($this->request('team')) != count($this->request('teamEstimate'))) return $this->sendError(400, 'Arrays team and teamEstimate should be the same length');
|
||||
$this->setPost('mode', $this->request('mode', 'linear'));
|
||||
$this->setPost('teamSource', array_fill(0, count($this->request('team')), ''));
|
||||
}
|
||||
|
||||
$this->setPost('execution', $executionID);
|
||||
|
||||
$control = $this->loadController('task', 'create');
|
||||
$this->requireFields('name,assignedTo,type,estStarted,deadline');
|
||||
|
||||
$control->create($executionID, $this->request('storyID', 0), $this->request('moduleID', 0), $this->request('copyTaskID', 0), $this->request('copyTodoID', 0));
|
||||
|
||||
$data = $this->getData();
|
||||
if(!isset($data->id)) return $this->sendError(400, $data->message);
|
||||
|
||||
$task = $this->loadModel('task')->getByID($data->id);
|
||||
|
||||
return $this->send(201, $this->format($task, 'deadline:date,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,realStarted:time,finishedBy:user,finishedDate:time,closedBy:user,closedDate:time,canceledBy:user,canceledDate:time,lastEditedBy:user,lastEditedDate:time,deleted:bool,mailto:userList'));
|
||||
}
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user