File Coverage

blib/lib/Apertur/SDK/Resource/Upload.pm
Criterion Covered Total %
statement 17 54 31.4
branch 0 16 0.0
condition 0 12 0.0
subroutine 6 8 75.0
pod 2 3 66.6
total 25 93 26.8


line stmt bran cond sub pod time code
1             package Apertur::SDK::Resource::Upload;
2              
3 1     1   5 use strict;
  1         1  
  1         29  
4 1     1   3 use warnings;
  1         1  
  1         48  
5              
6 1     1   4 use JSON qw(encode_json);
  1         1  
  1         4  
7 1     1   81 use File::Basename qw(basename);
  1         1  
  1         68  
8 1     1   414 use Apertur::SDK::Crypto qw(encrypt_image);
  1         2  
  1         488  
9              
10             sub new {
11 3     3 0 8 my ($class, %args) = @_;
12 3         15 return bless { http => $args{http} }, $class;
13             }
14              
15             sub image {
16 0     0 1   my ($self, $uuid, $file, %options) = @_;
17              
18 0           my ($data, $filename);
19 0 0         if (ref $file eq 'SCALAR') {
20             # Raw bytes passed as scalar ref
21 0           $data = $$file;
22 0   0       $filename = $options{filename} || 'image.jpg';
23             }
24             else {
25             # File path string
26 0   0       $filename = $options{filename} || basename($file);
27 0 0         open my $fh, '<:raw', $file
28             or die "Cannot open file '$file': $!\n";
29 0           local $/;
30 0           $data = <$fh>;
31 0           close $fh;
32             }
33              
34 0   0       my $mime_type = $options{mimeType} || $options{mime_type} || 'image/jpeg';
35              
36 0           my @multipart = (
37             file => [
38             undef,
39             $filename,
40             'Content-Type' => $mime_type,
41             Content => $data,
42             ],
43             );
44              
45 0 0         if ($options{source}) {
46 0           push @multipart, source => $options{source};
47             }
48              
49 0           my %headers;
50 0 0         if ($options{password}) {
51 0           $headers{'x-session-password'} = $options{password};
52             }
53              
54             return $self->{http}->request(
55 0           'POST', "/api/v1/upload/$uuid/images",
56             multipart => \@multipart,
57             headers => \%headers,
58             );
59             }
60              
61             sub image_encrypted {
62 0     0 1   my ($self, $uuid, $file, $public_key, %options) = @_;
63              
64 0           my ($data, $filename);
65 0 0         if (ref $file eq 'SCALAR') {
66 0           $data = $$file;
67 0   0       $filename = $options{filename} || 'image.jpg';
68             }
69             else {
70 0   0       $filename = $options{filename} || basename($file);
71 0 0         open my $fh, '<:raw', $file
72             or die "Cannot open file '$file': $!\n";
73 0           local $/;
74 0           $data = <$fh>;
75 0           close $fh;
76             }
77              
78 0           my $encrypted = encrypt_image($data, $public_key);
79              
80             # The server's `default` encrypted mode reads a multipart upload, parses
81             # the file bytes as a JSON envelope (camelCase), then RSA-OAEP-SHA256
82             # decrypts. Send the envelope as a file part, mirroring the plain
83             # `image` multipart transport.
84             my $envelope = encode_json({
85             encryptedKey => $encrypted->{encrypted_key},
86             iv => $encrypted->{iv},
87             encryptedData => $encrypted->{encrypted_data},
88             algorithm => $encrypted->{algorithm},
89 0           });
90              
91 0           my @multipart = (
92             file => [
93             undef,
94             'image.jpg.enc',
95             'Content-Type' => 'application/octet-stream',
96             Content => $envelope,
97             ],
98             );
99              
100 0 0         if ($options{source}) {
101 0           push @multipart, source => $options{source};
102             }
103              
104 0           my %headers = (
105             'X-Aptr-Encrypted' => 'default',
106             );
107 0 0         if ($options{password}) {
108 0           $headers{'x-session-password'} = $options{password};
109             }
110              
111             return $self->{http}->request(
112 0           'POST', "/api/v1/upload/$uuid/images",
113             multipart => \@multipart,
114             headers => \%headers,
115             );
116             }
117              
118             1;
119              
120             __END__