sub _mk_db_closure { my ($class, $dsn, $user, $pass, $attr) = @_; $attr ||= {}; my $dbh; my $process_id = $$; return sub { # set the PID in a private cache key to prevent us # from sharing one with the parent after fork. This # is better than disconnecting the existing $dbh since # the parent may still need the connection open. Note # that forking code also needs to set InactiveDestroy # on all open handles in the child or the connection # will be broken during DESTROY. $attr->{private_cache_key_pid} = $$; # reopen if this is a new process or if the connection # is bad if ($process_id != $$ or not ($dbh && $dbh->FETCH('Active') && $dbh->ping)) { $dbh = DBI->connect_cached($dsn, $user, $pass, $attr); $process_id = $$; } return $dbh; }; }