Panagiotis
Panagiotis

Reputation: 1567

tcl ping message every 30 seconds

I am following the echo service example on practical programming with tcl and tk, and I have some questions (in tcl) about implementing some additional things based on that code.

I am trying to transmit to all clients a message every 30 seconds. I am using "every" procedure defined in the wiki http://wiki.tcl.tk/9299 the part saying "To limit the number of repetitions, use return:[...]". Once the user leaves the server (via closing the socket), the every function still runs and I get error messages. How can I make a check to see if the socket is still on and if not I would stop sending messages?

Upvotes: 0

Views: 811

Answers (1)

Donal Fellows
Donal Fellows

Reputation: 137597

The every script is extremely simple-minded, as it provides no easy mechanism for cancelling the repetition. However, you're using a version that it is quite straight-forward to actually handle terminating things nicely with. You've just got to catch the error (from the closed channel) and respond by returning, which stops the after from being used.

proc every {ms body} {
    eval $body
    after $ms [info level 0]
}
every 30000 {
    if {[catch {
        puts $::channel "Hi there!"
    }]} return
}

It's probably better to do this with a helper procedure and a callback technically generated with list, which makes things touch on some of the more advanced features of Tcl:

proc every {ms body} {
    eval $body
    after $ms [info level 0]
}
proc sendThePing {channel} {
    if {[catch {
        puts $channel "Hi there!"
    }]} {
        # Make the _caller_ (every) return!
        return -level 2 done
    }
}

every 30000 [list sendThePing $theChannel]

This is better at handling multiple connections, more complex argument passing, etc.

Upvotes: 1

Related Questions