diff --git a/.gitignore b/.gitignore index 6213c09..a070e34 100644 --- a/.gitignore +++ b/.gitignore @@ -9,4 +9,5 @@ data/friday/** data/karma/** data/telegrambot-brains/** data/lat/** +data/image/** vendor_perl/** diff --git a/lib/botlib.pm b/lib/botlib.pm index bb78b7e..cc9854e 100644 --- a/lib/botlib.pm +++ b/lib/botlib.pm @@ -69,8 +69,8 @@ sub command { my $city = substr $text, 3; $reply = weather $city; } elsif (substr ($text, 1) eq 'cat' || substr ($text, 1) eq 'кис') { - $reply = kitty (); $msg->typing (); + $reply = kitty (); sleep (irand (2) + 1); $msg->replyMd ($reply); return; @@ -92,8 +92,8 @@ sub command { $reply = karmaGet ($chatid, $mytext); } elsif (substr ($text, 1) eq 'fox' || substr ($text, 1) eq 'лис') { - $reply = fox (); $msg->typing (); + $reply = fox (); sleep (irand (2) + 1); $msg->replyMd ($reply); return; @@ -116,8 +116,8 @@ sub command { substr ($text, 1) eq 'сисечки' ) { if (pluginEnabled $chatid, 'oboobs') { - $reply = oboobs (); $msg->typing (); + $reply = oboobs (); sleep (irand (2) + 1); $msg->replyMd ($reply); } @@ -131,8 +131,8 @@ sub command { substr ($text, 1) eq 'попка' ) { if (pluginEnabled $chatid, 'obutts') { - $reply = obutts (); $msg->typing (); + $reply = obutts (); sleep (irand (2) + 1); $msg->replyMd ($reply); } @@ -145,14 +145,14 @@ sub command { $msg->replyMd ($reply); return; } elsif (substr ($text, 1) eq 'dig' || substr ($text, 1) eq 'копать') { - $reply = dig $highlight; $msg->typing (); + $reply = dig $highlight; sleep (irand (2) + 1); $msg->replyMd ($reply); return; } elsif (substr ($text, 1) eq 'fish' || substr ($text, 1) eq 'fishing' || substr ($text, 1) eq 'рыба' || substr ($text, 1) eq 'рыбка' || substr ($text, 1) eq 'рыбалка' ) { - $reply = fish $highlight; $msg->typing (); + $reply = fish $highlight; sleep (irand (2) + 1); $msg->replyMd ($reply); return; diff --git a/lib/image.pm b/lib/image.pm index a335c85..345825e 100644 --- a/lib/image.pm +++ b/lib/image.pm @@ -14,6 +14,7 @@ use Math::Random::Secure qw (irand); use SQLite_File; use conf qw (loadConf); use flickr qw (flickr_by_tags); +use imgur qw (imgur); use util qw (urlencode); use version; our $VERSION = qw (1.0); @@ -22,10 +23,6 @@ our @EXPORT_OK = qw (kitty fox oboobs obutts rabbit owl); my $c = loadConf (); my $dir = $c->{image}->{dir}; -my $imgur_client_id = $c->{image}->{imgur}->{client_id}; -my $imgur_client_secret = $c->{image}->{imgur}->{client_secret}; -my $imgur_access_token = $c->{image}->{imgur}->{access_token};; -my $imgur_refresh_token = $c->{image}->{imgur}->{refresh_token}; sub kitty { my $r; @@ -167,142 +164,6 @@ sub obutts { return $ret; } -sub imgur { - my $tag = shift; - - my $refresh_url = 'https://api.imgur.com/oauth2/token'; - my $search_url = 'https://api.imgur.com/3/gallery/search/'; - my $http = HTTP::Tiny->new (timeout => 5); - - # load all tokens from api secrets db - my $backingfile = sprintf '%s/secrets.sqlite', $dir; - - unless (-d $dir) { - make_path ($dir) or do { - cluck "Unable to create $dir: $OS_ERROR"; - return undef; - }; - } - - tie my %secret, 'SQLite_File', $backingfile || do { - cluck "[ERROR] Unable to tie to $backingfile: $OS_ERROR"; - return undef; - }; - - # if there is no access_token in db - put there one from config - if (defined $secret{imgur_access_token}) { - $imgur_access_token = $secret{imgur_access_token}; - } else { - $secret{imgur_access_token} = $imgur_access_token; - } - - # if there is no refresh_token in db - put there one from config - if (defined $secret{imgur_refresh_token}) { - $imgur_refresh_token = $secret{imgur_refresh_token}; - } else { - $secret{imgur_refresh_token} = $imgur_refresh_token; - } - - # query api - my $r = $http->get ( - $search_url . $tag, - { - headers => { - Authorization => "Bearer $imgur_access_token" - } - } - ); - - # looks like we need to refresh token - if (($r->{status} == 401) || ($r->{status} == 403)) { - $r = $http->post_form ( - $refresh_url, - { - refresh_token => $imgur_refresh_token, - client_id => $imgur_client_id, - clinent_secret => $imgur_client_secret, - grant_type => 'refresh_token', - } - ); - - unless ($r->{success}) { - cluck "Unable to refresh imgur token, please re-authorise app! or imgur experiencing api outage: $r->{status} $r->{content}"; - untie %secret; - return undef; - } - - my $refresh = eval { decode_json $r->{content} }; - - if (defined $refresh) { - $imgur_refresh_token = $refresh->{refresh_token}; - $secret{imgur_refresh_token} = $refresh->{refresh_token}; - $imgur_access_token = $refresh->{access_token}; - $secret{imgur_access_token} = $refresh->{access_token}; - } else { - cluck "Unable to refresh imgur access_token, unable to decode json: $EVAL_ERROR"; - untie %secret; - return undef; - } - - # query api again - $r = $http->get ( - $search_url . $tag, - { - headers => { - Authorization => "Bearer $imgur_access_token" - } - } - ); - } - - untie %secret; - - if ($r->{success}) { - my $searchResult = eval { decode_json ($r->{content}) }; - my @urls; - - if (defined $searchResult) { - if ($searchResult->{success}) { - foreach my $item (@{$searchResult->{data}}) { - foreach my $image (@{$item->{images}}) { - if (defined ($image->{animated}) && (0 + $image->{animated}) != 0) { - next; - } - - if (($image->{type} eq 'image/jpeg') || ($image->{type} eq 'image/png')) { - if (defined ($image->{is_ad}) && (0 + $image->{is_ad}) !=0) { - next; - } - - if (defined ($image->{nsfw}) && (0 + $image->{nsfw}) != 0) { - next; - } - - push @urls, $image->{link}; - } - } - } - - if ($#urls > 0) { - return $urls[irand ($#urls + 1)]; - } else { - cluck 'Imgur api returned empty result.'; - return undef; - } - } else { - cluck "Unable to get results from imgur api: $r->{content}"; - return undef; - } - } else { - cluck "Unable to decode imgur api json: $EVAL_ERROR"; - return undef; - } - } else { - cluck "Unable to get results from imgur api: $r->{status}, $r->{content}"; - return undef; - } -} - # It works but results are not particulary relevant, partially. about 20-30% miss # So i prefer to use flickr rabbits selection :) sub rabbit_imgur { @@ -311,7 +172,7 @@ sub rabbit_imgur { urlencode 'year?q=animals AND (rabbits OR bunnies)', urlencode 'relevance?q=animals AND (rabbits OR bunnies)', urlencode 'relevance/year?q=animals AND (rabbits OR bunnies)', - urlencode 'score?q_not=cat OR kitten OR kittens OR dog OR cats OR dogs OR puppy OR puppies&q_tags=bunnies,bunny,rabbits,rabbit' + urlencode 'score?q_not=cat OR kitten OR kittens OR dog OR cats OR dogs OR puppy OR puppies&q_tags=bunnies,bunny,rabbits,rabbit', ); my $rabbit = imgur ($terms[irand ($#terms + 1)]); diff --git a/lib/imgur.pm b/lib/imgur.pm new file mode 100644 index 0000000..5739bdf --- /dev/null +++ b/lib/imgur.pm @@ -0,0 +1,164 @@ +package imgur; + +use 5.018; +use strict; +use warnings; +use utf8; +use open qw (:std :utf8); +use English qw ( -no_match_vars ); +use Carp qw (cluck); +use File::Path qw (make_path); +use JSON::XS; +use HTTP::Tiny; +use Math::Random::Secure qw (irand); +use SQLite_File; +use conf qw (loadConf); + +use version; our $VERSION = qw (1.0); +use Exporter qw (import); +our @EXPORT_OK = qw (imgur); + +my $c = loadConf (); +my $dir = $c->{image}->{dir}; +my $imgur_client_id = $c->{image}->{imgur}->{client_id}; +my $imgur_client_secret = $c->{image}->{imgur}->{client_secret}; +my $imgur_access_token = $c->{image}->{imgur}->{access_token};; +my $imgur_refresh_token = $c->{image}->{imgur}->{refresh_token}; + +sub imgur { + my $tag = shift; + + my $refresh_url = 'https://api.imgur.com/oauth2/token'; + my $search_url = 'https://api.imgur.com/3/gallery/search/'; + my $http = HTTP::Tiny->new (timeout => 5); + + # load all tokens from api secrets db + my $backingfile = sprintf '%s/secrets.sqlite', $dir; + + unless (-d $dir) { + make_path ($dir) or do { + cluck "Unable to create $dir: $OS_ERROR"; + return undef; + }; + } + + tie my %secret, 'SQLite_File', $backingfile || do { + cluck "[ERROR] Unable to tie to $backingfile: $OS_ERROR"; + return undef; + }; + + # if there is no access_token in db - put there one from config + if (defined $secret{imgur_access_token}) { + $imgur_access_token = $secret{imgur_access_token}; + } else { + $secret{imgur_access_token} = $imgur_access_token; + } + + # if there is no refresh_token in db - put there one from config + if (defined $secret{imgur_refresh_token}) { + $imgur_refresh_token = $secret{imgur_refresh_token}; + } else { + $secret{imgur_refresh_token} = $imgur_refresh_token; + } + + # query api + my $r = $http->get ( + $search_url . $tag, + { + headers => { + Authorization => "Bearer $imgur_access_token" + } + } + ); + + # looks like we need to refresh token + if (($r->{status} == 401) || ($r->{status} == 403)) { + $r = $http->post_form ( + $refresh_url, + { + refresh_token => $imgur_refresh_token, + client_id => $imgur_client_id, + clinent_secret => $imgur_client_secret, + grant_type => 'refresh_token', + } + ); + + unless ($r->{success}) { + cluck "Unable to refresh imgur token, please re-authorise app! or imgur experiencing api outage: $r->{status} $r->{content}"; + untie %secret; + return undef; + } + + my $refresh = eval { decode_json $r->{content} }; + + if (defined $refresh) { + $imgur_refresh_token = $refresh->{refresh_token}; + $secret{imgur_refresh_token} = $refresh->{refresh_token}; + $imgur_access_token = $refresh->{access_token}; + $secret{imgur_access_token} = $refresh->{access_token}; + } else { + cluck "Unable to refresh imgur access_token, unable to decode json: $EVAL_ERROR"; + untie %secret; + return undef; + } + + # query api again + $r = $http->get ( + $search_url . $tag, + { + headers => { + Authorization => "Bearer $imgur_access_token" + } + } + ); + } + + untie %secret; + + if ($r->{success}) { + my $searchResult = eval { decode_json ($r->{content}) }; + my @urls; + + if (defined $searchResult) { + if ($searchResult->{success}) { + foreach my $item (@{$searchResult->{data}}) { + foreach my $image (@{$item->{images}}) { + if (defined ($image->{animated}) && (0 + $image->{animated}) != 0) { + next; + } + + if (($image->{type} eq 'image/jpeg') || ($image->{type} eq 'image/png')) { + if (defined ($image->{is_ad}) && (0 + $image->{is_ad}) !=0) { + next; + } + + if (defined ($image->{nsfw}) && (0 + $image->{nsfw}) != 0) { + next; + } + + push @urls, $image->{link}; + } + } + } + + if ($#urls > 0) { + return $urls[irand ($#urls + 1)]; + } else { + cluck 'Imgur api returned empty result.'; + return undef; + } + } else { + cluck "Unable to get results from imgur api: $r->{content}"; + return undef; + } + } else { + cluck "Unable to decode imgur api json: $EVAL_ERROR"; + return undef; + } + } else { + cluck "Unable to get results from imgur api: $r->{status}, $r->{content}"; + return undef; + } +} + +1; \ No newline at end of file