package LIMS::Model::Email;

use Moose;
extends 'LIMS::Model::Base';
with (
    'LIMS::Model::Roles::SessionData', # provides $self->user_profile
    'LIMS::Model::Roles::HistoryAction',
);

use namespace::clean -except => 'meta';

has form_data => ( is => 'rw', isa => 'HashRef', default => sub { {} } );

__PACKAGE__->meta->make_immutable;

use LIMS::Local::Mail qw(dispatch);

#-------------------------------------------------------------------------------
sub diagnosis_status_alert {
    my $self = shift;
    my $data = shift; # hashref of: recipients (arrayref), settings (hashref),
                      # message (str), subject (str)
    
    my $recipients = $data->{all_recipients}; # arrayref
    
    my $db = $self->lims_db; # ie LIMS::DB->new_or_cached;

    $self->reset_actions; # clear previous addresses (if using cron for multiple records)

	for my $contact (@$recipients) {
		$data->{recipient} = $contact;
        # forward $data to send_messsage() - will ignore $data->{all_recipients}:
    	if ( my $rtn = $self->send_message($data) ) { # returns error or empty
            return $rtn;
        }
        $self->add_to_actions('e-mailed diagnosis status alert to ' . $contact);
    }
    
    $self->do_request_history();
    
    return 0;
}

#-------------------------------------------------------------------------------
sub send_message {
    my $self = shift;
    my $data = shift; # hashref of: recipient (str), config (hashref),
                      # message (str), subject (str), sender (str; optional),
                      # content (optional, eg html)

	my $message = $self->_generate_message($data);
    
    my $rtn = LIMS::Local::Mail::dispatch($message); # returns error or empty
    return $rtn || 0;    
}

#-------------------------------------------------------------------------------
sub send_attachment {
    my $self = shift;
    my $data = shift; # hashref of: recipient (str), config (hashref),
                      # message (str), subject (str), attachment (binary),
                      # sender (str; optional)
	
    my $message = $self->_generate_message($data); # adds common fields
    # add attachment:
    @{$message}{ qw(file filename) } = @{$data}{ qw(attachment filename) };
    
    my $rtn = LIMS::Local::Mail::send_attachment($message); # returns hasheref
    return $rtn;    
}

#-------------------------------------------------------------------------------
sub add_new_address {
    my ($self, $recipient) = @_;
	# add address if not exists:
	my $o = LIMS::DB::EmailAddress->new(address => $recipient)->load_or_insert;	
}

#-------------------------------------------------------------------------------
sub set_request_id {
    my ($self, $request_id) = @_;
    
    # set form_data params for do_request_history():
    $self->form_data({ _request_id => $request_id });
}

#-------------------------------------------------------------------------------
sub _generate_message {
	my ($self, $data) = @_;
	
	my $cfg = $data->{config};
	
    my %mail = (
        to       => $data->{recipient},
        from     => $data->{sender} || $cfg->{email_from},
        subject  => $data->{subject},
        message  => $data->{message},
        smtp     => $cfg->{smtp},
		_app_cfg => $cfg, # ignored by Mail::Sendmail::sendmail
    ); # $self->debug(\%mail); 

	if ( $cfg->{smtp_user} && $cfg->{smtp_pwd} ) {
		my %auth = (
			user => $cfg->{smtp_user},
			pass => $cfg->{smtp_pwd}, # alias for password
#			method   => 'DIGEST-MD5', # let it try all methods
#			required => 1, # let it try without
		);
		$mail{auth} = \%auth;
	}
	
    # add content-type headers if included:
    if ( my $content_type = $data->{content} ) {
        $mail{'content-type'} = _get_content_type($content_type);
    }
    
	return \%mail;
}

#-------------------------------------------------------------------------------
sub _get_content_type {
    my $content_type = shift;

    my $h = { # only using html so far:
        html => 'text/html; charset=ISO-8859-1',
    };

    my $type = $h->{$content_type};
    if (! $type) { warn "no entry for $content_type found" } # don't need fatal - will send anyway

    return $type;
}

1;