JavaEE学习日志持续更新----> 必看!JavaEE学习路线(文章总汇)
JavaEE学习日志(七十)
黑马商城项目(三)
今日任务
- 商品的详情
- 某个分类下的商品的分页展示
- 使用redis优化分类信息查询
商品的详情
实现步骤
- 首页拼接字符串,将每个商品的主键id传递到详情页面
- 详情页面获取商品主键,向服务器发送AJAX请求
- Servlet接收客户端请求的主键值
- 调用业务层方法,根据主键查询商品
- 业务层调用持久层查询商品传递,返回商品对象
- Servlet接收业务层返回的商品对象
- 商品对象封装Result对象,转成JSON数据,响应浏览器
前端
- header.html页面把商品的图片和文字连接,连接到商品详情页面,并传递pid参数
- 商品详情页面的js
<script type="text/javascript">
$(function(){
//获取传递过来的参数
//工具函数获取
var pid = HM.getParameter("pid");
var params = "method=findById&pid="+pid;
//发送ajax请求
HM.ajax("/product",params,function(data){
if(data.code==1){
//json取出商品数据
var product = data.obj;
$("#pname").html(product.pname);
$("#pid").html(product.pid);
$("#shop_price").html(product.shop_price);
$("#market_price").html("¥"+product.market_price);
$("#pimage").attr("src","http://www.itheima331.com:8020/web/"+product.pimage)
$("#pdesc").html(product.pdesc);
}
});
});
</script>
ProductDao
/*
传递主键查询商品信息
返回javabean
*/
@Override
public Product findById(String pid) throws SQLException {
//拼写sql语句
String sql = "select * from product where pid = ?";
return qr.query(sql,new BeanHandler<Product>(Product.class),pid);
}
ProductService
/*
根据主键查询商品
主键web层传递
调用dao层,传递主键,获取javabean
*/
@Override
public Product findById(String pid) {
Product p = null;
try {
p = productDao.findById(pid);
} catch (SQLException e) {
e.printStackTrace();
}
return p;
}
ProductServlet
/*
查询商品详情
接收页面请求发送商品主键
传递到业务层,获取返回的javabean
把返回的javabean封装到result中,转成json
*/
public void findById(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String pid = request.getParameter("pid");
Product p = productService.findById(pid);
Result result = new Result(Result.SUCCESS,"查询成功",p);
response.getWriter().print(JSONObject.fromObject(result));
}
某个分类下的商品的分页展示
实现步骤
- 菜单页面拼接超链接,传递商品分类主键
- 分类商品页面接收分类主键数据,向服务器发送AJAX请求
- Servlet接收客户端分类主键的数据
- 调用业务层方法组装PageBean数据
- 业务层调用持久层方法,分页查询数据表
- Servlet接收业务层返回的PageBean数据,转成JSON响应客户端
前端
首先从index.html中点击按钮,传入一个分类主键cid
分类分页前端:使用了工具类
<script type="text/javascript">
$(function(){
//获取页面传递的分类主线
var cid = HM.getParameter("cid");
//获取当前页数
var currentPage = HM.getParameter("currentPage")
var params = "method=findByPage&cid="+cid+"¤tPage="+currentPage;
//发送请求,参数传递主键
HM.ajax("/product",params,function(data){
if(data.code==1){
//取出json中的数据
var pb = data.obj;
//取出pagebean对象中的商品数据
var productList = pb.list;
var product = $("#product");
$.each(productList, function(index,element) {
//数组中的元素就是每个商品信息
var s = "<div style=\"height:260px\" class=\"col-md-2\">\n" +
"\t\t\t\t\t\t<a href=\"http://www.itheima331.com:8020/web/view/product/info.html?pid="+element.pid+"\">\n" +
"\t\t\t\t\t\t\t<img src=\"http://www.itheima331.com:8020/web/"+element.pimage+"\" width=\"170\" height=\"170\" style=\"display: inline-block;\">\n" +
"\t\t\t\t\t\t</a>\n" +
"\t\t\t\t\t\t<p><a href=\"info.htmll\" style='color:green'>"+element.pname+"</a></p>\n" +
"\t\t\t\t\t\t<p><font color=\"#FF0000\">商城价:¥"+element.shop_price+"</font></p>\n" +
"\t\t\t\t\t</div>";
product.append(s);
});
//处理页码
var page = $("#page");
//循环页码 开始第一页,到总页数结束
/*for(var i=1;i<=pb.totalPage;i++){
var s = "<li><a href=\"http://www.itheima331.com:8020/web/view/product/list.html?currentPage="+i+"&cid="+cid+"\">"+i+"</a></li>";
page.append(s);
}*/
//工具函数page
var p = HM.page(pb,"http://www.itheima331.com:8020/web/view/product/list.html?cid="+cid);
page.html(p);
}
});
});
</script>
工具类中page函数:传入pageBean对象和url,获得一个分页栏
page:function(pb,url){
if(url.indexOf("?") != -1){
//带参数
}else{
//不带参数
url+="?_t="+new Date().getTime();
}
var pageHTML="";
if(pb.currentPage==1){
pageHTML+="<li class=\"disabled\"><a href=\"javascript:;\" aria-label=\"Previous\"><span aria-hidden=\"true\">«</span></a></li>\n";
}else{
pageHTML+="<li ><a href=\""+url+"¤tPage="+(pb.currentPage-1)+"\" aria-label=\"Previous\"><span aria-hidden=\"true\">«</span></a></li>\n";
}
for(var i=1;i<=pb.totalPage;i++){
if(i==pb.currentPage){
pageHTML+="<li class='active'><a href='javascript:;' >"+i+"</a></li>"
}else{
pageHTML+="<li ><a href='"+url+"¤tPage="+i+"'>"+i+"</a></li>"
}
}
if(pb.currentPage==pb.totalPage){
pageHTML+="<li class=\"disabled\" ><a href=\"javascript:;\" aria-label=\"Next\"><span aria-hidden=\"true\">»</span></a></li>"
}else{
pageHTML+="<li><a href='"+url+"¤tPage="+(pb.currentPage+1)+"' aria-label=\"Next\"><span aria-hidden=\"true\">»</span></a></li>"
}
return pageHTML;
}
ProductDao
/*
根据分类查询的商品总数量
传递商品的分类外键
*/
@Override
public long getTotalCount(String cid) throws SQLException {
//拼写分类查询的sql
String sql = "select count(*) from product where cid = ?";
return qr.query(sql,new ScalarHandler<Long>(),cid);
}
/*
分页查询的商品数据
传递当前页,每页条数,分类外键
*/
@Override
public List<Product> findByPage(int currentPage, int pageSize, String cid) throws SQLException {
//拼写分页查询的sql语句
String sql = "select * from product where cid = ? limit ?,?";
return qr.query(sql,new BeanListHandler<Product>(Product.class),cid,(currentPage-1)*pageSize,pageSize);
}
ProductService
/*
封装好PageBean对象,返回到web层
*/
@Override
public PageBean<Product> findByPage(int currentPage, int pageSize, String cid) {
PageBean<Product> pb = new PageBean<>();
try {
//设置当前页数
pb.setCurrentPage(currentPage);
//设置每页显示的条数
pb.setPageSize(pageSize);
//设置显示的商品数据,调用dao
List<Product> productList = productDao.findByPage(currentPage, pageSize, cid);
pb.setList(productList);
//设置商品总数量
long totalCount = productDao.getTotalCount(cid);
pb.setTotalCount(totalCount);
//设置总页数
int totalPage = (int) Math.ceil(totalCount * 1.0 / pageSize);
pb.setTotalPage(totalPage);
}catch (Exception ex){ex.printStackTrace();}
return pb;
}
ProductServlet
/*
分页查询商品数据
页面获取分类的主键
获取当前页数
调用业务层方法,返回pagebean对象
封装到结果对象result,转成json响应
*/
public void findByPage(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//获取当前页
String currentPage = request.getParameter("currentPage");
if(currentPage==null || "null".equals(currentPage)){
currentPage="1";
}
//定义变量,保存每页个数
int pageSize = 12;
//获取分类外键
String cid = request.getParameter("cid");
//调用业务层方法,返回pagebean对象
PageBean<Product> pb = productService.findByPage(Integer.parseInt(currentPage), pageSize, cid);
Result result = new Result(Result.SUCCESS,"查询成功",pb);
response.getWriter().print(JSONObject.fromObject(result));
}
redis优化分类菜单
redis优化思想
优化CategoryService
注意:JSONUtils中的方法toList
,把json格式字符串转成集合list
参数:
- JSONArray对象:
JSONArray.fromObject(category)
- 被转换后的集合泛型的class对象
package com.itheima.service.impl;
import com.itheima.dao.CategoryDao;
import com.itheima.domain.Category;
import com.itheima.service.CategoryService;
import com.itheima.utils.BeanFactory;
import com.itheima.utils.JedisUtils;
import net.sf.json.JSONArray;
import net.sf.json.JSONObject;
import redis.clients.jedis.Jedis;
import java.sql.SQLException;
import java.util.List;
public class CategoryServiceImpl implements CategoryService {
//bean工厂,获取dao层的接口实现类
private CategoryDao categoryDao = BeanFactory.newInstance(CategoryDao.class);
/*
从redis数据库中查询导航数据
不存在:查询mysql,取出category表数据,数据转成json字符串,存到redis中
存在:把redis数据库中的字符串转成集合返回
*/
@Override
public List<Category> findAll() {
List<Category> categoryList = null;
//获取redis数据库连接对象
Jedis jedis = JedisUtils.getJedis();
//获取字符串
String category = jedis.get("category");
//判断是否有数据
try {
if (category == null) {
//没数据
//查询mysql数据库,取出category
categoryList = categoryDao.findAll();
//数据集合转成json,存储到redis
jedis.set("category", JSONArray.fromObject(categoryList).toString());
} else {
//有数据
//category转成集合返回
/*
toList,把json格式字符串转成集合list
参数:JSONArray对象
被转换后的集合泛型的class对象
*/
categoryList = JSONArray.toList(JSONArray.fromObject(category), Category.class);
}
} catch (Exception ex) {
ex.printStackTrace();
} finally {
JedisUtils.close(jedis);
}
return categoryList;
}
/*
调用dao层,查询所有的分类数据
返回集合list
*/
/* @Override
public List<Category> findAll() {
List<Category> categoryList = null;
try {
categoryList = categoryDao.findAll();
} catch (SQLException e) {
e.printStackTrace();
}
return categoryList;
}*/
}