This is the new home of the egghelp.org community forum.
All data has been migrated (including user logins/passwords) to a new phpBB version.


For more information, see this announcement post. Click the X in the top right-corner of this box to dismiss this message.

reading lines from a file

Old posts that have not been replied to for several years.
Locked
s
simonbell
Halfop
Posts: 68
Joined: Mon Aug 05, 2002 8:07 pm
Location: Washington, England
Contact:

reading lines from a file

Post by simonbell »

Hi

i have a script which reads all the lines from a file and outputs them:
proc msg_listpassreqs {nick uhost hand arg} {
global botnick requestpassfile
putnotc $nick "Listing Password Requests"
set fileread [open $requestpassfile r]
while {![eof $fileread] } {
foreach listing [gets $fileread line] {
set subtime [lindex $line 0]
set subnick [lindex $line 1]
set uhost [lindex $line 2]
set handle [lindex $line 3]
set regemail [lindex $line 4]
set newpass [lindex $line 5]
putlog "Submitted: \[Time:\] [ctime $subtime] \[Nick:\] $subnick \[Uhost:\] $uhost \[Handle:\] $hand \[RegEmail:\] $regemail \[NewPass:\] $newpass"
}
}
close $fileread
}
This does work, and outputs the 2 lines of information in the file, but with one problem:
<h4> [18:38] Submitted: [Time:] Sat Sep 21 22:08:34 2002 [Nick:] notbad [Uhost:] aooi58@usercf098.dsl.pipex.com [Handle:] Simon [RegEmail:] a@b.com [NewPass:] test
<h4> [18:38] Submitted: [Time:] Tue Oct 8 17:53:44 2002 [Nick:] bob [Uhost:] aooi58@usercf098.dsl.pipex.com [Handle:] Simon [RegEmail:] aooi58@dsl.pipex.com [NewPass:] test
<h4> [18:38] Submitted: [Time:] Thu Jan 1 00:00:00 1970 [Nick:] [Uhost:] [Handle:] Simon [RegEmail:] [NewPass:]
What am i doing wrong which is making it produce the bottom line?

thanks
Simon
p
ppslim
Revered One
Posts: 3914
Joined: Sun Sep 23, 2001 8:00 pm
Location: Liverpool, England

Post by ppslim »

You are testing for an eof, before it can occur.

EG.

1 Line in a file. The order the code is done.

Open file
Is file EOF
No, then read line 1
Output line 1
Loop
Is file EOF
No, read line 2. File is EOF, set EOF flag
Output line 2 (blank data)
Loop
Is file EOF
Yes, exit loop.

The EOF status is not set, until read or gets receives it.

A better method is to forget the while loop for reading the file.

Use read, to grab the whole of the file, so it can be closed right away, without worrying about EOF.
s
simonbell
Halfop
Posts: 68
Joined: Mon Aug 05, 2002 8:07 pm
Location: Washington, England
Contact:

Post by simonbell »

ok so when i output the whole file using read and i put it into a "putlog" it outputs
<h4> [14:28] bell_dead 1032646114 ****** aooi58@usercf098.dsl.pipex.com bob a@b.com ******
<h4> 1034099624 bob aooi58@usercf098.dsl.pipex.com moo aooi58@dsl.pipex.com ******
<h4> Submitted: 1034432741 Nick: bell_dead Address: aooi58@usercf098.dsl.pipex.com Handle: test3 RegEmail: a@b.com NewPass: ******
<h4> Submitted: Thu Jan 1 00:00:00 1970 Nick: bell_dead Address: aooi58@usercf098.dsl.pipex.com Handle: test2 RegEmail: a@b.com NewPass: ******
however, when i put it into a notice to the user, only the first line is output to the user. How can i rectify this?

Simon
s
spyda
Halfop
Posts: 64
Joined: Mon Aug 12, 2002 2:22 am
Location: Australia

This might help.

Post by spyda »

To start with you need to set where the file is on the box

Code: Select all

set file "/path/to/where/it/is"
That will tell the eggdrop where the file is located, and is set to a global value but can also be done within the script too.

Next is to open the file read the data and set it in a string so that you can send the infomation to anyone or use it to find out something else.

Code: Select all

set open_file [open $file/$filename.txt r]
set read_info [read $open_file]
Now all the findo that was located in $filename.txt in set into value $read_info. For there you can do many things with it. For what you are after here is a simple soulation.

Code: Select all

puthelp "NOTICE $nick :$read_info"
Now to write a little tcl to work it all, you would make it a little like this.

Code: Select all


set asus(file) "/eggdrop/scripts"
bind MSG - text asus_text
 
proc asus_text {nick uhost hand vasus} {
  global asus
  set asus_open [open $asus(file)/text.txt r]
  set asus_read [read $asus_open]
  close $asus_open
  puthelp "NOTICE $nick :$asus_read"
}
Have fun

------------
ThePope
s
simonbell
Halfop
Posts: 68
Joined: Mon Aug 05, 2002 8:07 pm
Location: Washington, England
Contact:

Post by simonbell »

i am actually already using this code:
proc msg_listpassreqs {nick uhost hand args} {
global botnick requestpassfile
putnotc $nick "Listing Password Requests"
set fileread [open $requestpassfile r]
set all [read $fileread]
close $fileread
puthelp "NOTICE $nick :$all"
}
which is pretty similar. It obviously knows where the file is because it reads at least one line from it. However, it does not read more than one line, eg.
-H4- Listing Password Requests
-H4- 1032646114 notbad aooi58@usercf098.dsl.pipex.com bob a@b.com *****
is all it outputs when i know there are 4 lines in the file to read, and if i replace notice with putlog, all 4 lines are output.

Simon
p
ppslim
Revered One
Posts: 3914
Joined: Sun Sep 23, 2001 8:00 pm
Location: Liverpool, England

Post by ppslim »

IRC servers use a \n to signify the end of a command.

As such, the read command reads all available data, int he case of a file, the whole file.

This ifnormation will include the \n's. As uch,t he IRC server will barf error for each line that isn't prepended with the command.

Thus, you need to split the input from read (using split), to create list (use \n as the split character). Then you can cycle through each element in the list, using foreach, and output it to the user the correct way.

something like

Code: Select all

foreach line [split [read $filepointer] \n] {
  puthelp "PRIVMSG $chan :$line"
}
s
simonbell
Halfop
Posts: 68
Joined: Mon Aug 05, 2002 8:07 pm
Location: Washington, England
Contact:

Post by simonbell »

that worked thanks.

Now i am trying to search through the same file for a specific handle. The handle will be found at [lindex $arg 10] on each line. I could obviously use the same method of reading the whole file then going through each line and checking whether what i input is the same as $arg 10. But once i find that, how would i find which line number in the file this match occurs at, and how do i then tell it to remove the line from the file altogether, i cant seem to find the last part about removing lines in the tutorial ive been going through. Or would i have to employ a different method altogether?

~ Simon
d
darko``
Op
Posts: 121
Joined: Sun Sep 08, 2002 5:33 pm
Location: Malta

Post by darko`` »

Kernel will not allow what you want. File has to be rewritten completely. A simple

set readfd [open file r]
set writefd [open file.tmp w]
while (1) {
set blah [gets $readfd]
if {[eof $readfd]} { break }
if {$blah not match something} {puts $writefd $blah}
}
close $writefd
close $readfd
mv file.tmp file
Ignorant and lazy people will save 30 minutes by chosing simple config file. Smart ones will save 3000 minutes of *everyone's* time by opting for complete config file.
Locked