Add WHO handing, fix nicklist prefixing

This commit is contained in:
Evert Prants 2020-02-08 15:31:01 +02:00
parent 4067ea31e0
commit 2db9b22cbf
Signed by: evert
GPG Key ID: 1688DA83D222D0B5
3 changed files with 156 additions and 45 deletions

View File

@ -538,6 +538,7 @@ class IRCConnectionHandler {
case 'MODE': case 'MODE':
let isChannelMode = false let isChannelMode = false
let method = '+' let method = '+'
let lts = line.trailing ? line.trailing.split(' ') : []
if (line.arguments[0].indexOf('#') !== -1) { if (line.arguments[0].indexOf('#') !== -1) {
isChannelMode = true isChannelMode = true
} }
@ -560,12 +561,17 @@ class IRCConnectionHandler {
if (isChannelMode) { if (isChannelMode) {
for (let i in modes) { for (let i in modes) {
let mode = modes[i] let mode = modes[i]
let modei = parseInt(i)
if (this.conn.data.supportedModes[mode]) { if (this.conn.data.supportedModes[mode]) {
this.conn.emit('fromServer', { this.conn.emit('fromServer', {
type: 'mode' + (method === '+' ? 'Add' : 'Del'), type: 'mode' + (method === '+' ? 'Add' : 'Del'),
target: line.arguments[0], target: line.arguments[0],
mode: mode, mode: mode,
modeTarget: line.arguments[2 + parseInt(i)], modeTarget: line.arguments[2]
? (line.arguments[2 + modei]
? line.arguments[2 + modei]
: lts[modei - 1])
: lts[modei],
server: serverName, server: serverName,
user: { user: {
nickname: sender nickname: sender
@ -596,11 +602,38 @@ class IRCConnectionHandler {
this.conn.write('NICK ' + newNick) this.conn.write('NICK ' + newNick)
this.conn.config.nickname = newNick this.conn.config.nickname = newNick
break break
case '352':
// who query response
// <channel> <user> <host> <server> <nick> <H|G>[*][@|+] :<hopcount> <real_name>
if (!this.conn.queue.who) {
this.conn.queue.who = []
}
this.conn.queue.who.push({
channel: line.arguments[1],
server: line.arguments[4],
modes: line.arguments[6],
hopcount: line.trailing.split(' ')[0],
hostmask: format('%s@%s', line.arguments[2], line.arguments[3]),
nickname: line.arguments[5],
realname: line.trailing.split(' ').slice(1).join(' ')
})
break
case '315':
this.conn.emit('fromServer', {
type: 'whoResponse',
who: this.conn.queue.who,
target: line.arguments[1],
message: line.trailing,
server: serverName,
from: realServerName
})
delete this.conn.queue.who
break
case '311': case '311':
// start whois queue // start whois queue
list = { list = {
nickname: line.arguments[1], nickname: line.arguments[1],
hostmask: format('%s!%s@%s', line.arguments[1], line.arguments[2], line.arguments[3]), hostmask: format('%s@%s', line.arguments[2], line.arguments[3]),
realname: line.trailing || '' realname: line.trailing || ''
} }
this.whoisManage(line.arguments[1], list) this.whoisManage(line.arguments[1], list)

View File

@ -175,6 +175,63 @@ function whoisMessage (whoisData, buffer) {
} }
} }
const whoQueue = {}
/*
function queryChannelMembers (server, channel) {
whoQueue[channel] = true
sendToServer(server, { command: 'who', arguments: [channel] })
}
*/
function whoResponse (data, buffer) {
let srv = irc.chat.getChatBuffersByServer(data.from)
let channels = []
for (let i in srv) {
let j = srv[i]
if (j.type === 'channel' && j.name === data.target) {
channels.push(j)
}
}
if (channels.length > 0) {
for (let c in channels) {
let chan = channels[c]
if (!chan.nicklist) continue
for (let i in data.who) {
let who = data.who[i]
chan.nicklist.setModesFromString(who.modes, who.nickname)
}
}
}
// Send message to buffer
if (whoQueue[data.target]) {
delete whoQueue[data.target]
return
}
let messages = []
for (let i in data.who) {
let dt = data.who[i]
messages.push(
sf('[%s]&nbsp;%s %s %s %s (%s)',
span(dt.channel, ['channel']),
span(dt.nickname, ['nick']),
span(dt.hostmask, ['hostmask']),
dt.modes,
dt.hopcount,
validators.escapeHTML(dt.realname)
)
)
}
messages.push(sf('[%s]&nbsp;%s', span(data.target, [(data.target.indexOf('#') === 0 ? 'channel' : 'nick')]), data.message))
for (let i in messages) {
buffer.addMessage(messages[i], null, 'whois')
}
}
const asterisk = span('&#8505;', ['asterisk']) const asterisk = span('&#8505;', ['asterisk'])
const arrowout = span('&#11013;', ['arrowout']) const arrowout = span('&#11013;', ['arrowout'])
const arrowin = span('&#10145;', ['arrowin']) const arrowin = span('&#10145;', ['arrowin'])
@ -567,15 +624,20 @@ let commands = {
whois: { whois: {
execute: function (buffer, handler, command, message, listargs) { execute: function (buffer, handler, command, message, listargs) {
if (!listargs[1]) { if (!listargs[1]) return handler.commandError(buffer, listargs[0].toUpperCase() + ': Missing parameters!')
return handler.commandError(buffer, listargs[0].toUpperCase() + ': Missing parameters!')
}
sendToServer(buffer.server, { command: 'whois', message: '', arguments: [listargs[1]] }) sendToServer(buffer.server, { command: 'whois', message: '', arguments: [listargs[1]] })
}, },
description: '<nickname> - Display information about a user.' description: '<nickname> - Display information about a user.'
}, },
who: {
execute: function (buffer, handler, command, message, listargs) {
if (!listargs[1]) listargs[1] = buffer.name
sendToServer(buffer.server, { command: 'who', arguments: [listargs[1]] })
},
description: '[<target>] - Display some information.'
},
connect: { connect: {
execute: function (buffer, handler, command, message, listargs) { execute: function (buffer, handler, command, message, listargs) {
clientdom.connector.frame.style.display = 'block' clientdom.connector.frame.style.display = 'block'
@ -595,9 +657,7 @@ let commands = {
help: { help: {
execute: function (buffer, handler, command, message, listargs) { execute: function (buffer, handler, command, message, listargs) {
if (!listargs[1]) { if (!listargs[1]) return handler.commandError(buffer, listargs[0].toUpperCase() + ': Missing parameters!')
return handler.commandError(buffer, listargs[0].toUpperCase() + ': Missing parameters!')
}
let cmd = listargs[1].toLowerCase() let cmd = listargs[1].toLowerCase()
if (cmd.indexOf('/') === 0) { if (cmd.indexOf('/') === 0) {
@ -692,6 +752,11 @@ class Nicklist {
clientdom.nicklist.appendChild(str) clientdom.nicklist.appendChild(str)
} }
reset () {
this.nicks = []
this.simplifiedNicksList = []
}
render () { render () {
if (!this.buffer.active) return if (!this.buffer.active) return
if (!irc.serverData[this.buffer.server]) return if (!irc.serverData[this.buffer.server]) return
@ -758,6 +823,20 @@ class Nicklist {
return result return result
} }
highestPriorityMode (modes) {
let highest = null
let modeTranslations = irc.serverData[this.buffer.server].modeTranslation
for (let mode in modeTranslations) {
if (modes.indexOf(mode) !== -1) {
highest = mode
break
}
}
return { highest, prefix: highest ? modeTranslations[highest] : null }
}
modeAdded (nickname, newMode) { modeAdded (nickname, newMode) {
let nickIndex = this.getNickIndex(nickname) let nickIndex = this.getNickIndex(nickname)
let nick = null let nick = null
@ -768,25 +847,11 @@ class Nicklist {
return return
} }
let modeTranslations = irc.serverData[this.buffer.server].modeTranslation // Add mode to nicks' modes list
let prefixes = irc.serverData[this.buffer.server].supportedPrefixes
nick.modes.push(newMode) nick.modes.push(newMode)
for (let mode in modeTranslations) { // Find the prefix to give to the nick
let prefix = modeTranslations[mode] nick.prefix = this.highestPriorityMode(nick.modes).prefix || ''
if (nick.modes.indexOf(mode) === -1) continue
let a = nick.modes.indexOf(mode) - 1
if (a >= 0) {
if (prefixes.indexOf(modeTranslations[nick.modes[a]]) < prefixes.indexOf(prefix)) {
nick.prefix = modeTranslations[nick.modes[a]]
break
}
} else {
nick.prefix = prefix
break
}
}
this.render() this.render()
} }
@ -801,29 +866,37 @@ class Nicklist {
return return
} }
let modeTranslations = irc.serverData[this.buffer.server].modeTranslation // Remove mode from nicks' modes list
let prefixes = irc.serverData[this.buffer.server].supportedPrefixes
removeStr(nick.modes, oldMode) removeStr(nick.modes, oldMode)
let currentLowest = '' // Find the prefix to give to the nick
nick.prefix = this.highestPriorityMode(nick.modes).prefix || ''
for (let n in nick.modes) { this.render()
let mode = nick.modes[n] }
let nextMode = nick.modes[n + 1]
if (!nextMode && mode) { setModesFromString (str, nickname) {
currentLowest = modeTranslations[mode] if (this.getNickIndex(nickname) === null) return
break
} else if (nextMode) { let spfx = irc.serverData[this.buffer.server].modeTranslation
if (prefixes.indexOf(modeTranslations[nextMode]) > prefixes.indexOf(modeTranslations[mode])) { let modes = []
currentLowest = modeTranslations[nextMode] let split = str.split('')
for (let i in split) {
let char = split[i]
if (char === 'H' || char === 'G' || char === '*' || char === 's') continue
for (let mode in spfx) {
let prefix = spfx[mode]
if (char === prefix) {
modes.push(mode)
break
} }
} else {
break
} }
} }
nick.prefix = currentLowest let nick = this.nicks[this.getNickIndex(nickname)]
nick.modes = modes
nick.prefix = this.highestPriorityMode(nick.modes).prefix || ''
this.render() this.render()
} }
@ -958,9 +1031,9 @@ class ChatBuffer {
if (this.topic != null && this.topic !== '') { if (this.topic != null && this.topic !== '') {
addClass(clientdom.chat, 'vtopic') addClass(clientdom.chat, 'vtopic')
if (irc.config.colors) { if (irc.config.colors) {
clientdom.topicbar.innerHTML = processors.linkify(processors.channelify(colorizer.stylize(this.topic))) clientdom.topicbar.innerHTML = processors.channelify(processors.linkify(colorizer.stylize(this.topic)))
} else { } else {
clientdom.topicbar.innerHTML = processors.linkify(processors.channelify(colorizer.strip(this.topic))) clientdom.topicbar.innerHTML = processors.channelify(processors.linkify(colorizer.strip(this.topic)))
} }
} }
@ -1400,6 +1473,9 @@ class ConnectionHandler {
case 'whoisResponse': case 'whoisResponse':
whoisMessage(data.whois, irc.chat.getActiveChatBuffer()) whoisMessage(data.whois, irc.chat.getActiveChatBuffer())
break break
case 'whoResponse':
whoResponse(data, irc.chat.getActiveChatBuffer())
break
case 'listedChannel': case 'listedChannel':
irc.chat.messageChatBuffer(server, server, irc.chat.messageChatBuffer(server, server,
{ {
@ -2020,6 +2096,8 @@ class IRCChatWindow {
let channelSendNicks = [] let channelSendNicks = []
buf.nicklist.reset()
for (let n in nicks) { for (let n in nicks) {
let nick = { nickname: '', prefix: '', modes: [] } let nick = { nickname: '', prefix: '', modes: [] }

View File

@ -1,5 +1,5 @@
import util from 'util' import util from 'util'
import config from './config' import config from '../globals'
module.exports.log = function () { module.exports.log = function () {
console.log.apply(null, arguments) console.log.apply(null, arguments)