From 930931f7a905b526819e03e2d8afff3dcb2075bd Mon Sep 17 00:00:00 2001 From: Robert Varga Date: Tue, 26 Oct 2021 11:06:53 +0200 Subject: [PATCH] Eliminate AbstractQueryParams We have a separate NotificationQueryParams which holds the request fields. AbstractQueryParams is only subclassed from AbstractCommonSubscriber, hence we have combine the two to keep things a tad more compact. JIRA: NETCONF-773 Change-Id: I188b4444bf81e57b6c3a6e672bd1ea90db041bca Signed-off-by: Robert Varga --- .../listeners/AbstractCommonSubscriber.java | 134 ++++++++++++++++- .../listeners/AbstractQueryParams.java | 135 ------------------ .../streams/listeners/ListenerAdapter.java | 2 +- .../NotificationListenerAdapter.java | 2 +- 4 files changed, 129 insertions(+), 144 deletions(-) delete mode 100644 restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractQueryParams.java diff --git a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractCommonSubscriber.java b/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractCommonSubscriber.java index 1aec614ed0..43c9ce6669 100644 --- a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractCommonSubscriber.java +++ b/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractCommonSubscriber.java @@ -10,13 +10,25 @@ package org.opendaylight.restconf.nb.rfc8040.streams.listeners; import static java.util.Objects.requireNonNull; import com.google.common.base.Preconditions; +import java.time.Instant; +import java.time.format.DateTimeFormatter; +import java.time.format.DateTimeFormatterBuilder; +import java.time.format.DateTimeParseException; +import java.time.temporal.ChronoField; +import java.time.temporal.TemporalAccessor; import java.util.HashSet; import java.util.Iterator; import java.util.Set; import java.util.concurrent.ExecutionException; +import javax.xml.xpath.XPathExpressionException; import org.checkerframework.checker.lock.qual.GuardedBy; import org.checkerframework.checker.lock.qual.Holding; +import org.eclipse.jdt.annotation.NonNull; +import org.eclipse.jdt.annotation.Nullable; +import org.opendaylight.restconf.common.errors.RestconfDocumentedException; +import org.opendaylight.restconf.nb.rfc8040.NotificationQueryParams; import org.opendaylight.restconf.nb.rfc8040.streams.StreamSessionHandler; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.DateAndTime; import org.opendaylight.yangtools.concepts.Registration; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -24,32 +36,47 @@ import org.slf4j.LoggerFactory; /** * Features of subscribing part of both notifications. */ -abstract class AbstractCommonSubscriber extends AbstractQueryParams implements BaseListenerInterface { +abstract class AbstractCommonSubscriber extends AbstractNotificationsData implements BaseListenerInterface { private static final Logger LOG = LoggerFactory.getLogger(AbstractCommonSubscriber.class); + private static final DateTimeFormatter FORMATTER = new DateTimeFormatterBuilder() + .appendValue(ChronoField.YEAR, 4).appendLiteral('-') + .appendValue(ChronoField.MONTH_OF_YEAR, 2).appendLiteral('-') + .appendValue(ChronoField.DAY_OF_MONTH, 2).appendLiteral('T') + .appendValue(ChronoField.HOUR_OF_DAY, 2).appendLiteral(':') + .appendValue(ChronoField.MINUTE_OF_HOUR, 2).appendLiteral(':') + .appendValue(ChronoField.SECOND_OF_MINUTE, 2) + .appendFraction(ChronoField.NANO_OF_SECOND, 0, 9, true) + .appendOffset("+HH:MM", "Z").toFormatter(); @GuardedBy("this") private final Set subscribers = new HashSet<>(); @GuardedBy("this") private Registration registration; + // FIXME: these should be final + private Instant start = null; + private Instant stop = null; + private boolean leafNodesOnly = false; + private boolean skipNotificationData = false; + @Override public final synchronized boolean hasSubscribers() { - return !this.subscribers.isEmpty(); + return !subscribers.isEmpty(); } @Override public final synchronized Set getSubscribers() { - return new HashSet<>(this.subscribers); + return new HashSet<>(subscribers); } @Override public final synchronized void close() throws InterruptedException, ExecutionException { - if (this.registration != null) { - this.registration.close(); - this.registration = null; + if (registration != null) { + registration.close(); + registration = null; } deleteDataInDS().get(); - this.subscribers.clear(); + subscribers.clear(); } @Override @@ -71,6 +98,58 @@ abstract class AbstractCommonSubscriber extends AbstractQueryParams implements B } } + public final Instant getStart() { + return start; + } + + /** + * Set query parameters for listener. + * + * @param params NotificationQueryParams to use. + */ + public final void setQueryParams(final NotificationQueryParams params) { + final var startTime = params.startTime(); + start = startTime == null ? Instant.now() : parseDateAndTime(startTime.value()); + + final var stopTime = params.stopTime(); + stop = stopTime == null ? null : parseDateAndTime(stopTime.value()); + + final var leafNodes = params.leafNodesOnly(); + leafNodesOnly = leafNodes == null ? false : leafNodes.value(); + + final var skipData = params.skipNotificationData(); + skipNotificationData = skipData == null ? false : skipData.value(); + + final var filter = params.filter(); + if (filter != null) { + try { + setFilter(filter.paramValue()); + } catch (XPathExpressionException e) { + throw new IllegalArgumentException("Failed to get filter", e); + } + } + } + + abstract void setFilter(@Nullable String xpathString) throws XPathExpressionException; + + /** + * Check whether this query should only notify about leaf node changes. + * + * @return true if this query should only notify about leaf node changes + */ + final boolean getLeafNodesOnly() { + return leafNodesOnly; + } + + /** + * Check whether this query should notify changes without data. + * + * @return true if this query should notify about changes with data + */ + final boolean isSkipNotificationData() { + return skipNotificationData; + } + /** * Sets {@link Registration} registration. * @@ -112,4 +191,45 @@ abstract class AbstractCommonSubscriber extends AbstractQueryParams implements B } } } + + @SuppressWarnings("checkstyle:IllegalCatch") + final boolean checkStartStop(final Instant now) { + if (stop != null) { + if (start.compareTo(now) < 0 && stop.compareTo(now) > 0) { + return true; + } + if (stop.compareTo(now) < 0) { + try { + close(); + } catch (final Exception e) { + throw new RestconfDocumentedException("Problem with unregister listener." + e); + } + } + } else if (start != null) { + if (start.compareTo(now) < 0) { + start = null; + return true; + } + } else { + return true; + } + return false; + } + + /** + * Parse input of query parameters - start-time or stop-time - from {@link DateAndTime} format + * to {@link Instant} format. + * + * @param uriValue Start-time or stop-time as string in {@link DateAndTime} format. + * @return Parsed {@link Instant} by entry. + */ + private static @NonNull Instant parseDateAndTime(final DateAndTime dateAndTime) { + final TemporalAccessor accessor; + try { + accessor = FORMATTER.parse(dateAndTime.getValue()); + } catch (final DateTimeParseException e) { + throw new RestconfDocumentedException("Cannot parse of value in date: " + dateAndTime, e); + } + return Instant.from(accessor); + } } diff --git a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractQueryParams.java b/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractQueryParams.java deleted file mode 100644 index f31a72f376..0000000000 --- a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/AbstractQueryParams.java +++ /dev/null @@ -1,135 +0,0 @@ -/* - * Copyright (c) 2016 Cisco Systems, Inc. and others. All rights reserved. - * - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v1.0 which accompanies this distribution, - * and is available at http://www.eclipse.org/legal/epl-v10.html - */ -package org.opendaylight.restconf.nb.rfc8040.streams.listeners; - -import java.time.Instant; -import java.time.format.DateTimeFormatter; -import java.time.format.DateTimeFormatterBuilder; -import java.time.format.DateTimeParseException; -import java.time.temporal.ChronoField; -import java.time.temporal.TemporalAccessor; -import javax.xml.xpath.XPathExpressionException; -import org.eclipse.jdt.annotation.NonNull; -import org.eclipse.jdt.annotation.Nullable; -import org.opendaylight.restconf.common.errors.RestconfDocumentedException; -import org.opendaylight.restconf.nb.rfc8040.NotificationQueryParams; -import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.DateAndTime; - -/** - * Features of query parameters part of both notifications. - */ -abstract class AbstractQueryParams extends AbstractNotificationsData { - private static final DateTimeFormatter FORMATTER = new DateTimeFormatterBuilder() - .appendValue(ChronoField.YEAR, 4).appendLiteral('-') - .appendValue(ChronoField.MONTH_OF_YEAR, 2).appendLiteral('-') - .appendValue(ChronoField.DAY_OF_MONTH, 2).appendLiteral('T') - .appendValue(ChronoField.HOUR_OF_DAY, 2).appendLiteral(':') - .appendValue(ChronoField.MINUTE_OF_HOUR, 2).appendLiteral(':') - .appendValue(ChronoField.SECOND_OF_MINUTE, 2) - .appendFraction(ChronoField.NANO_OF_SECOND, 0, 9, true) - .appendOffset("+HH:MM", "Z").toFormatter(); - - // FIXME: these should be final - private Instant start = null; - private Instant stop = null; - private boolean leafNodesOnly = false; - private boolean skipNotificationData = false; - - public final Instant getStart() { - return start; - } - - /** - * Set query parameters for listener. - * - * @param params NotificationQueryParams to use. - */ - public final void setQueryParams(final NotificationQueryParams params) { - final var startTime = params.startTime(); - start = startTime == null ? Instant.now() : parseDateAndTime(startTime.value()); - - final var stopTime = params.stopTime(); - stop = stopTime == null ? null : parseDateAndTime(stopTime.value()); - - final var leafNodes = params.leafNodesOnly(); - leafNodesOnly = leafNodes == null ? false : leafNodes.value(); - - final var skipData = params.skipNotificationData(); - skipNotificationData = skipData == null ? false : skipData.value(); - - final var filter = params.filter(); - if (filter != null) { - try { - setFilter(filter.paramValue()); - } catch (XPathExpressionException e) { - throw new IllegalArgumentException("Failed to get filter", e); - } - } - } - - abstract void setFilter(@Nullable String xpathString) throws XPathExpressionException; - - /** - * Parse input of query parameters - start-time or stop-time - from {@link DateAndTime} format - * to {@link Instant} format. - * - * @param uriValue Start-time or stop-time as string in {@link DateAndTime} format. - * @return Parsed {@link Instant} by entry. - */ - private static @NonNull Instant parseDateAndTime(final DateAndTime dateAndTime) { - final TemporalAccessor accessor; - try { - accessor = FORMATTER.parse(dateAndTime.getValue()); - } catch (final DateTimeParseException e) { - throw new RestconfDocumentedException("Cannot parse of value in date: " + dateAndTime, e); - } - return Instant.from(accessor); - } - - /** - * Check whether this query should only notify about leaf node changes. - * - * @return true if this query should only notify about leaf node changes - */ - boolean getLeafNodesOnly() { - return leafNodesOnly; - } - - /** - * Check whether this query should notify changes without data. - * - * @return true if this query should notify about changes with data - */ - public boolean isSkipNotificationData() { - return skipNotificationData; - } - - @SuppressWarnings("checkstyle:IllegalCatch") - boolean checkStartStop(final Instant now, final T listener) { - if (stop != null) { - if (start.compareTo(now) < 0 && stop.compareTo(now) > 0) { - return true; - } - if (stop.compareTo(now) < 0) { - try { - listener.close(); - } catch (final Exception e) { - throw new RestconfDocumentedException("Problem with unregister listener." + e); - } - } - } else if (start != null) { - if (start.compareTo(now) < 0) { - start = null; - return true; - } - } else { - return true; - } - return false; - } -} diff --git a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/ListenerAdapter.java b/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/ListenerAdapter.java index 8094d7be44..ddc573b95c 100644 --- a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/ListenerAdapter.java +++ b/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/ListenerAdapter.java @@ -93,7 +93,7 @@ public class ListenerAdapter extends AbstractCommonSubscriber implements Cluster @SuppressWarnings("checkstyle:IllegalCatch") public void onDataTreeChanged(final Collection dataTreeCandidates) { final Instant now = Instant.now(); - if (!checkStartStop(now, this)) { + if (!checkStartStop(now)) { return; } diff --git a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/NotificationListenerAdapter.java b/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/NotificationListenerAdapter.java index 3fc2c7af47..866bd45d81 100644 --- a/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/NotificationListenerAdapter.java +++ b/restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/streams/listeners/NotificationListenerAdapter.java @@ -95,7 +95,7 @@ public class NotificationListenerAdapter extends AbstractCommonSubscriber implem @SuppressWarnings("checkstyle:IllegalCatch") public void onNotification(final DOMNotification notification) { final Instant now = Instant.now(); - if (!checkStartStop(now, this)) { + if (!checkStartStop(now)) { return; } -- 2.36.6