Cookies-Roundtrip
view release on metacpan or search on metacpan
lib/Cookies/Roundtrip.pm view on Meta::CPAN
# we need to find the class of the cookie jar of mech
# this is probably unsupported but there is no other way:
my $cookie_jar_class = $ua->{'cookie_jar_class'};
my $ua_cookies;
if( ! defined($ua_cookies=$ua->cookie_jar) ){
# there is no cookiejar in $ua, make one and insert it into mech
if( ! defined($ua_cookies=$cookie_jar_class->new()) ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'HTTP::Cookies->new()'." has failed.\n"; return undef }
$ua->cookie_jar($ua_cookies);
}
# by now $ua has a cookie_jar (fresh or already there)
# and this is the cookie jar we supply to the sub below
# to load the input cookies
if( $cookie_jar_class eq 'HTTP::Cookies' ){
# we have a cookiejar entering a cookies in mech, need to convert
if( ! defined httpcookiejar2httpcookies($httpcookiejar, $ua_cookies, $skip_discard, $verbosity) ){ print STDERR "--begin HTTP::Cookies:\n".as_string_httpcookies($httpcookiejar)."\n--end cookies.\n\n"."${whoami}, line ".__LINE__." (via $parent): err...
} elsif( ($cookie_jar_class eq 'HTTP::CookieJar') || ($cookie_jar_class eq 'HTTP::CookieJar::LWP') ){
# we have the same class of cookiejar, we need to merge
if( ! defined merge_httpcookiejar($httpcookiejar, $ua_cookies, $skip_discard, $verbosity) ){ print STDERR "--begin HTTP::Cookies:\n".as_string_httpcookies($httpcookiejar)."\n--end cookies.\n\n"."${whoami}, line ".__LINE__." (via $parent): error, ca...
} else {
print STDERR "${whoami}, line ".__LINE__." (via $parent): error, input cookies type '$cookie_jar_class' is not known. Known cookies types are 'HTTP::Cookies' and 'HTTP::CookieJar'.\n";
return undef
}
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): inserted ".count_cookies($httpcookiejar, $skip_discard, $verbosity)." cookies in the input HTTP::Cookies and loaded them into the LWP::UserAgent. It now has ".count_cook...
return $ua->cookie_jar;
}
## Firefox::Marionette browser related subs
sub firefoxmarionette_get_cookies {
my ($ffmar, $verbosity) = @_;
#$verbosity //= 0;
#my $parent = ( caller(1) )[3] || "N/A";
#my $whoami = ( caller(0) )[3];
return [ $ffmar->cookies() ]
}
# Save cookies of LWP::UserAgent (they are HTTP::CookieJar)
# into a file. The file will be empty if no cookies.
# It returns 1 on failure, 0 on success.
sub firefoxmarionette_save_cookies_to_file {
my ($ffmar, $filename, $skip_discard, $verbosity) = @_;
$verbosity //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
my $cookies = firefoxmarionette_get_cookies($ffmar);
if( ! defined $cookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_get_cookies()'." has failed.\n"; return 1 }
if( firefoxmarionettecookies2file($cookies, $filename, $skip_discard, $verbosity) ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'httpcookies2file()'." has failed.\n"; return 1 }
return 0 # success
}
# Convenience method to load any kind of cookies
# or a cookies file, into the LWP::UserAgent
# it returns the $ffmar's cookies on success or undef on failure
# NOTE: firefox marionette will not load cookies unless we visit the site
# of the cookie domain. However, some sites redirect you if you
# do not ask for a full-path endpoint URL (e.g. www.abc.com/a/b/c
# instead of cookie domain www.abc.com. If you visit www.abc.com
# it may take you to cy.abc.com)
# So, parameter $visit_cookie_domain_first controls this
# if it is undef, then no visit is made,
# if '' (empty string) then it goes to the domain https://www.abc.com above
# if non-empty string it visits that URL instead, this is the most safe.
sub firefoxmarionette_load_cookies {
my ($ffmar, $cookies_or_file_etc, $visit_cookie_domain_first, $skip_discard, $verbosity) = @_;
$verbosity //= 0;
$skip_discard //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
my $r = ref($cookies_or_file_etc);
if( $r eq 'HTTP::Cookies' ){
my $ret = firefoxmarionette_load_httpcookies($ffmar, $cookies_or_file_etc, $visit_cookie_domain_first, $skip_discard, $verbosity);
if( ! defined $ret ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_httpcookies()'." has failed.\n"; return undef }
return $ret;
} elsif( ($r eq 'HTTP::CookieJar') || ($r eq 'HTTP::CookieJar::LWP') ){
my $ret = firefoxmarionette_load_httpcookiejar($ffmar, $cookies_or_file_etc, $visit_cookie_domain_first, $skip_discard, $verbosity);
if( ! defined $ret ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_httpcookiejar()'." has failed.\n"; return undef }
return $ret;
} elsif( $r eq 'ARRAY' ){
# an ARRAY_REF of cookie which can be strings as come from a server as Set-Cookie headers
# or can be an ARRAY of Firefox::Marionette::Cookie
my $ret;
if( (scalar(@$cookies_or_file_etc) > 0)
&& (ref($cookies_or_file_etc->[0])eq'Firefox::Marionette::Cookie')
){
$ret = firefoxmarionette_load_firefoxmarionettecookies(
$ffmar,
$cookies_or_file_etc,
$visit_cookie_domain_first,
$skip_discard, $verbosity
);
if( ! defined $ret ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_firefoxmarionettecookies()'." has failed.\n"; return undef }
} else {
$ret = firefoxmarionette_load_setcookies($ffmar, $cookies_or_file_etc, $visit_cookie_domain_first, $skip_discard, $verbosity);
if( ! defined $ret ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_setcookies()'." has failed.\n"; return undef }
}
return $ret;
} elsif( $r eq '' ){
# scalar means a filename
my $ret = firefoxmarionette_load_cookies_from_file($ffmar, $cookies_or_file_etc, $visit_cookie_domain_first, $skip_discard, $verbosity);
if( ! defined $ret ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_cookies_from_file()'." has failed.\n"; return undef }
return $ret;
}
# error!
print STDERR "${whoami}, line ".__LINE__." (via $parent): error, input cookies type '$r' is not known. Known cookies types are 'HTTP::Cookies' and 'HTTP::CookieJar'.\n";
return undef
}
# It loads cookies from specified file which needs
# to have this header:
# #LWP-Cookies-ZZZ.ZZZ
# and then followed by 'Set-Cookie: blahblah' lines,
# into the specified LWP::UserAgent object, appending
# cookies to it if already some there.
# It takes in the $ffmar, $filename and, optionally $verbosity (integer),
# and returns back the $ffmar's cookie jar (as HTTP::CookieJar object)
# It returns undef on failure.
# NOTE: firefox marionette will not load cookies unless we visit the site
# of the cookie domain. However, some sites redirect you if you
# do not ask for a full-path endpoint URL (e.g. www.abc.com/a/b/c
# instead of cookie domain www.abc.com. If you visit www.abc.com
# it may take you to cy.abc.com)
# So, parameter $visit_cookie_domain_first controls this
# if it is undef, then no visit is made,
# if '' (empty string) then it goes to the domain https://www.abc.com above
# if non-empty string it visits that URL instead, this is the most safe.
sub firefoxmarionette_load_cookies_from_file {
my ($ffmar, $filename, $visit_cookie_domain_first, $skip_discard, $verbosity) = @_;
$skip_discard //= 0;
$verbosity //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
my $httpcookies = file2httpcookies($filename, undef, $verbosity);
if( ! defined $httpcookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'file2httpcookies()'." has failed for cookies file '$filename'.\n"; return undef }
my $read_num_cookies = count_cookies($httpcookies, $skip_discard, $verbosity);
my $new_ffmar_cookies = httpcookies2firefoxmarionettecookies($httpcookies, undef, $skip_discard, $verbosity);
if( ! defined $new_ffmar_cookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'httpcookies2firefoxmarionettecookies()'." has failed for cookies file '$filename'.\n"; return undef }
if( ! defined firefoxmarionette_load_firefoxmarionettecookies(
$ffmar,
$new_ffmar_cookies,
$visit_cookie_domain_first,
$skip_discard,
$verbosity
) ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_firefoxmarionettecookies()'." has failed.\n"; return undef }
my $now_ffmar_cookies = firefoxmarionette_get_cookies($ffmar, $verbosity);
if( ! defined $now_ffmar_cookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_get_cookies()'." has failed.\n"; return undef }
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): loaded ${read_num_cookies} cookies into the specified Firefox::Marionette object. It now has ".count_cookies($now_ffmar_cookies, $skip_discard, $verbosity)." cookies.\n"...
return $now_ffmar_cookies;
}
# It loads the specified HTTP::Cookies object
# into the specified LWP::UserAgent object, appending
# cookies to it if already some there.
# It takes in the $ffmar, $httpcookies and, optionally $verbosity (integer),
# and returns back the $ffmar's cookie jar (as HTTP::CookieJar object)
# It returns undef on failure.
# NOTE: firefox marionette will not load cookies unless we visit the site
# of the cookie domain. However, some sites redirect you if you
# do not ask for a full-path endpoint URL (e.g. www.abc.com/a/b/c
# instead of cookie domain www.abc.com. If you visit www.abc.com
# it may take you to cy.abc.com)
# So, parameter $visit_cookie_domain_first controls this
# if it is undef, then no visit is made,
# if '' (empty string) then it goes to the domain https://www.abc.com above
# if non-empty string it visits that URL instead, this is the most safe.
sub firefoxmarionette_load_setcookies {
my ($ffmar, $setcookies, $visit_cookie_domain_first, $skip_discard, $verbosity) = @_;
$verbosity //= 0;
$skip_discard //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
my $firefoxmarionettecookies = setcookies2firefoxmarionettecookies($setcookies, undef, $verbosity);
if( ! defined $firefoxmarionettecookies ){ print STDERR "--begin cookies:\n".as_string_cookies($setcookies)."\n--end cookies.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'setcookies2firefoxmarionettecookies()'." has failed for a...
if( ! defined firefoxmarionette_load_firefoxmarionettecookies(
$ffmar,
$firefoxmarionettecookies,
$visit_cookie_domain_first,
$skip_discard,
$verbosity
) ){ print STDERR "--begin cookies:\n".as_string_cookies($setcookies)."\n--end cookies.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_firefoxmarionettecookies()'." has failed for above array of Firefox::Mar...
my $now_ffmar_cookies = firefoxmarionette_get_cookies($ffmar, $verbosity);
if( ! defined $now_ffmar_cookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_get_cookies()'." has failed.\n"; return undef }
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): loaded ".count_cookies($setcookies, $skip_discard, $verbosity)." cookies into the specified Firefox::Marionette object. It now has ".count_cookies($now_ffmar_cookies, $s...
return $now_ffmar_cookies;
}
# It loads the specified ARRAY of Firefox::Marionette::Cookie
# OR JUST A SINGLE Firefox::Marionette::Cookie object
# into the specified Firefox::Marionette browser object, appending
# cookies to it if already some there.
# It takes in the $ffmar, $firefoxmarionettecookies and, optionally $verbosity (integer),
# and returns back the $ffmar's cookie jar (as array of Firefox::Marionette::Cookie objects)
# It returns undef on failure.
# NOTE: if you have not visited a url then you can not add cookies!!!! (for firefox-marionette/firefox)
# if you have visited a url then you can add only cookies whose domain is the same as the
# current url!!! Otherwise you get error about cookie-averse document etc.
# see
# https://stackoverflow.com/questions/48352380/org-openqa-selenium-invalidcookiedomainexception-document-is-cookie-averse-usin
# So, we have an extra flag to visit the page of each cookie domain before loading it
# set $visit_cookie_domain_first to false in order not to visit (that means you are sure
# you are there already, otherwise this call will fail).
# Default is to visit first.
# NOTE: firefox marionette will not load cookies unless we visit the site
# of the cookie domain. However, some sites redirect you if you
# do not ask for a full-path endpoint URL (e.g. www.abc.com/a/b/c
# instead of cookie domain www.abc.com. If you visit www.abc.com
# it may take you to cy.abc.com)
# So, parameter $visit_cookie_domain_first controls this
# if it is undef, then no visit is made,
# if '' (empty string) then it goes to the domain https://www.abc.com above
# if non-empty string (and starts with https?://) it visits that URL instead, this is the most safe.
# BUT if you have a lot of cookies you need to load each with its own calculated url
# This is so stupid and will probably fail.
# Perhaps we can skip cookies which are failing to load and not dump core...
sub firefoxmarionette_load_firefoxmarionettecookies {
my ($ffmar, $firefoxmarionettecookies, $visit_cookie_domain_first, $skip_discard, $verbosity) = @_;
$verbosity //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
for my $acookie (
(ref($firefoxmarionettecookies) eq 'Firefox::Marionette::Cookie')
? [ $firefoxmarionettecookies ]
: @$firefoxmarionettecookies
){
my $domain = $acookie->domain;
if( ! defined($domain) || ($domain=~/^\s*$/) ){ print STDERR "--begin cookie:\n".as_string_cookies($acookie)."\n--end cookie.\n"."${whoami}, line ".__LINE__." (via $parent): error, above cookie has no domain!\n"; return undef }
my $rr;
if( defined $visit_cookie_domain_first ){
my $url;
if( $visit_cookie_domain_first eq '' ){
# visit the domain site as it is
$url = eval {
my $uri = URI->new();
$uri->scheme('https'); # i guess ... this can be a huge bug
# there may be a path else use some imaginary path
# hoping it will not redirect us OUTSIDE the domain, inside the domain is ok, cookie will be set.
$uri->path(defined($acookie->path)?$acookie->path:'a/b/c');
$uri->host($domain);
$uri->as_string;
};
if( $@ || ! $url ){ print STDERR "--begin cookie:\n".as_string_cookies($acookie)."\n--end cookie.\n"."${whoami}, line ".__LINE__." (via $parent): error, failed to create a URL from above cookie's domain".($@?": $@":".")."\n"; return undef }
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): visiting cookie's domain ($domain) to url ($url) before loading above cookie...\n" }
} elsif( $visit_cookie_domain_first =~ m!^https?\://!i ){
# we have a user-specified full url, hopefully, check it is valid
# and go there instead of the domain, this is much preferred
$url = eval {
my $uri = URI->new($visit_cookie_domain_first);
$uri->as_string;
};
if( $@ || ! $url ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, failed to create a URL from specified url parameter '${visit_cookie_domain_first}'".($@?": $@":".")."\n"; return undef }
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): visiting cookie's domain ($domain) to url ($url) before loading above cookie...\n" }
} else { print STDERR "${whoami}, line ".__LINE__." (via $parent): error, parameter 'visit_cookie_domain_first' was not understood ($visit_cookie_domain_first).\n"; return undef }
$rr = eval { $ffmar->go($url) };
if( $@ || ! $rr ){ print STDERR "--begin cookie:\n".as_string_cookies($acookie)."\n--end cookie.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'Firefox::Marionette::go()'." has failed for above cookie and url ($url). Warning: th...
}
$rr = eval { $ffmar->add_cookie($acookie) };
if( $@ || ! $rr ){
print STDERR "--begin cookie:\n".as_string_cookies($acookie)."\n--end cookie.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'Firefox::Marionette::add_cookie()'." has failed for above cookie but will continue with the others".($@...
# ignoring errors!
#return undef
}
}
my $now_ffmar_cookies = firefoxmarionette_get_cookies($ffmar, $verbosity);
if( ! defined $now_ffmar_cookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_get_cookies()'." has failed.\n"; return undef }
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): loaded ".count_cookies($firefoxmarionettecookies, $skip_discard, $verbosity)." cookies into the specified Firefox::Marionette object. It now has ".count_cookies($now_ffm...
return $now_ffmar_cookies;
}
# It loads the specified HTTP::Cookies object
# into the specified LWP::UserAgent object, appending
# cookies to it if already some there.
# It takes in the $ffmar, $httpcookies and, optionally $verbosity (integer),
# and returns back the $ffmar's cookie jar (as array of Firefox::Marionette::Cookie object)
# It returns undef on failure.
# NOTE: firefox marionette will not load cookies unless we visit the site
# of the cookie domain. However, some sites redirect you if you
# do not ask for a full-path endpoint URL (e.g. www.abc.com/a/b/c
# instead of cookie domain www.abc.com. If you visit www.abc.com
# it may take you to cy.abc.com)
# So, parameter $visit_cookie_domain_first controls this
# if it is undef, then no visit is made,
# if '' (empty string) then it goes to the domain https://www.abc.com above
# if non-empty string it visits that URL instead, this is the most safe.
sub firefoxmarionette_load_httpcookies {
my ($ffmar, $httpcookies, $visit_cookie_domain_first, $skip_discard, $verbosity) = @_;
$skip_discard //= 0;
$verbosity //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
my $firefoxmarionettecookies = httpcookies2firefoxmarionettecookies($httpcookies, undef, $verbosity);
if( ! defined $firefoxmarionettecookies ){ print STDERR "--begin cookies:\n".as_string_cookies($httpcookies)."\n--end cookies.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'httpcookies2firefoxmarionettecookies()'." has failed for...
if( ! defined firefoxmarionette_load_firefoxmarionettecookies(
$ffmar,
$firefoxmarionettecookies,
$visit_cookie_domain_first,
$skip_discard,
$verbosity
) ){ print STDERR "--begin cookies:\n".as_string_cookies($httpcookies)."\n--end cookies.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_firefoxmarionettecookies()'." has failed for above array of Firefox::Ma...
my $now_ffmar_cookies = firefoxmarionette_get_cookies($ffmar, $verbosity);
if( ! defined $now_ffmar_cookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_get_cookies()'." has failed.\n"; return undef }
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): loaded ".count_cookies($httpcookies, $skip_discard, $verbosity)." cookies into the specified Firefox::Marionette object. It now has ".count_cookies($now_ffmar_cookies, $...
return $now_ffmar_cookies;
}
# It loads the specified HTTP::CookieJar object
# into the specified LWP::UserAgent object, appending
# cookies to it if already some there.
# It takes in the $ffmar, $httpcookiejar and, optionally $verbosity (integer),
# and returns back the $ffmar's cookie jar (as HTTP::CookieJar object)
# If the $ffmar has no cookie jar then the supplied cookie jar will be
# first cloned and then into $ffmar.
# So the input $httpcookiejar will be independent of the one in $ffmar.
# It returns undef on failure.
# NOTE: firefox marionette will not load cookies unless we visit the site
# of the cookie domain. However, some sites redirect you if you
# do not ask for a full-path endpoint URL (e.g. www.abc.com/a/b/c
# instead of cookie domain www.abc.com. If you visit www.abc.com
# it may take you to cy.abc.com)
# So, parameter $visit_cookie_domain_first controls this
# if it is undef, then no visit is made,
# if '' (empty string) then it goes to the domain https://www.abc.com above
# if non-empty string it visits that URL instead, this is the most safe.
sub firefoxmarionette_load_httpcookiejar {
my ($ffmar, $httpcookiejar, $visit_cookie_domain_first, $skip_discard, $verbosity) = @_;
$skip_discard //= 0;
$verbosity //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
my $firefoxmarionettecookies = httpcookiejar2firefoxmarionettecookies($httpcookiejar, undef, $verbosity);
if( ! defined $firefoxmarionettecookies ){ print STDERR "--begin cookies:\n".as_string_cookies($httpcookiejar)."\n--end cookies.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'httpcookiejar2firefoxmarionettecookies()'." has failed...
if( ! defined firefoxmarionette_load_firefoxmarionettecookies(
$ffmar,
$firefoxmarionettecookies,
$visit_cookie_domain_first,
$skip_discard,
$verbosity
) ){ print STDERR "--begin cookies:\n".as_string_cookies($httpcookiejar)."\n--end cookies.\n"."${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_load_firefoxmarionettecookies()'." has failed for above array of Firefox::...
my $now_ffmar_cookies = firefoxmarionette_get_cookies($ffmar, $verbosity);
if( ! defined $now_ffmar_cookies ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'firefoxmarionette_get_cookies()'." has failed.\n"; return undef }
if( $verbosity > 0 ){ print STDOUT "${whoami}, line ".__LINE__." (via $parent): loaded ".count_cookies($httpcookiejar)." cookies into the specified Firefox::Marionette object. It now has ".count_cookies($now_ffmar_cookies)." cookies.\n" }
return $now_ffmar_cookies;
}
## WWW::Mechanize browser related subs
sub wwwmechanize_get_cookies {
my ($mech, $verbosity) = @_;
#$verbosity //= 0;
#my $parent = ( caller(1) )[3] || "N/A";
#my $whoami = ( caller(0) )[3];
return $mech->cookie_jar
}
# Save cookies of WWW::Mechanize::ANY (they are HTTP::Cookies)
# into a file. The file will be empty if no cookies.
# It returns 1 on failure, 0 on success.
sub wwwmechanize_save_cookies_to_file {
my ($mech, $filename, $skip_discard, $verbosity) = @_;
$verbosity //= 0;
my $parent = ( caller(1) )[3] || "N/A";
my $whoami = ( caller(0) )[3];
# WWW::Mechanize::* supports both HTTP::Cookies and HTTP::CookieJar
# cookie jars (depending on the 'cookie_jar_class' param to their constructor)
# we need to find the class of the cookie jar of mech
# this is probably unsupported but there is no other way:
my $cookie_jar_class = $mech->{'cookie_jar_class'};
if( $cookie_jar_class eq 'HTTP::Cookies' ){
if( httpcookies2file(
defined($mech->cookie_jar) ? $mech->cookie_jar : $cookie_jar_class->new(),
$filename, $skip_discard, $verbosity
) ){ print STDERR "${whoami}, line ".__LINE__." (via $parent): error, call to ".'httpcookies2file()'." has failed.\n"; return 1 }
( run in 0.640 second using v1.01-cache-2.11-cpan-c966e8aa7e8 )