Resolve Net::MySQL Hang problem if the database result has only 1 row or is empty
Net::MySQL is a simple MySQL perl Client to connect to MySQL servers. But Net::MySQL hangs if your result set is having just one row.
Sample Net::MySQL code
#!/usr/bin/perl use Net::MySQL; $mysql = Net::MySQL->new( hostname => 'localhost', database => 'db', user => 'user', password => 'password', ); $gid = 1; $mysql->query('SELECT * FROM table WHERE id = 1'); if ($mysql->has_selected_record) { my $record_set = $mysql->create_record_iterator; while(my $record = $record_set->each) { printf "First column: %s \n", $record->[0]; } } else { print "not found"; } $mysql->close;
This script would hang since the result set contains just one row. This is due to incorrect detection of the end of packet message on Net::MySQL module. The last 5 bytes of the end of packet is usually FE 00 00 22 00. If the result set is having just one row MySQL returns FE 00 00 02 00. The function on Net::MySQL package checks for end of packet and fails to find if the result set has only 1 row.
# Line 460 sub _has_next_packet { my $self = shift; return substr($_[0], -5) ne "\xfe\0\0\x22\x00"; }
Thus the Perl module loops back and waits for more data from the server, thus the blocking socket call to recv
makes the script hang.
Solve Net::MySQL Hanging Problem
In order to solve this problem use the following function to replace the MySQL.pm function : _has_next_packet.
sub _has_next_packet { my $self = shift; return (substr($_[0], -5) ne "\xfe\0\0\x02\x00" and substr($_[0], -5) ne "\xfe\0\0\x22\x00"); }
Now the script with Net::MySQL module should not hang

Comments
Post new comment