mirror of
https://github.com/acepanel/panel.git
synced 2026-02-07 13:13:06 +08:00
159 lines
5.3 KiB
HTML
159 lines
5.3 KiB
HTML
<!--
|
||
Name: SSH
|
||
Author: 耗子
|
||
Date: 2023-07-25
|
||
-->
|
||
<title>SSH</title>
|
||
<link href="https://registry.npmmirror.com/xterm/5.2.1/files/css/xterm.css" rel="stylesheet">
|
||
<div class="layui-fluid">
|
||
<div class="layui-card">
|
||
<div class="layui-card-header">
|
||
SSH
|
||
</div>
|
||
<div class="layui-card-body">
|
||
<div class="layui-form" style="overflow: hidden;" lay-filter="ssh_setting">
|
||
<div class="layui-inline">
|
||
<span style="margin-right: 10px;">地址</span>
|
||
<div class="layui-input-inline">
|
||
<input type="text" name="host" class="layui-input"
|
||
style="height: 30px; margin-top: 5px;">
|
||
</div>
|
||
<span style="margin-left: 40px; margin-right: 10px;">端口</span>
|
||
<div class="layui-input-inline">
|
||
<input type="text" name="port" class="layui-input"
|
||
style="height: 30px; margin-top: 5px;">
|
||
</div>
|
||
<span style="margin-left: 40px; margin-right: 10px;">账号</span>
|
||
<div class="layui-input-inline">
|
||
<input type="text" name="user" class="layui-input"
|
||
style="height: 30px; margin-top: 5px;">
|
||
</div>
|
||
<span style="margin-left: 40px; margin-right: 10px;">密码</span>
|
||
<div class="layui-input-inline">
|
||
<input type="text" name="password" class="layui-input"
|
||
style="height: 30px; margin-top: 5px;">
|
||
</div>
|
||
<div class="layui-input-inline">
|
||
<button lay-filter="save_ssh_setting" lay-submit class="layui-btn layui-btn-sm"
|
||
style="margin-left: 10px;">
|
||
保存
|
||
</button>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
<div id="terminal" style="width: 100%; height: 70vh; background-color: #000000; margin-top: 20px;">
|
||
</div>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
|
||
<script>
|
||
layui.use(['admin', 'jquery', 'form'], function () {
|
||
var admin = layui.admin;
|
||
var $ = layui.jquery;
|
||
var form = layui.form;
|
||
|
||
form.render();
|
||
|
||
admin.req({
|
||
url: "/api/panel/ssh/info"
|
||
, type: 'get'
|
||
, success: function (result) {
|
||
if (result.code !== 0) {
|
||
layer.msg('SSH信息获取失败,请刷新重试!')
|
||
return false;
|
||
}
|
||
form.val("ssh_setting",
|
||
result.data
|
||
);
|
||
}
|
||
});
|
||
|
||
form.on('submit(save_ssh_setting)', function (data) {
|
||
admin.req({
|
||
url: "/api/panel/ssh/info"
|
||
, type: 'post'
|
||
, data: data.field
|
||
, success: function (result) {
|
||
if (result.code !== 0) {
|
||
layer.alert('SSH信息保存失败,请刷新重试!')
|
||
return false;
|
||
}
|
||
layer.alert('SSH信息保存成功!')
|
||
}
|
||
});
|
||
return false;
|
||
});
|
||
})
|
||
</script>
|
||
|
||
<script>
|
||
const msgData = '1'
|
||
const msgResize = '2'
|
||
|
||
var terminal = new Terminal({
|
||
rendererType: "canvas",
|
||
fontSize: 15,
|
||
screenKeys: true,
|
||
useStyle: true,
|
||
cursorBlink: true, // 光标闪烁
|
||
theme: {
|
||
foreground: "#ECECEC", // 字体
|
||
background: "#000000", //背景色
|
||
cursor: "help", // 设置光标
|
||
lineHeight: 20
|
||
}
|
||
});
|
||
let fitAddon = new FitAddon.FitAddon();
|
||
terminal.loadAddon(fitAddon);
|
||
fitAddon.fit()
|
||
|
||
let terminalContainer = document.getElementById("terminal")
|
||
let token = layui.data('HaoZiPanel')['access_token']
|
||
const webSocket = new WebSocket(`ws://${window.location.host}/api/panel/ssh/session`, [token]);
|
||
webSocket.binaryType = 'arraybuffer';
|
||
const enc = new TextDecoder("utf-8");
|
||
webSocket.onmessage = (event) => {
|
||
terminal.write(enc.decode(event.data));
|
||
}
|
||
|
||
webSocket.onopen = () => {
|
||
terminal.open(terminalContainer)
|
||
fitAddon.fit()
|
||
terminal.write("\r\nWelcome to HaoZiPanel SSH. Connection success.\r\n")
|
||
terminal.focus()
|
||
}
|
||
|
||
webSocket.onclose = () => {
|
||
terminal.write("\r\nSSH connection closed. Please refresh the page.\r\n")
|
||
}
|
||
|
||
webSocket.onerror = (event) => {
|
||
console.error(event)
|
||
webSocket.close()
|
||
}
|
||
|
||
terminal.onData((data) => {
|
||
webSocket.send(msgData + CryptoJS.enc.Base64.stringify(CryptoJS.enc.Utf8.parse(data)), ArrayBuffer)
|
||
})
|
||
|
||
terminal.onResize(({cols, rows}) => {
|
||
if (webSocket.readyState === 1) {
|
||
webSocket.send(msgResize +
|
||
CryptoJS.enc.Base64.stringify(
|
||
CryptoJS.enc.Utf8.parse(
|
||
JSON.stringify({
|
||
columns: cols,
|
||
rows: rows
|
||
})
|
||
)
|
||
), ArrayBuffer
|
||
)
|
||
}
|
||
})
|
||
|
||
window.addEventListener("resize", () => {
|
||
fitAddon.fit()
|
||
}, false)
|
||
</script>
|