463 lines
19 KiB
PHP
463 lines
19 KiB
PHP
<?php
|
||
|
||
namespace Application\Form\item;
|
||
|
||
use Application\Common\Enum;
|
||
use Application\Common\EventEnum;
|
||
use Application\Service\DB\AbstractDb;
|
||
use Application\Service\DB\Db;
|
||
use Application\Service\DB\Dictionary\FormField;
|
||
use Application\Service\DB\Dictionary\FormGroup;
|
||
use Application\Service\Extension\Event;
|
||
use Application\Service\Extension\Events\ItemFormEventHandler;
|
||
use Application\Service\Extension\Helper\ArrayHelper;
|
||
use Application\Service\Extension\Helper\SDMHelper;
|
||
use Application\Service\Extension\Helper\StringHelper;
|
||
use Application\Service\Extension\Laminas;
|
||
use Application\Service\Extension\Validator\ValidatorApplication;
|
||
use Laminas\Db\Sql\Predicate\In;
|
||
use Laminas\Db\Sql\Predicate\Operator;
|
||
use Laminas\Validator\Exception\InvalidArgumentException;
|
||
|
||
class FormForm extends \Application\Form\FormForm
|
||
{
|
||
public function __construct(ValidatorApplication $validator = null)
|
||
{
|
||
parent::__construct($validator);
|
||
Event::on(EventEnum::EVENT_AFTER_ITEM_FORM_CREATE, [ItemFormEventHandler::class, 'afterItemFormCreate']);
|
||
}
|
||
|
||
protected function getForm():AbstractDb
|
||
{
|
||
return Laminas::$serviceManager->itemForm;
|
||
}
|
||
|
||
protected function getFormField()
|
||
{
|
||
return Laminas::$serviceManager->itemFormField;
|
||
}
|
||
|
||
protected function getFormRadio()
|
||
{
|
||
return Laminas::$serviceManager->itemFormFieldRadio;
|
||
}
|
||
|
||
protected function getFormText()
|
||
{
|
||
return Laminas::$serviceManager->itemFormFieldText;
|
||
}
|
||
|
||
protected function getFormVersion()
|
||
{
|
||
return Laminas::$serviceManager->itemFormVersion;
|
||
}
|
||
|
||
/**
|
||
* 验证AE, SAE, 实验总结, 随机分组类是否已经创建了多个
|
||
* @param $value
|
||
* @return void|null
|
||
*/
|
||
public function invalidGroupId($value)
|
||
{
|
||
if (!in_array($value, [FormGroup::AE, FormGroup::SAE, FormGroup::RANDOM_GROUP])) {
|
||
return null;
|
||
}
|
||
|
||
if ($_POST['id']) {
|
||
$query = $this->getForm()->fetchOne([
|
||
'columns' => ['id'],
|
||
'where' => ['is_del' => 0, 'item_id' => $_POST['item_id'], 'group_id' => $value]
|
||
]);
|
||
|
||
if ($query['id'] != $_POST['id']) {
|
||
throw new InvalidArgumentException("此类型表单只能设置一个, 请勿重复添加");
|
||
}
|
||
} else {
|
||
if (
|
||
Laminas::$serviceManager->itemForm->fetchOne([
|
||
'where' => [
|
||
'item_id' => $_POST['item_id'],
|
||
'group_id' => $value,
|
||
'is_del' => 0
|
||
]
|
||
])
|
||
) {
|
||
throw new InvalidArgumentException("此类型表单只能设置一个, 请勿重复添加");
|
||
}
|
||
}
|
||
|
||
return null;
|
||
}
|
||
|
||
/**
|
||
* 验证字典项表单名称是否添加重复
|
||
* @param $value
|
||
* @return null
|
||
*/
|
||
public function invalidCreateName($value)
|
||
{
|
||
$request = Laminas::$app->getMvcEvent()->getRequest();
|
||
|
||
if ($value !== null) {
|
||
// 没 id 说明是新增, 有 id 是编辑
|
||
$id = $request->getPost('id');
|
||
|
||
// 新增
|
||
if (!$id) {
|
||
$query = $this->getForm()->fetchOne([
|
||
'columns' => ['id'],
|
||
'where' => ['name' => $request->getPost('name'), 'is_del' => 0, 'item_id' => $request->getPost('item_id')]
|
||
]);
|
||
|
||
if ($query) {
|
||
throw new InvalidArgumentException("表单名称 {$value} 已存在, 请勿重复添加。");
|
||
}
|
||
|
||
} else {
|
||
$query = $this->getForm()->fetchOne([
|
||
'columns' => ['id'],
|
||
'where' => ['name' => $request->getPost('name'), 'is_del' => 0, 'item_id' => $request->getPost('item_id')]
|
||
]);
|
||
|
||
if ($query && (count($query) > 1 || $query['id'] != $request->getPost('id'))) {
|
||
throw new InvalidArgumentException("表单名称 {$value} 已在其他表单中使用, 请勿重复添加[e-2]。");
|
||
}
|
||
}
|
||
}
|
||
|
||
return null;
|
||
}
|
||
|
||
/**
|
||
* 验证删除表单id
|
||
* @return null
|
||
*/
|
||
public function invalidDeleteId($val)
|
||
{
|
||
$request = Laminas::$app->getMvcEvent()->getRequest();
|
||
|
||
$formData = Laminas::$serviceManager->itemForm->fetchOne([
|
||
'where' => ['id' => $request->getPost('id')]
|
||
]);
|
||
|
||
if (Laminas::$serviceManager->patientFormContent->fetchOne(['where' => [
|
||
'item_id' => $formData['item_id'],
|
||
'form_id' => $formData['id'],
|
||
'is_del' => 0
|
||
]])) {
|
||
throw new InvalidArgumentException("当前表单已有受试者填写。无法进行删除操作。", 1001);
|
||
}
|
||
|
||
//查询一下该form下的字段ID
|
||
$form_fileids = Laminas::$serviceManager->itemFormField->fetchCol('id',['is_del' => 0,'form_id' => $formData['id']]);
|
||
$relation_where = ['form_id' => $formData['id'], 'is_del' => 0, new Operator('relation_form_id', Operator::OP_NE, 0)];
|
||
if(!empty($form_fileids)){
|
||
$relation_where[] = ['field_id'=> StringHelper::toArray($form_fileids)];
|
||
}
|
||
|
||
if (Laminas::$serviceManager->itemFormRelation->getCount($relation_where)) {
|
||
throw new InvalidArgumentException("当前表单下已有其他关联表单。无法进行删除操作。请解除关联关系。", 1001);
|
||
}
|
||
|
||
if (Laminas::$serviceManager->itemFormFieldRadio->getCount([new \Laminas\Db\Sql\Predicate\Expression("FIND_IN_SET('$val',relation_information)")])) {
|
||
throw new InvalidArgumentException("当前表单已被其他表单关联。无法进行删除操作。请解除关联关系。", 1001);
|
||
}
|
||
|
||
return null;
|
||
}
|
||
|
||
public function validVarName($val)
|
||
{
|
||
$request = Laminas::$app->getMvcEvent()->getRequest();
|
||
|
||
$originData = $this->getForm()->fetchOne([
|
||
'where' => ['id' => $request->getPost('id')]
|
||
]);
|
||
|
||
// 如果有受试者填写过数据, 有些数据不允许更改
|
||
if ($originData) {
|
||
if (Laminas::$serviceManager->itemForm->getIsPatientWrite($request->getPost('id'))) {
|
||
$labelMap = [
|
||
'type' => '类型',
|
||
'group_id' => '表单类型',
|
||
];
|
||
|
||
foreach ($labelMap as $field => $label) {
|
||
if ($originData[$field] != $request->getPost($field)) {
|
||
throw new \Application\Service\Exceptions\InvalidArgumentException("已有受试者数据。无法更改 `{$label}`");
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
|
||
if ($request->getPost('form_type') == FormField::FORM_CONFIG_RADIO && !$val) {
|
||
return null;
|
||
}
|
||
|
||
//检查点变量名规则
|
||
$isMatched = preg_match('/^[a-zA-Z_]([a-zA-Z0-9_]+)?$/', $val);
|
||
if (!$isMatched) {
|
||
throw new \Laminas\Validator\Exception\InvalidArgumentException("变量名必须以A-Z(不区分大小写)或下划线(_)开始,且不能包括空格和特殊符号。", 1001);
|
||
}
|
||
if (strlen($val) > 32) {
|
||
throw new \Application\Service\Exceptions\InvalidArgumentException("不能超过32个字符", 1001);
|
||
}
|
||
|
||
// 验证变量名不能重复
|
||
// 【新系统】变量名,新加不可重复的控制 --李总,白老师
|
||
//https://e.gitee.com/yikeen_project/dashboard?issue=I72KSD
|
||
// 没 id 说明是新增, 有 id 是编辑
|
||
$where = ['item_id' => $request->getPost('item_id'), 'var_name' => $val, 'is_del' => 0];
|
||
$condition = $request->getPost('id') ? [new Operator('id', Operator::OP_NE, $request->getPost('id'))] : null;
|
||
if ($condition !== null) {
|
||
$where = ArrayHelper::merge($where, $condition);
|
||
}
|
||
$data = $this->getForm()->fetchAll([
|
||
'columns' => ['var_name', 'id', 'name'],
|
||
'where' => $where
|
||
]);
|
||
|
||
// 新增
|
||
if ($request->getPost('id')) {
|
||
if (count($data) > 1) {
|
||
throw new InvalidArgumentException("变量名 `{$val}` 已与 `{$data['name']}` 中的变量名重复, 请勿重复添加。", 1001);
|
||
}
|
||
|
||
$data = current($data);
|
||
if ($data && $data['id'] != $request->getPost('id')) {
|
||
throw new InvalidArgumentException("变量名 `{$val}` 已与 `{$data['name']}` 中的变量名重复, 请勿重复添加。", 1001);
|
||
}
|
||
$c = 1;
|
||
} else {
|
||
$c = 0;
|
||
}
|
||
|
||
if ($data && (count($data) > $c || current(ArrayHelper::getColumn($data, 'var_name')) != $request->getPost('var_name'))) {
|
||
$formName = current($data)['name'];
|
||
throw new InvalidArgumentException("变量名 `{$val}` 已与 `{$formName}` 中的变量名重复, 请勿重复添加。", 1001);
|
||
}
|
||
|
||
return null;
|
||
}
|
||
|
||
public function validGcoPool($value)
|
||
{
|
||
// 编辑
|
||
if ($_POST['id']) {
|
||
$isWrite = Laminas::$serviceManager->patientForm->fetchAll([
|
||
'columns' => ['id'],
|
||
'where' => [
|
||
'form_id' => ArrayHelper::getColumn(SDMHelper::app()->form->getGcoGroupForm($_POST['id']), 'id'),
|
||
'is_del' => 0
|
||
]
|
||
]);
|
||
|
||
// 没产生数据随便编辑。
|
||
if (!$isWrite) {
|
||
return;
|
||
}
|
||
|
||
$originGcoPool = SDMHelper::app()->form->getGcoPool($_POST['id']);
|
||
|
||
$currentGcoPool = $value;
|
||
|
||
if ($originGcoPool != $currentGcoPool) {
|
||
throw new InvalidArgumentException("已产生数据的表单, 识别分组无法更改。");
|
||
}
|
||
}
|
||
|
||
return ;
|
||
}
|
||
|
||
/**
|
||
* 进度管理
|
||
* 创建项目表单
|
||
* @return int
|
||
*/
|
||
public function createForm(): int
|
||
{
|
||
$this->event = EventEnum::EVENT_DICTIONARY_FORM_CREATE;
|
||
|
||
Db::beginTransaction();
|
||
|
||
// 实验总结类默认勾选所有隶属实验总结类检查点
|
||
if ($this->validator->attributes['group_id'] == FormGroup::TEST_SUMMARY) {
|
||
$this->validator->attributes['ds_stage'] = FormGroup::DS_STAGE;
|
||
}
|
||
|
||
$formId = Laminas::$serviceManager->itemForm->insert([
|
||
'name' => $this->validator->attributes['name'],
|
||
'type' => $this->validator->attributes['type'],
|
||
'item_id' => $this->validator->attributes['item_id'],
|
||
'is_patient' => ($this->validator->attributes['is_patient'] ?? '') ?: '',
|
||
'finish_condition' => $this->validator->attributes['finish_condition'],
|
||
'is_required' => $this->validator->attributes['is_required'],
|
||
'checklist_id' => $this->validator->attributes['checklist_id'],
|
||
'create_user_id' => Laminas::$serviceManager->identity->getId(),
|
||
'order' => $this->validator->attributes['order'],
|
||
'group_id' => $this->validator->attributes['group_id'],
|
||
'show_type' => $this->validator->attributes['show_type'],
|
||
'reference_file' => $this->validator->attributes['reference_file'],
|
||
'rdg_type' => $this->validator->attributes['rdg_type'] ?? 0,
|
||
'var_name' => $this->validator->attributes['var_name'] ?: '',
|
||
'expression' => $this->validator->attributes['expression'] ?: '',
|
||
'code' => $this->validator->attributes['code'] ?? '',
|
||
'except_checktime' => $this->getExceptCheckTime(),
|
||
'is_handwritten_signature' => $this->validator->attributes['can_patient_write'] ?? 0,
|
||
'ds_stage' => $this->validator->attributes['ds_stage'] ?? 1,
|
||
'guide' => $this->validator->attributes['guide'] ?? '',
|
||
'is_using_score' => $this->validator->attributes['is_using_score'] ?? 0,
|
||
'is_through_process_do' => $this->validator->attributes['is_through_process_do'] ?? 0,
|
||
'info_collect_type' => $this->validator->attributes['info_collect_type'] ?? 0,
|
||
'gco_pool' => $this->validator->attributes['gco_pool'] ?? '',
|
||
'is_patient_general_info' => $this->validator->attributes['is_patient_general_info'] ?? '',
|
||
'identification_edit' => ArrayHelper::getValue($this->validator->attributes, 'identification_edit', 0),
|
||
'is_export' => ArrayHelper::getValue($this->validator->attributes, 'is_export', 0),
|
||
'is_more_sdv' => ArrayHelper::getValue($this->validator->attributes, 'is_more_sdv', 0)
|
||
]);
|
||
|
||
// 添加随机分组字段
|
||
$this->initRandomGroupField($formId, $this->validator->attributes['rdg_type'] ?? 0);
|
||
|
||
if ($this->validator->attributes['checklist_id'] || $this->validator->attributes['group_id'] == FormGroup::CHECK_DO) {
|
||
$this->initCheckListField($formId);
|
||
}
|
||
|
||
// 医嘱识别
|
||
if ($this->validator->attributes['group_id'] == FormGroup::THROUGH_PROCESS && $this->validator->attributes['is_through_process_do'] == 1) {
|
||
if ($this->validator->attributes['type'] == 0) {
|
||
throw new \Application\Service\Exceptions\InvalidArgumentException('识别医嘱的类型不能为一对一');
|
||
}
|
||
// 初始化贯穿全程识别医嘱表单字段
|
||
$this->initThroughProcessDoField($formId);
|
||
}
|
||
|
||
Event::trigger(EventEnum::EVENT_AFTER_ITEM_FORM_CREATE, [$this]);
|
||
|
||
Db::commit();
|
||
|
||
return $formId;
|
||
}
|
||
|
||
/**
|
||
* 获取未选中的检查点
|
||
* 前端提交过来的是选中的检查点, 需要处理一下
|
||
* @return string
|
||
*/
|
||
private function getExceptCheckTime(): string
|
||
{
|
||
if (!isset($this->validator->attributes['except_checktime'])) {
|
||
return '';
|
||
}
|
||
|
||
$allCheckTime = Laminas::$serviceManager->itemChecktime->fetchAll([
|
||
'columns' => ['id'],
|
||
'where' => ['item_id' => $this->validator->attributes['item_id']]
|
||
]);
|
||
|
||
$exceptCheckTime = explode(',', $this->validator->attributes['except_checktime']);
|
||
|
||
if (!$exceptCheckTime) {
|
||
return '';
|
||
}
|
||
|
||
foreach ($allCheckTime as $key => $item) {
|
||
if (in_array($item['id'], $exceptCheckTime)) {
|
||
unset($allCheckTime[$key]);
|
||
}
|
||
}
|
||
|
||
return implode(',', array_values(ArrayHelper::getColumn($allCheckTime, 'id')));
|
||
}
|
||
|
||
/**
|
||
* 编辑项目表单
|
||
* @return array
|
||
* @throws \Exception
|
||
*/
|
||
public function editForm()
|
||
{
|
||
Db::beginTransaction();
|
||
|
||
// 随机分组处理
|
||
$rdgType = $this->validator->attributes['rdg_type'] ?? 0;
|
||
|
||
$originData = Laminas::$serviceManager->itemForm->fetchOne([
|
||
'where' => ['id' => $this->validator->attributes['id']]
|
||
]);
|
||
|
||
// 随机分组类型 1:手动新增;2:系统随机获取;
|
||
$originRdgType = $originData['rdg_type'] ?: 0;
|
||
$itemId = $originData['item_id'] ?: 0;
|
||
|
||
// 修改了随机分组随机号分配类型, 就去处理一些东西
|
||
if ($originRdgType && $originRdgType != $rdgType) {
|
||
if ($rdgType == 1) {
|
||
Laminas::$serviceManager->patient->delGroupAndNumber($itemId,1); // 0手改自,1自改手
|
||
} elseif ($rdgType == 2) {
|
||
Laminas::$serviceManager->patient->delGroupAndNumber($itemId,0); // 0手改自,1自改手
|
||
}
|
||
}
|
||
|
||
Laminas::$serviceManager->itemForm->save([
|
||
'id' => $this->validator->attributes['id'],
|
||
'name' => $this->validator->attributes['name'],
|
||
'type' => $this->validator->attributes['type'],
|
||
'is_patient' => $this->validator->attributes['is_patient'],
|
||
'finish_condition' => $this->validator->attributes['finish_condition'],
|
||
'is_required' => $this->validator->attributes['is_required'],
|
||
'checklist_id' => $this->validator->attributes['checklist_id'],
|
||
'order' => $this->validator->attributes['order'],
|
||
'group_id' => $this->validator->attributes['group_id'],
|
||
'show_type' => $this->validator->attributes['show_type'],
|
||
'reference_file' => $this->validator->attributes['reference_file'],
|
||
'rdg_type' => $rdgType,
|
||
'expression' => $this->validator->attributes['expression'] ?: '',
|
||
'var_name' => $this->validator->attributes['var_name'] ?: '',
|
||
'can_patient_write' => $this->validator->attributes['can_patient_write'] ?: 0,
|
||
'except_checktime' => $this->getExceptCheckTime(),
|
||
'is_handwritten_signature' => $this->validator->attributes['is_handwritten_signature'] ?? 0,
|
||
'ds_stage' => $this->validator->attributes['ds_stage'] ?: 1,
|
||
'guide' => $this->validator->attributes['guide'] ?: '',
|
||
'is_using_score' => $this->validator->attributes['is_using_score'] ?: 0,
|
||
'info_collect_type' => call_user_func(function () {
|
||
$r = $this->validator->attributes['info_collect_type'] ?: 0;
|
||
Laminas::$serviceManager->patientFormContentImg->isSetInfo(false)->update(['info_collect_type' => $r], ['form_id' => $this->validator->attributes['id']]);
|
||
return $r;
|
||
}),
|
||
'gco_pool' => $this->validator->attributes['gco_pool'] ?? '',
|
||
'is_patient_general_info' => $this->validator->attributes['is_patient_general_info'] ?? '',
|
||
'identification_edit' => ArrayHelper::getValue($this->validator->attributes, 'identification_edit', 0),
|
||
'is_export' => ArrayHelper::getValue($this->validator->attributes, 'is_export', 0),
|
||
'is_more_sdv' => ArrayHelper::getValue($this->validator->attributes, 'is_more_sdv', 0)
|
||
]);
|
||
|
||
$randomGroupId = Laminas::$serviceManager->itemFormField->fetchOne([
|
||
'where' => [
|
||
'var_name' => ['RANGC', 'RANGCA'],
|
||
'form_id' => $this->validator->attributes['id']
|
||
]
|
||
]);
|
||
|
||
// 如果当前表单是随机分组表单, 变更了随机分组类型, 需要同步修改生成出来的随即表单的变量和随机分组(研究分组)展示方式。
|
||
// 手写是单选, 系统分配是下拉框。
|
||
if ($randomGroupId) {
|
||
$type = $rdgType == 1 ? Enum::FORM_FIELD_TYPE_RADIO : Enum::FORM_FIELD_TYPE_DROPDOWN;
|
||
$varName = $rdgType == 1 ? 'RANGC' : 'RANGCA';
|
||
Laminas::$serviceManager->itemFormField->update([
|
||
'type' => $type,
|
||
'var_name' => $varName
|
||
], ['id' => $randomGroupId['id']]);
|
||
|
||
Laminas::$serviceManager->itemFormFieldText->update([
|
||
'var_name' => $varName
|
||
], ['field_id' => $randomGroupId['id']]);
|
||
}
|
||
|
||
Laminas::$serviceManager->itemFormVersion->generate($this->validator->attributes['id']);
|
||
|
||
Db::commit();
|
||
return [];
|
||
}
|
||
} |