Intial commit
This commit is contained in:
6293
frontend/package-lock.json
generated
Normal file
6293
frontend/package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load Diff
26
frontend/package.json
Normal file
26
frontend/package.json
Normal file
@@ -0,0 +1,26 @@
|
||||
{
|
||||
"name": "client",
|
||||
"version": "1.0.0",
|
||||
"dependencies": {
|
||||
"console.js": "^2.0.1",
|
||||
"parcel": "^1.12.4",
|
||||
"xterm": "^4.9.0",
|
||||
"xterm-addon-attach": "^0.6.0",
|
||||
"xterm-addon-fit": "^0.4.0",
|
||||
"xterm-addon-search": "^0.7.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"parcel-bundler": "latest"
|
||||
},
|
||||
"scripts": {
|
||||
"build": "parcel build src/index.html --out-dir ../public",
|
||||
"watch": "parcel watch src/index.html --out-dir ../public"
|
||||
},
|
||||
"browserslist": [
|
||||
"last 3 and_chr versions",
|
||||
"last 3 chrome versions",
|
||||
"last 3 opera versions",
|
||||
"last 3 ios_saf versions",
|
||||
"last 3 safari versions"
|
||||
]
|
||||
}
|
30
frontend/src/console.js
Normal file
30
frontend/src/console.js
Normal file
@@ -0,0 +1,30 @@
|
||||
import { Terminal } from 'xterm';
|
||||
import { AttachAddon } from 'xterm-addon-attach';
|
||||
import { FitAddon } from 'xterm-addon-fit';
|
||||
|
||||
window.customElements.define('console-component', class extends HTMLElement {
|
||||
constructor(host, server, token) {
|
||||
super();
|
||||
this.shadow = this.attachShadow({mode: 'open'});
|
||||
this.render();
|
||||
this.term = new Terminal();
|
||||
const fitAddon = new FitAddon();
|
||||
this.term.loadAddon(fitAddon);
|
||||
fitAddon.fit();
|
||||
term.open(document.getElementById('terminal'));
|
||||
this.connect();
|
||||
|
||||
}
|
||||
|
||||
connect() {
|
||||
this.socket = new WebSocket(`wss://${host}/server/${server}/logs?token=${token}`);
|
||||
const attachAddon = new AttachAddon(socket);
|
||||
term.loadAddon(attachAddon);
|
||||
}
|
||||
render() {
|
||||
this.shadow.innerHTML = `
|
||||
<div id="terminal"></div>
|
||||
`;
|
||||
}
|
||||
|
||||
});
|
26
frontend/src/index.html
Normal file
26
frontend/src/index.html
Normal file
@@ -0,0 +1,26 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Document</title>
|
||||
<link rel="stylesheet" href="../node_modules/xterm/css/xterm.css" />
|
||||
</head>
|
||||
<body>
|
||||
<select id="serverselect"></select>
|
||||
<button id="start">Start</button>
|
||||
<button id="stop">Stop</button>
|
||||
<label id="server"></label>
|
||||
<div id="terminal"></div>
|
||||
|
||||
<form id="send">
|
||||
<input type="submit" value="Send">
|
||||
<input type="text" name="send" value="">
|
||||
</form>
|
||||
|
||||
<console-component></console-component>
|
||||
|
||||
<script src="main.js"></script>
|
||||
<script src="console.js"></script>
|
||||
</body>
|
||||
</html>
|
156
frontend/src/main.js
Normal file
156
frontend/src/main.js
Normal file
@@ -0,0 +1,156 @@
|
||||
import { Terminal } from 'xterm';
|
||||
import { AttachAddon } from 'xterm-addon-attach';
|
||||
import { FitAddon } from 'xterm-addon-fit';
|
||||
import { SearchAddon } from 'xterm-addon-search';
|
||||
import 'console.js';
|
||||
|
||||
function main() {
|
||||
const urlParams = new URLSearchParams(window.location.search);
|
||||
const token = urlParams.get('token');
|
||||
if(token==null) {
|
||||
alert("You need a token to use this.");
|
||||
return;
|
||||
}
|
||||
const host = `${window.location.hostname}`;
|
||||
var server = window.location.hash.replace('#', '');
|
||||
var serverselect = document.getElementById('serverselect')
|
||||
var serverlabel = document.getElementById('server');
|
||||
var socket;
|
||||
var term = new Terminal();
|
||||
const fitAddon = new FitAddon();
|
||||
const searchAddon = new SearchAddon();
|
||||
|
||||
term.loadAddon(fitAddon);
|
||||
term.loadAddon(searchAddon);
|
||||
fitAddon.fit();
|
||||
serverlabel.innerText = server;
|
||||
getServers(token, host).then(servers => {
|
||||
if(servers==null) {
|
||||
alert("Invalid token");
|
||||
return;
|
||||
}
|
||||
servers.forEach(element => {
|
||||
let opt = document.createElement('option');
|
||||
opt.text = element;
|
||||
serverselect.add(opt);
|
||||
});
|
||||
if(server == "") {
|
||||
server = serverselect.options[0].value;
|
||||
window.location.hash = serverselect.value;
|
||||
}
|
||||
|
||||
serverselect.value = server;
|
||||
|
||||
console.log(server, servers, servers.includes(server));
|
||||
if(servers.includes(server)) {
|
||||
term.open(document.getElementById('terminal'));
|
||||
try {
|
||||
socket = new WebSocket(`wss://${host}/server/${server}/logs?token=${token}`);
|
||||
const attachAddon = new AttachAddon(socket);
|
||||
term.loadAddon(attachAddon);
|
||||
} catch(err) {
|
||||
alert("You are not allowed to use this server");
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
serverselect.addEventListener("click", (event) => {
|
||||
console.log(serverselect.value);
|
||||
window.location.hash = serverselect.value;
|
||||
socket.close();
|
||||
location.reload();
|
||||
})
|
||||
|
||||
window.onbeforeunload = function() {
|
||||
socket.close();
|
||||
console.log("Closing");
|
||||
alert("Closing");
|
||||
}
|
||||
|
||||
const start = document.getElementById('start');
|
||||
const stop = document.getElementById('stop');
|
||||
const send = document.getElementById('send');
|
||||
|
||||
start.addEventListener('click', async _ => {
|
||||
try {
|
||||
const response = await fetch(`https://${host}/server/${server}/start?token=${token}`, {
|
||||
method: 'post',
|
||||
body: {
|
||||
// Your body
|
||||
}
|
||||
});
|
||||
console.log('Completed!', response);
|
||||
if(await response.status==401) {
|
||||
alert("You are not allowed to start this server");
|
||||
return
|
||||
}
|
||||
socket.close();
|
||||
location.reload();
|
||||
} catch(err) {
|
||||
console.error(`Error: ${err}`);
|
||||
}
|
||||
});
|
||||
|
||||
stop.addEventListener('click', async _ => {
|
||||
try {
|
||||
const response = await fetch(`https://${host}/server/${server}/stop?token=${token}`, {
|
||||
method: 'post',
|
||||
body: {
|
||||
// Your body
|
||||
}
|
||||
});
|
||||
console.log('Completed!', response);
|
||||
if(await response.status==401) {
|
||||
alert("You are not allowed to stop this server");
|
||||
return
|
||||
}
|
||||
} catch(err) {
|
||||
console.error(`Error: ${err}`);
|
||||
}
|
||||
socket.close();
|
||||
});
|
||||
|
||||
|
||||
|
||||
send.onsubmit = async (e) => {
|
||||
e.preventDefault();
|
||||
let formdata = new FormData(send);
|
||||
let command = btoa(formdata.get('send'));
|
||||
console.log(command);
|
||||
//let command = btoa('say hello')
|
||||
try {
|
||||
let response = await fetch(`https://${host}/server/${server}/command/${command}?token=${token}`, {
|
||||
method: 'POST'
|
||||
});
|
||||
if(await response.status==401) {
|
||||
alert("You are not allowed to send commands to this server");
|
||||
return
|
||||
}
|
||||
} catch(err) {
|
||||
console.error(`Error: ${err}`);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
async function getServers(token, host) {
|
||||
try {
|
||||
console.log(`https://${host}/user/servers?token=${token}`);
|
||||
let response = await fetch(`https://${host}/user/servers?token=${token}`, {
|
||||
method: 'GET'
|
||||
});
|
||||
if(response.ok)
|
||||
return JSON.parse(await response.json());
|
||||
else return null;
|
||||
} catch(err) {
|
||||
console.error(`Error: ${err}`);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
window.onload = main();
|
Reference in New Issue
Block a user