@@ -16,12 +16,8 @@ import (
16
16
"cdr.dev/coder-cli/coder-sdk"
17
17
)
18
18
19
- // Dial connects to the broker and negotiates a connection to a listener.
20
- func Dial (ctx context.Context , broker string , iceServers []webrtc.ICEServer ) (* Dialer , error ) {
21
- if iceServers == nil {
22
- iceServers = []webrtc.ICEServer {}
23
- }
24
-
19
+ // DialWebsocket dials the broker with a WebSocket and negotiates a connection.
20
+ func DialWebsocket (ctx context.Context , broker string , iceServers []webrtc.ICEServer ) (* Dialer , error ) {
25
21
conn , resp , err := websocket .Dial (ctx , broker , nil )
26
22
if err != nil {
27
23
if resp != nil {
@@ -40,13 +36,21 @@ func Dial(ctx context.Context, broker string, iceServers []webrtc.ICEServer) (*D
40
36
// We should close the socket intentionally.
41
37
_ = conn .Close (websocket .StatusInternalError , "an error occurred" )
42
38
}()
39
+ return Dial (ctx , nconn , iceServers )
40
+ }
41
+
42
+ // Dial negotiates a connection to a listener.
43
+ func Dial (ctx context.Context , conn net.Conn , iceServers []webrtc.ICEServer ) (* Dialer , error ) {
44
+ if iceServers == nil {
45
+ iceServers = []webrtc.ICEServer {}
46
+ }
43
47
44
48
rtc , err := newPeerConnection (iceServers )
45
49
if err != nil {
46
50
return nil , fmt .Errorf ("create peer connection: %w" , err )
47
51
}
48
52
49
- flushCandidates := proxyICECandidates (rtc , nconn )
53
+ flushCandidates := proxyICECandidates (rtc , conn )
50
54
51
55
ctrl , err := rtc .CreateDataChannel (controlChannel , & webrtc.DataChannelInit {
52
56
Protocol : stringPtr (controlChannel ),
@@ -72,34 +76,34 @@ func Dial(ctx context.Context, broker string, iceServers []webrtc.ICEServer) (*D
72
76
if err != nil {
73
77
return nil , fmt .Errorf ("marshal offer message: %w" , err )
74
78
}
75
- _ , err = nconn .Write (offerMessage )
79
+ _ , err = conn .Write (offerMessage )
76
80
if err != nil {
77
81
return nil , fmt .Errorf ("write offer: %w" , err )
78
82
}
79
83
flushCandidates ()
80
84
81
85
dialer := & Dialer {
82
- ws : conn ,
86
+ conn : conn ,
83
87
ctrl : ctrl ,
84
88
rtc : rtc ,
85
89
}
86
90
87
- return dialer , dialer .negotiate (nconn )
91
+ return dialer , dialer .negotiate ()
88
92
}
89
93
90
94
// Dialer enables arbitrary dialing to any network and address
91
95
// inside a workspace. The opposing end of the WebSocket messages
92
96
// should be proxied with a Listener.
93
97
type Dialer struct {
94
- ws * websocket .Conn
98
+ conn net .Conn
95
99
ctrl * webrtc.DataChannel
96
100
ctrlrw datachannel.ReadWriteCloser
97
101
rtc * webrtc.PeerConnection
98
102
}
99
103
100
- func (d * Dialer ) negotiate (nconn net. Conn ) (err error ) {
104
+ func (d * Dialer ) negotiate () (err error ) {
101
105
var (
102
- decoder = json .NewDecoder (nconn )
106
+ decoder = json .NewDecoder (d . conn )
103
107
errCh = make (chan error )
104
108
// If candidates are sent before an offer, we place them here.
105
109
// We currently have no assurances to ensure this can't happen,
@@ -111,15 +115,15 @@ func (d *Dialer) negotiate(nconn net.Conn) (err error) {
111
115
defer close (errCh )
112
116
err := waitForDataChannelOpen (context .Background (), d .ctrl )
113
117
if err != nil {
114
- _ = d .ws .Close (websocket . StatusAbnormalClosure , "timeout" )
118
+ _ = d .conn .Close ()
115
119
errCh <- err
116
120
return
117
121
}
118
122
d .ctrlrw , err = d .ctrl .Detach ()
119
123
if err != nil {
120
124
errCh <- err
121
125
}
122
- _ = d .ws .Close (websocket . StatusNormalClosure , "connected" )
126
+ _ = d .conn .Close ()
123
127
}()
124
128
125
129
for {
0 commit comments