开发项目的标准流程应该有:需求分析、可行性分析、总体设计、详细设计等。
在具体开发时,应该先创建数据库、数据表,然后创建项目进行开发。
创建mall_pms数据库:
CREATE DATABASE mall_pms;在此数据库中创建数据表:
-- 数据库:mall_pms
--表:创建数据表
drop table if exists pms_spu;
create table pms_spu
(
id bigint unsigned not null comment '记录id',
name varchar(50) default null comment 'SPU名称',
type_number varchar(50) default null comment 'SPU编号',
title varchar(255) default null comment '标题',
description varchar(255) default null comment '简介',
list_price decimal(10, 2) default null comment '价格(显示在列表中)',
stock int unsigned default 0 comment '当前库存(冗余)',
stock_threshold int unsigned default 0 comment '库存预警阈值(冗余)',
unit varchar(50) default null comment '计件单位',
brand_id bigint unsigned default null comment '品牌id',
brand_name varchar(50) default null comment '品牌名称(冗余)',
category_id bigint unsigned default null comment '类别id',
category_name varchar(50) default null comment '类别名称(冗余)',
attribute_template_id bigint unsigned default null comment '属性模版id',
album_id bigint unsigned default null comment '相册id',
pictures varchar(500) default null comment '组图URLs,使用JSON数组表示',
keywords varchar(255) default null comment '关键词列表,各关键词使用英文的逗号分隔',
tags varchar(255) default null comment '标签列表,各标签使用英文的逗号分隔,原则上最多3个',
sales int unsigned default 0 comment '销量(冗余)',
comment_count int unsigned default 0 comment '买家评论数量总和(冗余)',
positive_comment_count int unsigned default 0 comment '买家好评数量总和(冗余)',
sort tinyint unsigned default 0 comment '自定义排序序号',
is_deleted tinyint unsigned default 0 comment '是否标记为删除,1=已删除,0=未删除',
is_published tinyint unsigned default 0 comment '是否上架(发布),1=已上架,0=未上架(下架)',
is_new_arrival tinyint unsigned default 0 comment '是否新品,1=新品,0=非新品',
is_recommend tinyint unsigned default 0 comment '是否推荐,1=推荐,0=不推荐',
is_checked tinyint unsigned default 0 comment '是否已审核,1=已审核,0=未审核',
check_user varchar(50) default null comment '审核人(冗余)',
gmt_check datetime default null comment '审核通过时间(冗余)',
gmt_create datetime default null comment '数据创建时间',
gmt_modified datetime default null comment '数据最后修改时间',
primary key (id)
) comment 'SPU(Standard Product Unit)' charset utf8mb4;
-- 数据表
pms_album;//相册
pms_picture;//图片
pms_category;//分类
pms_brand;//品牌
pms_brand_category;//品牌与分类关系
pms_attribute;
pms_attribute_template;
pms_spu;
pms_spu_detail;
pms_sku;
pms_sku_specification;Project:项目 / 工程
Module:模块
在较大规范的项目开发中,可能会把代码区分为多个Module进行开发,即某1个Project中可能有多个Module,各Module允许独立开发、独立运行,并且,可以在Project或某个父级Module中,对其子级的依赖项等部分的内容进行统筹管理。
需要注意:并不是每个Module都是可以独立运行的,在开发实践中,如果某些代码是多个Module都需要使用的,可以把这部分代码写在专门的Module中,其它Module依赖这个专门的Module即可(就像添加某个依赖项一样)。
当使用Project结合多个Module开发时,Project基本上不需要编写任何与功能相关的代码,只需要配置好pom.xml即可。
使用Spring Boot创建向导来创建Project,相关参数:
由于Project并不需要运行(也不能运行),对于各依赖项,只需要管理即可,并不需要实际的添加!
在Project的pom.xml中,如果直接使用
通常,会将依赖项的代码放在
为了在当前pom.xml集中管理各依赖的版本号,推荐在
1.8
2.5.9
2.2.2
8.0.28
1.18.22
另外,由于Project并不实现的编写需要运行的功能代码,更不会直接编译打包或运行,所以,在Project的pom.xml中的
最后,把Project的src全部删除!
应该在Project下创建某个Module,用于开发商品管理相关的功能,为了便于过渡到后续将要使用的微服务架构(需要将业务逻辑层的接口声明在专门的Module中,便于被其它微服务Module依赖),商品管理的Module需要再细分为2个,所以,目前项目结构应该是:
cgb2202-csmall-server[project]
csmall-product
csmall-product-webapi
csmall-product-service当存在Project和Module的“父子关系”或后续可能存在Module与Module的“父子关系”时,应该在父级的pom.xml中添加:
pom 并且,在父级的pom.xml中,通过
csmall-product
创建Module的操作步骤为:在cgb2202-csmall-server下创建csmall-product,再在csmall-product下创建csmall-product-webapi。
当Project和各Module创建出来后,调整各pom.xml文件。
最终,cgb2202-csmall-server根级Project的pom.xml为:
<?xml version="1.0" encoding="UTF-8"?>
4.0.0
org.springframework.boot
spring-boot-starter-parent
2.5.9
cn.celinf
csmall-server
0.0.1-SNAPSHOT
pom
csmall-product
1.8
2.5.9
2.2.2
8.0.28
1.18.22
1.1.20
org.springframework.boot
spring-boot-starter-validation
${spring-boot.version}
org.springframework.boot
spring-boot-starter-web
${spring-boot.version}
org.mybatis.spring.boot
mybatis-spring-boot-starter
${mybatis-boot.version}
mysql
mysql-connector-java
runtime
${mysql.version}
org.projectlombok
lombok
true
${lombok.version}
com.alibaba
druid
${druid.version}
org.springframework.boot
spring-boot-starter-test
test
${spring-boot.version}
根据已经添加的数据表,目前此项目中需要管理的数据类型大致有:
首先,需要分析以上数据类型的开发先后顺序,部分数据之间存在依赖与被依赖关系,例如SKU肯定归属于某个SPU,在开发时,必须先开发SPU,再开发SKU,同理,必须先开发品牌,才可以开发SPU……
根据分析,必要的顺序为:(品牌 | 类别 | (相册 >>> 图片) | (属性模板 >>> 属性)) >>> SPU >>> SKU。
分析出必要顺序后,存在一些不需要严格区分顺序的数据类型,例如以上的品牌和类型,实际的开发顺序可以是先简单、后复杂,例如品牌数据通常比类别数据更加简单,则应该先开发品牌数据的管理,再开发类别数据的管理。
本次学习过程中,先开发类别,至于品牌,可自行课后完成!
当确定了需要处理类别的数据时,需要规划需要开发此数据的哪些管理功能,例如:添加类别、启用类别、禁用类别、修改类别的基本信息、根据id查询、根据parent_id查询列表……
以上管理类别数据的功能,开发顺序应该是:添加类别 >>> (根据id查询 | 根据parent_id查询列表) >>> (启用类别 | 禁用类别 | 修改类别的基本信息)
由于目前是本项目第1次开发持久层,必须先完成必要的配置,包括:
应该先在csmall-product-webapi的src\main\resources下创建application-dev.properties文件,在其中添加连接数据库的参数:
# 连接数据库的配置信息
spring.datasource.url=jdbc:mysql://localhost:3306/mall_pms?useUnicode=true&characterEncoding=utf-8&serverTimezone=Asia/Shanghai
spring.datasource.username=root
spring.datasource.password=root然后,在application.properties中添加配置:
# 激活Profile配置
spring.profiles.active=dev
# 连接数据库的固定配置
spring.datasource.type=com.alibaba.druid.pool.DruidDataSource
# Mybatis的XML文件位置
mybatis.mapper-locations=classpath:mapper/*.xml然后,需要在src/main/resources下自行创建mapper文件夹,与以上配置对应。
还需要自行创建配置类,用于配置Mapper接口文件所在的包,则在cn.tedu.csmall.product.webapi下创建mapper子包,并在cn.tedu.csmall.product.webapi下创建config.MybatisConfiguration配置类,进行配置:
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.context.annotation.Configuration;
@Configuration
@MapperScan("cn.tedu.csmall.product.webapi.mapper")
public class MybatisConfiguration {
}完成后,可以尝试测试连接到数据库,则在src/test/java下找到默认即存在的测试类,编写并执行测试:
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import javax.sql.DataSource;
@SpringBootTest
class CsmallProductWebapiApplicationTests {
@Autowired
DataSource dataSource;
@Test
void contextLoads() {
}
@Test
void testConnection() {
Assertions.assertDoesNotThrow(() -> {
dataSource.getConnection();
});
}
}执行整个测试,应该能够通过测试。
此次需要执行的是“增加类别”,其数据操作的本质是向pms_category表中插入数据,需要执行的SQL语句大致是:
insert into pms_category (除了id以外的字段的列表) values (与字段列表匹配的各字段值);具体表现为:
insert into pms_category (name, parent_id, depth, keywords, sort, icon, enable, is_parent, is_display, gmt_create, gmt_modified) values (值列表);另外,还应该考虑在“添加类别”时,是否需要执行相关的检查,因为这些检查很可能是通过查询数据库来实现的,则在持久层也需要实现这些功能!
暂定规则“类别的名称不允许重复”,则后续在Service层进行处理时,应该先根据尝试添加的类别的名称进行查询,如果查询结果为null,表示此名称对应的类别尚不存在,将允许添加,如果查询结果不为null,表示此名称对应的类别已经存在,将不允许添加!
要实现以上检查的效果,需要执行的SQL语句可以是:
select * from pms_category where name=?;或者:
select count(*) from pms_category where name=?;以上2种做法,第1种做法的查询效率相对较低,或者说性能消耗略高,第2种做法的查询性能消耗更低,但是,第1种做法的查询可能具有复用性,而第2种做法的查询的复用性相对较低。
暂定可以使用以上第1种做法。
在插入数据之前,需要先创建“类别”对应的实体类型,而这个实体类型不能直接创建在csmall-product-webapi模块中,而是应该创建在另一个新的模块中,以便于其它各模块都可以使用到相同的实体类型(例如商品的实体类型,在商品管理模块和订单管理模块中都将需要使用)。
在Project中创建新的子模块csmall-pojo,创建出来后,需要:
然后,在cn.tedu.csmall.pojo.entity包下创建Category类:
import lombok.Data;
import java.io.Serializable;
import java.time.LocalDateTime;
@Data
public class Category implements Serializable {
private Long id;
private String name;
private Long parentId;
private Integer depth;
private String keywords;
private Integer sort;
private String icon;
private Integer enable;
private Integer isParent;
private Integer isDisplay;
private LocalDateTime gmtCreate;
private LocalDateTime gmtModified;
}为了实现其它Module可以依赖csmall-pojo,应该先在根级Project的pom.xml中对csmall-pojo实现依赖管理:
0.0.1-SNAPSHOT
cn.tedu
csmall-pojo
${csmall.version}
然后,在csmall-product-webapi的pom.xml中添加依赖:
cn.tedu
csmall-pojo
至此,在csmall-product-webapi中就已经成功的依赖了csmall-pojo,可以理解为csmall-pojo已经成为csmall-product-webapi的一部分。
在cn.tedu.csmall.product.webapi.mapper包下创建CategoryMapper接口,并在接口上添加@Repository注解(主要是避免IntelliJ IDEA在自动装配时的误判错误),并在接口中添加抽象方法:
/**
* 处理“类别”数据的持久层接口
*/
@Repository
public interface CategoryMapper {
/**
* 插入“类别”数据
* @param category 类别
* @return 受影响的行数
*/
int insert(Category category);
// 查询--待定
}从其它位置(或项目)中复制粘贴CategoryMapper.xml到csmall-product-webapi的src/main/resources/mapper下。
关于CategoryMapper.xml文件的配置:
<?xml version="1.0" encoding="UTF-8" ?>
insert into pms_category (
name, parent_id, depth, keywords, sort,
icon, enable, is_parent, is_display, gmt_create,
gmt_modified
) values (
#{name}, #{parentId}, #{depth}, #{keywords}, #{sort},
#{icon}, #{enable}, #{isParent}, #{isDisplay}, #{gmtCreate},
#{gmtModified}
)
先在src/test下创建resources文件夹,并在此文件夹中创建truncate.sql脚本,此脚本将用于重置数据表:
truncate pms_category;然后,在src/test/java的根包下创建mapper.CategoryMapperTests,编写并执行测试:
import cn.tedu.csmall.pojo.entity.Category;
import static org.junit.jupiter.api.Assertions.*;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.jdbc.Sql;
@SpringBootTest
public class CategoryMapperTests {
@Autowired
CategoryMapper mapper;
@Test
@Sql("classpath:truncate.sql")
public void testInsert() {
// 测试数据
Category category = new Category();
category.setName("手机");
// 断言不会抛出异常
assertDoesNotThrow(() -> {
int rows = mapper.insert(category);
assertEquals(1, rows);
assertEquals(1, category.getId());
});
}
}学习记录,如有侵权请联系删除
| 留言与评论(共有 0 条评论) “” |