電商專案day08(商家錄入商品&商品的上下架&運營商稽核&)
今日目標:
1.完成商品錄入之SKU列表生成
2.運營商的對商品的稽核
3.商家對商品的管理
一、商品錄入之SKU列表生成
前端js中,json格式的物件,最適合組裝動態變化的資料。
tb_item表中spec欄位,記錄商品特有的規格資料。
spec:{"機身記憶體":"16G","網路":"聯通3G"}
js陣列的組裝技巧
克隆 分為兩種:淺克隆和深克隆
要基於js克隆方式,實現spec物件組裝。
淺克隆 var a={name:"zhangsan"} var b=a; 宣告變數,重新賦予已經存在的變數。
深克隆 var a='{name:"zhangsan"}' var b={name:"zhangsan"} 深克隆:物件的內容完成相同,但是物件地址值引用不同
深克隆實現方式:
將原有物件,先轉化為json格式字串 '{name:"zhangsan"}' JSON.stringify();
再將json格式字串轉為json物件 {name:"zhangsan"} JSON.parse();
注意我們組裝資料要動態顯示,所以我們要json資料進行封裝
分析:如何實現這種效果,首先我們上次規格選項的點選的基礎上,在新增已給方法,createItemList ()這個方法主要是組裝我們需要的資料,通過深克隆,實現資料的收集類似於這種:
specList:[{"attributeName":"網路","attributeValue":["移動3G"]},{"attributeName":"機身記憶體","attributeValue":["16G"]}]
前臺程式碼實現:
//基於陣列中物件的值 獲取該物件返回 //[{"attributeName":"網路","attributeValue":["移動3G","移動4G"]}] //list是傳入的列表陣列 key是attributeName 是根據傳入值決定的 value 是對應的值,比如網路 $scope.getObjectByKey = function (list,key,value) { for (var i=0;i<list.length;i++){ //存在物件時 if (list[i][key]==value){ return list[i]; } } //不存在則返回空值 return null; }
//建立item列表 $scope.createItemList=function () { //初始化item物件 $scope.entity.itemList=[{spec:{},price:0,num:99999,status:"1",isDefault:"0"}]; //勾選規格結果集 //specList:[{"attributeName":"網路","attributeValue":["移動3G"]},{"attributeName":"機身記憶體","attributeValue":["16G"]}] var specList =$scope.entity.tbGoodsDesc.specificationItems; //如果規格選項全部取消 if(specList.length==0){ $scope.entity.itemList=[]; } for(var i=0;i<specList.length;i++){ //動態為列表中物件的spec屬性賦值方法,動態生成sku列表 行列方法 $scope.entity.itemList=addColumn($scope.entity.itemList,specList[i].attributeName,specList[i].attributeValue); } } addColumn=function (itemList,specName,specOptions) { var newList=[]; //動態組裝itemList列表中的spec物件資料 參考資料示例:{"機身記憶體":"16G","網路":"聯通3G"} for(var i=0;i<itemList.length;i++){ //獲取litmList列表物件 //{spec:{},price:0,num:99999,status:1,isDefault:0} var item = itemList[i]; //遍歷勾選的規格選項陣列 for(var j=0;j<specOptions.length;j++){ //基於深克隆實現構建item物件操作 var newItem = JSON.parse(JSON.stringify(item)); newItem.spec[specName]=specOptions[j]; newList.push(newItem); } } return newList; }
儲存的後臺實現:
我們上次已經實現了goods表,goodsDesc表,然後我們這次完成組裝tb_item表
//組裝tb_item表
List<TbItem> items = goods.getItems();
for (TbItem item : items) {
/*後臺組裝
`title` varchar(100) NOT NULL COMMENT '商品標題', // 商品名稱(SPU名稱)+ 商品規格選項名稱 中間以空格隔開
`image` varchar(2000) DEFAULT NULL COMMENT '商品圖片', // 從 tb_goods_desc item_images中獲取第一張
`categoryId` bigint(10) NOT NULL COMMENT '所屬類目,葉子類目', //三級分類id
`create_time` datetime NOT NULL COMMENT '建立時間',
`update_time` datetime NOT NULL COMMENT '更新時間',
`goods_id` bigint(20) DEFAULT NULL,
`seller_id` varchar(30) DEFAULT NULL,
//以下欄位作用:
`category` varchar(200) DEFAULT NULL, //三級分類名稱
`brand` varchar(100) DEFAULT NULL,//品牌名稱
`seller` varchar(200) DEFAULT NULL,//商家店鋪名稱*/
String title = tbGoods.getGoodsName();
//{"機身記憶體":"16G","網路":"聯通3G"}
String spec = item.getSpec();
Map<String,String> specMap = JSON.parseObject(spec,Map.class);
for (String s : specMap.keySet()) {
title+=" "+specMap.get(s);
}
item.setTitle(title);
//image資料組裝
String itemImages = tbGoodsDesc.getItemImages();
List<Map> imageList = JSON.parseArray(itemImages,Map.class);
//image資料組裝
//[{"color":"紅色","url":"http://192.168.25.133/group1/M00/00/01/wKgZhVmHINKADo__AAjlKdWCzvg874.jpg"},
// {"color":"黑色","url":"http://192.168.25.133/group1/M00/00/01/wKgZhVmHINyAQAXHAAgawLS1G5Y136.jpg"}]
if (imageList!=null&&imageList.size()>0){
String image = (String) imageList.get(0).get("url");
item.setImage(image);
}
//三級分類id
item.setCategoryid(tbGoods.getCategory1Id());
//時間設定
item.setCreateTime(new Date());
item.setUpdateTime(new Date());
//goods_id
item.setGoodsId(tbGoods.getId());
// selller_id
item.setSellerId(tbGoods.getSellerId());
//三級分類名稱
//注入三個mappper
TbItemCat tbItemCat = itemCatMapper.selectByPrimaryKey(tbGoods.getCategory3Id());
item.setCategory(tbItemCat.getName());
TbBrand tbBrand = brandMapper.selectByPrimaryKey(tbGoods.getBrandId());
item.setBrand(tbBrand.getName());
TbSeller tbSeller = sellerMapper.selectByPrimaryKey(tbGoods.getSellerId());
item.setSeller(tbSeller.getNickName());
itemMapper.insert(item);
}
3.完成規格的啟用
主要適用一個新的angularjs表示式來體現
is_enable_spec=0 不啟用規格
is_enable_spec=1 啟用規格
業務:庫存業務。商品銷售不受庫存影響。可以稍微延遲發貨時間,商家趕緊去補貨即可。
注意,後臺程式碼:不開啟規格,那麼頁面的資料無法提交,我們就要後臺自己組裝資料,通過if判斷是否啟用規格,我們將公共的能提交的程式碼封裝起來
程式碼:
} else {
//為不啟用規格
TbItem item = new TbItem();
item.setTitle(tbGoods.getGoodsName());
setItemValue(tbGoods, tbGoodsDesc, item);
/*為啟用規格時,組裝頁面需要提交的資料
`spec` varchar(200) DEFAULT NULL,
`price` decimal(20,2) NOT NULL COMMENT '商品價格,單位為:元',
`num` int(10) NOT NULL COMMENT '庫存數量',
`status` varchar(1) NOT NULL COMMENT '商品狀態,1-正常,2-下架,3-刪除',
`is_default` varchar(1) DEFAULT NULL,*/
item.setSpec("{}");
item.setPrice(tbGoods.getPrice());
item.setNum(9999);
item.setStatus("1");
item.setIsDefault("1");
itemMapper.insert(item);
}
}
//抽取item工具的方法
private void setItemValue(TbGoods tbGoods, TbGoodsDesc tbGoodsDesc, TbItem item) {
//image資料組裝
String itemImages = tbGoodsDesc.getItemImages();
List<Map> imageList = JSON.parseArray(itemImages, Map.class);
//image資料組裝
//[{"color":"紅色","url":"http://192.168.25.133/group1/M00/00/01/wKgZhVmHINKADo__AAjlKdWCzvg874.jpg"},
// {"color":"黑色","url":"http://192.168.25.133/group1/M00/00/01/wKgZhVmHINyAQAXHAAgawLS1G5Y136.jpg"}]
if (imageList != null && imageList.size() > 0) {
String image = (String) imageList.get(0).get("url");
item.setImage(image);
}
//三級分類id
item.setCategoryid(tbGoods.getCategory1Id());
//時間設定
item.setCreateTime(new Date());
item.setUpdateTime(new Date());
//goods_id
item.setGoodsId(tbGoods.getId());
// selller_id
item.setSellerId(tbGoods.getSellerId());
//三級分類名稱
//注入三個mappper
TbItemCat tbItemCat = itemCatMapper.selectByPrimaryKey(tbGoods.getCategory3Id());
item.setCategory(tbItemCat.getName());
TbBrand tbBrand = brandMapper.selectByPrimaryKey(tbGoods.getBrandId());
item.setBrand(tbBrand.getName());
TbSeller tbSeller = sellerMapper.selectByPrimaryKey(tbGoods.getSellerId());
item.setSeller(tbSeller.getNickName());
}
效果:
二、運營商的對商品的稽核
1.運營商的列表展示
思路:和商家一樣,包括欄位也是一樣的,所以直接複製就行
2.列表的批量稽核
後臺實現:
//批量稽核
@Override
public void deleteStatus(Long[] ids, String status) {
for (Long id : ids) {
TbGoods tbGoods = goodsMapper.selectByPrimaryKey(id);
tbGoods.setAuditStatus(status);
goodsMapper.updateByPrimaryKey(tbGoods);
}
}
前臺實現:
service層
//批量稽核
this.updateStatus=function(ids,status){
return $http.get('../goods/updateStatus.do?ids='+ids+"&status="+status);
}
controller層
//批量稽核
$scope.updateStatus=function(status){
//獲取選中的複選框
goodsService.updateStatus( $scope.selectIds ,status).success(
function(response){
if(response.success){
$scope.reloadList();//重新整理列表
$scope.selectIds=[];//注意清空
}
}
);
}
3.批量刪除功能的實現
思路:和上面的實現思路也是一樣的,在service中也是先查,在設定,後跟新,因為刪除的是邏輯的刪除,所以我們執行更新就行
邏輯刪除
更新is_delete欄位,預設為null時,未刪除商品,刪除時,需要將is_delete設定為1
效果:
三、商家對商品的管理
1.完成商品的展示
思路:修改search方法,通過條件查詢,商家的id查詢,注意修改 條件查詢的值為等值查詢而不是模糊查詢
2.修改商品稽核狀態
0 未稽核 1 已稽核 2 稽核未通過 3 關閉
['未稽核','已稽核','稽核未通過','關閉']
//定義商品狀態的陣列
$scope.status=['未稽核','已稽核','稽核未通過','關閉'];
<span>
{{status[pojo.auditStatus]}}
</span>
3.
商家後臺查詢未稽核商品列表
商品列表中展示分類名稱實現方式:
1、後臺組裝資料,根據分類id查詢分類名稱,返回前臺展示頁面。 缺點:效能較差
2、將商品分類列表資料一次性載入到頁面。將分類id作為分類列表索引值,將分類名稱作為該索引位置的內容。 缺點:消耗瀏覽器儲存空間
1 2
時間和空間 成本。
程式碼:
//定義查詢所有分類的方法
//注意初始化分類列表
$scope.itemCatList=[];
$scope.selectItemList=function () {
itemCatService.findAll().success(function (response) {
/* ["","手機","電腦" ...]*/
//定義記錄分類列表的資料
for(var i = 0;i<response.length;i++){
//分類物件
$scope.itemCatList[response[i].id]=response[i].name;
}
})
}
頁面展示:
<td>{{itemCatList[pojo.category1Id]}}</td>
<td>{{itemCatList[pojo.category2Id]}}</td>
<td>{{itemCatList[pojo.category3Id]}}</td>
注意:在頁面剛載入的時候就進行初始化ng-init="selectItemList()
4.商品的上下架
思路:也是跟新一個欄位id_marketable 0 為下架 1為上架
is_marketable=1 上架
is_marketable=0 下架
注意:稽核通過的商品才能上下架
後臺程式碼:
/**
* 批量上下架
* @param ids
* @return
*/
@RequestMapping("/updateIsMarketable")
public Result updateIsMarketable(Long [] ids,String isMarketable){
try {
goodsService.updateIsMarketable(ids,isMarketable);
return new Result(true, "上下架成功");
}
catch (RuntimeException e) {
e.printStackTrace();
return new Result(false,e.getMessage());
}catch (Exception e){
return new Result(false, "上下架失敗");
}
}
service層
@Override
public void updateIsMarketable(Long[] ids, String isMarketable) {
for (Long id : ids) {
TbGoods tbGoods = goodsMapper.selectByPrimaryKey(id);
//只有稽核通過的才能上下架
if ("1".equals(tbGoods.getAuditStatus())){
tbGoods.setIsMarketable(isMarketable);
goodsMapper.updateByPrimaryKey(tbGoods);
}else{
throw new RuntimeException("只有稽核通過的才能上下架");
}
}
}
前臺程式碼:
controller層
//定義商品的上下架
$scope.isMarketable=['下架','上架'];
//批量上下架
$scope.updateIsMarketable=function(isMarketable){
//獲取選中的複選框
goodsService.updateIsMarketable( $scope.selectIds,isMarketable ).success(
function(response){
if(response.success){
$scope.reloadList();//重新整理列表
$scope.selectIds=[];//清空記錄id的陣列
}else{
alert(response.message);
}
}
);
}
service層
//批量上下架
this.updateIsMarketable=function(ids,isMarketable){
return $http.get('../goods/updateIsMarketable.do?ids='+ids+"&isMarketable="+isMarketable);
}
效果:
四、常見錯誤
1.變數初始化問題
這個就是定義了方法,而沒有初始化變數
//注意初始化分類列表
$scope.itemCatList=[];
五、總結
js物件資料組裝技巧:
克隆
要基於js克隆方式,實現spec物件組裝。
淺克隆 var a={name:"zhangsan"} var b=a; 宣告變數,重新賦予已經存在的變數。
深克隆 var a='{name:"zhangsan"}' var b={name:"zhangsan"} 深克隆:物件的內容完成相同,但是物件地址值引用不同
深克隆實現方式:
將原有物件,先轉化為json格式字串 '{name:"zhangsan"}' JSON.stringify();
再將json格式字串轉為json物件 {name:"zhangsan"} JSON.parse();
item中status=1時,代表 啟用, status=0時,代表未啟用
item中isDefault=1時,代表 是預設商品, isDefault=0時,代表非預設商品
angularjs的指令
ng-true-value="1" ng-false-value="0"