Updated to RTM
This commit is contained in:
Родитель
7967a00854
Коммит
c17e81884b
|
@ -53,8 +53,8 @@
|
|||
<None Include="Scripts\jquery-1.8.3.intellisense.js" />
|
||||
<Content Include="Scripts\jquery-1.8.3.js" />
|
||||
<Content Include="Scripts\jquery-1.8.3.min.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0-rc1.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0-rc1.min.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0.min.js" />
|
||||
<Content Include="Web.config" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
|
Различия файлов скрыты, потому что одна или несколько строк слишком длинны
|
@ -57,21 +57,6 @@
|
|||
}
|
||||
},
|
||||
|
||||
isCrossDomain = function (url) {
|
||||
var link;
|
||||
|
||||
url = $.trim(url);
|
||||
if (url.indexOf("http") !== 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Create an anchor tag.
|
||||
link = window.document.createElement("a");
|
||||
link.href = url;
|
||||
|
||||
return link.protocol + link.host !== window.location.protocol + window.location.host;
|
||||
},
|
||||
|
||||
changeState = function (connection, expectedState, newState) {
|
||||
if (expectedState === connection.state) {
|
||||
connection.state = newState;
|
||||
|
@ -89,22 +74,30 @@
|
|||
|
||||
configureStopReconnectingTimeout = function (connection) {
|
||||
var stopReconnectingTimeout,
|
||||
onReconnectTimeout;
|
||||
|
||||
// Check if this connection has already been configured to stop reconnecting after a specified timeout.
|
||||
// Without this check if a connection is stopped then started events will be bound multiple times.
|
||||
if (!connection._.configuredStopReconnectingTimeout) {
|
||||
onReconnectTimeout = function (connection) {
|
||||
connection.log("Couldn't reconnect within the configured timeout (" + connection.disconnectTimeout + "ms), disconnecting.");
|
||||
connection.stop(/* async */ false, /* notifyServer */ false);
|
||||
};
|
||||
|
||||
connection.reconnecting(function () {
|
||||
var connection = this;
|
||||
stopReconnectingTimeout = window.setTimeout(function () { onReconnectTimeout(connection); }, connection.disconnectTimeout);
|
||||
});
|
||||
connection.reconnecting(function () {
|
||||
var connection = this;
|
||||
stopReconnectingTimeout = window.setTimeout(function () { onReconnectTimeout(connection); }, connection.disconnectTimeout);
|
||||
});
|
||||
|
||||
connection.stateChanged(function (data) {
|
||||
if (data.oldState === signalR.connectionState.reconnecting) {
|
||||
// Clear the pending reconnect timeout check
|
||||
window.clearTimeout(stopReconnectingTimeout);
|
||||
}
|
||||
});
|
||||
connection.stateChanged(function (data) {
|
||||
if (data.oldState === signalR.connectionState.reconnecting) {
|
||||
// Clear the pending reconnect timeout check
|
||||
window.clearTimeout(stopReconnectingTimeout);
|
||||
}
|
||||
});
|
||||
|
||||
connection._.configuredStopReconnectingTimeout = true;
|
||||
}
|
||||
};
|
||||
|
||||
signalR = function (url, qs, logging) {
|
||||
|
@ -173,14 +166,57 @@
|
|||
return requestedTransport;
|
||||
}
|
||||
|
||||
function getDefaultPort(protocol) {
|
||||
if(protocol === "http:") {
|
||||
return 80;
|
||||
}
|
||||
else if (protocol === "https:") {
|
||||
return 443;
|
||||
}
|
||||
}
|
||||
|
||||
function addDefaultPort(protocol, url) {
|
||||
// Remove ports from url. We have to check if there's a / or end of line
|
||||
// following the port in order to avoid removing ports such as 8080.
|
||||
if(url.match(/:\d+$/)) {
|
||||
return url;
|
||||
} else {
|
||||
return url + ":" + getDefaultPort(protocol);
|
||||
}
|
||||
}
|
||||
|
||||
signalR.fn = signalR.prototype = {
|
||||
init: function (url, qs, logging) {
|
||||
this.url = url;
|
||||
this.qs = qs;
|
||||
this._ = {};
|
||||
if (typeof (logging) === "boolean") {
|
||||
this.logging = logging;
|
||||
}
|
||||
},
|
||||
|
||||
isCrossDomain: function (url, against) {
|
||||
/// <summary>Checks if url is cross domain</summary>
|
||||
/// <param name="url" type="String">The base URL</param>
|
||||
/// <param name="against" type="Object">
|
||||
/// An optional argument to compare the URL against, if not specified it will be set to window.location.
|
||||
/// If specified it must contain a protocol and a host property.
|
||||
/// </param>
|
||||
var link;
|
||||
|
||||
url = $.trim(url);
|
||||
if (url.indexOf("http") !== 0) {
|
||||
return false;
|
||||
}
|
||||
configureStopReconnectingTimeout(this);
|
||||
|
||||
against = against || window.location;
|
||||
|
||||
// Create an anchor tag.
|
||||
link = window.document.createElement("a");
|
||||
link.href = url;
|
||||
|
||||
// When checking for cross domain we have to special case port 80 because the window.location will remove the
|
||||
return link.protocol + addDefaultPort(link.protocol, link.host) !== against.protocol + addDefaultPort(against.protocol, against.host);
|
||||
},
|
||||
|
||||
ajaxDataType: "json",
|
||||
|
@ -189,16 +225,12 @@
|
|||
|
||||
state: signalR.connectionState.disconnected,
|
||||
|
||||
groups: {},
|
||||
|
||||
keepAliveData: {},
|
||||
|
||||
reconnectDelay: 2000,
|
||||
|
||||
disconnectTimeout: 40000, // This should be set by the server in response to the negotiate request (40s default)
|
||||
|
||||
keepAliveTimeoutCount: 2,
|
||||
|
||||
keepAliveWarnAt: 2 / 3, // Warn user of slow connection if we breach the X% mark of the keep alive timeout
|
||||
|
||||
start: function (options, callback) {
|
||||
|
@ -242,6 +274,8 @@
|
|||
return deferred.promise();
|
||||
}
|
||||
|
||||
configureStopReconnectingTimeout(connection);
|
||||
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.disconnected,
|
||||
signalR.connectionState.connecting) === false) {
|
||||
|
@ -274,7 +308,7 @@
|
|||
config.transport = "longPolling";
|
||||
}
|
||||
|
||||
if (isCrossDomain(connection.url)) {
|
||||
if (this.isCrossDomain(connection.url)) {
|
||||
connection.log("Auto detected cross domain url.");
|
||||
|
||||
if (config.transport === "auto") {
|
||||
|
@ -368,6 +402,7 @@
|
|||
|
||||
connection.appRelativeUrl = res.Url;
|
||||
connection.id = res.ConnectionId;
|
||||
connection.token = res.ConnectionToken;
|
||||
connection.webSocketServerUrl = res.WebSocketServerUrl;
|
||||
|
||||
// Once the server has labeled the PersistentConnection as Disconnected, we should stop attempting to reconnect
|
||||
|
@ -376,15 +411,12 @@
|
|||
|
||||
|
||||
// If we have a keep alive
|
||||
if (res.KeepAlive) {
|
||||
// Convert to milliseconds
|
||||
res.KeepAlive *= 1000;
|
||||
|
||||
if (res.KeepAliveTimeout) {
|
||||
// Register the keep alive data as activated
|
||||
keepAliveData.activated = true;
|
||||
|
||||
// Timeout to designate when to force the connection into reconnecting
|
||||
keepAliveData.timeout = res.KeepAlive * connection.keepAliveTimeoutCount;
|
||||
// Timeout to designate when to force the connection into reconnecting converted to milliseconds
|
||||
keepAliveData.timeout = res.KeepAliveTimeout * 1000;
|
||||
|
||||
// Timeout to designate when to warn the developer that the connection may be dead or is hanging.
|
||||
keepAliveData.timeoutWarning = keepAliveData.timeout * connection.keepAliveWarnAt;
|
||||
|
@ -396,7 +428,7 @@
|
|||
keepAliveData.activated = false;
|
||||
}
|
||||
|
||||
if (!res.ProtocolVersion || res.ProtocolVersion !== "1.1") {
|
||||
if (!res.ProtocolVersion || res.ProtocolVersion !== "1.2") {
|
||||
$(connection).triggerHandler(events.onError, "SignalR: Incompatible protocol version.");
|
||||
deferred.reject("SignalR: Incompatible protocol version.");
|
||||
return;
|
||||
|
@ -576,7 +608,7 @@
|
|||
$(connection).triggerHandler(events.onDisconnect);
|
||||
|
||||
delete connection.messageId;
|
||||
delete connection.groups;
|
||||
delete connection.groupsToken;
|
||||
|
||||
// Remove the ID and the deferral on stop, this is to ensure that if a connection is restarted it takes on a new id/deferral.
|
||||
delete connection.id;
|
||||
|
@ -670,6 +702,37 @@
|
|||
}
|
||||
|
||||
signalR.transports._logic = {
|
||||
pingServer: function (connection, transport) {
|
||||
/// <summary>Pings the server</summary>
|
||||
/// <param name="connection" type="signalr">Connection associated with the server ping</param>
|
||||
/// <returns type="signalR" />
|
||||
var baseUrl = transport === "webSockets" ? "" : connection.baseUrl,
|
||||
url = baseUrl + connection.appRelativeUrl + "/ping",
|
||||
deferral = $.Deferred();
|
||||
|
||||
$.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
data: {},
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (data) {
|
||||
if (data.Response === "pong") {
|
||||
deferral.resolve();
|
||||
}
|
||||
else {
|
||||
deferral.reject("SignalR: Invalid ping response when pinging server: " + (data.responseText || data.statusText));
|
||||
}
|
||||
},
|
||||
error: function (data) {
|
||||
deferral.reject("SignalR: Error pinging server: " + (data.responseText || data.statusText));
|
||||
}
|
||||
});
|
||||
|
||||
return deferral.promise();
|
||||
},
|
||||
|
||||
addQs: function (url, connection) {
|
||||
if (!connection.qs) {
|
||||
return url;
|
||||
|
@ -683,18 +746,21 @@
|
|||
return url + "&" + connection.qs;
|
||||
}
|
||||
|
||||
return url + "&" + window.escape(connection.qs.toString());
|
||||
return url + "&" + window.encodeURIComponent(connection.qs.toString());
|
||||
},
|
||||
|
||||
getUrl: function (connection, transport, reconnecting, appendReconnectUrl) {
|
||||
/// <summary>Gets the url for making a GET based connect request</summary>
|
||||
var baseUrl = transport === "webSockets" ? "" : connection.baseUrl,
|
||||
url = baseUrl + connection.appRelativeUrl,
|
||||
qs = "transport=" + transport + "&connectionId=" + window.escape(connection.id),
|
||||
groups = this.getGroups(connection);
|
||||
qs = "transport=" + transport + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
|
||||
if (connection.data) {
|
||||
qs += "&connectionData=" + window.escape(connection.data);
|
||||
qs += "&connectionData=" + window.encodeURIComponent(connection.data);
|
||||
}
|
||||
|
||||
if (connection.groupsToken) {
|
||||
qs += "&groupsToken=" + window.encodeURIComponent(connection.groupsToken);
|
||||
}
|
||||
|
||||
if (!reconnecting) {
|
||||
|
@ -704,10 +770,7 @@
|
|||
url = url + "/reconnect";
|
||||
}
|
||||
if (connection.messageId) {
|
||||
qs += "&messageId=" + window.escape(connection.messageId);
|
||||
}
|
||||
if (groups.length !== 0) {
|
||||
qs += "&groups=" + window.escape(JSON.stringify(groups));
|
||||
qs += "&messageId=" + window.encodeURIComponent(connection.messageId);
|
||||
}
|
||||
}
|
||||
url += "?" + qs;
|
||||
|
@ -723,49 +786,18 @@
|
|||
Disconnect: typeof (minPersistentResponse.D) !== "undefined" ? true : false,
|
||||
TimedOut: typeof (minPersistentResponse.T) !== "undefined" ? true : false,
|
||||
LongPollDelay: minPersistentResponse.L,
|
||||
ResetGroups: minPersistentResponse.R,
|
||||
AddedGroups: minPersistentResponse.G,
|
||||
RemovedGroups: minPersistentResponse.g
|
||||
GroupsToken: minPersistentResponse.G
|
||||
};
|
||||
},
|
||||
|
||||
updateGroups: function (connection, resetGroups, addedGroups, removedGroups) {
|
||||
// Use the keys in connection.groups object as a set of groups.
|
||||
// Prefix all group names with # so we don't conflict with the object's prototype or __proto__.
|
||||
function addGroups(groups) {
|
||||
$.each(groups, function (_, group) {
|
||||
connection.groups['#' + group] = true;
|
||||
});
|
||||
updateGroups: function (connection, groupsToken) {
|
||||
if (groupsToken) {
|
||||
connection.groupsToken = groupsToken;
|
||||
}
|
||||
|
||||
if (resetGroups) {
|
||||
connection.groups = {};
|
||||
addGroups(resetGroups);
|
||||
} else {
|
||||
if (addedGroups) {
|
||||
addGroups(addedGroups);
|
||||
}
|
||||
if (removedGroups) {
|
||||
$.each(removedGroups, function (_, group) {
|
||||
delete connection.groups['# ' + group];
|
||||
});
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
getGroups: function (connection) {
|
||||
var groups = [];
|
||||
if (connection.groups) {
|
||||
$.each(connection.groups, function (group, _) {
|
||||
// Add keys from connection.groups without the # prefix
|
||||
groups.push(group.substr(1));
|
||||
});
|
||||
}
|
||||
return groups;
|
||||
},
|
||||
|
||||
ajaxSend: function (connection, data) {
|
||||
var url = connection.url + "/send" + "?transport=" + connection.transport.name + "&connectionId=" + window.escape(connection.id);
|
||||
var url = connection.url + "/send" + "?transport=" + connection.transport.name + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
url = this.addQs(url, connection);
|
||||
return $.ajax({
|
||||
url: url,
|
||||
|
@ -801,7 +833,7 @@
|
|||
// Async by default unless explicitly overidden
|
||||
async = typeof async === "undefined" ? true : async;
|
||||
|
||||
var url = connection.url + "/abort" + "?transport=" + connection.transport.name + "&connectionId=" + window.escape(connection.id);
|
||||
var url = connection.url + "/abort" + "?transport=" + connection.transport.name + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
url = this.addQs(url, connection);
|
||||
$.ajax({
|
||||
url: url,
|
||||
|
@ -842,7 +874,7 @@
|
|||
return;
|
||||
}
|
||||
|
||||
this.updateGroups(connection, data.ResetGroups, data.AddedGroups, data.RemovedGroups);
|
||||
this.updateGroups(connection, data.GroupsToken);
|
||||
|
||||
if (data.Messages) {
|
||||
$.each(data.Messages, function () {
|
||||
|
@ -961,10 +993,6 @@
|
|||
reconnecting = !onSuccess,
|
||||
$connection = $(connection);
|
||||
|
||||
if (window.MozWebSocket) {
|
||||
window.WebSocket = window.MozWebSocket;
|
||||
}
|
||||
|
||||
if (!window.WebSocket) {
|
||||
onFailed();
|
||||
return;
|
||||
|
@ -1398,8 +1426,7 @@
|
|||
if (connection.frame.stop) {
|
||||
connection.frame.stop();
|
||||
} else {
|
||||
try
|
||||
{
|
||||
try {
|
||||
cw = connection.frame.contentWindow || connection.frame.contentDocument;
|
||||
if (cw.document && cw.document.execCommand) {
|
||||
cw.document.execCommand("Stop");
|
||||
|
@ -1464,139 +1491,151 @@
|
|||
|
||||
reconnectDelay: 3000,
|
||||
|
||||
init: function (connection, onComplete) {
|
||||
/// <summary>Pings the server to ensure availability</summary>
|
||||
/// <param name="connection" type="signalr">Connection associated with the server ping</param>
|
||||
/// <param name="onComplete" type="Function">Callback to call once initialization has completed</param>
|
||||
|
||||
var that = this,
|
||||
pingLoop,
|
||||
// pingFail is used to loop the re-ping behavior. When we fail we want to re-try.
|
||||
pingFail = function (reason) {
|
||||
if (isDisconnecting(connection) === false) {
|
||||
connection.log("SignalR: Server ping failed because '" + reason + "', re-trying ping.");
|
||||
window.setTimeout(pingLoop, that.reconnectDelay);
|
||||
}
|
||||
};
|
||||
|
||||
connection.log("SignalR: Initializing long polling connection with server.");
|
||||
pingLoop = function () {
|
||||
// Ping the server, on successful ping call the onComplete method, otherwise if we fail call the pingFail
|
||||
transportLogic.pingServer(connection, that.name).done(onComplete).fail(pingFail);
|
||||
};
|
||||
|
||||
pingLoop();
|
||||
},
|
||||
|
||||
start: function (connection, onSuccess, onFailed) {
|
||||
/// <summary>Starts the long polling connection</summary>
|
||||
/// <param name="connection" type="signalR">The SignalR connection to start</param>
|
||||
var that = this,
|
||||
initialConnectFired = false;
|
||||
initialConnectedFired = false,
|
||||
fireConnect = function () {
|
||||
if (initialConnectedFired) {
|
||||
return;
|
||||
}
|
||||
initialConnectedFired = true;
|
||||
onSuccess();
|
||||
connection.log("Longpolling connected");
|
||||
};
|
||||
|
||||
if (connection.pollXhr) {
|
||||
connection.log("Polling xhr requests already exists, aborting.");
|
||||
connection.stop();
|
||||
}
|
||||
|
||||
connection.messageId = null;
|
||||
// We start with an initialization procedure which pings the server to verify that it is there.
|
||||
// On scucessful initialization we'll then proceed with starting the transport.
|
||||
that.init(connection, function () {
|
||||
connection.messageId = null;
|
||||
|
||||
window.setTimeout(function () {
|
||||
(function poll(instance, raiseReconnect) {
|
||||
var messageId = instance.messageId,
|
||||
connect = (messageId === null),
|
||||
reconnecting = !connect,
|
||||
url = transportLogic.getUrl(instance, that.name, reconnecting, raiseReconnect),
|
||||
reconnectTimeOut = null,
|
||||
reconnectFired = false,
|
||||
triggerReconnected = function () {
|
||||
// Fire the reconnect event if it hasn't been fired as yet
|
||||
if (reconnectFired === false) {
|
||||
connection.log("Raising the reconnect event");
|
||||
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.reconnecting,
|
||||
signalR.connectionState.connected) === true) {
|
||||
|
||||
$(instance).triggerHandler(events.onReconnect);
|
||||
reconnectFired = true;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
if (reconnecting === true && raiseReconnect === true &&
|
||||
!transportLogic.ensureReconnectingState(connection)) {
|
||||
return;
|
||||
}
|
||||
|
||||
connection.log("Attempting to connect to '" + url + "' using longPolling.");
|
||||
instance.pollXhr = $.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (minData) {
|
||||
var delay = 0,
|
||||
timedOutReceived = false,
|
||||
data;
|
||||
|
||||
if (minData) {
|
||||
data = transportLogic.maximizePersistentResponse(minData);
|
||||
}
|
||||
|
||||
if (initialConnectFired === false) {
|
||||
onSuccess();
|
||||
initialConnectFired = true;
|
||||
}
|
||||
|
||||
if (raiseReconnect === true) {
|
||||
triggerReconnected();
|
||||
}
|
||||
|
||||
transportLogic.processMessages(instance, minData);
|
||||
if (data &&
|
||||
$.type(data.LongPollDelay) === "number") {
|
||||
delay = data.LongPollDelay;
|
||||
}
|
||||
|
||||
if (data && data.TimedOut) {
|
||||
timedOutReceived = data.TimedOut;
|
||||
}
|
||||
|
||||
if (data && data.Disconnect) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (delay > 0) {
|
||||
window.setTimeout(function () {
|
||||
poll(instance, timedOutReceived);
|
||||
}, delay);
|
||||
} else {
|
||||
poll(instance, timedOutReceived);
|
||||
}
|
||||
},
|
||||
|
||||
error: function (data, textStatus) {
|
||||
if (textStatus === "abort") {
|
||||
connection.log("Aborted xhr requst.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (connection.state !== signalR.connectionState.reconnecting) {
|
||||
connection.log("An error occurred using longPolling. Status = " + textStatus + ". " + data.responseText);
|
||||
$(instance).triggerHandler(events.onError, [data.responseText]);
|
||||
}
|
||||
|
||||
// If the request failed then we clear the timeout so that the
|
||||
// reconnect event doesn't get fired
|
||||
window.clearTimeout(reconnectTimeOut);
|
||||
|
||||
window.setTimeout(function () {
|
||||
if (isDisconnecting(instance) === false) {
|
||||
poll(instance, true);
|
||||
}
|
||||
}, connection.reconnectDelay);
|
||||
}
|
||||
});
|
||||
|
||||
if (raiseReconnect === true) {
|
||||
reconnectTimeOut = window.setTimeout(triggerReconnected, that.reconnectDelay);
|
||||
}
|
||||
|
||||
}(connection));
|
||||
|
||||
// Now connected
|
||||
// There's no good way know when the long poll has actually started so
|
||||
// we assume it only takes around 150ms (max) to start the connection
|
||||
window.setTimeout(function () {
|
||||
if (initialConnectFired === false) {
|
||||
onSuccess();
|
||||
initialConnectFired = true;
|
||||
}
|
||||
}, 150);
|
||||
(function poll(instance, raiseReconnect) {
|
||||
var messageId = instance.messageId,
|
||||
connect = (messageId === null),
|
||||
reconnecting = !connect,
|
||||
url = transportLogic.getUrl(instance, that.name, reconnecting, raiseReconnect);
|
||||
|
||||
}, 250); // Have to delay initial poll so Chrome doesn't show loader spinner in tab
|
||||
// If we've disconnected during the time we've tried to re-instantiate the poll then stop.
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
connection.log("Attempting to connect to '" + url + "' using longPolling.");
|
||||
instance.pollXhr = $.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (minData) {
|
||||
var delay = 0,
|
||||
data;
|
||||
|
||||
fireConnect();
|
||||
|
||||
if (minData) {
|
||||
data = transportLogic.maximizePersistentResponse(minData);
|
||||
}
|
||||
|
||||
transportLogic.processMessages(instance, minData);
|
||||
|
||||
if (data &&
|
||||
$.type(data.LongPollDelay) === "number") {
|
||||
delay = data.LongPollDelay;
|
||||
}
|
||||
|
||||
if (data && data.Disconnect) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
// We never want to pass a raiseReconnect flag after a successful poll. This is handled via the error function
|
||||
if (delay > 0) {
|
||||
window.setTimeout(function () {
|
||||
poll(instance, false);
|
||||
}, delay);
|
||||
} else {
|
||||
poll(instance, false);
|
||||
}
|
||||
},
|
||||
|
||||
error: function (data, textStatus) {
|
||||
if (textStatus === "abort") {
|
||||
connection.log("Aborted xhr requst.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (connection.state !== signalR.connectionState.reconnecting) {
|
||||
connection.log("An error occurred using longPolling. Status = " + textStatus + ". " + data.responseText);
|
||||
$(instance).triggerHandler(events.onError, [data.responseText]);
|
||||
}
|
||||
|
||||
// Transition into the reconnecting state
|
||||
transportLogic.ensureReconnectingState(instance);
|
||||
|
||||
// If we've errored out we need to verify that the server is still there, so re-start initialization process
|
||||
// This will ping the server until it successfully gets a response.
|
||||
that.init(instance, function () {
|
||||
// Call poll with the raiseReconnect flag as true
|
||||
poll(instance, true);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
// This will only ever pass after an error has occured via the poll ajax procedure.
|
||||
if (reconnecting && raiseReconnect === true) {
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.reconnecting,
|
||||
signalR.connectionState.connected) === true) {
|
||||
// Successfully reconnected!
|
||||
connection.log("Raising the reconnect event");
|
||||
$(instance).triggerHandler(events.onReconnect);
|
||||
}
|
||||
}
|
||||
}(connection));
|
||||
|
||||
// Set an arbitrary timeout to trigger onSuccess, this will alot for enough time on the server to wire up the connection.
|
||||
// Will be fixed by #1189 and this code can be modified to not be a timeout
|
||||
window.setTimeout(function () {
|
||||
// Trigger the onSuccess() method because we've now instantiated a connection
|
||||
fireConnect();
|
||||
}, 250);
|
||||
}, 250); // Have to delay initial poll so Chrome doesn't show loader spinner in tab
|
||||
});
|
||||
},
|
||||
|
||||
lostConnection: function (connection) {
|
Различия файлов скрыты, потому что одна или несколько строк слишком длинны
|
@ -9,7 +9,7 @@
|
|||
<ul id="message">
|
||||
</ul>
|
||||
<script src="Scripts/jquery-1.8.3.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0-rc1.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0.min.js"></script>
|
||||
<script src="http://localhost:44914/signalR/hubs"></script>
|
||||
<script>
|
||||
$(function () {
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<ul id="message">
|
||||
</ul>
|
||||
<script src="Scripts/jquery-1.8.3.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0-rc1.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0.min.js"></script>
|
||||
<script>
|
||||
$(function () {
|
||||
// Open a connection to the remote server
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="jQuery" version="1.8.3" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.JS" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.JS" version="1.0.0" targetFramework="net45" />
|
||||
</packages>
|
|
@ -43,17 +43,20 @@
|
|||
<ItemGroup>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Core, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.0-rc1\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.0\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Owin">
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Owin.1.0.0-rc1\lib\net45\Microsoft.AspNet.SignalR.Owin.dll</HintPath>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Owin, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Owin.1.0.0\lib\net45\Microsoft.AspNet.SignalR.Owin.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.SystemWeb">
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.SystemWeb.1.0.0-rc1\lib\net45\Microsoft.AspNet.SignalR.SystemWeb.dll</HintPath>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.SystemWeb, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.SystemWeb.1.0.0\lib\net45\Microsoft.AspNet.SignalR.SystemWeb.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="Microsoft.Owin.Host.SystemWeb">
|
||||
<HintPath>..\packages\Microsoft.Owin.Host.SystemWeb.1.0.0-rc1\lib\net45\Microsoft.Owin.Host.SystemWeb.dll</HintPath>
|
||||
<Reference Include="Microsoft.Owin.Host.SystemWeb, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.Owin.Host.SystemWeb.1.0.0\lib\net45\Microsoft.Owin.Host.SystemWeb.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Newtonsoft.Json, Version=4.5.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
|
@ -277,8 +280,8 @@
|
|||
<Content Include="Scripts\jquery-1.8.3.min.js" />
|
||||
<Content Include="Scripts\jquery-ui-1.8.20.js" />
|
||||
<Content Include="Scripts\jquery-ui-1.8.20.min.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0-rc1.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0-rc1.min.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0.min.js" />
|
||||
<Content Include="Scripts\jquery.unobtrusive-ajax.js" />
|
||||
<Content Include="Scripts\jquery.unobtrusive-ajax.min.js" />
|
||||
<Content Include="Scripts\jquery.validate.js" />
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Web;
|
||||
using Microsoft.AspNet.SignalR.Hubs;
|
||||
using Microsoft.AspNet.SignalR;
|
||||
|
||||
namespace BasicChat.Mvc
|
||||
{
|
||||
|
|
Различия файлов скрыты, потому что одна или несколько строк слишком длинны
|
@ -57,21 +57,6 @@
|
|||
}
|
||||
},
|
||||
|
||||
isCrossDomain = function (url) {
|
||||
var link;
|
||||
|
||||
url = $.trim(url);
|
||||
if (url.indexOf("http") !== 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Create an anchor tag.
|
||||
link = window.document.createElement("a");
|
||||
link.href = url;
|
||||
|
||||
return link.protocol + link.host !== window.location.protocol + window.location.host;
|
||||
},
|
||||
|
||||
changeState = function (connection, expectedState, newState) {
|
||||
if (expectedState === connection.state) {
|
||||
connection.state = newState;
|
||||
|
@ -89,22 +74,30 @@
|
|||
|
||||
configureStopReconnectingTimeout = function (connection) {
|
||||
var stopReconnectingTimeout,
|
||||
onReconnectTimeout;
|
||||
|
||||
// Check if this connection has already been configured to stop reconnecting after a specified timeout.
|
||||
// Without this check if a connection is stopped then started events will be bound multiple times.
|
||||
if (!connection._.configuredStopReconnectingTimeout) {
|
||||
onReconnectTimeout = function (connection) {
|
||||
connection.log("Couldn't reconnect within the configured timeout (" + connection.disconnectTimeout + "ms), disconnecting.");
|
||||
connection.stop(/* async */ false, /* notifyServer */ false);
|
||||
};
|
||||
|
||||
connection.reconnecting(function () {
|
||||
var connection = this;
|
||||
stopReconnectingTimeout = window.setTimeout(function () { onReconnectTimeout(connection); }, connection.disconnectTimeout);
|
||||
});
|
||||
connection.reconnecting(function () {
|
||||
var connection = this;
|
||||
stopReconnectingTimeout = window.setTimeout(function () { onReconnectTimeout(connection); }, connection.disconnectTimeout);
|
||||
});
|
||||
|
||||
connection.stateChanged(function (data) {
|
||||
if (data.oldState === signalR.connectionState.reconnecting) {
|
||||
// Clear the pending reconnect timeout check
|
||||
window.clearTimeout(stopReconnectingTimeout);
|
||||
}
|
||||
});
|
||||
connection.stateChanged(function (data) {
|
||||
if (data.oldState === signalR.connectionState.reconnecting) {
|
||||
// Clear the pending reconnect timeout check
|
||||
window.clearTimeout(stopReconnectingTimeout);
|
||||
}
|
||||
});
|
||||
|
||||
connection._.configuredStopReconnectingTimeout = true;
|
||||
}
|
||||
};
|
||||
|
||||
signalR = function (url, qs, logging) {
|
||||
|
@ -173,14 +166,57 @@
|
|||
return requestedTransport;
|
||||
}
|
||||
|
||||
function getDefaultPort(protocol) {
|
||||
if(protocol === "http:") {
|
||||
return 80;
|
||||
}
|
||||
else if (protocol === "https:") {
|
||||
return 443;
|
||||
}
|
||||
}
|
||||
|
||||
function addDefaultPort(protocol, url) {
|
||||
// Remove ports from url. We have to check if there's a / or end of line
|
||||
// following the port in order to avoid removing ports such as 8080.
|
||||
if(url.match(/:\d+$/)) {
|
||||
return url;
|
||||
} else {
|
||||
return url + ":" + getDefaultPort(protocol);
|
||||
}
|
||||
}
|
||||
|
||||
signalR.fn = signalR.prototype = {
|
||||
init: function (url, qs, logging) {
|
||||
this.url = url;
|
||||
this.qs = qs;
|
||||
this._ = {};
|
||||
if (typeof (logging) === "boolean") {
|
||||
this.logging = logging;
|
||||
}
|
||||
},
|
||||
|
||||
isCrossDomain: function (url, against) {
|
||||
/// <summary>Checks if url is cross domain</summary>
|
||||
/// <param name="url" type="String">The base URL</param>
|
||||
/// <param name="against" type="Object">
|
||||
/// An optional argument to compare the URL against, if not specified it will be set to window.location.
|
||||
/// If specified it must contain a protocol and a host property.
|
||||
/// </param>
|
||||
var link;
|
||||
|
||||
url = $.trim(url);
|
||||
if (url.indexOf("http") !== 0) {
|
||||
return false;
|
||||
}
|
||||
configureStopReconnectingTimeout(this);
|
||||
|
||||
against = against || window.location;
|
||||
|
||||
// Create an anchor tag.
|
||||
link = window.document.createElement("a");
|
||||
link.href = url;
|
||||
|
||||
// When checking for cross domain we have to special case port 80 because the window.location will remove the
|
||||
return link.protocol + addDefaultPort(link.protocol, link.host) !== against.protocol + addDefaultPort(against.protocol, against.host);
|
||||
},
|
||||
|
||||
ajaxDataType: "json",
|
||||
|
@ -189,16 +225,12 @@
|
|||
|
||||
state: signalR.connectionState.disconnected,
|
||||
|
||||
groups: {},
|
||||
|
||||
keepAliveData: {},
|
||||
|
||||
reconnectDelay: 2000,
|
||||
|
||||
disconnectTimeout: 40000, // This should be set by the server in response to the negotiate request (40s default)
|
||||
|
||||
keepAliveTimeoutCount: 2,
|
||||
|
||||
keepAliveWarnAt: 2 / 3, // Warn user of slow connection if we breach the X% mark of the keep alive timeout
|
||||
|
||||
start: function (options, callback) {
|
||||
|
@ -242,6 +274,8 @@
|
|||
return deferred.promise();
|
||||
}
|
||||
|
||||
configureStopReconnectingTimeout(connection);
|
||||
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.disconnected,
|
||||
signalR.connectionState.connecting) === false) {
|
||||
|
@ -274,7 +308,7 @@
|
|||
config.transport = "longPolling";
|
||||
}
|
||||
|
||||
if (isCrossDomain(connection.url)) {
|
||||
if (this.isCrossDomain(connection.url)) {
|
||||
connection.log("Auto detected cross domain url.");
|
||||
|
||||
if (config.transport === "auto") {
|
||||
|
@ -368,6 +402,7 @@
|
|||
|
||||
connection.appRelativeUrl = res.Url;
|
||||
connection.id = res.ConnectionId;
|
||||
connection.token = res.ConnectionToken;
|
||||
connection.webSocketServerUrl = res.WebSocketServerUrl;
|
||||
|
||||
// Once the server has labeled the PersistentConnection as Disconnected, we should stop attempting to reconnect
|
||||
|
@ -376,15 +411,12 @@
|
|||
|
||||
|
||||
// If we have a keep alive
|
||||
if (res.KeepAlive) {
|
||||
// Convert to milliseconds
|
||||
res.KeepAlive *= 1000;
|
||||
|
||||
if (res.KeepAliveTimeout) {
|
||||
// Register the keep alive data as activated
|
||||
keepAliveData.activated = true;
|
||||
|
||||
// Timeout to designate when to force the connection into reconnecting
|
||||
keepAliveData.timeout = res.KeepAlive * connection.keepAliveTimeoutCount;
|
||||
// Timeout to designate when to force the connection into reconnecting converted to milliseconds
|
||||
keepAliveData.timeout = res.KeepAliveTimeout * 1000;
|
||||
|
||||
// Timeout to designate when to warn the developer that the connection may be dead or is hanging.
|
||||
keepAliveData.timeoutWarning = keepAliveData.timeout * connection.keepAliveWarnAt;
|
||||
|
@ -396,7 +428,7 @@
|
|||
keepAliveData.activated = false;
|
||||
}
|
||||
|
||||
if (!res.ProtocolVersion || res.ProtocolVersion !== "1.1") {
|
||||
if (!res.ProtocolVersion || res.ProtocolVersion !== "1.2") {
|
||||
$(connection).triggerHandler(events.onError, "SignalR: Incompatible protocol version.");
|
||||
deferred.reject("SignalR: Incompatible protocol version.");
|
||||
return;
|
||||
|
@ -576,7 +608,7 @@
|
|||
$(connection).triggerHandler(events.onDisconnect);
|
||||
|
||||
delete connection.messageId;
|
||||
delete connection.groups;
|
||||
delete connection.groupsToken;
|
||||
|
||||
// Remove the ID and the deferral on stop, this is to ensure that if a connection is restarted it takes on a new id/deferral.
|
||||
delete connection.id;
|
||||
|
@ -670,6 +702,37 @@
|
|||
}
|
||||
|
||||
signalR.transports._logic = {
|
||||
pingServer: function (connection, transport) {
|
||||
/// <summary>Pings the server</summary>
|
||||
/// <param name="connection" type="signalr">Connection associated with the server ping</param>
|
||||
/// <returns type="signalR" />
|
||||
var baseUrl = transport === "webSockets" ? "" : connection.baseUrl,
|
||||
url = baseUrl + connection.appRelativeUrl + "/ping",
|
||||
deferral = $.Deferred();
|
||||
|
||||
$.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
data: {},
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (data) {
|
||||
if (data.Response === "pong") {
|
||||
deferral.resolve();
|
||||
}
|
||||
else {
|
||||
deferral.reject("SignalR: Invalid ping response when pinging server: " + (data.responseText || data.statusText));
|
||||
}
|
||||
},
|
||||
error: function (data) {
|
||||
deferral.reject("SignalR: Error pinging server: " + (data.responseText || data.statusText));
|
||||
}
|
||||
});
|
||||
|
||||
return deferral.promise();
|
||||
},
|
||||
|
||||
addQs: function (url, connection) {
|
||||
if (!connection.qs) {
|
||||
return url;
|
||||
|
@ -683,18 +746,21 @@
|
|||
return url + "&" + connection.qs;
|
||||
}
|
||||
|
||||
return url + "&" + window.escape(connection.qs.toString());
|
||||
return url + "&" + window.encodeURIComponent(connection.qs.toString());
|
||||
},
|
||||
|
||||
getUrl: function (connection, transport, reconnecting, appendReconnectUrl) {
|
||||
/// <summary>Gets the url for making a GET based connect request</summary>
|
||||
var baseUrl = transport === "webSockets" ? "" : connection.baseUrl,
|
||||
url = baseUrl + connection.appRelativeUrl,
|
||||
qs = "transport=" + transport + "&connectionId=" + window.escape(connection.id),
|
||||
groups = this.getGroups(connection);
|
||||
qs = "transport=" + transport + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
|
||||
if (connection.data) {
|
||||
qs += "&connectionData=" + window.escape(connection.data);
|
||||
qs += "&connectionData=" + window.encodeURIComponent(connection.data);
|
||||
}
|
||||
|
||||
if (connection.groupsToken) {
|
||||
qs += "&groupsToken=" + window.encodeURIComponent(connection.groupsToken);
|
||||
}
|
||||
|
||||
if (!reconnecting) {
|
||||
|
@ -704,10 +770,7 @@
|
|||
url = url + "/reconnect";
|
||||
}
|
||||
if (connection.messageId) {
|
||||
qs += "&messageId=" + window.escape(connection.messageId);
|
||||
}
|
||||
if (groups.length !== 0) {
|
||||
qs += "&groups=" + window.escape(JSON.stringify(groups));
|
||||
qs += "&messageId=" + window.encodeURIComponent(connection.messageId);
|
||||
}
|
||||
}
|
||||
url += "?" + qs;
|
||||
|
@ -723,49 +786,18 @@
|
|||
Disconnect: typeof (minPersistentResponse.D) !== "undefined" ? true : false,
|
||||
TimedOut: typeof (minPersistentResponse.T) !== "undefined" ? true : false,
|
||||
LongPollDelay: minPersistentResponse.L,
|
||||
ResetGroups: minPersistentResponse.R,
|
||||
AddedGroups: minPersistentResponse.G,
|
||||
RemovedGroups: minPersistentResponse.g
|
||||
GroupsToken: minPersistentResponse.G
|
||||
};
|
||||
},
|
||||
|
||||
updateGroups: function (connection, resetGroups, addedGroups, removedGroups) {
|
||||
// Use the keys in connection.groups object as a set of groups.
|
||||
// Prefix all group names with # so we don't conflict with the object's prototype or __proto__.
|
||||
function addGroups(groups) {
|
||||
$.each(groups, function (_, group) {
|
||||
connection.groups['#' + group] = true;
|
||||
});
|
||||
updateGroups: function (connection, groupsToken) {
|
||||
if (groupsToken) {
|
||||
connection.groupsToken = groupsToken;
|
||||
}
|
||||
|
||||
if (resetGroups) {
|
||||
connection.groups = {};
|
||||
addGroups(resetGroups);
|
||||
} else {
|
||||
if (addedGroups) {
|
||||
addGroups(addedGroups);
|
||||
}
|
||||
if (removedGroups) {
|
||||
$.each(removedGroups, function (_, group) {
|
||||
delete connection.groups['# ' + group];
|
||||
});
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
getGroups: function (connection) {
|
||||
var groups = [];
|
||||
if (connection.groups) {
|
||||
$.each(connection.groups, function (group, _) {
|
||||
// Add keys from connection.groups without the # prefix
|
||||
groups.push(group.substr(1));
|
||||
});
|
||||
}
|
||||
return groups;
|
||||
},
|
||||
|
||||
ajaxSend: function (connection, data) {
|
||||
var url = connection.url + "/send" + "?transport=" + connection.transport.name + "&connectionId=" + window.escape(connection.id);
|
||||
var url = connection.url + "/send" + "?transport=" + connection.transport.name + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
url = this.addQs(url, connection);
|
||||
return $.ajax({
|
||||
url: url,
|
||||
|
@ -801,7 +833,7 @@
|
|||
// Async by default unless explicitly overidden
|
||||
async = typeof async === "undefined" ? true : async;
|
||||
|
||||
var url = connection.url + "/abort" + "?transport=" + connection.transport.name + "&connectionId=" + window.escape(connection.id);
|
||||
var url = connection.url + "/abort" + "?transport=" + connection.transport.name + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
url = this.addQs(url, connection);
|
||||
$.ajax({
|
||||
url: url,
|
||||
|
@ -842,7 +874,7 @@
|
|||
return;
|
||||
}
|
||||
|
||||
this.updateGroups(connection, data.ResetGroups, data.AddedGroups, data.RemovedGroups);
|
||||
this.updateGroups(connection, data.GroupsToken);
|
||||
|
||||
if (data.Messages) {
|
||||
$.each(data.Messages, function () {
|
||||
|
@ -961,10 +993,6 @@
|
|||
reconnecting = !onSuccess,
|
||||
$connection = $(connection);
|
||||
|
||||
if (window.MozWebSocket) {
|
||||
window.WebSocket = window.MozWebSocket;
|
||||
}
|
||||
|
||||
if (!window.WebSocket) {
|
||||
onFailed();
|
||||
return;
|
||||
|
@ -1398,8 +1426,7 @@
|
|||
if (connection.frame.stop) {
|
||||
connection.frame.stop();
|
||||
} else {
|
||||
try
|
||||
{
|
||||
try {
|
||||
cw = connection.frame.contentWindow || connection.frame.contentDocument;
|
||||
if (cw.document && cw.document.execCommand) {
|
||||
cw.document.execCommand("Stop");
|
||||
|
@ -1464,139 +1491,151 @@
|
|||
|
||||
reconnectDelay: 3000,
|
||||
|
||||
init: function (connection, onComplete) {
|
||||
/// <summary>Pings the server to ensure availability</summary>
|
||||
/// <param name="connection" type="signalr">Connection associated with the server ping</param>
|
||||
/// <param name="onComplete" type="Function">Callback to call once initialization has completed</param>
|
||||
|
||||
var that = this,
|
||||
pingLoop,
|
||||
// pingFail is used to loop the re-ping behavior. When we fail we want to re-try.
|
||||
pingFail = function (reason) {
|
||||
if (isDisconnecting(connection) === false) {
|
||||
connection.log("SignalR: Server ping failed because '" + reason + "', re-trying ping.");
|
||||
window.setTimeout(pingLoop, that.reconnectDelay);
|
||||
}
|
||||
};
|
||||
|
||||
connection.log("SignalR: Initializing long polling connection with server.");
|
||||
pingLoop = function () {
|
||||
// Ping the server, on successful ping call the onComplete method, otherwise if we fail call the pingFail
|
||||
transportLogic.pingServer(connection, that.name).done(onComplete).fail(pingFail);
|
||||
};
|
||||
|
||||
pingLoop();
|
||||
},
|
||||
|
||||
start: function (connection, onSuccess, onFailed) {
|
||||
/// <summary>Starts the long polling connection</summary>
|
||||
/// <param name="connection" type="signalR">The SignalR connection to start</param>
|
||||
var that = this,
|
||||
initialConnectFired = false;
|
||||
initialConnectedFired = false,
|
||||
fireConnect = function () {
|
||||
if (initialConnectedFired) {
|
||||
return;
|
||||
}
|
||||
initialConnectedFired = true;
|
||||
onSuccess();
|
||||
connection.log("Longpolling connected");
|
||||
};
|
||||
|
||||
if (connection.pollXhr) {
|
||||
connection.log("Polling xhr requests already exists, aborting.");
|
||||
connection.stop();
|
||||
}
|
||||
|
||||
connection.messageId = null;
|
||||
// We start with an initialization procedure which pings the server to verify that it is there.
|
||||
// On scucessful initialization we'll then proceed with starting the transport.
|
||||
that.init(connection, function () {
|
||||
connection.messageId = null;
|
||||
|
||||
window.setTimeout(function () {
|
||||
(function poll(instance, raiseReconnect) {
|
||||
var messageId = instance.messageId,
|
||||
connect = (messageId === null),
|
||||
reconnecting = !connect,
|
||||
url = transportLogic.getUrl(instance, that.name, reconnecting, raiseReconnect),
|
||||
reconnectTimeOut = null,
|
||||
reconnectFired = false,
|
||||
triggerReconnected = function () {
|
||||
// Fire the reconnect event if it hasn't been fired as yet
|
||||
if (reconnectFired === false) {
|
||||
connection.log("Raising the reconnect event");
|
||||
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.reconnecting,
|
||||
signalR.connectionState.connected) === true) {
|
||||
|
||||
$(instance).triggerHandler(events.onReconnect);
|
||||
reconnectFired = true;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
if (reconnecting === true && raiseReconnect === true &&
|
||||
!transportLogic.ensureReconnectingState(connection)) {
|
||||
return;
|
||||
}
|
||||
|
||||
connection.log("Attempting to connect to '" + url + "' using longPolling.");
|
||||
instance.pollXhr = $.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (minData) {
|
||||
var delay = 0,
|
||||
timedOutReceived = false,
|
||||
data;
|
||||
|
||||
if (minData) {
|
||||
data = transportLogic.maximizePersistentResponse(minData);
|
||||
}
|
||||
|
||||
if (initialConnectFired === false) {
|
||||
onSuccess();
|
||||
initialConnectFired = true;
|
||||
}
|
||||
|
||||
if (raiseReconnect === true) {
|
||||
triggerReconnected();
|
||||
}
|
||||
|
||||
transportLogic.processMessages(instance, minData);
|
||||
if (data &&
|
||||
$.type(data.LongPollDelay) === "number") {
|
||||
delay = data.LongPollDelay;
|
||||
}
|
||||
|
||||
if (data && data.TimedOut) {
|
||||
timedOutReceived = data.TimedOut;
|
||||
}
|
||||
|
||||
if (data && data.Disconnect) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (delay > 0) {
|
||||
window.setTimeout(function () {
|
||||
poll(instance, timedOutReceived);
|
||||
}, delay);
|
||||
} else {
|
||||
poll(instance, timedOutReceived);
|
||||
}
|
||||
},
|
||||
|
||||
error: function (data, textStatus) {
|
||||
if (textStatus === "abort") {
|
||||
connection.log("Aborted xhr requst.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (connection.state !== signalR.connectionState.reconnecting) {
|
||||
connection.log("An error occurred using longPolling. Status = " + textStatus + ". " + data.responseText);
|
||||
$(instance).triggerHandler(events.onError, [data.responseText]);
|
||||
}
|
||||
|
||||
// If the request failed then we clear the timeout so that the
|
||||
// reconnect event doesn't get fired
|
||||
window.clearTimeout(reconnectTimeOut);
|
||||
|
||||
window.setTimeout(function () {
|
||||
if (isDisconnecting(instance) === false) {
|
||||
poll(instance, true);
|
||||
}
|
||||
}, connection.reconnectDelay);
|
||||
}
|
||||
});
|
||||
|
||||
if (raiseReconnect === true) {
|
||||
reconnectTimeOut = window.setTimeout(triggerReconnected, that.reconnectDelay);
|
||||
}
|
||||
|
||||
}(connection));
|
||||
|
||||
// Now connected
|
||||
// There's no good way know when the long poll has actually started so
|
||||
// we assume it only takes around 150ms (max) to start the connection
|
||||
window.setTimeout(function () {
|
||||
if (initialConnectFired === false) {
|
||||
onSuccess();
|
||||
initialConnectFired = true;
|
||||
}
|
||||
}, 150);
|
||||
(function poll(instance, raiseReconnect) {
|
||||
var messageId = instance.messageId,
|
||||
connect = (messageId === null),
|
||||
reconnecting = !connect,
|
||||
url = transportLogic.getUrl(instance, that.name, reconnecting, raiseReconnect);
|
||||
|
||||
}, 250); // Have to delay initial poll so Chrome doesn't show loader spinner in tab
|
||||
// If we've disconnected during the time we've tried to re-instantiate the poll then stop.
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
connection.log("Attempting to connect to '" + url + "' using longPolling.");
|
||||
instance.pollXhr = $.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (minData) {
|
||||
var delay = 0,
|
||||
data;
|
||||
|
||||
fireConnect();
|
||||
|
||||
if (minData) {
|
||||
data = transportLogic.maximizePersistentResponse(minData);
|
||||
}
|
||||
|
||||
transportLogic.processMessages(instance, minData);
|
||||
|
||||
if (data &&
|
||||
$.type(data.LongPollDelay) === "number") {
|
||||
delay = data.LongPollDelay;
|
||||
}
|
||||
|
||||
if (data && data.Disconnect) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
// We never want to pass a raiseReconnect flag after a successful poll. This is handled via the error function
|
||||
if (delay > 0) {
|
||||
window.setTimeout(function () {
|
||||
poll(instance, false);
|
||||
}, delay);
|
||||
} else {
|
||||
poll(instance, false);
|
||||
}
|
||||
},
|
||||
|
||||
error: function (data, textStatus) {
|
||||
if (textStatus === "abort") {
|
||||
connection.log("Aborted xhr requst.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (connection.state !== signalR.connectionState.reconnecting) {
|
||||
connection.log("An error occurred using longPolling. Status = " + textStatus + ". " + data.responseText);
|
||||
$(instance).triggerHandler(events.onError, [data.responseText]);
|
||||
}
|
||||
|
||||
// Transition into the reconnecting state
|
||||
transportLogic.ensureReconnectingState(instance);
|
||||
|
||||
// If we've errored out we need to verify that the server is still there, so re-start initialization process
|
||||
// This will ping the server until it successfully gets a response.
|
||||
that.init(instance, function () {
|
||||
// Call poll with the raiseReconnect flag as true
|
||||
poll(instance, true);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
// This will only ever pass after an error has occured via the poll ajax procedure.
|
||||
if (reconnecting && raiseReconnect === true) {
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.reconnecting,
|
||||
signalR.connectionState.connected) === true) {
|
||||
// Successfully reconnected!
|
||||
connection.log("Raising the reconnect event");
|
||||
$(instance).triggerHandler(events.onReconnect);
|
||||
}
|
||||
}
|
||||
}(connection));
|
||||
|
||||
// Set an arbitrary timeout to trigger onSuccess, this will alot for enough time on the server to wire up the connection.
|
||||
// Will be fixed by #1189 and this code can be modified to not be a timeout
|
||||
window.setTimeout(function () {
|
||||
// Trigger the onSuccess() method because we've now instantiated a connection
|
||||
fireConnect();
|
||||
}, 250);
|
||||
}, 250); // Have to delay initial poll so Chrome doesn't show loader spinner in tab
|
||||
});
|
||||
},
|
||||
|
||||
lostConnection: function (connection) {
|
Различия файлов скрыты, потому что одна или несколько строк слишком длинны
|
@ -19,7 +19,7 @@
|
|||
</section>
|
||||
}
|
||||
@section scripts {
|
||||
<script src="~/Scripts/jquery.signalR-1.0.0-rc1.min.js"></script>
|
||||
<script src="~/Scripts/jquery.signalR-1.0.0.min.js"></script>
|
||||
<script src="~/signalR/hubs"></script>
|
||||
<script>
|
||||
$(function () {
|
||||
|
|
|
@ -14,11 +14,11 @@
|
|||
<package id="Microsoft.AspNet.Mvc" version="4.0.20710.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.Mvc.FixedDisplayModes" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.Razor" version="2.0.20715.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.JS" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Owin" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.SystemWeb" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.JS" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Owin" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.SystemWeb" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.Web.Optimization" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.WebApi" version="4.0.20710.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.WebApi.Client" version="4.0.20710.0" targetFramework="net45" />
|
||||
|
@ -35,7 +35,7 @@
|
|||
<package id="Microsoft.jQuery.Unobtrusive.Ajax" version="2.0.20710.0" targetFramework="net45" />
|
||||
<package id="Microsoft.jQuery.Unobtrusive.Validation" version="2.0.20710.0" targetFramework="net45" />
|
||||
<package id="Microsoft.Net.Http" version="2.0.20710.0" targetFramework="net45" />
|
||||
<package id="Microsoft.Owin.Host.SystemWeb" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.Owin.Host.SystemWeb" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.Web.Infrastructure" version="1.0.0.0" targetFramework="net45" />
|
||||
<package id="Modernizr" version="2.5.3" targetFramework="net45" />
|
||||
<package id="Newtonsoft.Json" version="4.5.11" targetFramework="net45" />
|
||||
|
|
|
@ -34,11 +34,13 @@
|
|||
<WarningLevel>4</WarningLevel>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Core">
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.0-rc1\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Core, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.0\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Owin">
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Owin.1.0.0-rc1\lib\net45\Microsoft.AspNet.SignalR.Owin.dll</HintPath>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Owin, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Owin.1.0.0\lib\net45\Microsoft.AspNet.SignalR.Owin.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.Owin.Host.HttpListener">
|
||||
<HintPath>..\packages\Microsoft.Owin.Host.HttpListener.0.18.0-alpha\lib\net45\Microsoft.Owin.Host.HttpListener.dll</HintPath>
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
using Microsoft.AspNet.SignalR.Hubs;
|
||||
using Microsoft.AspNet.SignalR;
|
||||
|
||||
namespace BasicChat.SelfHost.Hubs
|
||||
{
|
||||
|
|
|
@ -7,7 +7,7 @@ namespace BasicChat.SelfHost
|
|||
// This method name is important
|
||||
public void Configuration(IAppBuilder app)
|
||||
{
|
||||
app.MapHubs("/signalr");
|
||||
app.MapHubs();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Owin" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Owin" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.Owin.Host.HttpListener" version="0.18.0-alpha" targetFramework="net45" />
|
||||
<package id="Microsoft.Owin.Hosting" version="0.18.0-alpha" targetFramework="net45" />
|
||||
<package id="Newtonsoft.Json" version="4.5.11" targetFramework="net45" />
|
||||
|
|
|
@ -42,17 +42,20 @@
|
|||
<ItemGroup>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Core, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.0-rc1\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.0\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Owin">
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Owin.1.0.0-rc1\lib\net45\Microsoft.AspNet.SignalR.Owin.dll</HintPath>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Owin, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Owin.1.0.0\lib\net45\Microsoft.AspNet.SignalR.Owin.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.SystemWeb">
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.SystemWeb.1.0.0-rc1\lib\net45\Microsoft.AspNet.SignalR.SystemWeb.dll</HintPath>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.SystemWeb, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.SystemWeb.1.0.0\lib\net45\Microsoft.AspNet.SignalR.SystemWeb.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="Microsoft.Owin.Host.SystemWeb">
|
||||
<HintPath>..\packages\Microsoft.Owin.Host.SystemWeb.1.0.0-rc1\lib\net45\Microsoft.Owin.Host.SystemWeb.dll</HintPath>
|
||||
<Reference Include="Microsoft.Owin.Host.SystemWeb, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.Owin.Host.SystemWeb.1.0.0\lib\net45\Microsoft.Owin.Host.SystemWeb.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.Web.Infrastructure, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<Private>True</Private>
|
||||
|
@ -87,8 +90,9 @@
|
|||
<None Include="Scripts\jquery-1.8.3.intellisense.js" />
|
||||
<Content Include="Scripts\jquery-1.8.3.js" />
|
||||
<Content Include="Scripts\jquery-1.8.3.min.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0-rc1.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0-rc1.min.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0.js" />
|
||||
<Content Include="Scripts\jquery.signalR-1.0.0.min.js" />
|
||||
<Content Include="Web.config" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Web;
|
||||
using Microsoft.AspNet.SignalR.Hubs;
|
||||
using Microsoft.AspNet.SignalR;
|
||||
|
||||
namespace BasicChat
|
||||
{
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNet.SignalR.Hubs;
|
||||
using Microsoft.AspNet.SignalR;
|
||||
|
||||
namespace BasicChat
|
||||
{
|
||||
|
|
|
@ -57,21 +57,6 @@
|
|||
}
|
||||
},
|
||||
|
||||
isCrossDomain = function (url) {
|
||||
var link;
|
||||
|
||||
url = $.trim(url);
|
||||
if (url.indexOf("http") !== 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Create an anchor tag.
|
||||
link = window.document.createElement("a");
|
||||
link.href = url;
|
||||
|
||||
return link.protocol + link.host !== window.location.protocol + window.location.host;
|
||||
},
|
||||
|
||||
changeState = function (connection, expectedState, newState) {
|
||||
if (expectedState === connection.state) {
|
||||
connection.state = newState;
|
||||
|
@ -89,22 +74,30 @@
|
|||
|
||||
configureStopReconnectingTimeout = function (connection) {
|
||||
var stopReconnectingTimeout,
|
||||
onReconnectTimeout;
|
||||
|
||||
// Check if this connection has already been configured to stop reconnecting after a specified timeout.
|
||||
// Without this check if a connection is stopped then started events will be bound multiple times.
|
||||
if (!connection._.configuredStopReconnectingTimeout) {
|
||||
onReconnectTimeout = function (connection) {
|
||||
connection.log("Couldn't reconnect within the configured timeout (" + connection.disconnectTimeout + "ms), disconnecting.");
|
||||
connection.stop(/* async */ false, /* notifyServer */ false);
|
||||
};
|
||||
|
||||
connection.reconnecting(function () {
|
||||
var connection = this;
|
||||
stopReconnectingTimeout = window.setTimeout(function () { onReconnectTimeout(connection); }, connection.disconnectTimeout);
|
||||
});
|
||||
connection.reconnecting(function () {
|
||||
var connection = this;
|
||||
stopReconnectingTimeout = window.setTimeout(function () { onReconnectTimeout(connection); }, connection.disconnectTimeout);
|
||||
});
|
||||
|
||||
connection.stateChanged(function (data) {
|
||||
if (data.oldState === signalR.connectionState.reconnecting) {
|
||||
// Clear the pending reconnect timeout check
|
||||
window.clearTimeout(stopReconnectingTimeout);
|
||||
}
|
||||
});
|
||||
connection.stateChanged(function (data) {
|
||||
if (data.oldState === signalR.connectionState.reconnecting) {
|
||||
// Clear the pending reconnect timeout check
|
||||
window.clearTimeout(stopReconnectingTimeout);
|
||||
}
|
||||
});
|
||||
|
||||
connection._.configuredStopReconnectingTimeout = true;
|
||||
}
|
||||
};
|
||||
|
||||
signalR = function (url, qs, logging) {
|
||||
|
@ -173,14 +166,57 @@
|
|||
return requestedTransport;
|
||||
}
|
||||
|
||||
function getDefaultPort(protocol) {
|
||||
if(protocol === "http:") {
|
||||
return 80;
|
||||
}
|
||||
else if (protocol === "https:") {
|
||||
return 443;
|
||||
}
|
||||
}
|
||||
|
||||
function addDefaultPort(protocol, url) {
|
||||
// Remove ports from url. We have to check if there's a / or end of line
|
||||
// following the port in order to avoid removing ports such as 8080.
|
||||
if(url.match(/:\d+$/)) {
|
||||
return url;
|
||||
} else {
|
||||
return url + ":" + getDefaultPort(protocol);
|
||||
}
|
||||
}
|
||||
|
||||
signalR.fn = signalR.prototype = {
|
||||
init: function (url, qs, logging) {
|
||||
this.url = url;
|
||||
this.qs = qs;
|
||||
this._ = {};
|
||||
if (typeof (logging) === "boolean") {
|
||||
this.logging = logging;
|
||||
}
|
||||
},
|
||||
|
||||
isCrossDomain: function (url, against) {
|
||||
/// <summary>Checks if url is cross domain</summary>
|
||||
/// <param name="url" type="String">The base URL</param>
|
||||
/// <param name="against" type="Object">
|
||||
/// An optional argument to compare the URL against, if not specified it will be set to window.location.
|
||||
/// If specified it must contain a protocol and a host property.
|
||||
/// </param>
|
||||
var link;
|
||||
|
||||
url = $.trim(url);
|
||||
if (url.indexOf("http") !== 0) {
|
||||
return false;
|
||||
}
|
||||
configureStopReconnectingTimeout(this);
|
||||
|
||||
against = against || window.location;
|
||||
|
||||
// Create an anchor tag.
|
||||
link = window.document.createElement("a");
|
||||
link.href = url;
|
||||
|
||||
// When checking for cross domain we have to special case port 80 because the window.location will remove the
|
||||
return link.protocol + addDefaultPort(link.protocol, link.host) !== against.protocol + addDefaultPort(against.protocol, against.host);
|
||||
},
|
||||
|
||||
ajaxDataType: "json",
|
||||
|
@ -189,16 +225,12 @@
|
|||
|
||||
state: signalR.connectionState.disconnected,
|
||||
|
||||
groups: {},
|
||||
|
||||
keepAliveData: {},
|
||||
|
||||
reconnectDelay: 2000,
|
||||
|
||||
disconnectTimeout: 40000, // This should be set by the server in response to the negotiate request (40s default)
|
||||
|
||||
keepAliveTimeoutCount: 2,
|
||||
|
||||
keepAliveWarnAt: 2 / 3, // Warn user of slow connection if we breach the X% mark of the keep alive timeout
|
||||
|
||||
start: function (options, callback) {
|
||||
|
@ -242,6 +274,8 @@
|
|||
return deferred.promise();
|
||||
}
|
||||
|
||||
configureStopReconnectingTimeout(connection);
|
||||
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.disconnected,
|
||||
signalR.connectionState.connecting) === false) {
|
||||
|
@ -274,7 +308,7 @@
|
|||
config.transport = "longPolling";
|
||||
}
|
||||
|
||||
if (isCrossDomain(connection.url)) {
|
||||
if (this.isCrossDomain(connection.url)) {
|
||||
connection.log("Auto detected cross domain url.");
|
||||
|
||||
if (config.transport === "auto") {
|
||||
|
@ -368,6 +402,7 @@
|
|||
|
||||
connection.appRelativeUrl = res.Url;
|
||||
connection.id = res.ConnectionId;
|
||||
connection.token = res.ConnectionToken;
|
||||
connection.webSocketServerUrl = res.WebSocketServerUrl;
|
||||
|
||||
// Once the server has labeled the PersistentConnection as Disconnected, we should stop attempting to reconnect
|
||||
|
@ -376,15 +411,12 @@
|
|||
|
||||
|
||||
// If we have a keep alive
|
||||
if (res.KeepAlive) {
|
||||
// Convert to milliseconds
|
||||
res.KeepAlive *= 1000;
|
||||
|
||||
if (res.KeepAliveTimeout) {
|
||||
// Register the keep alive data as activated
|
||||
keepAliveData.activated = true;
|
||||
|
||||
// Timeout to designate when to force the connection into reconnecting
|
||||
keepAliveData.timeout = res.KeepAlive * connection.keepAliveTimeoutCount;
|
||||
// Timeout to designate when to force the connection into reconnecting converted to milliseconds
|
||||
keepAliveData.timeout = res.KeepAliveTimeout * 1000;
|
||||
|
||||
// Timeout to designate when to warn the developer that the connection may be dead or is hanging.
|
||||
keepAliveData.timeoutWarning = keepAliveData.timeout * connection.keepAliveWarnAt;
|
||||
|
@ -396,7 +428,7 @@
|
|||
keepAliveData.activated = false;
|
||||
}
|
||||
|
||||
if (!res.ProtocolVersion || res.ProtocolVersion !== "1.1") {
|
||||
if (!res.ProtocolVersion || res.ProtocolVersion !== "1.2") {
|
||||
$(connection).triggerHandler(events.onError, "SignalR: Incompatible protocol version.");
|
||||
deferred.reject("SignalR: Incompatible protocol version.");
|
||||
return;
|
||||
|
@ -576,7 +608,7 @@
|
|||
$(connection).triggerHandler(events.onDisconnect);
|
||||
|
||||
delete connection.messageId;
|
||||
delete connection.groups;
|
||||
delete connection.groupsToken;
|
||||
|
||||
// Remove the ID and the deferral on stop, this is to ensure that if a connection is restarted it takes on a new id/deferral.
|
||||
delete connection.id;
|
||||
|
@ -670,6 +702,37 @@
|
|||
}
|
||||
|
||||
signalR.transports._logic = {
|
||||
pingServer: function (connection, transport) {
|
||||
/// <summary>Pings the server</summary>
|
||||
/// <param name="connection" type="signalr">Connection associated with the server ping</param>
|
||||
/// <returns type="signalR" />
|
||||
var baseUrl = transport === "webSockets" ? "" : connection.baseUrl,
|
||||
url = baseUrl + connection.appRelativeUrl + "/ping",
|
||||
deferral = $.Deferred();
|
||||
|
||||
$.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
data: {},
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (data) {
|
||||
if (data.Response === "pong") {
|
||||
deferral.resolve();
|
||||
}
|
||||
else {
|
||||
deferral.reject("SignalR: Invalid ping response when pinging server: " + (data.responseText || data.statusText));
|
||||
}
|
||||
},
|
||||
error: function (data) {
|
||||
deferral.reject("SignalR: Error pinging server: " + (data.responseText || data.statusText));
|
||||
}
|
||||
});
|
||||
|
||||
return deferral.promise();
|
||||
},
|
||||
|
||||
addQs: function (url, connection) {
|
||||
if (!connection.qs) {
|
||||
return url;
|
||||
|
@ -683,18 +746,21 @@
|
|||
return url + "&" + connection.qs;
|
||||
}
|
||||
|
||||
return url + "&" + window.escape(connection.qs.toString());
|
||||
return url + "&" + window.encodeURIComponent(connection.qs.toString());
|
||||
},
|
||||
|
||||
getUrl: function (connection, transport, reconnecting, appendReconnectUrl) {
|
||||
/// <summary>Gets the url for making a GET based connect request</summary>
|
||||
var baseUrl = transport === "webSockets" ? "" : connection.baseUrl,
|
||||
url = baseUrl + connection.appRelativeUrl,
|
||||
qs = "transport=" + transport + "&connectionId=" + window.escape(connection.id),
|
||||
groups = this.getGroups(connection);
|
||||
qs = "transport=" + transport + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
|
||||
if (connection.data) {
|
||||
qs += "&connectionData=" + window.escape(connection.data);
|
||||
qs += "&connectionData=" + window.encodeURIComponent(connection.data);
|
||||
}
|
||||
|
||||
if (connection.groupsToken) {
|
||||
qs += "&groupsToken=" + window.encodeURIComponent(connection.groupsToken);
|
||||
}
|
||||
|
||||
if (!reconnecting) {
|
||||
|
@ -704,10 +770,7 @@
|
|||
url = url + "/reconnect";
|
||||
}
|
||||
if (connection.messageId) {
|
||||
qs += "&messageId=" + window.escape(connection.messageId);
|
||||
}
|
||||
if (groups.length !== 0) {
|
||||
qs += "&groups=" + window.escape(JSON.stringify(groups));
|
||||
qs += "&messageId=" + window.encodeURIComponent(connection.messageId);
|
||||
}
|
||||
}
|
||||
url += "?" + qs;
|
||||
|
@ -723,49 +786,18 @@
|
|||
Disconnect: typeof (minPersistentResponse.D) !== "undefined" ? true : false,
|
||||
TimedOut: typeof (minPersistentResponse.T) !== "undefined" ? true : false,
|
||||
LongPollDelay: minPersistentResponse.L,
|
||||
ResetGroups: minPersistentResponse.R,
|
||||
AddedGroups: minPersistentResponse.G,
|
||||
RemovedGroups: minPersistentResponse.g
|
||||
GroupsToken: minPersistentResponse.G
|
||||
};
|
||||
},
|
||||
|
||||
updateGroups: function (connection, resetGroups, addedGroups, removedGroups) {
|
||||
// Use the keys in connection.groups object as a set of groups.
|
||||
// Prefix all group names with # so we don't conflict with the object's prototype or __proto__.
|
||||
function addGroups(groups) {
|
||||
$.each(groups, function (_, group) {
|
||||
connection.groups['#' + group] = true;
|
||||
});
|
||||
updateGroups: function (connection, groupsToken) {
|
||||
if (groupsToken) {
|
||||
connection.groupsToken = groupsToken;
|
||||
}
|
||||
|
||||
if (resetGroups) {
|
||||
connection.groups = {};
|
||||
addGroups(resetGroups);
|
||||
} else {
|
||||
if (addedGroups) {
|
||||
addGroups(addedGroups);
|
||||
}
|
||||
if (removedGroups) {
|
||||
$.each(removedGroups, function (_, group) {
|
||||
delete connection.groups['# ' + group];
|
||||
});
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
getGroups: function (connection) {
|
||||
var groups = [];
|
||||
if (connection.groups) {
|
||||
$.each(connection.groups, function (group, _) {
|
||||
// Add keys from connection.groups without the # prefix
|
||||
groups.push(group.substr(1));
|
||||
});
|
||||
}
|
||||
return groups;
|
||||
},
|
||||
|
||||
ajaxSend: function (connection, data) {
|
||||
var url = connection.url + "/send" + "?transport=" + connection.transport.name + "&connectionId=" + window.escape(connection.id);
|
||||
var url = connection.url + "/send" + "?transport=" + connection.transport.name + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
url = this.addQs(url, connection);
|
||||
return $.ajax({
|
||||
url: url,
|
||||
|
@ -801,7 +833,7 @@
|
|||
// Async by default unless explicitly overidden
|
||||
async = typeof async === "undefined" ? true : async;
|
||||
|
||||
var url = connection.url + "/abort" + "?transport=" + connection.transport.name + "&connectionId=" + window.escape(connection.id);
|
||||
var url = connection.url + "/abort" + "?transport=" + connection.transport.name + "&connectionToken=" + window.encodeURIComponent(connection.token);
|
||||
url = this.addQs(url, connection);
|
||||
$.ajax({
|
||||
url: url,
|
||||
|
@ -842,7 +874,7 @@
|
|||
return;
|
||||
}
|
||||
|
||||
this.updateGroups(connection, data.ResetGroups, data.AddedGroups, data.RemovedGroups);
|
||||
this.updateGroups(connection, data.GroupsToken);
|
||||
|
||||
if (data.Messages) {
|
||||
$.each(data.Messages, function () {
|
||||
|
@ -961,10 +993,6 @@
|
|||
reconnecting = !onSuccess,
|
||||
$connection = $(connection);
|
||||
|
||||
if (window.MozWebSocket) {
|
||||
window.WebSocket = window.MozWebSocket;
|
||||
}
|
||||
|
||||
if (!window.WebSocket) {
|
||||
onFailed();
|
||||
return;
|
||||
|
@ -1398,8 +1426,7 @@
|
|||
if (connection.frame.stop) {
|
||||
connection.frame.stop();
|
||||
} else {
|
||||
try
|
||||
{
|
||||
try {
|
||||
cw = connection.frame.contentWindow || connection.frame.contentDocument;
|
||||
if (cw.document && cw.document.execCommand) {
|
||||
cw.document.execCommand("Stop");
|
||||
|
@ -1464,139 +1491,151 @@
|
|||
|
||||
reconnectDelay: 3000,
|
||||
|
||||
init: function (connection, onComplete) {
|
||||
/// <summary>Pings the server to ensure availability</summary>
|
||||
/// <param name="connection" type="signalr">Connection associated with the server ping</param>
|
||||
/// <param name="onComplete" type="Function">Callback to call once initialization has completed</param>
|
||||
|
||||
var that = this,
|
||||
pingLoop,
|
||||
// pingFail is used to loop the re-ping behavior. When we fail we want to re-try.
|
||||
pingFail = function (reason) {
|
||||
if (isDisconnecting(connection) === false) {
|
||||
connection.log("SignalR: Server ping failed because '" + reason + "', re-trying ping.");
|
||||
window.setTimeout(pingLoop, that.reconnectDelay);
|
||||
}
|
||||
};
|
||||
|
||||
connection.log("SignalR: Initializing long polling connection with server.");
|
||||
pingLoop = function () {
|
||||
// Ping the server, on successful ping call the onComplete method, otherwise if we fail call the pingFail
|
||||
transportLogic.pingServer(connection, that.name).done(onComplete).fail(pingFail);
|
||||
};
|
||||
|
||||
pingLoop();
|
||||
},
|
||||
|
||||
start: function (connection, onSuccess, onFailed) {
|
||||
/// <summary>Starts the long polling connection</summary>
|
||||
/// <param name="connection" type="signalR">The SignalR connection to start</param>
|
||||
var that = this,
|
||||
initialConnectFired = false;
|
||||
initialConnectedFired = false,
|
||||
fireConnect = function () {
|
||||
if (initialConnectedFired) {
|
||||
return;
|
||||
}
|
||||
initialConnectedFired = true;
|
||||
onSuccess();
|
||||
connection.log("Longpolling connected");
|
||||
};
|
||||
|
||||
if (connection.pollXhr) {
|
||||
connection.log("Polling xhr requests already exists, aborting.");
|
||||
connection.stop();
|
||||
}
|
||||
|
||||
connection.messageId = null;
|
||||
// We start with an initialization procedure which pings the server to verify that it is there.
|
||||
// On scucessful initialization we'll then proceed with starting the transport.
|
||||
that.init(connection, function () {
|
||||
connection.messageId = null;
|
||||
|
||||
window.setTimeout(function () {
|
||||
(function poll(instance, raiseReconnect) {
|
||||
var messageId = instance.messageId,
|
||||
connect = (messageId === null),
|
||||
reconnecting = !connect,
|
||||
url = transportLogic.getUrl(instance, that.name, reconnecting, raiseReconnect),
|
||||
reconnectTimeOut = null,
|
||||
reconnectFired = false,
|
||||
triggerReconnected = function () {
|
||||
// Fire the reconnect event if it hasn't been fired as yet
|
||||
if (reconnectFired === false) {
|
||||
connection.log("Raising the reconnect event");
|
||||
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.reconnecting,
|
||||
signalR.connectionState.connected) === true) {
|
||||
|
||||
$(instance).triggerHandler(events.onReconnect);
|
||||
reconnectFired = true;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
if (reconnecting === true && raiseReconnect === true &&
|
||||
!transportLogic.ensureReconnectingState(connection)) {
|
||||
return;
|
||||
}
|
||||
|
||||
connection.log("Attempting to connect to '" + url + "' using longPolling.");
|
||||
instance.pollXhr = $.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (minData) {
|
||||
var delay = 0,
|
||||
timedOutReceived = false,
|
||||
data;
|
||||
|
||||
if (minData) {
|
||||
data = transportLogic.maximizePersistentResponse(minData);
|
||||
}
|
||||
|
||||
if (initialConnectFired === false) {
|
||||
onSuccess();
|
||||
initialConnectFired = true;
|
||||
}
|
||||
|
||||
if (raiseReconnect === true) {
|
||||
triggerReconnected();
|
||||
}
|
||||
|
||||
transportLogic.processMessages(instance, minData);
|
||||
if (data &&
|
||||
$.type(data.LongPollDelay) === "number") {
|
||||
delay = data.LongPollDelay;
|
||||
}
|
||||
|
||||
if (data && data.TimedOut) {
|
||||
timedOutReceived = data.TimedOut;
|
||||
}
|
||||
|
||||
if (data && data.Disconnect) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (delay > 0) {
|
||||
window.setTimeout(function () {
|
||||
poll(instance, timedOutReceived);
|
||||
}, delay);
|
||||
} else {
|
||||
poll(instance, timedOutReceived);
|
||||
}
|
||||
},
|
||||
|
||||
error: function (data, textStatus) {
|
||||
if (textStatus === "abort") {
|
||||
connection.log("Aborted xhr requst.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (connection.state !== signalR.connectionState.reconnecting) {
|
||||
connection.log("An error occurred using longPolling. Status = " + textStatus + ". " + data.responseText);
|
||||
$(instance).triggerHandler(events.onError, [data.responseText]);
|
||||
}
|
||||
|
||||
// If the request failed then we clear the timeout so that the
|
||||
// reconnect event doesn't get fired
|
||||
window.clearTimeout(reconnectTimeOut);
|
||||
|
||||
window.setTimeout(function () {
|
||||
if (isDisconnecting(instance) === false) {
|
||||
poll(instance, true);
|
||||
}
|
||||
}, connection.reconnectDelay);
|
||||
}
|
||||
});
|
||||
|
||||
if (raiseReconnect === true) {
|
||||
reconnectTimeOut = window.setTimeout(triggerReconnected, that.reconnectDelay);
|
||||
}
|
||||
|
||||
}(connection));
|
||||
|
||||
// Now connected
|
||||
// There's no good way know when the long poll has actually started so
|
||||
// we assume it only takes around 150ms (max) to start the connection
|
||||
window.setTimeout(function () {
|
||||
if (initialConnectFired === false) {
|
||||
onSuccess();
|
||||
initialConnectFired = true;
|
||||
}
|
||||
}, 150);
|
||||
(function poll(instance, raiseReconnect) {
|
||||
var messageId = instance.messageId,
|
||||
connect = (messageId === null),
|
||||
reconnecting = !connect,
|
||||
url = transportLogic.getUrl(instance, that.name, reconnecting, raiseReconnect);
|
||||
|
||||
}, 250); // Have to delay initial poll so Chrome doesn't show loader spinner in tab
|
||||
// If we've disconnected during the time we've tried to re-instantiate the poll then stop.
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
connection.log("Attempting to connect to '" + url + "' using longPolling.");
|
||||
instance.pollXhr = $.ajax({
|
||||
url: url,
|
||||
global: false,
|
||||
cache: false,
|
||||
type: "GET",
|
||||
dataType: connection.ajaxDataType,
|
||||
success: function (minData) {
|
||||
var delay = 0,
|
||||
data;
|
||||
|
||||
fireConnect();
|
||||
|
||||
if (minData) {
|
||||
data = transportLogic.maximizePersistentResponse(minData);
|
||||
}
|
||||
|
||||
transportLogic.processMessages(instance, minData);
|
||||
|
||||
if (data &&
|
||||
$.type(data.LongPollDelay) === "number") {
|
||||
delay = data.LongPollDelay;
|
||||
}
|
||||
|
||||
if (data && data.Disconnect) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isDisconnecting(instance) === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
// We never want to pass a raiseReconnect flag after a successful poll. This is handled via the error function
|
||||
if (delay > 0) {
|
||||
window.setTimeout(function () {
|
||||
poll(instance, false);
|
||||
}, delay);
|
||||
} else {
|
||||
poll(instance, false);
|
||||
}
|
||||
},
|
||||
|
||||
error: function (data, textStatus) {
|
||||
if (textStatus === "abort") {
|
||||
connection.log("Aborted xhr requst.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (connection.state !== signalR.connectionState.reconnecting) {
|
||||
connection.log("An error occurred using longPolling. Status = " + textStatus + ". " + data.responseText);
|
||||
$(instance).triggerHandler(events.onError, [data.responseText]);
|
||||
}
|
||||
|
||||
// Transition into the reconnecting state
|
||||
transportLogic.ensureReconnectingState(instance);
|
||||
|
||||
// If we've errored out we need to verify that the server is still there, so re-start initialization process
|
||||
// This will ping the server until it successfully gets a response.
|
||||
that.init(instance, function () {
|
||||
// Call poll with the raiseReconnect flag as true
|
||||
poll(instance, true);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
// This will only ever pass after an error has occured via the poll ajax procedure.
|
||||
if (reconnecting && raiseReconnect === true) {
|
||||
if (changeState(connection,
|
||||
signalR.connectionState.reconnecting,
|
||||
signalR.connectionState.connected) === true) {
|
||||
// Successfully reconnected!
|
||||
connection.log("Raising the reconnect event");
|
||||
$(instance).triggerHandler(events.onReconnect);
|
||||
}
|
||||
}
|
||||
}(connection));
|
||||
|
||||
// Set an arbitrary timeout to trigger onSuccess, this will alot for enough time on the server to wire up the connection.
|
||||
// Will be fixed by #1189 and this code can be modified to not be a timeout
|
||||
window.setTimeout(function () {
|
||||
// Trigger the onSuccess() method because we've now instantiated a connection
|
||||
fireConnect();
|
||||
}, 250);
|
||||
}, 250); // Have to delay initial poll so Chrome doesn't show loader spinner in tab
|
||||
});
|
||||
},
|
||||
|
||||
lostConnection: function (connection) {
|
Различия файлов скрыты, потому что одна или несколько строк слишком длинны
|
@ -9,7 +9,7 @@
|
|||
<ul id="message">
|
||||
</ul>
|
||||
<script src="Scripts/jquery-1.8.3.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0-rc1.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0.min.js"></script>
|
||||
<script src="signalR/hubs"></script>
|
||||
<script>
|
||||
$(function () {
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<ul id="message">
|
||||
</ul>
|
||||
<script src="Scripts/jquery-1.8.3.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0-rc1.min.js"></script>
|
||||
<script src="Scripts/jquery.signalR-1.0.0.min.js"></script>
|
||||
<script src="signalR/hubs"></script>
|
||||
<script>
|
||||
$(function () {
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="jQuery" version="1.8.3" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.JS" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Owin" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.SystemWeb" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.Owin.Host.SystemWeb" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.JS" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Owin" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.SystemWeb" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.Owin.Host.SystemWeb" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Microsoft.Web.Infrastructure" version="1.0.0.0" targetFramework="net45" />
|
||||
<package id="Newtonsoft.Json" version="4.5.11" targetFramework="net45" />
|
||||
<package id="Owin" version="1.0" targetFramework="net45" />
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
<ItemGroup>
|
||||
<Reference Include="Microsoft.AspNet.SignalR.Client, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Client.1.0.0-rc1\lib\net40\Microsoft.AspNet.SignalR.Client.dll</HintPath>
|
||||
<HintPath>..\packages\Microsoft.AspNet.SignalR.Client.1.0.0\lib\net45\Microsoft.AspNet.SignalR.Client.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Newtonsoft.Json">
|
||||
<HintPath>..\packages\Newtonsoft.Json.4.5.11\lib\net40\Newtonsoft.Json.dll</HintPath>
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="Microsoft.AspNet.SignalR.Client" version="1.0.0-rc1" targetFramework="net45" />
|
||||
<package id="Microsoft.AspNet.SignalR.Client" version="1.0.0" targetFramework="net45" />
|
||||
<package id="Newtonsoft.Json" version="4.5.11" targetFramework="net45" />
|
||||
</packages>
|
Загрузка…
Ссылка в новой задаче