ztavern/node-server-manager/Lib/MasterServer.js
2024-10-18 00:19:19 +00:00

151 lines
No EOL
4.1 KiB
JavaScript

const ws = require('ws')
const https = require('https')
const { machineId } = require('node-machine-id')
const Utils = new (require('../Utils/Utils.js'))()
class MasterServer {
constructor(Managers) {
this.Managers = Managers
this.interval = 60 * 1000 * 1
this.hostname = 'master.fed0001.xyz'
}
async init() {
this.DB = this.Managers[0].Server.DB
this.apikey = await this.getApiKey()
this.connect()
}
async connect() {
var master = new ws(`wss://${this.hostname}?key=${this.apikey}`)
var interval = null
var ping = null
master.onopen = async () => {
console.log(`Connected to master server \x1b[32m${this.hostname}\x1b[0m`)
interval = setInterval(() => {
try {
this.heartbeat(master)
}
catch (e) {
console.log(e)
}
}, this.interval)
ping = setInterval(() => {
master.send()
}, 5000)
}
master.onerror = async (e) => {
master.close()
}
master.onclose = async (e) => {
clearInterval(interval)
clearInterval(ping)
console.log('Connection to master server lost, reconnecting...')
setTimeout(() => {
this.connect(this.hostname, this.apikey)
}, 5000)
}
master.onmessage = async (msg) => {
try {
if (!Utils.isJson(msg)) {
switch (msg) {
}
return
}
var event = JSON.parse(msg)
switch (event.type) {
case 'bt':
this.Managers.forEach(Manager => {
Manager.Server.Broadcast(event.message)
})
break
}
}
catch (e) {}
}
}
async makeRequest(method, hostname, path, port, data) {
return new Promise((resolve, reject) => {
let options = {
host: hostname,
port: port,
path: path,
method: method,
headers: {
'Content-Type': 'application/json'
}
}
const req = https.request(options, res => {
res.on('data', data => {
resolve(data.toString())
})
})
req.on('error', error => {
reject(error)
})
req.write(JSON.stringify(data))
req.end()
})
}
async getApiKey() {
let id = await machineId()
let endpoint = '/api/key'
let key = JSON.parse(await this.makeRequest('POST', this.hostname, endpoint, 443, {action: 'get', id }))
return key.key
}
heartbeat(webSocket) {
var servers = []
this.Managers.filter(Manager => Manager.Server.Rcon.isRunning).forEach(Manager => {
if (!Manager.Server.Rcon.isRunning) return
var server = {}
var clients = []
Manager.Server.Clients.forEach(Client => {
if (!Client) return
clients.push({
name: Client.Name,
guid: Client.Guid
})
})
server.dvars = {
mapname: Manager.Server.Mapname,
gametype: Manager.Server.Gametype,
gamename: Manager.Server.Gamename,
hostname: Manager.Server.HostnameRaw,
maxclients: Manager.Server.MaxClients
}
server.ip = Manager.Server.externalIP
server.port = Manager.Server.PORT
server.clients = clients
servers.push(server)
})
var heartbeat = { type: 'heartbeat', servers }
servers.length && webSocket.send(JSON.stringify(heartbeat))
}
}
module.exports = MasterServer