Issue
In the SonarQube scan, it shows a major bug at the below-mentioned lines. The issue says, Singleton class writes to a field in an unsynchronized manner. I am not able to figure out, why this is an issue?
@Configuration
@ConfigurationProperties(prefix = "app")
public class UrlConfigs() {
@Autowired
private List<UrlItems> item;
//Getter & Setter
}
@Component
public class UrlItems {
private String url;
private String location;
// Getter
public void setUrl(String url){
this.url = url; // ISSUE: Singleton class writes to a field in an unsynchronized manner
}
public void setLocation(String location) {
this.location = location; // ISSUE: Singleton class writes to a field in an unsynchronized manner
}
}
Solution
Typically classes annotated with spring‘s @Component
annotation are singletons unless a different scope (like request) is specified. That is the very same instance of this class will be injected by spring in each and every place this class is autowired. By providing a setter for internal fields of the singleton separate threads could set the value in an unsynchronized way, messing up the internal logic of your class.
Typically SonarQube should provide additional information and hints on how to solve warnings like this.
The most simple fix for the warning would be to add the synchronized
keyword to the setter methods. To make your code at least potentially correct this synchronization would need to be added to all read and write usages of the respective members. And this will most likely result in other issues - not talking about performance…
The question should be
Why do you need state in an @Component class and are there ways to avoid this state?
To answer this it would be needed to know how this class and it’s members are actually used.
If you’re only using UrlItems
in the context of the @ConfigurationProperties class you don’t need to auto wire it and don’t need an @Component class but a simple Java bean. Spring will create instances of this class as needed.
Answered By - dpr