RSS Git Download  Clone
Raw Blame History
use v5.34;
package Model::DB;

use Moo;
use Local::DB;  # default action to auto-expand dates to DateTime objects
use Model::SQL; # provides app queries
use Data::Printer;

#-------------------------------------------------------------------------------
has app_config => ( is => 'ro', required => 1 ); # appdir, environment, etc
has dbix => (
    is => 'lazy',
    predicate => 1, # so we can call has_dbix
    clearer   => 1, # to remove object if db connection gone away
);
sub _build_dbix { # auto-expands dates to DateTime objects:
    my $self = shift; $self->debug('creating new dbix object');
    my $db   = $self->app_config->{db_name};
    Local::DB->dbix({ dbname => $db, log_query => 1 });
}
has sql_lib => ( is => 'lazy', clearer => 1, builder => sub {
    # needs list of patient table cols - for demo only, not needed for live app:
    Model::SQL->new( patient_cols => [ shift->dbix->get_cols('patients') ] )
} );

sub debug { # warn $ENV{DANCER_ENVIRONMENT}; p $_[0]->app_config;
    p @_ if shift->app_config->{environment} =~ /^dev/;
}

#-------------------------------------------------------------------------------
sub get_user_details {
    my ($self, $ref) = @_; # p $ref; # href key => userId (key = nhs-no, email or patient.id)
    my ($sql, @bind) = $self->sql_lib->user_details($ref); # p $sql; p \@bind;
    return $self->dbix->query($sql, @bind)->hash;
}

sub get_pack_dispatches {
    my ($self, $patient_id) = @_; # p $patient_id;

    my ($sql, @bind) = $self->sql_lib->get_pack_dispatches($patient_id); # p $sql; p \@bind;
    return $self->dbix->query($sql, @bind)->hashes;
}

sub update_last_login {
    my ($self, $patient_id) = @_; # p $patient_id;

    my $now = 'NOW()'; # DateTime->now( time_zone => 'Europe/London' );
    $self->dbix->update( 'patient_access',
        { last_login => \$now },
        { patient_id => $patient_id },
    );
}

# check persistent dbix object still has an active db connection, if not then
# clear dbix object - will be re-created on demand when needed for next db query:
sub check_db_connection {  # or _check_db_connection() - logs to sdtout:
    my $self = shift; # say 'has dbix: '. ( $self->has_dbix || 'no' );
    # call has_dbix() 1st in case object hasn't been created yet (dbix is lazy):
    if ( $self->has_dbix and not $self->dbix->dbh->ping ) {
        $self->clear_dbix;
    }
    return undef; # routine has no return value so don't return anything
}

#=begin # same as check_db_connection() but writes to stdout:
sub _check_db_connection {
    my $self = shift; # say $self->has_dbix ? 'have dbix' : 'do not have dbix';

    my $app_name = $self->app_config->{appname};
    my @log = Local::Utils::time_now . " checking $app_name db connection:";
    # call has_dbix() 1st in case object hasn't been created yet (dbix is lazy):
    if ( $self->has_dbix ) {
        my $id = $self->dbix->dbh->{mysql_thread_id};
        push @log, "have dbix object (thread_id=$id), testing ping:";
        if (! $self->dbix->dbh->ping ) {
            push @log, '*** inactive ping ***, clearing dbix object';
            $self->clear_dbix;
        }
        else { push @log, 'dbh still active' }
    }
    else { push @log, 'no dbix object' }
    $self->debug(@log);
    return undef; # routine has no return value so don't return anything
}
#=cut

1;