'/index.php/Retail/Statistics/goods_statistics', 'stocks' => '/index.php/Retail/Statistics/stocks', 'sell_statistics' => '/index.php/Retail/Statistics/sell_statistics', 'sell_order' => '/index.php/Retail/Statistics/sell_order', 'inventoryList' => '/index.php/Retail/Statistics/getGoodsInventoryList', 'inventoryInfo' => '/index.php/Retail/Statistics/getGoodsInventoryInfo', ); $authArr = checkFunction($arr); $this->assign('authArr', json_encode($authArr)); $result = $this->getStoreList(); $this->assign('storeList', json_encode($result['store_list'])); $this->assign('platform_type', $this->role_info['platform_type']); $this->display(); } /** * 获取门店列表 * @return array */ protected function getStoreList() { $merchant_id = session('merchant_userinfo')['id']; $store = new Store(); $storeList = $store->getStoreList(['merchant_id' => $merchant_id]); //获取门店列表 $res = array('status' => 1, 'store_list' => $storeList, 'merchant_id' => $merchant_id); return $res; } /** * 展示门店库存统计 * 获取普通商品库存 * @return array $res */ public function getGoodsStock() { // 获取门店 $result = $this->getStoreList(); if ($result['status'] == 0) { $this->ajaxReturn($result); } $store_list = $result['store_list']; $merchant_id = $result['merchant_id']; // 门店商品条件 $map = array( 'g.merchant_id' => $merchant_id, 'g.status' => array('in', array(0, 1)), 'g.attribute_state' => 1, ); // 处理数据 foreach ($store_list as &$val) { $map1 = $map; $map1['g.store_id'] = $val['id']; // 合计 $result2 = $this->merchantTotalStoreGoodsStock($map1); $val['count'] = floatval(round($result2['count'], 2)); $val['all_purchase'] = floatval(round($result2['all_purchase'], 2)); $val['piece_stock'] = floatval(round($result2['piece_stock'], 2)); $val['pricing_stock'] = floatval(round($result2['pricing_stock'], 2)); $val['sell_retail_total'] = floatval(round($result2['sell_retail_total'], 2)); $val['sell_online_total'] = floatval(round($result2['sell_online_total'], 2)); unset($map1); unset($result2); } $res['status'] = 1; $res['goods_statistics'] = $store_list; $this->ajaxReturn($res); } /** * 商户统计门店普通商品库存 * @param array $map 查询条件 * @return array $res */ protected function merchantTotalStoreGoodsStock($map) { // 定义返回值 $res = array( 'count' => 0, // 商品合计 'all_purchase' => 0, // 进价合计 'piece_stock' => 0, // 计件库存合计 'pricing_stock' => 0, // 计量库存合计 'sell_retail_total' => 0, // 店内售出合计 'sell_online_total' => 0, // 商城售出合计 ); // 查询门店商品 $goods_list = M('retail_goods as g') ->join('ls_retail_store_sale_goods as a on g.id=a.goods_id') ->field('g.purchase_price,g.retail_price,g.online_price,g.pricing_method,a.goods_num') ->where($map) ->select(); foreach ($goods_list as &$val) { $res['count']++; $res['all_purchase'] += floatval($val['goods_num']) * floatval($val['purchase_price']); $res['sell_retail_total'] += floatval($val['goods_num']) * floatval($val['retail_price']); $res['sell_online_total'] += floatval($val['goods_num']) * floatval($val['online_price']); if ($val['pricing_method'] == 1) { // 计件商品 $res['piece_stock'] += floatval($val['goods_num']); } else { // 计量商品 $res['pricing_stock'] += floatval($val['goods_num']); } } return $res; } /** * 展示门店库存统计 * 获取规格商品库存 * @return array $res */ public function getSkuGoodsStock() { // 获取门店 $result = $this->getStoreList(); if ($result['status'] == 0) { $this->ajaxReturn($result); } $store_list = $result['store_list']; $merchant_id = $result['merchant_id']; // 门店商品条件 $map = array( 'merchant_id' => $merchant_id, 'status' => array('in', array(0, 1)), 'attribute_state' => 2, ); // 处理数据 foreach ($store_list as &$val) { $map1 = $map; $map1['store_id'] = $val['id']; $result2 = $this->merchantTotalStoreSkuGoodsStock($map1); $val['count'] = floatval(round($result2['count'], 2)); $val['all_purchase'] = floatval(round($result2['all_purchase'], 2)); $val['piece_stock'] = floatval(round($result2['piece_stock'], 2)); $val['pricing_stock'] = floatval(round($result2['pricing_stock'], 2)); $val['sell_retail_total'] = floatval(round($result2['sell_retail_total'], 2)); $val['sell_online_total'] = floatval(round($result2['sell_online_total'], 2)); unset($map1); unset($result2); } $res['status'] = 1; $res['sku_statistics'] = $store_list; $this->ajaxReturn($res); } /** * 商户统计门店规格商品库存 * @param array $map 查询条件 * @return array $res */ protected function merchantTotalStoreSkuGoodsStock($map) { // 定义返回值 $res = array( 'count' => 0, // 商品合计 'all_purchase' => 0, // 进价合计 'piece_stock' => 0, // 计件库存合计 'pricing_stock' => 0, // 计量库存合计 'sell_retail_total' => 0, // 店内售出合计 'sell_online_total' => 0, // 商城售出合计 ); // 查询门店商品id $goods_ids = M('retail_goods')->where($map)->getField('id', true); if (empty($goods_ids)) { return $res; } // 查询规格商品 $map2 = array( 's.goods_id' => array('in', $goods_ids), 's.store_id' => $map['store_id'], 's.status' => 1, 's.state' => 0 ); $sku_list = M('retail_sku_goods as s') ->join('ls_retail_store_sale_goods as a on a.sku_id=s.id') ->field('s.purchase_price,s.retail_price,s.online_price,a.pricing_method,a.goods_num') ->where($map2) ->select(); foreach ($sku_list as &$val) { $res['count']++; $res['all_purchase'] += floatval($val['goods_num']) * floatval($val['purchase_price']); $res['sell_retail_total'] += floatval($val['goods_num']) * floatval($val['retail_price']); $res['sell_online_total'] += floatval($val['goods_num']) * floatval($val['online_price']); if ($val['pricing_method'] == 1) { // 计件商品 $res['piece_stock'] += floatval($val['goods_num']); } else { // 计量商品 $res['pricing_stock'] += floatval($val['goods_num']); } } return $res; } /** * 获取销售统计 * @return array $res */ public function getSellTotal() { $result = $this->getStoreList(); if ($result['status'] == 0) { $this->ajaxReturn($result); } $store_list = $result['store_list']; $merchant_id = $result['merchant_id']; // 定义公共查询条件 $map = array( 'b.merchant_id' => $merchant_id, 'b.pay_state' => 1, 'b.pay_type' => array('neq', 0), ); foreach ($store_list as &$val) { $map1 = $map; $map1['b.store_id'] = $val['id']; $result2 = $this->merchantGetStoreSellTotal($map1); $val['sell_num'] = floatval($result2['sell_num']); $val['refund_num'] = floatval($result2['refund_num']); $val['sell_money'] = floatval($result2['sell_money']); $val['refund_money'] = floatval($result2['refund_money']); $val['income'] = floatval($result2['income']); $val['cost'] = floatval($result2['cost']); $val['profit'] = floatval($result2['profit']); $val['profit_margin'] = floatval($result2['profit_margin']) . '%'; unset($map1); unset($result2); } $res['status'] = 1; $res['sell_statistics'] = $store_list; $this->ajaxReturn($res); } /** * 统计金额(公共方法) * @param array $map 查询条件 * @return array $res */ protected function merchantGetStoreSellTotal($map) { // 销售 $map['b.order_type'] = 1; // 笔数 $sell_num = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->count(); // 金额 $sell_money = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->sum('all_money'); // 所有销售成本 $sell_ids = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->field('b.id') ->where($map) ->select(); $sell_ids = array_column($sell_ids, 'id'); $sell_cost = 0; if ($sell_ids) { // 销售成本 $all_sell = M('retail_sell')->field('num,purchase_price')->where(array('bill_id' => array('in', $sell_ids), 'purchase_price' => array('gt', 0)))->select(); foreach ($all_sell as &$v1) { $sell_cost += floatval(round($v1['num'] * $v1['purchase_price'], 2)); } } // 退款 unset($map['b.order_type']); $map['b.order_type'] = 2; // 笔数 $refund_num = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->count(); // 金额 $refund_money = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->sum('all_money'); // 所有退款成本 $refund_ids = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->field('b.id') ->where($map) ->select(); $refund_ids = $refund_ids ? array_column($refund_ids, 'id') : '0'; // 销售成本 $refund_cost = 0; if ($refund_ids) { $all_refund = M('retail_sell')->field('num,purchase_price')->where(array('bill_id' => array('in', $refund_ids), 'purchase_price' => array('gt', 0)))->select(); foreach ($all_refund as &$v2) { $refund_cost += floatval(round($v2['num'] * $v2['purchase_price'], 2)); } } // 计算成本 (销售成本 - 退款成本) $cost = floatval(round($sell_cost - $refund_cost, 2)); // 实际金额 (销售金额 - 退款金额) $income = floatval(round($sell_money - $refund_money, 2)); // 计算盈利,利润() $profit = floatval(round($income - $cost, 2)); $profit_margin = floatval(round($profit / $income * 100, 2)) . '%'; $res = array( 'sell_num' => $sell_num ? $sell_num : 0, 'refund_num' => $refund_num ? $refund_num : 0, 'sell_money' => $sell_money ? $sell_money : 0, 'refund_money' => $refund_money ? $refund_money : 0, 'income' => $income ? $income : 0, 'cost' => $cost ? $cost : 0, 'profit' => $profit ? $profit : 0, 'profit_margin' => $profit_margin ? $profit_margin : '0%' ); return $res; } /** * 商品库存统计(加载模板) * @param int $storeid */ public function stocks() { // 操作权限 $arr = array( 'stock_export' => '/index.php/Retail/Statistics/stock_export', ); $authArr = checkFunction($arr); // 接受参数 $store_id = I('get.store_id'); $this->assign('authArr', $authArr); $this->assign('store_id', $store_id ? $store_id : 0); $this->display(); } /** * 获取分类 品牌 供货商(公共方法) * @return array $res */ public function get_seek_list() { $user = I('session.ls_userinfo'); $store_id = I('post.store_id'); if (!$store_id) { $res = array('status' => 0, 'msg' => '参数缺失'); $this->ajaxReturn($res); } // 商品分类 $class_data = M('retail_goods_class')->field('id,class_name')->where(array('pid' => 0, 'status' => 0, 'merchantid' => $user['merchantid'], 'type' => 1))->order('id asc')->select(); if ($class_data) { foreach ($class_data as &$val) { $children1 = M('retail_goods_class')->field('id,class_name')->where(array('pid' => $val['id'], 'status' => 0, 'merchantid' => $user['merchantid'], 'type' => 2))->order('id asc')->select(); if ($children1) { foreach ($children1 as &$value) { $children2 = M('retail_goods_class')->field('id,class_name')->where(array('pid' => $value['id'], 'status' => 0, 'merchantid' => $user['merchantid'], 'type' => 3))->order('id asc')->select(); $value['children'] = $children2; } } $val['children'] = $children1; } } // 供货商 $res['supplier'] = M('retail_supplier')->field('id,supplier_name')->where(array('merchantid' => $user['merchantid'], 'status' => 1))->select(); // 品牌 $res['goods_brand'] = M('retail_goods_brand')->field('id,name')->where(array('merchantid' => $user['merchantid'], 'state' => 0))->select(); // 导购员 $res['guide'] = M('retail_guide')->field('id,guidename')->where(array('merchantid' => $user['merchantid'], 'storeid' => $store_id, 'status' => 1))->select(); $res['class_data'] = $class_data; $this->ajaxReturn($res); } /** * 获取普通商品库存展示 * @param int $page 分页 * @param int $limit 每页数量 * @param array $seek_data 搜索条件 * @return array $res */ public function getGoodsList() { // 获取session $user = I('session.ls_userinfo'); $store_id = I('post.store_id'); // 接收数据 $page = (int)I('post.page'); $limit = (int)I('post.limit'); $seek_data = I('post.seek_data'); // 分类搜索 $class_id = array_pop($seek_data['class_ids']); if ($class_id) { $class1 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class_id))->find(); if ($class1['pid'] == 0) { // 一级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->join('ls_retail_goods_class as c3 on c2.id=c3.pid AND c3.status=0', 'LEFT') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id,c3.id as c3_id') ->select(); if ($class) { $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } if ($val['c3_id']) { if (!in_array($val['c3_id'], $arr)) { $arr[] = $val['c3_id']; } } } $map['g.goods_class_id'] = array('in', $arr); } else { $map['g.goods_class_id'] = $class_id; } } else { $class2 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { // 二级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id') ->select(); if ($class) { $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } } $map['g.goods_class_id'] = array('in', $arr); } else { $map['g.goods_class_id'] = $class_id; } } else { // 三级分类 $map['g.goods_class_id'] = $class_id; } } } // 商品名称搜索 if (trim($seek_data['goods_name'], '')) { $map['g.goods_name'] = array('like', '%' . $seek_data['goods_name'] . '%'); } // 商品货号、条码搜索 if (trim($seek_data['keyword'], '')) { $map['g.goods_number|goods_code'] = array('like', '%' . $seek_data['keyword'] . '%'); } // 供货商搜索 if ($seek_data['supplier_id']) { $map['g.supplier_id'] = $seek_data['supplier_id']; } // 品牌搜索 if ($seek_data['goods_brand_id']) { $map['g.goods_brand_id'] = $seek_data['goods_brand_id']; } // 称重类型搜索 if ($seek_data['pricing_method']) { $map['g.pricing_method'] = $seek_data['pricing_method']; } $map['g.store_id'] = $store_id; $map['g.merchant_id'] = $user['merchantid']; $map['g.status'] = array('in', "0,1"); $map['g.attribute_state'] = 1; $goods_list = M('retail_goods as g') ->join('ls_retail_store_sale_goods as a on g.id=a.goods_id') ->field('g.id as goods_id,g.goods_class_id,g.goods_name,g.goods_number,g.goods_code,g.purchase_price,g.retail_price,g.online_price,g.company,g.pricing_method,g.source_type,g.shop_mem_status,g.shop_mem_price,g.store_mem_status,g.store_mem_price,g.goods_brand_id,g.supplier_id,g.serial_number_state,a.goods_num') ->where($map) ->page($page, $limit) ->order('g.id desc') ->select(); $total = M('retail_goods as g') ->join('ls_retail_store_sale_goods as a on g.id=a.goods_id') ->where($map)->count(); foreach ($goods_list as &$val) { // 获取商品分类 $class1 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $val['goods_class_id']))->find(); if ($class1['pid'] == 0) { $val['class_name'] = '/' . $class1['class_name']; } else { $class2 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { $val['class_name'] = '/' . $class2['class_name'] . '/' . $class1['class_name']; } else { $class3 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class2['pid']))->find(); $val['class_name'] = '/' . $class3['class_name'] . '/' . $class2['class_name'] . '/' . $class1['class_name']; } } // 处理货号 $val['goods_number'] = $val['goods_number'] ? $val['goods_number'] : '未设置'; // 进价合计 $val['all_purchase'] = floatval(round($val['goods_num'] * $val['purchase_price'], 2)); // 处理进价 $val['purchase_price'] = floatval($val['purchase_price']); // 处理库存(加上单位) $val['goods_num'] = $val['goods_num'] ? floatval($val['goods_num']) : 0; $val['stock'] = floatval($val['goods_num']) . $val['company']; // 处理店内价 $val['retail_price'] = floatval($val['retail_price']); // 处理商城价 $val['online_price'] = floatval($val['online_price']); // 店内售出合计 $val['sell_retail_total'] = floatval(round($val['retail_price'] * $val['goods_num'], 2)); // 商城售出合计 $val['sell_online_total'] = floatval(round($val['online_price'] * $val['goods_num'], 2)); // 店内会员价 $val['store_mem_price'] = $val['store_mem_status'] == 1 && $val['store_mem_price'] > 0 ? $val['store_mem_price'] : '关闭'; // 商城会员价 $val['shop_mem_price'] = $val['shop_mem_status'] == 1 && $val['shop_mem_price'] > 0 ? $val['shop_mem_price'] : '关闭'; // 称重类型 $val['exchange_weigh_type'] = $val['pricing_method'] == 1 ? '非称重' : '称重'; // 供货商 if ($val['supplier_id']) { $supplier_name = M('retail_supplier')->where(array('id' => $val['supplier_id'], 'merchantid' => $user['merchantid'], 'status' => 1))->getField('supplier_name'); $val['supplier_name'] = $supplier_name ? $supplier_name : '无'; } else { $val['supplier_name'] = '无'; } // 商品品牌 if ($val['goods_brand_id']) { $goods_brand_name = M('retail_goods_brand')->where(array('id' => $val['goods_brand_id'], 'merchantid' => $user['merchantid'], 'state' => 0))->getField('name'); $val['goods_brand_name'] = $goods_brand_name ? $goods_brand_name : '无'; } else { $val['goods_brand_name'] = '无'; } // 商品来源 switch ($val['source_type']) { case 1: $val['source_name'] = '店长添加'; break; case 2: $val['source_name'] = '同步商户'; break; case 3: $val['source_name'] = '收银员添加'; break; default: $val['source_name'] = '未知来源'; } } $res = $this->goodsStatistics($map); $res['status'] = $goods_list ? 1 : 0; $res['goods_list'] = $goods_list; $res['total'] = $total ? (int)$total : 0; $this->ajaxReturn($res); } /** * 统计普通商品数据 * @param array $map 搜索条件 * @return array $res */ protected function goodsStatistics($map) { $goods = M('retail_goods as g') ->join('ls_retail_store_sale_goods as a on g.id=a.goods_id') ->field('g.purchase_price,g.retail_price,g.online_price,g.pricing_method,a.goods_num') ->where($map) ->order('g.id desc') ->select(); $weigh_stock = 0; // 称重总库存 $not_weigh_stock = 0; // 非承重总库存 $purchase_price = 0; // 总进价 $retail_price_total = 0; // 店内售出合计 $online_price_total = 0; // 商城售出合计 foreach ($goods as &$val) { if ($val['pricing_method'] == 1) { // 称重 $not_weigh_stock += $val['goods_num']; } else { // 非称重 $weigh_stock += $val['goods_num']; } $purchase_price += $val['goods_num'] * $val['purchase_price']; $retail_price_total += $val['goods_num'] * $val['retail_price']; $online_price_total += $val['goods_num'] * $val['online_price']; } $res['purchase_price'] = $purchase_price ? floatval(round($purchase_price, 2)) : 0; $res['weigh_stock'] = $weigh_stock ? floatval($weigh_stock) : 0; $res['not_weigh_stock'] = $not_weigh_stock ? floatval($not_weigh_stock) : 0; $res['retail_price_total'] = $retail_price_total ? floatval(round($retail_price_total, 2)) : 0; $res['online_price_total'] = $online_price_total ? floatval(round($online_price_total, 2)) : 0; return $res; } /** * 获取规格商品库存展示 * @param int $page 分页 * @param int $limit 每页数量 * @param array $seek_data 搜索条件 * @return array $res */ public function getSkuGoodsList() { $user = I('session.ls_userinfo'); $store_id = I('post.store_id'); $page = (int)I('post.page'); $limit = (int)I('post.limit'); $seek_data = I('post.seek_data'); // 分类搜索 $class_id = array_pop($seek_data['class_ids']); if ($class_id) { $class1 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class_id))->find(); if ($class1['pid'] == 0) { // 一级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->join('ls_retail_goods_class as c3 on c2.id=c3.pid AND c3.status=0', 'LEFT') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id,c3.id as c3_id') ->select(); if ($class) { // 一级分类有子分类 $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } if ($val['c3_id']) { if (!in_array($val['c3_id'], $arr)) { $arr[] = $val['c3_id']; } } } $map['goods_class_id'] = array('in', $arr); } else { // 一级分类无子分类 $map['goods_class_id'] = $class_id; } } else { $class2 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { // 二级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id') ->select(); if ($class) { $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } } $map['goods_class_id'] = array('in', $arr); } else { $map['goods_class_id'] = $class_id; } } else { // 三级分类 $map['goods_class_id'] = $class_id; } } } // 商品名称搜索 if (trim($seek_data['goods_name'], '')) { $map['goods_name'] = array('like', '%' . $seek_data['goods_name'] . '%'); } // 商品货号、条码搜索 if (trim($seek_data['keyword'], '')) { $map['goods_number|goods_code'] = array('like', '%' . $seek_data['keyword'] . '%'); } // 供货商搜索 if ($seek_data['supplier_id']) { $map['supplier_id'] = $seek_data['supplier_id']; } // 品牌搜索 if ($seek_data['goods_brand_id']) { $map['goods_brand_id'] = $seek_data['goods_brand_id']; } // 称重类型搜索 if ($seek_data['pricing_method']) { $map['pricing_method'] = $seek_data['pricing_method']; } $map['store_id'] = $store_id; $map['merchant_id'] = $user['merchantid']; $map['status'] = array('in', "0,1"); $map['attribute_state'] = 2; $goods_ids = M('retail_goods')->where($map)->getField('id', true); if (!$goods_ids) { $res['status'] = 0; $res['msg'] = '暂无商品'; $this->ajaxReturn($res); } $where['sk.goods_id'] = array('in', $goods_ids); $where['sk.store_id'] = $store_id; $where['sk.status'] = 1; $where['sk.state'] = 0; $sku_list = M('retail_sku_goods as sk') ->join('ls_retail_store_sale_goods as a on a.sku_id=sk.id') ->join('ls_retail_goods as g on g.id=a.goods_id') ->field('sk.goods_id,sk.purchase_price,sk.sku_code as goods_code,sk.retail_price,sk.online_price,sk.sku_id_list,sk.shop_mem_price,sk.store_mem_price,g.goods_class_id,g.goods_name,g.goods_number,g.company,g.pricing_method,g.source_type,g.shop_mem_status,g.store_mem_status,g.goods_brand_id,g.supplier_id,a.goods_num') ->where($where) ->page($page, $limit) ->order('sk.id desc') ->select(); $total = M('retail_sku_goods as sk') ->join('ls_retail_store_sale_goods as a on a.sku_id=sk.id') ->join('ls_retail_goods as g on g.id=a.goods_id') ->where($where)->count(); $RSLModel = D('RetailSkuList'); foreach ($sku_list as &$val) { // 获取商品分类 $class1 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $val['goods_class_id']))->find(); if ($class1['pid'] == 0) { $val['class_name'] = '/' . $class1['class_name']; } else { $class2 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { $val['class_name'] = '/' . $class2['class_name'] . '/' . $class1['class_name']; } else { $class3 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class2['pid']))->find(); $val['class_name'] = '/' . $class3['class_name'] . '/' . $class2['class_name'] . '/' . $class1['class_name']; } } // 处理规格名称 $sku_name = $RSLModel->getFindField(array($RSLModel::ID => array('in', $val['sku_id_list'])), $RSLModel::NAME, true); $val['goods_name'] = $val['goods_name'] . '(' . implode(',', $sku_name) . ')'; // 处理货号 $val['goods_number'] = $val['goods_number'] ? $val['goods_number'] : '未设置'; // 进价合计 $val['all_purchase'] = round($val['goods_num'] * $val['purchase_price'], 2); // 处理进价 $val['purchase_price'] = floatval($val['purchase_price']); // 处理库存(加上单位) $val['goods_num'] = $val['goods_num'] ? floatval($val['goods_num']) : 0; $val['stock'] = $val['goods_num'] . $val['company']; // 处理店内售价 $val['retail_price'] = floatval($val['retail_price']); // 处理商城售价 $val['online_price'] = floatval($val['online_price']); // 店内售出合计 $val['sell_retail_total'] = floatval(round($val['retail_price'] * $val['goods_num'], 2)); // 商城售出合计 $val['sell_online_total'] = floatval(round($val['online_price'] * $val['goods_num'], 2)); // 店内会员价 $val['store_mem_price'] = $val['store_mem_status'] == 1 && $val['store_mem_price'] > 0 ? floatval($val['store_mem_price']) : ' 关闭 '; // 商城会员价 $val['shop_mem_price'] = $val['shop_mem_status'] == 1 && $val['shop_mem_price'] > 0 ? floatval($val['shop_mem_price']) : ' 关闭 '; // 商品称重类型 $val['exchange_weigh_type'] = $val['pricing_method'] == 1 ? '非称重' : '称重'; // 供货商 if ($val['supplier_id']) { $supplier_name = M('retail_supplier')->where(array('id' => $val['supplier_id'], 'merchantid' => $user['merchantid'], 'status' => 1))->getField('supplier_name'); $val['supplier_name'] = $supplier_name ? $supplier_name : '无'; } else { $val['supplier_name'] = '无'; } // 商品品牌 if ($val['goods_brand_id']) { $goods_brand_name = M('retail_goods_brand')->where(array('id' => $val['goods_brand_id'], 'merchantid' => $user['merchantid'], 'state' => 0))->getField('name'); $val['goods_brand_name'] = $goods_brand_name ? $goods_brand_name : '无'; } else { $val['goods_brand_name'] = '无'; } // 商品来源 switch ($val['source_type']) { case 1: $val['source_name'] = '店长添加'; break; case 2: $val['source_name'] = '同步商户'; break; case 3: $val['source_name'] = '收银员添加'; break; default: $val['source_name'] = '未知来源'; } } $res = $this->skuStatistics($where); $res['status'] = $sku_list ? 1 : 0; $res['goods_list'] = $sku_list ? $sku_list : array(); $res['total'] = $total ? (int)$total : 0; $this->ajaxReturn($res); } /** * 统计规格商品数据 * @param array $map 搜索条件 * @return array $res */ protected function skuStatistics($where) { $sku = M('retail_sku_goods as sk') ->join('ls_retail_store_sale_goods as a on a.sku_id=sk.id') ->field('sk.purchase_price,sk.retail_price,sk.online_price,a.pricing_method,a.goods_num') ->where($where) ->select(); $weigh_stock = 0; // 称重总库存 $not_weigh_stock = 0; // 非承重总库存 $purchase_price = 0; // 总进价 $retail_price_total = 0; // 店内售出合计 $online_price_total = 0; // 商城售出合计 foreach ($sku as &$val) { if ($val['pricing_method'] == 1) { // 非称重 $not_weigh_stock += $val['goods_num']; } else { // 称重 $weigh_stock += $val['goods_num']; } $purchase_price += $val['goods_num'] * $val['purchase_price']; $retail_price_total += $val['goods_num'] * $val['retail_price']; $online_price_total += $val['goods_num'] * $val['online_price']; } $res['purchase_price'] = $purchase_price ? round($purchase_price, 2) : 0; $res['weigh_stock'] = $weigh_stock ? floatval($weigh_stock) : 0; $res['not_weigh_stock'] = $not_weigh_stock ? floatval($not_weigh_stock) : 0; $res['retail_price_total'] = $retail_price_total ? floatval(round($retail_price_total, 2)) : 0; $res['online_price_total'] = $online_price_total ? floatval(round($online_price_total, 2)) : 0; return $res; } /** * 门店库存统计展示 * 规格 * @param int $storeid * @param int $page 分页 * @param int $limit 每页数量 * @param array seek_data 搜索条件 * @return array $res */ public function get_sku_list() { $user = I('session.ls_userinfo'); $storeid = I('post.storeid'); $page = (int)I('post.page'); $limit = (int)I('post.limit'); $seek_data = I('post.seek_data'); /* 分类搜索 */ $class_id = array_pop($seek_data['class_ids']); if ($class_id) { $class1 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class_id))->find(); if ($class1['pid'] == 0) { // 一级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->join('ls_retail_goods_class as c3 on c2.id=c3.pid AND c3.status=0', 'LEFT') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id,c3.id as c3_id') ->select(); if ($class) { $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } if ($val['c3_id']) { if (!in_array($val['c3_id'], $arr)) { $arr[] = $val['c3_id']; } } } $map['goods_class_id'] = array('in', $arr); } } else { $class2 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { // 二级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id') ->select(); if ($class) { $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } } $map['goods_class_id'] = array('in', $arr); } } else { // 三级分类 $map['goods_class_id'] = $class_id; } } } /* 商品名称搜索 */ if (trim($seek_data['goods_name'], '')) { $map['goods_name'] = array('like', '%' . $seek_data['goods_name'] . '%'); } /* 商品货号、条码搜索 */ if (trim($seek_data['keyword'], '')) { $map['goods_number|goods_code'] = array('like', '%' . $seek_data['keyword'] . '%'); } /* 供货商搜索 */ if ($seek_data['supplier_id']) { $map['supplier_id'] = $seek_data['supplier_id']; } /* 品牌搜索 */ if ($seek_data['goods_brand_id']) { $map['goods_brand_id'] = $seek_data['goods_brand_id']; } /* 称重类型搜索 */ if ($seek_data['can_exchange_weigh']) { $map['pricing_method'] = $seek_data['can_exchange_weigh']; } $map['store_id'] = $storeid; $map['merchant_id'] = $user['merchantid']; $map['status'] = array('in', "0,1"); $map['attribute_state'] = 2; $goods_ids = M('retail_goods')->where($map)->getField('id', true); if (!$goods_ids) { $res['goods_list'] = array(); $res['total'] = 0; $this->ajaxReturn($res); } $where['sk.goods_id'] = array('in', $goods_ids); $where['sk.store_id'] = $storeid; $where['sk.status'] = 1; $where['sk.state'] = 0; $sku_list = M('retail_sku_goods as sk') ->join('ls_retail_store_sale_goods as a on a.sku_id=sk.id') ->join('ls_retail_goods as g on g.id=a.goods_id') ->field('sk.goods_id,sk.sku_code as goods_code,sk.purchase_price,sk.retail_price,sk.online_price,sk.sku_id_list,sk.shop_mem_price,sk.store_mem_price,g.goods_class_id,g.goods_name,g.goods_number,g.company,g.pricing_method,g.source_type,g.shop_mem_status,g.store_mem_status,g.goods_brand_id,g.supplier_id,a.goods_num') ->where($where) ->page($page, $limit) ->order('sk.id desc') ->select(); $total = M('retail_sku_goods as sk') ->join('ls_retail_store_sale_goods as a on a.sku_id=sk.id') ->join('ls_retail_goods as g on g.id=a.goods_id') ->where($where)->count(); $res = $this->statistics_sku($where); foreach ($sku_list as &$val) { $class1 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $val['goods_class_id']))->find(); if ($class1['pid'] == 0) { $val['class_name'] = '/' . $class1['class_name']; } else { $class2 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { $val['class_name'] = '/' . $class2['class_name'] . '/' . $class1['class_name']; } else { $class3 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class2['pid']))->find(); $val['class_name'] = '/' . $class3['class_name'] . '/' . $class2['class_name'] . '/' . $class1['class_name']; } } $sku_name = M('retail_sku_list')->where(array('id' => array('in', $val['sku_id_list'])))->getField('name', true); $val['goods_name'] = $val['goods_name'] . '(' . implode(',', $sku_name) . ')'; $val['goods_num'] = floatval($val['goods_num']); $val['stock'] = $val['goods_num'] . $val['company']; $val['purch_price'] = floatval($val['purchase_price']); $val['all_purch'] = round($val['goods_num'] * $val['purchase_price'], 2); $val['retail_price'] = floatval($val['retail_price']); $val['online_price'] = floatval($val['online_price']); $val['retail_price_total'] = floatval(round($val['retail_price'] * $val['goods_num'], 2)); $val['online_price_total'] = floatval(round($val['online_price'] * $val['goods_num'], 2)); $val['shop_mem_price'] = $val['shop_mem_status'] == 1 && $val['shop_mem_price'] > 0 ? floatval($val['shop_mem_price']) : '关闭'; $val['store_mem_price'] = $val['store_mem_status'] == 1 && $val['store_mem_price'] > 0 ? floatval($val['store_mem_price']) : '关闭'; $val['source_name'] = $val['source_type'] == 3 ? '调拨' : '进货'; $val['pricing_method'] = $val['pricing_method'] == 1 ? '非称重' : '称重'; if ($val['supplier_id'] && $val['supplier_id'] == -1) { $val['supplier_name'] = '自采/其他'; } else if ($val['supplier_id'] && $val['supplier_id'] != -1) { $supplier_name = M('retail_supplier')->where(array('id' => $val['supplier_id'], 'merchantid' => $map['merchantid'], 'status' => 1))->getField('supplier_name'); $val['supplier_name'] = $supplier_name ? $supplier_name : '无'; } else { $val['supplier_name'] = '无'; } if ($val['goods_brand_id']) { $goods_brand_name = M('retail_goods_brand')->where(array('id' => $val['goods_brand_id'], 'merchantid' => $map['merchantid'], 'state' => 0))->getField('name'); $val['goods_brand_name'] = $goods_brand_name ? $goods_brand_name : '无'; } else { $val['goods_brand_name'] = '无'; } $val['goods_code'] = $val['goods_code'] ? $val['goods_code'] : '无'; $val['good_number'] = $val['goods_number'] ? $val['goods_number'] : '无'; } $res['status'] = 1; $res['goods_list'] = $sku_list ? $sku_list : array(); $res['total'] = $total ? (int)$total : 0; $this->ajaxReturn($res); } /** * 统计金额(公共方法) * @param array $map 查询条件 * @return array $res */ protected function statistics_sell($map) { // 销售 $map['b.order_type'] = 1; // 笔数 $sell_num = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->count(); // 金额 $sell_money = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->sum('all_money'); // 退款 unset($map['b.order_type']); $map['b.order_type'] = 2; // 笔数 $refund_num = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->count(); // 金额 $refund_money = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->sum('all_money'); // 所有订单 unset($map['b.order_type']); $map['b.order_type'] = 1; // 销售成本 // 获取销售 $all_bill_ids = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->field('b.id') ->where($map) ->select(); $bill_ids = $all_bill_ids ? array_column($all_bill_ids, 'id') : '0'; // 销售成本 $all_sell = M('retail_sell')->field('num,purchase_price')->where(array('bill_id' => array('in', $bill_ids), 'purchase_price' => array('gt', 0)))->select(); $cost = 0; foreach ($all_sell as &$val) { $cost += floatval(round($val['num'] * $val['purchase_price'], 2)); } // 实收金额(总金额 - 退款金额) $income = floatval(round($sell_money - $refund_money, 2)); // 计算盈利,利润() $profit = floatval(round($income - $cost, 2)); $profit_margin = floatval(round($profit / $income * 100, 2)) . '%'; $res['sell_num'] = $sell_num ? $sell_num : 0; $res['refund_num'] = $refund_num ? $refund_num : 0; $res['sell_money'] = $sell_money ? $sell_money : 0; $res['refund_money'] = $refund_money ? $refund_money : 0; $res['income'] = $income ? $income : 0; $res['cost'] = $cost ? $cost : 0; $res['profit'] = $profit ? $profit : 0; $res['profit_margin'] = $profit_margin ? $profit_margin : '0%'; return $res; } /* 库存统计导出 * */ public function stock_export() { $user = I('session.ls_userinfo'); $store_id = I('get.store_id'); $type = I('get.type'); // 类型 $seek_data = json_decode($_GET['seek_data'], true); // 搜索条件 /* 分类搜索 */ $class_id = array_pop($seek_data['class_ids']); if ($class_id) { $class1 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class_id))->find(); if ($class1['pid'] == 0) { // 一级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->join('ls_retail_goods_class as c3 on c2.id=c3.pid AND c3.status=0', 'LEFT') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id,c3.id as c3_id') ->select(); if ($class) { $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } if ($val['c3_id']) { if (!in_array($val['c3_id'], $arr)) { $arr[] = $val['c3_id']; } } } $map['g.goods_class_id'] = array('in', $arr); } else { $map['g.goods_class_id'] = $class_id; } } else { $class2 = M('retail_goods_class')->field('id,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { // 二级分类 $class = M('retail_goods_class as c1') ->join('ls_retail_goods_class as c2 on c1.id=c2.pid') ->where(array('c1.id' => $class_id, 'c2.status' => 0)) ->field('c2.id') ->select(); if ($class) { $arr = array(); $arr[] = $class_id; foreach ($class as &$val) { if (!in_array($val['id'], $arr)) { $arr[] = $val['id']; } } $map['g.goods_class_id'] = array('in', $arr); } else { $map['g.goods_class_id'] = $class_id; } } else { // 三级分类 $map['g.goods_class_id'] = $class_id; } } } /* 商品名称搜索 */ if (trim($seek_data['goods_name'], '')) { $map['g.goods_name'] = array('like', '%' . $seek_data['goods_name'] . '%'); } // 商品货号、条码搜索 if (trim($seek_data['keyword'], '')) { $map['g.goods_number|g.goods_code'] = array('like', '%' . $seek_data['keyword'] . '%'); } /* 供货商搜索 */ if ($seek_data['supplier_id']) { $map['g.supplier_id'] = $seek_data['supplier_id']; } /* 品牌搜索 */ if ($seek_data['goods_brand_id']) { $map['g.goods_brand_id'] = $seek_data['goods_brand_id']; } /* 称重类型搜索 */ if ($seek_data['pricing_method']) { $map['g.pricing_method'] = $seek_data['pricing_method']; } $map['g.store_id'] = $store_id; $map['g.merchant_id'] = $user['merchantid']; $map['g.status'] = array('in', "0,1"); if ($type == 1) { $map['g.attribute_state'] = 1; $result = $this->goods_export($map); if ($result['status'] == 1) { $store_list = $result['goods_list']; } } else { $map['g.attribute_state'] = 2; $result = $this->sku_export($map); if ($result['status'] == 1) { $store_list = $result['sku_list']; } } $store_list = $store_list ? $store_list : array(); $name = $type == 1 ? '普通商品库存统计报表' : '规格商品库存统计报表'; $headArr = array( array('index', '序号'), array('goods_name', '商品名称'), array('class_name', '商品分类'), array('goods_number', '商品货号'), array('stock', '库存'), array('purchase_price', '进价(单个)'), array('all_purchase', '进价(合计)'), array('retail_price', '售价(店内)'), array('online_price', '售价(商城)'), array('sell_retail_total', '售出合计(店内)'), array('sell_online_total', '售出合计(商城)'), array('store_mem_price', '会员价(店内)'), array('shop_mem_price', '会员价(商城)'), array('source_name', '渠道'), array('pricing_method', '类型'), array('supplier_name', '供货商'), array('goods_brand_name', '品牌') ); $str = $name . '导出时间' . date('Y-m-d H:i:s', time()); getExcel($name, $headArr, $store_list, $str); } /* 普通商品导出 * @return array() * */ protected function goods_export($map) { $goods_list = M('retail_goods as g') ->join('ls_retail_store_sale_goods as a on a.goods_id=g.id') ->field('g.id as goods_id,g.goods_class_id,g.goods_name,g.goods_number,g.goods_code,g.purchase_price,g.retail_price,g.online_price,g.company,g.pricing_method,g.shop_mem_status,g.shop_mem_price,g.store_mem_status,g.source_type,g.store_mem_price,g.goods_brand_id,g.supplier_id,a.goods_num') ->where($map) ->order('g.id desc') ->select(); if (!$goods_list) { $res['status'] = 0; $res['msg'] = '暂无数据'; return $res; } foreach ($goods_list as $key => &$val) { $val['index'] = $key + 1; // 获取商品分类 $class1 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $val['goods_class_id']))->find(); if ($class1['pid'] == 0) { $val['class_name'] = '/' . $class1['class_name']; } else { $class2 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { $val['class_name'] = '/' . $class2['class_name'] . '/' . $class1['class_name']; } else { $class3 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class2['pid']))->find(); $val['class_name'] = '/' . $class3['class_name'] . '/' . $class2['class_name'] . '/' . $class1['class_name']; } } $val['all_purchase'] = strval(floatval(round($val['goods_num'] * $val['purchase_price'], 2))); $val['goods_num'] = floatval($val['goods_num']); $val['stock'] = $val['goods_num'] . $val['company']; $val['purchase_price'] = strval(floatval($val['purchase_price'])); $val['retail_price'] = strval(floatval($val['retail_price'])); $val['online_price'] = strval(floatval($val['online_price'])); $val['sell_retail_total'] = strval(floatval(round($val['retail_price'] * $val['goods_num'], 2))); $val['sell_online_total'] = strval(floatval(round($val['online_price'] * $val['goods_num'], 2))); $val['shop_mem_price'] = $val['shop_mem_status'] == 1 && $val['shop_mem_price'] > 0 ? strval(floatval($val['shop_mem_price'])) : '关闭'; $val['store_mem_price'] = $val['store_mem_status'] == 1 && $val['store_mem_price'] > 0 ? strval(floatval($val['store_mem_price'])) : '关闭'; $val['pricing_method'] = $val['pricing_method'] == 1 ? '非称重' : '称重'; if ($val['supplier_id']) { $supplier_name = M('retail_supplier')->where(array('id' => $val['supplier_id'], 'merchantid' => $map['merchant_id'], 'status' => 1))->getField('supplier_name'); $val['supplier_name'] = $supplier_name ? $supplier_name : '无'; } else { $val['supplier_name'] = '无'; } if ($val['goods_brand_id']) { $goods_brand_name = M('retail_goods_brand')->where(array('id' => $val['goods_brand_id'], 'merchantid' => $map['merchant_id'], 'state' => 0))->getField('name'); $val['goods_brand_name'] = $goods_brand_name ? $goods_brand_name : '无'; } else { $val['goods_brand_name'] = '无'; } // 商品来源 switch ($val['source_type']) { case 1: $val['source_name'] = '店长添加'; break; case 2: $val['source_name'] = '同步商户'; break; case 3: $val['source_name'] = '收银员添加'; break; default: $val['source_name'] = '未知来源'; } } $res['status'] = 1; $res['goods_list'] = $goods_list; return $res; } /* 普通商品导出 * @return array() * */ protected function sku_export($map) { /* 查看进价权限 */ $show_purch_price = I('session.global_store_jurisdiction')['showpurch_price']; $goods_ids = M('retail_goods as g')->field('g.id')->where($map)->select(); // 处理二位数组 $goods_ids = array_column($goods_ids, 'id'); if (empty($goods_ids)) { $res['status'] = 0; $res['msg'] = '暂无商品数据'; return $res; } $where['sk.goods_id'] = array('in', $goods_ids); $where['sk.store_id'] = $map['g.store_id']; $where['sk.status'] = 1; $where['sk.state'] = 0; $sku_list = M('retail_sku_goods as sk') ->join('ls_retail_store_sale_goods as a on a.sku_id=sk.id') ->join('ls_retail_goods as g on g.id=a.goods_id') ->field('sk.goods_id,sk.purchase_price,sk.sku_code as goods_code,sk.retail_price,sk.online_price,sk.sku_id_list,sk.shop_mem_price,sk.store_mem_price,g.goods_class_id,g.goods_name,g.goods_number,g.company,g.pricing_method,g.source_type,g.shop_mem_status,g.store_mem_status,g.goods_brand_id,g.supplier_id,a.goods_num') ->where($where) ->order('sk.id desc') ->select(); if (!$sku_list) { $res['status'] = 0; $res['msg'] = '暂无规格商品'; return $res; } foreach ($sku_list as $key => &$val) { $val['index'] = $key + 1; $class1 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $val['goods_class_id']))->find(); if ($class1['pid'] == 0) { $val['class_name'] = '/' . $class1['class_name']; } else { $class2 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class1['pid']))->find(); if ($class2['pid'] == 0) { $val['class_name'] = '/' . $class2['class_name'] . '/' . $class1['class_name']; } else { $class3 = M('retail_goods_class')->field('id,class_name,pid')->where(array('id' => $class2['pid']))->find(); $val['class_name'] = '/' . $class3['class_name'] . '/' . $class2['class_name'] . '/' . $class1['class_name']; } } $sku_name = M('retail_sku_list')->where(array('id' => array('in', $val['sku_id_list'])))->getField('name', true); $val['goods_name'] = $val['goods_name'] . '(' . implode(',', $sku_name) . ')'; $val['all_purchase'] = strval(floatval(round($val['goods_num'] * $val['purchase_price'], 2))); $val['goods_num'] = floatval($val['goods_num']); $val['stock'] = strval($val['goods_num'] . $val['company']); $val['purchase_price'] = strval(floatval($val['purchase_price'])); $val['retail_price'] = strval(floatval($val['retail_price'])); $val['online_price'] = strval(floatval($val['online_price'])); $val['sell_retail_total'] = strval(floatval(round($val['retail_price'] * $val['goods_num'], 2))); $val['sell_online_total'] = strval(floatval(round($val['retail_price'] * $val['goods_num'], 2))); $val['shop_mem_status'] = $val['shop_mem_status'] == 1 && $val['shop_mem_price'] > 0 ? strval(floatval($val['shop_mem_price'])) : ' 关闭 '; $val['store_mem_status'] = $val['store_mem_status'] == 1 && $val['store_mem_price'] > 0 ? strval(floatval($val['store_mem_price'])) : ' 关闭 '; $val['pricing_method'] = $val['pricing_method'] == 1 ? '非称重' : '称重'; if ($val['supplier_id']) { $supplier_name = M('retail_supplier')->where(array('id' => $val['supplier_id'], 'merchantid' => $map['merchant_id'], 'status' => 1))->getField('supplier_name'); $val['supplier_name'] = $supplier_name ? $supplier_name : '无'; } else { $val['supplier_name'] = '无'; } if ($val['goods_brand_id']) { $goods_brand_name = M('retail_goods_brand')->where(array('id' => $val['goods_brand_id'], 'merchantid' => $map['merchant_id'], 'state' => 0))->getField('name'); $val['goods_brand_name'] = $goods_brand_name ? $goods_brand_name : '无'; } else { $val['goods_brand_name'] = '无'; } // 商品来源 switch ($val['source_type']) { case 1: $val['source_name'] = '店长添加'; break; case 2: $val['source_name'] = '同步商户'; break; case 3: $val['source_name'] = '收银员添加'; break; default: $val['source_name'] = '未知来源'; } } $res['status'] = 1; $res['sku_list'] = $sku_list; return $res; } /** * 销售订单统计(加载模板) * @param int $storeid */ public function sell_order() { // 操作权限 $arr = array( 'sell_export' => '/index.php/Retail/Statistics/sell_export', ); $authArr = checkFunction($arr); // 接受参数 $store_id = I('get.store_id'); $this->assign('authArr', $authArr); $this->assign('store_id', $store_id ? $store_id : 0); $this->display(); } /** * 获取销售数据展示 * @param int $page 分页 * @param int $limit 每页数量 * @param array $seek_data 搜索条件 * @return array $res */ public function getBillList() { // 获取session $user = I('session.ls_userinfo'); $store_id = I('post.store_id'); // 接收数据 $page = (int)I('post.page'); $limit = (int)I('post.limit'); $seek_data = I('post.seek_data'); /* 时间搜索 */ $start_time = $seek_data['start_time']; $end_time = $seek_data['end_time']; if ($start_time && $end_time) { $start_time = strtotime($start_time); $end_time = strtotime($end_time); $map['b.add_time'] = array('between', array($start_time, $end_time)); } else if ($start_time && !$end_time) { $start_time = strtotime($start_time); $map['b.add_time'] = array('egt', $start_time); } else if (!$start_time && $end_time) { $end_time = strtotime($end_time); $map['b.add_time'] = array('elt', $end_time); } /* 订单号搜索 */ if (trim($seek_data['order_id'], '')) { $map['b.order_no'] = array('like', '%' . $seek_data['order_id'] . '%'); } /* 导购员搜索 */ if ($seek_data['guide_id']) { $map['b.guide_id'] = $seek_data['guide_id']; } $map[] = array( 'b.order_type' => 1, array( 'b.order_type' => array('in', '2,3'), 'b.refund_status' => 2, ), '_logic' => 'OR', ); /* 类型搜索 */ if ($seek_data['order_mold']) { switch ($seek_data['order_mold']) { case 1: $map['b.type'] = 2; break; case 2: $map['b.type'] = 1; break; case 3: $map['b.type'] = 2; $map['b.order_type'] = 1; break; case 4: $map['b.type'] = 1; $map['b.order_type'] = 1; break; case 5: $map['b.type'] = 2; $map['b.order_type'] = 2; break; case 6: $map['b.type'] = 1; $map['b.order_type'] = 2; break; default: break; } } $map['b.merchant_id'] = $user['merchantid']; $map['b.store_id'] = $store_id; $map['b.pay_state'] = 1; $map['b.pay_type'] = array('neq', 0); $bill_list = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->page($page, $limit) ->order('b.add_time desc') ->select(); $total = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->count(); $BillOrder = new BillOrder(); foreach ($bill_list as &$val) { $val['add_time'] = date('Y-m-d H:i:s', $val['add_time']); $val['pay_name'] = $BillOrder->getPayType($val['pay_type'], $val['id']); /* 消费对象 */ if ($val['vid']) { $vip = M('retail_vip')->field('name,nickname')->where(array('id' => $val['vid']))->find(); if ($vip) { if ($vip['name']) { $val['consumer_object'] = $vip['name']; } else if ($vip['nickname']) { $val['consumer_object'] = $vip['nickname']; } else { $val['consumer_object'] = '未设置'; } } else { $val['consumer_object'] = '散客'; } } else if ($val['third_vip_code']) { $val['consumer_object'] = $val['third_vip_name']; } else { $val['consumer_object'] = '散客'; } /* 统计成本 */ $val['purchase_price'] = 0; $sell_list = M('retail_sell')->field('num,purchase_price')->where(array('bill_id' => $val['id']))->select(); foreach ($sell_list as &$v) { $val['purchase_price'] += floatval(round($v['num'] * $v['purchase_price'], 2)); } $val['delivery_fee'] = $val['delivery_fee'] ? floatval($val['delivery_fee']) : 0; $val['profit'] = floatval(round($val['all_money'] - $val['purchase_price'] - $val['delivery_fee'], 2)); $val['profit_margin'] = floatval(round($val['profit'] / ($val['all_money'] - $val['delivery_fee']) * 100, 2)) . '%'; $val['dismoney'] = $val['vip_dis_money'] && $val['vip_dis_money'] > 0 ? floatval($val['vip_dis_money']) : '无'; $val['coupon_money'] = $val['coupon_money'] && $val['coupon_money'] > 0 ? floatval($val['coupon_money']) : '无'; $val['delivery_fee'] = $val['delivery_fee'] && $val['delivery_fee'] > 0 ? floatval($val['delivery_fee']) : '无'; $val['small_changes_money'] = $val['small_changes_money'] && $val['small_changes_money'] > 0 ? floatval($val['small_changes_money']) : '无'; if ($val['discount'] > 0 && $val['discount'] < 1 && $val['cashier_dis_money']) { $val['discount_remark'] = floatval($val['discount']) . '折金额:' . floatval($val['cashier_dis_money']); } else { $val['discount_remark'] = '未打折金额:无'; } /* 查询导购员 */ if ($val['guide_id']) { $guide_name = M('retail_guide')->where(array('id' => $val['guide_id']))->getField('guidename'); $val['guide_name'] = $guide_name ? $guide_name : '未设置'; } else { $val['guide_name'] = '自购'; } /* 类型 */ $type_name = $val['type'] == 1 ? '商城' : '店内'; $order_type_name = $val['order_type'] == 1 ? '销售' : '退款'; $val['order_mold'] = $type_name . $order_type_name; /* 退款订单加负号 */ if ($val['order_type'] != 1) { $val['all_money'] = '-' . $val['all_money']; $val['profit'] = 0; $val['profit_margin'] = '0%'; } } /* 统计 */ $res = $this->sellStatistics($map); $res['status'] = 1; $res['bill_list'] = $bill_list; $res['total'] = $total ? (int)$total : 0; $this->ajaxReturn($res); } /** * 统计金额(公共方法) * @param array $map 查询条件 * @return array $res */ protected function sellStatistics($map) { // 销售 $map['b.order_type'] = 1; // 笔数 $sell_num = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->count(); // 金额 $sell_money = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->sum('all_money'); // 所有销售成本 $sell_ids = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->field('b.id') ->where($map) ->select(); $sell_ids = array_column($sell_ids, 'id'); $sell_cost = 0; if ($sell_ids) { // 销售成本 $all_sell = M('retail_sell')->field('num,purchase_price')->where(array('bill_id' => array('in', $sell_ids), 'purchase_price' => array('gt', 0)))->select(); foreach ($all_sell as &$v1) { $sell_cost += floatval(round($v1['num'] * $v1['purchase_price'], 2)); } } // 退款 unset($map['b.order_type']); $map['b.order_type'] = 2; // 笔数 $refund_num = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->count(); // 金额 $refund_money = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->where($map) ->sum('all_money'); // 所有退款成本 $refund_ids = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->field('b.id') ->where($map) ->select(); $refund_ids = $refund_ids ? array_column($refund_ids, 'id') : '0'; // 销售成本 $refund_cost = 0; if ($refund_ids) { $all_refund = M('retail_sell')->field('num,purchase_price')->where(array('bill_id' => array('in', $refund_ids), 'purchase_price' => array('gt', 0)))->select(); foreach ($all_refund as &$v2) { $refund_cost += floatval(round($v2['num'] * $v2['purchase_price'], 2)); } } // 计算成本 (销售成本 - 退款成本) $cost = floatval(round($sell_cost - $refund_cost, 2)); // 实际金额 (销售金额 - 退款金额) $income = floatval(round($sell_money - $refund_money, 2)); // 计算盈利,利润() $profit = floatval(round($income - $cost, 2)); $profit_margin = floatval(round($profit / $income * 100, 2)) . '%'; $res['sell_num'] = $sell_num ? $sell_num : 0; $res['refund_num'] = $refund_num ? $refund_num : 0; $res['sell_money'] = $sell_money ? $sell_money : 0; $res['refund_money'] = $refund_money ? $refund_money : 0; $res['income'] = $income ? $income : 0; $res['cost'] = $cost ? $cost : 0; $res['profit'] = $profit ? $profit : 0; $res['profit_margin'] = $profit_margin ? $profit_margin : '0%'; return $res; } /** * 普通商品库存报表 */ public function getGoodsInventoryList() { $data = I('post.'); $data['merchant_id'] = $this->merchant_id; $inventory = new Inventory(); $result = $inventory->getStoreSyncGoodsInventoryList($data); $this->ajaxReturn($result); } /** * 普通商品库存报表详情 */ public function getGoodsInventoryInfo() { $data = I('post.'); $data['merchant_id'] = $this->merchant_id; $inventory = new Inventory(); $result = $inventory->getSyncGoodsInfo($data); $this->ajaxReturn($result); } /** * 规格商品库存报表 */ public function getGoodsSkuInventoryList() { $data = I('post.'); $data['merchant_id'] = $this->merchant_id; $inventory = new Inventory(); $result = $inventory->getStoreSyncGoodsSkuInventoryList($data); $this->ajaxReturn($result); } /** * 规格商品库存报表详情 */ public function getGoodsSkuInventoryInfo() { $data = I('post.'); $data['merchant_id'] = $this->merchant_id; $inventory = new Inventory(); $result = $inventory->getSyncGoodsSkuInfo($data); $this->ajaxReturn($result); } //串号列表 public function serialList() { $data = I('post.'); $data['user_type'] = 4; $data['merchant_id'] = $this->merchant_id; $SerialClass = new SerialNumberGoods(); $result = $SerialClass->warehouseSerialList($data); $this->ajaxReturn($result); } /** * 销售报表导出 * @throws \PHPExcel_Exception * @throws \PHPExcel_Reader_Exception * @throws \PHPExcel_Writer_Exception */ public function sell_export() { if (IS_POST) { $ExporttableController = new ExporttableController(); $RetailGuideModel = new RetailGuideModel(); $RetailVipModel = new RetailVipModel(); ini_set('memory_limit', '64M'); $user = I('session.ls_userinfo'); $store_id = I('post.store_id') ? I('post.store_id') : $this->store_id; //搜索条件 $seek_data = I('post.seek_data') ? I('post.seek_data') : []; $directory_name = I('post.directory_name'); $page = I('post.page') ? I('post.page') : 1; $limit = I('post.limit') ? I('post.limit') : 500; /* 时间搜索 */ $start_time = $seek_data['start_time']; $end_time = $seek_data['end_time']; if ($start_time && $end_time) { $start_time = strtotime($start_time); $end_time = strtotime($end_time); $map['b.add_time'] = ['between', [$start_time, $end_time]]; } else if ($start_time && !$end_time) { $start_time = strtotime($start_time); $map['b.add_time'] = ['egt', $start_time]; } else if (!$start_time && $end_time) { $start_time = strtotime($start_time); $map['b.add_time'] = ['elt', $start_time]; } /* 订单号搜索 */ if (trim($seek_data['order_id'], '')) { $map['b.order_no'] = ['like', '%' . $seek_data['order_id'] . '%']; } /* 导购员搜索 */ if ($seek_data['guide_id']) { $map['b.guide_id'] = $seek_data['guide_id']; } $map[] = [ 'b.order_type' => 1, [ 'b.order_type' => ['in', '2,3'], 'b.refund_status' => 2, ], '_logic' => 'OR', ]; /* 类型搜索 */ if ($seek_data['order_mold']) { switch ($seek_data['order_mold']) { case 1: $map['b.type'] = 2; break; case 2: $map['b.type'] = 1; break; case 3: $map['b.type'] = 2; $map['b.order_type'] = 1; break; case 4: $map['b.type'] = 1; $map['b.order_type'] = 1; break; case 5: $map['b.type'] = 2; $map['b.order_type'] = 2; break; case 6: $map['b.type'] = 1; $map['b.order_type'] = 2; break; default: break; } } $map['b.merchant_id'] = $user['merchantid']; $map['b.store_id'] = $store_id; $map['b.pay_state'] = 1; $map['b.pay_type'] = ['neq', 0]; $bill_list = M('retail_bill_order as b') ->join('ls_retail_bill_discount as d on b.id=d.bill_id') ->join('ls_retail_bill_online as o on b.id=o.bill_id', 'LEFT') ->field('id,order_no,all_money,pay_type,type,order_type,b.add_time,vid,guide_id,vip_dis_money,coupon_money,small_changes_money,delivery_fee,discount,cashier_dis_money,third_vip_code,third_vip_name') ->where($map) ->page((int)$page, (int)$limit) ->order('b.add_time desc') ->select(); $BillOrder = new BillOrder(); foreach ($bill_list as $key => &$val) { $val['index'] = $key + 1; $val['add_time'] = date('Y-m-d H:i:s', $val['add_time']); $val['pay_name'] = $BillOrder->getPayType($val['pay_type'], $val['id']); /* 消费对象 */ if ($val['vid']) { $vip = $RetailVipModel->getFind(['id' => $val['vid']], 'name,nickname'); if ($vip) { if ($vip['name']) { $val['consumer_object'] = $vip['name']; } else if ($vip['nickname']) { $val['consumer_object'] = $vip['nickname']; } else { $val['consumer_object'] = '未设置'; } } else { $val['consumer_object'] = '散客'; } } else if ($val['third_vip_code']) { $val['consumer_object'] = $val['third_vip_name']; } else { $val['consumer_object'] = '散客'; } /* 统计成本 */ $val['purchase_price'] = 0; $sell_list = M('retail_sell')->field('num,purchase_price')->where(array('bill_id' => $val['id']))->select(); foreach ($sell_list as &$v) { $val['purchase_price'] += floatval(round($v['num'] * $v['purchase_price'], 2)); } $val['delivery_fee'] = $val['delivery_fee'] ? floatval($val['delivery_fee']) : 0; $val['profit'] = floatval(round($val['all_money'] - $val['purchase_price'] - $val['delivery_fee'], 2)); $val['profit_margin'] = floatval(round($val['profit'] / ($val['all_money'] - $val['delivery_fee']) * 100, 2)) . '%'; $val['dismoney'] = $val['vip_dis_money'] && $val['vip_dis_money'] > 0 ? floatval($val['vip_dis_money']) : '无'; $val['coupon_money'] = $val['coupon_money'] && $val['coupon_money'] > 0 ? floatval($val['coupon_money']) : '无'; $val['delivery_fee'] = $val['delivery_fee'] && $val['delivery_fee'] > 0 ? floatval($val['delivery_fee']) : '无'; $val['small_changes_money'] = $val['small_changes_money'] && $val['small_changes_money'] > 0 ? floatval($val['small_changes_money']) : '无'; if ($val['discount'] > 0 && $val['discount'] < 1 && $val['cashier_dis_money']) { $val['discount_remark'] = floatval($val['discount']) . '折金额:' . floatval($val['cashier_dis_money']); } else { $val['discount_remark'] = '未打折金额:无'; } /* 查询导购员 */ if ($val['guide_id']) { $guide_name = $RetailGuideModel->getFindField(['id' => $val['guideid']], 'guidename'); $val['guide_name'] = $guide_name ? $guide_name : '未设置'; } else { $val['guide_name'] = '自购'; } /* 类型 */ $type_name = $val['type'] == 1 ? '商城' : '店内'; $order_type_name = $val['order_type'] == 1 ? '销售' : '退款'; $val['order_mold'] = $type_name . $order_type_name; /* 退款订单加负号 */ if ($val['order_type'] != 1) { $val['all_money'] = '-' . $val['all_money']; $val['profit'] = 0; $val['profit_margin'] = '0%'; } } import("Vendor.PHPExcel.PHPExcel"); import("Vendor.PHPExcel.Writer.Excel5"); import("Vendor.PHPExcel.IOFactory.php"); $filename = 'SellListReport' . date("ymdHis", time()); $headArr = [ ['index', '序号'], ['order_mold', '类型'], ['order_no', '订单号'], ['add_time', '售出时间'], ['consumer_object', '消费对象'], ['guide_name', '导购'], ['pay_name', '支付方式'], ['all_money', '支付金额'], ['purchase_price', '成本合计'], ['coupon_money', '优惠券'], ['small_changes_money', '抹零'], ['vip_dis_money', '会员折扣'], ['discount_remark', '收银折扣'], ['delivery_fee', '费送费'], ['profit', '利润'], ['profit_margin', '利润率'], ]; $str = $filename . '表格生成时间:' . date('Y-m-d H:i:s'); if (!$directory_name) { $num = createKey(); $directory_name = "./Uploads/storeGoodsExcel/{$store_id}/{$num}"; } $ExporttableController->setExcel($filename, $headArr, $bill_list, $str, $directory_name); $result = array( 'status' => 1, 'type' => 1, 'directory_name' => $directory_name, 'msg' => '请继续生成文件' ); if (count($bill_list) < $limit) { $result['type'] = 2; $result['msg'] = '数据生成完毕'; } $this->ajaxReturn($result); } else if (IS_GET) { $directory_name = I('get.directory_name'); $ExporttalController = new ExporttableController(); $res = $ExporttalController->fileZipAddToDel($directory_name, 'SellList'); $this->ajaxReturn($res); } } /** * 获取商户概况数据统计 */ public function getMerchantStatisticsList() { $Statistics = new \Common\Order\Statistics(); if (!$this->merchant_id) { $this->ajaxReturn(['status' => 0, 'msg' => '登录超时,请重新登录']); } $result = $Statistics->getMerchantStatisticsList($this->merchant_id); $this->ajaxReturn($result); } /** * 获取门店概况数据统计 */ public function getStoreStatisticsList() { $Statistics = new \Common\Order\Statistics(); if (!$this->merchant_id || !$this->store_id) { $this->ajaxReturn(['status' => 0, 'msg' => '登录超时,请重新登录']); } $result = $Statistics->getStoreStatisticsList($this->merchant_id, $this->store_id); $this->ajaxReturn($result); } }