|
Joined: Apr 2003
Posts: 61
Babel fish
|
OP
Babel fish
Joined: Apr 2003
Posts: 61 |
Hello, I'm trying to read a socket with everything into just one %var But it outputs line 1 \n line 2 \n line 3 I want it like this: line 1 | line 2 | line 3 I tried this: sockread -n %data
echo -a $target $replace(%data,$crlf,|) No success.  Any ideas?
__________________________ Curiosity killed the cat.
|
|
|
|
Joined: Oct 2004
Posts: 8,330
Hoopy frood
|
Hoopy frood
Joined: Oct 2004
Posts: 8,330 |
You do not want to have your echo line in the sockread event. Or, at least, you don't want it until a check that shows you're done reading from the socket. Everything in the sockread event is done/checked for each line in the socketed file. So you are echoing after every line is read.
on *:sockread:socketname: {
sockread %data
set %output %output $chr(124) %data
}
on *:sockclose:socknetname: {
if (%output) {
echo -a %output
unset %output
}
else { echo -a No data. }
}
* This is a very basic example and probably needs "fleshed out" a bit depending on the data in the socketed file. ** If you have a LOT of text, you may have to use a binary variable instead. EDIT: I put in an error check if you have no data from the socket. It can be edited or removed as needed.
Last edited by Riamus2; 21/04/10 07:56 PM.
Invision Support #Invision on irc.irchighway.net
|
|
|
|
Joined: Apr 2003
Posts: 61
Babel fish
|
OP
Babel fish
Joined: Apr 2003
Posts: 61 |
Use a binary variable to read multiple lines into one variable. Can you show me how you would do this?
__________________________ Curiosity killed the cat.
|
|
|
|
Joined: Oct 2004
Posts: 8,330
Hoopy frood
|
Hoopy frood
Joined: Oct 2004
Posts: 8,330 |
Invision Support #Invision on irc.irchighway.net
|
|
|
|
Joined: Apr 2003
Posts: 61
Babel fish
|
OP
Babel fish
Joined: Apr 2003
Posts: 61 |
You do not want to have your echo line in the sockread event. Or, at least, you don't want it until a check that shows you're done reading from the socket. Everything in the sockread event is done/checked for each line in the socketed file. So you are echoing after every line is read.
on *:sockread:socketname: {
sockread %data
set %output %output $chr(124) %data
}
on *:sockclose:socknetname: {
if (%output) {
echo -a %output
unset %output
}
else { echo -a No data. }
}
* This is a very basic example and probably needs "fleshed out" a bit depending on the data in the socketed file. ** If you have a LOT of text, you may have to use a binary variable instead. EDIT: I put in an error check if you have no data from the socket. It can be edited or removed as needed. Thank you very much, this works!  But if I've got this %var = Show Name@House | Show URL How would I get only House out of this? I tried this and it works, but I think it's too complicated: $gettok($matchtok(%var,Show Name,1,124),2,64) Is there any simpler method?
Last edited by gaui; 21/04/10 11:54 PM.
__________________________ Curiosity killed the cat.
|
|
|
|
Joined: Apr 2010
Posts: 969
Hoopy frood
|
Hoopy frood
Joined: Apr 2010
Posts: 969 |
on *:SOCKREAD:sockname:{
if ($sockerr) { return }
:loop
if (!$sockbr) { return }
sockread &bvardata
set %sockdata %sockdata $+ $bvar(&bvardata,$bvar(&bvardata,0)).text
goto loop
}
on *:sockclose:sockname:{
if ($sockerr) { return }
echo -a %data
} Something for thought though: mIRC has a text buffer that allows only so many characters to be handled at one time. So if the page is to big you will get a "Set line to long" error
|
|
|
|
Joined: Apr 2003
Posts: 61
Babel fish
|
OP
Babel fish
Joined: Apr 2003
Posts: 61 |
on *:SOCKREAD:sockname:{
if ($sockerr) { return }
:loop
if (!$sockbr) { return }
sockread &bvardata
set %sockdata %sockdata $+ $bvar(&bvardata,$bvar(&bvardata,0)).text
goto loop
}
on *:sockclose:sockname:{
if ($sockerr) { return }
echo -a %data
} Something for thought though: mIRC has a text buffer that allows only so many characters to be handled at one time. So if the page is to big you will get a "Set line to long" error Doesn't matter, the page is never too big.
__________________________ Curiosity killed the cat.
|
|
|
|
Joined: Oct 2004
Posts: 8,330
Hoopy frood
|
Hoopy frood
Joined: Oct 2004
Posts: 8,330 |
If you are using a binary variable for the sockread, you shouldn't be using a regular variable for the data. If you stick to just binary variables, you should never get the line too long error. That's the reason for using the binary variable in the first place. Also, with binary variables, I don't think you'll need a second variable if you set it correctly. I'd have to look into it as I really don't use binary variables for anything, so don't have a lot of experience with them. And since the OP doesn't need them, I'll just leave it the way it was.
Invision Support #Invision on irc.irchighway.net
|
|
|
|
Joined: Apr 2010
Posts: 969
Hoopy frood
|
Hoopy frood
Joined: Apr 2010
Posts: 969 |
Once a script/event is done processing the bvar unsets. U can either set that data to a variable, save it in a hashtable(which has a switch for adding bvars) or use /fopen /fwrite and /close to just write it all to a file the use /bread to retrieve all the data when you're done getting the info
|
|
|
|
Joined: Apr 2010
Posts: 969
Hoopy frood
|
Hoopy frood
Joined: Apr 2010
Posts: 969 |
var %a = $regex(get,Show Name@somename,/Show Name@([^\s]+)/i)
var %var = $regml(get,1) this gets everything upto the next space after "Show Name@"
|
|
|
|
Joined: Oct 2004
Posts: 8,330
Hoopy frood
|
Hoopy frood
Joined: Oct 2004
Posts: 8,330 |
Once a script/event is done processing the bvar unsets. U can either set that data to a variable, save it in a hashtable(which has a switch for adding bvars) or use /fopen /fwrite and /close to just write it all to a file the use /bread to retrieve all the data when you're done getting the info Or, the better method... You'd put the final echo into the sockread event in an IF that checks for the end of the file.
Invision Support #Invision on irc.irchighway.net
|
|
|
|
Joined: Apr 2010
Posts: 969
Hoopy frood
|
Hoopy frood
Joined: Apr 2010
Posts: 969 |
on *:SOCKREAD:sockname:{
;loop back position
:loop
;Check for sockerr
if ($sockerr) {
;if sockerror occured, check if hashtable is opened
if ($hget($sockname)) {
;if hashtable is opened, close it
hfree $sockname
}
;if sockerr, stop processing
return
}
;read data from socket to &tmp1
sockread &tmp1
;if no data was read, stop processing
if (!$sockbr) { return }
;retrive data, if present, from the hashtable and set it to &tmp2
var %a = $hget($sockname,1,&tmp2)
;append the data that was read from the socket to the end of the stored data
bcopy -c &tmp2 $bvar(&tmp2,0) &tmp1 1 -1
;store &tmp2(old data + fresh data from socket)
hadd -mb $sockname 1 &tmp2
;loop back
goto loop
}
on *:SOCKWRITE:sockname:{
;check for socket errors
if ($sockerr) {
;if a sockerror occured, check to see if the hashtable is opened
if ($hget($sockname)) {
;free the hashtable if it's opened
hfree $sockname
}
;if a sockerr occured, stop processing
}
}
on *:sockclose:sockname:{
;check for socket errors
if ($sockerr) {
;if a sockerror occured, check to see if the hashtable is opened
if ($hget($sockname)) {
;free the hashtable if it's opened
hfree $sockname
}
;if a sockerr occured, stop processing
}
;check to see if any data was stored.
if ($hashtable($sockname)) {
;retrive data from the hashtable, and clear the hashtable
var %a = $hget($sockname,1,&tmp)
hfree $sockname
;replace all carriage-return+linefeeds with char(124) "|" (this also stops you from having multiple pipes side be side. IE: || )
var %data = $regsubex($bvar(&tmp,1,$bvar(&tmp,0)).text,/(?:\s+?\r\n\s+?)+/g,$chr(124))
;echo data out
echo -a %data
}
} I didn't test the regex so it might be off, but other than that, it's good.
Last edited by FroggieDaFrog; 23/04/10 01:55 AM.
|
|
|
|
Joined: Oct 2004
Posts: 8,330
Hoopy frood
|
Hoopy frood
Joined: Oct 2004
Posts: 8,330 |
You are once again mixing binary and non-binary variables. A main reason for using binary variables is to avoid line too long issues. If you stick a binary into a non-binary, you risk losing data and/or getting errors. Like I said, stick the echo into the sockread event and avoid unnecessary things like hash tables. They aren't needed for something like this.
if (!$sockbr) { echo -a $regsubex($bvar(&tmp,1,$bvar(&tmp,0)).text,/(?:\s+?\r\n\s+?)+/g,$chr(124)) }
That's assuming your regex is correct. I don't know regex, so have no idea. But in either case, this avoids 1) hash tables, and 2) mixing variables. And as long as you're not re-triggering the sockread (i.e. you're using a loop), the binary variable shouldn't get reset. All of that said, the OP does not appear to need binary variables and so there's no need for any of this.
Invision Support #Invision on irc.irchighway.net
|
|
|
|
Joined: Oct 2003
Posts: 3,918
Hoopy frood
|
Hoopy frood
Joined: Oct 2003
Posts: 3,918 |
Using $bvar().text converts the binary data to text, defeating the purpose of storing binary data. Converting it to text and using it in an mIRC command subjects it to the same line length issues that %vars would have, so you're right in saying there's no need for binary data here.
Just sockread %var and perform your operations on %var. *IF* the line is too long, deal with it then. There is no easy way to process large (>4k) blocks of data in mIRC, so stick to the simple case.
- argv[0] on EFnet #mIRC - "Life is a pointer to an integer without a cast"
|
|
|
|
Joined: Apr 2003
Posts: 61
Babel fish
|
OP
Babel fish
Joined: Apr 2003
Posts: 61 |
Okay, so how do I read a webpage that has: line1 line2 line3 into a %var like this: line1 | line2 | line3 ? I have something like this:
sockread %data
set %output %data $chr(124) $gettok(%data,1,13)
%output is then: line3 | line3
Last edited by gaui; 27/09/10 12:28 AM.
__________________________ Curiosity killed the cat.
|
|
|
|
Joined: Nov 2006
Posts: 1,559
Hoopy frood
|
Hoopy frood
Joined: Nov 2006
Posts: 1,559 |
sockread %data set %output %output $chr(124) $gettok(%data,1,13)
will result in: "| line1 | line2 | line3" - to get rid of the first "| ", use e.g. $mid(%output,3-)
|
|
|
|
|