From 74122885f17756e2522b46bff05ba872703ce003 Mon Sep 17 00:00:00 2001 From: wolfcode <37436228+wolf-leo@users.noreply.github.com> Date: Mon, 7 Apr 2025 13:44:12 +0800 Subject: [PATCH] =?UTF-8?q?feat(mall):=20=E6=96=B0=E5=A2=9E=E5=9B=9E?= =?UTF-8?q?=E6=94=B6=E7=AB=99=E5=8A=9F=E8=83=BD=20add=20recycle=20function?= =?UTF-8?q?ality=20for=20goods?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Add recycle feature to goods management - Implement recycle button in toolbar - Create recycle page for deleted goods - Add functionality to restore or permanently delete goods --- app/admin/controller/mall/Goods.php | 31 ++++++++ app/admin/view/mall/goods/index.html | 1 + app/admin/view/mall/goods/recycle.html | 11 +++ public/static/admin/js/mall/goods.js | 75 +++++++++++++++++++- public/static/plugs/easy-admin/easy-admin.js | 4 ++ 5 files changed, 121 insertions(+), 1 deletion(-) create mode 100644 app/admin/view/mall/goods/recycle.html diff --git a/app/admin/controller/mall/Goods.php b/app/admin/controller/mall/Goods.php index e17de04..8d20823 100644 --- a/app/admin/controller/mall/Goods.php +++ b/app/admin/controller/mall/Goods.php @@ -132,4 +132,35 @@ EOF; $this->success('success', compact('choices')); } + #[NodeAnnotation(title: '回收站', auth: true)] + public function recycle(Request $request): Json|string + { + if (!$request->isAjax()) { + return $this->fetch(); + } + $id = $request->param('id', []); + $type = $request->param('type', ''); + switch ($type) { + case 'restore': + self::$model::withTrashed()->whereIn('id', $id)->update(['delete_time' => null, 'update_time' => time()]); + $this->success('success'); + break; + case 'delete': + self::$model::destroy($id, true); + $this->success('success'); + break; + default: + list($page, $limit, $where) = $this->buildTableParams(); + $count = self::$model::withTrashed()->whereNotNull('delete_time')->count(); + $list = self::$model::withTrashed()->with(['cate'])->where($where)->page($page, $limit)->order($this->sort)->whereNotNull('delete_time')->select()->toArray(); + $data = [ + 'code' => 0, + 'msg' => '', + 'count' => $count, + 'data' => $list, + ]; + return json($data); + } + + } } \ No newline at end of file diff --git a/app/admin/view/mall/goods/index.html b/app/admin/view/mall/goods/index.html index 5016922..fe02941 100644 --- a/app/admin/view/mall/goods/index.html +++ b/app/admin/view/mall/goods/index.html @@ -5,6 +5,7 @@ data-auth-edit="{:auth('mall.goods/edit')}" data-auth-delete="{:auth('mall.goods/delete')}" data-auth-stock="{:auth('mall.goods/stock')}" + data-auth-recycle="{:auth('mall.goods/recycle')}" lay-filter="currentTable"> diff --git a/app/admin/view/mall/goods/recycle.html b/app/admin/view/mall/goods/recycle.html new file mode 100644 index 0000000..29b8573 --- /dev/null +++ b/app/admin/view/mall/goods/recycle.html @@ -0,0 +1,11 @@ +
+
+ +
+
+
+ \ No newline at end of file diff --git a/public/static/admin/js/mall/goods.js b/public/static/admin/js/mall/goods.js index 433752f..eb41ef0 100644 --- a/public/static/admin/js/mall/goods.js +++ b/public/static/admin/js/mall/goods.js @@ -10,6 +10,7 @@ define(["jquery", "easy-admin"], function ($, ea) { export_url: 'mall.goods/export', modify_url: 'mall.goods/modify', stock_url: 'mall.goods/stock', + recycle_url: 'mall.goods/recycle', }; return { @@ -27,7 +28,7 @@ define(["jquery", "easy-admin"], function ($, ea) { icon: 'fa fa-plus ', extend: 'data-width="90%" data-height="95%"', }], - 'delete', 'export'], + 'delete', 'export', 'recycle'], cols: [[ {type: "checkbox"}, {field: 'id', width: 80, title: 'ID', searchOp: '='}, @@ -107,6 +108,78 @@ define(["jquery", "easy-admin"], function ($, ea) { stock: function () { ea.listen(); }, + recycle: function () { + init.index_url = init.recycle_url; + ea.table.render({ + init: init, + toolbar: ['refresh', + [{ + class: 'layui-btn layui-btn-sm', + method: 'get', + field: 'id', + icon: 'fa fa-refresh', + text: '全部恢复', + title: '确定恢复?', + auth: 'recycle', + url: init.recycle_url + '?type=restore', + checkbox: true + }, { + class: 'layui-btn layui-btn-danger layui-btn-sm', + method: 'get', + field: 'id', + icon: 'fa fa-delete', + text: '彻底删除', + title: '确定彻底删除?', + auth: 'recycle', + url: init.recycle_url + '?type=delete', + checkbox: true + }], 'export', + ], + cols: [[ + {type: "checkbox"}, + {field: 'id', width: 80, title: 'ID', searchOp: '='}, + {field: 'sort', width: 80, title: '排序', edit: 'text'}, + {field: 'cate_id', minWidth: 80, title: '商品分类', search: 'select', selectList: cateSelects, laySearch: true}, + {field: 'title', minWidth: 80, title: '商品名称'}, + {field: 'logo', minWidth: 80, title: '分类图片', search: false, templet: ea.table.image}, + {field: 'status', title: '状态', width: 85, selectList: {0: '禁用', 1: '启用'}}, + // 演示多选,实际数据库并无 status2 字段,搜索后会报错 + { + field: 'status2', title: '演示多选', width: 105, search: 'xmSelect', selectList: {1: '模拟选项1', 2: '模拟选项2', 3: '模拟选项3', 4: '模拟选项4', 5: '模拟选项5'}, + searchOp: 'in', templet: function (res) { + // 根据自己实际项目进行输出 + return res?.status2 || '模拟数据' + } + }, + {field: 'create_time', minWidth: 80, title: '创建时间', search: 'range'}, + {field: 'delete_time', minWidth: 80, title: '删除时间', search: 'range'}, + { + width: 250, + title: '操作', + templet: ea.table.tool, + operat: [ + [{ + title: '确认恢复?', + text: '恢复数据', + filed: 'id', + url: init.recycle_url + '?type=restore', + method: 'get', + auth: 'recycle', + class: 'layui-btn layui-btn-xs layui-btn-success', + }, { + title: '想好了吗?', + text: '彻底删除', + filed: 'id', + method: 'get', + url: init.recycle_url + '?type=delete', + auth: 'recycle', + class: 'layui-btn layui-btn-xs layui-btn-normal layui-bg-red', + }]] + } + ]], + }); + ea.listen(); + }, }; function aiOptimization(data) { diff --git a/public/static/plugs/easy-admin/easy-admin.js b/public/static/plugs/easy-admin/easy-admin.js index 91cfbf5..567df8a 100644 --- a/public/static/plugs/easy-admin/easy-admin.js +++ b/public/static/plugs/easy-admin/easy-admin.js @@ -312,6 +312,10 @@ define(["jquery", "tableSelect", "miniTheme", "xmSelect", "lazyload"], function if (admin.checkAuth('export', elem)) { toolbarHtml += '\n'; } + } else if (v === 'recycle') { + if (admin.checkAuth('recycle', elem)) { + toolbarHtml += '\n'; + } } else if (typeof v === "object") { $.each(v, function (ii, vv) { vv.class = vv.class || '';