2012-05-10 2 views
0

저는 zabbix와 협력하여 zabbix API와 상호 작용할 수있는 인터페이스를 작성하고 있습니다. zabbix가 jsonrpc 인터페이스를 공개 했으므로 MojoX :: JSON :: RPC :: Service를 사용하기로 결정했습니다. 제가 지금 당면하는 문제는 Mojolicious :: Controller를 사용하여 작성된 다른 서비스와 상호 작용하는 것에 직면 해 있다는 것입니다. Mojolicious :: Controller 객체를 기대하는 곳입니다. MojoX :: JSON :: RPC :: Service를 사용할 때 사용할 수있는 Mojolicious :: Controller 객체는 없습니다.MojoX :: JS :: RPC :: Service에 Mojolicious :: Controller를 통합하는 방법이 있습니까?

my $obj = $rpc_obj->register(
       'retrieve', 
       sub { 
        # do stuff 
       }, 
       { with_mojo_tx => 1 } 
); 

'retrieve'라는 경로가 등록됩니다. 경로가 액세스되고 익명의 서브 루틴이 실행되면 서브 루틴은 Mojo :: Transaction :: HTTP 객체에만 액세스 할 수 있습니다.

그래서 플러그인을 사용하기 위해 앱에 액세스 할 수 없으며 Mojolicious가 제공하는 숨겨진 다른 것들을 사용할 수 없습니다. MojoX :: JS :: RPC :: Service에 Mojolicious :: Controller를 통합 할 수있는 방법이 있습니까?

Mojolicious :: Controller를 사용하도록 다시 작성할 수는 있지만 가능한 경우이를 피하려고합니다.

답변

0

Mojolicious::Controller

SYNOPSIS에서 모든 속성을 상속과 같이, MojoX::JSON::RPC::Dispatcher를 사용하는 것이 좋습니다 :

# lib/your-application.pm 

use base 'Mojolicious'; 
use MojoX::JSON::RPC::Service; 

sub startup { 
    my $self = shift; 
    my $svc = MojoX::JSON::RPC::Service->new; 

    $svc->register(
     'sum', 
     sub { 
      my @params = @_; 
      my $sum = 0; 
      $sum += $_ for @params; 
      return $sum; 
     } 
    ); 

    $self->plugin(
     'json_rpc_dispatcher', 
     services => { 
      '/jsonrpc' => $svc 
     } 
    ); 
} 

[업데이트] 훅 예 :

package Application; 
use Mojo::Base 'Mojolicious'; 
use Application::Firewall; 

# This method will run once at server start 
sub startup { 
    my $app = shift; 

    # Routes 
    my $r = $app->routes; 

    # Validation Middleware 
    $app->hook(
     before_dispatch => sub { 
      my $self = shift; 
      my $data = $self->req->params->to_hash; 
      my $vald = Application::Firewall->new($data); 

      # mojolicious bug at the time of coding 
      delete $data->{""} if defined $data->{""}; 

      $app->{input} = {}; 

      if (keys %{$data}) { 

       # validation the submitted data 
       unless ($vald->validate(keys %{$data})) { 
        $self->render(
         text => join("", @{ $vald->errors }), 
         status => 500 
        ); 
        return 0; 
       } 

       # Helper (optional) 
       # create a helper to get access to the transformed data 
       # if your validation rules had/has filters 
       # Note! due to a bug in the params function we must do this 
       # (... i know, so what) 
       $app->{input} = { 
        map { $_ => $vald->{fields}->{$_}->{value} } 
         keys %{ $vald->{fields} } 
       }; 

      } 

      return 1; 
     } 
    ); 

    # Normal route to controller * with auto-matic input validation * 
    $r->route('/')->to(
     cb => sub { 
      my $self = shift; 
      $self->render(
       text => 'Hello ' . ($app->{input}->{foobar} || 'World'), 
       status => 200 
      ); 
     } 
    ); 
} 

1; 
+0

그래, 그게 내가하고있는 일이야. 내가 가지고있는 문제는 'sum'경로가 실행될 때 컨트롤러에 액세스 할 수 없다는 것입니다. 기본적으로 나는 루트를 실행하기 전에 약간의 권한 부여를하고 싶었다. 그래서, 지금은 $ self-> app-> hook (before_dispatch => sub {...});으로 $ self-> app에 후크를 추가하려고합니다. 응용 프로그램에서 'sum()'의 Mojolicious :: Controller에 액세스 할 필요가 없습니다. http://search.cpan.org/~sri/Mojolicious-2.94/lib/Mojolicious.pm#hook – jmcneirney

+0

@jmcneirney -'my $ self = shift; '를 사용하면'$ self-> hook 만 있으면된다. '... 또는'my $ app = shift;'를 사용하면'$ app-> hook'이지만 왜'$ self-> app-> hook'을 사용해야하는지 모르겠습니다. –

+0

예. 네가 옳아. – jmcneirney