在SpringMvc中使用shiro进行安全配置

前言

在去年一年之间用过shiro的一些内容,但是最近又有点忘却了。现在正好有一个机会,所以正好搭建起来了然后自己做些记录

搭建过程

引入jar包:

需要使用shiro的话先在maven中引入以下Jar包:

阅读更多

记踩过的SpringMvc的一些坑

时隔一年多,再次在新公司期间接触了SpringMvc,由于之前一段时间再用Python和SpringBoot做项目,所以一时间导致SpringMvc配置中出现了好多坑,遂逐一记录:

关于Dao层找不到的异常

在配置的过程中这个异常出现的次数是最多的,也是最烦人的,一般是由于在Controller层中找不到Service层,然后Service层的Impl在自动装配dao的时候找不到dao,所以异常就会沿着service到达contrller层,但是总结起来,在今天的配置中遇到的情况主要又以下几种:

web.xml中的配置出现了错误:

在Spring5中默认xml文件是在WEB-INF中的,于是也就想着少配置一点是一点的原则,所以在web.xml中只是配置了分发器。但是今天却在其中发现了一些可能会导致Dao层找不到的原因,如下所示是我之前在web.xml中配置的一个详情:

阅读更多

关于Java的链式代理

关于Java的代理

思路:

  1. 了解Enhancer的意义
  2. 查看生成的字节码(和原来的对比)
  3. 分析代理的区别
  4. 完成代理链

首先需要新建一个代理管理类,这个管理类会存储目标代理类,目标代理方法,以及一个List,List中存储的是一些代理类,最后是需要一个操作就是

记一次使用Spring5构件Web的过程

由于当时在学习Spring的时候还是在一年前,那时候Spring才是刚到4.3还是4.5.然后做了一个项目之后便了解到了SpringBoot,于是一直在用SpringBoot,所以导致现在配置起来就有点忘记了。所以现在记录下此次配置的过程中所遇到的坑。

踩过的坑:

遇到在web.xml中分发请求的类找不到

第一个坑就是org.springframework.web.servlet.DispatcherServlet这个类一直找不到;于是在POM中添加了个各种依赖终于发现缺少Spring Web MVC这个依赖包。。。

1
2
3
4
5
<servlet>
<servlet-name>spring-dispatcher</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class><!-- 需要webmvc这个jar包-->
<load-on-startup>1</load-on-startup>
</servlet>
阅读更多

Java通过反射用指定构造器初始化

Java通过反射用指定构造器初始化

首先, 一般来讲在Java中初始化一个类是通过new来操作的, 但是有一种情况却不适合这种new操作,那就是通过配置文件来进行实例化操作。

例如,在Spring中,需要加载配置文件中的类,这是比较常见的配置。 那么在Spring启动类中如何将这个类加载进容器中呢,显然进行new操作是不太现实的。 这时候就需要Java的反射操作了,Java的反射操作一般来讲有两种:分别是Class.forName()classLoader.loadCLass() 最后都是通过newInstance() 来进行初始化,但是在这里却发现假设反射的类中含有带参数的构造器,那么此时这个newInstance()就会抛NoSuchMethodException ,这是因为newInstance()因为不加参数所以调用的是默认构造器,而反射类中已经包含了带参数的构造器,所以无不带参数构造器,遂抛出异常。

但是此时newInstance()是加不了参数的,所以若需要通过制定构造器来进行反射的话需要一个类叫Constructor,

新建一个实体类:

阅读更多

记一次springboot-mybatis找不到dao层的错误

写了三个多月的Python,今天再写一个springboot-mybatis的项目的时候好多东西都忘记了,尤其是在今天下午遇到了一个关于mybatis的错误:

1
2
3
4
5
6
7
8
Description:

Field peopleDao in com.example.serviceImpl.PeopleServiceImpl required a bean of type 'com.example.dao.PeopleDao' that could not be found.


Action:

Consider defining a bean of type 'com.example.dao.PeopleDao' in your configuration

很明显就是dao层无法被扫描到,在一下午的尝试中,首先检查了包结构,如下:
com
—example
——controller
————XXX.java
——dao
————XXX.java
——–***
——Application.java

也就是说这个包结构是完全符合springboot的规范的,也就表示在启动类上面的注解是完全可以扫描到dao包下面的那个接口的。所以注解不存在问题。

然后尝试了第二种方法。修改启动类的扫描结构:

阅读更多

关于Java线程的一些思考

消费者和生产者的模型:

今天在看《现代操作系统》P73页的一个关于多线程的竞态条件的时候书中说到了唤醒等待位方法,这个方法使我突然想起联想到以前在Java多线程中sleep()方法会清除中断状态的一些类似之处:
树上的代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#definde N 100
int count =0;
void producer(void){
int item;
while(True){
item=producer_item();
if (count == N) sleep();
insert_item(item);
count=count+1;
if (count == 1 )wakeup(consumer);
}
}

void consumer(void){
int item;
while(true){
if (count == 0)sleep();
item =remove_item();
count=count -1;
if (count == N-1) wakeup(producer);
consumer_item()
}
}

在书中提到过一个情况就是:当消费者判断count==0的时候是会睡眠的,但是此时由于某种情况(线程的sleep()方法还没被执行完),而恰巧生产者又生产了一个item,导致此时count加一为1,而当count为1的时候生产者是会发出一个wakeup信号给消费者的,此时,由于消费者并没有睡眠因此会忽略掉该信号,而当消费者真正睡眠之后又由于生产者再不会进行通知,导致队列被生产者塞满,从而该模型阻塞。
那么为了解决该方法,书中引入了唤醒等待位方法,该方法就是在生产者发出信号给消费者的时候添加一个中断状态,而当该线程需要进行睡眠的时候会先判断状态,若是wakeup则不进行睡眠

Java多线程中的引用:

阅读更多

关于流和多态的一些记录

流的读取问题

read()方法

read()方法经常用于读取一个byte数组或者char数组,其内部的方法如下:

1
2
3
public final int read(byte b[]) throws IOException {
return in.read(b, 0, b.length);
}

首先在读取字节流的时候是所有的字节流的顶级类的是InputStream抽象类,而继承自Inputstream的类都是带有read方法,每一个类几乎丢重写了自己的read方法,而这就是多态的一种体现。

阅读更多

关于Java的HashMap

Map接口:

  1. 在map接口中的存在一个主接口:public interface Map 和一个内部接口:interface Entry
  2. 其中Map接口主要功能是提供map的一些基本的操作,例如put,inEmpty,get等,而Entry接口则主要是负责遍历操作时的一些方法,例如getKey(),getValue(),setValue

#HashMap实现类:

  1. 在HaspMap这个类里面其实包含了很多的内部类:如下图:
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    Node
    HashMap
    KeySet
    KeySpliterator
    EntrySet
    Values
    HashIterator
    KeyIterator
    ValueIterator
    EntryIterator
    HashMapSpliterator
    ValueSpliterator
    EntrySpliterator
    TreeNode

    TreeNode类: TreeNode类是一个红黑树:里面包含的是一些红黑树的操作;

    EntrySet类: EntrySet类是提供一个HashMap的遍历方式的一个类,EntrySet类里面有iterator方法,其作用在于map的一种遍历方式:

    1
    2
    3
    4
    5
    Iterator iterator =map.entrySet().iterator();
    while (iterator.hasNext()){
    Map.Entry<Object,Object> map1 = (Map.Entry<Object, Object>) iterator.next();
    System.out.println(map1.getKey());
    }
    这里涉及的知识是EntrySet是继承了AbstractSet间接实现了Set接口,而map.entrySet()方法返回的是一个Set<Map.Entry<K,V>>这个实例。

    其他的暂时还不知道有什么用

关于HashMap的其他细节

阅读更多

关于ArrayList的所见所想

关于ArrrayList扩容:

今天在面试的时候面试官提到过ArrayList扩容是原来的1.5倍加一,但是我看jdk1.8的时候是显示为1.5倍

查看源码:

1
2
3
4
5
6
7
8
9
10
11
12
//Java1.8的扩容方法
private void grow(int minCapacity) {
// overflow-conscious code
int oldCapacity = elementData.length;
int newCapacity = oldCapacity + (oldCapacity >> 1);
if (newCapacity - minCapacity < 0)
newCapacity = minCapacity;
if (newCapacity - MAX_ARRAY_SIZE > 0)
newCapacity = hugeCapacity(minCapacity);
// minCapacity is usually close to size, so this is a win:
elementData = Arrays.copyOf(elementData, newCapacity);
}

那么ArrayList会是扩充1.5倍之后加一呢?

阅读更多