From: Robert Varga Date: Wed, 6 Dec 2023 08:15:43 +0000 (+0100) Subject: Allow dataPUT() to control ETag/Last-Modified X-Git-Tag: v7.0.0~192 X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?a=commitdiff_plain;h=1b27f137e0c1b1efc863f75f3a78bf47713b4203;hp=6abc1687ad1712848535a7be07d3dce323afd018;p=netconf.git Allow dataPUT() to control ETag/Last-Modified When creating or replacing a data resource, the underlying strategy should be free to indicate ETag/Last-Modified headers. Allow this information to be communicated via DataPutResult and pick it up when generating a Response. JIRA: NETCONF-1207 Change-Id: I86b726fcaa5bfb7d762483f007d6de77b894f802 Signed-off-by: Robert Varga --- diff --git a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/jaxrs/JaxRsRestconf.java b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/jaxrs/JaxRsRestconf.java index 1b7d8b90ee..d593a6ccbd 100644 --- a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/jaxrs/JaxRsRestconf.java +++ b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/jaxrs/JaxRsRestconf.java @@ -608,11 +608,10 @@ public final class JaxRsRestconf implements ParamConverterProvider { future.addCallback(new JaxRsRestconfCallback<>(ar) { @Override Response transform(final DataPutResult result) { - return switch (result) { - // Note: no Location header, as it matches the request path - case CREATED -> Response.status(Status.CREATED).build(); - case REPLACED -> Response.noContent().build(); - }; + // Note: no Location header, as it matches the request path + final var builder = result.created() ? Response.status(Status.CREATED) : Response.noContent(); + fillConfigurationMetadata(builder, result); + return builder.build(); } }); } diff --git a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/rfc8040/rests/transactions/RestconfStrategy.java b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/rfc8040/rests/transactions/RestconfStrategy.java index 6c2de8a46d..a1313afcd0 100644 --- a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/rfc8040/rests/transactions/RestconfStrategy.java +++ b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/nb/rfc8040/rests/transactions/RestconfStrategy.java @@ -179,6 +179,8 @@ public abstract class RestconfStrategy { } private static final Logger LOG = LoggerFactory.getLogger(RestconfStrategy.class); + private static final @NonNull DataPutResult PUT_CREATED = new DataPutResult(true); + private static final @NonNull DataPutResult PUT_REPLACED = new DataPutResult(false); private final @NonNull ImmutableMap localRpcs; private final @NonNull ApiPathNormalizer pathNormalizer; @@ -376,7 +378,7 @@ public abstract class RestconfStrategy { Futures.addCallback(commitFuture, new FutureCallback() { @Override public void onSuccess(final CommitInfo result) { - ret.set(exists ? DataPutResult.REPLACED : DataPutResult.CREATED); + ret.set(exists ? PUT_REPLACED : PUT_CREATED); } @Override diff --git a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/DataPutResult.java b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/DataPutResult.java index 019b0476cc..7ff715e7f9 100644 --- a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/DataPutResult.java +++ b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/DataPutResult.java @@ -7,18 +7,23 @@ */ package org.opendaylight.restconf.server.api; +import java.time.Instant; +import org.eclipse.jdt.annotation.Nullable; + /** * Result of a {@code PUT} request as defined in * RFC8040 section 4.5. The definition makes it * clear that the logical operation is {@code create-or-replace}. + * + * @param created {@code true} if the resource was created, {@code false} if it was replaced + * @param entityTag response {@code ETag} header, or {@code null} if not applicable + * @param lastModified response {@code Last-Modified} header, or {@code null} if not applicable */ -public enum DataPutResult { - /** - * A new resource has been created. - */ - CREATED, - /* - * An existing resources has been replaced. - */ - REPLACED; +public record DataPutResult( + boolean created, + @Nullable EntityTag entityTag, + @Nullable Instant lastModified) implements ConfigurationMetadata { + public DataPutResult(final boolean created) { + this(created, null, null); + } } \ No newline at end of file diff --git a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/RestconfServer.java b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/RestconfServer.java index 5b269718ee..c900e24eec 100644 --- a/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/RestconfServer.java +++ b/restconf/restconf-nb/src/main/java/org/opendaylight/restconf/server/api/RestconfServer.java @@ -26,8 +26,6 @@ import org.opendaylight.yangtools.yang.common.Empty; * An implementation of a RESTCONF server, implementing the * RESTCONF API Resource. */ -// FIXME: NETCONF-1207: configuration datastore should maintain ETag and Last-Modified headers, so that these can be -// returned when PATCH/PUT modify the data. @NonNullByDefault public interface RestconfServer { /** @@ -63,6 +61,7 @@ public interface RestconfServer { * @param body data node for put to config DS * @return A {@link RestconfFuture} of the operation */ + // FIXME: NETCONF-1207: result should carry ConfigurationMetadata RestconfFuture dataPATCH(ResourceBody body); /** @@ -73,6 +72,7 @@ public interface RestconfServer { * @param body data node for put to config DS * @return A {@link RestconfFuture} of the operation */ + // FIXME: NETCONF-1207: result should carry ConfigurationMetadata RestconfFuture dataPATCH(ApiPath identifier, ResourceBody body); /** @@ -82,6 +82,7 @@ public interface RestconfServer { * @param body YANG Patch body * @return A {@link RestconfFuture} of the {@link PatchStatusContext} content */ + // FIXME: NETCONF-1207: result should carry ConfigurationMetadata RestconfFuture dataPATCH(PatchBody body); /** @@ -92,6 +93,7 @@ public interface RestconfServer { * @param body YANG Patch body * @return A {@link RestconfFuture} of the {@link PatchStatusContext} content */ + // FIXME: NETCONF-1207: result should carry ConfigurationMetadata RestconfFuture dataPATCH(ApiPath identifier, PatchBody body); RestconfFuture dataPOST(ChildBody body, Map queryParameters);