Forum Discussion
Azure AD Proxy With RDS Gateway and WebClient - WebSockets Error
Hi all, I’m not sure if this is the right crowd for this but I’m pulling my hair out trying to get it working so figured I’d give it a shot here.
I’m trying to set up RDS (Remote Desktop Services) with the HTML5 WebClient behind an Azure AD Application proxy. We are trying to eliminate RDP/3389 and go completely HTTPS/443 with the WebClient and RemoteApp. This is because we need MFA on our on-prem application to be eligible for security insurance.
I’ve got all RDS services running on a single server with the web application proxy running great using a custom DNS name and a proper cert in every location possible (IIS, Gateway, Session Broker, Webclient, Uploaded to Azure AD proxy, etc.)
Everything is working great and clean, no errors until I try to open the remoteapp in the webclient. At that point, the webclient fails to connect to the remoteapp and shows a websocket error.
I’ve followed every install guide out there trying all the little tricks and gotchas with no luck. It’s been weeks of staying up until 1am troubleshooting with no progress. I’m starting to wonder if this is possible.
The only way I ever got it to work was by publishing the RDWeb /RPC as a separate application with pass through auth set on the app proxy. But that wouldn’t protect this with MFA.
Appreciate any help or ideas.
Thanks Dan
9 Replies
- DanWheelerBrass Contributor
Full error below but here's what I assume is the important part:
WebSocketTransport(NORM): WebSocket closed, url=wss://app.company.com:443/remoteDesktopGateway?CorId=%7Bfbb95263-fc51-4f0d-a0f7-34e2d86b0000%7D&ConId=%7B9bdbb68f-ced9-4068-976e-cdf10be2c8dc%7D&ClGen=HTML%3D1&ClBld=Type%3DRdClient%3B%20Build%3Dprivate&AuthS=SSPI_NTLM, wasClean=false, code=1006, reason=""
2023-05-08T16:15:39.922Z Connection(ERR): The connection generated an internal exception with disconnect code=ConnectionBroken(8), extended code=<null>, reason=WebSocket closed with code: 1006 reason:
Thrown in thread 1136492 at:
websockettransport.cpp(335)2023-05-08T16:15:34.682Z Exception: Possibly unhandled rejection: backdrop click Cause: undefined
at Logger.a.error (https://app.company.com/rdweb/webclient/js/client.73f8fc46.js:1:3061),at https://app.company.com/rdweb/webclient/js/client.73f8fc46.js:9:13128,at i (https://app.company.com/rdweb/webclient/js/components.5bb17b48.js:5:28550),at m.$digest (https://app.company.com/rdweb/webclient/js/components.5bb17b48.js:6:2561),at https://app.company.com/rdweb/webclient/js/components.5bb17b48.js:6:4278,at lc.completeTask (https://app.company.com/rdweb/webclient/js/components.5bb17b48.js:6:10379),at https://app.company.com/rdweb/webclient/js/components.5bb17b48.js:4:15392
2023-05-08T16:15:37.446Z RdpFileParser(NORM): Setting "redirectclipboard" = "1"
2023-05-08T16:15:37.447Z RdpFileParser(NORM): Setting "redirectprinters" = "1"
2023-05-08T16:15:37.447Z RdpFileParser(NORM): Setting "redirectcomports" = "1"
2023-05-08T16:15:37.448Z RdpFileParser(NORM): Setting "redirectsmartcards" = "1"
2023-05-08T16:15:37.449Z RdpFileParser(NORM): Setting "devicestoredirect" = "*"
2023-05-08T16:15:37.449Z RdpFileParser(NORM): Setting "drivestoredirect" = "*"
2023-05-08T16:15:37.450Z RdpFileParser(NORM): Setting "redirectdrives" = "1"
2023-05-08T16:15:37.451Z RdpFileParser(NORM): Setting "session bpp" = "32"
2023-05-08T16:15:37.453Z RdpFileParser(NORM): Setting "prompt for credentials on client" = "1"
2023-05-08T16:15:37.456Z RdpFileParser(NORM): Setting "span monitors" = "1"
2023-05-08T16:15:37.457Z RdpFileParser(NORM): Setting "use multimon" = "1"
2023-05-08T16:15:37.458Z RdpFileParser(NORM): Setting "remoteapplicationmode" = "1"
2023-05-08T16:15:37.459Z RdpFileParser(NORM): Setting "server port" = "3389"
2023-05-08T16:15:37.460Z RdpFileParser(NORM): Setting "allow font smoothing" = "1"
2023-05-08T16:15:37.461Z RdpFileParser(NORM): Setting "promptcredentialonce" = "1"
2023-05-08T16:15:37.462Z RdpFileParser(NORM): Setting "require pre-authentication" = "1"
2023-05-08T16:15:37.464Z RdpFileParser(NORM): Setting "gatewayusagemethod" = "1"
2023-05-08T16:15:37.465Z RdpFileParser(NORM): Setting "gatewayprofileusagemethod" = "1"
2023-05-08T16:15:37.466Z RdpFileParser(NORM): Setting "gatewaycredentialssource" = "0"
2023-05-08T16:15:37.467Z RdpFileParser(NORM): Setting "full address" = "ONPREMRDS.ADDOMAIN.NET"
2023-05-08T16:15:37.467Z RdpFileParser(NORM): Setting "alternate shell" = "||Calculator"
2023-05-08T16:15:37.468Z RdpFileParser(NORM): Setting "remoteapplicationprogram" = "||Calculator"
2023-05-08T16:15:37.470Z RdpFileParser(NORM): Setting "gatewayhostname" = "app.company.com"
2023-05-08T16:15:37.476Z RdpFileParser(NORM): Setting "pre-authentication server address" = "https://app.company.com/rdweb/"
2023-05-08T16:15:37.478Z RdpFileParser(NORM): Setting "remoteapplicationname" = "Calculator"
2023-05-08T16:15:37.479Z RdpFileParser(NORM): Setting "remoteapplicationcmdline" = ""
2023-05-08T16:15:37.480Z RdpFileParser(NORM): Setting "workspace id" = "ONPREMRDS.ADDOMAIN.NET"
2023-05-08T16:15:37.481Z RdpFileParser(NORM): Setting "use redirection server name" = "1"
2023-05-08T16:15:37.482Z RdpFileParser(NORM): Setting "loadbalanceinfo" = "tsv://MS Terminal Services Plugin.1.QuickSessionCollection"
2023-05-08T16:15:37.483Z RdpFileParser(NORM): Setting "alternate full address" = "ONPREMRDS.ADDOMAIN.NET"
2023-05-08T16:15:37.484Z RdpFileParser(NORM): Setting "signscope" = "Full Address,Alternate Full Address,Use Redirection Server Name,Server Port,GatewayHostname,GatewayUsageMethod,GatewayProfileUsageMethod,GatewayCredentialsSource,PromptCredentialOnce,Require pre-authentication,Pre-authentication server address,Alternate Shell,RemoteApplicationProgram,RemoteApplicationMode,RemoteApplicationName,RemoteApplicationCmdLine,RedirectDrives,RedirectPrinters,RedirectCOMPorts,RedirectSmartCards,RedirectClipboard,DevicesToRedirect,DrivesToRedirect,LoadBalanceInfo"
2023-05-08T16:15:37.489Z RdpFileParser(NORM): Setting "signature" REDACTED
2023-05-08T16:15:37.497Z [ConnectionFactory] Creating connection to:
2023-05-08T16:15:37.497Z {"hostName":"ONPREMRDS.ADDOMAIN.NET","port":3389,"gatewayHostName":"app.company.com","gatewayPort":443,"remoteApplicationMode":true,"remoteApplicationProgram":"||Calculator","remoteApplicationCmdLine":"","connectionSettings":{"AzureRemoteApp":false},"tenantId":null,"properties":{"AzureRemoteApp":false},"EventLogUploadAddress":"","GatewayCertLogonAuthority":""}
2023-05-08T16:15:37.499Z RdClientConnectionProxy::Create(NORM): LibRDP version: 1.28.0
2023-05-08T16:15:37.500Z RdClientConnectionProxy::Create(NORM): loading webworkers from path: https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js
2023-05-08T16:15:37.555Z WebWorker(NORM): Created Webworker with path: https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js onMessage: HandleConnectionMessage
2023-05-08T16:15:37.585Z [SessionProvider] Connection created event received.
2023-05-08T16:15:37.587Z [SessionFactory] Launching remote app: ||Calculator
2023-05-08T16:15:37.587Z [Connection] Rail is not active adding application to pending list: ||Calculator
2023-05-08T16:15:37.588Z [SessionProvider] Session created received in provider
2023-05-08T16:15:37.589Z [SessionViewModel] Session created event received for: 7da09e21-35b6-4a6b-90ea-306eb621bd74
2023-05-08T16:15:37.592Z [Connection] Connection.connect called
2023-05-08T16:15:37.593Z [SessionViewModel] Received monitorBound event on UI layer
2023-05-08T16:15:37.594Z [Connection] Using default scaleFactor of 1
2023-05-08T16:15:37.609Z [Session] Session focus changed to true id:7da09e21-35b6-4a6b-90ea-306eb621bd74 window id:null
2023-05-08T16:15:37.609Z [SessionViewModel] Session focused event received in view model session id: 7da09e21-35b6-4a6b-90ea-306eb621bd74
2023-05-08T16:15:37.610Z Setting KeyboardLayout :1033 KeyboardType :[object Object] KeyboardSubType :0
2023-05-08T16:15:37.610Z Value of UseConnectionWebWorkers flag = true
2023-05-08T16:15:37.990Z [SessionViewModel] Mouse left canvas mouse position: 236:165.33333206176758
2023-05-08T16:15:38.018Z Connection(NORM): Connection created with correlation ID={fbb95263-fc51-4f0d-a0f7-34e2d86b0000}
2023-05-08T16:15:38.021Z RdClientConnection::Create(NORM): LibRDP version: 1.28.0
2023-05-08T16:15:38.022Z Connection::Initialize(NORM): LibRDP version: 1.28.0
2023-05-08T16:15:38.026Z DVCManager(NORM): Registered plugin DisplayControlGraphicsPlugin
2023-05-08T16:15:38.027Z DVCManager(NORM): Registered plugin InputPlugin
2023-05-08T16:15:38.029Z Html5FilesystemDevice(NORM): File system successfully mounted at /html5fs
2023-05-08T16:15:38.029Z Html5FilesystemDevice::PullIndexedDBChanges(NORM): Pulling FS changes from IndexedDB
2023-05-08T16:15:38.033Z DVCManager(NORM): Registered plugin GfxChannelGraphicsPlugin
2023-05-08T16:15:38.049Z Connection(NORM): SetMonitorLayout called with width 1504, height 800, orientation 0, scaleFactor 100
2023-05-08T16:15:38.060Z DVCManager(NORM): Creating plugin DisplayControlGraphicsPlugin
2023-05-08T16:15:38.060Z DVCManager(NORM): Registering a listener for DVC Microsoft::Windows::RDS::DisplayControl
2023-05-08T16:15:38.062Z DVCManager(NORM): Creating plugin GfxChannelGraphicsPlugin
2023-05-08T16:15:38.064Z DVCManager(NORM): Registering a listener for DVC Microsoft::Windows::RDS::Graphics
2023-05-08T16:15:38.066Z DVCManager(NORM): Creating plugin InputPlugin
2023-05-08T16:15:38.066Z DVCManager(NORM): Registering a listener for DVC Microsoft::Windows::RDS::Input
2023-05-08T16:15:38.067Z GatewayTransport(NORM): Using the Gateway protocol variation for RD Gateway (on-prem)...
2023-05-08T16:15:38.067Z BaseTransportConnectState(NORM): Entering Gateway connection state BaseTransportConnectState
2023-05-08T16:15:38.075Z WebSocketTransport(NORM): Connection process begun for url=wss://app.company.com:443/remoteDesktopGateway?CorId=%7Bfbb95263-fc51-4f0d-a0f7-34e2d86b0000%7D&ConId=%7B9bdbb68f-ced9-4068-976e-cdf10be2c8dc%7D&ClGen=HTML%3D1&ClBld=Type%3DRdClient%3B%20Build%3Dprivate&AuthS=SSPI_NTLM
2023-05-08T16:15:38.076Z GatewayTransport(NORM): GatewayTransport connecting...
2023-05-08T16:15:38.082Z [Connection] Connection state changed to: Opening remote port
2023-05-08T16:15:38.082Z [SessionViewModel] Session 7da09e21-35b6-4a6b-90ea-306eb621bd74 changed canvas display to none
2023-05-08T16:15:39.885Z WebSocketTransport(ERR): WebSocket error received for url=wss://app.company.com:443/remoteDesktopGateway?CorId=%7Bfbb95263-fc51-4f0d-a0f7-34e2d86b0000%7D&ConId=%7B9bdbb68f-ced9-4068-976e-cdf10be2c8dc%7D&ClGen=HTML%3D1&ClBld=Type%3DRdClient%3B%20Build%3Dprivate&AuthS=SSPI_NTLM
websockettransport.cpp(304): OnErrorFromJS()
at Logger.a.errorWithoutTimestamp (https://app.company.com/rdweb/webclient/js/client.73f8fc46.js:1:2849),at Function.<anonymous> (https://app.company.com/rdweb/webclient/js/client.73f8fc46.js:9:14231),at methodCaller_emscripten$$val_$emscripten$$val_emscripten$$val$ (eval at new_ (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:207132), <anonymous>:6:26),at __emval_call_method (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:228824),at invoke_diiiii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:263542),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[8216]:0x452a4f,at invoke_viii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:260685),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[1449]:0xdf103,at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[1790]:0x10d41e,at invoke_vii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:260848),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[7618]:0x3923c3,at invoke_vii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:260848),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[728]:0x67eb0,at OnMessageCallback.OnMessageCallback$Invoke [as Invoke] (eval at new_ (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:207132), <anonymous>:9:1),at Worker.<anonymous> (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:25889)
2023-05-08T16:15:39.892Z WebSocketTransport(NORM): WebSocket closed, url=wss://app.company.com:443/remoteDesktopGateway?CorId=%7Bfbb95263-fc51-4f0d-a0f7-34e2d86b0000%7D&ConId=%7B9bdbb68f-ced9-4068-976e-cdf10be2c8dc%7D&ClGen=HTML%3D1&ClBld=Type%3DRdClient%3B%20Build%3Dprivate&AuthS=SSPI_NTLM, wasClean=false, code=1006, reason=""
2023-05-08T16:15:39.922Z Connection(ERR): The connection generated an internal exception with disconnect code=ConnectionBroken(8), extended code=<null>, reason=WebSocket closed with code: 1006 reason:
Thrown in thread 1136492 at:
websockettransport.cpp(335)
Call Stack:
at invoke_iiiiii
at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[7858]:0x3cf3e2
at invoke_vii
at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[728]:0x67eb0connection.cpp(1801): OnException()
at Logger.a.errorWithoutTimestamp (https://app.company.com/rdweb/webclient/js/client.73f8fc46.js:1:2849),at Function.<anonymous> (https://app.company.com/rdweb/webclient/js/client.73f8fc46.js:9:14231),at methodCaller_emscripten$$val_$emscripten$$val_emscripten$$val$ (eval at new_ (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:207132), <anonymous>:6:26),at __emval_call_method (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:228824),at invoke_diiiii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:263542),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[8216]:0x452a4f,at invoke_viii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:260685),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[1449]:0xdf103,at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[1790]:0x10d41e,at invoke_vii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:260848),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[7618]:0x3923c3,at invoke_vii (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:260848),at https://app.company.com/rdweb/webclient/librdp/html/librdphtml.a2d54375.wasm:wasm-function[728]:0x67eb0,at OnMessageCallback.OnMessageCallback$Invoke [as Invoke] (eval at new_ (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:207132), <anonymous>:9:1),at Worker.<anonymous> (https://app.company.com/rdweb/webclient/librdp/html/librdphtml.38d7d737.js:86:25889)
2023-05-08T16:15:39.926Z [Connection] Disconnecting
2023-05-08T16:15:39.925Z WebSocketTransport(NORM): Connection close initiated for url=wss://app.company.com:443/remoteDesktopGateway?CorId=%7Bfbb95263-fc51-4f0d-a0f7-34e2d86b0000%7D&ConId=%7B9bdbb68f-ced9-4068-976e-cdf10be2c8dc%7D&ClGen=HTML%3D1&ClBld=Type%3DRdClient%3B%20Build%3Dprivate&AuthS=SSPI_NTLM, code=1000, reason="NormalClosure(1000)"
2023-05-08T16:15:39.926Z GatewayTransport(NORM): GatewayTransport closed.
2023-05-08T16:15:39.929Z [Connection] Disconnected
2023-05-08T16:15:39.934Z [SessionViewModel] Received retireCanvas event on UI layer, connectionID=fbb95263-fc51-4f0d-a0f7-34e2d86b0000
2023-05-08T16:15:39.935Z [SessionProvider] Session disconnect received in provider
2023-05-08T16:15:39.935Z [SessionViewModel] Received didDisconnect event on UI layer
2023-05-08T16:15:39.939Z [Connection] Cleaning up connection
2023-05-08T16:15:39.939Z [SessionProvider] Connection destroyed event received.
2023-05-08T16:15:39.939Z [SessionProvider] Session disconnect received in provider
2023-05-08T16:15:39.939Z [SessionViewModel] Received didDisconnect event on UI layer
2023-05-08T16:15:39.964Z [SessionViewModel] Canvas lost focus- PCPackrat46573Copper ContributorI am also trying this method and having the same results. Also tired using other proxy services (Fortigate) with the same result for websockets.
- DanWheelerBrass Contributor
PCPackrat46573 after weeks of thrashing on this issue, I finally got it to work by creating an internal DNS zone on my DCs for the external URL so my internal and external URLs match. So my Azure AD proxy config has a public CNAME for app.company.com that points to app-company.msapproxy.net then the internal URL for the app proxy is configured for app.company.com. Then internally, I have a DNS zone for app.company.com with a default A-record that points to the internal IP address of the remoteapp server. So if you're on the company network, app.company.com goes directly to the server via the A-record. If you're external, app.company.com goes to the Azure AD proxy then the app proxy calls IIS using the public DNS name internally... if that makes sense. I believe root cause for all this was a certificate mismatch. I was testing different scenarios and found that when I had the wrong certificates installed, I'd get the same websockets 1006 error. So on a whim, I tried creating that internal DNS zone and it worked immediately. Some of the documentation says you *should* have matching internal/external DNS names but not that you *must*. So that was wrong. Maybe you only need matching internal/external names when websockets are in play. Such a huge weight off my shoulders to have this working. Hope others will find this when they run into the same.