How do you deal with the extra complexity added by spring beans?

I have been writing software for many years and have always tried to create expressive, understandable, user-friendly, reliable code. I recently joined a team developing web applications using Spring managed objects. But I am very uncomfortable with this technology. For me, it seems that all the principles of encapsulation and information hiding, the achievements of decades of software development were simply abandoned. I clearly see the advantages of using the Inversion of Control container to move system dependencies from program code to configuration files. But now I see that Spring is used in such a way that, I believe, just adds unnecessary complexity without any benefit.

Using Spring to create support for webapp beans, objects will no longer be clearly organized in modules and will no longer have the highest possible visibility. Instead, there is now one global bean namespace. Because of this, objects tend to get terrible names such as "pendingOrderCustomerName", and to make matters worse, such names do not even clearly identify a clearly defined object, because bean definitions can come from various definition sources collected from explicitly defined locations: instead of just being defined by the class in the package, Spring beans are assembled from xml files with free overriding capabilities and weakly defined relationships.

For example, when I have the type "Account" in simple Java, in the package "my.webstore", I usually know about the properties, relationships and features of this type in one place, "my / webstore" /Account.java ". Instances "Accounts" exist as links to objects that work with accounts, the state of any instance is precisely determined by the class. However, things are complicated with Spring beans: the "Account" instance now exists under a global name in the container management area, which has state collected from xml files found by file search path based on naming templates ...

Gone are the days when, in order to understand what an object does and how it behaves, you just had to read its source program. Today you need a java source object (which can be quite complicated to understand), plus you have to find any configuration files that can change this object, which is not so simple, because you need to find out all the ways from which the configuration can arise need to figure out in which order they redefine each other

Maybe this is just a matter of taste, but I also wonder why people prefer the detailed, clumsy xml syntax, as in:

<bean id="p1" class="Point" scope="prototype"> <property name="x"> <value>20</value> </property> <property name="y"> <value>80</value> </property> </bean> 

above this:

  p1 = new Point(20,80); 

This example may seem exaggerated, but I tell you that I have seen worse!

I do not intend to criticize the Spring framework by itself; it is very strong and is an excellent ingredient in many cases. My problems relate to how to prevent misuse, how to maintain maintainability, how to guarantee quality and stability, how to find dependencies, how to document code ... what is your experience?

+4
source share
2 answers

As you saw, it's pretty easy to abuse Spring if you don't understand the principles of object-oriented design correctly. The Spring IoC container (let's forget about the rest for now, as there is a huge portfolio of libraries under the Spring umbrella) really shines when you use it:

  • Define a component model (e.g., controllers, services, repositories, and their dependencies)
  • centralize component dependency searches (for example, replace service locators, JNDI searches, or other stateless component search strategies)
  • Decorate components with technical aspects (e.g., transaction management, caching, access control, etc.).

Spring, or any IoC container, allows you to have a single component model, remove a lot of template code, and isolate cross-cutting issues in centralized ways. It should also push you to implement a system consisting of loosely coupled components focused on the implementation of business logic, which will improve readability, testability and ease of maintenance in the end.

Of course, you won’t get anything (and actually lose a lot) if you start defining Account and Point as Spring components. They must still be created as objects or objects of value. They should still be part of the proper package, and appropriate visibility modifiers should be applied. They still need to be created, managed and managed using strategies that you would use if your application did not use the IoC container.

It seems that you already know the principles of reasonable design, so I would advise you to trust your instincts. If the class is a reusable (and often stagnant) component, declare it as a Spring component and enter it where necessary. If you're not sure, leave this as a regular, unmanaged class and use it normally. You will understand where it makes sense to declare components, and where not.

I also recommend that you learn how to use @Component and <context:component-scan> declarations to reduce the amount of XML data.

Good luck.

+2
source

Many Spring features are misused. I'm used to thinking the same way you do, but recently, when I understood more about Spring, I started to like this, despite the fact that any dependency injection infrastructure would do, and I would prefer Guice over Spring if I have a choice.

The problem is that people know how to use Spring, but not why. Especially when not using it. Spring beans are useful when you have several implementations. This is where addiction is poured. In your example, I, of course, hope that Point does not have any other implementations, and thus Spring has been misused.

For me, Guice's motivation led me to understand more about dependency injection; it treats Spring equally well.

However, you can check Spring annotations to see how your configuration and code can be stored in one place.

0
source

Source: https://habr.com/ru/post/1484159/


All Articles