如何构建Subejct
上一篇我们讲了Subject这个类,知道了在每一次访问时都会创建一个新的subject,而这个subject会绑定到ThreadContext上,然后通过SecurityUtils在程序的任何地方调用getSubject时都会返回同一个subject。以用户登录时的例子分析源码:
通过查看SecurityUtils源码可以看到,它是通过从ThreadContext上获取Subject,如果存在直接返回,否则通过Subject.Builder().buildSubject()去创建Subject,创建后再将Subject绑定到ThreadContext
接着通过查看Subject源码发现,其实它是一个interface,其中声明了一个Builder类
Builder类中有这么一个方法buildSubject(),它通过shiro核心组件SecurityManager调用createSubject()去创建需要的Subject,其中通过传入参数可以知道,它是使用SubjectContext来构建我们需要的Subject
查看SubjectContext源码可以知道其实它就是一个Map
DefaultSubjectContext是SubjectContext的实现类,又是MapContext的子类
而这一系列过程都是为了将构建subject的所有属性都组织到一起,然后传递给一个subjectFactory,用于构建一个subject
在DefaultSecurityManager中,通过doCreateSubject()方法将SubjectContext传递给SubjectFactory
通过SubjectFactory构建Subject,返回Subject的实现类DelegatingSubject,以及DelegatingSubject的子类WebDelegatingSubject