From 6f77eaca134e10307b71f3980ddb7231367dd40d Mon Sep 17 00:00:00 2001
From: Andrew Stanton-Nurse <andrew@stanton-nurse.com>
Date: Thu, 3 May 2018 12:09:07 -0700
Subject: [PATCH] add tests

---
 .../signalr/spec/LongPollingTransport.spec.ts | 60 ++++++++++++++++++-
 .../ts/signalr/src/LongPollingTransport.ts    |  3 -
 2 files changed, 58 insertions(+), 5 deletions(-)

diff --git a/clients/ts/signalr/spec/LongPollingTransport.spec.ts b/clients/ts/signalr/spec/LongPollingTransport.spec.ts
index 8023ab27d47..018e1ece9da 100644
--- a/clients/ts/signalr/spec/LongPollingTransport.spec.ts
+++ b/clients/ts/signalr/spec/LongPollingTransport.spec.ts
@@ -6,7 +6,8 @@ import { LongPollingTransport } from "../src/LongPollingTransport";
 import { ConsoleLogger } from "../src/Utils";
 
 import { TestHttpClient } from "./TestHttpClient";
-import { asyncit as it, PromiseSource } from "./Utils";
+import { asyncit as it, PromiseSource, delay } from "./Utils";
+import { HttpError, TimeoutError } from "../src/Errors";
 
 describe("LongPollingTransport", () => {
     it("shuts down poll after timeout even if server doesn't shut it down on receiving the DELETE", async () => {
@@ -48,6 +49,8 @@ describe("LongPollingTransport", () => {
                     return new HttpResponse(200);
                 } else {
                     await deleteReceived.promise;
+                    // Force the shutdown timer to be registered by not returning inline
+                    await delay(10);
                     pollCompleted.resolve();
                     return new HttpResponse(204);
                 }
@@ -56,7 +59,8 @@ describe("LongPollingTransport", () => {
                 deleteReceived.resolve();
                 return new HttpResponse(202);
             });
-        const transport = new LongPollingTransport(client, null, NullLogger.instance, false);
+        const logMessages: string[] = [];
+        const transport = new LongPollingTransport(client, null, NullLogger.instance, false, 100);
 
         await transport.connect("http://example.com", TransferFormat.Text);
         await transport.stop();
@@ -64,4 +68,56 @@ describe("LongPollingTransport", () => {
         // This should complete, because the DELETE request triggers it to stop.
         await pollCompleted.promise;
     });
+
+    for (const result of [200, 204, 300, new HttpError("Boom", 500), new TimeoutError()]) {
+        const resultName = typeof result === "number" ? result.toString() : result.constructor.name;
+        it(`does not fire shutdown timer when poll terminates with ${resultName}`, async () => {
+            let firstPoll = true;
+            const deleteReceived = new PromiseSource();
+            const pollCompleted = new PromiseSource();
+            const client = new TestHttpClient()
+                .on("GET", async (r) => {
+                    if (firstPoll) {
+                        firstPoll = false;
+                        return new HttpResponse(200);
+                    } else {
+                        await deleteReceived.promise;
+                        // Force the shutdown timer to be registered by not returning inline
+                        await delay(10);
+                        pollCompleted.resolve();
+
+                        if (typeof result === "number") {
+                            return new HttpResponse(result);
+                        } else {
+                            throw result;
+                        }
+                    }
+                })
+                .on("DELETE", (r) => {
+                    deleteReceived.resolve();
+                    return new HttpResponse(202);
+                });
+            const logMessages: string[] = [];
+            const transport = new LongPollingTransport(client, null, {
+                log(level: LogLevel, message: string) {
+                    logMessages.push(message);
+                },
+            }, false, 100);
+
+            await transport.connect("http://example.com", TransferFormat.Text);
+            await transport.stop();
+
+            // This should complete, because the DELETE request triggers it to stop.
+            await pollCompleted.promise;
+
+            // Wait for the shutdown timeout to elapse
+            // This can be much cleaner when we port to Jest because it has a built-in set of
+            // fake timers!
+            await delay(150);
+
+            expect(logMessages)
+                .not
+                .toContain("(LongPolling transport) server did not terminate after DELETE request, canceling poll.");
+        });
+    }
 });
\ No newline at end of file
diff --git a/clients/ts/signalr/src/LongPollingTransport.ts b/clients/ts/signalr/src/LongPollingTransport.ts
index c8e31ee7cec..1874d21277d 100644
--- a/clients/ts/signalr/src/LongPollingTransport.ts
+++ b/clients/ts/signalr/src/LongPollingTransport.ts
@@ -108,9 +108,6 @@ export class LongPollingTransport implements ITransport {
                     if (response.statusCode === 204) {
                         this.logger.log(LogLevel.Information, "(LongPolling transport) Poll terminated by server");
 
-                        // If we were on a timeout waiting for shutdown, unregister it.
-                        clearTimeout(this.shutdownTimer);
-
                         this.running = false;
                     } else if (response.statusCode !== 200) {
                         this.logger.log(LogLevel.Error, `(LongPolling transport) Unexpected response code: ${response.statusCode}`);
-- 
GitLab