工单沟通记录

This commit is contained in:
2025-07-03 15:28:19 +08:00
parent 78447737ea
commit 8d36ffe13b
9 changed files with 300 additions and 1 deletions
@@ -0,0 +1,46 @@
<?php
namespace app\ticket\controller;
use app\ticket\service\ConversationService;
use support\Request;
class ConversationController extends BaseController
{
public function index(Request $request)
{
try {
$ticket_id = $request->input('ticket_id');
if(empty($ticket_id)){
return $this->error('ticket_id不能为空');
}
$result = (new ConversationService())->list($request->all());
return $this->success($this->page($result));
} catch (\Throwable $e) {
return $this->error($e->getMessage().$e->getLine().$e->getFile());
}
}
public function add(Request $request)
{
try {
$request->setPost('user_id', 1);
return (new ConversationService())->add($request->all())
? $this->success()
: $this->error();
} catch (\Throwable $th) {
return $this->error($th->getMessage().' '.$th->getLine().' '.$th->getFile());
}
}
public function edit(Request $request)
{
try {
$request->setPost('user_id', 1);
$result = (new ConversationService())->edit($request->all());
return $result
? $this->success($result)
: $this->error();
} catch (\Throwable $th) {
return $this->error($th->getMessage().' '.$th->getLine().' '.$th->getFile());
}
}
}
+24 -1
View File
@@ -39,7 +39,30 @@ class TicketController extends BaseController
? $this->success($result)
: $this->error();
} catch (\Throwable $th) {
return $this->error($th->getMessage().' '.$th->getLine().' '.$th->getFile());
return $this->error($th->getMessage());
}
}
public function status(Request $request)
{
try {
$request->setPost('user_id', 1);
$result = (new TicketService())->status($request->all());
return $result
? $this->success($result)
: $this->error();
} catch (\Throwable $th) {
return $this->error($th->getMessage());
}
}
public function getStatus(Request $request)
{
try {
$result = (new TicketService())->getStatus($request->all());
return $result
? $this->success($result)
: $this->error();
} catch (\Throwable $th) {
return $this->error($th->getMessage());
}
}
+46
View File
@@ -0,0 +1,46 @@
<?php
namespace app\ticket\logic;
use app\ticket\model\Conversation;
use support\Log;
use support\exception\BusinessException;
class ConversationLogic
{
public function list($params)
{
$where = [];
if (!empty($params['ticket_id'])) {
$where['ticket_id'] = $params['ticket_id'];
}
$size = $params['size'] ?? 10;
$current = $params['current'] ?? 1;
return Conversation::where($where)->paginate($size, ['*'], 'page', $current);
}
public function add(array $data)
{
try {
return Conversation::create($data);
} catch (\Throwable $e) {
Log::error('会话创建失败', [
'data' => $data,
'error' => $e->getMessage()
]);
throw new BusinessException('会话创建失败,请稍后重试', 500);
}
}
public function edit(array $data)
{
try {
$conversation = Conversation::updateOrCreate(['id' => $data['id']], $data);
return $conversation;
} catch (\Throwable $e) {
Log::error('会话编辑失败', [
'data' => $data,
'error' => $e->getMessage()
]);
throw new BusinessException($e->getMessage().'会话编辑失败,请稍后重试', 500);
}
}
}
+6
View File
@@ -50,6 +50,12 @@ class TicketLogic
}
}
public function find(int $id)
{
$ticket = Ticket::find($id);
return $ticket;
}
public static function generateSimpleTicketNo(): string
{
$date = date('Ymd'); // 日期
+33
View File
@@ -0,0 +1,33 @@
<?php
namespace app\ticket\model;
use support\Model;
/**
* ticket_conversation 工单会话表
* @property integer $id 主键
* @property integer $ticket_id 工单ID
* @property integer $user_id 用户ID
* @property string $content 会话内容
* @property string $created_at 创建时间
* @property string $updated_at 更新时间
*/
class Conversation extends Model
{
protected $connection = 'mysql';
protected $table = 'ticket_conversation';
protected $primaryKey = 'id';
public $timestamps = true;
protected $dateFormat = 'U';
protected $dates = ['created_at', 'updated_at'];
protected $casts = [
'updated_at' => 'datetime:Y-m-d H:i:s',
'created_at' => 'datetime:Y-m-d H:i:s',
];
protected $fillable = [
'ticket_id',
'user_id',
'content',
];
}
@@ -0,0 +1,50 @@
<?php
namespace app\ticket\service;
use app\ticket\logic\ConversationLogic;
use config\constants\Constants;
use support\Db;
use support\exception\BusinessException;
class ConversationService
{
public function list($params)
{
// $locale = locale();
$locale = 'zh';
$ticket_status = $locale == 'zh'? Constants::TICKET_STATUS_ZH:Constants::TICKET_STATUS_EN;
// $ticket_status = Constants::TICKET_STATUS_ZH;
// $params['locale'] = locale();
$result = (new ConversationLogic())->list($params);
$status_fanyi = array_map(fn($v) => "{{{$v}}}", array_flip(Constants::TICKET_STATUS));
foreach ($result as $key => $value) {
$result[$key]['content'] = str_replace($status_fanyi,$ticket_status,$value['content']);
}
return $result;
}
public function add(array $data)
{
try {
return (new ConversationLogic())->add($data);
} catch (\Throwable $e) {
Db::rollback();
throw $e;
}
}
public function edit(array $data)
{
try {
Db::beginTransaction();
$result = (new ConversationLogic())->edit($data);
Db::commit();
return $result;
} catch (\Throwable $e) {
Db::rollback();
throw $e;
}
}
}
+48
View File
@@ -3,14 +3,17 @@
namespace app\ticket\service;
use app\ticket\logic\AttachmentLogic;
use app\ticket\logic\ConversationLogic;
use app\ticket\logic\TicketLogic;
use app\ticket\model\Ticket;
use config\constants\Constants;
use support\Db;
use support\exception\BusinessException;
use support\Log;
class TicketService
{
public function list($params)
{
$res = (new TicketLogic())->list($params);
@@ -51,4 +54,49 @@ class TicketService
throw $e;
}
}
public function status(array $data)
{
try {
Db::beginTransaction();
$msg = $data['msg']??[];
$ticket = (new TicketLogic())->find($data['id']);
if(empty($ticket)){
throw new BusinessException('工单不存在');
}
if($data['status'] == $ticket->status){
throw new BusinessException('状态未修改');
}
// if(!in_array($ticket->status, [Constants::TICKET_STATUS['PENDING'], Constants::TICKET_STATUS['CONFIRM']])
// && empty($msg)){
// throw new BusinessException('提交失败');
// }
$ticket->status = $data['status'];
$result = $ticket->save();
if(!empty($msg)){
$conversation = [
'ticket_id' => $ticket->id,
'user_id' => $data['user_id'],
'content' => '状态更新为{{'.array_search($data['status'],Constants::TICKET_STATUS).'}}:'.$msg
];
$res = (new ConversationLogic())->add($conversation);
}
Db::commit();
return $result;
} catch (\Throwable $e) {
Db::rollback();
throw $e;
}
}
public function getStatus(array $data)
{
$locale = locale();
$ticket_status = $locale == 'zh'? Constants::TICKET_STATUS_ZH:Constants::TICKET_STATUS_EN;
return $ticket_status;
}
}
+37
View File
@@ -0,0 +1,37 @@
<?php
namespace config\constants;
class Constants
{
//工单状态
public const TICKET_STATUS = [
'PENDING' => 1, // 待受理
'PROCESS' => 2, //处理中
'CONFIRM' => 3, // 待确认
'FINISH' => 4, // 已完成
'REJECTED' => 5, // 已驳回
];
public const TICKET_STATUS_ZH = [
self::TICKET_STATUS['PENDING'] => '待受理',
self::TICKET_STATUS['PROCESS'] => '处理中',
self::TICKET_STATUS['CONFIRM'] => '待确认',
self::TICKET_STATUS['FINISH'] => '已完成',
self::TICKET_STATUS['REJECTED'] => '已驳回',
];
public const TICKET_STATUS_EN = [
self::TICKET_STATUS['PENDING'] => 'Pending acceptance',
self::TICKET_STATUS['PROCESS'] => 'Processing',
self::TICKET_STATUS['CONFIRM'] => 'To be confirmed',
self::TICKET_STATUS['FINISH'] => 'Completed',
self::TICKET_STATUS['REJECTED'] => 'Rejected',
];
public const TICKET_STATUS_RU = [
self::TICKET_STATUS['PENDING'] => 'Подлежит рассмотрению',
self::TICKET_STATUS['PROCESS'] => 'В процессе обработки',
self::TICKET_STATUS['CONFIRM'] => 'Подлежит подтверждению',
self::TICKET_STATUS['FINISH'] => 'Завершено',
self::TICKET_STATUS['REJECTED'] => 'Отклонено',
];
}
+10
View File
@@ -35,9 +35,19 @@ Route::group('/common', function () {
Route::group('/ticket', function () {
//工单
Route::any('/ticket/add', [app\ticket\controller\TicketController::class, 'add']);
Route::any('/ticket/edit', [app\ticket\controller\TicketController::class, 'edit']);
Route::any('/ticket/list', [app\ticket\controller\TicketController::class, 'index']);
Route::any('/ticket/status', [app\ticket\controller\TicketController::class, 'status']);
Route::any('/ticket/getStatus', [app\ticket\controller\TicketController::class, 'getStatus']);
Route::any('/upload', [app\common\controller\UploadController::class, 'uploadFile']);
//工单沟通记录
Route::any('/conversation/add', [app\ticket\controller\ConversationController::class, 'add']);
Route::any('/conversation/edit', [app\ticket\controller\ConversationController::class, 'edit']);
Route::any('/conversation/list', [app\ticket\controller\ConversationController::class, 'index']);
});