Class Swappers
This class provides built-in object transformation strategies that handle common wrapper
types and asynchronous objects. These swappers are automatically registered when using
BasicBeanConverter.Builder.defaultSettings()
.
Purpose:
Swappers pre-process objects before stringification or listification, enabling the converter to handle wrapper types, lazy evaluation objects, and asynchronous results consistently. They transform objects into more primitive forms that can be easily converted to strings or lists.
Built-in Swappers:
optionalSwapper()
- UnwrapsOptional
values to their contained objects ornull supplierSwapper()
- EvaluatesSupplier
functions to get their supplied valuesfutureSwapper()
- Extracts completedFuture
results or returns status messages
Usage Example:
Custom Swapper Development:
When creating custom swappers, follow these patterns:
- Null Safety: Handle
null inputs gracefully - Exception Handling: Convert exceptions to meaningful error messages
- Status Indication: Provide clear status for incomplete or error states
- Non-blocking: Avoid blocking operations that might hang tests
- Recursion Prevention: Ensure swappers don't create circular transformations that could lead to
StackOverflowError
. The framework does not check for recursion, so developers must avoid registering swappers that transform objects back to types that would trigger the same or other swappers in an endless cycle.
-
Method Summary
Modifier and TypeMethodDescriptionReturns a swapper forFuture
objects that extracts completed results or status information.Returns a swapper forOptional
objects that unwraps them to their contained values.Returns a swapper forSupplier
objects that evaluates them to get their supplied values.
-
Method Details
-
optionalSwapper
Returns a swapper forOptional
objects that unwraps them to their contained values.This swapper extracts the value from Optional instances, returning the contained object if present, or
null if the Optional is empty. This allows Optional-wrapped values to be processed naturally by the converter without special handling.Behavior:
- Present value: Returns the contained object for further processing
- Empty Optional: Returns
null , which will be rendered as the configured null value
Usage Examples:
// Test Optional with value var optional = Optional.of ("Hello" );assertBean (optional ,"<self>" ,"Hello" );// Test empty Optional var empty = Optional.empty ();assertBean (empty ,"<self>" ,"<null>" );// Test nested Optional in object var user =new User().setName(Optional.of ("John" ));assertBean (user ,"name" ,"John" );Integration:
This swapper is particularly useful when working with modern Java APIs that return Optional values. It allows test assertions to focus on the actual data rather than Optional wrapper mechanics.
-
supplierSwapper
Returns a swapper forSupplier
objects that evaluates them to get their supplied values.This swapper calls the
Supplier.get()
method to obtain the value that the supplier provides. This enables testing of lazy-evaluated or dynamically-computed values as if they were regular objects.Behavior:
- Successful evaluation: Returns the result of calling
Supplier.get()
- Exception during evaluation: Allows the exception to propagate (no special handling)
Usage Examples:
// Test supplier with simple value var supplier = () ->"Hello World" ;assertBean (supplier ,"<self>" ,"Hello World" );// Test supplier in object property var config =new Configuration().setDynamicValue(() -> calculateValue());assertBean (config ,"dynamicValue" ,"computed-result" );// Test supplier returning null var nullSupplier = () ->null ;assertBean (nullSupplier ,"<self>" ,"<null>" );Important Notes:
- Side Effects: The supplier will be evaluated during conversion, which may cause side effects
- Performance: Expensive computations in suppliers will impact test performance
- Exception Handling: Exceptions from suppliers are not caught by this swapper
- Successful evaluation: Returns the result of calling
-
futureSwapper
Returns a swapper forFuture
objects that extracts completed results or status information.This swapper handles
Future
objects in a non-blocking manner, providing meaningful information about the future's state without waiting for completion:Behavior:
- Completed successfully: Returns the actual result value
- Completed with exception: Returns
"<error: {message}>" format - Cancelled: Returns
"<cancelled>" - Still pending: Returns
"<pending>"
Usage Examples:
// Test completed future var future = CompletableFuture.completedFuture ("Hello" );assertBean (future ,"<self>" ,"Hello" );// Test pending future var pending =new CompletableFuture<String>();assertBean (pending ,"<self>" ,"<pending>" );// Test cancelled future var cancelled =new CompletableFuture<String>();cancelled .cancel(true );assertBean (cancelled ,"<self>" ,"<cancelled>" );// Test failed future var failed =new CompletableFuture<String>();failed .completeExceptionally(new RuntimeException("Test error" ));assertBean (failed ,"<self>" ,"<error: Test error>" );Non-blocking Guarantee:
This swapper never calls
Future.get()
without first checkingFuture.isDone()
, ensuring that test execution is never blocked by incomplete futures. This makes it safe to use in unit tests without risking hangs or timeouts.Error Handling:
When a future completes exceptionally, the swapper extracts the exception message and formats it as
"<error: {message}>" . This provides useful debugging information while maintaining a consistent string format for assertions.
-