#---------------------------------------------------------------
# ____                   _ _         ____  _
#|  _ \ ___  _   _  __ _| | |_ _   _/ ___|| |__   __ _ _ __ ___
#| |_) / _ \| | | |/ _` | | __| | | \___ \| '_ \ / _` | '__/ _ \
#|  _ < (_) | |_| | (_| | | |_| |_| |___) | | | | (_| | | |  __/
#|_| \_\___/ \__, |\__,_|_|\__|\__, |____/|_| |_|\__,_|_|  \___|
#            |___/             |___/
#
# Copyright (C) 2013 RoyaltyShare, Inc.   All Rights Reserved
#---------------------------------------------------------------

package RPS::Import::Puretracks::v13;

use strict;

use lib '/app/tools/common/lib';
use Common::Consts;
use Common::Assert;
use Common::Log;

use lib '/app/tools/rps/lib';
use base 'RPS::Import::Importer';

# The same columns are used for both album and track sales, which
# appear on different sheets, however the columns are actually shifted
# over on the album sheet.  See _getOffset, below.
#
sub _fieldMap {
    {
        labelName        => 'F',
        dateBegin        => 'A',

        serviceProductID => 'E',
        mediaType        => 'B',
        artistName       => 'H',
        upc              => 'C',
        isrc             => 'D',
        units            => 'J',
    }
}

sub _unverifiedFieldMap {
    {
        wholesale       => 'L',
        publishing      => 'M',
        title           => 'I', # can be either album or track title, depending on the sheet
    }
}

sub _headerIdentifier { ( upc => 'UPC' ) }

sub currencyCode { 'USD' };  # applies to both US and CA sales

sub saleDates {
    my $self = shift;
    my $startDate = $self->_getDateBegin();

    if( $startDate =~ /^\d{5}$/ )
    {
        $startDate =  Spreadsheet::ParseExcel::Utility::ExcelFmt( "yyyy-mm-dd", $startDate );
    }
    return $self->_getDates( date_begin => $startDate );
}

sub countryCode {

    # Determined from filename (see _preProcess)
    #
    my $self = shift;
    $self->fail("Filename doesn't contain CA or US") if( !$self->{_countryCode} );
    return $self->{_countryCode};
}

sub productType {
    my $self = shift;

    # from sheet header.. see _processSheet
    #
    return $self->{_productType};
}

sub price {
    my $self = shift;
    my $wholesale  = $self->_getByFieldName('wholesale');
    my $publishing = $self->_getByFieldName('publishing');
    return $wholesale - $publishing;
}

sub albumName {
    my $self = shift;
    my $title = $self->_getByFieldName('title');
    return ( $self->productType eq RPS::File::Sale::TYPE_ALBUM ) ? $title : undef;
}

sub trackName {
    my $self = shift;
    my $title = $self->_getByFieldName('title');
    return ( $self->productType eq RPS::File::Sale::TYPE_TRACK ) ? $title : undef;
}

sub isrc {
    my $self = shift;
    my $isrc = $self->_getByFieldName('isrc');
    return ( $self->productType eq RPS::File::Sale::TYPE_TRACK ) ? $isrc : undef;
}

sub formatType {
    my $self = shift;
    my $type = $self->_getByFieldName('mediaType');
    if( $type =~ /^mp3$/i )
    {
        return RPS::File::Sale::FORMAT_DOWNLOAD;
    }
    $self->fail("Unable to determine media type from '$type'");
}

sub mediaType {
    my $self = shift;
    my $type = $self->_getByFieldName('mediaType');
    if( $type =~ /^mp3$/i )
    {
        return RPS::DB::Item::MediaType::kMediaTypeAudio;
    }
    $self->fail("Unable to determine media type from '$type'");
}

sub _preProcess {

    my $self = shift;

    my %args = @_;
    my $fileName = $args{file}->OrigFileName();

    my $countryCode;

    # If the filename starts with "CA" or "CANADA", followed by spaces or an underscore or period,
    # then assume it's Canadian.
    # If the filename starts with "US" or "USA", followed by spaces or an underscore or period,
    # then assume it's US.
    #
    if ( $fileName =~ /^ca(nada)?(\s+|_|\.)/i )
    {
        $countryCode  = "CA";
    }
    elsif ( $fileName =~ /^us(a)?(\s+|_|\.)/i )
    {
        $countryCode  = "US";
    }
    else
    {
        return undef;
    }

    $self->{_countryCode}  = $countryCode;
}

# _processSheet is used to process a worksheet from the sales file.
#
# All we're doing here is determining the product type to be applied to all
# sales on the sheet. Also, we invoke the inherited _processSheet so that
# normal line processing occurs.
#
sub _processSheet {
    my $self     = shift;
    my $sheet    = shift;

    my $sheetnum = $self->{sheetnum};

    $self->{_productType} = "";

    # prevents shifting of album columns; we'll change this if we
    # detect that the album columns are in fact shifted over
    #
    $self->{_noshift} = 1;

    my $productType;

    if( $sheetnum > 0 )
    {
        my $headerFound;
        my $checkHeader;

        foreach my $line (@$sheet)
        {
            $self->{line} = $line;

            if( $self->_isHeader() )
            {
                $headerFound = 1;
            }

            if( !$headerFound && !$productType )
            {
                if( $line->[0] =~ /^album sales$/i )
                {
                    $productType = RPS::File::Sale::TYPE_ALBUM;
                    $checkHeader = 1;
                }
                elsif( $line->[0] =~ /^track sales$/i )
                {
                    $productType = RPS::File::Sale::TYPE_TRACK;
                }
                next;
            }

            if( $checkHeader )
            {
                # peek at the next line on the album worksheet (which should be the
                # header) and see if the header identifier is where we expect it or
                # it's one column to the right.
                #
                my ( $field, $value ) = $self->_headerIdentifier();
                if( ref($field) )
                {
                    my ($key) = keys(%$field);
                    $value    = $field->{$key};
                    $field    = $key;
                }

                my $offset = $self->_getOffset( $field );

                if( defined($line->[$offset]) && $line->[$offset] eq $value )
                {
                    #print STDERR "_preProcess: album columns are in same position as track columns\n";
                    $self->{_noshift} = 1; # no shifting required for album columns
                }
                elsif( defined($line->[$offset+1]) && $line->[$offset+1] eq $value )
                {
                    #print STDERR "_preProcess: album columns are shifted relative to track columns\n";
                    $self->{_noshift} = 0; # shifting required for album columns
                }

                undef $checkHeader;

            }
        }
    }

    $self->{_productType} = $productType if( $productType );

    return $self->SUPER::_processSheet( $sheet, $sheetnum );
}


# The album sheet (sheet #2) has the same column headings as the track sheet (sheet #3),
# however its columns MIGHT be shifted over by one because the 'DATE' column (column A) has
# been merged with column B.  E.g., the date is in column A on the track sheet, but takes
# up A + B on the album sheet.  The rest of the columns ('MEDIA TYPE', 'UPC', etc.) are
# in the same relative position after the DATE column.
#
# To accomodate the shift, we override _getOffset and adjust the index values for
# sheet #2.  This allows the same fieldMap to be used for both the album and track sheets.
#
sub _getOffset {
    my $self = shift;
    my $field = shift;

    my $offset = $self->SUPER::_getOffset( $field );

    return undef if( !defined $offset );

    # noshift is set if we previously detected that the album
    # columns are in the same location at the track columns.
    # If it isn't set, then shift the columns on sheet #2. 
    #
    return $offset if( $self->{_noshift} );

    my $sheetnum = $self->sheetnum;

    my $_offset = ( $sheetnum == 2) ? ($offset + 1 ) : $offset;

    return $_offset;
}

###
1;# Play nicely.
###
