From ab449ecb26f99c6e2d7e979dd514a19de528b9ce Mon Sep 17 00:00:00 2001 From: Alex Tymchenko Date: Wed, 4 Jan 2023 15:02:28 +0000 Subject: [PATCH 1/5] Bump the version. --- version.gradle.kts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.gradle.kts b/version.gradle.kts index eee4f311..f85eeb1b 100644 --- a/version.gradle.kts +++ b/version.gradle.kts @@ -29,5 +29,5 @@ val spineTimeVersion: String by extra("1.9.0-SNAPSHOT.5") val spineCoreVersion: String by extra("1.9.0-SNAPSHOT.6") val spineVersion: String by extra(spineCoreVersion) -val versionToPublish: String by extra("1.9.0-SNAPSHOT.7") +val versionToPublish: String by extra("1.9.0-SNAPSHOT.8") val versionToPublishJs: String by extra(versionToPublish) From 3a28b69d9ce2c70b871e744ef38e1b3c9281bac6 Mon Sep 17 00:00:00 2001 From: Alex Tymchenko Date: Wed, 4 Jan 2023 15:39:53 +0000 Subject: [PATCH 2/5] Transfer the changes from `web#170` which originally were included into `1.7.4` (transfer in progress). --- .../client/firebase-subscription-service.js | 31 +++++---- client-js/main/client/http-endpoint.js | 48 +++++++++++--- .../FirebaseSubscriptionBridge.java | 26 ++++++++ .../test/firebase-client/subscribe-test.js | 4 +- .../given/TestSubscriptionKeepUpServlet.java | 7 +- .../web/subscription/SubscriptionBridge.java | 51 +++++++++++++-- .../SubscriptionBulkKeepUpServlet.java | 64 +++++++++++++++++++ .../servlet/SubscriptionCancelAllServlet.java | 63 ++++++++++++++++++ .../servlet/SubscriptionKeepUpServlet.java | 2 +- web/src/main/proto/spine/web/keeping_up.proto | 51 +++++++++++++++ 10 files changed, 311 insertions(+), 36 deletions(-) create mode 100644 web/src/main/java/io/spine/web/subscription/servlet/SubscriptionBulkKeepUpServlet.java create mode 100644 web/src/main/java/io/spine/web/subscription/servlet/SubscriptionCancelAllServlet.java create mode 100644 web/src/main/proto/spine/web/keeping_up.proto diff --git a/client-js/main/client/firebase-subscription-service.js b/client-js/main/client/firebase-subscription-service.js index dd2029cc..44b80c66 100644 --- a/client-js/main/client/firebase-subscription-service.js +++ b/client-js/main/client/firebase-subscription-service.js @@ -125,20 +125,23 @@ export class FirebaseSubscriptionService { * @private */ _keepUpSubscriptions() { - this._subscriptions.forEach(subscription => { - const spineSubscription = subscription.internal(); - if (subscription.closed) { - this._endpoint.cancelSubscription(spineSubscription).then(() => { - this._removeSubscription(subscription); - }); - } else { - this._endpoint.keepUpSubscription(spineSubscription).then(response => { - const responseStatus = response.status; - const responseStatusProto = ObjectToProto.convert(responseStatus, Status.typeUrl()); - if (responseStatusProto.getStatusCase() !== Status.StatusCase.OK) { - this._removeSubscription(subscription) - } - }); + const cancelledSubscriptions = this._subscriptions.filter(s => s.closed); + if (cancelledSubscriptions.length > 0) { + const subscriptionMessages = cancelledSubscriptions.map(s => s.internal()) + this._endpoint.cancelAll(subscriptionMessages); + cancelledSubscriptions.forEach(s => this._removeSubscription(s)) + } + const subscriptions = this._subscriptions.map(value => value.internal()); + if (subscriptions.length === 0) { + return; + } + this._endpoint.keepUpSubscriptions(subscriptions).then(response => { + for (let i = 0; i < response.response.length; i++) { + const r = response.response[i]; + const status = ObjectToProto.convert(r.status, Status.typeUrl()); + if (status.getStatusCase() !== Status.StatusCase.OK) { + this._removeSubscription(subscriptions[i]) + } } }); } diff --git a/client-js/main/client/http-endpoint.js b/client-js/main/client/http-endpoint.js index cc2c4fb5..fc04c323 100644 --- a/client-js/main/client/http-endpoint.js +++ b/client-js/main/client/http-endpoint.js @@ -28,6 +28,7 @@ import {TypedMessage} from './typed-message'; import {ClientError, ConnectionError, ServerError, SpineError} from './errors'; +import {Subscriptions} from '../proto/spine/web/keeping_up_pb'; /** * @typedef {Object} SubscriptionRouting @@ -36,8 +37,12 @@ import {ClientError, ConnectionError, ServerError, SpineError} from './errors'; * the name of the subscription creation endpoint; defaults to "/subscription/create" * @property {string} keepUp * the name of the subscription keep up endpoint; defaults to "/subscription/keep-up" + * @property {string} keepUpAll + * the name of the subscription bulk keep up endpoint; defaults to "/subscription/keep-up-all" * @property {string} cancel * the name of the subscription cancellation endpoint; defaults to "/subscription/cancel" + * @property {string} cancelAll + * the name of the subscription bulk cancellation endpoint; defaults to "/subscription/cancel-all" */ /** @@ -54,7 +59,7 @@ import {ClientError, ConnectionError, ServerError, SpineError} from './errors'; class Endpoint { /** - * Sends off a command to the endpoint. + * Sends a command to the endpoint. * * @param {!TypedMessage} command a Command to send to the Spine server * @return {Promise} a promise of a successful server response, rejected if @@ -65,7 +70,7 @@ class Endpoint { } /** - * Sends off a query to the endpoint. + * Sends a query to the endpoint. * * @param {!spine.client.Query} query a Query to Spine server to retrieve some domain entities * @return {Promise} a promise of a successful server response, rejected if @@ -77,7 +82,7 @@ class Endpoint { } /** - * Sends off a request to subscribe to a provided topic to an endpoint. + * Sends a request to subscribe to a provided topic to an endpoint. * * @param {!spine.client.Topic} topic a topic for which a subscription is created * @return {Promise} a promise of a successful server response, rejected if @@ -89,21 +94,33 @@ class Endpoint { } /** - * Sends off a request to keep a subscription, stopping it from being closed by server. + * Sends a request to keep a subscription, stopping it from being closed by server. * * @param {!spine.client.Subscription} subscription a subscription that should be kept open - * @return {Promise} a promise of a successful server response, rejected if - * an error occurs + * @returns {Promise} a promise of a successful server response, rejected if + * an error occurs */ - keepUpSubscription(subscription) { + keepUpSingleSubscription(subscription) { const typedSubscription = TypedMessage.of(subscription); return this._keepUp(typedSubscription); } /** - * Sends off a request to cancel an existing subscription. + * Sends a request to keep up several subscriptions, preventing them + * from being closed by the server. + * + * @param {!Array} subscriptions subscriptions that should be kept open + * @return {Promise} a promise of a successful server response, rejected if + * an error occurs + */ + keepUpSubscriptions(subscriptions) { + return this._keepUpAll(subscriptions); + } + + /** + * Sends a request to cancel an existing subscription. * - * Cancelling subscription stops the server updating subscription with new values. + * Cancelling subscription stops the server from updating subscription with new values. * * @param {!spine.client.Subscription} subscription a subscription that should be kept open * @return {Promise} a promise of a successful server response, rejected if @@ -114,6 +131,19 @@ class Endpoint { return this._cancel(typedSubscription); } + /** + * Sends a request to cancel all the given subscriptions. + * + * Cancelling subscriptions stops the server from updating subscription with new values. + * + * @param {!Array>} subscriptions subscriptions that should + * be cancelled + * @return {Promise} a promise of a successful server response, rejected if + * an error occurs + */ + cancelAll(subscriptions) { + return this._cancelAll(subscriptions); + } /** * @param {!TypedMessage} command a Command to send to the Spine server diff --git a/firebase-web/src/main/java/io/spine/web/firebase/subscription/FirebaseSubscriptionBridge.java b/firebase-web/src/main/java/io/spine/web/firebase/subscription/FirebaseSubscriptionBridge.java index 8a43abb6..56eaac34 100644 --- a/firebase-web/src/main/java/io/spine/web/firebase/subscription/FirebaseSubscriptionBridge.java +++ b/firebase-web/src/main/java/io/spine/web/firebase/subscription/FirebaseSubscriptionBridge.java @@ -36,6 +36,8 @@ import io.spine.core.Response; import io.spine.core.Status; import io.spine.type.TypeUrl; +import io.spine.web.Responses; +import io.spine.web.Subscriptions; import io.spine.web.firebase.FirebaseClient; import io.spine.web.firebase.NodePath; import io.spine.web.firebase.RequestNodePath; @@ -107,6 +109,18 @@ public Response keepUp(Subscription subscription) { return exists ? ok() : missing(subscription); } + @Override + public Responses keepUpAll(Subscriptions subscriptions) { + checkNotNull(subscriptions); + return subscriptions.getSubscriptionList() + .stream() + .map(this::keepUp) + .collect(Responses::newBuilder, + Responses.Builder::addResponse, + (l, r) -> l.addAllResponse(r.getResponseList())) + .vBuild(); + } + @Override public Response cancel(Subscription subscription) { checkNotNull(subscription); @@ -120,6 +134,18 @@ public Response cancel(Subscription subscription) { return localSubscription.isPresent() ? ok() : missing(subscription); } + @Override + public Responses cancelAll(Subscriptions request) { + checkNotNull(request); + Responses.Builder result = Responses.newBuilder(); + for (Subscription subscription : request.getSubscriptionList()) { + Response response = cancel(subscription); + result.addResponse(response); + } + return result.vBuild(); + } + + private static Response missing(Subscription subscription) { String errorMessage = format("Subscription `%s` is unknown or already canceled.", diff --git a/integration-tests/js-tests/test/firebase-client/subscribe-test.js b/integration-tests/js-tests/test/firebase-client/subscribe-test.js index 429e8016..99e786a1 100644 --- a/integration-tests/js-tests/test/firebase-client/subscribe-test.js +++ b/integration-tests/js-tests/test/firebase-client/subscribe-test.js @@ -499,12 +499,12 @@ describe('FirebaseClient subscription', function () { function keepUpEndpointSpy() { const httpEndpoint = client._subscribing._endpoint; - return sandbox.spy(httpEndpoint, 'keepUpSubscription'); + return sandbox.spy(httpEndpoint, 'keepUpSubscriptions'); } function cancelEndpointSpy() { const httpEndpoint = client._subscribing._endpoint; - return sandbox.spy(httpEndpoint, 'cancelSubscription'); + return sandbox.spy(httpEndpoint, 'cancelAll'); } /** diff --git a/integration-tests/test-app/src/main/java/io/spine/web/test/given/TestSubscriptionKeepUpServlet.java b/integration-tests/test-app/src/main/java/io/spine/web/test/given/TestSubscriptionKeepUpServlet.java index 93d1d151..d303b5d6 100644 --- a/integration-tests/test-app/src/main/java/io/spine/web/test/given/TestSubscriptionKeepUpServlet.java +++ b/integration-tests/test-app/src/main/java/io/spine/web/test/given/TestSubscriptionKeepUpServlet.java @@ -26,8 +26,7 @@ package io.spine.web.test.given; -import io.spine.core.Response; -import io.spine.web.subscription.servlet.SubscriptionKeepUpServlet; +import io.spine.web.subscription.servlet.SubscriptionBulkKeepUpServlet; import javax.servlet.annotation.WebServlet; @@ -36,9 +35,9 @@ /** * An endpoint for client requests to keep subscription running. */ -@WebServlet("/subscription/keep-up") +@WebServlet("/subscription/keep-up-all") @SuppressWarnings("serial") -public class TestSubscriptionKeepUpServlet extends SubscriptionKeepUpServlet { +public class TestSubscriptionKeepUpServlet extends SubscriptionBulkKeepUpServlet { public TestSubscriptionKeepUpServlet() { super(application().subscriptionBridge()); diff --git a/web/src/main/java/io/spine/web/subscription/SubscriptionBridge.java b/web/src/main/java/io/spine/web/subscription/SubscriptionBridge.java index 96de6654..e28dfd1b 100644 --- a/web/src/main/java/io/spine/web/subscription/SubscriptionBridge.java +++ b/web/src/main/java/io/spine/web/subscription/SubscriptionBridge.java @@ -29,6 +29,8 @@ import com.google.protobuf.Message; import io.spine.client.Subscription; import io.spine.client.Topic; +import io.spine.web.Responses; +import io.spine.web.Subscriptions; /** * A bridge for requests to a subscription {@link io.spine.server.SubscriptionService}. @@ -57,24 +59,61 @@ public interface SubscriptionBridgeThis operation is performed because subscription can only live some finite amount of time. - * Server cancels the subscription at some point, because maintaining the subscription requires - * resources and the client cannot be trusted to cancel every subscription it creates. + *

This operation is performed because a subscription lifetime is finite. Server cancels + * all subscriptions at some point, because maintaining them requires resources and the client + * cannot be trusted to cancel every subscription it creates. + * + *

Also, in some environments, HTTP requests to the server are required in order for a server + * instance to stay alive. If the environment kills off all server instances, + * there would be no one to propagate subscription updates to the clients. * * @param subscription * a subscription that should stay open * @return the keep-up response + * @see #keepUpAll(Subscriptions) for the preferable way + * of keeping up the batch of subscriptions */ K keepUp(Subscription subscription); /** - * Cancel the existing subscription, which stopping sending new data updates to the client. + * Keeps up given subscriptions, preventing them from closing from the server. + * + *

This operation is performed because a subscription lifetime is finite. Server cancels + * all subscriptions at some point, because maintaining them requires resources and the client + * cannot be trusted to cancel every subscription it creates. + * + *

Also, in some environments, HTTP requests to the server are required in order for a server + * instance to stay alive. If the environment kills off all server instances, + * there would be no one to propagate subscription updates to the clients. + * + * @param subscriptions + * subscriptions that should stay open + * @return the keep-up response + * @see #keepUp(Subscription) + */ + Responses keepUpAll(Subscriptions subscriptions); + + /** + * Cancels the existing subscription. + * + *

After this call, the server will stop sending subscription updates to the client. * * @param subscription - * a subscription that should be stopped from receiving updates + * a subscription that should be cancelled * @return the cancellation response */ C cancel(Subscription subscription); + + /** + * Cancels existing subscriptions. + * + *

After this call, the server will stop sending subscription updates to the clients. + * + * @param request + * subscriptions that should be cancelled + * @return the cancellation response + */ + Responses cancelAll(Subscriptions request); } diff --git a/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionBulkKeepUpServlet.java b/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionBulkKeepUpServlet.java new file mode 100644 index 00000000..b45d7476 --- /dev/null +++ b/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionBulkKeepUpServlet.java @@ -0,0 +1,64 @@ +/* + * Copyright 2023, TeamDev. All rights reserved. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.web.subscription.servlet; + +import io.spine.web.MessageServlet; +import io.spine.web.Responses; +import io.spine.web.Subscriptions; +import io.spine.web.subscription.SubscriptionBridge; + +import static com.google.common.base.Preconditions.checkNotNull; + +/** + * An abstract servlet handling the bulk {@link io.spine.client.Subscription Subscription}s + * keep-up requests. + * + *

This servlet parses the client requests and passes it to the {@link SubscriptionBridge} + * to process. After, a processing result is written to the servlet response. + */ +@SuppressWarnings("serial") // Java serialization is not supported. +public class SubscriptionBulkKeepUpServlet extends MessageServlet { + + private final SubscriptionBridge bridge; + + /** + * Creates a new instance of {@code SubscriptionBulkKeepUpServlet} with + * the given {@link SubscriptionBridge}. + * + * @param bridge + * the subscription bridge to be used to keep up subscriptions + */ + protected SubscriptionBulkKeepUpServlet(SubscriptionBridge bridge) { + super(); + this.bridge = checkNotNull(bridge); + } + + @Override + protected Responses handle(Subscriptions request) { + return bridge.keepUpAll(request); + } +} diff --git a/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionCancelAllServlet.java b/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionCancelAllServlet.java new file mode 100644 index 00000000..f040996c --- /dev/null +++ b/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionCancelAllServlet.java @@ -0,0 +1,63 @@ +/* + * Copyright 2023, TeamDev. All rights reserved. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +package io.spine.web.subscription.servlet; + +import io.spine.web.MessageServlet; +import io.spine.web.Responses; +import io.spine.web.Subscriptions; +import io.spine.web.subscription.SubscriptionBridge; + +/** + * An abstract servlet for a client request to cancel + * a batch of {@link io.spine.client.Subscription Subscription}s. + * + *

This servlet parses the client requests and passes it to the {@link SubscriptionBridge} + * to process. After, a processing result is written to the servlet response. + */ +@SuppressWarnings("serial") // Java serialization is not supported. +public abstract class SubscriptionCancelAllServlet + extends MessageServlet { + + private final SubscriptionBridge bridge; + + /** + * Creates a new instance of {@code SubscriptionCancelAllServlet} with the given + * {@link SubscriptionBridge}. + * + * @param bridge + * the subscription bridge to be used to cancel subscriptions + */ + protected SubscriptionCancelAllServlet(SubscriptionBridge bridge) { + super(); + this.bridge = bridge; + } + + @Override + protected Responses handle(Subscriptions request) { + return bridge.cancelAll(request); + } +} diff --git a/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionKeepUpServlet.java b/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionKeepUpServlet.java index 1c66dcf9..ce015e52 100644 --- a/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionKeepUpServlet.java +++ b/web/src/main/java/io/spine/web/subscription/servlet/SubscriptionKeepUpServlet.java @@ -51,7 +51,7 @@ public abstract class SubscriptionKeepUpServlet * {@link SubscriptionBridge}. * * @param bridge - * the subscription bridge to be used to keep-up subscriptions + * the subscription bridge to be used to keep up subscriptions */ protected SubscriptionKeepUpServlet(SubscriptionBridge bridge) { super(); diff --git a/web/src/main/proto/spine/web/keeping_up.proto b/web/src/main/proto/spine/web/keeping_up.proto new file mode 100644 index 00000000..4ed71ed2 --- /dev/null +++ b/web/src/main/proto/spine/web/keeping_up.proto @@ -0,0 +1,51 @@ +/* + * Copyright 2023, TeamDev. All rights reserved. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Redistribution and use in source and/or binary forms, with or without + * modification, must retain the above copyright notice and the following + * disclaimer. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +syntax = "proto3"; + +package spine.web; + +import "spine/options.proto"; + +option (type_url_prefix) = "type.spine.io"; +option java_package = "io.spine.web"; +option java_outer_classname = "KeepingUpProto"; +option java_multiple_files = true; + +import "spine/client/subscription.proto"; +import "spine/core/response.proto"; + +// A list of subscriptions to keep up. +message Subscriptions { + repeated client.Subscription subscription = 1 [(required) = true, (validate) = true]; +} + +// A list of keep up responses. +// +// The order of responses corresponds to the order of subscriptions in the `Subscriptions` request. +// +message Responses { + repeated core.Response response = 1 [(required) = true, (validate) = true]; +} \ No newline at end of file From 8820165b339e9f6aa8020aa9d4fd7d811b86b668 Mon Sep 17 00:00:00 2001 From: Alex Tymchenko Date: Wed, 4 Jan 2023 15:40:28 +0000 Subject: [PATCH 3/5] Update the report files. --- client-js/package.json | 2 +- integration-tests/js-tests/package.json | 2 +- license-report.md | 32 ++++++++++++------------- pom.xml | 2 +- 4 files changed, 19 insertions(+), 19 deletions(-) diff --git a/client-js/package.json b/client-js/package.json index 5430419b..6ac5491c 100644 --- a/client-js/package.json +++ b/client-js/package.json @@ -1,6 +1,6 @@ { "name": "spine-web", - "version": "1.9.0-SNAPSHOT.7", + "version": "1.9.0-SNAPSHOT.8", "license": "Apache-2.0", "description": "A JS client for interacting with Spine applications.", "homepage": "https://spine.io", diff --git a/integration-tests/js-tests/package.json b/integration-tests/js-tests/package.json index a8eae539..60b0b184 100644 --- a/integration-tests/js-tests/package.json +++ b/integration-tests/js-tests/package.json @@ -1,6 +1,6 @@ { "name": "client-js-tests", - "version": "1.9.0-SNAPSHOT.7", + "version": "1.9.0-SNAPSHOT.8", "license": "Apache-2.0", "description": "Tests of a `spine-web` JS library against the Spine-based application.", "scripts": { diff --git a/license-report.md b/license-report.md index 89bc33dd..82e8e756 100644 --- a/license-report.md +++ b/license-report.md @@ -1,6 +1,6 @@ -# Dependencies of `io.spine:spine-client-js:1.9.0-SNAPSHOT.7` +# Dependencies of `io.spine:spine-client-js:1.9.0-SNAPSHOT.8` ## Runtime 1. **Group:** com.google.code.findbugs **Name:** jsr305 **Version:** 3.0.2 @@ -368,10 +368,10 @@ The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Wed Jan 04 14:37:41 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Wed Jan 04 15:35:39 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). -#NPM dependencies of `spine-web@1.9.0-SNAPSHOT.7` +#NPM dependencies of `spine-web@1.9.0-SNAPSHOT.8` ## `Production` dependencies: @@ -405,7 +405,7 @@ This report was generated on **Wed Jan 04 14:37:41 WET 2023** using [Gradle-Lice 1. **rxjs@6.5.5** * Licenses: Apache-2.0 * Repository: [https://github.com/reactivex/rxjs](https://github.com/reactivex/rxjs) -1. **spine-web@1.9.0-SNAPSHOT.7** +1. **spine-web@1.9.0-SNAPSHOT.8** * Licenses: Apache-2.0 * Repository: [https://github.com/SpineEventEngine/web](https://github.com/SpineEventEngine/web) 1. **tr46@0.0.3** @@ -1958,7 +1958,7 @@ This report was generated on **Wed Jan 04 14:37:41 WET 2023** using [Gradle-Lice 1. **spdx-satisfies@4.0.1** * Licenses: MIT * Repository: [https://github.com/kemitchell/spdx-satisfies.js](https://github.com/kemitchell/spdx-satisfies.js) -1. **spine-web@1.9.0-SNAPSHOT.7** +1. **spine-web@1.9.0-SNAPSHOT.8** * Licenses: Apache-2.0 * Repository: [https://github.com/SpineEventEngine/web](https://github.com/SpineEventEngine/web) 1. **sprintf-js@1.0.3** @@ -2140,12 +2140,12 @@ This report was generated on **Wed Jan 04 14:37:41 WET 2023** using [Gradle-Lice * Repository: [https://github.com/sindresorhus/yocto-queue](https://github.com/sindresorhus/yocto-queue) -This report was generated on **Wed Jan 04 2023 14:37:41 GMT+0000 (Western European Standard Time)** using [NPM License Checker](https://github.com/davglass/license-checker) library. +This report was generated on **Wed Jan 04 2023 15:35:40 GMT+0000 (Western European Standard Time)** using [NPM License Checker](https://github.com/davglass/license-checker) library. -# Dependencies of `io.spine.gcloud:spine-firebase-web:1.9.0-SNAPSHOT.7` +# Dependencies of `io.spine.gcloud:spine-firebase-web:1.9.0-SNAPSHOT.8` ## Runtime 1. **Group:** com.fasterxml.jackson.core **Name:** jackson-annotations **Version:** 2.9.10 @@ -2932,12 +2932,12 @@ This report was generated on **Wed Jan 04 2023 14:37:41 GMT+0000 (Western Europe The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Wed Jan 04 14:37:47 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Wed Jan 04 15:35:45 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). -# Dependencies of `io.spine:spine-js-tests:1.9.0-SNAPSHOT.7` +# Dependencies of `io.spine:spine-js-tests:1.9.0-SNAPSHOT.8` ## Runtime 1. **Group:** com.google.code.findbugs **Name:** jsr305 **Version:** 3.0.2 @@ -3327,12 +3327,12 @@ This report was generated on **Wed Jan 04 14:37:47 WET 2023** using [Gradle-Lice The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Wed Jan 04 14:37:51 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Wed Jan 04 15:35:50 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). -# Dependencies of `io.spine:spine-test-app:1.9.0-SNAPSHOT.7` +# Dependencies of `io.spine:spine-test-app:1.9.0-SNAPSHOT.8` ## Runtime 1. **Group:** com.fasterxml.jackson.core **Name:** jackson-annotations **Version:** 2.9.10 @@ -4906,12 +4906,12 @@ This report was generated on **Wed Jan 04 14:37:51 WET 2023** using [Gradle-Lice The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Wed Jan 04 14:37:53 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Wed Jan 04 15:35:51 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). -# Dependencies of `io.spine:spine-testutil-web:1.9.0-SNAPSHOT.7` +# Dependencies of `io.spine:spine-testutil-web:1.9.0-SNAPSHOT.8` ## Runtime 1. **Group:** com.google.android **Name:** annotations **Version:** 4.1.1.4 @@ -5370,12 +5370,12 @@ This report was generated on **Wed Jan 04 14:37:53 WET 2023** using [Gradle-Lice The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Wed Jan 04 14:37:55 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). +This report was generated on **Wed Jan 04 15:35:53 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). -# Dependencies of `io.spine:spine-web:1.9.0-SNAPSHOT.7` +# Dependencies of `io.spine:spine-web:1.9.0-SNAPSHOT.8` ## Runtime 1. **Group:** com.google.android **Name:** annotations **Version:** 4.1.1.4 @@ -5873,4 +5873,4 @@ This report was generated on **Wed Jan 04 14:37:55 WET 2023** using [Gradle-Lice The dependencies distributed under several licenses, are used according their commercial-use-friendly license. -This report was generated on **Wed Jan 04 14:37:57 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file +This report was generated on **Wed Jan 04 15:35:57 WET 2023** using [Gradle-License-Report plugin](https://github.com/jk1/Gradle-License-Report) by Evgeny Naumenko, licensed under [Apache 2.0 License](https://github.com/jk1/Gradle-License-Report/blob/master/LICENSE). \ No newline at end of file diff --git a/pom.xml b/pom.xml index f4da321b..6c8ed70a 100644 --- a/pom.xml +++ b/pom.xml @@ -12,7 +12,7 @@ all modules and does not describe the project structure per-subproject. io.spine spine-web -1.9.0-SNAPSHOT.7 +1.9.0-SNAPSHOT.8 2015 From 049438386b6c7fde9ba03a37b249c5a3dfa348ee Mon Sep 17 00:00:00 2001 From: Alex Tymchenko Date: Wed, 4 Jan 2023 17:35:13 +0000 Subject: [PATCH 4/5] Continue migration of `web#170`. --- client-js/main/client/http-endpoint.js | 100 ++++++++++++++++++++----- 1 file changed, 80 insertions(+), 20 deletions(-) diff --git a/client-js/main/client/http-endpoint.js b/client-js/main/client/http-endpoint.js index fc04c323..817024a8 100644 --- a/client-js/main/client/http-endpoint.js +++ b/client-js/main/client/http-endpoint.js @@ -189,6 +189,17 @@ class Endpoint { throw new Error('Not implemented in abstract base.'); } + /** + * @param {!Array>} subscriptions subscriptions to keep up + * @return {Promise} a promise of a successful server response, rejected if + * an error occurs + * @protected + * @abstract + */ + _keepUpAll(subscriptions) { + throw new Error('Not implemented in abstract base.'); + } + /** * @param {!TypedMessage} subscription a subscription to be canceled * @return {Promise} a promise of a successful server response, rejected if @@ -199,10 +210,22 @@ class Endpoint { _cancel(subscription) { throw new Error('Not implemented in abstract base.'); } + + + /** + * @param {!Array} subscriptions subscriptions to be canceled + * @return {Promise} a promise of a successful server response, rejected if + * an error occurs + * @protected + * @abstract + */ + _cancelAll(subscriptions) { + throw new Error('Not implemented in abstract base.'); + } } /** - * Spine HTTP endpoint which is used to send off Commands and Queries using + * Spine HTTP endpoint which is used to send Commands and Queries using * the provided HTTP client. */ export class HttpEndpoint extends Endpoint { @@ -218,12 +241,12 @@ export class HttpEndpoint extends Endpoint { } /** - * Sends off a command to the endpoint. + * Sends a command to the endpoint. * * @param {!TypedMessage} command a Command to send to the Spine server * @return {Promise} a promise of a successful server response JSON data, - * rejected if the client response is not 2xx or a - * connection error occurs + * rejected if the client response is not `2xx`, + * or a connection error occurs * @protected */ _executeCommand(command) { @@ -232,12 +255,12 @@ export class HttpEndpoint extends Endpoint { } /** - * Sends off a query to the endpoint. + * Sends a query to the endpoint. * * @param {!TypedMessage} query a Query to Spine server to retrieve some domain entities * @return {Promise} a promise of a successful server response JSON data, - * rejected if the client response is not 2xx or a - * connection error occurs + * rejected if the client response is not `2xx`, + * or a connection error occurs * @protected */ _performQuery(query) { @@ -246,12 +269,12 @@ export class HttpEndpoint extends Endpoint { } /** - * Sends off a request to create a subscription for a topic. + * Sends a request to create a subscription for a topic. * * @param {!TypedMessage} topic a topic to subscribe to * @return {Promise} a promise of a successful server response JSON data, - * rejected if the client response is not 2xx or a - * connection error occurs + * rejected if the client response is not `2xx`, + * or a connection error occurs * @protected */ _subscribeTo(topic) { @@ -261,13 +284,13 @@ export class HttpEndpoint extends Endpoint { } /** - * Sends off a request to keep alive a subscription. + * Sends a request to keep alive the given subscription. * * @param {!TypedMessage} subscription a subscription that is prevented * from being closed by server * @return {Promise} a promise of a successful server response JSON data, - * rejected if the client response is not 2xx or a - * connection error occurs + * rejected if the client response is not `2xx`, + * or a connection error occurs * @protected */ _keepUp(subscription) { @@ -277,12 +300,31 @@ export class HttpEndpoint extends Endpoint { } /** - * Sends off a request to cancel a subscription. + * Sends a request to keep alive the given subscriptions. + * + * @param {!Array} subscriptions subscriptions that are prevented + * from being closed by the server + * @return {Promise} a promise of a successful server response JSON data, + * rejected if the client response is not `2xx`, + * or a connection error occurs + * @protected + */ + _keepUpAll(subscriptions) { + const path = (this._routing && this._routing.subscription && this._routing.subscription.keepUpAll) + || '/subscription/keep-up-all'; + const request = new Subscriptions() + request.setSubscriptionList(subscriptions); + const typed = TypedMessage.of(request); + return this._sendMessage(path, typed); + } + + /** + * Sends a request to cancel the given subscription. * * @param {!TypedMessage} subscription a subscription to be canceled * @return {Promise} a promise of a successful server response JSON data, - * rejected if the client response is not 2xx or a - * connection error occurs + * rejected if the client response is not `2xx`, + * or a connection error occurs * @protected */ _cancel(subscription) { @@ -291,14 +333,32 @@ export class HttpEndpoint extends Endpoint { return this._sendMessage(path, subscription); } + /** + * Sends a request to cancel the given subscriptions. + * + * @param {!Array} subscriptions subscriptions to be canceled + * @return {Promise} a promise of a successful server response JSON data, + * rejected if the client response is not `2xx`, + * or a connection error occurs + * @protected + */ + _cancelAll(subscriptions) { + const path = (this._routing && this._routing.subscription && this._routing.subscription.cancelAll) + || '/subscription/cancel-all'; + const request = new Subscriptions(); + request.setSubscriptionList(subscriptions); + const typed = TypedMessage.of(request); + return this._sendMessage(path, typed); + } + /** * Sends the given message to the given endpoint. * * @param {!string} endpoint an endpoint to send the message to * @param {!TypedMessage} message a message to send, as a {@link TypedMessage} * @return {Promise} a promise of a successful server response JSON data, - * rejected if the client response is not 2xx or a - * connection error occurs + * rejected if the client response is not `2xx`, + * or a connection error occurs * @private */ _sendMessage(endpoint, message) { @@ -316,8 +376,8 @@ export class HttpEndpoint extends Endpoint { * * @param {!Response} response an HTTP request response * @return {Promise} a promise of a successful server response JSON data, - * rejected if the client response is not 2xx or if JSON - * parsing fails + * rejected if the client response is not `2xx`, + * or if JSON parsing fails * @private */ static _jsonOrError(response) { From 4532cf3c0420bc9c31c71e3db0dacd5cd978afc3 Mon Sep 17 00:00:00 2001 From: Alex Tymchenko Date: Thu, 5 Jan 2023 13:04:28 +0000 Subject: [PATCH 5/5] Finalize the migration of `web#170`. --- .../js-tests/test/firebase-client/subscribe-test.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/integration-tests/js-tests/test/firebase-client/subscribe-test.js b/integration-tests/js-tests/test/firebase-client/subscribe-test.js index 99e786a1..eb566942 100644 --- a/integration-tests/js-tests/test/firebase-client/subscribe-test.js +++ b/integration-tests/js-tests/test/firebase-client/subscribe-test.js @@ -418,7 +418,7 @@ describe('FirebaseClient subscription', function () { subscribeToAllTasks().then(async ({itemAdded, itemChanged, itemRemoved, unsubscribe}) => { await nextInterval(); assert.ok(keepUpEndpoint.calledOnce); - const subscriptionMessage = keepUpEndpoint.getCall(0).args[0]; + const subscriptionMessage = keepUpEndpoint.getCall(0).args[0][0]; checkAllTasks(subscriptionMessage); unsubscribe(); done(); @@ -433,7 +433,7 @@ describe('FirebaseClient subscription', function () { unsubscribe(); await nextInterval(); assert.ok(cancelEndpoint.calledOnce); - const subscriptionMessage = cancelEndpoint.getCall(0).args[0]; + const subscriptionMessage = cancelEndpoint.getCall(0).args[0][0]; checkAllTasks(subscriptionMessage); done(); });