增加SSH功能
This commit is contained in:
parent
366935c575
commit
86276b2ffd
@ -254,8 +254,6 @@ export const SSHTerminalContent: React.FC<SSHTerminalContentProps> = ({
|
|||||||
ws.onopen = () => {
|
ws.onopen = () => {
|
||||||
console.log('🔗 WebSocket已连接:', wsUrl);
|
console.log('🔗 WebSocket已连接:', wsUrl);
|
||||||
console.log('📺 Terminal实例存在:', !!terminalInstanceRef.current);
|
console.log('📺 Terminal实例存在:', !!terminalInstanceRef.current);
|
||||||
terminalInstanceRef.current?.writeln('\x1b[32m✓ WebSocket连接已建立\x1b[0m');
|
|
||||||
terminalInstanceRef.current?.writeln('\x1b[36m正在建立SSH会话...\x1b[0m\r\n');
|
|
||||||
};
|
};
|
||||||
|
|
||||||
ws.onmessage = (event) => {
|
ws.onmessage = (event) => {
|
||||||
@ -287,7 +285,13 @@ export const SSHTerminalContent: React.FC<SSHTerminalContentProps> = ({
|
|||||||
if (msg.status) {
|
if (msg.status) {
|
||||||
setConnectionStatus(msg.status);
|
setConnectionStatus(msg.status);
|
||||||
if (msg.status === 'connected') {
|
if (msg.status === 'connected') {
|
||||||
terminalInstanceRef.current?.writeln('\x1b[32m✓ SSH会话已建立\x1b[0m\r\n');
|
// 显示审计警告
|
||||||
|
terminalInstanceRef.current?.writeln('\r\n\x1b[33m┌────────────────────────────────────────────────────────────┐\x1b[0m');
|
||||||
|
terminalInstanceRef.current?.writeln('\x1b[33m│ ⚠️ 安全提示:本次SSH会话将被全程审计记录 │\x1b[0m');
|
||||||
|
terminalInstanceRef.current?.writeln('\x1b[33m│ • 所有操作命令、输入、输出都将被完整记录 │\x1b[0m');
|
||||||
|
terminalInstanceRef.current?.writeln('\x1b[33m│ • 审计日志用于安全审查、故障排查和合规要求 │\x1b[0m');
|
||||||
|
terminalInstanceRef.current?.writeln('\x1b[33m│ • 请规范操作,遵守企业信息安全管理制度 │\x1b[0m');
|
||||||
|
terminalInstanceRef.current?.writeln('\x1b[33m└────────────────────────────────────────────────────────────┘\x1b[0m\r\n');
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
fitAddonRef.current?.fit();
|
fitAddonRef.current?.fit();
|
||||||
}, 100);
|
}, 100);
|
||||||
|
|||||||
@ -176,33 +176,43 @@ export const SSHWindowManager: React.FC<SSHWindowManagerProps> = ({ onOpenWindow
|
|||||||
<div className="fixed bottom-4 right-4 flex flex-col-reverse gap-2 z-[1001]">
|
<div className="fixed bottom-4 right-4 flex flex-col-reverse gap-2 z-[1001]">
|
||||||
{windows
|
{windows
|
||||||
.filter(w => w.isMinimized)
|
.filter(w => w.isMinimized)
|
||||||
.map((window) => (
|
.map((window) => {
|
||||||
<button
|
// 计算同一服务器的窗口数量和当前窗口序号
|
||||||
key={window.id}
|
const sameServerWindows = windows.filter(w => w.server.id === window.server.id);
|
||||||
className={`flex items-center gap-3 px-4 py-3 ${getButtonStyle(window.connectionStatus)} text-white rounded-lg shadow-lg transition-all hover:scale-105 hover:shadow-xl relative`}
|
const needsIndex = sameServerWindows.length > 1;
|
||||||
onClick={() => restoreWindow(window.id)}
|
const windowIndex = sameServerWindows.findIndex(w => w.id === window.id) + 1;
|
||||||
title={`恢复: ${window.server.serverName}`}
|
|
||||||
>
|
return (
|
||||||
{/* 状态指示灯 */}
|
<button
|
||||||
<div className="absolute top-2 right-2">
|
key={window.id}
|
||||||
<div className={`h-2 w-2 rounded-full ${
|
className={`flex items-center gap-3 px-4 py-3 ${getButtonStyle(window.connectionStatus)} text-white rounded-lg shadow-lg transition-all hover:scale-105 hover:shadow-xl relative`}
|
||||||
window.connectionStatus === 'connected' ? 'bg-white animate-pulse' :
|
onClick={() => restoreWindow(window.id)}
|
||||||
window.connectionStatus === 'error' || window.connectionStatus === 'disconnected' ? 'bg-white/70' :
|
title={`恢复: ${window.server.serverName}${needsIndex ? ` #${windowIndex}` : ''}`}
|
||||||
'bg-white/50 animate-pulse'
|
>
|
||||||
}`} />
|
{/* 状态指示灯 */}
|
||||||
</div>
|
<div className="absolute top-2 right-2">
|
||||||
|
<div className={`h-2 w-2 rounded-full ${
|
||||||
<Terminal className="h-5 w-5" />
|
window.connectionStatus === 'connected' ? 'bg-white animate-pulse' :
|
||||||
<div className="text-left">
|
window.connectionStatus === 'error' || window.connectionStatus === 'disconnected' ? 'bg-white/70' :
|
||||||
<div className="text-sm font-semibold">
|
'bg-white/50 animate-pulse'
|
||||||
{window.server.serverName}
|
}`} />
|
||||||
</div>
|
</div>
|
||||||
<div className="text-xs opacity-90">
|
|
||||||
{window.server.hostIp}
|
<Terminal className="h-5 w-5" />
|
||||||
|
<div className="text-left">
|
||||||
|
<div className="text-sm font-semibold flex items-center gap-2">
|
||||||
|
<span>{window.server.serverName}</span>
|
||||||
|
{needsIndex && (
|
||||||
|
<span className="text-xs opacity-75">#{windowIndex}</span>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
<div className="text-xs opacity-90">
|
||||||
|
{window.server.hostIp}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</button>
|
||||||
</button>
|
);
|
||||||
))}
|
})}
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</>
|
</>
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user