add CHANSERV UNREGISTER

This commit is contained in:
Shivaram Lingamneni 2018-06-04 05:02:22 -04:00
parent 7bf18443a8
commit 31f386f5a9
5 changed files with 115 additions and 54 deletions

View File

@ -157,6 +157,17 @@ func (channel *Channel) SetRegistered(founder string) error {
return nil
}
// SetUnregistered deletes the channel's registration information.
func (channel *Channel) SetUnregistered() {
channel.stateMutex.Lock()
defer channel.stateMutex.Unlock()
channel.registeredFounder = ""
var zeroTime time.Time
channel.registeredTime = zeroTime
channel.accountToUMode = make(map[string]modes.Mode)
}
// IsRegistered returns whether the channel is registered.
func (channel *Channel) IsRegistered() bool {
channel.stateMutex.RLock()

View File

@ -201,6 +201,20 @@ func (reg *ChannelRegistry) LoadChannel(nameCasefolded string) (info *Registered
return info
}
func (reg *ChannelRegistry) Delete(casefoldedName string, info RegisteredChannel) {
if !reg.server.ChannelRegistrationEnabled() {
return
}
reg.Lock()
defer reg.Unlock()
reg.server.store.Update(func(tx *buntdb.Tx) error {
reg.deleteChannel(tx, casefoldedName, info)
return nil
})
}
// Rename handles the persistence part of a channel rename: the channel is
// persisted under its new name, and the old name is cleaned up if necessary.
func (reg *ChannelRegistry) Rename(channel *Channel, casefoldedOldName string) {

View File

@ -22,6 +22,10 @@ To see in-depth help for a specific ChanServ command, try:
Here are the commands you can use:
%s`
func chanregEnabled(server *Server) bool {
return server.ChannelRegistrationEnabled()
}
var (
chanservCommands = map[string]*serviceCommand{
"op": {
@ -32,6 +36,7 @@ OP makes the given nickname, or yourself, a channel admin. You can only use
this command if you're the founder of the channel.`,
helpShort: `$bOP$b makes the given user (or yourself) a channel admin.`,
authRequired: true,
enabled: chanregEnabled,
},
"register": {
handler: csRegisterHandler,
@ -42,6 +47,15 @@ given admin privs on it. Modes set on the channel and the topic will also be
remembered.`,
helpShort: `$bREGISTER$b lets you own a given channel.`,
authRequired: true,
enabled: chanregEnabled,
},
"unregister": {
handler: csUnregisterHandler,
help: `Syntax: $bUNREGISTER #channel$b
UNREGISTER deletes a channel registration, allowing someone else to claim it.`,
helpShort: `$bUNREGISTER$b deletes a channel registration.`,
enabled: chanregEnabled,
},
"amode": {
handler: csAmodeHandler,
@ -53,6 +67,7 @@ account the +o operator mode every time they join #channel. To list current
accounts and modes, use $bAMODE #channel$b. Note that users are always
referenced by their registered account names, not their nicknames.`,
helpShort: `$bAMODE$b modifies persistent mode settings for channel members.`,
enabled: chanregEnabled,
},
}
)
@ -197,11 +212,6 @@ func csOpHandler(server *Server, client *Client, command, params string, rb *Res
}
func csRegisterHandler(server *Server, client *Client, command, params string, rb *ResponseBuffer) {
if !server.channelRegistrationEnabled {
csNotice(rb, client.t("Channel registration is not enabled"))
return
}
channelName := strings.TrimSpace(params)
if channelName == "" {
csNotice(rb, ircfmt.Unescape(client.t("Syntax: $bREGISTER #channel$b")))
@ -246,3 +256,33 @@ func csRegisterHandler(server *Server, client *Client, command, params string, r
}
}
}
func csUnregisterHandler(server *Server, client *Client, command, params string, rb *ResponseBuffer) {
channelName := strings.TrimSpace(params)
channelKey, err := CasefoldChannel(channelName)
if channelKey == "" || err != nil {
csNotice(rb, client.t("Channel name is not valid"))
return
}
channel := server.channels.Get(channelKey)
if channel == nil {
csNotice(rb, client.t("No such channel"))
return
}
hasPrivs := client.HasRoleCapabs("chanreg")
if !hasPrivs {
founder := channel.Founder()
hasPrivs = founder != "" && founder == client.Account()
}
if !hasPrivs {
csNotice(rb, client.t("Insufficient privileges"))
return
}
info := channel.ExportRegistration(0)
channel.SetUnregistered()
go server.channelRegistry.Delete(channelKey, info)
csNotice(rb, fmt.Sprintf(client.t("Channel %s is now unregistered"), channelKey))
}

View File

@ -62,7 +62,7 @@ func (server *Server) DefaultChannelModes() modes.Modes {
func (server *Server) ChannelRegistrationEnabled() bool {
server.configurableStateMutex.RLock()
defer server.configurableStateMutex.RUnlock()
return server.channelRegistrationEnabled
return server.config.Channels.Registration.Enabled
}
func (server *Server) AccountConfig() *AccountConfig {

View File

@ -87,51 +87,50 @@ type ListenerWrapper struct {
// Server is the main Oragono server.
type Server struct {
accounts *AccountManager
batches *BatchManager
channelRegistrationEnabled bool
channels *ChannelManager
channelRegistry *ChannelRegistry
checkIdent bool
clients *ClientManager
config *Config
configFilename string
configurableStateMutex sync.RWMutex // tier 1; generic protection for server state modified by rehash()
connectionLimiter *connection_limits.Limiter
connectionThrottler *connection_limits.Throttler
ctime time.Time
defaultChannelModes modes.Modes
dlines *DLineManager
loggingRawIO bool
isupport *isupport.List
klines *KLineManager
languages *languages.Manager
limits Limits
listeners map[string]*ListenerWrapper
logger *logger.Manager
maxSendQBytes uint32
monitorManager *MonitorManager
motdLines []string
name string
nameCasefolded string
networkName string
operators map[string]*Oper
operclasses map[string]*OperClass
password []byte
passwords *passwd.SaltedManager
recoverFromErrors bool
rehashMutex sync.Mutex // tier 4
rehashSignal chan os.Signal
pprofServer *http.Server
proxyAllowedFrom []string
signals chan os.Signal
snomasks *SnoManager
store *buntdb.DB
stsEnabled bool
webirc []webircConfig
whoWas *WhoWasList
stats *Stats
semaphores *ServerSemaphores
accounts *AccountManager
batches *BatchManager
channels *ChannelManager
channelRegistry *ChannelRegistry
checkIdent bool
clients *ClientManager
config *Config
configFilename string
configurableStateMutex sync.RWMutex // tier 1; generic protection for server state modified by rehash()
connectionLimiter *connection_limits.Limiter
connectionThrottler *connection_limits.Throttler
ctime time.Time
defaultChannelModes modes.Modes
dlines *DLineManager
loggingRawIO bool
isupport *isupport.List
klines *KLineManager
languages *languages.Manager
limits Limits
listeners map[string]*ListenerWrapper
logger *logger.Manager
maxSendQBytes uint32
monitorManager *MonitorManager
motdLines []string
name string
nameCasefolded string
networkName string
operators map[string]*Oper
operclasses map[string]*OperClass
password []byte
passwords *passwd.SaltedManager
recoverFromErrors bool
rehashMutex sync.Mutex // tier 4
rehashSignal chan os.Signal
pprofServer *http.Server
proxyAllowedFrom []string
signals chan os.Signal
snomasks *SnoManager
store *buntdb.DB
stsEnabled bool
webirc []webircConfig
whoWas *WhoWasList
stats *Stats
semaphores *ServerSemaphores
}
var (
@ -955,9 +954,6 @@ func (server *Server) applyConfig(config *Config, initial bool) error {
server.operators = opers
server.checkIdent = config.Server.CheckIdent
// registration
server.channelRegistrationEnabled = config.Channels.Registration.Enabled
server.defaultChannelModes = ParseDefaultChannelModes(config)
server.configurableStateMutex.Unlock()