User-based content filtering
Fluxzero provides a flexible way to redact or tailor object content per user using the @FilterContent
annotation.
This enables domain models or documents to define exactly what is visible to different users, based on roles, ownership, or context.
Basic example
Section titled “Basic example”@FilterContentOrder filter(User user) { return user.hasRole(Role.admin) ? this : new Order(maskSensitiveFieldsOnly());}@FilterContentfun filter(user: User): Order { return if (user.hasRole(Role.admin)) this else Order(maskSensitiveFieldsOnly())}To invoke filtering:
Order filtered = Fluxzero.filterContent(order, currentUser);val filtered: Order = Fluxzero.filterContent(order, currentUser)Recursive filtering
Section titled “Recursive filtering”Filtering applies recursively to fields and nested objects.
If a nested item is a list, map, or complex structure, it will also be filtered using its own @FilterContent method if present.
If a nested object returns null from filtering:
- It is removed from a list
- It is excluded from a map
Root context injection
Section titled “Root context injection”Filtering methods can optionally accept both:
- The current
User - The root object being filtered
This is useful for making decisions based on global context.
@FilterContentLineItem filter(User user, Order root) { return root.isOwner(user) ? this : null;}@FilterContentfun filter(user: User, root: Order): LineItem? { return if (root.isOwner(user)) this else null}Manual filtering
Section titled “Manual filtering”Developers can explicitly apply filtering by calling Fluxzero.filterContent(object, user) when they want precise control over when and how filtering occurs.
This is useful when you want to:
- Filter only part of a response
- Aggregate or transform data before filtering
- Perform filtering outside of handler contexts
For example, you may want to manually filter a document before returning it from a method:
public Optional<Order> getFilteredOrder(User user, OrderId orderId) { Optional<Order> order = Fluxzero.getDocument(orderId, "orders"); return Fluxzero.filterContent(order, user);}fun getFilteredOrder(user: User, orderId: OrderId): Order? { val order = Fluxzero.getDocument(orderId, "orders") return Fluxzero.filterContent(order, user)}Automatic filtering
Section titled “Automatic filtering”Filtering can be triggered automatically for request results when @FilterContent is also applied to the handler method, its class, or its package (or parent package).
This eliminates the need to call Fluxzero.filterContent(...) manually in many cases.
- Method level: filters results of a specific handler method
- Type level: filters results of all handler methods in a class
- Package level: filters results of all handler methods in a package or subpackage
For example, you can annotate a query handler so that all results it returns are automatically filtered based on the current user.
public record GetOrder(OrderId orderId) implements Request<Order> { @HandleQuery @FilterContent public Optional<Order> handle() { return Fluxzero.getDocument(orderId, "orders"); } } data class GetOrder(val orderId: OrderId) : Request<Order?> { @HandleQuery @FilterContent fun handle(): Order? { return Fluxzero.getDocument(orderId, "orders") } }Explicit filtering remains available for finer-grained control.
© 2026 Fluxzero