CGI-Application-Plugin-OpenTracing

 view release on metacpan or  search on metacpan

lib/CGI/Application/Plugin/OpenTracing.pm  view on Meta::CPAN

package CGI::Application::Plugin::OpenTracing;

use strict;
use warnings;

our $VERSION = 'v0.104.2';

use syntax 'maybe';

use OpenTracing::Implementation;
use OpenTracing::GlobalTracer;

use Carp qw( croak carp );
use HTTP::Headers;
use HTTP::Status qw( is_server_error :constants);
use Scalar::Util qw( refaddr );
use Time::HiRes qw( gettimeofday );

use constant CGI_LOAD_TMPL    => 'CGI_APPLICATION_LOAD_TMPL';
use constant CGI_REQUEST      => 'CGI_APPLICATION_REQUEST';
use constant CGI_RUN          => 'CGI_APPLICATION_RUN';
use constant CGI_SETUP        => 'CGI_APPLICATION_SETUP';
use constant CGI_TEARDOWN     => 'CGI_APPLICATION_TEARDOWN';
use constant TRC_ACTIVE_SCOPE => 'TRC_SCOPEMANAGER_ACTIVE_SCOPE';

our $implementation_import_name;
our @implementation_import_opts;

our $TAG_JOIN_CHAR = ',';



################################################################################
#
# NOTE: please take a minute to understand the structure of this module
#
# CGI::Application::Plugin has an interesting design on itself
#
# within this code base there are three sections:
# - import
# - callbacks, as defined by CGI::Application
# - plugin related methods, that deal with the plugin internals
# - tracing specific routines
# - cgi related routines, that just work on the CGI::Application only
#
################################################################################



sub import {
    my $package = shift;
    
    ( $implementation_import_name, @implementation_import_opts ) = @_;
    $ENV{OPENTRACING_DEBUG} && carp "OpenTracing Implementation not defined during import\n"
        unless defined $implementation_import_name;
    
    my $caller  = caller;
    $caller->add_callback( init      => \&init      );
    $caller->add_callback( prerun    => \&prerun    );
    $caller->add_callback( postrun   => \&postrun   );
    $caller->add_callback( load_tmpl => \&load_tmpl );
    $caller->add_callback( teardown  => \&teardown  );
    $caller->add_callback( error     => \&error     );
    

    my $run_glob = do { no strict 'refs'; \*{ $caller . '::run' } };
    my $run_orig
        = defined &$run_glob
        ? \&run_glob
        : eval "package $caller;"  # SUPER works based on the package it's defined in
             . 'sub { my $self = shift; $self->SUPER::run(@_) }';
    no warnings 'redefine';
    *$run_glob = _wrap_run($run_orig);

    return;
}



sub new {
    my $class = shift;
    my %args  = @_;
    
    my $tracer = delete $args{tracer} // OpenTracing::GlobalTracer->get_global_tracer();
    
    bless {
        SCOPE  => {
            # one for each callback
        },
        TRACER => $tracer,
    }
}



################################################################################
#
#   Callbacks
#
################################################################################



( run in 0.797 second using v1.01-cache-2.11-cpan-39bf76dae61 )