use all non-arch-specific non-core dirs in @INC
[scpubgit/Tak.git] / lib / Tak / EvalService.pm
CommitLineData
36cf3bcb 1package Tak::EvalService;
2
3use Eval::WithLexicals;
36cf3bcb 4use Data::Dumper::Concise;
5use Capture::Tiny qw(capture);
31a246e4 6use Moo;
7
8with 'Tak::Role::Service';
36cf3bcb 9
10has 'eval_withlexicals' => (is => 'lazy');
11
71be5860 12has 'service_client' => (is => 'ro', predicate => 'has_service_client');
13
36cf3bcb 14sub _build_eval_withlexicals {
71be5860 15 my ($self) = @_;
16 Eval::WithLexicals->new(
17 $self->has_service_client
18 ? (lexicals => { '$client' => \($self->service_client) })
19 : ()
20 );
36cf3bcb 21}
22
23sub handle_eval {
24 my ($self, $perl) = @_;
25 unless ($perl) {
31a246e4 26 die [ mistake => eval_input => "No code supplied" ];
36cf3bcb 27 }
28 if (my $ref = ref($perl)) {
31a246e4 29 die [ mistake => eval_input => "Code was a ${ref} reference" ];
36cf3bcb 30 }
31a246e4 31 my ($ok, @ret);
36cf3bcb 32 my ($stdout, $stderr);
33 if (eval {
34 ($stdout, $stderr) = capture {
35 @ret = $self->eval_withlexicals->eval($perl);
36 };
37 1
38 }) {
31a246e4 39 $ok = 1;
36cf3bcb 40 } else {
31a246e4 41 ($ok, @ret) = (0, $@);
36cf3bcb 42 }
43 my $dumped_ret;
44 unless (eval { $dumped_ret = Dumper(@ret); 1 }) {
31a246e4 45 $dumped_ret = "Error dumping ${\($ok ? 'result' : 'exception')}: $@";
46 $ok = 0;
36cf3bcb 47 }
31a246e4 48 return {
49 stdout => $stdout, stderr => $stderr,
50 ($ok ? 'return' : 'exception') => $dumped_ret
36cf3bcb 51 };
52}
53
541;