egghelp.org community Forum Index
[ egghelp.org home | forum home ]
egghelp.org community
Discussion of eggdrop bots, shell accounts and tcl scripts.
 
 FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

Script works in shell but not as a proc

 
Post new topic   Reply to topic    egghelp.org community Forum Index -> Scripting Help
View previous topic :: View next topic  
Author Message
Coixi
Voice


Joined: 12 Nov 2006
Posts: 6

PostPosted: Sun Nov 12, 2006 6:51 am    Post subject: Script works in shell but not as a proc Reply with quote

Hello, i've a simple double-foreach script which works nicely when it's runned in shell but when i put it inside proc { }, it won't work anymore.

Here's the script:

Code:
set channels "#chan1 #chan2 #chan3"

set messages "msg1 msg2 msg3"

foreach message $messages {

        foreach channel $channels {

                after 10000 {
                puts "PRIVMSG $message $channel ([clock format [clock seconds] -format %H:%M:%S])"
                set ::pleasewait 1
                }

        vwait ::pleasewait

        }
}


When i start my eggdrop ( v1.6.18 ) it will output this after modules have been loaded:

Code:
PRIVMSG msg1 #chan1 (11:55:44)
PRIVMSG msg1 #chan2 (11:55:54)
PRIVMSG msg1 #chan3 (11:56:04)
PRIVMSG msg2 #chan1 (11:56:14)
PRIVMSG msg2 #chan2 (11:56:24)
PRIVMSG msg2 #chan3 (11:56:34)
PRIVMSG msg3 #chan1 (11:56:44)
PRIVMSG msg3 #chan2 (11:56:54)
PRIVMSG msg3 #chan3 (11:57:04)


After this userfile will be loaded and bot starts normally. The script work as i want it to work but when i want eggdrop to send those messages to channels (make it proc {}), it won't work anymore.

I'm trying it with this code:

Code:
set channels "#chan1 #chan2 #chan3"

set messages "msg1 msg2 msg3"

proc sendmsg {} {
global channels messages

foreach message $messages {

        foreach channel $channels {

                after 10000 {
                puts "PRIVMSG $message $channel ([clock format [clock seconds] -format %H:%M:%S])"
                set ::pleasewait 1
                }

        vwait ::pleasewait

        }
}

}

::sendmsg


But when i start my eggdrop, i'm getting these errors after module loading:

Code:
can't read "message": no such variable
    while executing
"puts "PRIVMSG $message $channel ([clock format [clock seconds] -format %H:%M:%S])""
    ("after" script)
[12:41] Tcl error in file 'coixi.conf':
[12:41] can't wait for variable "::pleasewait":  would wait forever
    while executing
"vwait ::pleasewait"
    (procedure "::sendmsg" line 13)
    invoked from within
"::sendmsg"
    (file "scripts/sendmsg.tcl" line 24)
    invoked from within
"source scripts/sendmsg.tcl"
    (file "coixi.conf" line 1343)
[12:41] * CONFIG FILE NOT LOADED (NOT FOUND, OR ERROR)


I've Googled, i've been going thru these forums and tried those variables with and without global, with/without $ and with :: but i cannot get it work. Also that can't wait for variable "::pleasewait": would wait forever part is bothering me.

If someone could solve or help with this problem, i'd be happyhappyhappy Smile
Back to top
View user's profile Send private message
Sir_Fz
Revered One


Joined: 27 Apr 2003
Posts: 3793
Location: Lebanon

PostPosted: Sun Nov 12, 2006 11:50 am    Post subject: Reply with quote

Because the variable message is in the proc while the after executes outside the proc; the variable cannot be found. Instead, use the [utimer] eggdrop command.
_________________
Follow me on GitHub

- Opposing

Public Tcl scripts
Back to top
View user's profile Send private message Visit poster's website
Coixi
Voice


Joined: 12 Nov 2006
Posts: 6

PostPosted: Sun Nov 12, 2006 12:28 pm    Post subject: Reply with quote

Well, i did that but now the script sends the last message of $messages array to last channel in $channels array.

Could you place the utimer in there in a way that it works like with after? Like this:

Code:
PRIVMSG msg1 #chan1 (11:55:44)
PRIVMSG msg1 #chan2 (11:55:54)
PRIVMSG msg1 #chan3 (11:56:04)
PRIVMSG msg2 #chan1 (11:56:14)
PRIVMSG msg2 #chan2 (11:56:24)
PRIVMSG msg2 #chan3 (11:56:34)
PRIVMSG msg3 #chan1 (11:56:44)
PRIVMSG msg3 #chan2 (11:56:54)
PRIVMSG msg3 #chan3 (11:57:04)
Back to top
View user's profile Send private message
Sir_Fz
Revered One


Joined: 27 Apr 2003
Posts: 3793
Location: Lebanon

PostPosted: Sun Nov 12, 2006 12:37 pm    Post subject: Reply with quote

Code:
set messages {"msg1" "msg2" "msg3"}
set channels {#chan1 #chan2 #chan3}

proc sendmsg {} {
 global messages channels
 set i 0
 foreach message $messages {
  foreach chan $channels {
   utimer [expr {10*[incr i]}] [list puthelp "PRIVMSG $chan :$message"]
  }
 }
}

sendmsg

_________________
Follow me on GitHub

- Opposing

Public Tcl scripts
Back to top
View user's profile Send private message Visit poster's website
Coixi
Voice


Joined: 12 Nov 2006
Posts: 6

PostPosted: Sun Nov 12, 2006 1:11 pm    Post subject: Reply with quote

Works like a charm, thanks.

Is utimer/timer best way to keep this whole proc running?

Or would you suggest something else. I want this to run in a loop, when everything is foreached -> it starts again. But i don't know any good way to do so.
Back to top
View user's profile Send private message
rosc2112
Revered One


Joined: 19 Feb 2006
Posts: 1454
Location: Northeast Pennsylvania

PostPosted: Sun Nov 12, 2006 1:17 pm    Post subject: Reply with quote

This format is incorrect for eggdrop (although it may work for tclsh):
puts "PRIVMSG $message $channel ([clock format [clock seconds] -format %H:%M:%S])"

in eggdrop, you'd need to use:

puthelp "PRIVMSG $channel :$message etc"

Note the format of privmsg, the space and the colon are required in the format for irc, refer you to the rfc:

http://www.irchelp.org/irchelp/rfc/chapter4.html
Read section: 4.4.1 Private messages
Back to top
View user's profile Send private message
Sir_Fz
Revered One


Joined: 27 Apr 2003
Posts: 3793
Location: Lebanon

PostPosted: Sun Nov 12, 2006 8:24 pm    Post subject: Reply with quote

Coixi wrote:
Works like a charm, thanks.

Is utimer/timer best way to keep this whole proc running?

Or would you suggest something else. I want this to run in a loop, when everything is foreached -> it starts again. But i don't know any good way to do so.

Call the proc again after the last msg, like this:
Code:
set messages {"msg1" "msg2" "msg3"}
set channels {#chan1 #chan2 #chan3}

proc sendmsg {} {
 global messages channels
 set i 0
 foreach message $messages {
  foreach chan $channels {
   utimer [set t [expr {10*[incr i]}]] [list puthelp "PRIVMSG $chan :$message"]
  }
 }
 utimer $t sendmsg
}

sendmsg

Notice how the delay-time is stored in $t, the proc will restart when the last message is sent.
_________________
Follow me on GitHub

- Opposing

Public Tcl scripts
Back to top
View user's profile Send private message Visit poster's website
Coixi
Voice


Joined: 12 Nov 2006
Posts: 6

PostPosted: Wed Nov 15, 2006 3:01 pm    Post subject: Reply with quote

Heya,

How do i make sure that those timers won't become duplicate when i .rehash. I've seen a very simple script for that but after two hours of hardcore googling i haven't found it.

It was a if {} with some info_exists stuff but i just cannot find it.
Back to top
View user's profile Send private message
rosc2112
Revered One


Joined: 19 Feb 2006
Posts: 1454
Location: Northeast Pennsylvania

PostPosted: Wed Nov 15, 2006 4:23 pm    Post subject: Reply with quote

Code:

if {![string match "*name_of_timer*" [timers]]} {timer 5 name_of_timer}

the 5 is the number of minutes as an example..
Back to top
View user's profile Send private message
Sir_Fz
Revered One


Joined: 27 Apr 2003
Posts: 3793
Location: Lebanon

PostPosted: Wed Nov 15, 2006 5:17 pm    Post subject: Reply with quote

Read Searching and killing timers.
_________________
Follow me on GitHub

- Opposing

Public Tcl scripts
Back to top
View user's profile Send private message Visit poster's website
demond
Revered One


Joined: 12 Jun 2004
Posts: 3073
Location: San Francisco, CA

PostPosted: Thu Nov 16, 2006 5:34 am    Post subject: Reply with quote

Sir_Fz wrote:
Because the variable message is in the proc while the after executes outside the proc; the variable cannot be found. Instead, use the [utimer] eggdrop command.


there is nothing wrong with using [after] in eggdrop scripts; [utimer] was devised before [after] appeared in Tcl (circa 8.0)

of course, [vwait] usage in eggdrop is a no-no as it blocks
_________________
connection, sharing, dcc problems? click <here>
before asking for scripting help, read <this>
use [code] tag when posting logs, code
Back to top
View user's profile Send private message Visit poster's website
Sir_Fz
Revered One


Joined: 27 Apr 2003
Posts: 3793
Location: Lebanon

PostPosted: Thu Nov 16, 2006 10:30 am    Post subject: Reply with quote

Didn't say he can't use [after], simply in his case using [utimer] is better since he won't have to worry about changing environments.
_________________
Follow me on GitHub

- Opposing

Public Tcl scripts
Back to top
View user's profile Send private message Visit poster's website
demond
Revered One


Joined: 12 Jun 2004
Posts: 3073
Location: San Francisco, CA

PostPosted: Thu Nov 16, 2006 9:10 pm    Post subject: Reply with quote

Sir_Fz wrote:
Didn't say he can't use [after], simply in his case using [utimer] is better since he won't have to worry about changing environments.


actually it's the other way around - [after] is preferable in this case as it allows you to "kill timer" simply by using [after cancel] and there is no need to enumerate timers first and only then do the match & kill
_________________
connection, sharing, dcc problems? click <here>
before asking for scripting help, read <this>
use [code] tag when posting logs, code
Back to top
View user's profile Send private message Visit poster's website
Display posts from previous:   
Post new topic   Reply to topic    egghelp.org community Forum Index -> Scripting Help All times are GMT - 4 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Forum hosting provided by Reverse.net

Powered by phpBB © 2001, 2005 phpBB Group
subGreen style by ktauber