The online document editor uses a WebSocket connection to synchronize the document server-side. To initialize the editor, a connection is routed to the endpoint TXWebSocket that creates the WebSocketHandler. The WebSocketHandler is coordinating the traffic between the client and the backend service.

The WebSocket traffic itself uses the same security layer like the underlying HTTP (or HTTPS) protocol. The WebSocketHandler address is defined through the WebSocketURL property in the HtmlHelper. For example:

@Html.TXTextControl().TextControl(settings => {
settings.WebSocketURL = "wss://localhost:1151/api/TXWebSocket";
}).Render()
view raw test.cshtml hosted with ❤ by GitHub

Like other requests to controller or api controller methods, these requests should be secured by adding an authentication filter to this endpoint.

This very simple ActionFilterAttribute filter compares an access token passed in the query string with a hardcoded token. In real-worlds applications, this access token would be a dynamic OAuth access token or any other token of identity protocols.

public class WebSocketAuth : ActionFilterAttribute
{
// stored access token usually retrieved from any storage
// implemented thought OAuth or any other identity protocol
private const string access_token = "821e2f35-86e3-4917-a963-b0c4228d1315";
public override void OnActionExecuting(HttpActionContext actionContext)
{
// retrieve access token from query string
var sAccess_token = HttpUtility.ParseQueryString(
actionContext.Request.RequestUri.Query)["access_token"];
// show case only: easy comparison of tokens
if (sAccess_token != access_token)
throw new UnauthorizedAccessException();
}
}
view raw api.cs hosted with ❤ by GitHub

When adding the TX Text Control MVC NuGet package to an ASP.NET Web Application, the TXWebSocketController is added to the project. By adding the attribute [WebSocketAuth] to the controller, the filter is executed before the controller method.

[WebSocketAuth]
public class TXWebSocketController : ApiController {
public HttpResponseMessage Get() {
if (HttpContext.Current.IsWebSocketRequest) {
var wsHandler = new WebSocketHandler();
wsHandler.ProcessRequest(HttpContext.Current);
return new HttpResponseMessage(HttpStatusCode.SwitchingProtocols);
}
return new HttpResponseMessage(HttpStatusCode.OK);
}
}
view raw api.cs hosted with ❤ by GitHub

In the HtmlHelper code, the access token is passed as a query string in the WebSocketURL property:

@using TXTextControl.Web.MVC
@{
// use an access token (for example returned by OAuth)
var sAccessToken = "821e2f35-86e3-4917-a963-b0c4228d1315";
// build WebSocketURL including access token in query string
var sProtocol = (Request.Url.Scheme == "https") ? "wss://" : "ws://";
var sWebSocketURL = sProtocol + Request.Url.Authority +
"/api/TXWebSocket?access_token=" + sAccessToken;
}
@Html.TXTextControl().TextControl(settings => {
settings.WebSocketURL = sWebSocketURL; // pass built WebSocketURL
}).Render()
view raw test.cshtml hosted with ❤ by GitHub