mirror of
https://gitlab.com/MrFry/moodle-test-userscript
synced 2025-04-01 20:22:48 +02:00
p2p functionality
This commit is contained in:
parent
3ad9e897f3
commit
b12e7a9a55
2 changed files with 383 additions and 157 deletions
|
@ -2,8 +2,9 @@ module.exports = {
|
|||
env: {
|
||||
browser: true,
|
||||
es6: true,
|
||||
node: true,
|
||||
jest: true,
|
||||
},
|
||||
parserOptions: {
|
||||
ecmaVersion: 8,
|
||||
},
|
||||
extends: ['eslint:recommended'],
|
||||
globals: {
|
||||
|
|
535
stable.user.js
535
stable.user.js
|
@ -46,7 +46,7 @@
|
|||
// : Script header {{{
|
||||
// ==UserScript==
|
||||
// @name Moodle/Elearning/KMOOC test help
|
||||
// @version 2.1.3.15
|
||||
// @version 2.1.4.0
|
||||
// @description Online Moodle/Elearning/KMOOC test help
|
||||
// @author MrFry
|
||||
// @match https://elearning.uni-obuda.hu/*
|
||||
|
@ -72,6 +72,7 @@
|
|||
// @match https://v39.moodle.uniduna.hu/*
|
||||
// @match https://mentok.net/*
|
||||
// @match https://qmining.frylabs.net/*
|
||||
// @match https://frylabs.net/*
|
||||
// @noframes
|
||||
// @run-at document-start
|
||||
// @grant GM_getResourceText
|
||||
|
@ -83,16 +84,25 @@
|
|||
// @grant GM_openInTab
|
||||
// @grant unsafeWindow
|
||||
// @license GNU General Public License v3.0 or later
|
||||
// @supportURL qmining.frylabs.net
|
||||
// @contributionURL qmining.frylabs.net
|
||||
// @namespace https://qmining.frylabs.net
|
||||
// @updateURL https://qmining.frylabs.net/moodle-test-userscript/stable.user.js?up
|
||||
// @supportURL frylabs.net
|
||||
// @contributionURL frylabs.net
|
||||
// @namespace https://frylabs.net
|
||||
// @updateURL https://frylabs.net/moodle-test-userscript/stable.user.js?up
|
||||
// ==/UserScript==
|
||||
// : }}}
|
||||
|
||||
;(function () {
|
||||
// : ESLINT bs {{{
|
||||
// CONFIG
|
||||
let originalServer = { host: 'frylabs.net', port: 443 }
|
||||
const logElementGetting = false
|
||||
const logEnabled = true
|
||||
const motdShowCount = 5 // Ammount of times to show motd
|
||||
let infoExpireTime = 60 * 5 // Every n seconds basic info should be (re)loaded from server
|
||||
let p2pInfoExpireTime = 60 * 60 * 24
|
||||
const messageOpacityDelta = 0.1
|
||||
const minMessageOpacity = 0.2
|
||||
|
||||
// : ESLINT bs {{{
|
||||
// eslint-disable-line
|
||||
// GM functions, only to disable ESLINT errors
|
||||
/* eslint-disable */
|
||||
|
@ -125,31 +135,21 @@
|
|||
// Devel vars
|
||||
// ------------------------------------------------------------------------------
|
||||
// forcing pages for testing. unless you test, do not set these to true!
|
||||
const isDevel = true
|
||||
const isDevel = false
|
||||
const forcedMatchString = isDevel ? 'default' : null
|
||||
// only one of these should be true for testing
|
||||
const forceTestPage = isDevel && false
|
||||
const forceResultPage = isDevel && true
|
||||
const forceResultPage = isDevel && false
|
||||
const forceDefaultPage = isDevel && false
|
||||
// ------------------------------------------------------------------------------
|
||||
|
||||
const logElementGetting = false
|
||||
const logEnabled = true
|
||||
const showErrors = true
|
||||
|
||||
let serverAdress = getPeerUrl(originalServer)
|
||||
let apiAdress = getPeerUrl(originalServer) + 'api/'
|
||||
var addEventListener // add event listener function
|
||||
let serverAdress = 'https://qmining.frylabs.net/'
|
||||
let apiAdress = 'https://api.frylabs.net/'
|
||||
|
||||
const motdShowCount = 5 /* Ammount of times to show motd */
|
||||
const messageOpacityDelta = 0.1
|
||||
const minMessageOpacity = 0.2
|
||||
let infoExpireTime = 60 * 5 // Every n seconds basic info should be loaded from server
|
||||
var motd = ''
|
||||
var lastestVersion = ''
|
||||
var subjInfo
|
||||
var uiShowing = true
|
||||
|
||||
let uiShowing = getVal('uishowing')
|
||||
// array, where elems are added to shadow-root, but its position should be at target.
|
||||
var updatableElements = [] // { elem: ..., target: ... }
|
||||
var elementUpdaterInterval = -1
|
||||
|
@ -158,8 +158,29 @@
|
|||
if (isDevel) {
|
||||
warn('Moodle script running in developement mode!')
|
||||
infoExpireTime = 1
|
||||
serverAdress = 'http://localhost:8080/'
|
||||
apiAdress = 'http://localhost:8080/'
|
||||
p2pInfoExpireTime = 1
|
||||
originalServer = { host: 'localhost', port: 8080 }
|
||||
serverAdress = getPeerUrl(originalServer)
|
||||
apiAdress = getPeerUrl(originalServer) + 'api/'
|
||||
setVal('motdcount', 5)
|
||||
}
|
||||
|
||||
const peerToUseString = getVal('peerToUse')
|
||||
var usingPeer = false
|
||||
if (peerToUseString) {
|
||||
try {
|
||||
const peerToUse = JSON.parse(peerToUseString)
|
||||
|
||||
if (peerToUse && peerToUse.host && peerToUse.port) {
|
||||
const url = getPeerUrl(peerToUse)
|
||||
debugLog('Using saved peer url: ' + url)
|
||||
serverAdress = url
|
||||
apiAdress = url + 'api/'
|
||||
usingPeer = true
|
||||
}
|
||||
} catch (e) {
|
||||
debugLog('peerToUse not JSON')
|
||||
}
|
||||
}
|
||||
|
||||
const currUrl = location.href.includes('file:///')
|
||||
|
@ -171,8 +192,7 @@
|
|||
const huTexts = {
|
||||
fatalError:
|
||||
'Fatál error. Check console (f12). Kattints az üzenetre az összes kérdés/válaszért manuális kereséshez! (új böngésző tab-ban)',
|
||||
consoleErrorInfo:
|
||||
'Itteni hibák 100% a moodle hiba. Kivéve, ha oda van írva hogy script error ;) Ha ilyesmi szerepel itt, akkor olvasd el a segítség szekciót! https://qmining.frylabs.net/manual?scriptcmd',
|
||||
consoleErrorInfo: `Itteni hibák 100% a moodle hiba. Kivéve, ha oda van írva hogy script error ;) Ha ilyesmi szerepel itt, akkor olvasd el a segítség szekciót! ${serverAdress}`,
|
||||
freshStartWarning:
|
||||
'<h1>Moodle teszt userscript:<h1><h3>1.5.0 verzió: a script mostantól XMLHTTP kéréseket küld szerver fele! Erre a userscript futtató kiegészítőd is figyelmeztetni fog! Ha ez történik, a script rendes működése érdekében engedélyezd (Always allow domain)! Ha nem akarod, hogy ez történjen, akkor ne engedélyezd, vagy a menüben válaszd ki a "helyi fájl használata" opciót!</h3> <h3>Elküldött adatok: minden teszt után a kérdés-válasz páros. Fogadott adatok: Az összes eddig ismert kérdés. Érdemes help-et elolvasni!!!</h3><h5>Ez az ablak frissités után eltűnik. Ha nem, akkor a visza gombbal próbálkozz.</h5>',
|
||||
noResult:
|
||||
|
@ -193,20 +213,24 @@
|
|||
dataEditorTitle: 'Adatbázisban lévő kérdések szerkesztése',
|
||||
invalidPW: 'Hibás jelszó: ',
|
||||
search: 'Keresés ...',
|
||||
loading: 'Betöltés ...',
|
||||
connecting: 'Csatlakozás: ',
|
||||
login: 'Belépés',
|
||||
newPWTitle: 'Új jelszó új felhasználónak',
|
||||
pwRequest: 'Jelszó új felhasználónak',
|
||||
noServer: 'Nem elérhető a szerver!',
|
||||
tryingPeer: 'Csatlakozás: ',
|
||||
noPeersOnline: 'Egy peer sem elérhető!',
|
||||
peerTryingError: 'Hiba peerek keresése közben!',
|
||||
usingpeer: `A script eredeti szervere megszűnt, vagy nem elérhető, így egy másik peert használ! Hogy továbbra is kapj frissítéseekt újra kell telepítened a scriptet. További infó: <a href="${serverAdress}faq?tab=newpeer">${serverAdress}faq?tab=newpeer</a>`,
|
||||
pwHere: 'Jelszó ...',
|
||||
noServerConsoleMessage: `Nem elérhető a szerver, vagy kis eséllyel kezeletlen hiba történt! Ha elérhető a weboldal, akkor ott meg bírod nézni a kérdéseket itt: ${serverAdress}legacy`,
|
||||
noServerConsoleMessage: `Nem elérhető a szerver! Ha elérhető a weboldal, akkor ott meg bírod nézni a kérdéseket itt: ${serverAdress}allQuestions`,
|
||||
unhandledErrorConsoleMessage: `Kezeletlen hiba történt! Ha elérhető a weboldal, akkor ott meg bírod nézni a kérdéseket itt: ${serverAdress}allQuestions`,
|
||||
noParseableQuestionResult:
|
||||
'A tesztben nem találhatók kérdések, amit fel lehet dolgozni, vagy hiba történt feldolgozásuk közben',
|
||||
unableToParseTestQuestion:
|
||||
'Hiba történt a kérdések beolvasása közben :/ Kattints az üzenetre a manuális kereséshez (új böngésző tab-ban)',
|
||||
loadingAnswer: 'Válaszok betöltése ...',
|
||||
reinstallFromCorrectSource:
|
||||
'Scriptet nem a qmining weboldalról raktad fel. Könnyebb kezelhetőség szempontjából kérlek onnan telepítsd. <a href="https://qmining.frylabs.net/manual.html#scriptreinstall">Részletes leírás</a>',
|
||||
reinstallFromCorrectSource: `Scriptet nem a qmining weboldalról raktad fel. Könnyebb kezelhetőség szempontjából kérlek onnan telepítsd. <a href="${serverAdress}">Részletes leírás</a>`,
|
||||
versionUpdated: 'Verzió frissítve ',
|
||||
newVersionAvaible: 'Új verzió elérhető: ',
|
||||
userSpecifitMotdAvailable:
|
||||
|
@ -1463,10 +1487,6 @@
|
|||
|
||||
log('Moodle / E-Learning script')
|
||||
preventWindowClose()
|
||||
console.log(
|
||||
'%c Moodle / E-Learning script',
|
||||
'font-weight: bold; font-size: 50px;color: yellow; text-shadow: 3px 3px 0 rgb(245,221,8) , 6px 6px 0 rgb(226,91,14) , 9px 9px 0 rgb(217,31,38) , 12px 12px 0 rgb(5,148,68) , 15px 15px 0 rgb(2,135,206) , 18px 18px 0 rgb(4,77,145) , 21px 21px 0 rgb(42,21,113)'
|
||||
)
|
||||
|
||||
if (document.readyState === 'loading') {
|
||||
document.addEventListener('DOMContentLoaded', Init)
|
||||
|
@ -1694,13 +1714,13 @@
|
|||
SetupMenu()
|
||||
ShowMenu()
|
||||
}
|
||||
ConnectToServer(AfterLoad)
|
||||
ConnectToServer()
|
||||
}
|
||||
|
||||
function Auth(pw) {
|
||||
post('login', { pw: pw, script: true }).then((res) => {
|
||||
if (res.result === 'success') {
|
||||
ConnectToServer(AfterLoad)
|
||||
ConnectToServer()
|
||||
clearAllMessages()
|
||||
resetMenu()
|
||||
} else {
|
||||
|
@ -1722,44 +1742,137 @@
|
|||
elem.style.display = 'none'
|
||||
})
|
||||
SafeGetElementById('infoMainDiv', (elem) => {
|
||||
elem.innerText = texts.loading
|
||||
elem.innerText = texts.connecting + getShortServerURL(serverAdress)
|
||||
})
|
||||
}
|
||||
|
||||
function ConnectToServer(cwith) {
|
||||
function ConnectToServer() {
|
||||
clearAllMessages()
|
||||
GetXHRInfos()
|
||||
.then((inf) => {
|
||||
if (inf.result === 'nouser') {
|
||||
NoUserAction()
|
||||
return
|
||||
}
|
||||
lastestVersion = inf.version.replace(/\n/g, '')
|
||||
motd = inf.motd
|
||||
if (getUid() !== inf.uid) {
|
||||
try {
|
||||
if (inf.result === 'nouser') {
|
||||
NoUserAction()
|
||||
return
|
||||
}
|
||||
lastestVersion = inf.version.replace(/\n/g, '')
|
||||
motd = inf.motd
|
||||
if (getUid() !== inf.uid) {
|
||||
setVal('userId', inf.uid)
|
||||
}
|
||||
subjInfo = inf.subjinfo
|
||||
setVal('userId', inf.uid)
|
||||
overlay.querySelector(
|
||||
'#infoMainDiv'
|
||||
).innerText = `${subjInfo.subjects.toLocaleString()} tárgy, ${subjInfo.questions.toLocaleString()} kérdés. UID: #${getUid()}\n${getShortServerURL(
|
||||
serverAdress
|
||||
)}`
|
||||
if (inf.unreads.length > 0) {
|
||||
overlay.querySelector('#mailButton').innerText = '📬'
|
||||
}
|
||||
|
||||
getPeers().catch(() => warn('unable to get p2p info'))
|
||||
AfterLoad()
|
||||
} catch (e) {
|
||||
warn(texts.unhandledErrorConsoleMessage)
|
||||
warn(e)
|
||||
}
|
||||
subjInfo = inf.subjinfo
|
||||
setVal('userId', inf.uid)
|
||||
overlay.querySelector(
|
||||
'#infoMainDiv'
|
||||
).innerText = `${subjInfo.subjects.toLocaleString(
|
||||
'hu'
|
||||
)} tárgy, ${subjInfo.questions.toLocaleString(
|
||||
'hu'
|
||||
)} kérdés.\nUser ID: ${getUid()}`
|
||||
if (inf.unreads.length > 0) {
|
||||
overlay.querySelector('#mailButton').innerText = '📬'
|
||||
}
|
||||
// FIXME: if cwith() throws an unhandled error it sais server is not avaible
|
||||
cwith()
|
||||
})
|
||||
.catch(() => {
|
||||
NoServerAction()
|
||||
.catch((e) => {
|
||||
warn(texts.noServerConsoleMessage)
|
||||
warn(e)
|
||||
tryAnotherPeer()
|
||||
})
|
||||
}
|
||||
|
||||
async function tryAnotherPeer() {
|
||||
SafeGetElementById('scriptMenuDiv', (elem) => {
|
||||
elem.style.backgroundColor = 'red'
|
||||
})
|
||||
|
||||
debugLog('Unable to connect to main server, trying peers')
|
||||
try {
|
||||
const lastp2pinfo = JSON.parse(getVal('lastp2pinfo'))
|
||||
if (
|
||||
!lastp2pinfo ||
|
||||
(Array.isArray(lastp2pinfo) && lastp2pinfo.length === 0)
|
||||
) {
|
||||
debugLog('No saved p2p info available!')
|
||||
return
|
||||
}
|
||||
debugLog('Saved peers: ', lastp2pinfo)
|
||||
const shuffledPeers = lastp2pinfo.sort(() => 0.5 - Math.random())
|
||||
if (usingPeer) {
|
||||
debugLog('Added original server')
|
||||
shuffledPeers.unshift(originalServer)
|
||||
}
|
||||
|
||||
let suitablePeer = null
|
||||
let i = 0
|
||||
while (suitablePeer === null && i < shuffledPeers.length) {
|
||||
const peer = shuffledPeers[i]
|
||||
i++
|
||||
|
||||
const url = getPeerUrl(peer)
|
||||
SafeGetElementById('infoMainDiv', (elem) => {
|
||||
elem.innerText = texts.tryingPeer + getShortServerURL(url)
|
||||
})
|
||||
debugLog('Trying ' + url)
|
||||
|
||||
try {
|
||||
const res = await head(url)
|
||||
if (res.status === 401) {
|
||||
debugLog(url + ' responded with ' + res.status)
|
||||
} else if (res.status === 200) {
|
||||
suitablePeer = peer
|
||||
}
|
||||
} catch (e) {
|
||||
debugLog('Unable to connect!')
|
||||
}
|
||||
}
|
||||
|
||||
if (suitablePeer) {
|
||||
const url = getPeerUrl(suitablePeer)
|
||||
debugLog('Found suitable peer with URL: ' + url + 'index: ' + i)
|
||||
serverAdress = url
|
||||
apiAdress = url + 'api/'
|
||||
if (
|
||||
suitablePeer.host === originalServer.host &&
|
||||
suitablePeer.port === originalServer.port
|
||||
) {
|
||||
setVal('peerToUse', undefined)
|
||||
usingPeer = false
|
||||
} else {
|
||||
setVal('peerToUse', JSON.stringify(suitablePeer))
|
||||
usingPeer = true
|
||||
}
|
||||
|
||||
SafeGetElementById('scriptMenuDiv', (elem) => {
|
||||
elem.style.backgroundColor = '#222426'
|
||||
})
|
||||
|
||||
ConnectToServer()
|
||||
} else {
|
||||
SafeGetElementById('retryContainer', (elem) => {
|
||||
elem.style.display = 'flex'
|
||||
})
|
||||
SafeGetElementById('infoMainDiv', (elem) => {
|
||||
elem.innerText = texts.noPeersOnline
|
||||
})
|
||||
debugLog('None of the peers are online!')
|
||||
}
|
||||
} catch (e) {
|
||||
SafeGetElementById('retryContainer', (elem) => {
|
||||
elem.style.display = 'flex'
|
||||
})
|
||||
SafeGetElementById('infoMainDiv', (elem) => {
|
||||
elem.innerText = texts.peerTryingError
|
||||
})
|
||||
warn('Error ocurred during trying to connect to peers!')
|
||||
warn(e)
|
||||
}
|
||||
}
|
||||
|
||||
function NoUserAction() {
|
||||
SafeGetElementById('scriptMenuDiv', (elem) => {
|
||||
elem.style.backgroundColor = '#44cc00'
|
||||
|
@ -1772,18 +1885,6 @@
|
|||
})
|
||||
}
|
||||
|
||||
function NoServerAction() {
|
||||
SafeGetElementById('scriptMenuDiv', (elem) => {
|
||||
elem.style.backgroundColor = 'red'
|
||||
})
|
||||
SafeGetElementById('infoMainDiv', (elem) => {
|
||||
elem.innerText = texts.noServer
|
||||
})
|
||||
SafeGetElementById('retryContainer', (elem) => {
|
||||
elem.style.display = 'flex'
|
||||
})
|
||||
}
|
||||
|
||||
function VersionActions() {
|
||||
FreshStart()
|
||||
}
|
||||
|
@ -1836,9 +1937,6 @@
|
|||
let timeout = null
|
||||
const greetMsg = []
|
||||
|
||||
if (isNewVersionAvaible || newVersion || showMOTD) {
|
||||
greetMsg.push(texts.scriptName + info().script.version)
|
||||
}
|
||||
if (isNewVersionAvaible) {
|
||||
timeout = 5
|
||||
greetMsg.push(texts.newVersionAvaible + lastestVersion)
|
||||
|
@ -1852,12 +1950,14 @@
|
|||
greetMsg.push(texts.motd + motd)
|
||||
timeout = null
|
||||
}
|
||||
if (usingPeer) {
|
||||
greetMsg.push(texts.usingpeer)
|
||||
}
|
||||
if (greetMsg.length > 0) {
|
||||
greetMsg.unshift(texts.scriptName + info().script.version)
|
||||
}
|
||||
|
||||
ShowMessage(
|
||||
greetMsg.join('\n'),
|
||||
|
||||
timeout
|
||||
)
|
||||
ShowMessage(greetMsg.join('\n'), timeout)
|
||||
}
|
||||
|
||||
// : }}}
|
||||
|
@ -2167,6 +2267,8 @@
|
|||
}
|
||||
|
||||
function getConvertedMessageNode(message) {
|
||||
if (!message) return ''
|
||||
|
||||
const messageNode = document.createElement('p')
|
||||
const resultNode = document.createElement('p')
|
||||
messageNode.innerHTML = message.replace(/\n/g, '</br>')
|
||||
|
@ -2263,6 +2365,7 @@
|
|||
true
|
||||
)
|
||||
uiShowing = !uiShowing
|
||||
setVal('uishowing', uiShowing)
|
||||
}
|
||||
|
||||
function SetupMenu() {
|
||||
|
@ -2315,6 +2418,7 @@
|
|||
width: width + 'px',
|
||||
opacity: getVal(`${id}_opacity`),
|
||||
cursor: funct ? 'pointer' : 'move',
|
||||
display: uiShowing ? '' : 'none',
|
||||
})
|
||||
if (funct) {
|
||||
addEventListener(messageElem, 'click', funct)
|
||||
|
@ -2517,7 +2621,14 @@
|
|||
result.msgContainer.child.leftSideDiv.child.matchPercent.elem.innerText =
|
||||
isNaN(getCurrMsg().p) ? '' : getCurrMsg().p + '%'
|
||||
|
||||
result.msgContainer.child.msgDiv.elem.innerText = getCurrMsg().m
|
||||
if (isSimpleMessage) {
|
||||
result.msgContainer.child.msgDiv.elem.replaceChildren()
|
||||
result.msgContainer.child.msgDiv.elem.appendChild(
|
||||
getConvertedMessageNode(getCurrMsg().m)
|
||||
)
|
||||
} else {
|
||||
result.msgContainer.child.msgDiv.elem.innerText = getCurrMsg().m
|
||||
}
|
||||
} catch (e) {
|
||||
warn('Error in message updating')
|
||||
warn(e)
|
||||
|
@ -2545,6 +2656,8 @@
|
|||
const id = 'scriptMenuDiv'
|
||||
scriptMenuDiv.setAttribute('id', id)
|
||||
SetStyle(scriptMenuDiv, {
|
||||
display: uiShowing ? 'flex' : 'none',
|
||||
flexDirection: 'column',
|
||||
width: '300px',
|
||||
height: '90px',
|
||||
position: 'fixed',
|
||||
|
@ -2599,9 +2712,8 @@
|
|||
style: {
|
||||
position: 'absolute',
|
||||
display: 'inline',
|
||||
bottom: '20px',
|
||||
left: '5px',
|
||||
bottom: '15px',
|
||||
margin: '5px',
|
||||
fontSize: '30px',
|
||||
cursor: 'pointer',
|
||||
},
|
||||
|
@ -2643,72 +2755,82 @@
|
|||
},
|
||||
},
|
||||
},
|
||||
infoContainer: {
|
||||
id: 'infoMainDiv',
|
||||
innerText: texts.loading,
|
||||
statusContainer: {
|
||||
style: {
|
||||
color: '#ffffff',
|
||||
margin: '5px 50px',
|
||||
textAlign: 'center',
|
||||
},
|
||||
},
|
||||
loginContainer: {
|
||||
id: 'loginDiv',
|
||||
style: {
|
||||
display: 'none',
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
justifyContent: 'center',
|
||||
flex: 1,
|
||||
margin: '0px 50px',
|
||||
},
|
||||
children: {
|
||||
loginInput: {
|
||||
customElem: () => {
|
||||
const loginInput = document.createElement('input')
|
||||
loginInput.setAttribute('id', 'pwInput')
|
||||
loginInput.type = 'text'
|
||||
loginInput.placeholder = texts.pwHere
|
||||
SetStyle(loginInput, {
|
||||
width: '100%',
|
||||
textAlign: 'center',
|
||||
})
|
||||
return loginInput
|
||||
},
|
||||
},
|
||||
loginButton: {
|
||||
innerText: texts.login,
|
||||
style: buttonStyle,
|
||||
onClick: () => {
|
||||
SafeGetElementById('pwInput', (elem) => {
|
||||
Auth(elem.value)
|
||||
})
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
retryContainer: {
|
||||
id: 'retryContainer',
|
||||
style: {
|
||||
display: 'none',
|
||||
justifyContent: 'center',
|
||||
},
|
||||
children: {
|
||||
retryButton: {
|
||||
innerText: texts.retry,
|
||||
infoContainer: {
|
||||
id: 'infoMainDiv',
|
||||
innerText: texts.connecting + getShortServerURL(serverAdress),
|
||||
style: {
|
||||
position: '',
|
||||
padding: '0px 8px',
|
||||
border: '1px solid #333',
|
||||
borderRadius: '2px',
|
||||
color: '#ffffff',
|
||||
cursor: 'pointer',
|
||||
textAlign: 'center',
|
||||
},
|
||||
onClick: () => {
|
||||
scriptMenuDiv.style.background = '#262626'
|
||||
SafeGetElementById('infoMainDiv', (elem) => {
|
||||
elem.innerText = texts.loading
|
||||
})
|
||||
SafeGetElementById('retryContainer', (elem) => {
|
||||
elem.style.display = 'none'
|
||||
})
|
||||
ConnectToServer(AfterLoad)
|
||||
},
|
||||
loginContainer: {
|
||||
id: 'loginDiv',
|
||||
style: {
|
||||
display: 'none',
|
||||
},
|
||||
children: {
|
||||
loginInput: {
|
||||
customElem: () => {
|
||||
const loginInput = document.createElement('input')
|
||||
loginInput.setAttribute('id', 'pwInput')
|
||||
loginInput.type = 'text'
|
||||
loginInput.placeholder = texts.pwHere
|
||||
SetStyle(loginInput, {
|
||||
width: '100%',
|
||||
textAlign: 'center',
|
||||
})
|
||||
return loginInput
|
||||
},
|
||||
},
|
||||
loginButton: {
|
||||
innerText: texts.login,
|
||||
style: buttonStyle,
|
||||
onClick: () => {
|
||||
SafeGetElementById('pwInput', (elem) => {
|
||||
Auth(elem.value)
|
||||
})
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
retryContainer: {
|
||||
id: 'retryContainer',
|
||||
style: {
|
||||
display: 'none',
|
||||
justifyContent: 'center',
|
||||
},
|
||||
children: {
|
||||
retryButton: {
|
||||
innerText: texts.retry,
|
||||
style: {
|
||||
position: '',
|
||||
padding: '0px 8px',
|
||||
border: '1px solid #333',
|
||||
borderRadius: '2px',
|
||||
color: '#ffffff',
|
||||
cursor: 'pointer',
|
||||
},
|
||||
onClick: () => {
|
||||
scriptMenuDiv.style.background = '#262626'
|
||||
SafeGetElementById('infoMainDiv', (elem) => {
|
||||
elem.innerText =
|
||||
texts.connecting + getShortServerURL(serverAdress)
|
||||
})
|
||||
SafeGetElementById('retryContainer', (elem) => {
|
||||
elem.style.display = 'none'
|
||||
})
|
||||
ConnectToServer()
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
@ -2801,6 +2923,24 @@
|
|||
log('------------------------------------------')
|
||||
}
|
||||
|
||||
function getShortServerURL(url) {
|
||||
const maxlegnth = 30
|
||||
const shortUrl = url.replace('https://', '').replace('http://', '')
|
||||
if (shortUrl.length <= maxlegnth) {
|
||||
return shortUrl
|
||||
} else {
|
||||
return shortUrl.substring(0, maxlegnth - 3) + '...'
|
||||
}
|
||||
}
|
||||
|
||||
function getPeerUrl(peer) {
|
||||
let protocol = 'https://'
|
||||
if (isDevel) {
|
||||
let protocol = 'http://'
|
||||
}
|
||||
return protocol + peer.host + ':' + peer.port + '/'
|
||||
}
|
||||
|
||||
function getUid() {
|
||||
return getVal('userId')
|
||||
}
|
||||
|
@ -2896,22 +3036,12 @@
|
|||
const now = new Date().getTime()
|
||||
const lastCheck = getVal('lastInfoCheckTime')
|
||||
if (!lastCheck) {
|
||||
setVal('lastInfoCheckTime', now)
|
||||
setVal('lastInfoCheckTime', 0)
|
||||
}
|
||||
|
||||
let lastInfo = { result: 'noLastInfo' }
|
||||
try {
|
||||
lastInfo = JSON.parse(getVal('lastInfo'))
|
||||
} catch (e) {
|
||||
if (showErrors) {
|
||||
warn(e)
|
||||
}
|
||||
}
|
||||
|
||||
if (
|
||||
lastInfo.result !== 'success' ||
|
||||
now > lastCheck + infoExpireTime * 1000
|
||||
) {
|
||||
if (now > lastCheck + infoExpireTime * 1000) {
|
||||
return new Promise((resolve, reject) => {
|
||||
const url =
|
||||
apiAdress +
|
||||
|
@ -2923,11 +3053,11 @@
|
|||
Promise.all([get(url), get(apiAdress + 'hasNewMsg')])
|
||||
.then(([{ responseText: infos }, { responseText: hasNewMsg }]) => {
|
||||
try {
|
||||
setVal('lastInfoCheckTime', now)
|
||||
const infosObj = JSON.parse(infos)
|
||||
const hasNewMsgsObj = JSON.parse(hasNewMsg)
|
||||
const merged = Object.assign({}, infosObj, hasNewMsgsObj)
|
||||
setVal('lastInfo', JSON.stringify(merged))
|
||||
setVal('lastInfoCheckTime', now)
|
||||
resolve(merged)
|
||||
} catch (e) {
|
||||
log('Errro paring JSON in GetXHRInfos')
|
||||
|
@ -2944,6 +3074,7 @@
|
|||
} else {
|
||||
return new Promise((resolve, reject) => {
|
||||
try {
|
||||
lastInfo = JSON.parse(getVal('lastInfo'))
|
||||
resolve(lastInfo)
|
||||
} catch (e) {
|
||||
log('Errro paring JSON in GetXHRInfos, when using old data!')
|
||||
|
@ -2954,12 +3085,102 @@
|
|||
}
|
||||
}
|
||||
|
||||
function updateP2pData(newData) {
|
||||
const lastp2pinfo = getVal('lastp2pinfo')
|
||||
const oldPeers = lastp2pinfo ? JSON.parse(lastp2pinfo) : []
|
||||
const merged = newData.reduce((acc, peer) => {
|
||||
const peerAlreadyExists = acc.find((existingPeer) => {
|
||||
const p1 = peer.host + ':' + peer.port
|
||||
const p2 = existingPeer.host + ':' + existingPeer.port
|
||||
return p1 === p2
|
||||
})
|
||||
|
||||
if (!peerAlreadyExists) {
|
||||
peer.added = new Date().getTime()
|
||||
return [peer, ...acc]
|
||||
}
|
||||
|
||||
return acc
|
||||
}, oldPeers)
|
||||
return merged
|
||||
}
|
||||
|
||||
function getPeers() {
|
||||
const now = new Date().getTime()
|
||||
const lastCheck = getVal('lastp2pchecktime')
|
||||
if (!lastCheck) {
|
||||
setVal('lastp2pchecktime', 0)
|
||||
}
|
||||
|
||||
let lastp2pinfo = {}
|
||||
|
||||
if (now > lastCheck + p2pInfoExpireTime * 1000) {
|
||||
return new Promise((resolve, reject) => {
|
||||
const url = apiAdress + 'p2pinfo'
|
||||
|
||||
get(url)
|
||||
.then(({ responseText: p2pinfo }) => {
|
||||
try {
|
||||
const p2pinfoObj = updateP2pData(JSON.parse(p2pinfo).myPeers)
|
||||
setVal('lastp2pinfo', JSON.stringify(p2pinfoObj))
|
||||
setVal('lastp2pchecktime', now)
|
||||
resolve(p2pinfoObj)
|
||||
} catch (e) {
|
||||
log('Errro paring JSON in getPeers')
|
||||
log(p2pinfo)
|
||||
log(e)
|
||||
reject(e)
|
||||
}
|
||||
})
|
||||
.catch((e) => {
|
||||
log('Info get Error', e)
|
||||
reject(e)
|
||||
})
|
||||
})
|
||||
} else {
|
||||
return new Promise((resolve, reject) => {
|
||||
try {
|
||||
lastp2pinfo = JSON.parse(getVal('lastp2pinfo'))
|
||||
resolve(lastp2pinfo)
|
||||
} catch (e) {
|
||||
log('Errro paring JSON in GetXHRInfos, when using old data!')
|
||||
log(e)
|
||||
reject(e)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
function head(url) {
|
||||
return new Promise((resolve, reject) => {
|
||||
xmlhttpRequest({
|
||||
method: 'HEAD',
|
||||
url: url,
|
||||
crossDomain: true,
|
||||
timeout: 5 * 1000,
|
||||
ontimeout: () => {
|
||||
reject(new Error('HEAD request timed out'))
|
||||
},
|
||||
onload: function (response) {
|
||||
resolve(response)
|
||||
},
|
||||
onerror: (e) => {
|
||||
reject(e)
|
||||
},
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
function get(url) {
|
||||
return new Promise((resolve, reject) => {
|
||||
xmlhttpRequest({
|
||||
method: 'GET',
|
||||
url: url,
|
||||
crossDomain: true,
|
||||
timeout: 15 * 1000,
|
||||
ontimeout: () => {
|
||||
reject(new Error('GET request timed out'))
|
||||
},
|
||||
xhrFields: { withCredentials: true },
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
|
@ -2984,6 +3205,10 @@
|
|||
method: 'POST',
|
||||
url: url,
|
||||
crossDomain: true,
|
||||
timeout: 30 * 1000,
|
||||
ontimeout: () => {
|
||||
reject(new Error('POST request timed out'))
|
||||
},
|
||||
xhrFields: { withCredentials: true },
|
||||
data: message,
|
||||
headers: {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue