53 lines
1.3 KiB
Go
53 lines
1.3 KiB
Go
package app
|
|
|
|
import (
|
|
"errors"
|
|
|
|
"lol.mleku.dev/chk"
|
|
"lol.mleku.dev/log"
|
|
"git.mleku.dev/mleku/nostr/encoders/envelopes/closeenvelope"
|
|
)
|
|
|
|
// HandleClose processes a CLOSE envelope by unmarshalling the request,
|
|
// validates the presence of an <id> field, and signals cancellation for
|
|
// the associated listener through the server's publisher mechanism.
|
|
func (l *Listener) HandleClose(req []byte) (err error) {
|
|
var rem []byte
|
|
env := closeenvelope.New()
|
|
if rem, err = env.Unmarshal(req); chk.E(err) {
|
|
return
|
|
}
|
|
if len(rem) > 0 {
|
|
log.I.F("extra '%s'", rem)
|
|
}
|
|
if len(env.ID) == 0 {
|
|
return errors.New("CLOSE has no <id>")
|
|
}
|
|
|
|
subID := string(env.ID)
|
|
|
|
// Cancel the subscription goroutine by calling its cancel function
|
|
l.subscriptionsMu.Lock()
|
|
if cancelFunc, exists := l.subscriptions[subID]; exists {
|
|
log.D.F("cancelling subscription %s for %s", subID, l.remote)
|
|
cancelFunc()
|
|
delete(l.subscriptions, subID)
|
|
} else {
|
|
log.D.F("subscription %s not found for %s (already closed?)", subID, l.remote)
|
|
}
|
|
l.subscriptionsMu.Unlock()
|
|
|
|
// Also remove from publisher's tracking
|
|
l.publishers.Receive(
|
|
&W{
|
|
Cancel: true,
|
|
remote: l.remote,
|
|
Conn: l.conn,
|
|
Id: subID,
|
|
},
|
|
)
|
|
|
|
log.D.F("CLOSE processed for subscription %s @ %s", subID, l.remote)
|
|
return
|
|
}
|