File Coverage

blib/lib/Business/GoCardless/Resource.pm
Criterion Covered Total %
statement 49 53 92.4
branch 17 20 85.0
condition 2 2 100.0
subroutine 10 10 100.0
pod 3 4 75.0
total 81 89 91.0


line stmt bran cond sub pod time code
1             package Business::GoCardless::Resource;
2              
3             =head1 NAME
4              
5             Business::GoCardless::Resource
6              
7             =head1 DESCRIPTION
8              
9             This is a base class for gocardless resource classes, it implements common
10             behaviour. You shouldn't use this class directly, but extend it instead.
11              
12             =cut
13              
14 19     19   8441 use strict;
  19         44  
  19         486  
15 19     19   88 use warnings;
  19         33  
  19         390  
16              
17 19     19   85 use Moo;
  19         38  
  19         82  
18 19     19   6312 use Carp qw/ carp confess /;
  19         52  
  19         1006  
19 19     19   666 use JSON ();
  19         8217  
  19         14468  
20              
21             =head1 ATTRIBUTES
22              
23             =head2 endpoint
24              
25             The gocardless API endpoint that corresponds to the resource, for example a
26             L object will have an endpoint of "bills". This
27             is handled automatically, you do not need to pass this unless the name of the
28             resource differs significantly from the endpoint.
29              
30             =head2 client
31              
32             The client object, defaults to L.
33              
34             =cut
35              
36             has endpoint => (
37             is => 'ro',
38             default => sub {
39             my ( $self ) = @_;
40             my ( $class ) = ( split( ':',ref( $self ) ) )[-1];
41              
42             confess( "You must subclass Business::GoCardless::Resource" )
43             if $class eq 'Resource';
44              
45             $class =~ s/([a-z])([A-Z])/$1 . '_' . lc( $2 )/eg;
46             $class = lc( $class );
47             return "/${class}s/%s";
48             },
49             );
50              
51             has client => (
52             is => 'ro',
53             isa => sub {
54             confess( "$_[0] is not a Business::GoCardless::Client" )
55             if ref $_[0] ne 'Business::GoCardless::Client'
56             },
57             required => 1,
58             );
59              
60             =head1 METHODS
61              
62             =head2 find_with_client
63              
64             Calls the gocardless API and populates the resource object with the data.
65              
66             my $Bill = Business::GoCardless::Bill->new( client => $self->client );
67             $Bill->find_with_client;
68              
69             =cut
70              
71             sub find_with_client {
72 18     18 1 61 my ( $self,$sub_key ) = @_;
73              
74 18         205 my $path = sprintf( $self->endpoint,$self->id );
75 18         118 my $data = $self->client->api_get( $path );
76              
77 18 100       75 $data = $data->{$sub_key} if $sub_key;
78              
79 18         37 foreach my $attr ( keys( %{ $data } ) ) {
  18         91  
80             # as per https://developer.gocardless.com/api-reference/#overview-backwards-compatibility
81             #
82             # The following changes are considered backwards compatible
83             # "Adding new properties to the responses from existing API endpoints"
84             #
85             # so we need to be able to handle attributes we don't know about yet, hence the eval
86 203         246 eval { $self->$attr( $data->{$attr} ); };
  203         544  
87 203 50       358 $@ && do {
88 0         0 carp( "Couldn't set $attr on @{[ ref( $self ) ]}: $@" );
  0         0  
89             };
90             }
91              
92 18         166 return $self;
93             }
94              
95             sub _operation {
96 8     8   29 my ( $self,$operation,$method,$params,$suffix ) = @_;
97              
98 8 100 100     84 $method //= 'api_post',
99              
100             my $uri = $operation
101             ? sprintf( $self->endpoint,$self->id ) . "/$operation"
102             : sprintf( $self->endpoint,$self->id );
103              
104 8 100       29 $uri .= "/$suffix" if $suffix;
105              
106 8         46 my $data = $self->client->$method( $uri,$params );
107              
108 8 100       170 if ( $self->client->api_version > 1 ) {
109              
110             $data = $data->{payments}
111 3 100       36 if ref( $self ) eq 'Business::GoCardless::Payment';
112             $data = $data->{subscriptions}
113 3 100       12 if ref( $self ) eq 'Business::GoCardless::Subscription';
114             $data = $data->{mandates}
115 3 50       11 if ref( $self ) eq 'Business::GoCardless::Mandate';
116             }
117              
118 8         60 foreach my $attr ( keys( %{ $data } ) ) {
  8         39  
119 129         150 eval { $self->$attr( $data->{$attr} ); };
  129         299  
120 129 50       210 $@ && do {
121 0         0 carp( "Couldn't set $attr on @{[ ref( $self ) ]}: $@" );
  0         0  
122             };
123             }
124              
125 8         76 return $self;
126             }
127              
128             sub uri {
129 3     3 0 10 my ( $self ) = @_;
130              
131 3         29 my $endpoint = sprintf( $self->endpoint,$self->id );
132              
133 3 100       83 return $self->client->api_version > 1
134             ? join( '/',$self->client->base_url . $self->client->api_path . $endpoint )
135             : join( '/',$self->client->base_url . $endpoint );
136             }
137              
138             =head2 to_hash
139              
140             Returns a hash representation of the object.
141              
142             my %data = $Bill->to_hash;
143              
144             =head2 to_json
145              
146             Returns a json string representation of the object.
147              
148             my $json = $Bill->to_json;
149              
150             =cut
151              
152             sub to_hash {
153 2     2 1 2797 my ( $self ) = @_;
154              
155 2         6 my %hash = %{ $self };
  2         14  
156 2         8 delete( $hash{client} );
157 2         43 return %hash;
158             }
159              
160             sub to_json {
161 1     1 1 11199 my ( $self ) = @_;
162 1         27 return JSON->new->canonical->encode( { $self->to_hash } );
163             }
164              
165             =head1 AUTHOR
166              
167             Lee Johnson - C
168              
169             This library is free software; you can redistribute it and/or modify it under
170             the same terms as Perl itself. If you would like to contribute documentation,
171             features, bug fixes, or anything else then please raise an issue / pull request:
172              
173             https://github.com/Humanstate/business-gocardless
174              
175             =cut
176              
177             1;
178              
179             # vim: ts=4:sw=4:et