Announcement Announcement Module
Collapse
No announcement yet.
How to make sure beans created via Spring Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • How to make sure beans created via Spring

    Hi,

    I've got a pretty basic (and hopefully easy to solve) problem. My app. is using Spring/Acegi Security and I couldn't be happier. In my opinon, Spring is (after water and air) the nicest thing around.

    My question is simple: Can I somehow enforce, that my managers/daos are only (!) created by Spring? I mean,
    Code:
    this.entityManager = (IEntityManager)getBean(SpringBean.MANAGER_ENTITY);
    works great but if another developer, who doesn't know Spring uses something like
    Code:
    this.entityManager = new EntityManager();
    nothing will work, since Spring is simply bypassed, yet the code is absolutely vaild. What can I do, to make sure, that the Spring is actually used to instantiate my beans, apart from documenting it?

    Regards,
    Tom

  • #2
    Interesting question.

    There are things you can do to ensure that beans are correctly instantiated by Spring (implementing InitializingBean), but I don't know of any way to ensure that Spring creates the beans.

    Basically; communicate

    Comment


    • #3
      You could turn your objects into singletons (private constructor, static getInstance method, surely you know the drill) and let spring instantiate them using the factory-method attribute.

      Comment


      • #4
        Originally posted by Kees de Kooter
        You could turn your objects into singletons (private constructor, static getInstance method, surely you know the drill) and let spring instantiate them using the factory-method attribute.
        But then all my managers would have to be singletons and I am not sure I want that. Apart from that, what keeps users from calling myManger.getInstance(). Doesn't that only shift the problem to another location?

        Apart from that, I have yet another question: My daos are also spring-managed and injected into my managers, yet only my managers are using declarative transactions. So how do I keep other programmers from using my daos? They should ONLY be accessed by the manager classes. The only (ugly) solution I can think of, is to turn all daos into (private) inner classes of the corresponding manager - but I don't want to do this.

        Any ideas?

        Regards,
        Tom

        Comment


        • #5
          Why would you want to prevent that your classes are being reused, and why would you want to force using Spring?
          I can give you multiple reason for not preventing this:
          • One of the key advantages of dependency injection (DI) is better re-use because you code to interfaces iso implementations. So don't prevent re-use.
          • One of the key advantages of Spring is that your code is not aware of it, so that it can be re-used without Spring.
          • It is even recommended NOT to use Spring in your unit tests, but explicitly calling setters for DI.
          You should document your code so that anyone who wants to re-use it without using Spring, knows which dependencies to resolve after instantiating an object.

          Ivo

          Comment


          • #6
            Hi Ivo,

            as I said before, only my managers have transaction support. Right now, it is possible, to access a DAO via Spring and load an object via Hibernate. Great - but if you want to access any (all) collections, you'll get the infamous LazyInitializationException because the sessions is already closed. Yet if I can prevent other programmers from directly accessing the DAOs, this will not happen.

            I do not think that reusing the objects without Spring (although possible) is something you really want/need. Imagine 50% of your objects being spring-managed and the other 50% not. How would you ever now how to instantiate which object?

            My aim would be to have a simple and clean API that exposes only relevant objects. Why should front-end developers know anything about Hibernate, transactions and DAOs, when the business layer is all the ought to be concerned with?

            Regards,
            Tom

            Comment


            • #7
              Tom,

              As I understand it, your EntityManager class is simply not part of your public API. So you should just state this in the javadoc iso preventing that objects are being instantiated. Your public API should only contain the IEntityManager interface.
              You could go one step further and provide a factory for your manager classes, so that client programmers don't even have to know anything about Spring.

              All API's that I've used so far take the same aproach: if you know what you're doing and you realy want to use internal classes, you may do so at your own risk.

              Ivo

              Comment


              • #8
                How about build time?

                And if you're still nervious, build in some sort of check at build time. If you keep your interfaces in a different package than the implementations, simply grepping for usage of the impls should work.

                Comment

                Working...
                X