ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/Coro-Mysql/Mysql.pm
(Generate patch)

Comparing Coro-Mysql/Mysql.pm (file contents):
Revision 1.8 by root, Thu Jan 13 12:08:56 2011 UTC vs.
Revision 1.11 by root, Sun Feb 20 10:35:10 2011 UTC

34 34
35If you make sure that you never run two or more requests in parallel, you 35If you make sure that you never run two or more requests in parallel, you
36can freely share the database handles between threads, of course. 36can freely share the database handles between threads, of course.
37 37
38Also, this module uses a number of "unclean" techniques (patching an 38Also, this module uses a number of "unclean" techniques (patching an
39internal libmysql structure for one thing) and was hacked within a few 39internal libmysql structure for one thing) and was initially hacked within
40hours on a long flight to Malaysia. 40a few hours on a long flight to Malaysia.
41 41
42It does, however, check whether it indeed got the structure layout 42It does, however, check whether it indeed got the structure layout
43correct, so you should expect perl exceptions or early crashes as opposed 43correct, so you should expect perl exceptions or early crashes as opposed
44to data corruption when something goes wrong during patching. 44to data corruption when something goes wrong during patching.
45 45
46=head2 SPEED 46=head2 SPEED
47 47
48This module is implemented in XS, and as long as mysqld replies quickly 48This module is implemented in XS, and as long as mysqld replies quickly
49enough, it adds no overhead to the standard libmysql communication 49enough, it adds no overhead to the standard libmysql communication
50routines (which are very badly written, btw.). 50routines (which are very badly written, btw.). In fact, since it has a
51more efficient buffering and allows requests to run in parallel, it often
52decreases the actual time to run many queries considerably.
51 53
52For very fast queries ("select 0"), this module can add noticable overhead 54For very fast queries ("select 0"), this module can add noticable overhead
53(around 15%) as it tries to switch to other coroutines when mysqld doesn't 55(around 15%, 7% when EV can be used) as it tries to switch to other
54deliver the data instantly. 56coroutines when mysqld doesn't deliver the data immediately, although,
57again, when running queries in parallel, they will usually execute faster.
55 58
56For most types of queries, there will be no extra latency, especially on 59For most types of queries, there will be no extra latency, especially on
57multicore systems where your perl process can do other things while mysqld 60multicore systems where your perl process can do other things while mysqld
58does its stuff. 61does its stuff.
59 62
62This module only supports "standard" mysql connection handles - this 65This module only supports "standard" mysql connection handles - this
63means unix domain or TCP sockets, and excludes SSL/TLS connections, named 66means unix domain or TCP sockets, and excludes SSL/TLS connections, named
64pipes (windows) and shared memory (also windows). No support for these 67pipes (windows) and shared memory (also windows). No support for these
65connection types is planned, either. 68connection types is planned, either.
66 69
70=head1 CANCELLATION
71
72Cancelling a thread that is within a mysql query will likely make the
73handle unusable. As far as Coro::Mysql is concerned, the handle can be
74safely destroyed, but it's not clear how mysql itself will react to a
75cancellation.
76
67=head1 FUNCTIONS 77=head1 FUNCTIONS
68 78
69Coro::Mysql offers a single user-accessible function: 79Coro::Mysql offers a single user-accessible function:
70 80
71=over 4 81=over 4
79 89
80use Scalar::Util (); 90use Scalar::Util ();
81use Carp qw(croak); 91use Carp qw(croak);
82 92
83use Guard; 93use Guard;
94use AnyEvent ();
84use Coro::Handle (); 95use Coro ();
96use Coro::AnyEvent (); # not necessary with newer Coro versions
85 97
86# we need this extra indirection, as Coro doesn't support 98# we need this extra indirection, as Coro doesn't support
87# calling SLF-like functions via call_sv. 99# calling SLF-like functions via call_sv.
88 100
89sub readable { &Coro::Handle::FH::readable } 101sub readable { &Coro::Handle::FH::readable }
90sub writable { &Coro::Handle::FH::writable } 102sub writable { &Coro::Handle::FH::writable }
91 103
92BEGIN { 104BEGIN {
93 our $VERSION = '1.02'; 105 our $VERSION = '1.1';
94 106
95 require XSLoader; 107 require XSLoader;
96 XSLoader::load Coro::Mysql::, $VERSION; 108 XSLoader::load Coro::Mysql::, $VERSION;
97} 109}
98 110
107It is safe to call this function on any database handle (or just about any 119It is safe to call this function on any database handle (or just about any
108value), but it will only do anything to L<DBD::mysql> handles, others are 120value), but it will only do anything to L<DBD::mysql> handles, others are
109returned unchanged. That means it is harmless when applied to database 121returned unchanged. That means it is harmless when applied to database
110handles of other databases. 122handles of other databases.
111 123
124It is also safe to pass C<undef>, so code like this is works as expected:
125
126 my $dbh = DBI->connect ($database, $user, $pass)->Coro::Mysql::unblock
127 or die $DBI::errstr;
128
112=cut 129=cut
113 130
114sub unblock { 131sub unblock {
115 my ($DBH) = @_; 132 my ($DBH) = @_;
116 133
117 if ($DBH->{Driver}{Name} eq "mysql") { 134 if ($DBH && $DBH->{Driver}{Name} eq "mysql") {
118 my $sock = $DBH->{sock}; 135 my $sock = $DBH->{sock};
119 136
120 open my $fh, "+>&" . $DBH->{sockfd} 137 open my $fh, "+>&" . $DBH->{sockfd}
121 or croak "Coro::Mysql unable to clone mysql fd"; 138 or croak "Coro::Mysql unable to clone mysql fd";
122 139
140 if (AnyEvent::detect ne "AnyEvent::Impl::EV" || !_use_ev) {
141 require Coro::Handle;
123 $fh = Coro::Handle::unblock $fh; 142 $fh = Coro::Handle::unblock ($fh);
143 }
124 144
125 _patch $sock, $DBH->{sockfd}, $fh, tied ${$fh}; 145 _patch $sock, $DBH->{sockfd}, $fh, tied ${$fh};
126 } 146 }
127 147
128 $DBH 148 $DBH
145 use PApp::SQL; 165 use PApp::SQL;
146 166
147 sub with_db($$$&) { 167 sub with_db($$$&) {
148 my ($database, $user, $pass, $cb) = @_; 168 my ($database, $user, $pass, $cb) = @_;
149 169
150 my $dbh = Coro::Mysql::unblock DBI->connect ($database, $user, $pass) 170 my $dbh = DBI->connect ($database, $user, $pass)->Coro::Mysql::unblock
151 or die $DBI::errstr; 171 or die $DBI::errstr;
152 172
153 Coro::on_enter { $PApp::SQL::DBH = $dbh }; 173 Coro::on_enter { $PApp::SQL::DBH = $dbh };
154 174
155 $cb->(); 175 $cb->();

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines