Skip to content

Commit 6320efd

Browse files
authored
fix handleTOPIC only supporting modern RPL_TOPIC (#72)
handleTOPIC was using the wrong event parameters when a TOPIC message or (old) RPL_TOPIC was received, it only handles (new) RPL_TOPIC messages correctly. TOPIC messages are defined as `TOPIC <channel> [:<topic>]` in both specs while RPL_TOPIC differs between RFC1459/RFC2812 and "Modern IRC" such that they are respectively defined as `RPC_TOPIC <channel> :<topic>` and `RPL_TOPIC <client> <channel> :<topic>`. The old code only correctly parsed the "Modern IRC" RPL_TOPIC variant and not the (old) RPL_TOPIC or TOPIC events, these were instead silently never used in state tracking of the channel topic.
1 parent 0c03e8d commit 6320efd

File tree

2 files changed

+15
-5
lines changed

2 files changed

+15
-5
lines changed

builtin.go

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -223,14 +223,19 @@ func handlePART(c *Client, e Event) {
223223
// handleTOPIC handles incoming TOPIC events and keeps channel tracking info
224224
// updated with the latest channel topic.
225225
func handleTOPIC(c *Client, e Event) {
226-
var name string
226+
var name, topic string
227227
switch len(e.Params) {
228228
case 0:
229229
return
230-
case 1:
230+
case 1: // TOPIC, message format is `TOPIC <channel>`
231231
name = e.Params[0]
232-
default:
232+
topic = ""
233+
case 2: // TOPIC, message format is `TOPIC <channel> :<topic>`
234+
name = e.Params[0]
235+
topic = e.Last()
236+
default: // RPL_TOPIC, message format is `332 <client> <channel> :<topic>`
233237
name = e.Params[1]
238+
topic = e.Last()
234239
}
235240

236241
c.state.Lock()
@@ -240,7 +245,7 @@ func handleTOPIC(c *Client, e Event) {
240245
return
241246
}
242247

243-
channel.Topic = e.Last()
248+
channel.Topic = topic
244249
c.state.Unlock()
245250
c.state.notify(c, UPDATE_STATE)
246251
}

state_test.go

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,12 +42,13 @@ const mockConnStartState = `:dummy.int NOTICE * :*** Looking up your hostname...
4242
:dummy.int 354 nick 1 #channel nick2 other.int nick2 nick2 :realname2
4343
:dummy.int 315 nick #channel :End of /WHO list.
4444
:[email protected] JOIN #channel2 * :realname
45-
:dummy.int 332 nick #channel2 :example topic
45+
:dummy.int 332 nick #channel2 :example init topic
4646
:dummy.int 353 nick = #channel2 :[email protected] @[email protected]
4747
:dummy.int 366 nick #channel2 :End of /NAMES list.
4848
:dummy.int 354 nick 1 #channel2 ~user local.int nick 0 :realname
4949
:dummy.int 354 nick 1 #channel2 nick2 other.int nick2 nick2 :realname2
5050
:dummy.int 315 nick #channel2 :End of /WHO list.
51+
:dummy.int TOPIC #channel2 :example topic
5152
`
5253

5354
const mockConnEndState = `:[email protected] QUIT :example reason
@@ -190,6 +191,10 @@ func TestState(t *testing.T) {
190191
t.Fatal("User.InChannel() returned false for existing channel")
191192
}
192193

194+
if ch2 := c.LookupChannel("#channel2"); ch2.Topic != "example topic" {
195+
t.Fatalf("Channel.Topic == %q, want \"example topic\"", ch2.Topic)
196+
}
197+
193198
finishStart <- true
194199
})
195200

0 commit comments

Comments
 (0)