基于SSM框架的校园二手商品交易平台 - 源码深度解析

JavaJavaScriptHTMLCSSSSM框架MavenMySQL
2026-02-088 浏览

文章摘要

本平台基于SSM(Spring + Spring MVC + MyBatis)框架构建,旨在为高校师生提供一个安全、便捷的校内二手商品交易环境。项目核心业务价值在于精准解决校园内信息不对称和交易信任度低的痛点。传统线下交易或大型电商平台无法有效过滤校外人员、保障交易安全,而本平台通过严格的校内身份验...

在高校环境中,二手商品交易具有巨大的市场潜力和实际需求。传统的线下交易模式存在信息不对称、交易效率低下、安全性无法保障等问题,而大型电商平台又无法有效区分校内用户,导致交易环境复杂化。校园闲置交易引擎应运而生,它通过严格的校内身份验证机制,构建了一个封闭而安全的交易环境,有效解决了校园二手交易的核心痛点。

该系统采用经典的B/S架构,基于SSM(Spring + Spring MVC + MyBatis)框架构建,实现了高内聚低耦合的设计理念。Spring框架作为整个系统的核心,通过控制反转(IoC)容器统一管理业务对象,利用面向切面编程(AOP)处理事务管理、日志记录等横切关注点。Spring MVC负责Web请求的分发与控制,实现清晰的MVC分离架构。数据持久化层采用MyBatis框架,通过灵活的XML配置实现对象关系映射,同时保留了对SQL的精细控制能力。

前端技术栈采用JSP作为视图层模板,结合JSTL标签库进行数据渲染,使用jQuery处理页面交互逻辑。项目采用Maven进行依赖管理,确保第三方库版本的统一性。数据库选用MySQL 5.7,通过合理的表结构设计和索引优化保障系统性能。

数据库设计深度解析

数据库设计是系统稳定性的基石,本项目通过22张表的精心设计,构建了完整的业务数据模型。以下重点分析几个核心表的设计亮点:

商品信息表(product)设计分析:

CREATE TABLE `product` (
  `id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
  `productno` varchar(255) DEFAULT NULL COMMENT '商品编号',
  `productname` varchar(255) DEFAULT NULL COMMENT '商品名称',
  `filename` varchar(255) DEFAULT NULL COMMENT '文件名',
  `price` decimal(10,2) DEFAULT NULL COMMENT '价格',
  `tprice` decimal(10,2) DEFAULT NULL COMMENT '特价价格',
  `fid` varchar(255) DEFAULT NULL COMMENT '父分类ID',
  `sid` varchar(255) DEFAULT NULL COMMENT '子分类ID',
  `content` text DEFAULT NULL COMMENT '内容',
  `delstatus` varchar(255) DEFAULT NULL COMMENT '删除状态',
  `issj` varchar(255) DEFAULT NULL COMMENT '是否上架',
  `istj` varchar(255) DEFAULT NULL COMMENT '是否特价',
  `saver` varchar(255) DEFAULT NULL COMMENT '上传者',
  `productid` varchar(255) DEFAULT NULL COMMENT '商品ID',
  `leibie` varchar(255) DEFAULT NULL COMMENT '类别',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=135 DEFAULT CHARSET=utf8 COMMENT='商品信息表'

该表设计体现了良好的业务抽象能力。价格字段采用decimal类型,精确到小数点后两位,避免浮点数运算误差。delstatusissjistj等状态字段采用varchar类型,便于扩展多种状态。商品描述使用text类型,支持大段文字内容。分类设计采用父子ID结构,实现多级分类管理。

订单信息表(ordermsg)的复杂业务建模:

CREATE TABLE `ordermsg` (
  `id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
  `ddno` varchar(255) DEFAULT NULL COMMENT '订单号',
  `memberid` varchar(255) DEFAULT NULL COMMENT '会员ID',
  `productid` varchar(255) DEFAULT NULL COMMENT '商品ID',
  `num` int(11) DEFAULT NULL COMMENT '数量',
  `total` double(255,2) DEFAULT NULL COMMENT '总计',
  `fkstatus` varchar(255) DEFAULT NULL COMMENT '付款状态',
  `shstatus` varchar(11) DEFAULT NULL COMMENT '审核状态',
  `addr` varchar(255) DEFAULT NULL COMMENT '地址',
  `savetime` varchar(255) DEFAULT NULL COMMENT '保存时间',
  `delstatus` varchar(255) DEFAULT NULL COMMENT '删除状态',
  `shfs` varchar(255) DEFAULT NULL COMMENT '配送方式',
  `zffs` varchar(255) DEFAULT NULL COMMENT '支付方式',
  `saver` varchar(255) DEFAULT NULL COMMENT '上传者',
  `isdd` varchar(255) DEFAULT NULL COMMENT '是否订单',
  `fid` varchar(255) DEFAULT NULL COMMENT '父订单ID',
  `goodsid` varchar(255) DEFAULT NULL COMMENT '商品ID',
  `goodstype` varchar(255) DEFAULT NULL COMMENT '商品类型',
  `remark` varchar(255) DEFAULT NULL COMMENT '备注',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=47 DEFAULT CHARSET=utf8 COMMENT='订单信息表'

订单表的设计充分考虑了电商业务的复杂性。通过fid字段实现父子订单关系,支持拆分订单场景。多种状态字段(fkstatusshstatusdelstatus)完整跟踪订单生命周期。shfs(配送方式)和zffs(支付方式)字段为后续扩展留有余地。时间字段采用varchar存储,便于灵活格式化显示。

核心功能实现深度解析

商品管理与发布系统

商品管理是平台的核心功能,采用分层架构实现。实体类设计简洁明了:

public class Product {
    private int id;
    private String productno;
    private String productname;
    private String filename;
    private BigDecimal price;
    private BigDecimal tprice;
    private String fid;
    private String sid;
    private String content;
    private String delstatus;
    private String issj;
    private String istj;
    private String saver;
    private String productid;
    private String leibie;
    
    // Getter和Setter方法
    public int getId() { return id; }
    public void setId(int id) { this.id = id; }
    // ... 其他getter/setter方法
}

商品发布功能通过Spring MVC控制器处理表单提交:

@Controller
@RequestMapping("/product")
public class ProductController {
    
    @Autowired
    private ProductService productService;
    
    @RequestMapping("/publish")
    public String publishProduct(Product product, 
                               MultipartFile file, 
                               HttpServletRequest request) {
        // 文件上传处理
        if (!file.isEmpty()) {
            String filename = file.getOriginalFilename();
            String path = request.getSession().getServletContext()
                         .getRealPath("/upload/");
            File destFile = new File(path + filename);
            file.transferTo(destFile);
            product.setFilename(filename);
        }
        
        // 设置商品状态
        product.setDelstatus("0"); // 未删除
        product.setIssj("1"); // 上架状态
        product.setSaver(getCurrentUser(request));
        
        productService.saveProduct(product);
        return "redirect:/product/list";
    }
    
    @RequestMapping("/list")
    public String productList(@RequestParam(defaultValue = "1") int page,
                             HttpServletRequest request) {
        PageInfo<Product> pageInfo = productService.getProductList(page, 10);
        request.setAttribute("pageInfo", pageInfo);
        return "product/list";
    }
}

商品发布界面

商品发布界面设计直观易用,支持图片上传、价格设置、分类选择等完整功能。通过MyBatis的动态SQL实现灵活的商品查询:

<!-- ProductMapper.xml -->
<select id="selectByCondition" parameterType="map" resultType="Product">
    SELECT * FROM product 
    WHERE delstatus = '0' AND issj = '1'
    <if test="productname != null and productname != ''">
        AND productname LIKE CONCAT('%', #{productname}, '%')
    </if>
    <if test="fid != null and fid != ''">
        AND fid = #{fid}
    </if>
    <if test="minPrice != null">
        AND price >= #{minPrice}
    </if>
    <if test="maxPrice != null">
        AND price <= #{maxPrice}
    </if>
    ORDER BY 
    <choose>
        <when test="sort == 'price_asc'">price ASC</when>
        <when test="sort == 'price_desc'">price DESC</when>
        <when test="sort == 'time_desc'">id DESC</when>
        <otherwise>id DESC</otherwise>
    </choose>
    LIMIT #{start}, #{pageSize}
</select>

购物车与订单管理系统

购物车功能采用Session存储临时数据,订单管理则持久化到数据库。订单生成的业务逻辑复杂,需要处理库存校验、价格计算等多个环节:

@Service
@Transactional
public class OrderService {
    
    @Autowired
    private OrderDAO orderDAO;
    
    @Autowired
    private ProductDAO productDAO;
    
    public String createOrder(OrderDTO orderDTO, HttpServletRequest request) {
        // 1. 生成订单号
        String orderNo = generateOrderNo();
        
        // 2. 验证商品库存
        for (OrderItemDTO item : orderDTO.getItems()) {
            Product product = productDAO.findById(item.getProductId());
            if (product.getStock() < item.getQuantity()) {
                throw new BusinessException("商品库存不足: " + product.getProductname());
            }
        }
        
        // 3. 计算总金额
        BigDecimal totalAmount = calculateTotal(orderDTO.getItems());
        
        // 4. 创建订单主记录
        OrderMsg order = new OrderMsg();
        order.setDdno(orderNo);
        order.setMemberid(orderDTO.getMemberId());
        order.setTotal(totalAmount.doubleValue());
        order.setFkstatus("待支付");
        order.setShstatus("待审核");
        order.setSavetime(new Date().toString());
        order.setDelstatus("0");
        
        orderDAO.save(order);
        
        // 5. 创建订单明细并扣减库存
        for (OrderItemDTO item : orderDTO.getItems()) {
            createOrderItem(order.getId(), item);
            productDAO.decreaseStock(item.getProductId(), item.getQuantity());
        }
        
        return orderNo;
    }
    
    private String generateOrderNo() {
        return "DD" + System.currentTimeMillis() + 
               String.format("%04d", new Random().nextInt(10000));
    }
}

购物车界面

订单状态管理采用状态模式设计,支持完整的订单生命周期管理:

public interface OrderState {
    void pay(OrderMsg order);
    void cancel(OrderMsg order);
    void confirm(OrderMsg order);
    void deliver(OrderMsg order);
}

@Component
public class PendingPaymentState implements OrderState {
    @Override
    public void pay(OrderMsg order) {
        order.setFkstatus("已支付");
        order.setShstatus("待发货");
        // 更新数据库
        orderDAO.update(order);
    }
    
    @Override
    public void cancel(OrderMsg order) {
        order.setFkstatus("已取消");
        // 恢复库存
        restoreStock(order);
    }
}

用户收藏与消息系统

收藏功能通过favbbs表实现用户与帖子的多对多关系:

CREATE TABLE `favbbs` (
  `id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
  `bbsid` int(11) DEFAULT NULL COMMENT '帖子ID',
  `mid` int(11) DEFAULT NULL COMMENT '会员ID',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=6 DEFAULT CHARSET=utf8 COMMENT='帖子收藏表'

收藏业务的Service层实现:

@Service
public class FavoriteService {
    
    @Autowired
    private FavbbsDAO favbbsDAO;
    
    public boolean addFavorite(int memberId, int bbsId) {
        // 检查是否已收藏
        Favbbs existing = favbbsDAO.findByMemberAndBbs(memberId, bbsId);
        if (existing != null) {
            return false; // 已收藏
        }
        
        Favbbs favbbs = new Favbbs();
        favbbs.setMid(memberId);
        favbbs.setBbsid(bbsId);
        favbbsDAO.save(favbbs);
        return true;
    }
    
    public List<Bbs> getFavoriteBbs(int memberId) {
        return favbbsDAO.findBbsByMemberId(memberId);
    }
}

收藏帖子界面

后台管理系统

后台管理采用RBAC权限控制模型,支持商品审核、订单管理、用户管理等核心功能:

@Controller
@RequestMapping("/admin")
public class AdminProductController {
    
    @RequestMapping("/product/audit")
    public String auditProduct(@RequestParam int productId, 
                              @RequestParam String status,
                              HttpServletRequest request) {
        Product product = productDAO.findById(productId);
        product.setIssj(status);
        productDAO.update(product);
        
        // 记录审核日志
        AuditLog log = new AuditLog();
        log.setProductId(productId);
        log.setAuditor(getCurrentAdmin(request));
        log.setAction("审核商品");
        log.setResult(status);
        auditLogDAO.save(log);
        
        return "redirect:/admin/product/list";
    }
    
    @RequestMapping("/order/statistics")
    @ResponseBody
    public Map<String, Object> getOrderStatistics(
            @RequestParam String startDate,
            @RequestParam String endDate) {
        
        Map<String, Object> result = new HashMap<>();
        result.put("totalOrders", orderDAO.countByDateRange(startDate, endDate));
        result.put("totalAmount", orderDAO.sumAmountByDateRange(startDate, endDate));
        result.put("categoryStats", orderDAO.getCategoryStatistics(startDate, endDate));
        
        return result;
    }
}

后台订单管理

实体模型设计精要

系统采用贫血模型设计,实体类主要承载数据属性,业务逻辑集中在Service层。以About实体为例:

package com.entity;

import java.util.*;

public class About {
    private int id;
    private String content;
    
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }
    public String getContent() {
        return content;
    }
    public void setContent(String content) {
        this.content = content;
    }
    
    @Override
    public String toString() {
        return "About [content=" + content + ", id=" + id + "]";
    }
}

控制器层通过注解方式实现请求映射和依赖注入:

@Controller
@Resource
public class AboutController extends BaseController {
    @Resource
    AboutDAO aboutDAO;
    CategoryDAO categoryDAO;
    @Resource
    Saveobject saveobject;
    
    @RequestMapping("/admin/showAbout")
    public String showAbout(int id, HttpServletRequest request){
        String pagemsg = request.getParameter("pagemsg");
        About about = aboutDAO.findById(id);
        request.setAttribute("about", about);
        request.setAttribute("pagemsg", pagemsg);
        return "admin/aboutedit";
    }
    
    @RequestMapping("/admin/aboutEdit")
    public String aboutEdit(About about, HttpServletRequest request){
        aboutDAO.update(about);
        return "redirect:showAbout.do?id=1";
    }
}

功能展望与技术优化方向

基于当前系统架构,未来可从以下几个方向进行深度优化:

1. 引入Redis缓存集群

@Service
public class ProductServiceWithCache {
    
    @Autowired
    private RedisTemplate<String, Object> redisTemplate;
    
    private static final String PRODUCT_CACHE_KEY = "product:";
    private static final long CACHE_EXPIRE = 3600; // 1小时
    
    public Product getProductWithCache(int id) {
        String cacheKey = PRODUCT_CACHE_KEY + id;
        Product product = (Product) redisTemplate.opsForValue().get(cacheKey);
        
        if (product == null) {
            product = productDAO.findById(id);
            if (product != null) {
                redisTemplate.opsForValue().set(cacheKey, product, 
                    CACHE_EXPIRE, TimeUnit.SECONDS);
            }
        }
        return product;
    }
}

2. 微服务架构改造 将单体应用拆分为用户服务、商品服务、订单服务、支付服务等微服务,通过Spring Cloud实现服务治理。商品服务独立部署:

# application.yml for product-service
server:
  port: 8081
spring:
  application:
    name: product-service
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848
eureka:
  client:
    service-url:
      defaultZone: http://localhost:8761/eureka/

3. Elasticsearch搜索优化 实现更强大的商品搜索功能:

@Service
public class ProductSearchService {
    
    @Autowired
    private ElasticsearchRestTemplate elasticsearchTemplate;
    
    public SearchResponse<Product> searchProducts(String keyword, 
                                                 String category, 
                                                 Double minPrice, 
                                                 Double maxPrice) {
        
        NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
        
        if (StringUtils.hasText(keyword)) {
            queryBuilder.withQuery(QueryBuilders.multiMatchQuery(keyword, 
                "productname", "content", "leibie"));
        }
        
        // 添加过滤条件
        BoolQueryBuilder filterQuery = QueryBuilders.boolQuery();
        if (StringUtils.hasText(category)) {
            filterQuery.must(QueryBuilders.termQuery("leibie", category));
        }
        if (minPrice != null || maxPrice != null) {
            RangeQueryBuilder priceRange = QueryBuilders.rangeQuery("price");
            if (minPrice != null) priceRange.gte(minPrice);
            if (maxPrice != null) priceRange.lte(maxPrice);
            filterQuery.must(priceRange);
        }
        
        queryBuilder.withFilter(filterQuery);
        return elasticsearchTemplate.search(queryBuilder.build(), Product.class);
    }
}

4. 消息队列异步处理 使用RabbitMQ处理高并发场景:

@Component
public class OrderMessageProducer {
    
    @Autowired
    private RabbitTemplate rabbitTemplate;
    
    public void sendOrderCreate
本文关键词
SSM框架校园二手商品交易平台源码解析数据库设计MyBatis

上下篇

上一篇
没有更多文章
下一篇
没有更多文章