Announcement Announcement Module
No announcement yet.
Stateful Services and storing with User Principal Page Title Module
Move Remove Collapse
This topic is closed
Conversation Detail Module
  • Filter
  • Time
  • Show
Clear All
new posts

  • Stateful Services and storing with User Principal


    I am currently working with a legacy system and trying to migrate it to Spring and Spring Security.

    The system has a legacy data access layer (with clients exposed by a factory) that is essentially stateful. It is currently stored in the HttpSession.

    e.g. UserClient uc = factory.getUserClient();
    Basically, these data access clients are the only way to access the database. They are stateful because they send certain pieces of User information along with every request to the backend.

    My question; would it make sense to store this factory as part of the User Principial in the SecurityContext? This is because once I am authenticated, I need to store this special factory.

    Any comments/help/discussion would be appreciated.

  • #2
    for me it makes sense, because that factory is closely related to the authenticated user, so it feels logic that that user has a reference to "his" factory.

    I hope this help you.


    • #3
      Thank you. Thats my opinion as well.

      Im now wondering about how I would go about retrieving these services? Would I provide a UserService (UserDetailsService) that retrieves the User from the AuthenticationContext and then obtain this factory? Or would there be a better approach that Im missing? I guess, it appears that Im trying to make services that appear stateless, but that use this factory in the background.


      • #4
        i'd create my own implementation for UserDetails and UserDetailsService.
        Then configure spring to use my UserDetailsService for authentication.

        If someone is authenticated you can access that UserDetails like:

        Originally posted by spring security reference 5.2.1
        Object obj = SecurityContextHolder.getContext().getAuthentication().getPrincipal();
        Off course you'd check if the obtained object object is an instance of your userdetails implementation.


        • #5
          Thank you, thats right along the lines that Im thinking.

          Im just slightly concerned here, is it not a problem that all my services would be retrieving the Principal in this way, just to get access to the factory? It seems to go against the grain of DI a bit.

          On the other hand, this seems better than the current situation, where this stateful factory is stored on the HttpSession and passed into the service methods.

          service.retrieveBook(factory, 123);
          Code like that is exactly what Im trying to avoid, since its currently being used to propogate everything down into the service layer.

          In fact, the code is typically uglier than above. It generally looks like:

          service.retrieveBook(session, 123);


          • #6
            i'd do the following (don't look at the names, it's the idea that counts):

            create a clean data access interface (as if you don't need to use the legacy system).

            interface CleanDataInterface{
            Book findBook(int id);
            Your services would use that clean interface.

            Then you create an implementation that adopts the method call to the legacy system. (adapter pattern)

            public class AdapterImplementation implements CleanDataInterface{
            public Book findBook(int id){
            //retrieve principal from securitycontext and get factory, //probably using a helper class return legacyDataLayer.findBook(factory.getNeededUserInformation, id);
            If ever you decide to abandon the legacy data system, you only have to write another implementation of the CleanDatainterface, your other layers aren't affected.
            Last edited by davymeers; Jun 23rd, 2009, 05:16 AM.


            • #7
              I like your solution. Thank you for the help.