欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

空气质量管理系统+SSM(Spring+SpringMVC+Mybatis)+前后端分离总结

程序员文章站 2022-07-02 12:42:06
空气质量管理系统+SSM(Spring+SpringMVC+Mybatis)+前后端分离总结 ......
作者:故事我忘了
个人微信公众号:程序猿的月光宝盒
空气质量管理系统+SSM(Spring+SpringMVC+Mybatis)+前后端分离总结

点我进ssm演示地址

1.目录结构:

空气质量管理系统+SSM(Spring+SpringMVC+Mybatis)+前后端分离总结

2.需要注意的地方

2.1在web-info下新建

空气质量管理系统+SSM(Spring+SpringMVC+Mybatis)+前后端分离总结

2.1.1 springmvc-servlet.xml

<?xml version="1.0" encoding="utf-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/xmlschema-instance"
       xmlns:aop="http://www.springframework.org/schema/aop"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:tx="http://www.springframework.org/schema/tx"
       xmlns:mvc="http://www.springframework.org/schema/mvc"
       xsi:schemalocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd
       http://www.springframework.org/schema/aop
       http://www.springframework.org/schema/aop/spring-aop.xsd
       http://www.springframework.org/schema/context
       http://www.springframework.org/schema/context/spring-context.xsd
       http://www.springframework.org/schema/tx
       http://www.springframework.org/schema/tx/spring-tx.xsd
       http://www.springframework.org/schema/mvc
       http://www.springframework.org/schema/mvc/spring-mvc.xsd
">
    <context:component-scan base-package="monster._52cc"/>
    <bean id="datasource" class="org.springframework.jdbc.datasource.drivermanagerdatasource">
        <property name="driverclassname" value="com.mysql.jdbc.driver"/>
        <property name="url" value="jdbc:mysql:///kh75?useunicode=true&amp;characterencoding=utf-8"/>
        <property name="username" value="root"/>
        <property name="password" value="admin"/>
    </bean>
    <bean id="sqlsessionfactory" class="org.mybatis.spring.sqlsessionfactorybean">
        <property name="datasource" ref="datasource"/>
        <property name="typealiasespackage" value="monster._52cc.pojo"/>
        <property name="typealiases" value="monster._52cc.util.pageutils"/>
    </bean>
    <bean id="transactionmanager" class="org.springframework.jdbc.datasource.datasourcetransactionmanager">
        <property name="datasource" ref="datasource"/>
    </bean>
    <tx:annotation-driven/>
    <bean class="org.mybatis.spring.mapper.mapperscannerconfigurer">
        <property name="basepackage" value="monster._52cc.mapper"/>
    </bean>
    <!--这是从controller层使用@restcontroller注解引起从数据库到前台时间出现long类型的时间(从1970-1-1至今的毫秒),解决springmvc 中@restcontroller 返回日期格式为时间戳-->
    <mvc:annotation-driven>
        <mvc:message-converters>
            <bean class="org.springframework.http.converter.json.mappingjackson2httpmessageconverter">
                <property name="objectmapper">
                    <bean class="com.fasterxml.jackson.databind.objectmapper">
                        <property name="dateformat">
                            <bean class="java.text.simpledateformat">
                                <constructor-arg type="java.lang.string" value="yyyy-mm-dd hh:mm:ss"/>
                            </bean>
                        </property>
                    </bean>
                </property>
            </bean>
        </mvc:message-converters>
    </mvc:annotation-driven>
</beans>

2.1.2 web.xml

<!doctype web-app public
        "-//sun microsystems, inc.//dtd web application 2.3//en"
        "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app>
    <display-name>archetype created web application</display-name>
    <filter>
        <filter-name>encodingfilter</filter-name>
        <filter-class>org.springframework.web.filter.characterencodingfilter</filter-class>
        <init-param>
            <param-name>encoding</param-name>
            <param-value>utf-8</param-value>
        </init-param>
    </filter>
    <filter-mapping>
        <filter-name>encodingfilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>
    <servlet>
        <servlet-name>springmvc</servlet-name>
        <servlet-class>org.springframework.web.servlet.dispatcherservlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>springmvc</servlet-name>
        <url-pattern>*.do</url-pattern>
    </servlet-mapping>
    <welcome-file-list>
        <welcome-file>list.html</welcome-file>
    </welcome-file-list>
</web-app>

2.2实体类,对应数据库中data的字段上加注解 @datetimeformat(pattern = "yyyy-mm-dd")

@data
@allargsconstructor
@noargsconstructor
public class airqualityindex {
    /**
    * 记录编号
    */
    private integer id;

    /**
    * 区域编号
    */
    private integer districtid;

    /**
    * 检测时间
    */
    @datetimeformat(pattern = "yyyy-mm-dd")
    private date monitortime;

    /**
    * pm10值
    */
    private integer pm10;

    /**
    * pm2.5值
    */
    private integer pm2_5;

    /**
    * 监测站
    */
    private string monitoringstation;

    /**
    * 最后修改时间
    */
    private string lastmodifytime;
}

2.3 暂时没有用到mybatis的分页插件,所以自己写分页工具类

@tostring
public class pageutils {
    private integer pagesize;
    private integer pageno;
    private integer totalcount;
    private integer totalpages;
    private integer startrow;
    /**
     * 需要分页的对象
     */
    private airqualityindex airqualityindex;

    public pageutils() {
    }

    public pageutils(integer pagesize, integer pageno, integer totalcount, airqualityindex airqualityindex) {
        this.pagesize = pagesize;
        this.pageno = pageno;
        this.totalcount = totalcount;
        this.airqualityindex = airqualityindex;

        setstartrow(pagesize,pageno);
        settotalpages(pagesize,totalcount);
    }

    public integer getpagesize() {
        return pagesize;
    }

    public void setpagesize(integer pagesize) {
        this.pagesize = pagesize;
    }

    public integer getpageno() {
        return pageno;
    }

    public void setpageno(integer pageno) {
        this.pageno = pageno;
    }

    public integer gettotalcount() {
        return totalcount;
    }

    public void settotalcount(integer totalcount) {
        this.totalcount = totalcount;
    }

    public integer gettotalpages() {
        return totalpages;
    }

    public void settotalpages(integer pagesize,integer totalcount) {
        this.totalpages = totalcount%pagesize==0?totalcount/pagesize:totalcount/pagesize+1;
    }

    public integer getstartrow() {
        return startrow;
    }

    public void setstartrow(integer pagesize,integer pageno) {
        this.startrow = (pageno-1)*pagesize;
    }

    public airqualityindex getairqualityindex() {
        return airqualityindex;
    }

    public void setairqualityindex(airqualityindex airqualityindex) {
        this.airqualityindex = airqualityindex;
    }
}

2.4 省去mapper的xml,使用注解写sql

注意查询的动态sql上要用<script></script>包起来

airqualityindexmapper.java

public interface airqualityindexmapper {

    @delete("delete from air_quality_index where id = #{id}")
    int deletebyprimarykey(integer id);

    @insert("insert into air_quality_index values (null,#{districtid}, #{monitortime}, #{pm10}, #{pm2_5}, #{monitoringstation}, #{lastmodifytime})")
    int insert(airqualityindex airqualityindex);

    @update("update air_quality_index set districtid = #{districtid},monitortime = #{monitortime},pm10 = #{pm10},pm2_5 = #{pm2_5},monitoringstation = #{monitoringstation},lastmodifytime = #{lastmodifytime} where id = #{id}")
    int updatebyprimarykey(airqualityindex airqualityindex);

    @select("<script>" +
            "select a.*,d.name from air_quality_index a,district d where a.districtid = d.id" +
            "<if test='airqualityindex != null and airqualityindex.id != null'>" +
            "  and a.id=#{airqualityindex.id}" +
            "</if>" +
            "<if test='airqualityindex != null and airqualityindex.districtid != -1 and airqualityindex.districtid != null'>" +
            "  and a.districtid=#{airqualityindex.districtid}" +
            "</if>" +
            "<if test='pagesize != null and startrow != null'>" +
            "  limit #{startrow},#{pagesize}" +
            "</if>" +
            "</script>")
    list<map<string,object>> selectbyprimarykey(pageutils pageutils);

    @select("<script>" +
            "  select count(0) from air_quality_index" +
            "  <where>" +
            "    <if test='districtid != null and districtid != -1'>" +
            "        and districtid=#{districtid}" +
            "    </if>" +
            "  </where>" +
            "</script>")
    int gettotalcount(airqualityindex airqualityindex);
}

2.5 service中要注意的事情

2.5.1因为分页逻辑属于service要做的事,所以贴上对应serviceimp中的逻辑

airqualityindexserviceimpl.java中的selectbyprimarykey(pageutils pageutils)

@service
@transactional
public class airqualityindexserviceimpl implements airqualityindexservice {
    @autowired
    private airqualityindexmapper airqualityindexmapper;

    @override
    public int deletebyprimarykey(integer id) {
        return airqualityindexmapper.deletebyprimarykey(id);
    }

    @override
    public int insert(airqualityindex airqualityindex) {
        //todo获取当前系统时间
        date d = new date();
        simpledateformat sdf = new simpledateformat("yyyy-mm-dd hh:mm:ss");
        //2019-10-23 10:31:37
        airqualityindex.setlastmodifytime(sdf.format(d));
        if (airqualityindex.getdistrictid() == -1) {
            return 0;
        }
        return airqualityindexmapper.insert(airqualityindex);
    }

    @override
    public int updatebyprimarykey(airqualityindex airqualityindex) {
        //todo获取当前系统时间
        date d = new date();
        simpledateformat sdf = new simpledateformat("yyyy-mm-dd hh:mm:ss");
        //2019-10-23 10:31:37
        //设置时区
        sdf.settimezone(timezone.gettimezone("asia/shanghai"));
        airqualityindex.setlastmodifytime(sdf.format(d));
        if (airqualityindex.getdistrictid() == -1) {
            return 0;
        }
        system.out.println(airqualityindex);
        return airqualityindexmapper.updatebyprimarykey(airqualityindex);
    }

    @override
    public list<map<string, object>> selectbyprimarykey(pageutils pageutils) {
        if(pageutils.getpageno()==null){
            return airqualityindexmapper.selectbyprimarykey(pageutils);
        }
        pageutils.settotalcount(airqualityindexmapper.gettotalcount(pageutils.getairqualityindex()));
        pageutils.setpagesize(5);
        pageutils.settotalpages(pageutils.getpagesize(), pageutils.gettotalcount());
        pageutils.setstartrow(pageutils.getpagesize(), pageutils.getpageno());
        return airqualityindexmapper.selectbyprimarykey(pageutils);
    }
}

2.5.2其中,因为要实时保存修改时间,所以也在service中实现

//todo获取当前系统时间
        date d = new date();
        simpledateformat sdf = new simpledateformat("yyyy-mm-dd hh:mm:ss");
        //2019-10-23 10:31:37
        //设置时区
        sdf.settimezone(timezone.gettimezone("asia/shanghai"));
        airqualityindex.setlastmodifytime(sdf.format(d));
        if (airqualityindex.getdistrictid() == -1) {
            return 0;
        }
        system.out.println(airqualityindex);

2.6最终的controller文件

centercontrollerofair.java

@restcontroller
public class centercontrollerofair{
    @autowired
    private airqualityindexservice airqualityindexservice;
    @autowired
    private districtservice districtservice;

    @requestmapping("/deletebyprimarykey.do")
    public int deletebyprimarykey(integer id) {
        return airqualityindexservice.deletebyprimarykey(id);
    }

    @requestmapping("/insert.do")
    public int insert(airqualityindex airqualityindex) {
        if(airqualityindex.getdistrictid()==-1 || airqualityindex.getmonitoringstation()==null || airqualityindex.getmonitortime()==null || airqualityindex.getpm2_5()==null || airqualityindex.getpm10()==null){
            return 0;
        }
        return airqualityindexservice.insert(airqualityindex);
    }

    @requestmapping("/updatebyprimarykey.do")
    public int updatebyprimarykey(airqualityindex airqualityindex) {
        if(airqualityindex.getdistrictid()==-1 || airqualityindex.getmonitoringstation()==null || "".equals(airqualityindex.getmonitoringstation().trim()) || airqualityindex.getmonitortime()==null || airqualityindex.getpm2_5()==null || airqualityindex.getpm10()==null){
            return 0;
        }
        return airqualityindexservice.updatebyprimarykey(airqualityindex);
    }

    @requestmapping("/selectbyprimarykey.do")
    public map<string, object> selectbyprimarykey(pageutils pageutils) {
        map<string, object> map = new hashmap<>(16);
        list<map<string, object>> airqualityindexlist = airqualityindexservice.selectbyprimarykey(pageutils);
        map.put("airqualityindexlist",airqualityindexlist);
        map.put("pageutils",pageutils);
        return map;
    }

    @requestmapping("/showalldistrict.do")
    public list<map<string, object>> showalldistrict() {
        return districtservice.showalldistrict();
    }

    @requestmapping("/info.do")
    public map<string, object> info(pageutils pageutils) {
        map<string, object> map = new hashmap<>(16);
        map.put("airqualityindex",airqualityindexservice.selectbyprimarykey(pageutils).get(0));
        map.put("optiondata",districtservice.showalldistrict());
        return map;
    }
}

2.7对应的几个页面要注意的:

list.html

<!doctype html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title>title</title>
</head>
<body>
<center>
    <h1>空气质量监测信息库</h1>
    <form id="seldistrictform">
    按区域查询
        <select name="districtid" id="seldistrictsel" title="区域查询">
            <option value="-1">不限</option>
        </select>
        <input type="button" name="sel" value="查找"/>
        &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
        <a href="add.html">添加空气质量信息</a>
    </form>
    <br/>
    <table>
        <tr>
            <th>序号</th>
            <th>区域</th>
            <th>监测时间</th>
            <th>pm10</th>
            <th>pm2.5</th>
            <th>监测站</th>
        </tr>
    </table>
    <p class="pagefoot"></p>
</center>
<script rel="script" type="text/javascript" src="js/jquery-1.11.2.min.js"></script>
<script rel="script" type="text/javascript" src="js/initoptionsel.js"></script>
<script rel="script" type="text/javascript" src="js/list.js"></script>
</body>
</html>

list.js

$(function () {
    // 初始化分页数据
    initpagedata(1);
    //条件查找
    $("[type=button]").click(function () {
        initpagedata(1);
    });

});



function initpagedata(pageno) {
    var table = $("table");
    var pagefoot = $("[class=pagefoot]");
    var districtid = $("[name=districtid]").val();
    $.ajax({
        url: "selectbyprimarykey.do",
        type: "post",
        datatype: "json",
        data: {"pageno": pageno, "airqualityindex.districtid": districtid},
        async: true,
        success: function (obj) {
            var tablestr = "";
            console.log(obj.airqualityindexlist.length===0);
            if (obj.airqualityindexlist.length===0){
                $("tr:gt(0)").remove();
                tablestr=`
                <tr style="text-align: center">
                    <td colspan="6"><strong>抱歉,暂无数据</strong></td>
                </tr>
                `;
            }else{
                //在循环的前面清空标题以下的所有行
                //获取行>0的那行.移除方法
                $("tr:gt(0)").remove();
                $.each(obj.airqualityindexlist, function (i) {
                    tablestr += `
                <tr>
                  <td>${obj.airqualityindexlist[i].id}</td>
                  <td> <a href="edit.html?id=${obj.airqualityindexlist[i].id}">${obj.airqualityindexlist[i].name}</a></td>
                  <td>${obj.airqualityindexlist[i].monitortime}</td>
                  <td>${obj.airqualityindexlist[i].pm10}</td>
                  <td>${obj.airqualityindexlist[i].pm2_5}</td>
                  <td>${obj.airqualityindexlist[i].monitoringstation}</td>
                </tr>
                `;
                });
            }
            table.attr("width", "600");
            table.append(tablestr);
            $("tr").first().attr("style", "background-color:#add8e6");
            $("tr:gt(0):odd").attr("style", "background-color:#90ee90");

            //分页
            //在分页前,清空原来分页的内容
            pagefoot.html("");
            var pagestr = "";
            if(obj.pageutils.totalcount===0){//如果没有数据,就不显示分页条
                return ;
            }
            if (obj.pageutils.pageno === 1 && obj.pageutils.pageno !== obj.pageutils.totalpages) {//如果是第一页,并且还有下一页
                pagestr = `
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;">首&nbsp;页</a>|
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;"><< 上一页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno + 1 });">下一页>></a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.totalpages});">尾&nbsp;页</a>
                `
            }else if (obj.pageutils.pageno === 1 && obj.pageutils.pageno !== obj.pageutils.totalpages) {//如果是第一页,并且没有有下一页
                pagestr = ``//nothing to do
            }else if(obj.pageutils.pageno !== 1 && obj.pageutils.pageno !== obj.pageutils.totalpages){//如果不是第一页,并且还有下一页
                pagestr = `
                <a href="javascript:void(0);" onclick="initpagedata(1)">首&nbsp;页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno - 1 });"><< 上一页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno + 1 });">下一页>></a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.totalpages});">尾&nbsp;页</a>
                `
            }else if(obj.pageutils.pageno !== 1 && obj.pageutils.pageno === obj.pageutils.totalpages){//如果不是第一页,且是最后一页
                pagestr = `
                <a href="javascript:void(0);" onclick="initpagedata(1)">首&nbsp;页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno - 1 })"><< 上一页</a>|
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;">下一页>></a>|
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;">尾&nbsp;页</a>
                `
            }
            pagestr += `
            第&nbsp;
                ${obj.pageutils.pageno}
                页/共
                ${obj.pageutils.totalpages}
                页(${obj.pageutils.totalcount}条)
            `;
            pagefoot.append(pagestr);
        },
        error: function () {
            alert("initpagedata error");
        }
    })
}

2.7.1其中,分页逻辑可以以后稍作修改直接使用

            //分页
            //在分页前,清空原来分页的内容
            pagefoot.html("");
            var pagestr = "";
            if(obj.pageutils.totalcount===0){//如果没有数据,就不显示分页条
                return ;
            }
            if (obj.pageutils.pageno === 1 && obj.pageutils.pageno !== obj.pageutils.totalpages) {//如果是第一页,并且还有下一页
                pagestr = `
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;">首&nbsp;页</a>|
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;"><< 上一页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno + 1 });">下一页>></a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.totalpages});">尾&nbsp;页</a>
                `
            }else if (obj.pageutils.pageno === 1 && obj.pageutils.pageno !== obj.pageutils.totalpages) {//如果是第一页,并且没有有下一页
                pagestr = ``//nothing to do
            }else if(obj.pageutils.pageno !== 1 && obj.pageutils.pageno !== obj.pageutils.totalpages){//如果不是第一页,并且还有下一页
                pagestr = `
                <a href="javascript:void(0);" onclick="initpagedata(1)">首&nbsp;页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno - 1 });"><< 上一页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno + 1 });">下一页>></a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.totalpages});">尾&nbsp;页</a>
                `
            }else if(obj.pageutils.pageno !== 1 && obj.pageutils.pageno === obj.pageutils.totalpages){//如果不是第一页,且是最后一页
                pagestr = `
                <a href="javascript:void(0);" onclick="initpagedata(1)">首&nbsp;页</a>|
                <a href="javascript:void(0);" onclick="initpagedata(${obj.pageutils.pageno - 1 })"><< 上一页</a>|
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;">下一页>></a>|
                <a href="javascript:void(0);" style="text-decoration: none;color: grey;cursor:no-drop;">尾&nbsp;页</a>
                `
            }
            pagestr += `
            第&nbsp;
                ${obj.pageutils.pageno}
                页/共
                ${obj.pageutils.totalpages}
                页(${obj.pageutils.totalcount}条)
            `;
            pagefoot.append(pagestr);

initoptionsel.js

初始化下拉列表

$(function () {
    //初始化查询下啦列表
    initseloption();}
);
function initseloption() {
    $.ajax({
        url: "showalldistrict.do",
        type: "post",
        datatype: "json",
        data: {},
        async: true,
        success: function (obj) {
            var str = "";
            $.each(obj, function (i) {
                str += `
               <option value="${obj[i].id}">${obj[i].name}</option>
               `
            });
            //获取下拉列表
            $("#seldistrictsel").append(str);
        },
        error: function () {
            alert("initseloption error");
        }
    })
}

以上,结束