apache / apache/dubbo

[Feature] Avoid Calling Other Methods in Constructors

Open
#15,600 3 comments 0 reactions 3 assignees Claimed by @redoom View on GitHub
help wanted type/bug
Dominant language
Java
Stars
41.6k
Forks
26.4k
Avg merge
15h 13m
Merged PRs (30d)
4

Description

### Pre-check

- [x] I am sure that all the content I provide is in English.

### Search before asking

- [x] I had searched in the [issues](https://github.com/apache/dubbo/issues?q=is%3Aissue) and found no similar feature requirement.

### Apache Dubbo Component

Java SDK (apache/dubbo)

### Descriptions

**Key Reasons to Avoid Child Method Calls in Constructors**

1. ‌Incomplete Object Initialization‌: When a constructor calls other methods, those methods might execute before the object is fully initialized, leading to potential NullPointerExceptions or inconsistent states.
2. Inheritance Issues‌: If the called method is overridden by a subclass, the subclass version will execute before the subclass constructor completes, violating the expected initialization order.
3. Reduced Code Clarity‌: Constructors should focus solely on initialization. Adding method calls makes the code harder to understand and maintain.
4. Testing Difficulties‌: Methods called during construction make unit testing more complex, as you can't test the constructor independently from those methods.

**Better Alternatives**
Instead of calling methods in constructors:

- Initialize fields directly
- Use factory methods
- Implement lazy initialization
- Apply the Initialization-on-demand holder idiom for singletons

**Example of Problematic Code**

```
public abstract class AAA {
public AAA() {
System.out.println("Build AAA");
initialize();
}

protected void initialize();
}

public class BBB extends AAA {
private final FFF myFinal = new FFF();

public BBB() {
super();
System.out.println("Build BBB");
}

@Override
public void initialize() {
System.out.println("Run initialize");
new Thread(() -> {
// The assertion might fail because myFinal isn't initialized during running BBB construction.
Assertions.assertNotNull(myFinal);
}).start();
}
}

public class FFF {
public FFF() {
System.out.println("Build FFF");
}
}
```

**Help Wanted**
Keeping constructors simple and focused on field initialization to create more maintainable and reliable code that properly follows object-oriented principles.

### Related issues

[During the initialization process of AbstractServer, the doOpen() method publishes the uninitialized internal state to the external thread, resulting in: "this.dubboChannels" is null](https://github.com/apache/dubbo/issues/14848)

### Are you willing to submit a pull request to fix on your own?

- [ ] Yes I am willing to submit a pull request on my own!

### Code of Conduct

- [x] I agree to follow this project's [Code of Conduct](https://www.apache.org/foundation/policies/conduct)

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.