]>
Commit | Line | Data |
---|---|---|
dcf3d43b DC |
1 | console.log('xtermjs: starting'); |
2 | ||
3 | var states = { | |
4 | start: 1, | |
5 | connecting: 2, | |
6 | connected: 3, | |
7 | disconnecting: 4, | |
8 | disconnected: 5, | |
9 | }; | |
10 | ||
11 | var term, | |
12 | protocol, | |
13 | socketURL, | |
14 | socket, | |
15 | ticket, | |
dcf3d43b DC |
16 | resize, |
17 | ping, | |
18 | state = states.start; | |
19 | ||
20 | function updateState(newState, msg) { | |
21 | var timeout, severity, message; | |
22 | switch (newState) { | |
23 | case states.connecting: | |
24 | message = "Connecting..."; | |
25 | timeout = 0; | |
26 | severity = severities.warning; | |
27 | break; | |
28 | case states.connected: | |
29 | message = "Connected"; | |
30 | break; | |
31 | case states.disconnecting: | |
32 | message = "Disconnecting..."; | |
33 | timeout = 0; | |
34 | severity = severities.warning; | |
35 | break; | |
36 | case states.disconnected: | |
37 | switch (state) { | |
38 | case states.start: | |
39 | case states.connecting: | |
40 | message = "Connection failed"; | |
41 | timeout = 0; | |
42 | severity = severities.error; | |
43 | break; | |
44 | case states.connected: | |
45 | case states.disconnecting: | |
46 | message = "Connection closed"; | |
47 | timeout = 0; | |
48 | break; | |
49 | case states.disconnected: | |
50 | // no state change | |
51 | break; | |
52 | default: | |
53 | throw "unknown state"; | |
54 | } | |
55 | break; | |
56 | default: | |
57 | throw "unknown state"; | |
58 | } | |
59 | if (msg) { | |
60 | message += " (" + msg + ")"; | |
61 | } | |
62 | state = newState; | |
63 | showMsg(message, timeout, severity); | |
64 | } | |
65 | ||
66 | var terminalContainer = document.getElementById('terminal-container'); | |
67 | document.getElementById('status_bar').addEventListener('click', hideMsg); | |
68 | ||
69 | createTerminal(); | |
70 | ||
71 | function createTerminal() { | |
72 | term = new Terminal(); | |
73 | ||
74 | term.on('resize', function (size) { | |
75 | if (state === states.connected) { | |
76 | socket.send("1:" + size.cols + ":" + size.rows + ":"); | |
77 | } | |
78 | }); | |
79 | ||
80 | protocol = (location.protocol === 'https:') ? 'wss://' : 'ws://'; | |
81 | ||
82 | var params = {}; | |
83 | var type = getQueryParameter('console'); | |
84 | var vmid = getQueryParameter('vmid'); | |
85 | var vmname = getQueryParameter('vmname'); | |
86 | var nodename = getQueryParameter('node'); | |
87 | var url = '/nodes/' + nodename; | |
88 | switch (type) { | |
89 | case 'kvm': | |
90 | url += '/qemu/' + vmid; | |
dcf3d43b DC |
91 | break; |
92 | case 'lxc': | |
93 | url += '/lxc/' + vmid; | |
dcf3d43b DC |
94 | break; |
95 | case 'upgrade': | |
96 | params.upgrade = 1; | |
dcf3d43b DC |
97 | break; |
98 | } | |
99 | API2Request({ | |
100 | method: 'POST', | |
101 | params: params, | |
102 | url: url + '/termproxy', | |
103 | success: function(result) { | |
104 | var port = encodeURIComponent(result.data.port); | |
105 | ticket = result.data.ticket; | |
106 | socketURL = protocol + location.hostname + ((location.port) ? (':' + location.port) : '') + '/api2/json' + url + '/vncwebsocket?port=' + port + '&vncticket=' + encodeURIComponent(ticket); | |
107 | ||
108 | term.open(terminalContainer, true); | |
109 | socket = new WebSocket(socketURL, 'binary'); | |
110 | socket.binaryType = 'arraybuffer'; | |
111 | socket.onopen = runTerminal; | |
112 | socket.onclose = stopTerminal; | |
113 | socket.onerror = errorTerminal; | |
114 | window.onbeforeunload = stopTerminal; | |
115 | updateState(states.connecting); | |
116 | }, | |
117 | failure: function(msg) { | |
118 | updateState(states.disconnected,msg); | |
119 | } | |
120 | }); | |
121 | ||
122 | } | |
123 | ||
124 | function runTerminal() { | |
125 | socket.onmessage = function(event) { | |
126 | var answer = Utf8ArrayToStr(event.data); | |
127 | if (state === states.connected) { | |
128 | term.write(answer); | |
129 | } else if(state === states.connecting) { | |
130 | if (answer.slice(0,2) === "OK") { | |
131 | updateState(states.connected); | |
132 | term.write(answer.slice(2)); | |
133 | } else { | |
134 | socket.close(); | |
135 | } | |
136 | } | |
137 | }; | |
138 | ||
139 | term.on('data', function(data) { | |
140 | if (state === states.connected) { | |
141 | socket.send("0:" + unescape(encodeURIComponent(data)).length.toString() + ":" + data); | |
142 | } | |
143 | }); | |
144 | ||
145 | ping = setInterval(function() { | |
146 | socket.send("2"); | |
147 | }, 30*1000); | |
148 | ||
149 | window.addEventListener('resize', function() { | |
150 | clearTimeout(resize); | |
151 | resize = setTimeout(function() { | |
152 | // done resizing | |
153 | term.fit(); | |
154 | }, 250); | |
155 | }); | |
156 | ||
5e91985c | 157 | socket.send(PVE.UserName + ':' + ticket + "\n"); |
dcf3d43b DC |
158 | |
159 | setTimeout(function() {term.fit();}, 250); | |
160 | } | |
161 | ||
162 | function stopTerminal(event) { | |
163 | term.off('resize'); | |
164 | term.off('data'); | |
165 | clearInterval(ping); | |
166 | socket.close(); | |
167 | updateState(states.disconnected, event.msg + event.code); | |
168 | } | |
169 | ||
170 | function errorTerminal(event) { | |
171 | term.off('resize'); | |
172 | term.off('data'); | |
173 | clearInterval(ping); | |
174 | socket.close(); | |
175 | term.destroy(); | |
176 | updateState(states.disconnected, event.msg + event.code); | |
177 | } |