or run

tessl search
Log in

Version

Workspace
tessl
Visibility
Public
Created
Last updated
Describes
mavenpkg:maven/io.quarkus/quarkus-resteasy-reactive@3.15.x

docs

index.md
tile.json

tessl/maven-io-quarkus--quarkus-resteasy-reactive

tessl install tessl/maven-io-quarkus--quarkus-resteasy-reactive@3.15.0

A Jakarta REST implementation utilizing build time processing and Vert.x for high-performance REST endpoints with reactive capabilities in cloud-native environments.

caching.mddocs/reference/

Caching

Quarkus REST provides declarative HTTP caching through annotations that set Cache-Control headers on responses.

Import

import org.jboss.resteasy.reactive.Cache;
import org.jboss.resteasy.reactive.NoCache;

@Cache

Sets Cache-Control header directives for HTTP caching.

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Cache {
    int maxAge() default -1;              // max-age in seconds (-1 = not set)
    int sMaxAge() default -1;             // s-maxage in seconds (-1 = not set)
    boolean noStore() default false;      // no-store directive
    boolean noTransform() default false;  // no-transform directive
    boolean mustRevalidate() default false;      // must-revalidate directive
    boolean proxyRevalidate() default false;     // proxy-revalidate directive
    boolean isPrivate() default false;    // private directive
    boolean noCache() default false;      // no-cache directive
}

@NoCache

Sets Cache-Control: no-cache header, optionally for specific fields.

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface NoCache {
    String[] fields() default {};  // Specific fields for no-cache (empty = all)
}

Usage

Basic Caching

@GET
@Path("/{id}")
@Cache(maxAge = 3600)  // Cache for 1 hour
public Item get(@RestPath String id) {
    return itemService.findById(id);
}

Private Cache

@GET
@Path("/user/profile")
@Cache(maxAge = 300, isPrivate = true)  // Cache for 5 minutes, private only
public UserProfile getProfile() {
    return userService.getCurrentProfile();
}

Shared Cache

@GET
@Path("/public/data")
@Cache(maxAge = 86400, sMaxAge = 3600)  // Client: 24h, Proxy: 1h
public PublicData getData() {
    return dataService.getPublicData();
}

Must Revalidate

@GET
@Path("/critical")
@Cache(maxAge = 300, mustRevalidate = true)  // Must revalidate when stale
public CriticalData getCritical() {
    return dataService.getCritical();
}

No Store

@GET
@Path("/sensitive")
@Cache(noStore = true)  // Do not store in any cache
public SensitiveData getSensitive() {
    return dataService.getSensitive();
}

No Cache

@GET
@Path("/dynamic")
@NoCache  // Always revalidate with server
public DynamicData getDynamic() {
    return dataService.getDynamic();
}

@GET
@Path("/user")
@NoCache(fields = {"password", "token"})  // No-cache for specific fields
public User getUser() {
    return userService.getCurrentUser();
}

Combined Directives

@GET
@Path("/data")
@Cache(
    maxAge = 600,           // 10 minutes
    sMaxAge = 300,          // 5 minutes for proxies
    mustRevalidate = true,  // Must revalidate when stale
    isPrivate = false,      // Can be cached by proxies
    noTransform = true      // No transformation allowed
)
public Data getData() {
    return dataService.getData();
}

Cache-Control Header Examples

AnnotationResulting Header
@Cache(maxAge = 3600)Cache-Control: max-age=3600
@Cache(maxAge = 3600, isPrivate = true)Cache-Control: private, max-age=3600
@Cache(maxAge = 3600, sMaxAge = 1800)Cache-Control: max-age=3600, s-maxage=1800
@Cache(noStore = true)Cache-Control: no-store
@Cache(mustRevalidate = true)Cache-Control: must-revalidate
@NoCacheCache-Control: no-cache
@NoCache(fields = {"password"})Cache-Control: no-cache="password"

Best Practices

Static Resources

@GET
@Path("/static/{file}")
@Cache(maxAge = 31536000)  // Cache for 1 year
public File getStaticFile(@RestPath String file) {
    return fileService.getStatic(file);
}

User-Specific Data

@GET
@Path("/user/data")
@Cache(maxAge = 60, isPrivate = true)  // Short cache, private only
public UserData getUserData() {
    return userService.getCurrentUserData();
}

Frequently Changing Data

@GET
@Path("/live/data")
@NoCache  // Always fresh
public LiveData getLiveData() {
    return dataService.getLiveData();
}

Public API Data

@GET
@Path("/api/public")
@Cache(maxAge = 300, sMaxAge = 600)  // Client: 5min, Proxy: 10min
public ApiData getPublicApi() {
    return apiService.getPublicData();
}

Conditional Caching

Combine with ETag and Last-Modified headers for conditional requests:

@GET
@Path("/{id}")
@Cache(maxAge = 3600, mustRevalidate = true)
public Response get(@RestPath String id, @Context Request request) {
    Item item = itemService.findById(id);

    EntityTag etag = new EntityTag(item.getVersion());
    Response.ResponseBuilder builder = request.evaluatePreconditions(etag);

    if (builder != null) {
        // Client has current version, return 304 Not Modified
        return builder.build();
    }

    // Return full response with ETag
    return Response.ok(item)
        .tag(etag)
        .build();
}

Programmatic Cache Control

For dynamic cache control, use Response builder:

@GET
@Path("/{id}")
public Response get(@RestPath String id) {
    Item item = itemService.findById(id);

    int maxAge = item.isMutable() ? 60 : 3600;

    CacheControl cacheControl = new CacheControl();
    cacheControl.setMaxAge(maxAge);
    cacheControl.setPrivate(item.isPrivate());

    return Response.ok(item)
        .cacheControl(cacheControl)
        .build();
}