概述:webssh泛指一种技术可以在网页上实现一个SSH终端,从而无需Xshell之类的模拟终端工具进行SSH连接。经查阅,显示控制台这个操作页面采用xterm.js(https://xtermjs.org/)实现。前后端交互通过websocket实现。
实现:
1.下载xterm:npm install --save xterm
2.页面引入:import { Terminal } from 'xterm';
3.前端代码:
webssh.component.ts
import { Component, OnInit } from '@angular/core';
import { Terminal } from 'xterm';
// import 'xterm/css/xterm.css'; //踩坑:xterm的css一定要引入,不然页面显示异常。引入位置是放在最外层style.css里的:@import "./node_modules/xterm/css/xterm";
@Component({
selector: 'app-webssh',
templateUrl: './webssh.component.html',
styleUrls: ['./webssh.component.scss']
})
export class WebsshComponent implements OnInit {
// public term: Terminal;
constructor() { }
ngOnInit() {
}
// 页面点击事件,显示webssh,与websocket交互
createServer = () => {
// 创建一个新的Terminal对象
const term = new Terminal({
'cursorBlink': true,
});
// 挂载到终端的Dom元素,打开终端
term.open(document.getElementById('terminal'));
term.onData(function (data) {
const msg = { operation: 'stdin', data: data };
conn.send(JSON.stringify(msg));
});
const url = 'ws://xxx';
const conn = new WebSocket(url);
// 连接建立时触发
conn.onopen = function (e) {
// 写入客户端
term.write('\r');
const msg = { operation: 'stdin', data: 'export TERM=xterm && clear \r' };
conn.send(JSON.stringify(msg));
term.clear();
};
// 客户端接收服务端数据时触发
conn.onmessage = function (event) {
const msg = JSON.parse(event.data);
if (msg.operation === 'stdout') {
term.write(msg.data);
} else {
console.log('invalid msg operation: ' + msg);
}
};
// 连接关闭时触发
conn.onclose = function (event) {
if (event.wasClean) {
console.log(`[close] Connection closed cleanly, code=${event.code} reason=${event.reason}`);
} else {
console.log('[close] Connection died');
term.writeln('');
}
term.write('Connection Reset By Peer! Try Refresh.');
};
// 通信发生错误时触发
conn.onerror = function (error) {
console.log('[error] Connection error');
term.write('error: ' + error);
term.clear();
};
}
}
webssh.component.html
<div>
<button nz-button [nzType]="'primary'" (click)="createServer()">
<i class="anticon anticon-plus"></i>连接
</button>
<div id='terminal'></div>
</div>
4.页面效果
PS:若有错误或考虑不周之处,敬请指正!