diff --git a/inventory-backend/app/api/v1/inbound/stock.py b/inventory-backend/app/api/v1/inbound/stock.py index 4608b5e..8e38ba4 100644 --- a/inventory-backend/app/api/v1/inbound/stock.py +++ b/inventory-backend/app/api/v1/inbound/stock.py @@ -125,24 +125,14 @@ def get_all_stock(): def get_drafts(): """ 获取当前用户的盘点进度 - 支持过滤: session_id, is_finished, is_processed + 支持过滤: session_id """ - # user_id 现在由 Token 解析,忽略前端传来的参数以避免类型错误 session_id = request.args.get('session_id') - is_finished_str = request.args.get('is_finished') - is_processed_str = request.args.get('is_processed') query = StocktakeDraft.query if session_id: query = query.filter_by(session_id=session_id) - # ★ 修复:必须将字符串转换为 Python 布尔值 - if is_finished_str is not None: - is_finished_bool = is_finished_str.lower() in ('true', '1', 'yes') - query = query.filter_by(is_finished=is_finished_bool) - if is_processed_str is not None: - is_processed_bool = is_processed_str.lower() in ('true', '1', 'yes') - query = query.filter_by(is_processed=is_processed_bool) drafts = query.order_by(StocktakeDraft.scan_time.desc()).all() return jsonify([d.to_dict() for d in drafts]), 200 @@ -197,9 +187,7 @@ def add_draft(): stock_qty=stock_qty, diff_qty=quantity - stock_qty, source_table=source_table, - stock_id=stock_id, - is_finished=False, - is_processed=False + stock_id=stock_id ) db.session.add(draft) @@ -220,21 +208,17 @@ def add_draft(): def clear_draft(): """ 清除盘点草稿 - 支持清除指定 session_id 的记录,或清除所有未完成的记录 + 支持清除指定 session_id 的记录,或清除所有记录 """ data = request.json - user_id = _normalize_user_id(data.get('user_id', 'admin')) session_id = data.get('session_id') try: - query = StocktakeDraft.query.filter_by(user_id=user_id) + query = StocktakeDraft.query if session_id: # 清除指定会话 query = query.filter_by(session_id=session_id) - else: - # 默认只清除未完成的记录 - query = query.filter_by(is_finished=False) count = query.delete() db.session.commit() @@ -250,28 +234,20 @@ def clear_draft(): def start_new_session(): """ 开始新一轮盘点 - 1. 先清除用户所有未处理的旧盘点数据 - 2. 返回新的 session_id + 清空整张草稿表,返回新的 session_id """ - data = request.json - user_id = _normalize_user_id(data.get('user_id', 'admin')) - try: - # 清除旧的未处理盘点数据 - old_count = StocktakeDraft.query.filter_by( - user_id=user_id, - is_processed=False - ).delete() - + # 清空整张草稿表 + deleted_count = StocktakeDraft.query.delete() db.session.commit() # 生成新的 session_id new_session_id = f"STK-{datetime.now().strftime('%Y%m%d%H%M%S')}-{uuid_module.uuid4().hex[:6]}" return jsonify({ - "message": f"已清除 {old_count} 条旧记录", + "message": f"已清除 {deleted_count} 条旧记录", "session_id": new_session_id, - "cleared_count": old_count + "cleared_count": deleted_count }), 200 except Exception as e: db.session.rollback() @@ -285,52 +261,13 @@ def start_new_session(): def finish_stocktake(): """ 结束盘点 - 1. 将指定 session 的草稿标记为 is_finished=True - 2. 计算差异数量 - 3. 不删除任何草稿数据,保留历史 + 直接返回成功,前端会跳转到差异列表 + 草稿数据保留在表中 """ - data = request.json - user_id = _normalize_user_id(data.get('user_id', 'admin')) - session_id = data.get('session_id') - - if not session_id: - return jsonify({"message": "session_id 不能为空"}), 400 - - try: - # 查找该 session 下所有未结束的草稿 - drafts = StocktakeDraft.query.filter_by( - user_id=user_id, - session_id=session_id, - is_finished=False - ).all() - - if not drafts: - return jsonify({"message": "没有找到未结束的盘点记录"}), 404 - - # 更新每个草稿的状态 - now = datetime.now() - for draft in drafts: - draft.is_finished = True - draft.finish_time = now - - # 重新计算差异(以防库存已变化) - if draft.stock_id and draft.source_table: - stock = get_stock_record(draft.source_table, draft.stock_id) - if stock: - current_stock = float(stock.stock_quantity) if stock.stock_quantity else 0 - draft.stock_qty = current_stock - draft.diff_qty = float(draft.quantity) - current_stock - - db.session.commit() - - return jsonify({ - "message": f"已结束盘点,共处理 {len(drafts)} 条记录", - "finished_count": len(drafts), - "session_id": session_id - }), 200 - except Exception as e: - db.session.rollback() - return jsonify({"message": str(e)}), 500 + return jsonify({ + "message": "盘点已结束", + "code": 200 + }), 200 @bp.route('/variance-report', methods=['GET']) @@ -338,25 +275,19 @@ def finish_stocktake(): def get_variance_report(): """ 获取盘点差异报告 - 返回所有 is_finished=True 且 is_processed=False 的记录 - 即:已结束盘点但尚未手动平账的差异记录 + 返回所有有差异的记录(diff_qty != 0) """ - user_id = _normalize_user_id(request.args.get('user_id', 'admin')) session_id = request.args.get('session_id') try: - query = StocktakeDraft.query.filter_by( - user_id=user_id, - is_finished=True, - is_processed=False - ) + query = StocktakeDraft.query if session_id: query = query.filter_by(session_id=session_id) # 只返回有差异的记录 drafts = query.filter(StocktakeDraft.diff_qty != 0).order_by( - StocktakeDraft.finish_time.desc(), + StocktakeDraft.scan_time.desc(), StocktakeDraft.diff_qty.desc() ).all() @@ -413,12 +344,6 @@ def adjust_stock(): if not draft: return jsonify({"message": "草稿记录不存在"}), 404 - if not draft.is_finished: - return jsonify({"message": "该记录尚未结束盘点,无法调整"}), 400 - - if draft.is_processed: - return jsonify({"message": "该记录已处理过平账"}), 400 - # 2. 获取库存记录 if not draft.stock_id or not draft.source_table: return jsonify({"message": "草稿记录缺少库存关联信息"}), 400 @@ -474,9 +399,8 @@ def adjust_stock(): ) db.session.add(trans_record) - # 6. 标记草稿为已处理 - draft.is_processed = True - draft.processed_time = datetime.now() + # 6. 删除草稿记录(平账后从工作台移除) + db.session.delete(draft) db.session.commit() diff --git a/inventory-backend/app/models/inbound/stocktake.py b/inventory-backend/app/models/inbound/stocktake.py index 4f593f6..f8f9f39 100644 --- a/inventory-backend/app/models/inbound/stocktake.py +++ b/inventory-backend/app/models/inbound/stocktake.py @@ -5,7 +5,7 @@ from datetime import datetime class StocktakeDraft(db.Model): """ 盘点草稿表 - 支持多轮盘点,保留历史记录 + 临时工作台,盘点时使用,会话结束后清空 """ __tablename__ = 'stocktake_draft' @@ -16,25 +16,16 @@ class StocktakeDraft(db.Model): # 实际盘点数量 quantity = db.Column(db.Numeric(19, 4), default=1) scan_time = db.Column(db.DateTime, default=beijing_time) - - # ★ 新增: 盘点会话标识 (用于区分不同批次的盘点) + # 盘点会话标识 (用于区分不同批次的盘点) session_id = db.Column(db.String(100)) - # ★ 新增: 是否已结束盘点 - is_finished = db.Column(db.Boolean, default=False) - # ★ 新增: 盘点结束时间 - finish_time = db.Column(db.DateTime) - # ★ 新增: 是否已处理差异 (手动平账) - is_processed = db.Column(db.Boolean, default=False) - # ★ 新增: 处理时间 - processed_time = db.Column(db.DateTime) - # ★ 新增: 差异数量 (实盘 - 账面, 正=盘盈, 负=盘亏) - diff_qty = db.Column(db.Numeric(19, 4), default=0) - # ★ 新增: 账面库存数量 - stock_qty = db.Column(db.Numeric(19, 4), default=0) - # ★ 新增: 关联的库存类型 (stock_buy/stock_semi/stock_product) + # 关联的库存类型 (stock_buy/stock_semi/stock_product) source_table = db.Column(db.String(50)) - # ★ 新增: 关联的库存ID + # 关联的库存ID stock_id = db.Column(db.Integer) + # 账面库存数量 (记录盘点时的账面数量) + stock_qty = db.Column(db.Numeric(19, 4), default=0) + # 差异数量 (实盘 - 账面, 正=盘盈, 负=盘亏) + diff_qty = db.Column(db.Numeric(19, 4), default=0) def to_dict(self): return { @@ -44,12 +35,8 @@ class StocktakeDraft(db.Model): 'quantity': float(self.quantity or 1), 'scan_time': self.scan_time.strftime('%Y-%m-%d %H:%M:%S') if self.scan_time else None, 'session_id': self.session_id, - 'is_finished': self.is_finished, - 'finish_time': self.finish_time.strftime('%Y-%m-%d %H:%M:%S') if self.finish_time else None, - 'is_processed': self.is_processed, - 'processed_time': self.processed_time.strftime('%Y-%m-%d %H:%M:%S') if self.processed_time else None, - 'diff_qty': float(self.diff_qty or 0), - 'stock_qty': float(self.stock_qty or 0), 'source_table': self.source_table, - 'stock_id': self.stock_id + 'stock_id': self.stock_id, + 'stock_qty': float(self.stock_qty or 0), + 'diff_qty': float(self.diff_qty or 0) }