首页
关于
Search
1
sql的注入原因和解决办法
138 阅读
2
SpringBoot整合腾讯云存储COS及基本使用,增删改查......
128 阅读
3
深究contains方法
100 阅读
4
多线程概述
74 阅读
5
学习的第一个注解@WebServlet - JavaWeb
73 阅读
默认分类
Java
C/C++
Mysql
JavaWeb
SpringBoot
算法
前端
Linux
Search
标签搜索
Spring
HTTP
Java
JavaWeb
IOC
mybatis
腾讯云
COS
云存储
CDN
redis
分布式
id
全局唯一id
Typecho
累计撰写
26
篇文章
累计收到
2
条评论
首页
栏目
默认分类
Java
C/C++
Mysql
JavaWeb
SpringBoot
算法
前端
Linux
页面
关于
搜索到
12
篇与
JavaWeb
的结果
2022-08-12
bs_typeadhead - 关键字自动补全插件
bs_typeadhead - 文本框关键字自动补全插件此插件基于bootstrap首先引入三大部分的依赖jquery、bootstrap、bs_typeadhead<%-- jquery--%> <script type="text/javascript" src="jquery/jquery-1.11.1-min.js"></script> <!-- bootstrap --> <link rel="stylesheet" href="jquery/bootstrap_3.3.0/css/bootstrap.min.css"> <script type="text/javascript" src="jquery/bootstrap_3.3.0/js/bootstrap.min.js"></script> <%-- bs_typeadhead--%> <script type="text/javascript" src="jquery/bs_typeahead/bootstrap3-typeahead.min.js"></script>页面添加一个div容器<input type="text" id="customerName">在入口函数,对容器注册bs_typeadhead 函数部分说明:typeahead( ) 函数的source属性就是自动补全的数据的来源,来源分为静态数据和动态数据。静态数据:可以是数组 [ ]。动态数据:source是一个函数,里面是ajax请求,请求的结果必须是可遍历的json对象<script type="text/javascript"> $(function (){ $("#customerName").typeahead({ //数据的来源-静态 // source:['京东商城','阿里巴巴','百度科技公司','字节跳动','动力节点'] //数据的来源-动态 source:function(jquery,process){ //参数列表里的process是一个函数,作用是把ajax返回的data赋值给属性source。 //用户在容器中获取的关键字 //发送请求 $.ajax({ url:'workbench/transaction/queryCustomerNameByName.do?customerName'+jquery, type:'post', dataType:'json', success:function (data){ process(data); //参数列表里的process是一个函数,作用是把ajax返回的data赋值给属性source。 } }); } }); });ajax请求部分对应的后端代码 @RequestMapping("/workbench/transaction/queryCustomerNameByName.do") @ResponseBody public List<String> queryCustomerNameByName(String customerName){ List<String> customerNameList = customerService.queryCustomerNameByName(); return customerNameList; }typeahead( ) 函数的其他属性source: 规定包含查询时要显示的值的数据源。值的类型是 array,默认值是 [ ]。items: 规定查询时要显示的条目的最大值。数据类型是 number,默认值是 8。matcher: 决定查询是否匹配条目。带有一个单一的参数,即要测试查询的条目。当前查询通过 this.query 访问。返回一个布尔值 true,表示查询匹配。数据类型是 function。默认情况下是大小写不敏感的。sorter: 用于自动分类结果。带有一个单一的参数,即具有 typeahead 实例范围的条目。当前查询通过 this.query 访问。数据类型是 function。默认值是精确匹配的,其他的值还可以是大小写敏感、大小写不敏感。highlighter: 用于自动高亮突出显示结果。带有一个单一的参数,即具有 typeahead 实例范围的条目。数据类型是 function。默认情况下是高亮突出显示所有默认的匹配项。
2022年08月12日
49 阅读
0 评论
0 点赞
2022-08-01
日历插件datatimepicker的使用 - JSP
DateTimePicker图形化日历时间日期选择器DateTimePicker是基于JQuery的时间日期选择插件。只需要2行代码,即可轻松实现网页图形化日期时间选择器。 datatimepicker软件包下载地址:https://www.datetimepicker.cn/download/有一个编辑框<body> <input id="myDate" type="text" readonly> </body>然后按顺序引入相关css和jsjquery依赖bootstrap框架dataTimePicker插件<%-- jquery--%> <script type="text/javascript" src="jquery/jquery-1.11.1-min.js"></script> <%-- bootstrapk框架--%> <link rel="stylesheet" href="jquery/bootstrap_3.3.0/css/bootstrap.min.css"> <script type="text/javascript" href="jquery/bootstrap_3.3.0/js/bootstrap.min.js"></script> <%-- bootstrap datetimepicker插件--%> <link rel="stylesheet" href="jquery/bootstrap-datetimepicker-master/css/bootstrap-datetimepicker.min.css"> <script type="text/javascript" src="jquery/bootstrap-datetimepicker-master/js/bootstrap-datetimepicker.js"></script> <script type="text/javascript" src="jquery/bootstrap-datetimepicker-master/locale/bootstrap-datetimepicker.zh-CN.js"></script>在页面加载完成后注册插件<script type="text/javascript"> $(function (){ //当容器加载完成,对容器调用工具函数 $("#myDate").datetimepicker({ language:'zh-CN', //语言 format:'yyyy-mm-dd', //日期格式 minView:'month', //最小精度 autoclose:'true', //默认值false,当选择一个日期之后是否立即关闭此日期时间选择器。 initData:new Date(), //默认时间 todayBtn:'ture', //是否显示选择当前时间按钮 clearBtn:'true' //是否显示清空按钮 }); })完整代码<%@ page contentType="text/html;charset=UTF-8" language="java" %> <% String basePath=request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+request.getContextPath()+"/"; %> <html> <head> <base href="<%=basePath%>"> <meta charset="UTF-8"> <%-- jquery--%> <script type="text/javascript" src="jquery/jquery-1.11.1-min.js"></script> <%-- bootstrapk框架--%> <link rel="stylesheet" href="jquery/bootstrap_3.3.0/css/bootstrap.min.css"> <script type="text/javascript" href="jquery/bootstrap_3.3.0/js/bootstrap.min.js"></script> <%-- bootstrap datetimepicker插件--%> <link rel="stylesheet" href="jquery/bootstrap-datetimepicker-master/css/bootstrap-datetimepicker.min.css"> <script type="text/javascript" src="jquery/bootstrap-datetimepicker-master/js/bootstrap-datetimepicker.js"></script> <script type="text/javascript" src="jquery/bootstrap-datetimepicker-master/locale/bootstrap-datetimepicker.zh-CN.js"></script> <title>演示bs_datetimepicker插件</title> <script type="text/javascript"> $(function (){ //当容器加载完成,对容器调用工具函数 $("#myDate").datetimepicker({ language:'zh-CN', //语言 format:'yyyy-mm-dd', //日期格式 minView:'month', //最小精度 autoclose:'true', //默认值false,当选择一个日期之后是否立即关闭此日期时间选择器。 initData:new Date(), //默认时间 todayBtn:'ture', //是否显示选择当前时间按钮 clearBtn:'true' //是否显示清空按钮 }); }) </script> </head> <body> <input type="text" id="myDate" readonly> </body> </html>
2022年08月01日
63 阅读
0 评论
0 点赞
2022-07-09
手动注入JdbcTemplate - SpringBoot
在Spring的某些无法自动注入的情况下,可以选择手动注入。数据源:就是配置数据库的驱动、连接地址、账号、密码//配置数据源 DriverManagerDataSource dataSource = new DriverManagerDataSource(); dataSource.setDriverClassName("com.mysql.cj.jdbc.Driver"); dataSource.setUrl("jdbc:mysql://localhost:3306/userdb?useUnicode=true&characterEncoding=utf-8&useSSL=false&serverTimezone=Asia/Shanghai"); dataSource.setUsername("root"); dataSource.setPassword("123456"); //new出JdbcTemplate,并将数据源放入其构造方法 JdbcTemplate jdbcTemplate = new JdbcTemplate(dataSource);例子将注入过程放到类的构造方法比较合理。@SpringBootTest public class mysqlTest { private JdbcTemplate jdbcTemplate; public mysqlTest(){ DriverManagerDataSource dataSource = new DriverManagerDataSource(); dataSource.setDriverClassName("com.mysql.cj.jdbc.Driver"); dataSource.setUrl("jdbc:mysql://localhost:3306/userdb?useUnicode=true&characterEncoding=utf-8&useSSL=false&serverTimezone=Asia/Shanghai"); dataSource.setUsername("root"); dataSource.setPassword("123456"); this.jdbcTemplate = new JdbcTemplate(dataSource); } @Test public void contextLoads(){ Long count = jdbcTemplate.queryForObject("select count(*) from userinfo", Long.class); System.out.println("userinfo数据表记录总数为:" + count); } }
2022年07月09日
34 阅读
0 评论
0 点赞
2022-05-15
Spring - IOC
[TOC]一、IOC控制反转IOC就是对象创建的由谁来控制。正转:由程序员进行对象的创建和依赖注入称之为正传。就是程序员说了算。Student.stu = new Student( ); ===>程序员创建对象 stu.setName("张三"); ===>程序员进行赋值 stu.setAge(18); 反转:由Spring容器创建对象和依赖注入称为反转,将控制权从程序员手上夺走,由Spring管理,称之为反转。<bean id="stu" class="com.achong.entity.Student"> ===>Spring容器负责对象的创建 <property name="name" value="张三"> ===>Spring容器依赖注入值,也就是对对象赋值 <property name="age" value="20"> </bean>二、Bean管理Bean管理是指两个操作:Spring创建对象 和 Spring给对象的属性注入值。Bean管理有两种实现方式:基于XML配置文件 和 基于注解 。三、IOC接口IOC思想基于IOC容器完成,IOC容器底层就是对象工厂。Spring提供IOC容器实现的两种方式:BeanFactory和ApplicationContextBeanFactoryIOC容器的基本实现,是Spring内部使用的接口,一般不提供开发人员使用。ApplicationContextBeanFactory接口的子接口,提供更多更强大的功能,一般由开发人员使用。两者的区别是:BeanFactory在加载配置文件的时候不会创建对象,在获取对象的时候采取创建对象;而ApplicationContext会在配置文件加载的时候就把对象创建好。四、 基于XML配置文件的Bean管理4.1.两种方式创建对象方式一:创建对象并注入值Bean标签是创建对象id是对象名称,名称唯一 ;class是对象的完全包名。propertory标签是为对象的属性注入值。若不需要注入则该标签不用写。name是属性名,value是属性值。注意:创建对象是调用无参构造方法,注入值是使用set方法。所以必须保证对象类里有这两种方法。<!--创建学生对象,在容器启动的时候--> <bean id="stu" class="com.achong.entity.Student"> <property name="name" value="张三"></property> <property name="age" value="18"></property> </bean> 取出对象 ClassPathXmlApplicationContext( )方法读取xml配置文件。 getBean( )方法取出创建好的对象。参数名为xml里对应Bean标签的id。 @Test public void TestSpringStudent(){ ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml"); Student stu = (Student) ac.getBean("stu"); System.out.println(stu ); }方式二:创建对象并注入值此方式调用的是带参的构造方法创建对象。使用 构造方法 的 参数名称 注入值。 <bean id="school" class="com.achong.entity.School"> <constructor-arg name="name" value="广东工程职业技术学院"></constructor-arg> <constructor-arg name="address" value="广东省清远市清城区"></constructor-arg> </bean>使用 构造方法 的 下标 注入值。 <bean id="stu" class="com.achong.entity3.Student"> <constructor-arg index="0" value="2005"></constructor-arg> <constructor-arg index="1" value="achong"></constructor-arg> <constructor-arg index="2" value="18"></constructor-arg> <constructor-arg index="3" ref="school"></constructor-arg> </bean>使用 构造方法 的 参数 的 顺序 注入值。<bean id="stu" class="com.achong.entity4.Student"> <constructor-arg value="2005"></constructor-arg> <constructor-arg value="achong"></constructor-arg> <constructor-arg value="18"></constructor-arg> <constructor-arg ref="school"></constructor-arg> </bean>4.2. 三种方式注入属性值简单类型注入 简单类型指的是八大基本数据类型。使用value属性注入。上面的例子就是简单类型注入。引用类型注入 引用类型指的是另一个对象。使用ref属性注入。集合类型注入 集合类型注入指数组,List,Map。 例如User类里包含另一个Address类。这时候就需要引用类型注入。代码实现 - 引用类型注入<!-- 创建学校对象--> <bean id="school" class="com.achong.entity2.School"> <property name="name" value="广东工程职业技术学院"></property> <property name="address" value="广东省清远市清城区中宿路"></property> </bean> <!-- 创建学生对象--> <bean id="stu" class="com.achong.entity2.Student"> <property name="name" value="achong"></property> <property name="age" value="20"></property> <property name="school" ref="school"></property> </bean>代码实现 - 集合类型注入<bean id="stu" class="com.achong.entity.Student"> <!--数组类型--> <property name="courses"> <array> <value>java</value> <value>Mysql</value> </array> </property> <!--List类型注入--> <property name="maps"> <list> <value>张三</value> <value>李四</value> </list> </property> <!--Map类型注入--> <property name="sets"> <set> <value>Mysql</value> <value>Redis</value> </set> </property> </bean>添加util约束空间,把list提取出来。提取出来的集合独立,可供多个Bean使用。 <util:list id="bookList"> <value>java</value> <value>Mysql</value> <value>Servlet</value> </util:list> <bean id="stu" class="com.achong.entity5.Student"> <property name="courseList" ref="bookList"></property> </bean>内部Bean写法 <bean id="stu" class="com.achong.entity2.Student"> <property name="name" value="achong"></property> <property name="age" value="20"></property> <property name="school"> <bean id="school" class="com.achong.entity2.School"> <property name="name" value="广东工程职业技术学院"></property> <property name="address" value="广东省清远市"></property> </bean> </property> </bean>4.3 属性值包含空值、特殊符号空值<property name="address"> <null/> </property>特殊符号 第二个中括号里面的内容为输入值。<property name="address"> <vlaue><[!CDATA[<<广东省>>]]></vlaue> </property>五、基于注解的Bean管理也称为DI(Dependency Injection),它是IOC的具体实现的技术。使用注解管理bean,可以省去在xml配置文件里写很多行代码,为xml减负。5.1 创建对象的注解@Component("指定的名称"):可以创建任意对象。@Controller("指定的名称"):专门用来创建控制器的对象(Servlet),这种对象可以接收用户的请求,可以返回处理结果给客户端。@Service("指定的名称"):专门用来创建业务逻辑层的对象,负责向下访问数据访问层,处理完成后的结果返回给界面层。Repository("指定的名称"):专门用来创建数据访问层的对象,负责数据库中的增删改查所有操作。四个注解的功能一模一样,可以混用,但是不建议,因为这本来就是用来区分三层结构的,value也可以不写,不写的话,创建的对象的名字按照驼峰命名法来命名。@Resource( ): 可以根据类型注入,根据名称注入。但是因为这个包是java拓展的而不是Spring提供的,所以不建议使用。5.2 属性值注入的注解值类型的注入@Value:用来给简单类型注入值。相当于构造函数赋值。引用类型的注入@Autowired:使用类型注入值,从整个Bean工厂中搜索同源类型的对象进行注入。@Autowired、@Quelifier:使用名称注入值,从整个Bean工厂中搜索相同名称的对象进行注入。5.3实现步骤添加包扫描只扫描指定包。指定包下面的,带有指定注解的类将被创建。<context:component-scan base-package="com.achong.entity"></context:component-scan>创建对象并注入@Component public class Student { @Value("2005") private int id; @Value("achong") private String name; @Value("18") private int age; @Autowired private School school; }添加测试类测试@Test public void Test01(){ ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml"); Student stu = (Student) ac.getBean("student"); System.out.println(stu); }注意:在有父子类的情况下,使用按类型注入,就意味着有多个可注入的对象,此时按照名称进行二次筛选,选中与被注入对象相同名称的对象进行注入。所以,如果有父子类,建议使用按名称注入。5.4 细节批量包扫描, 逗号隔开<context:component-scan base-package="com.achong.entity , com.achong.entity2 , com.achong.entity3"></context:component-scan>自定义包扫描规则<!-- use-default-filters 表示不使用默认扫描规则 include-filter 设置扫描哪些内容,这里表示 只扫描Controller这个注解 --> <context:component-scan base-package="com.achong" use-default-filters="false"> <context:include-filter type="annotation" expression="org.springframework.stereotype.Controller"/> </context:component-scan> <!-- exclude-filter 设置哪些内容不扫描,这里表示Controller这个注解不会被扫描 --> <context:component-scan base-package="com.achong"> <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller"/> </context:component-scan>5.4 配置类替代xml上面的方法需要使用到xml配置文件。但是,使用配置类可以替代配置文件。步骤: 创建一个空白类,添加相应注解@Configuration //标记为配置类,替代xml文件 @ComponentScan(basePackages = {"com.achong.entity4"}) //扫描路径 public class SpringConfig { }添加测试方法测试。注意:原本的 new AnnotationConfigApplicationContext(SpringConfig.class) 应改成new AnnotationConfigApplicationContext(SpringConfig.class); @Test public void Test04(){ ApplicationContext ac = new AnnotationConfigApplicationContext(SpringConfig.class); Student student = (Student) ac.getBean("student"); System.out.println(student); }
2022年05月15日
48 阅读
0 评论
0 点赞
2022-04-30
sql的注入原因和解决办法
sql注入原因:sql注入的根本原因是用户输入的信息中含有sql语句的关键字,并且这些关键字参与了sql语句的编译过程,导致sql的原意被扭曲,进而达到sql注入。例如以下查询方法。 //该方法查询数据库是否有此账号密码,返回一个布尔值 private static boolean userQuery(String userName, String userPassword) { boolean flag = false; Connection conn = null; Statement stmt = null; ResultSet rs = null; try { conn = DBUtils.getConnection(); stmt = conn.createStatement(); //执行sql语句 String sql = "select * from userinfo where userName='"+userName+"' and userPassword='"+userPassword+"'"; rs = stmt.executeQuery(sql); if (rs.next()) flag = true; } catch (SQLException throwables) { throwables.printStackTrace(); }finally { DBUtils.close(conn,stmt,rs); } return flag; }用一个变量接收用户输入的密码,如果接收到的是一个正常的密码:123456,那么拼接后的sql语句就是正常的。select * from userinfo where userName='王五' and userPassword='123456'但是如果接收到的密码不是一个正常的密码,而是 abc' or '1'='1。这样的不正常密码带有sql的关键字or,再加上巧妙的组合,最终会使拼接后的sql语句就是这样的。分析以下sql的条件语句:因为or后面的条件 '1'='1' 是永远是正确的,所以前面的条件userName='123' and userPassword='abc' 可以无视。即使用户输入的账号密码不正确或者不存在,这条sql语句也会正常成功执行。且有返回值。select * from userinfo where userName='123' and userPassword='abc' or '1'='1'解决sql注入解决方法:只要用户输入的信息不参与sql语句的编译过程,问题就解决了。首先,将Statement接口改成子接口PreparedStatement。在编写sql语句的时候,在关键位置用 "?" 占位,这里吧?叫做占位符在JDBC第三步,获取数据库操作对象的时候,传入sql语句。这步是把sql预处理,也就是搭起sql语句的框架。下一步使用setString方法设置占位符对应的关键字。索引从1开始。注意:字符串用setString() , int类型数据用setInt()最后,执行sql就ok。不过还要注意,此时已经不需要传入sql语句,因为前面的预编译和设置占位就已经完成了。修改后的jdbc过程。//该方法查询数据库是否有此账号密码 private static boolean userQuery(String userName, String userPassword) { Connection conn = null; //将Statement接口改成PreparedStatement接口,这俩是继承关系。 PreparedStatement stmt = null; ResultSet rs = null; boolean flag = false; try { conn = DBUtils.getConnection(); //1.在sql语句的关键位置用?占位。 String sql = "select * from userinfo where userName=? and userPassword=?"; //2.预编译sql,也就是按处理好sql的框架 stmt = conn.prepareStatement(sql); //3.setString方法设置占位符对应的关键字,索引从1开始 stmt.setString(1,userName); stmt.setString(2,userPassword); //4.执行查询,但是这里不需要传sql rs = stmt.executeQuery(); if (rs.next()) flag = true; } catch (SQLException throwables) { throwables.printStackTrace(); } finally { DBUtils.close(conn,stmt,rs); } return flag; }虽然Preparedment的操作多一点,但是安全。因为它是先把带有 "?" 占位符的sql语句先编译了,然后通过setString方法在传入占位符对应的值,这样做即使传入的值带有mysql的关键字也没事,因为此时的sql语句已经预编译了,后面传入的值没有参与编译过程。如果用户还是传入不规范的数据,则sql执行会报错。
2022年04月30日
138 阅读
1 评论
1 点赞
1
2
3