zoukankan      html  css  js  c++  java
  • JSP/Servlet 实现简单的留言板

                                             系  统  概  述

      一个简单的留言板所实现的功能有:用户注册、用户登录、查看留言信息和留言四个功能。在学习了JSP/Servlet后编写的

    一个简单的实例,虽然简单,却拥有一个完整系统的必要功能,所以可以让自己初步了解使用JSP/Servlet技术开发系统的一般步骤。

      

    系统功能简介:

      用户注册:当用户注册一个新用户时,就是向数据库user_table表中添加一条记录。

        当用户输入注册信息后,将用户的的注册信息提交到服务端负责处理注册信息的Servlet。当Servlet成功处理完用户的信息后,

    客户端自动跳转到【登录界面】进行登录。

        用户登录:当用户输入用户名、密码和验证码时。系统将信息提交的处理登录信息的Servlet。Servlet则调用服务器控制器里

    的方法来处理用户登录。当用户登录成功时,客户端自动跳转到【留言板】。

        留言板:调用数据库中的留言信息,显示在页面上。同时用户可以通过【留言】按钮,跳转到【留言】界面,留言功能和注册功能

    类似,向数据库ly_table表中添加一条记录。

       

    数据库的设计:

      对于该系统来说有两个表【user_table】和【ly_table】。

      【user_table】如下:

    字段名 类型 含义
    id int 用户id
    username varchar(20) 用户名
    password varchar(20) 密码

      【ly_table】如下:

    字段名 类型 含义
    id int 留言信息的id
    userId int 用户的id
    title varchar(25) 标题名字
    date date 留言时间
    connect text 留言类容

      

    实现系统的基础类:

      实现在注册、登录系统中使用的一些重要的类:连接和操作数据库的DB类、存储用户的User类、

    存储留言信息的LeaveMessageTable类和实现图形验证码的ValidationCode类。

      连接和操作数据库的DB类中具体包括如下方法:

            public User checkUser(String username , String password) :检查用户时候存在,存在就返回一个User对象,否则返回null 。

          public boolean checkValidationCode(HttpServletRequest request ,String validationCode) :检测验证码是否正确。

        public boolean addInfo(LeaveMessageTable ly) : 向数据库插入留言。

        public boolean insertUser(String username,String password) :向数据库存入用户。

        public ArrayList findLyInfo() : 从数据库中导出留言,返回一个ArrayList对象。

         private ResultSet execSQL(String sql , Object ...args)  : 执行SQL语句。

     

        在DB类的构造函数中连接数据库。这样有Servlet类创建DB对象时,便在创建过程中进行数据库的连接。

        

    View Code
    package com.cnblogs.jbelial.DBServlet;
    
    
    import java.sql.Connection;
    import java.sql.DriverManager;
    import java.sql.PreparedStatement;
    import java.sql.ResultSet;
    import java.sql.SQLException;
    import java.util.*;
    
    import javax.servlet.http.HttpServletRequest;
    
    import Common.Encrypter;
    import Common.LeaveMessageTable; 
    import Common.User;
    
    public class DB{
        
    //    定义数据库连接变量
        private Connection connection ;  
    //    定义参数
        private String sql_driver = "com.mysql.jdbc.Driver" ; 
        private String sql_url = "jdbc:mysql://localhost:3306/web_ly_table" ; 
        private String sql_username = "root" ; 
        private String sql_password = "hezuoan" ; 
        
        public DB()
        {
            try
            {
                   //建立数据库的连接
                   Class.forName(sql_driver) ;
                   connection = DriverManager.getConnection(sql_url,sql_username,sql_password) ; 
               }
            catch(Exception e)
            {
                e.printStackTrace() ; 
            }
        }
        
    //    用于执行各种SQL语句的方法
        private ResultSet execSQL(String sql , Object ...args) 
                throws SQLException
        {
            PreparedStatement pstmt = connection.prepareStatement(sql) ;
    //        为PreparedStatement对象设置SQL参数
            for (int i = 0 ; i < args.length ; ++ i)
            {
                pstmt.setObject(1 + i, args[i]) ; 
            }
    //        运行
            pstmt.execute() ; 
            return  pstmt.getResultSet(); 
        }
    //    核对用户输入的验证码是否正确
        public boolean checkValidationCode(HttpServletRequest request , 
                String validationCode)
        {
            String validationCodeSession = (String) request.getSession().getAttribute("validationCode") ; 
            if(validationCodeSession == null)
            {
    //            给result.jsp设置信息
                request.setAttribute("info" , "验证码过期") ;
    //            给login.jsp设置信息
                request.setAttribute("codeError", "验证码过期") ;
                return false ; 
            }
            if(!validationCode.equalsIgnoreCase(validationCodeSession))
            {
                request.setAttribute("info","验证码错误") ;
                request.setAttribute("codeError", "验证码错误") ;
                return false ; 
            }
            return true; 
        }
    //    检查用户登录信息
        public User checkUser(String username , String password)
        {
            try
            {
                String sql = "select * from user_table where username = ? and  password = ?" ;
                ResultSet rs = execSQL(sql,username,password) ; 
                User user = new User() ; 
                while (rs.next())
                {    
                    user.setId(rs.getInt("id")) ; 
                    user.setUsername(rs.getString("username")) ; 
                    user.setPassword(rs.getString("password")) ; 
                    return user ;
                } 
                return null ;
            }
            catch(Exception e)
            {
                e.printStackTrace();
                return null ; 
            }
        }
    //    插入留言
        public boolean addInfo(LeaveMessageTable ly){
            try{
                String sql = "insert into ly_table(userId,data,title,content) values(?,?,?,?)" ; 
                execSQL(sql , ly.getUserId(), ly.getDate(),ly.getTitle(),ly.getContent());
                return true;
            }catch(Exception e){
                e.printStackTrace();
                return false;
            }
        }
    //    插入用户
        public boolean insertUser(String username,String password){
            try{
                String sql = "insert into user_table(username,password) values(?,?)" ; 
                execSQL(sql ,username , password) ;  
                return true;
            }catch(Exception e){
                e.printStackTrace();
                return false;
            }
        }
    //    获取留言信息。
        public ArrayList findLyInfo()
        {
             ArrayList arrayList = new ArrayList() ; 
             try 
             {
                 String sql = "select * from ly_table" ; 
                 ResultSet rs = execSQL(sql) ; 
                 while(rs.next())
                 {
                     LeaveMessageTable ly = new LeaveMessageTable() ; 
                     ly.setId(rs.getInt("id")) ; 
                     ly.setUserId(rs.getInt("userId")) ;
                     ly.setDate(rs.getDate("data")) ; 
                     ly.setTitle(rs.getString("title")) ;
                     ly.setContent(rs.getString("content")) ; 
                     arrayList.add(ly) ; 
                 }
                 return arrayList ; 
             }
             catch(Exception e)
             {
                 e.printStackTrace() ; 
                 return null ; 
             }
        }
    //    获取用户名
        public String getUserName(int id)
        {
            String username = null;
            try{
                String sql = "select username from user_table where id = ?" ;
                ResultSet rs= execSQL(sql , new Object[]{id});
                while(rs.next()){
                     username=rs.getString(1);
                }
                return username;
            }catch(Exception e){
                e.printStackTrace();
                return null;
            }
        }
    }

      User类和LeaveMessageTable类:

      User类中则包含Id、用户名和密码三个属性。同时包含各个属性的set和get方法。

      

    View Code
    package Common;
    
    public class User {
    //    用户的id
        private int id ;
    //    用户名
        private String username ;
    //    用户密码
        private String password ;
        public int getId() {
            return id;
        }
        public void setId(int id) {
            this.id = id;
        }
        public String getUsername() {
            return username;
        }
        public void setUsername(String username) {
            this.username = username;
        }
        public String getPassword() {
            return password;
        }
        public void setPassword(String password) {
            this.password = password;
        }
        
    
    }

      

      LeaveMessageTable类:包含了如下属性Id、留言用户Id、留言标题、留言时间、留言类容属性。同时也包含了各个属性的

    set和get方法。  

    View Code
    package Common;
    import java.sql.Date;
    public class LeaveMessageTable {
        private int id ;
        private int userId ; 
        private Date date ; 
        private String title ; 
        private String content ;
        public int getId() {
            return id;
        }
        public void setId(int id) {
            this.id = id;
        }
        public int getUserId() {
            return userId;
        }
        public void setUserId(int userId) {
            this.userId = userId;
        }
        public Date getDate() {
            return date;
        }
        public void setDate(Date date) {
            this.date = date;
        }
        public String getTitle() {
            return title;
        }
        public void setTitle(String title) {
            this.title = title;
        }
        public String getContent() {
            return content;
        }
        public void setContent(String content) {
            this.content = content;
        }
        
    }

      实现图形验证码:

      实现图形验证码大致分为5步上来完成:

      1、建立图形缓冲区; 

      2、在图形缓冲区用随机颜色填充背景。

      3、在图形缓冲区上输出验证码。

      4、将验证码保存在HttpSession对象中。

      5、向客户端输出图形验证码。

      通过ValidationCode类来实现验证码功能,该类也是Servlet类,在客户端只要像访问普通Servlet一样访问ValidationCode类即可。

      

    View Code
    package com.cnblogs.jbelial.Validation;
    
    import java.awt.*;
    import java.awt.image.BufferedImage;
    import java.io.* ; 
    import java.util.Random;
    
    import javax.imageio.ImageIO;
    import javax.servlet.http.HttpServlet;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    import javax.servlet.http.HttpSession;
    
    @SuppressWarnings("serial")
    public class ValidationCode extends HttpServlet
    {
    //    图形验证码的字符集合,系统通过随机从这些字符串中选择一些字符作为验证码
        private static String codeChars = 
            "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTYVWXYZ" ; 
    //    返回一个随机颜色
        private static Color getRandomColor(int minColor , int maxColor)
        {
            Random random = new Random() ;
            if (minColor > 255)
                minColor = 255 ; 
            if (maxColor > 255)
                maxColor = 255 ; 
    //        获取颜色的随机值
            int red = minColor + random.nextInt(maxColor - minColor) ; 
            int green = minColor + random.nextInt(maxColor - minColor) ; 
            int blue = minColor + random.nextInt(maxColor - minColor) ; 
            return new Color(red,green,blue) ;  
        }
        public void doGet (HttpServletRequest request ,
                HttpServletResponse response) throws IOException
        {
            
            
    //       获取验证码集合的长度。
            int charsLength = codeChars.length() ; 
    //        关闭浏览器缓冲区
            response.setHeader("ragma", "No-cache") ; 
            response.setHeader("Cache-Control", "no-cache") ;
            response.setDateHeader("Expires", 0) ; 
    //        设置图片传送的格式。
            response.setContentType("image/jpeg");
            
    //        设置图形验证码的长和宽度
            int width = 90 ;
            int height = 20 ;
    //        建立图形缓冲区
            BufferedImage image = new BufferedImage(width , height,
                    BufferedImage.TYPE_INT_RGB) ; 
    //        获取用于输出文字的Graphics对象
            Graphics graphics = image.getGraphics() ; 
            
            Random random = new Random() ; 
            
    //        设置要填充的颜色
            graphics.setColor(getRandomColor(180 , 250)) ; 
    //        填充图形背景
            graphics.fillRect(0, 0, width, height) ; 
    //        设置初始字体和颜色
            graphics.setFont(new Font("Time New Roman" , Font.ITALIC, height)) ; 
            graphics.setColor(getRandomColor(120,180)) ; 
            
    //        保存验证码
            StringBuilder validationCode = new StringBuilder() ; 
    //        验证码的随机字体
            String[] fontNames = {"Times New Roman" , "Book antiqua" , "Arial" } ;
    //        随机生成验证码
            for (int i = 0 ; i < 4 ; ++ i)
            {
    //            设置当前验证码字符的字体
                graphics.setFont(new Font(fontNames[random.nextInt(3)] , Font.ITALIC ,
                        height)) ; 
    //            随机获得验证码的字符
                char codeChar = codeChars.charAt(random.nextInt(charsLength)) ;
                validationCode.append(codeChar) ; 
                graphics.setColor(getRandomColor(20,120)) ; 
    //            在图形上输出验证码字符
                graphics.drawString(String.valueOf(codeChar), 16*i+random.nextInt(7), 
                        height - random.nextInt(6) ) ; 
            } 
    //        获得Session对象,并设置Session对象为3分钟
            HttpSession session = request.getSession(); 
            session.setMaxInactiveInterval(5*60) ; 
    //        将验证码放入session对象中.
            session.setAttribute("validationCode",validationCode.toString() ) ; 
            
            
    //        关闭graphics对象。
            graphics.dispose() ;  
    //        向客户端发送图形验证码
            ImageIO.write(image,"JPEG" ,response.getOutputStream()) ; 
            
        
            
        }
        public void doPost (HttpServletRequest request ,
                HttpServletResponse response) throws IOException
        {
                doGet(request , response) ; 
        }
        
    }

      

     实现注册系统:

      包括一个register.jsp、result.jsp和RegisterServlet类。

      RegisterServlet类负责处理处理用户的提交的注册信息。

        RegisterServlet类在处理用户注册信息之前,创建DB类对象来连接数据库。然后通过调用DB类的方法来判断验证码是否正确和用户名是否被注册。

    当一系列的判断都通过时,则向数据库中插入用户记录。

      RegisterServlet类的最后不管是否向数据库中插入用户记录,都会跳转到result.jsp页面。

      

    View Code
    package com.cnblogs.jbelial.Register;
    
    import java.io.IOException; 
    
    import javax.servlet.RequestDispatcher;
    import javax.servlet.ServletException;
    import javax.servlet.http.HttpServlet;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    
    import Common.User;
    
    import com.cnblogs.jbelial.DBServlet.DB;
    
    public class RegisterServlet extends HttpServlet {
    
        /**
         * The doGet method of the servlet. <br>
         *
         * This method is called when a form has its tag value method equals to get.
         * 
         * @param request the request send by the client to the server
         * @param response the response send by the server to the client
         * @throws ServletException if an error occurred
         * @throws IOException if an error occurred
         */
        public void doGet(HttpServletRequest request, HttpServletResponse response)
                throws ServletException, IOException 
        {
    //        设置字符集编码
            request.setCharacterEncoding("UTF-8") ; 
            response.setContentType("UTF-8");  
    //        判断是否跳到【登录】
            if (request.getParameter("login") != null)
            {
                response.sendRedirect("login.jsp") ;
                return ; 
            }
            DB db = new DB() ; 
            String username  = null ;
    //        设置result页面要跳转的页面
            String page = "login.jsp" ;
            try
            { 
    //            获取界面的用户名和密码参数
                username = request.getParameter("username") ; 
                String password = request.getParameter("password") ;
                String validationCode = request.getParameter("validationCode") ; 
    //            核对验证码
                if (!db.checkValidationCode(request, validationCode))  
                    return ;   
                User user = db.checkUser(username,password) ; 
                if (user != null) 
                {
                    request.setAttribute("info", username + "已被使用!") ;
                    page = "register.jsp" ; 
                }
                else if (db.insertUser(username , password)) 
                {
    //                定义result.jsp中使用的消息
                    request.setAttribute("info" , "用户注册成功") ;
                } 
                request.setAttribute("page", page) ; 
            }
            catch(Exception e) { }
            finally
            { 
    //            跳转到result.jsp 
                RequestDispatcher rd = request.getRequestDispatcher("/result.jsp") ; 
                rd.forward(request, response) ; 
            }
        }
    
        /**
         * The doPost method of the servlet. <br>
         *
         * This method is called when a form has its tag value method equals to post.
         * 
         * @param request the request send by the client to the server
         * @param response the response send by the server to the client
         * @throws ServletException if an error occurred
         * @throws IOException if an error occurred
         */
        public void doPost(HttpServletRequest request, HttpServletResponse response)
                throws ServletException, IOException {
            doGet(request,response) ; 
        }
    
    }

      

      register.jsp则负责显示注册页面:

    View Code
    <%@ page language="java" pageEncoding="UTF-8"%> 
    <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
    <html>
      <head>
        <title>用户注册</title>
        <script type="text/javaScript">
             function refresh()
             {
                 var img = document.getElementById("imgValidationCode") ; 
                 img.src = "ValidationCode"+Math.random() ; 
             }
             function checkRegister()
             {
                 var username = document.getElementById("username") ;
                 if(username.value == "" )
                 {
                     alert("请输入用户名!") ; 
                     //把焦点放到username输入文本上
                     username.focus() ; 
                     return ;
                 }
                 var password = document.getElementById("password") ;
                 if(password.value == "" )
                 {
                     alert("请输入密码!");
                     password.focus() ;
                     return ; 
                 }
                 var re_password = document.getElementById("re_password") ;
                 if(re_password.value != password.value)
                 {
                     alert("输入的密码不一致!") ; 
                     re_password.focus() ; 
                     return ; 
                 }
                 var validationCode = document.getElementById("validationCode") ;
                 if(validatoinCode.value == "")
                 {
                     alert("请输入验证码!");
                     validatoinCode.focus() ;
                     return ;
                 }
                 register_form.submit() ; 
             }
         </script> 
      </head>
      
      <body> 
          <center>
              <h2>用户注册</h2>
              <form  name = "register_form" action = "RegisterServlet" method = "post">
                  <table>
                      <tr>
                          <td>
                              用户名:
                          </td>
                          <td>
                              <input type = "text" id = "username" name = "username" 
                                  size = "25">
                          </td>
                      </tr>
                      <tr>
                          <td>
                              密码:
                          </td>
                          <td>
                              <input type = "password" id = "password" name = "password"
                                  size = "25">
                          </td>
                      </tr>
                      <tr>
                          <td>
                              再次输入密码:
                          </td>
                          <td>
                          <input type = "password" id = "re_password" name = "re_password"
                                  size = "25">
                          </td>
                      </tr>
                      <tr>
                          <td>
                              验证码:
                          </td>
                          <td>
                            <input type = "text" id = "validationCode" name = "validationCode"
                                style = "60px;margin-top:10px"/>  
                            <img id = "imgValidationCode" src = "ValidationCode"/>
                            <input type = "button" value = "刷新"  onclick = "refresh()"/>
                        </td>
                      </tr>
                  </table>
                  <input type = "button" value = "注册" onclick = "checkRegister()"/>
                  <input type = "submit" value = "登录" name = "login">
              </form>
          </center>
      </body>
    </html>

      result.jsp页面则负责显示结果:

      

    View Code
    <%@ page language="java"  pageEncoding="UTF-8"%> 
    <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
    <html>
      <body>
          <form name = "result_form" action = "${requestScope.page}" , method = "post"> 
            ${requestScope.info} 
                <input type = "submit" value = "确定" >  
          </form>
      </body>
    </html>

      

     实现登录系统:

       登录系统和注册系统类似,包含login.jsp和LoginServlet类。

       LoginServlet类负责处理用户提交的登录信息。通过创建DB对象来连接数据库,再调用DB中的方法来判断用户提交的验证码和用户名、密码

    的真确性,如果都正确则跳转到main.jsp,否则返回到login.jsp并显示提示消息;

       

    View Code
    package com.cnblogs.jbelial.Login;
    
    import java.io.IOException;
    import java.util.ArrayList;
    
    import javax.servlet.RequestDispatcher;
    import javax.servlet.ServletException;
    import javax.servlet.http.HttpServlet;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    import javax.servlet.http.HttpSession;
    
    import Common.User;
    
    import com.cnblogs.jbelial.DBServlet.DB;
    
    public class LoginServlet extends HttpServlet {
    
        /**
         * The doGet method of the servlet. <br>
         *
         * This method is called when a form has its tag value method equals to get.
         * 
         * @param request the request send by the client to the server
         * @param response the response send by the server to the client
         * @throws ServletException if an error occurred
         * @throws IOException if an error occurred
         */
        public void doGet(HttpServletRequest request, HttpServletResponse response)
                throws ServletException, IOException {
     
    //        设置字符集编码
            request.setCharacterEncoding("UTF-8") ; 
            response.setContentType("UTF-8");  
    //        判断是否跳到【注册】
            if (request.getParameter("register") != null)
            {
                response.sendRedirect("register.jsp") ;
                return ; 
            }
            DB db = new DB() ;
    //        设置跳转界面
            String page = "login.jsp" ;  
            String username = null ;
            try
            {
    //            获取请求页面的参数
                username = request.getParameter("username") ; 
                String password = request.getParameter("password") ; 
                String validationCode = request.getParameter("validationCode") ; 
    //            验证码检测
                if (!db.checkValidationCode(request, validationCode))
                        return ; 
                User user = db.checkUser(username,password) ; 
                if (user == null)
                    request.setAttribute("userError", "用户名或密码错误") ; 
                if (user != null)
                {
    //                如果根据检查,user不为空,表示用户名正确和密码正确,进行下一步操作。
                    ArrayList arrayList = new ArrayList() ; 
                    arrayList = db.findLyInfo() ; 
                    request.setAttribute("arrayList", arrayList) ;
    //                设置跳转到主界面
                    page = "main.jsp" ;
                    request.getSession().setAttribute("user", user) ; 
                }
        
                
            }
            catch(Exception e){}
            finally
            {
                request.setAttribute("username", username) ; 
                RequestDispatcher rd = request.getRequestDispatcher("/"+page) ; 
                rd.forward(request, response) ; 
            }
        }
        /**
         * The doPost method of the servlet. <br>
         *
         * This method is called when a form has its tag value method equals to post.
         * 
         * @param request the request send by the client to the server
         * @param response the response send by the server to the client
         * @throws ServletException if an error occurred
         * @throws IOException if an error occurred
         */
        public void doPost(HttpServletRequest request, HttpServletResponse response)
                throws ServletException, IOException {
            doGet(request,response) ; 
        }
    
    }

        

       login.jsp则负责显示登录界面

    View Code
    <%@ page language="java" pageEncoding="UTF-8"%> 
    <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
    <html>
      <head>
        <title>用户登录</title> 
      </head> 
         <script type="text/javaScript">
             function refresh()
             {
                 var img = document.getElementById("imgValidationCode") ; 
                 img.src = "ValidationCode" ; 
             }
             function checkLogin()
             {
                 var username = document.getElementById("username_id"); 
                 if (username.value == "" )
                 {
                     alert("请输入用户名!") ;
                     username.focus() ; 
                     return ; 
                 }
                 var password = document.getElementById("password_id") ;
                 if (password.value == "")
                 {
                     alert("密码不能为空");
                     password.focus() ; 
                     return ;
                 }
                 var validationCode = document.getElementById("validationCode_id") ; 
                 if ( validationCode.value == "")
                 {
                     alert("验证吗不能为空") ;
                     validationCode.focus() ;
                    return ; 
                 }
                 login_form.submit() ; 
             }
         </script> 
      <body>
          <center> 
              <h2>用户登录</h2>
              <form name = "login_form" action = "LoginServlet" method = "post" >
                  <table>
                      <tr>
                          <td>
                               用户名:
                           </td>
                           <td>
                               <input type = "text" id = "username_id" value = "${requestScope.username}" name = "username"  
                                  size = "25" />${requestScope.userError}
                          </td>
                      </tr>
                      <tr>
                          <td>
                              密  码:
                          </td>
                           <td>
                            <input type="password" id="password_id" name="password" size="25">
                        </td>
                    </tr>
                    <tr>
                        <td>
                            验证码:
                        </td>
                        <td>
                            <input type = "text" id = "validationCode_id" name = "validationCode"
                                style = "60px;margin-top:10px"/>  
                            <img id = "imgValidationCode" src = "ValidationCode"/>
                            <input type = "button" value = "刷新"  onclick = "refresh()"/>
                            ${requestScope.codeError}
                        </td>
                    </tr> 
                  </table>
                  <input type = "button" value = "登录" onclick = "checkLogin()">
                  <input type = "submit" value = "注册" name = "register">
              </form>
          </center>
      </body>
    </html>

     

    实现留言系统:

      留言系统包括负责显示用户留言的main.jsp页面、用户写留言的LeaveMessage.jsp页面和处理用户提交留言的addMessageServlet类 。

      addMessageServlet类就是把用户提交的留言信息提取出来,然后存入数据库。

      main.jsp则在用户登录后,自动跳转到显示留言的界面。 

    留言板的源代码:MessageBoardSystem.rar

  • 相关阅读:
    用 HTML 格式导出 Excel 时,如何保留显示网格线
    [转载] 让SciTE能够和IDE一样进行成员提示
    RedHat 上安装多个 mysql 实例并配置 django 连接的操作记录
    我的 SciTEGlobal.properties 配置文件
    FrameSet 不能支持透明
    RedHat 上安装 lighttpd 并配置 fastcgi + django 的记录
    系统设计与开发 辅助工具大集成终结版
    SQL Server Management Object(SMO)大大简化数据库工具的开发 几行代码开发功能强大的SQL工具
    Enterprise Solution 解决方案与源代码下载
    LLBL Gen 实体映射工具技术原理剖析
  • 原文地址:https://www.cnblogs.com/jbelial/p/2444009.html
Copyright © 2011-2022 走看看