File Coverage

blib/lib/Games/Lacuna/Task/Role/Helper.pm
Criterion Covered Total %
statement 7 9 77.7
branch n/a
condition n/a
subroutine 3 3 100.0
pod n/a
total 10 12 83.3


line stmt bran cond sub pod time code
1             package Games::Lacuna::Task::Role::Helper;
2              
3 1     1   2800 use utf8;
  1         12  
  1         7  
4 1     1   45 use 5.010;
  1         4  
  1         71  
5             our $VERSION = $Games::Lacuna::Task::VERSION;
6              
7 1     1   535 use Moose::Role;
  0            
  0            
8              
9             use List::Util qw(max min);
10              
11             use Games::Lacuna::Task::Constants;
12             use Data::Dumper;
13             use Games::Lacuna::Task::Utils qw(normalize_name parse_date);
14              
15             sub my_planets {
16             my $self = shift;
17            
18             my @planets;
19             foreach my $body_id ($self->my_bodies) {
20             my $body_status = $self->my_body_status($body_id);
21            
22             next
23             unless defined $body_status;
24             next
25             unless $body_status->{type} eq 'habitable planet'
26             || $body_status->{type} eq 'gas giant';
27             push(@planets,$body_status);
28             }
29             return @planets;
30             }
31              
32             sub my_stations {
33             my $self = shift;
34            
35             my @stations;
36             foreach my $body_id ($self->my_bodies) {
37             my $body_status = $self->my_body_status($body_id);
38             next
39             unless $body_status->{type} eq 'space station';
40             push(@stations,$body_status);
41             }
42             return @stations;
43             }
44              
45             sub my_body_status {
46             my ($self,$body) = @_;
47            
48             return
49             unless defined $body;
50            
51             return $body
52             if ref($body) eq 'HASH';
53            
54             my $body_id = $self->my_body_id($body);
55            
56             return
57             unless defined $body_id;
58              
59             my $body_status = $self->get_cache('body/'.$body_id);
60            
61             return $body_status
62             if defined $body_status;
63            
64             $body_status = $self->request(
65             object => $self->build_object('Body', id => $body_id),
66             method => 'get_status',
67             );
68            
69             return
70             unless defined $body_status;
71            
72             return $body_status->{body};
73             }
74              
75             sub get_building_object {
76             my ($self,$body,$type) = @_;
77            
78             my $body_id = $self->my_body_id($body);
79             return
80             unless $body_id;
81            
82             # Get space port
83             my $building_data = $self->find_building($body_id,$type);
84            
85             return
86             unless $building_data;
87            
88             return $self->build_object($building_data);
89             }
90              
91             sub find_building {
92             my ($self,$body,$type) = @_;
93            
94             my $body_id = $self->my_body_id($body);
95             return
96             unless $body_id;
97              
98             my $type_url = '/'.lc($type);
99            
100             # Get buildings
101             my @results;
102             foreach my $building_data ($self->buildings_body($body_id)) {
103             next
104             unless $building_data->{name} eq $type
105             || $building_data->{url} eq $type_url;
106            
107             if (defined $building_data->{pending_build}
108             && $building_data->{level} == 0) {
109             my $timestamp = time();
110             my $build_end = parse_date($building_data->{pending_build}{end});
111             next
112             if ($build_end > $timestamp);
113             }
114             push (@results,$building_data);
115             }
116            
117             @results = (sort { $b->{level} <=> $a->{level} } @results);
118             return wantarray ? @results : $results[0];
119             }
120              
121             sub buildings_body {
122             my ($self,$body) = @_;
123            
124             my $body_id = $self->my_body_id($body);
125             return
126             unless $body_id;
127              
128             my $key = 'body/'.$body_id.'/buildings';
129             my $buildings = $self->get_cache($key) || $self->request(
130             object => $self->build_object('Body', id => $body_id),
131             method => 'get_buildings',
132             )->{buildings};
133            
134             my @results;
135             foreach my $building_id (keys %{$buildings}) {
136             $buildings->{$building_id}{id} = $building_id;
137             push(@results,$buildings->{$building_id});
138             }
139             return @results;
140             }
141              
142             sub max_resource_building_level {
143             my ($self,$body_id) = @_;
144            
145             $body_id = $self->my_body_id($body_id);
146             return
147             unless $body_id;
148            
149             my $max_resource_level = 15;
150             my $stockpile = $self->find_building($body_id,'Stockpile');
151             if (defined $stockpile) {
152             $max_resource_level += int(sprintf("%i",$stockpile->{level}/3));
153             }
154             my $university_level = $self->university_level + 1;
155            
156             return min($max_resource_level,$university_level);
157             }
158              
159             sub university_level {
160             my ($self) = @_;
161            
162             my @university_levels;
163             foreach my $planet_stats ($self->my_planets) {
164             my $university = $self->find_building($planet_stats,'University');
165             next
166             unless $university;
167             push(@university_levels,$university->{level});
168             }
169             return max(@university_levels);
170             }
171              
172             sub my_bodies {
173             my $self = shift;
174            
175             my $planets = $self->get_stash('planets');
176             return keys %{$planets};
177             }
178              
179             sub home_planet_id {
180             my $self = shift;
181            
182             return $self->get_stash('home_planet_id')
183             }
184              
185             sub my_body_id {
186             my ($self,$body) = @_;
187              
188             return
189             unless defined $body;
190              
191             return $body
192             if $body =~ m/^\d+$/ && $body ~~ [$self->my_bodies];
193              
194             return $body->{id}
195             if ref($body) eq 'HASH' && exists $body->{id};
196              
197             # Get my planets
198             my $planets = $self->get_stash('planets');
199              
200             # Exact match
201             foreach my $id (keys %$planets) {
202             return $id
203             if $planets->{$id} eq $body;
204             }
205              
206             my $name_simple = normalize_name($body);
207            
208             # Similar match
209             foreach my $id (keys %$planets) {
210             return $id
211             if $name_simple eq normalize_name($planets->{$id});
212             }
213              
214             return;
215             }
216              
217             sub can_afford {
218             my ($self,$planet_data,$cost) = @_;
219            
220             $planet_data = $self->my_body_status($planet_data);
221            
222             foreach my $resource (qw(food ore water energy)) {
223             return 0
224             if (( $planet_data->{$resource.'_stored'} - 1000 ) < $cost->{$resource});
225             }
226            
227             return 0
228             if (defined $cost->{waste}
229             && ($planet_data->{'waste_capacity'} - $planet_data->{'waste_stored'}) < $cost->{waste});
230            
231             return 1;
232             }
233              
234             sub my_affinity {
235             my ($self) = @_;
236            
237             my $affinity = $self->client->get_cache('affinity');
238            
239             return $affinity
240             if defined $affinity;
241            
242             my $response = $self->request(
243             object => $self->build_object('Empire'),
244             method => 'view_species_stats',
245             );
246            
247             $affinity = $response->{species};
248            
249             $self->client->set_cache(
250             key => 'affinity',
251             value => $affinity,
252             max_age => (60 * 60 * 24)
253             );
254            
255             return $affinity;
256             }
257              
258             sub send_message {
259             my ($self, $subject, $message) = @_;
260            
261             $message =~ s/>=/≥/g;
262             $message =~ tr/></)(/;
263            
264             $self->request(
265             object => $self->build_object('Inbox'),
266             method => 'send_message',
267             params => [
268             $self->empire_name,
269             $subject,
270             $message,
271             ],
272             );
273             }
274              
275             no Moose::Role;
276             1;
277              
278              
279             =encoding utf8
280              
281             =head1 NAME
282              
283             Games::Lacuna::Task::Role::Helper - Various helper methods
284              
285             =head1 METHODS
286              
287             =head2 my_bodies
288              
289             Returns an array of your body IDs
290              
291             =head2 my_planets
292              
293             Returns an array of your planet IDs
294              
295             =head2 my_stations
296              
297             Returns an array of alliance stations IDs
298              
299             =head2 my_body_status
300              
301             my $body_status = $self->my_body_status($body_id OR $body_name);
302              
303             Returns the status hash of a given body/planet.
304              
305             =head2 my_body_id
306              
307             my $body_id = $self->my_body_id($body_name);
308              
309             Returns the id for a given body name. Ignores case and accents
310             so that eg. 'Hà Nôi' equals 'HA NOI'.
311              
312             =head2 buildings_body
313              
314             my $body_buildings = $self->buildings_body($body_id OR $boSdy_name);
315              
316             Returns all buildings for a given planet.
317              
318             =head2 can_afford
319              
320             $self->can_afford($planet_id or $planet_stats_hash,$cost_hash);
321              
322             Calculates if the upgrade/repair can be afforded
323              
324             =head2 find_building
325              
326             my @spaceports = $self->find_building($body_id or $body_name,'Space Port');
327              
328             Finds all buildings on a given body of a given type ordered by level.
329              
330             =head2 home_planet_id
331              
332             Returns the id of the empire' home planet id
333              
334             =head2 planet_ids
335              
336             Returns the empire' planet ids
337              
338             =head2 university_level
339              
340             Returns your empire' university level
341              
342             =head2 send_message
343              
344             $self->send_message($subject, $message);
345              
346             Send yourself a notification via the in-game messaging system.
347              
348             =head2 max_resource_building_level
349              
350             my $level = $self->max_resource_building_level($body_id);
351              
352             Returns the max possible ressource building level for the given planet.
353              
354             =head2 can_afford