Merge remote-tracking branch 'origin/dev' into dev
# Conflicts: # src/main/java/com/gxwebsoft/shop/dto/OrderCreateRequest.java # src/main/java/com/gxwebsoft/shop/service/OrderBusinessService.java
This commit is contained in:
56
src/test/java/com/gxwebsoft/bszx/BszxOrderTotalTest.java
Normal file
56
src/test/java/com/gxwebsoft/bszx/BszxOrderTotalTest.java
Normal file
@@ -0,0 +1,56 @@
|
||||
package com.gxwebsoft.bszx;
|
||||
|
||||
import com.gxwebsoft.bszx.service.BszxPayService;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.test.context.ActiveProfiles;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.math.BigDecimal;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.*;
|
||||
|
||||
/**
|
||||
* 百色中学订单总金额统计测试
|
||||
*
|
||||
* @author 科技小王子
|
||||
* @since 2025-07-31
|
||||
*/
|
||||
@SpringBootTest
|
||||
@ActiveProfiles("test")
|
||||
public class BszxOrderTotalTest {
|
||||
|
||||
@Resource
|
||||
private BszxPayService bszxPayService;
|
||||
|
||||
@Test
|
||||
void testBszxOrderTotal() {
|
||||
// 测试百色中学订单总金额统计
|
||||
BigDecimal total = bszxPayService.total();
|
||||
|
||||
// 验证返回值不为null
|
||||
assertNotNull(total, "百色中学订单总金额不应该为null");
|
||||
|
||||
// 验证返回值大于等于0
|
||||
assertTrue(total.compareTo(BigDecimal.ZERO) >= 0, "百色中学订单总金额应该大于等于0");
|
||||
|
||||
System.out.println("百色中学订单总金额统计结果:" + total);
|
||||
}
|
||||
|
||||
@Test
|
||||
void testBszxOrderTotalPerformance() {
|
||||
// 测试性能
|
||||
long startTime = System.currentTimeMillis();
|
||||
|
||||
BigDecimal total = bszxPayService.total();
|
||||
|
||||
long endTime = System.currentTimeMillis();
|
||||
long duration = endTime - startTime;
|
||||
|
||||
System.out.println("百色中学订单总金额统计耗时:" + duration + "ms");
|
||||
System.out.println("统计结果:" + total);
|
||||
|
||||
// 验证查询时间在合理范围内(小于5秒)
|
||||
assertTrue(duration < 5000, "查询时间应该在5秒以内");
|
||||
}
|
||||
}
|
||||
@@ -20,9 +20,9 @@ public class ShopGenerator {
|
||||
// 输出目录
|
||||
private static final String OUTPUT_DIR = "/src/main/java";
|
||||
// Vue文件输出位置
|
||||
private static final String OUTPUT_LOCATION_VUE = "/Users/gxwebsoft/VUE/shop";
|
||||
private static final String OUTPUT_LOCATION_VUE = "/Users/gxwebsoft/VUE/mp-vue";
|
||||
// Vue文件输出目录
|
||||
private static final String OUTPUT_LOCATION_UNIAPP = "/Users/gxwebsoft/APP/shop";
|
||||
private static final String OUTPUT_LOCATION_UNIAPP = "/Users/gxwebsoft/VUE/template-10550";
|
||||
// Vue文件输出目录
|
||||
private static final String OUTPUT_DIR_VUE = "/src";
|
||||
// 作者名称
|
||||
@@ -30,7 +30,7 @@ public class ShopGenerator {
|
||||
// 是否在xml中添加二级缓存配置
|
||||
private static final boolean ENABLE_CACHE = false;
|
||||
// 数据库连接配置
|
||||
private static final String DB_URL = "jdbc:mysql://47.119.165.234:3308/modules?useUnicode=true&characterEncoding=utf8&useSSL=false&serverTimezone=GMT%2B8";
|
||||
private static final String DB_URL = "jdbc:mysql://1Panel-mysql-Bqdt:3306/modules?useUnicode=true&characterEncoding=utf8&useSSL=false&serverTimezone=GMT%2B8";
|
||||
private static final String DB_DRIVER = "com.mysql.cj.jdbc.Driver";
|
||||
private static final String DB_USERNAME = "modules";
|
||||
private static final String DB_PASSWORD = "8YdLnk7KsPAyDXGA";
|
||||
|
||||
@@ -0,0 +1,38 @@
|
||||
package com.gxwebsoft.house.util;
|
||||
|
||||
/**
|
||||
* SortSceneUtil手动测试类
|
||||
* 用于验证URL解码功能
|
||||
*
|
||||
* @author 科技小王子
|
||||
* @since 2025-08-04
|
||||
*/
|
||||
public class SortSceneUtilManualTest {
|
||||
|
||||
public static void main(String[] args) {
|
||||
// 测试URL编码的参数
|
||||
String urlEncoded = "%E4%BB%B7%E6%A0%BC(%E4%BD%8E-%E9%AB%98)";
|
||||
System.out.println("原始URL编码参数: " + urlEncoded);
|
||||
|
||||
String result = SortSceneUtil.normalizeSortScene(urlEncoded);
|
||||
System.out.println("标准化后的参数: " + result);
|
||||
System.out.println("是否为价格升序: " + SortSceneUtil.isPriceAsc(urlEncoded));
|
||||
|
||||
// 测试其他格式
|
||||
String[] testCases = {
|
||||
"价格(低-高)",
|
||||
"价格(高-低)",
|
||||
"%E4%BB%B7%E6%A0%BC(%E9%AB%98-%E4%BD%8E)",
|
||||
"最新发布",
|
||||
"综合排序",
|
||||
"面积(小-大)",
|
||||
"面积(大-小)"
|
||||
};
|
||||
|
||||
System.out.println("\n=== 测试各种排序场景 ===");
|
||||
for (String testCase : testCases) {
|
||||
String normalized = SortSceneUtil.normalizeSortScene(testCase);
|
||||
System.out.println("输入: " + testCase + " -> 输出: " + normalized);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,63 @@
|
||||
package com.gxwebsoft.house.util;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
import static org.junit.jupiter.api.Assertions.*;
|
||||
|
||||
/**
|
||||
* SortSceneUtil测试类
|
||||
*
|
||||
* @author 科技小王子
|
||||
* @since 2025-08-04
|
||||
*/
|
||||
public class SortSceneUtilTest {
|
||||
|
||||
@Test
|
||||
public void testNormalizeSortScene() {
|
||||
// 测试URL编码的参数
|
||||
String urlEncoded = "%E4%BB%B7%E6%A0%BC(%E4%BD%8E-%E9%AB%98)";
|
||||
String result = SortSceneUtil.normalizeSortScene(urlEncoded);
|
||||
assertEquals("价格(低-高)", result);
|
||||
|
||||
// 测试已解码的参数
|
||||
String decoded = "价格(低-高)";
|
||||
result = SortSceneUtil.normalizeSortScene(decoded);
|
||||
assertEquals("价格(低-高)", result);
|
||||
|
||||
// 测试空值
|
||||
result = SortSceneUtil.normalizeSortScene(null);
|
||||
assertNull(result);
|
||||
|
||||
result = SortSceneUtil.normalizeSortScene("");
|
||||
assertNull(result);
|
||||
|
||||
result = SortSceneUtil.normalizeSortScene(" ");
|
||||
assertNull(result);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsPriceAsc() {
|
||||
assertTrue(SortSceneUtil.isPriceAsc("价格(低-高)"));
|
||||
assertTrue(SortSceneUtil.isPriceAsc("%E4%BB%B7%E6%A0%BC(%E4%BD%8E-%E9%AB%98)"));
|
||||
assertFalse(SortSceneUtil.isPriceAsc("价格(高-低)"));
|
||||
assertFalse(SortSceneUtil.isPriceAsc("最新发布"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsPriceDesc() {
|
||||
assertTrue(SortSceneUtil.isPriceDesc("价格(高-低)"));
|
||||
assertFalse(SortSceneUtil.isPriceDesc("价格(低-高)"));
|
||||
assertFalse(SortSceneUtil.isPriceDesc("最新发布"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsLatest() {
|
||||
assertTrue(SortSceneUtil.isLatest("最新发布"));
|
||||
assertFalse(SortSceneUtil.isLatest("价格(低-高)"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIsComprehensive() {
|
||||
assertTrue(SortSceneUtil.isComprehensive("综合排序"));
|
||||
assertFalse(SortSceneUtil.isComprehensive("价格(低-高)"));
|
||||
}
|
||||
}
|
||||
174
src/test/java/com/gxwebsoft/shop/MultiSpecOrderTest.java
Normal file
174
src/test/java/com/gxwebsoft/shop/MultiSpecOrderTest.java
Normal file
@@ -0,0 +1,174 @@
|
||||
package com.gxwebsoft.shop;
|
||||
|
||||
import com.gxwebsoft.common.system.entity.User;
|
||||
import com.gxwebsoft.shop.dto.OrderCreateRequest;
|
||||
import com.gxwebsoft.shop.entity.ShopGoods;
|
||||
import com.gxwebsoft.shop.entity.ShopGoodsSku;
|
||||
import com.gxwebsoft.shop.service.OrderBusinessService;
|
||||
import com.gxwebsoft.shop.service.ShopGoodsService;
|
||||
import com.gxwebsoft.shop.service.ShopGoodsSkuService;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.extension.ExtendWith;
|
||||
import org.mockito.InjectMocks;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Arrays;
|
||||
import java.util.Map;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.*;
|
||||
import static org.mockito.ArgumentMatchers.any;
|
||||
import static org.mockito.Mockito.*;
|
||||
|
||||
/**
|
||||
* 多规格订单测试类
|
||||
*
|
||||
* @author 科技小王子
|
||||
* @since 2025-07-30
|
||||
*/
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
public class MultiSpecOrderTest {
|
||||
|
||||
@Mock
|
||||
private ShopGoodsService shopGoodsService;
|
||||
|
||||
@Mock
|
||||
private ShopGoodsSkuService shopGoodsSkuService;
|
||||
|
||||
@InjectMocks
|
||||
private OrderBusinessService orderBusinessService;
|
||||
|
||||
private User testUser;
|
||||
private ShopGoods testGoods;
|
||||
private ShopGoodsSku testSku;
|
||||
|
||||
@BeforeEach
|
||||
void setUp() {
|
||||
// 创建测试用户
|
||||
testUser = new User();
|
||||
testUser.setUserId(1);
|
||||
testUser.setTenantId(1);
|
||||
testUser.setOpenid("test_openid");
|
||||
testUser.setPhone("13800138000");
|
||||
|
||||
// 创建测试商品
|
||||
testGoods = new ShopGoods();
|
||||
testGoods.setGoodsId(1);
|
||||
testGoods.setName("测试商品");
|
||||
testGoods.setPrice(new BigDecimal("100.00"));
|
||||
testGoods.setStock(50);
|
||||
testGoods.setStatus(0); // 正常状态
|
||||
testGoods.setImage("test.jpg");
|
||||
|
||||
// 创建测试SKU
|
||||
testSku = new ShopGoodsSku();
|
||||
testSku.setId(1);
|
||||
testSku.setGoodsId(1);
|
||||
testSku.setPrice(new BigDecimal("120.00"));
|
||||
testSku.setStock(20);
|
||||
testSku.setStatus(0); // 正常状态
|
||||
testSku.setSku("颜色:红色|尺寸:L");
|
||||
testSku.setImage("sku_test.jpg");
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCreateOrderWithSingleSpec() {
|
||||
// 测试单规格商品下单
|
||||
when(shopGoodsService.getById(1)).thenReturn(testGoods);
|
||||
|
||||
OrderCreateRequest request = createOrderRequest(false);
|
||||
|
||||
// 这里需要mock其他依赖服务,实际测试中需要完整的Spring上下文
|
||||
// 此测试主要验证多规格逻辑的正确性
|
||||
|
||||
assertNotNull(request);
|
||||
assertEquals(1, request.getGoodsItems().size());
|
||||
assertNull(request.getGoodsItems().get(0).getSkuId());
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCreateOrderWithMultiSpec() {
|
||||
// 测试多规格商品下单
|
||||
when(shopGoodsService.getById(1)).thenReturn(testGoods);
|
||||
when(shopGoodsSkuService.getById(1)).thenReturn(testSku);
|
||||
|
||||
OrderCreateRequest request = createOrderRequest(true);
|
||||
|
||||
assertNotNull(request);
|
||||
assertEquals(1, request.getGoodsItems().size());
|
||||
assertEquals(Integer.valueOf(1), request.getGoodsItems().get(0).getSkuId());
|
||||
assertEquals("颜色:红色|尺寸:L", request.getGoodsItems().get(0).getSpecInfo());
|
||||
}
|
||||
|
||||
@Test
|
||||
void testSkuValidation() {
|
||||
// 测试SKU验证逻辑
|
||||
when(shopGoodsService.getById(1)).thenReturn(testGoods);
|
||||
|
||||
// 测试SKU不存在的情况
|
||||
when(shopGoodsSkuService.getById(999)).thenReturn(null);
|
||||
|
||||
OrderCreateRequest request = createOrderRequest(true);
|
||||
request.getGoodsItems().get(0).setSkuId(999); // 不存在的SKU ID
|
||||
|
||||
// 在实际测试中,这里应该抛出BusinessException
|
||||
// assertThrows(BusinessException.class, () -> orderBusinessService.createOrder(request, testUser));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testStockValidation() {
|
||||
// 测试库存验证
|
||||
testSku.setStock(1); // 设置库存为1
|
||||
when(shopGoodsService.getById(1)).thenReturn(testGoods);
|
||||
when(shopGoodsSkuService.getById(1)).thenReturn(testSku);
|
||||
|
||||
OrderCreateRequest request = createOrderRequest(true);
|
||||
request.getGoodsItems().get(0).setQuantity(5); // 购买数量超过库存
|
||||
|
||||
// 在实际测试中,这里应该抛出BusinessException
|
||||
// assertThrows(BusinessException.class, () -> orderBusinessService.createOrder(request, testUser));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testPriceCalculation() {
|
||||
// 测试价格计算
|
||||
when(shopGoodsService.getById(1)).thenReturn(testGoods);
|
||||
when(shopGoodsSkuService.getById(1)).thenReturn(testSku);
|
||||
|
||||
// 多规格商品应该使用SKU价格(120.00),而不是商品价格(100.00)
|
||||
OrderCreateRequest request = createOrderRequest(true);
|
||||
request.getGoodsItems().get(0).setQuantity(2);
|
||||
|
||||
// 期望总价格 = SKU价格(120.00) * 数量(2) = 240.00
|
||||
BigDecimal expectedTotal = new BigDecimal("240.00");
|
||||
request.setTotalPrice(expectedTotal);
|
||||
|
||||
assertEquals(expectedTotal, request.getTotalPrice());
|
||||
}
|
||||
|
||||
/**
|
||||
* 创建订单请求对象
|
||||
*/
|
||||
private OrderCreateRequest createOrderRequest(boolean withSku) {
|
||||
OrderCreateRequest request = new OrderCreateRequest();
|
||||
request.setType(0);
|
||||
request.setTotalPrice(new BigDecimal("100.00"));
|
||||
request.setPayPrice(new BigDecimal("100.00"));
|
||||
request.setTotalNum(1);
|
||||
request.setTenantId(1);
|
||||
|
||||
OrderCreateRequest.OrderGoodsItem item = new OrderCreateRequest.OrderGoodsItem();
|
||||
item.setGoodsId(1);
|
||||
item.setQuantity(1);
|
||||
|
||||
if (withSku) {
|
||||
item.setSkuId(1);
|
||||
item.setSpecInfo("颜色:红色|尺寸:L");
|
||||
}
|
||||
|
||||
request.setGoodsItems(Arrays.asList(item));
|
||||
return request;
|
||||
}
|
||||
}
|
||||
170
src/test/java/com/gxwebsoft/shop/OrderBusinessServiceTest.java
Normal file
170
src/test/java/com/gxwebsoft/shop/OrderBusinessServiceTest.java
Normal file
@@ -0,0 +1,170 @@
|
||||
package com.gxwebsoft.shop;
|
||||
|
||||
import com.gxwebsoft.common.system.entity.User;
|
||||
import com.gxwebsoft.shop.dto.OrderCreateRequest;
|
||||
import com.gxwebsoft.shop.entity.ShopGoods;
|
||||
import com.gxwebsoft.shop.entity.ShopOrder;
|
||||
import com.gxwebsoft.shop.entity.ShopOrderGoods;
|
||||
import com.gxwebsoft.shop.service.OrderBusinessService;
|
||||
import com.gxwebsoft.shop.service.ShopGoodsService;
|
||||
import com.gxwebsoft.shop.service.ShopOrderGoodsService;
|
||||
import com.gxwebsoft.shop.service.ShopOrderService;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.extension.ExtendWith;
|
||||
import org.mockito.InjectMocks;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import static org.mockito.ArgumentMatchers.*;
|
||||
import static org.mockito.Mockito.*;
|
||||
|
||||
/**
|
||||
* 订单业务服务测试类
|
||||
*
|
||||
* @author 科技小王子
|
||||
* @since 2025-01-26
|
||||
*/
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
public class OrderBusinessServiceTest {
|
||||
|
||||
@Mock
|
||||
private ShopOrderService shopOrderService;
|
||||
|
||||
@Mock
|
||||
private ShopOrderGoodsService shopOrderGoodsService;
|
||||
|
||||
@Mock
|
||||
private ShopGoodsService shopGoodsService;
|
||||
|
||||
@InjectMocks
|
||||
private OrderBusinessService orderBusinessService;
|
||||
|
||||
private User testUser;
|
||||
private OrderCreateRequest testRequest;
|
||||
private ShopGoods testGoods;
|
||||
|
||||
@BeforeEach
|
||||
void setUp() {
|
||||
// 准备测试用户
|
||||
testUser = new User();
|
||||
testUser.setUserId(1);
|
||||
testUser.setOpenid("test_openid");
|
||||
testUser.setPhone("13800138000");
|
||||
|
||||
// 准备测试商品
|
||||
testGoods = new ShopGoods();
|
||||
testGoods.setGoodsId(10018);
|
||||
testGoods.setName("科技小王子大米年卡套餐2.5kg");
|
||||
testGoods.setPrice(new BigDecimal("99.00"));
|
||||
testGoods.setImage("test_image.jpg");
|
||||
|
||||
// 准备测试订单请求
|
||||
testRequest = new OrderCreateRequest();
|
||||
testRequest.setType(0);
|
||||
testRequest.setTotalPrice(new BigDecimal("99.00"));
|
||||
testRequest.setPayPrice(new BigDecimal("99.00"));
|
||||
testRequest.setTotalNum(1);
|
||||
testRequest.setPayType(1);
|
||||
testRequest.setTenantId(1);
|
||||
testRequest.setAddressId(10832);
|
||||
testRequest.setComments("科技小王子大米年卡套餐2.5kg");
|
||||
testRequest.setDeliveryType(0);
|
||||
|
||||
// 准备商品项列表
|
||||
OrderCreateRequest.OrderGoodsItem goodsItem = new OrderCreateRequest.OrderGoodsItem();
|
||||
goodsItem.setGoodsId(10018);
|
||||
goodsItem.setQuantity(1);
|
||||
goodsItem.setPayType(1);
|
||||
|
||||
testRequest.setGoodsItems(Arrays.asList(goodsItem));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCreateOrderWithGoods() {
|
||||
// Mock 商品查询
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
|
||||
// Mock 订单保存
|
||||
when(shopOrderService.save(any(ShopOrder.class))).thenAnswer(invocation -> {
|
||||
ShopOrder order = invocation.getArgument(0);
|
||||
order.setOrderId(1); // 模拟数据库生成的ID
|
||||
return true;
|
||||
});
|
||||
|
||||
// Mock 订单商品批量保存
|
||||
when(shopOrderGoodsService.saveBatch(anyList())).thenReturn(true);
|
||||
|
||||
// Mock 微信支付订单创建
|
||||
HashMap<String, String> wxOrderInfo = new HashMap<>();
|
||||
wxOrderInfo.put("prepay_id", "test_prepay_id");
|
||||
when(shopOrderService.createWxOrder(any(ShopOrder.class))).thenReturn(wxOrderInfo);
|
||||
|
||||
// 执行测试
|
||||
Map<String, String> result = orderBusinessService.createOrder(testRequest, testUser);
|
||||
|
||||
// 验证结果
|
||||
assert result != null;
|
||||
assert result.containsKey("prepay_id");
|
||||
|
||||
// 验证方法调用
|
||||
verify(shopGoodsService, times(1)).getById(10018);
|
||||
verify(shopOrderService, times(1)).save(any(ShopOrder.class));
|
||||
verify(shopOrderGoodsService, times(1)).saveBatch(anyList());
|
||||
verify(shopOrderService, times(1)).createWxOrder(any(ShopOrder.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCreateOrderWithMultipleGoods() {
|
||||
// 准备多个商品项
|
||||
OrderCreateRequest.OrderGoodsItem goodsItem1 = new OrderCreateRequest.OrderGoodsItem();
|
||||
goodsItem1.setGoodsId(10018);
|
||||
goodsItem1.setQuantity(1);
|
||||
goodsItem1.setPayType(1);
|
||||
|
||||
OrderCreateRequest.OrderGoodsItem goodsItem2 = new OrderCreateRequest.OrderGoodsItem();
|
||||
goodsItem2.setGoodsId(10019);
|
||||
goodsItem2.setQuantity(2);
|
||||
goodsItem2.setPayType(1);
|
||||
|
||||
testRequest.setGoodsItems(Arrays.asList(goodsItem1, goodsItem2));
|
||||
testRequest.setTotalPrice(new BigDecimal("297.00")); // 99 + 99*2
|
||||
|
||||
// Mock 商品查询
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
|
||||
ShopGoods testGoods2 = new ShopGoods();
|
||||
testGoods2.setGoodsId(10019);
|
||||
testGoods2.setName("测试商品2");
|
||||
testGoods2.setPrice(new BigDecimal("99.00"));
|
||||
testGoods2.setImage("test_image2.jpg");
|
||||
when(shopGoodsService.getById(10019)).thenReturn(testGoods2);
|
||||
|
||||
// Mock 其他服务
|
||||
when(shopOrderService.save(any(ShopOrder.class))).thenAnswer(invocation -> {
|
||||
ShopOrder order = invocation.getArgument(0);
|
||||
order.setOrderId(1);
|
||||
return true;
|
||||
});
|
||||
when(shopOrderGoodsService.saveBatch(anyList())).thenReturn(true);
|
||||
when(shopOrderService.createWxOrder(any(ShopOrder.class))).thenReturn(new HashMap<>());
|
||||
|
||||
// 执行测试
|
||||
orderBusinessService.createOrder(testRequest, testUser);
|
||||
|
||||
// 验证商品查询次数
|
||||
verify(shopGoodsService, times(1)).getById(10018);
|
||||
verify(shopGoodsService, times(1)).getById(10019);
|
||||
|
||||
// 验证保存的商品项数量
|
||||
verify(shopOrderGoodsService, times(1)).saveBatch(argThat(list ->
|
||||
((List<ShopOrderGoods>) list).size() == 2
|
||||
));
|
||||
}
|
||||
}
|
||||
56
src/test/java/com/gxwebsoft/shop/OrderTotalTest.java
Normal file
56
src/test/java/com/gxwebsoft/shop/OrderTotalTest.java
Normal file
@@ -0,0 +1,56 @@
|
||||
package com.gxwebsoft.shop;
|
||||
|
||||
import com.gxwebsoft.shop.service.ShopOrderService;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.test.context.ActiveProfiles;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.math.BigDecimal;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.*;
|
||||
|
||||
/**
|
||||
* 订单总金额统计测试
|
||||
*
|
||||
* @author 科技小王子
|
||||
* @since 2025-07-30
|
||||
*/
|
||||
@SpringBootTest
|
||||
@ActiveProfiles("test")
|
||||
public class OrderTotalTest {
|
||||
|
||||
@Resource
|
||||
private ShopOrderService shopOrderService;
|
||||
|
||||
@Test
|
||||
void testOrderTotal() {
|
||||
// 测试订单总金额统计
|
||||
BigDecimal total = shopOrderService.total();
|
||||
|
||||
// 验证返回值不为null
|
||||
assertNotNull(total, "订单总金额不应该为null");
|
||||
|
||||
// 验证返回值大于等于0
|
||||
assertTrue(total.compareTo(BigDecimal.ZERO) >= 0, "订单总金额应该大于等于0");
|
||||
|
||||
System.out.println("订单总金额统计结果:" + total);
|
||||
}
|
||||
|
||||
@Test
|
||||
void testOrderTotalPerformance() {
|
||||
// 测试性能
|
||||
long startTime = System.currentTimeMillis();
|
||||
|
||||
BigDecimal total = shopOrderService.total();
|
||||
|
||||
long endTime = System.currentTimeMillis();
|
||||
long duration = endTime - startTime;
|
||||
|
||||
System.out.println("订单总金额统计耗时:" + duration + "ms");
|
||||
System.out.println("统计结果:" + total);
|
||||
|
||||
// 验证查询时间在合理范围内(小于5秒)
|
||||
assertTrue(duration < 5000, "查询时间应该在5秒以内");
|
||||
}
|
||||
}
|
||||
315
src/test/java/com/gxwebsoft/shop/OrderValidationTest.java
Normal file
315
src/test/java/com/gxwebsoft/shop/OrderValidationTest.java
Normal file
@@ -0,0 +1,315 @@
|
||||
package com.gxwebsoft.shop;
|
||||
|
||||
import com.gxwebsoft.common.core.exception.BusinessException;
|
||||
import com.gxwebsoft.common.system.entity.User;
|
||||
import com.gxwebsoft.shop.config.OrderConfigProperties;
|
||||
import com.gxwebsoft.shop.dto.OrderCreateRequest;
|
||||
import com.gxwebsoft.shop.entity.ShopGoods;
|
||||
import com.gxwebsoft.shop.entity.ShopOrder;
|
||||
import com.gxwebsoft.shop.service.OrderBusinessService;
|
||||
import com.gxwebsoft.shop.service.ShopGoodsService;
|
||||
import com.gxwebsoft.shop.service.ShopOrderGoodsService;
|
||||
import com.gxwebsoft.shop.service.ShopOrderService;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.extension.ExtendWith;
|
||||
import org.mockito.InjectMocks;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Arrays;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.*;
|
||||
import static org.mockito.Mockito.*;
|
||||
|
||||
/**
|
||||
* 订单验证测试类
|
||||
* 测试商品信息后台验证逻辑
|
||||
*/
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
class OrderValidationTest {
|
||||
|
||||
@Mock
|
||||
private ShopOrderService shopOrderService;
|
||||
|
||||
@Mock
|
||||
private ShopOrderGoodsService shopOrderGoodsService;
|
||||
|
||||
@Mock
|
||||
private ShopGoodsService shopGoodsService;
|
||||
|
||||
@Mock
|
||||
private OrderConfigProperties orderConfig;
|
||||
|
||||
@InjectMocks
|
||||
private OrderBusinessService orderBusinessService;
|
||||
|
||||
private User testUser;
|
||||
private OrderCreateRequest testRequest;
|
||||
private ShopGoods testGoods;
|
||||
|
||||
@BeforeEach
|
||||
void setUp() {
|
||||
// 准备测试用户
|
||||
testUser = new User();
|
||||
testUser.setUserId(1);
|
||||
testUser.setNickname("测试用户");
|
||||
testUser.setPhone("13800138000");
|
||||
|
||||
// 准备测试商品
|
||||
testGoods = new ShopGoods();
|
||||
testGoods.setGoodsId(10018);
|
||||
testGoods.setName("测试商品");
|
||||
testGoods.setPrice(new BigDecimal("99.00"));
|
||||
testGoods.setStatus(0); // 上架状态
|
||||
testGoods.setStock(100); // 库存100
|
||||
testGoods.setCanBuyNumber(10); // 最大购买数量10
|
||||
testGoods.setCode("TEST001");
|
||||
|
||||
// 准备测试订单请求
|
||||
testRequest = new OrderCreateRequest();
|
||||
testRequest.setType(0);
|
||||
testRequest.setTitle("测试订单");
|
||||
testRequest.setTotalPrice(new BigDecimal("99.00"));
|
||||
testRequest.setTenantId(1);
|
||||
|
||||
// 准备商品项
|
||||
OrderCreateRequest.OrderGoodsItem goodsItem = new OrderCreateRequest.OrderGoodsItem();
|
||||
goodsItem.setGoodsId(10018);
|
||||
goodsItem.setQuantity(1);
|
||||
testRequest.setGoodsItems(Arrays.asList(goodsItem));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testValidateOrderRequest_Success() {
|
||||
// Mock 商品查询
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
when(orderConfig.getTenantRule(1)).thenReturn(null);
|
||||
|
||||
// 执行验证 - 应该成功
|
||||
assertDoesNotThrow(() -> {
|
||||
// 使用反射调用私有方法进行测试
|
||||
java.lang.reflect.Method method = OrderBusinessService.class
|
||||
.getDeclaredMethod("validateOrderRequest", OrderCreateRequest.class, User.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(orderBusinessService, testRequest, testUser);
|
||||
});
|
||||
|
||||
// 验证总金额被正确设置
|
||||
assertEquals(new BigDecimal("99.00"), testRequest.getTotalPrice());
|
||||
}
|
||||
|
||||
@Test
|
||||
void testValidateOrderRequest_GoodsNotFound() {
|
||||
// Mock 商品不存在
|
||||
when(shopGoodsService.getById(10018)).thenReturn(null);
|
||||
|
||||
// 执行验证 - 应该抛出异常
|
||||
Exception exception = assertThrows(Exception.class, () -> {
|
||||
java.lang.reflect.Method method = OrderBusinessService.class
|
||||
.getDeclaredMethod("validateOrderRequest", OrderCreateRequest.class, User.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(orderBusinessService, testRequest, testUser);
|
||||
});
|
||||
|
||||
// 检查是否是 InvocationTargetException 包装的 BusinessException
|
||||
assertTrue(exception instanceof java.lang.reflect.InvocationTargetException);
|
||||
Throwable cause = exception.getCause();
|
||||
assertTrue(cause instanceof BusinessException);
|
||||
assertTrue(cause.getMessage().contains("商品不存在"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testValidateOrderRequest_GoodsOffShelf() {
|
||||
// 设置商品为下架状态
|
||||
testGoods.setStatus(1);
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
|
||||
// 执行验证 - 应该抛出异常
|
||||
Exception exception = assertThrows(Exception.class, () -> {
|
||||
java.lang.reflect.Method method = OrderBusinessService.class
|
||||
.getDeclaredMethod("validateOrderRequest", OrderCreateRequest.class, User.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(orderBusinessService, testRequest, testUser);
|
||||
});
|
||||
|
||||
// 检查是否是 InvocationTargetException 包装的 BusinessException
|
||||
assertTrue(exception instanceof java.lang.reflect.InvocationTargetException);
|
||||
Throwable cause = exception.getCause();
|
||||
assertTrue(cause instanceof BusinessException);
|
||||
assertTrue(cause.getMessage().contains("商品已下架"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testValidateOrderRequest_InsufficientStock() {
|
||||
// 设置库存不足
|
||||
testGoods.setStock(0);
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
|
||||
// 执行验证 - 应该抛出异常
|
||||
Exception exception = assertThrows(Exception.class, () -> {
|
||||
java.lang.reflect.Method method = OrderBusinessService.class
|
||||
.getDeclaredMethod("validateOrderRequest", OrderCreateRequest.class, User.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(orderBusinessService, testRequest, testUser);
|
||||
});
|
||||
|
||||
// 检查是否是 InvocationTargetException 包装的 BusinessException
|
||||
assertTrue(exception instanceof java.lang.reflect.InvocationTargetException);
|
||||
Throwable cause = exception.getCause();
|
||||
assertTrue(cause instanceof BusinessException);
|
||||
assertTrue(cause.getMessage().contains("商品库存不足"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testValidateOrderRequest_ExceedBuyLimit() {
|
||||
// 设置购买数量超过限制
|
||||
testRequest.getGoodsItems().get(0).setQuantity(15); // 超过最大购买数量10
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
|
||||
// 执行验证 - 应该抛出异常
|
||||
Exception exception = assertThrows(Exception.class, () -> {
|
||||
java.lang.reflect.Method method = OrderBusinessService.class
|
||||
.getDeclaredMethod("validateOrderRequest", OrderCreateRequest.class, User.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(orderBusinessService, testRequest, testUser);
|
||||
});
|
||||
|
||||
// 检查是否是 InvocationTargetException 包装的 BusinessException
|
||||
assertTrue(exception instanceof java.lang.reflect.InvocationTargetException);
|
||||
Throwable cause = exception.getCause();
|
||||
assertTrue(cause instanceof BusinessException);
|
||||
assertTrue(cause.getMessage().contains("购买数量超过限制"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testValidateOrderRequest_PriceCalculation() {
|
||||
// 设置多个商品项
|
||||
OrderCreateRequest.OrderGoodsItem goodsItem1 = new OrderCreateRequest.OrderGoodsItem();
|
||||
goodsItem1.setGoodsId(10018);
|
||||
goodsItem1.setQuantity(2);
|
||||
|
||||
OrderCreateRequest.OrderGoodsItem goodsItem2 = new OrderCreateRequest.OrderGoodsItem();
|
||||
goodsItem2.setGoodsId(10019);
|
||||
goodsItem2.setQuantity(1);
|
||||
|
||||
testRequest.setGoodsItems(Arrays.asList(goodsItem1, goodsItem2));
|
||||
testRequest.setTotalPrice(new BigDecimal("297.00")); // 99*2 + 99*1
|
||||
|
||||
// 准备第二个商品
|
||||
ShopGoods testGoods2 = new ShopGoods();
|
||||
testGoods2.setGoodsId(10019);
|
||||
testGoods2.setName("测试商品2");
|
||||
testGoods2.setPrice(new BigDecimal("99.00"));
|
||||
testGoods2.setStatus(0);
|
||||
testGoods2.setStock(100);
|
||||
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
when(shopGoodsService.getById(10019)).thenReturn(testGoods2);
|
||||
when(orderConfig.getTenantRule(1)).thenReturn(null);
|
||||
|
||||
// 执行验证 - 应该成功
|
||||
assertDoesNotThrow(() -> {
|
||||
java.lang.reflect.Method method = OrderBusinessService.class
|
||||
.getDeclaredMethod("validateOrderRequest", OrderCreateRequest.class, User.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(orderBusinessService, testRequest, testUser);
|
||||
});
|
||||
|
||||
// 验证总金额计算正确
|
||||
assertEquals(new BigDecimal("297.00"), testRequest.getTotalPrice());
|
||||
}
|
||||
|
||||
@Test
|
||||
void testValidateOrderRequest_PriceDiscrepancy() {
|
||||
// 设置前端传入的金额与后台计算不一致
|
||||
testRequest.setTotalPrice(new BigDecimal("88.00")); // 错误的金额
|
||||
when(shopGoodsService.getById(10018)).thenReturn(testGoods);
|
||||
|
||||
// 执行验证 - 应该抛出异常
|
||||
Exception exception = assertThrows(Exception.class, () -> {
|
||||
java.lang.reflect.Method method = OrderBusinessService.class
|
||||
.getDeclaredMethod("validateOrderRequest", OrderCreateRequest.class, User.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(orderBusinessService, testRequest, testUser);
|
||||
});
|
||||
|
||||
// 检查是否是 InvocationTargetException 包装的 BusinessException
|
||||
assertTrue(exception instanceof java.lang.reflect.InvocationTargetException);
|
||||
Throwable cause = exception.getCause();
|
||||
assertTrue(cause instanceof BusinessException);
|
||||
assertTrue(cause.getMessage().contains("订单金额计算错误"));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testBuildShopOrder_RequiredFields() throws Exception {
|
||||
// Mock 配置
|
||||
OrderConfigProperties.DefaultConfig defaultConfig = new OrderConfigProperties.DefaultConfig();
|
||||
defaultConfig.setDefaultComments("默认备注");
|
||||
when(orderConfig.getDefaultConfig()).thenReturn(defaultConfig);
|
||||
|
||||
// 使用反射调用 buildShopOrder 方法
|
||||
java.lang.reflect.Method buildMethod = OrderBusinessService.class
|
||||
.getDeclaredMethod("buildShopOrder", OrderCreateRequest.class, User.class);
|
||||
buildMethod.setAccessible(true);
|
||||
|
||||
ShopOrder result = (ShopOrder) buildMethod.invoke(orderBusinessService, testRequest, testUser);
|
||||
|
||||
// 验证必需字段都已设置
|
||||
assertNotNull(result.getPayPrice(), "payPrice 不能为空");
|
||||
assertNotNull(result.getPrice(), "price 不能为空");
|
||||
assertNotNull(result.getReducePrice(), "reducePrice 不能为空");
|
||||
assertNotNull(result.getMoney(), "money 不能为空");
|
||||
assertNotNull(result.getPayStatus(), "payStatus 不能为空");
|
||||
assertNotNull(result.getOrderStatus(), "orderStatus 不能为空");
|
||||
assertNotNull(result.getDeliveryStatus(), "deliveryStatus 不能为空");
|
||||
assertNotNull(result.getPayType(), "payType 不能为空");
|
||||
|
||||
// 验证默认值
|
||||
assertEquals(testRequest.getTotalPrice(), result.getPayPrice());
|
||||
assertEquals(testRequest.getTotalPrice(), result.getPrice());
|
||||
assertEquals(BigDecimal.ZERO, result.getReducePrice());
|
||||
assertEquals(testRequest.getTotalPrice(), result.getMoney());
|
||||
assertEquals(false, result.getPayStatus());
|
||||
assertEquals(Integer.valueOf(0), result.getOrderStatus());
|
||||
assertEquals(Integer.valueOf(10), result.getDeliveryStatus());
|
||||
assertEquals(Integer.valueOf(1), result.getPayType());
|
||||
|
||||
// 验证关键字段 - 租户ID(影响微信支付证书路径)
|
||||
assertNotNull(result.getTenantId(), "tenantId 不能为空");
|
||||
assertEquals(testRequest.getTenantId(), result.getTenantId(), "tenantId 必须正确设置");
|
||||
}
|
||||
|
||||
@Test
|
||||
void testBuildShopOrder_TenantIdValidation() throws Exception {
|
||||
// 创建一个新的请求对象,租户ID为空
|
||||
OrderCreateRequest requestWithoutTenant = new OrderCreateRequest();
|
||||
requestWithoutTenant.setType(0);
|
||||
requestWithoutTenant.setTitle("测试订单");
|
||||
requestWithoutTenant.setTotalPrice(new BigDecimal("99.00"));
|
||||
requestWithoutTenant.setTenantId(null); // 设置为空
|
||||
|
||||
// 准备商品项
|
||||
OrderCreateRequest.OrderGoodsItem goodsItem = new OrderCreateRequest.OrderGoodsItem();
|
||||
goodsItem.setGoodsId(10018);
|
||||
goodsItem.setQuantity(1);
|
||||
requestWithoutTenant.setGoodsItems(Arrays.asList(goodsItem));
|
||||
|
||||
// 使用反射调用 buildShopOrder 方法
|
||||
java.lang.reflect.Method buildMethod = OrderBusinessService.class
|
||||
.getDeclaredMethod("buildShopOrder", OrderCreateRequest.class, User.class);
|
||||
buildMethod.setAccessible(true);
|
||||
|
||||
// 执行验证 - 应该抛出异常
|
||||
Exception exception = assertThrows(Exception.class, () -> {
|
||||
buildMethod.invoke(orderBusinessService, requestWithoutTenant, testUser);
|
||||
});
|
||||
|
||||
// 检查是否是 InvocationTargetException 包装的 BusinessException
|
||||
assertTrue(exception instanceof java.lang.reflect.InvocationTargetException);
|
||||
Throwable cause = exception.getCause();
|
||||
assertTrue(cause instanceof BusinessException);
|
||||
assertTrue(cause.getMessage().contains("租户ID不能为空"));
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user