提交 02b9ad5a authored 作者: 梁业锦's avatar 梁业锦 💬

- 商品导入相关逻辑

上级 b535bbfe
......@@ -25,6 +25,9 @@ public class TbProductMissEntity implements Serializable {
* 失败类型【1:已存在】【2:出现了异常】
*/
private Integer missType;
private String missReason;
/**
* 页数(每250个)
*/
......@@ -99,4 +102,12 @@ public class TbProductMissEntity implements Serializable {
public Date getCreateTime() {
return createTime;
}
public String getMissReason() {
return missReason;
}
public void setMissReason(String missReason) {
this.missReason = missReason;
}
}
......@@ -60,12 +60,14 @@
`id`,
`product_id`,
`miss_type`,
`miss_reason`,
`page_size`,
`create_time`)
values(
#{id},
#{productId},
#{missType},
#{missReason},
#{pageSize},
#{createTime})
</insert>
......@@ -92,4 +94,4 @@
</foreach>
</delete>
</mapper>
\ No newline at end of file
</mapper>
package test;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import java.util.concurrent.*;
/**
* 并发测试
*
* @author 爱酱油不爱醋
* @version 1.0
*/
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = {"classpath*:/applicationContext-test.xml"})
public class ConcurrencyApi {
private final int corePoolSize = 15;
private final int maximumPoolSize = 35;
@Test
public void test() {
ExecutorService executor = Executors.newCachedThreadPool();
int i = 0;
while (true) {
RunningTest test = new RunningTest(i);
executor.submit(test);
System.out.println("正在执行的线程编号:" + i);
i++;
}
}
}
......@@ -79,12 +79,9 @@ public class ImpartCode {
*/
@Test
public void goImport() {
List<String> list = Arrays.asList(/*"Men", "Women", "Children", "Afri Home", "Cosmetics",*/ "Hair", "Sportswear", "Electronics");
List<String> list = Arrays.asList("Men", "Women", "Children", "Afri Home", "Cosmetics", "Hair", "Sportswear", "Electronics");
for (String product_type : list) {
// 记录商品数量
int productCount = 0;
// 记录页数
int pageSize = 1;
// 测试数量
String link = "https://mollykitty.myshopify.com/admin/api/" + VERSION + "/products/count.json" + "?product_type=" + product_type;
String data = HttpRequest.get(link)
......@@ -94,7 +91,7 @@ public class ImpartCode {
// 导入请求
link = "https://mollykitty.myshopify.com/admin/api/" + VERSION + "/products.json" + "?product_type=" + product_type + "&limit=250";
// 开始第一次导入商品
importMethod(link, pageSize, productCount);
importMethod(link);
// 获取第一次循环的请求头
String headerLink = HttpRequest.get(link)
.header("Authorization", "Basic N2YwZTA0OGFjNDAxNmI5MzU3YmIxZWIyMjE3ZTQyMDE6MWM5N2ExMjIyYzViNDBlMDU5N2M4MTZjNmRmZWNhYzA=")
......@@ -107,9 +104,8 @@ public class ImpartCode {
}
// 无限导入
while (true) {
// 导入商品
productCount++;
importMethod(headerLink, pageSize, productCount);
importMethod(headerLink);
// 获取下一页的链接
try {
......@@ -117,7 +113,6 @@ public class ImpartCode {
.header("Authorization", "Basic N2YwZTA0OGFjNDAxNmI5MzU3YmIxZWIyMjE3ZTQyMDE6MWM5N2ExMjIyYzViNDBlMDU5N2M4MTZjNmRmZWNhYzA=")
.execute().header("link")
.split(",")[1];
Console.error(headerLink);
headerLink = headerLink.substring(2, headerLink.indexOf(">"));
} catch (Exception e) {
// 死循环的终点为获取下一页链接抛出数组越界异常
......@@ -132,10 +127,8 @@ public class ImpartCode {
* 商品导入处理
*
* @param link 请求链接
* @param pageSize 正在导入的页数
* @param productCount 正在导入的商品数量
*/
private void importMethod(String link, int pageSize, int productCount) {
private void importMethod(String link) {
// 请求
String data = HttpRequest.get(link)
.header("Authorization", "Basic N2YwZTA0OGFjNDAxNmI5MzU3YmIxZWIyMjE3ZTQyMDE6MWM5N2ExMjIyYzViNDBlMDU5N2M4MTZjNmRmZWNhYzA=")
......@@ -148,34 +141,62 @@ public class ImpartCode {
int threadCount = 0;
for (int i = 0; i < productsArr.size(); i++) {
JSONObject productsObj = productsArr.getJSONObject(i);
productCount++;
Console.log("当前正在导入的商品个数为:" + productCount);
// 商品主体信息的商品 id
String itemId = IdUtil.simpleUUID();
// 复用的日期
Date date = new Date();
// 商品的平台 id
String id = productsObj.getString("id");
// 查询该商品的 id 是否已保存
if (tbCfStationItemDao.queryByCode(id) != null) {
System.err.println("已存在的商品,跳过导入的商品id为:" + id);
// 跳过循环
continue;
}
threadCount ++;
// 线程任务
int finalThreadCount = threadCount;
threadCount++;
Runnable runnable = () -> {
try {
// 用于记录 option 的属性名
// 商品详情
int optionNum = 0;
// 下方商品主体信息需要的商品属性,以"/"隔开
StringBuilder optionBuilder = new StringBuilder();
StringBuilder imageBuilder = new StringBuilder();
JSONArray imagesArr = productsObj.getJSONArray("images");
for (int j = 0; j < imagesArr.size(); j++) {
JSONObject imageObj = imagesArr.getJSONObject(j);
// 上传图片
String skuSrc = imageObj.getString("src");
InputStream skuInputStream = getImageStream(skuSrc);
byte[] skuBytes = toByteArray(skuInputStream);
String url = OssUtil.upload(skuBytes, id + "_sku_" + j + ".jpg", "zion");
// 拼接富文本的 HTML
imageBuilder.append("<p><img src=\"")
.append(url).append("\" title=\"")
.append(IdUtil.randomUUID()).append("_350x350")
.append(IdUtil.simpleUUID()).append(".jpg\"/></p>");
System.err.println("富文本图片内容:" + imageBuilder.toString());
}
TbCfItemDescEntity itemDescEntity = tbCfItemDescDao.queryObject(itemId);
if (itemDescEntity == null) {
itemDescEntity = new TbCfItemDescEntity();
itemDescEntity.setItemId(itemId);
itemDescEntity.setItemDesc(imageBuilder.toString());
itemDescEntity.setCreateTime(date);
tbCfItemDescDao.save(itemDescEntity);
}
// 上传图片获取主图
String src = productsObj.getJSONObject("image").getString("src");
InputStream inputStream = getImageStream(src);
byte[] bytes = toByteArray(inputStream);
String url = OssUtil.upload(bytes, id + "_station.jpg", "zion");
System.err.println("主图的链接为: " + url);
// 商品的属性
JSONArray optionsArr = productsObj.getJSONArray("options");
for (int j = 0; j < optionsArr.size(); j++) {
......@@ -237,8 +258,9 @@ public class ImpartCode {
tbCfCategoryDao.update(categoryEntity);
}
}
TbCfStationItemEntity tbCfStationItem = new TbCfStationItemEntity(); // 商品主体信息实体类
// 商品主体信息实体类
TbCfStationItemEntity tbCfStationItem = new TbCfStationItemEntity();
// 保存商品的变体数据
JSONArray variantsArr = productsObj.getJSONArray("variants");
......@@ -278,7 +300,7 @@ public class ImpartCode {
String product_type = productsObj.getString("product_type"); // 商品的分类
// 保存一级分类名
String goods_type_id = IdUtil.simpleUUID(); // 商品分类id
String goods_type_id = IdUtil.simpleUUID();
if (tbCfGoodstypeDao.queryByTitle(product_type) == null) { // 如果分类名已存在则不保存
TbCfGoodstypeEntity tbCfGoodstypeEntity = new TbCfGoodstypeEntity();
tbCfGoodstypeEntity.setGoodstypeId(goods_type_id);
......@@ -292,13 +314,11 @@ public class ImpartCode {
TbCfGoodstypeEntity tbCfGoodstypeEntity = tbCfGoodstypeDao.queryByTitle(product_type);
goods_type_id = tbCfGoodstypeEntity.getGoodstypeId();
}
// 级分类名
// 解析二三级分类名
String tags = "";
// 三级分类名
String three = "";
String[] s = productsObj.getString("tags").split(",");
Console.error(Arrays.toString(s));
for (String str : s) {
if (str.indexOf("#") == 0) {
tags = str.replaceAll("#", "");
......@@ -308,7 +328,7 @@ public class ImpartCode {
}
// 保存二级分类名
String goodsTwoId = IdUtil.simpleUUID(); // 商品二级分类id
String goodsTwoId = IdUtil.simpleUUID();
if (tbCfGoodstwotypeDao.queryTitle(tags) == null) {
TbCfGoodstwotypeEntity tbCfGoodstwotypeEntity = new TbCfGoodstwotypeEntity();
tbCfGoodstwotypeEntity.setGoodstwotypeId(goodsTwoId);
......@@ -321,7 +341,7 @@ public class ImpartCode {
}
// 保存三级分类名(品名)
String goodsThreeId = IdUtil.simpleUUID(); // 商品三级分类id
String goodsThreeId = IdUtil.simpleUUID();
if (tbCfDescripitonDao.queryByDescriptionName(three) == null) {
TbCfDescripitonEntity tbCfDescripitonEntity = new TbCfDescripitonEntity();
tbCfDescripitonEntity.setDescripitionId(goodsThreeId);
......@@ -348,48 +368,10 @@ public class ImpartCode {
tbCfStationItem.setItemDescritionId(goodsThreeId);
tbCfStationItem.setItemTags(product_type + "," + tags + "," + three);
tbCfStationItem.setItemTop("N");
// 上传图片
String src = productsObj.getJSONObject("image").getString("src");
InputStream inputStream = getImageStream(src);
byte[] bytes = toByteArray(inputStream);
String url = OssUtil.upload(bytes, id + "_station.jpg", "zion");
System.err.println("主图的链接为: " + url);
tbCfStationItem.setItemImg(url);
tbCfStationItem.setEnableFlag(2);
tbCfStationItemDao.save(tbCfStationItem);
// 商品的富文本描述
StringBuilder imageBuilder = new StringBuilder();
JSONArray imagesArr = productsObj.getJSONArray("images");
for (int j = 0; j < imagesArr.size(); j++) {
JSONObject imageObj = imagesArr.getJSONObject(j);
// 上传图片
src = imageObj.getString("src");
inputStream = getImageStream(src);
if (inputStream != null) {
bytes = toByteArray(inputStream);
}
url = OssUtil.upload(bytes, id + "_sku_" + j + ".jpg", "zion");
// 拼接富文本的 HTML
imageBuilder.append("<p><img src=\"")
.append(url).append("\" title=\"")
.append(IdUtil.randomUUID()).append("_350x350")
.append(IdUtil.simpleUUID()).append(".jpg\"/></p>");
System.err.println("富文本图片内容:" + imageBuilder.toString());
}
// 商品详情
TbCfItemDescEntity itemDescEntity = tbCfItemDescDao.queryObject(itemId);
if (itemDescEntity == null) {
itemDescEntity = new TbCfItemDescEntity();
itemDescEntity.setItemId(itemId);
itemDescEntity.setItemDesc(imageBuilder.toString());
itemDescEntity.setCreateTime(date);
tbCfItemDescDao.save(itemDescEntity);
}
System.err.println("线程号:" + finalThreadCount + ",已执行完成!");
} catch (Exception e) {
e.printStackTrace();
// 记录失败的产品记录
......@@ -397,11 +379,14 @@ public class ImpartCode {
tbProductMissEntity.setId(IdUtil.simpleUUID());
tbProductMissEntity.setProductId(id);
tbProductMissEntity.setMissType(2);
tbProductMissEntity.setPageSize(pageSize);
tbProductMissEntity.setMissReason(e.getMessage());
tbProductMissEntity.setPageSize(1);
tbProductMissEntity.setCreateTime(new Date());
tbProductMissDao.save(tbProductMissEntity);
}
System.err.println("线程号:" + finalThreadCount + ",已执行完成!");
};
// 提交任务执行
executorService.submit(runnable);
System.err.println("线程号:" + finalThreadCount + ",开始提交任务!");
......@@ -447,5 +432,5 @@ public class ImpartCode {
}
return output.toByteArray();
}
}
package test;
/**
* @author 爱酱油不爱醋
* @version 1.0
*/
public class RunningTest implements Runnable {
private int taskNum;
public RunningTest(int num) {
this.taskNum = num;
}
@Override
public void run() {
System.out.println("正在执行任务:" + taskNum);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("执行完毕:" + taskNum);
}
}
......@@ -67,7 +67,6 @@ public class TestApi {
*/
private final String API_URL = "https://mollykitty.myshopify.com/admin/api/" + VERSION + "/products.json";
@Test
public void host() {
String link = API_URL + "?limit=250&page_info=eyJwcm9kdWN0X3R5cGUiOiJXb21lbiIsImxhc3RfaWQiOjQ0OTc2Nzg5NTg2ODksImxhc3RfdmFsdWUiOiJDYXN1YWwgU2xpbSBTd2VhdGVycyIsImRpcmVjdGlvbiI6Im5leHQifQ";
......@@ -720,12 +719,6 @@ public class TestApi {
return output.toByteArray();
}
public static void main(String[] args) throws Exception {
String link = "https://cdn.shopify.com/s/files/1/0079/8330/0705/products/0_-9_aee971dc-5661-46bb-9d7e-11f0a3ee5b35.jpg?v=1580133539";
InputStream inputStream = getImageStream(link);
byte[] bytes = toByteArray(inputStream);
String url = OssUtil.upload(bytes, IdUtil.simpleUUID() + ".jpg", "zion");
System.out.println(url);
}
}
truncate from tb_category_template;
DELETE from tb_cf_category;
DELETE from tb_cf_goodstwotype;
DELETE from tb_cf_goodstype;
DELETE from tb_cf_item_desc;
DELETE from tb_cf_item_skus;
DELETE from tb_cf_option;
DELETE from tb_cf_station_item;
\ No newline at end of file
SELECT count(*) FROM tb_cf_station_item WHERE item_category = '2fe6be991b4941608c7ebcea7091288f';
SELECT count(*) FROM tb_cf_station_item WHERE item_category = '7c0d04650ad649fd9bf6b9476947c118';
SELECT count(*) FROM tb_cf_station_item WHERE item_category = '03f2d9ab2ea44893a27d54c280233c9f';
SELECT count(*) FROM tb_cf_station_item WHERE item_category = '59a9e2c64d2a4a1696a06045f39c0166';
SELECT count(*) FROM tb_cf_station_item WHERE item_category = 'f0100ca392074027bb99da3a93625d63';
SELECT count(*) FROM tb_cf_station_item WHERE item_category = 'a777a18b4fc4423082fa843231cfc7bc';
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论