@aspnet/signalr-client
Advanced tools
Comparing version 1.0.0-alpha1-final to 1.0.0-alpha2-final
@@ -24,12 +24,23 @@ "use strict"; | ||
(function (BinaryMessageFormat) { | ||
// The length prefix of binary messages is encoded as VarInt. Read the comment in | ||
// the BinaryMessageParser.TryParseMessage for details. | ||
function write(output) { | ||
// .byteLength does is undefined in IE10 | ||
// msgpack5 uses returns Buffer instead of Uint8Array on IE10 and some other browser | ||
// in which case .byteLength does will be undefined | ||
let size = output.byteLength || output.length; | ||
let buffer = new Uint8Array(size + 8); | ||
// javascript bitwise operators only support 32-bit integers | ||
for (let i = 7; i >= 4; i--) { | ||
buffer[i] = size & 0xff; | ||
size = size >> 8; | ||
} | ||
buffer.set(output, 8); | ||
let lenBuffer = []; | ||
do { | ||
let sizePart = size & 0x7f; | ||
size = size >> 7; | ||
if (size > 0) { | ||
sizePart |= 0x80; | ||
} | ||
lenBuffer.push(sizePart); | ||
} while (size > 0); | ||
// msgpack5 uses returns Buffer instead of Uint8Array on IE10 and some other browser | ||
// in which case .byteLength does will be undefined | ||
size = output.byteLength || output.length; | ||
let buffer = new Uint8Array(lenBuffer.length + size); | ||
buffer.set(lenBuffer, 0); | ||
buffer.set(output, lenBuffer.length); | ||
return buffer.buffer; | ||
@@ -41,27 +52,29 @@ } | ||
let uint8Array = new Uint8Array(input); | ||
// 8 - the length prefix size | ||
const maxLengthPrefixSize = 5; | ||
const numBitsToShift = [0, 7, 14, 21, 28]; | ||
for (let offset = 0; offset < input.byteLength;) { | ||
if (input.byteLength < offset + 8) { | ||
throw new Error("Cannot read message size"); | ||
let numBytes = 0; | ||
let size = 0; | ||
let byteRead; | ||
do { | ||
byteRead = uint8Array[offset + numBytes]; | ||
size = size | ((byteRead & 0x7f) << (numBitsToShift[numBytes])); | ||
numBytes++; | ||
} while (numBytes < Math.min(maxLengthPrefixSize, input.byteLength - offset) && (byteRead & 0x80) != 0); | ||
if ((byteRead & 0x80) !== 0 && numBytes < maxLengthPrefixSize) { | ||
throw new Error("Cannot read message size."); | ||
} | ||
// Note javascript bitwise operators only support 32-bit integers - for now cutting bigger messages. | ||
// Tracking bug https://github.com/aspnet/SignalR/issues/613 | ||
if (!(uint8Array[offset] == 0 && uint8Array[offset + 1] == 0 && uint8Array[offset + 2] == 0 | ||
&& uint8Array[offset + 3] == 0 && (uint8Array[offset + 4] & 0x80) == 0)) { | ||
throw new Error("Messages bigger than 2147483647 bytes are not supported"); | ||
if (numBytes === maxLengthPrefixSize && byteRead > 7) { | ||
throw new Error("Messages bigger than 2GB are not supported."); | ||
} | ||
let size = 0; | ||
for (let i = 4; i < 8; i++) { | ||
size = (size << 8) | uint8Array[offset + i]; | ||
} | ||
if (uint8Array.byteLength >= (offset + 8 + size)) { | ||
if (uint8Array.byteLength >= (offset + numBytes + size)) { | ||
// IE does not support .slice() so use subarray | ||
result.push(uint8Array.slice | ||
? uint8Array.slice(offset + 8, offset + 8 + size) | ||
: uint8Array.subarray(offset + 8, offset + 8 + size)); | ||
? uint8Array.slice(offset + numBytes, offset + numBytes + size) | ||
: uint8Array.subarray(offset + numBytes, offset + numBytes + size)); | ||
} | ||
else { | ||
throw new Error("Incomplete message"); | ||
throw new Error("Incomplete message."); | ||
} | ||
offset = offset + 8 + size; | ||
offset = offset + numBytes + size; | ||
} | ||
@@ -68,0 +81,0 @@ return result; |
@@ -24,4 +24,4 @@ import { DataReceived, ConnectionClosed } from "./Common"; | ||
private resolveUrl(url); | ||
onDataReceived: DataReceived; | ||
onClosed: ConnectionClosed; | ||
onreceive: DataReceived; | ||
onclose: ConnectionClosed; | ||
} |
@@ -49,4 +49,4 @@ "use strict"; | ||
this.transport = this.createTransport(this.options.transport, negotiateResponse.availableTransports); | ||
this.transport.onDataReceived = this.onDataReceived; | ||
this.transport.onClosed = e => this.stopConnection(true, e); | ||
this.transport.onreceive = this.onreceive; | ||
this.transport.onclose = e => this.stopConnection(true, e); | ||
let requestedTransferMode = this.features.transferMode === 2 /* Binary */ | ||
@@ -122,4 +122,4 @@ ? 2 /* Binary */ | ||
this.connectionState = 3 /* Disconnected */; | ||
if (raiseClosed && this.onClosed) { | ||
this.onClosed(error); | ||
if (raiseClosed && this.onclose) { | ||
this.onclose(error); | ||
} | ||
@@ -132,3 +132,3 @@ } | ||
} | ||
if (typeof window === 'undefined') { | ||
if (typeof window === 'undefined' || !window || !window.document) { | ||
throw new Error(`Cannot resolve '${url}'.`); | ||
@@ -141,2 +141,5 @@ } | ||
: `${parser.protocol}//${parser.host}`; | ||
if (!url || url[0] != '/') { | ||
url = '/' + url; | ||
} | ||
let normalizedUrl = baseUrl + url; | ||
@@ -143,0 +146,0 @@ this.logger.log(ILogger_1.LogLevel.Information, `Normalizing '${url}' to '${normalizedUrl}'`); |
@@ -17,7 +17,7 @@ import { ConnectionClosed } from "./Common"; | ||
private id; | ||
private connectionClosedCallback; | ||
private closedCallbacks; | ||
constructor(urlOrConnection: string | IConnection, options?: IHubConnectionOptions); | ||
private onDataReceived(data); | ||
private processIncomingData(data); | ||
private invokeClientMethod(invocationMessage); | ||
private onConnectionClosed(error); | ||
private connectionClosed(error?); | ||
start(): Promise<void>; | ||
@@ -29,4 +29,5 @@ stop(): void; | ||
on(methodName: string, method: (...args: any[]) => void): void; | ||
onClosed: ConnectionClosed; | ||
off(methodName: string, method: (...args: any[]) => void): void; | ||
onclose(callback: ConnectionClosed): void; | ||
private createInvocation(methodName, args, nonblocking); | ||
} |
@@ -42,13 +42,10 @@ "use strict"; | ||
this.protocol = options.protocol || new JsonHubProtocol_1.JsonHubProtocol(); | ||
this.connection.onDataReceived = data => { | ||
this.onDataReceived(data); | ||
}; | ||
this.connection.onClosed = (error) => { | ||
this.onConnectionClosed(error); | ||
}; | ||
this.connection.onreceive = (data) => this.processIncomingData(data); | ||
this.connection.onclose = (error) => this.connectionClosed(error); | ||
this.callbacks = new Map(); | ||
this.methods = new Map(); | ||
this.closedCallbacks = []; | ||
this.id = 0; | ||
} | ||
onDataReceived(data) { | ||
processIncomingData(data) { | ||
// Parse the messages | ||
@@ -79,5 +76,5 @@ let messages = this.protocol.parseMessages(data); | ||
invokeClientMethod(invocationMessage) { | ||
let method = this.methods.get(invocationMessage.target.toLowerCase()); | ||
if (method) { | ||
method.apply(this, invocationMessage.arguments); | ||
let methods = this.methods.get(invocationMessage.target.toLowerCase()); | ||
if (methods) { | ||
methods.forEach(m => m.apply(this, invocationMessage.arguments)); | ||
if (!invocationMessage.nonblocking) { | ||
@@ -91,3 +88,3 @@ // TODO: send result back to the server? | ||
} | ||
onConnectionClosed(error) { | ||
connectionClosed(error) { | ||
let errorCompletionMessage = { | ||
@@ -102,5 +99,3 @@ type: 3 /* Completion */, | ||
this.callbacks.clear(); | ||
if (this.connectionClosedCallback) { | ||
this.connectionClosedCallback(error); | ||
} | ||
this.closedCallbacks.forEach(c => c.apply(this, [error])); | ||
} | ||
@@ -186,7 +181,30 @@ start() { | ||
on(methodName, method) { | ||
this.methods.set(methodName.toLowerCase(), method); | ||
if (!methodName || !method) { | ||
return; | ||
} | ||
methodName = methodName.toLowerCase(); | ||
if (!this.methods.has(methodName)) { | ||
this.methods.set(methodName, []); | ||
} | ||
this.methods.get(methodName).push(method); | ||
} | ||
set onClosed(callback) { | ||
this.connectionClosedCallback = callback; | ||
off(methodName, method) { | ||
if (!methodName || !method) { | ||
return; | ||
} | ||
methodName = methodName.toLowerCase(); | ||
let handlers = this.methods.get(methodName); | ||
if (!handlers) { | ||
return; | ||
} | ||
var removeIdx = handlers.indexOf(method); | ||
if (removeIdx != -1) { | ||
handlers.splice(removeIdx, 1); | ||
} | ||
} | ||
onclose(callback) { | ||
if (callback) { | ||
this.closedCallbacks.push(callback); | ||
} | ||
} | ||
createInvocation(methodName, args, nonblocking) { | ||
@@ -193,0 +211,0 @@ let id = this.id; |
@@ -7,4 +7,4 @@ import { DataReceived, ConnectionClosed } from "./Common"; | ||
stop(): void; | ||
onDataReceived: DataReceived; | ||
onClosed: ConnectionClosed; | ||
onreceive: DataReceived; | ||
onclose: ConnectionClosed; | ||
} |
@@ -17,4 +17,4 @@ import { DataReceived, TransportClosed } from "./Common"; | ||
stop(): void; | ||
onDataReceived: DataReceived; | ||
onClosed: TransportClosed; | ||
onreceive: DataReceived; | ||
onclose: TransportClosed; | ||
} | ||
@@ -28,4 +28,4 @@ export declare class WebSocketTransport implements ITransport { | ||
stop(): void; | ||
onDataReceived: DataReceived; | ||
onClosed: TransportClosed; | ||
onreceive: DataReceived; | ||
onclose: TransportClosed; | ||
} | ||
@@ -41,4 +41,4 @@ export declare class ServerSentEventsTransport implements ITransport { | ||
stop(): void; | ||
onDataReceived: DataReceived; | ||
onClosed: TransportClosed; | ||
onreceive: DataReceived; | ||
onclose: TransportClosed; | ||
} | ||
@@ -56,4 +56,4 @@ export declare class LongPollingTransport implements ITransport { | ||
stop(): void; | ||
onDataReceived: DataReceived; | ||
onClosed: TransportClosed; | ||
onreceive: DataReceived; | ||
onclose: TransportClosed; | ||
} |
@@ -42,4 +42,4 @@ "use strict"; | ||
this.logger.log(ILogger_1.LogLevel.Trace, `(WebSockets transport) data received: ${message.data}`); | ||
if (this.onDataReceived) { | ||
this.onDataReceived(message.data); | ||
if (this.onreceive) { | ||
this.onreceive(message.data); | ||
} | ||
@@ -49,8 +49,8 @@ }; | ||
// webSocket will be null if the transport did not start successfully | ||
if (this.onClosed && this.webSocket) { | ||
if (this.onclose && this.webSocket) { | ||
if (event.wasClean === false || event.code !== 1000) { | ||
this.onClosed(new Error(`Websocket closed with status code: ${event.code} (${event.reason})`)); | ||
this.onclose(new Error(`Websocket closed with status code: ${event.code} (${event.reason})`)); | ||
} | ||
else { | ||
this.onClosed(); | ||
this.onclose(); | ||
} | ||
@@ -90,10 +90,10 @@ } | ||
eventSource.onmessage = (e) => { | ||
if (this.onDataReceived) { | ||
if (this.onreceive) { | ||
try { | ||
this.logger.log(ILogger_1.LogLevel.Trace, `(SSE transport) data received: ${e.data}`); | ||
this.onDataReceived(e.data); | ||
this.onreceive(e.data); | ||
} | ||
catch (error) { | ||
if (this.onClosed) { | ||
this.onClosed(error); | ||
if (this.onclose) { | ||
this.onclose(error); | ||
} | ||
@@ -107,4 +107,4 @@ return; | ||
// don't report an error if the transport did not start successfully | ||
if (this.eventSource && this.onClosed) { | ||
this.onClosed(new Error(e.message || "Error occurred")); | ||
if (this.eventSource && this.onclose) { | ||
this.onclose(new Error(e.message || "Error occurred")); | ||
} | ||
@@ -159,3 +159,3 @@ }; | ||
if (pollXhr.status == 200) { | ||
if (this.onDataReceived) { | ||
if (this.onreceive) { | ||
try { | ||
@@ -167,3 +167,3 @@ let response = transferMode === 1 /* Text */ | ||
this.logger.log(ILogger_1.LogLevel.Trace, `(LongPolling transport) data received: ${response}`); | ||
this.onDataReceived(response); | ||
this.onreceive(response); | ||
} | ||
@@ -175,4 +175,4 @@ else { | ||
catch (error) { | ||
if (this.onClosed) { | ||
this.onClosed(error); | ||
if (this.onclose) { | ||
this.onclose(error); | ||
} | ||
@@ -185,9 +185,9 @@ return; | ||
else if (this.pollXhr.status == 204) { | ||
if (this.onClosed) { | ||
this.onClosed(); | ||
if (this.onclose) { | ||
this.onclose(); | ||
} | ||
} | ||
else { | ||
if (this.onClosed) { | ||
this.onClosed(new HttpError_1.HttpError(pollXhr.statusText, pollXhr.status)); | ||
if (this.onclose) { | ||
this.onclose(new HttpError_1.HttpError(pollXhr.statusText, pollXhr.status)); | ||
} | ||
@@ -197,5 +197,5 @@ } | ||
pollXhr.onerror = () => { | ||
if (this.onClosed) { | ||
if (this.onclose) { | ||
// network related error or denied cross domain request | ||
this.onClosed(new Error("Sending HTTP request failed.")); | ||
this.onclose(new Error("Sending HTTP request failed.")); | ||
} | ||
@@ -202,0 +202,0 @@ }; |
{ | ||
"name": "@aspnet/signalr-client", | ||
"version": "1.0.0-alpha1-final", | ||
"version": "1.0.0-alpha2-final", | ||
"description": "ASP.NET Core SignalR", | ||
@@ -5,0 +5,0 @@ "main": "dist/src/index.js", |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Minified code
QualityThis package contains minified code. This may be harmless in some cases where minified code is included in packaged libraries, however packages on npm should not minify code.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
No README
QualityPackage does not have a README. This may indicate a failed publish or a low quality package.
Found 1 instance in 1 package
Minified code
QualityThis package contains minified code. This may be harmless in some cases where minified code is included in packaged libraries, however packages on npm should not minify code.
Found 1 instance in 1 package
1006811
47
19848
1
34
11