-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
BLZT-71 add PostConstruct functionality
* BLZT-71 add annotation * BLZT-71 add PostConstruct functionality * BLZT-71 refactoring * BLZT-71 add documentation * BLZT-71 fix imports in ReflectionUtils * BLZT-71 fixes
- Loading branch information
1 parent
100af02
commit 72c261c
Showing
9 changed files
with
248 additions
and
7 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
58 changes: 58 additions & 0 deletions
58
core/src/main/java/com/bobocode/bring/core/annotation/PostConstruct.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,58 @@ | ||
package com.bobocode.bring.core.annotation; | ||
|
||
import java.lang.annotation.ElementType; | ||
import java.lang.annotation.Retention; | ||
import java.lang.annotation.RetentionPolicy; | ||
import java.lang.annotation.Target; | ||
|
||
/** | ||
* <p>The {@code PostConstruct} annotation is used on a method that needs | ||
* to be executed after dependency injection is done to perform any | ||
* initialization. This method is called immediately after the bean's | ||
* properties have been set and the bean has been placed into the | ||
* Bring container.</p> | ||
* | ||
* <p>Methods annotated with {@code @PostConstruct} are invoked only once | ||
* in the bean's lifecycle, and they provide a convenient way to | ||
* initialize resources or perform any setup logic that is required | ||
* before the bean is ready for use.</p> | ||
* | ||
* <p>The method annotated with {@code @PostConstruct} must be non-static | ||
* and should not have any parameters, as it is meant to be an | ||
* initialization callback method for the bean instance. If multiple | ||
* methods are annotated with {@code @PostConstruct} within a single | ||
* class, the order of execution is not guaranteed.</p> | ||
* | ||
* <p>Example:</p> | ||
* <pre> | ||
* {@code | ||
* import com.bobocode.bring.core.annotation.PostConstruct; | ||
* | ||
* public class ExampleBean { | ||
* | ||
* private String message; | ||
* | ||
* @PostConstruct | ||
* public void init() { | ||
* message = "Hello, this is an example!"; | ||
* // Additional initialization logic | ||
* } | ||
* | ||
* public String getMessage() { | ||
* return message; | ||
* } | ||
* } | ||
* } | ||
* </pre> | ||
* | ||
* <p>In this example, the {@code init} method will be automatically | ||
* invoked after the {@code ExampleBean} is constructed, providing a | ||
* way to perform custom initialization logic.</p> | ||
* | ||
* @author Blyzhnytsia Team | ||
* @since 1.0 | ||
*/ | ||
@Retention(RetentionPolicy.RUNTIME) | ||
@Target(ElementType.METHOD) | ||
public @interface PostConstruct { | ||
} |
28 changes: 28 additions & 0 deletions
28
core/src/main/java/com/bobocode/bring/core/bpp/impl/PostConstructBeanPostProcessor.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
package com.bobocode.bring.core.bpp.impl; | ||
|
||
import com.bobocode.bring.core.annotation.BeanProcessor; | ||
import com.bobocode.bring.core.annotation.PostConstruct; | ||
import com.bobocode.bring.core.bpp.BeanPostProcessor; | ||
import com.bobocode.bring.core.exception.PostConstructException; | ||
|
||
import java.lang.annotation.Annotation; | ||
import java.lang.reflect.Method; | ||
|
||
import static com.bobocode.bring.core.utils.ReflectionUtils.processBeanPostProcessorAnnotation; | ||
|
||
|
||
@BeanProcessor | ||
public class PostConstructBeanPostProcessor implements BeanPostProcessor { | ||
|
||
@Override | ||
public Object postProcessInitialization(Object bean, String beanName) { | ||
Method[] declaredMethods = bean.getClass().getMethods(); | ||
try { | ||
processBeanPostProcessorAnnotation(bean, declaredMethods, PostConstruct.class); | ||
} catch (Exception exception) { | ||
throw new PostConstructException(exception); | ||
} | ||
|
||
return BeanPostProcessor.super.postProcessInitialization(bean, beanName); | ||
} | ||
} |
8 changes: 8 additions & 0 deletions
8
core/src/main/java/com/bobocode/bring/core/exception/PostConstructException.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
package com.bobocode.bring.core.exception; | ||
|
||
public class PostConstructException extends RuntimeException { | ||
public static String POST_CONSTRUCT_EXCEPTION_MESSAGE ="@PostConstruct should be added to method without parameters"; | ||
public PostConstructException(Throwable cause) { | ||
super(POST_CONSTRUCT_EXCEPTION_MESSAGE, cause); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
37 changes: 37 additions & 0 deletions
37
core/src/test/java/com/bobocode/bring/core/bpp/impl/PostConstructBeanPostProcessorTest.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
package com.bobocode.bring.core.bpp.impl; | ||
|
||
import com.bobocode.bring.core.BringApplication; | ||
import com.bobocode.bring.core.exception.PostConstructException; | ||
import org.junit.jupiter.api.Test; | ||
import org.junit.jupiter.api.function.Executable; | ||
import testdata.postconstruct.positive.CustomPostConstruct; | ||
|
||
import static org.assertj.core.api.Assertions.assertThat; | ||
import static org.junit.jupiter.api.Assertions.assertThrows; | ||
|
||
class PostConstructBeanPostProcessorTest { | ||
|
||
@Test | ||
void shouldFillMessage_postProcessInitialization() { | ||
//given | ||
var bringApplicationContext = BringApplication.run("testdata.postconstruct.positive"); | ||
|
||
//when | ||
var myCustomPostConstruct = bringApplicationContext.getBean(CustomPostConstruct.class); | ||
|
||
//then | ||
assertThat(myCustomPostConstruct.getMessage()).isEqualTo("Hello!"); | ||
} | ||
|
||
@Test | ||
void shouldThrowException_postProcessInitialization() { | ||
//given | ||
var expectedMessage = "@PostConstruct should be added to method without parameters"; | ||
// when | ||
Executable executable = () -> BringApplication.run("testdata.postconstruct.negative"); | ||
|
||
// then | ||
PostConstructException postConstructException = assertThrows(PostConstructException.class, executable); | ||
assertThat(postConstructException.getMessage()).isEqualTo(expectedMessage); | ||
} | ||
} |
17 changes: 17 additions & 0 deletions
17
core/src/test/java/testdata/postconstruct/negative/CustomPostConstruct.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
package testdata.postconstruct.negative; | ||
|
||
import com.bobocode.bring.core.annotation.Component; | ||
import com.bobocode.bring.core.annotation.PostConstruct; | ||
import lombok.Getter; | ||
|
||
@Getter | ||
@Component | ||
public class CustomPostConstruct { | ||
|
||
private String message; | ||
|
||
@PostConstruct | ||
public void fillMessage(String invalidParam) { | ||
message = "Hello!"; | ||
} | ||
} |
17 changes: 17 additions & 0 deletions
17
core/src/test/java/testdata/postconstruct/positive/CustomPostConstruct.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
package testdata.postconstruct.positive; | ||
|
||
import com.bobocode.bring.core.annotation.Component; | ||
import com.bobocode.bring.core.annotation.PostConstruct; | ||
import lombok.Getter; | ||
|
||
@Component | ||
@Getter | ||
public class CustomPostConstruct { | ||
|
||
private String message; | ||
|
||
@PostConstruct | ||
public void fillMessage() { | ||
message = "Hello!"; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,66 @@ | ||
# @PostConstruct | ||
|
||
## Introduction | ||
|
||
In the Bring framework, `@PostConstruct` is a method-level annotation used to indicate that a method should be invoked immediately after an instance of the bean is constructed, and before any other initialization logic occurs. | ||
## Usage | ||
|
||
To use `@PostConstruct`, follow these steps: | ||
|
||
1. **Add the Annotation**: Place the `@PostConstruct` annotation on a method within your Bring bean class. | ||
|
||
```java | ||
import com.bobocode.bring.core.annotation.PostConstruct; | ||
|
||
public class MyBean { | ||
|
||
@PostConstruct | ||
public void init() { | ||
// Initialization logic here | ||
// This method will be called after bean instantiation. | ||
} | ||
} | ||
``` | ||
|
||
|
||
2. **Invoke the Bring Container**: Make sure that you obtain the bean from the Bring container. The `@PostConstruct` annotated method will be automatically invoked. | ||
|
||
```java | ||
import com.bobocode.bring.core.BringApplication; | ||
|
||
public class MyApp { | ||
public static void main(String[] args) { | ||
var bringApplicationContext = BringApplication.run("your.path"); | ||
var myBean = bringApplicationContext.getBean(CustomPostConstruct.class); | ||
// Your bean is now initialized, and @PostConstruct method has been called. | ||
} | ||
} | ||
``` | ||
|
||
## Important Points | ||
|
||
- The method annotated with `@PostConstruct` must not have any parameters. | ||
- This annotation is generally used in conjunction with the `@Component` stereotype annotations (e.g., `@Service`, `@Repository`, `@Controller`) or in configuration classes. | ||
- The `@PostConstruct` method will be invoked after the bean has been constructed and before any custom initialization logic specified in the bean definition. | ||
|
||
## Example | ||
|
||
Here is a simple example of a class using `@PostConstruct`: | ||
|
||
```java | ||
import com.bobocode.bring.core.annotation.PostConstruct; | ||
|
||
public class ExampleBean { | ||
|
||
private String message; | ||
|
||
@PostConstruct | ||
public void init() { | ||
message = "Hello, this is an example!"; | ||
// Additional initialization logic | ||
} | ||
|
||
public String getMessage() { | ||
return message; | ||
} | ||
} |