Spring Security/JSF/Hibernate Accidental Session H

2019-02-17 10:13发布

问题:

Something very strange and embarrassing happened to me the other day and I don't have words to describe what happened.

My app runs Spring 3 integrated with JSF 2.1, Hibernate 4, Spring Security all on Tomcat 7. I was over the phone with someone important from C-level and we were both simultaneously on the test environment at the same time on the same pages. He went to navigate to a page that I was navigating to at pretty much the same moment when his page came up with my personal account details. I didn't believe him, so I walked over to his office and sure enough, he somehow was logged on as my account which he doesn't have the password for.

The application will have protected patient health information so I was ordered to provide C-level a full report with what had happened, but I cannot find how this was possible. I scoured the code base and came up with nothing. I tried to reproduce the exact scenario on multiple occasions and was never able to reproduce it. I don't even have an educated guess that I am happy with.

I think perhaps there might have been some unsafe thread operation on sessions stored in the Tomcat application context implementation but I have no way to prove this if it is not reproducible. I also thought that since Spring Security operates as a Filter ahead of other requests and forwards that perhaps one of the other servlet filters interfered. The other two were the Primefaces File Upload filter and the Omnifaces SEO filter that I had recently added.

The Omnifaces filter did in fact interfere with the Primefaces File Upload filter that I had to tinker with its configuration so the two of them would play nice with each other, so I still feel like that might be a possibility too.

Are there any known bugs with Spring Security that have caused similar issues? Are there known issues with Tomcat regarding accidentally serving the wrong session state from the ApplicationContext? Has anybody else experienced a similar problem or have some unique insight into this?

EDIT: Shortly after posting this I found this, posted only a few days ago:

Session mix up - apache httpd with mod_jk, tomcat, spring security - serving data of other user

It is almost exactly the same setup as I have Apache httpd+mod_jk plugin in front of Tomcat so surely I am not crazy :)

UPDATE:

I was able to reproduce the issue in my development environment without mod_jk or Apache in front, so I can reliably rule this out as the culprit.

回答1:

I figured it out :)

It was sort of a developer error, but it is also a ridiculous default behavior of Spring. I had a JSF Managed Bean called SessionBean that I declared as @SessionScope. When you integrate JSF and Spring, the JSF dependency injection conflicts with Spring dependency injection so Spring rewrote the JSF module that handles that to just wrap Spring DI instead. So when I declare a JSF ManagedBean as Session Scoped, I must also give it a @Controller annotation so that it is recognized as a Spring Bean as well.

Turns out that Spring doesn't however understand the JSF @RequestScoped and @SessionScoped annotations. Spring has its own annotation called simply @Scope(value = "request|session|singleton?|etc...") .

Because Spring didn't recognize the JSF scope that I set, it treated the newly created bean in its default for beans, as a SINGLETON.

So everytime somebody logged on, it was overrwriting the property I used to cache the logged in user that I fetched from the Authentication Principal. Then everybody who did anything was logged on as a different user.

Nice of Spring by the way to warn you that you misconfigured your damn bean.

Thanks for everybodies help, I hope this benefits future visitors!