package BookPub::Import::Importer::Google::Version23;

use strict;
use warnings;

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

use lib '/app/tools/bookpub/lib';
use base 'BookPub::Import::Importer::Google::Version16';

sub _fieldMap {
    {
        dateBegin                => 'B',
        purchaseType             => 'D',
        rAuthor                  => 'K',
        rTitle                   => 'J',
        rIsbn13                  => 'H',
        rImprint                 => 'I',
        rState                   => 'T',
        rPostalCode              => 'U',
        countryCode              => 'S',
        rReturns                 => 'E',
        rSales                   => 'E',
        rUnits                   => 'G',
        rListPrice               => 'M',
        rListPriceCurrency       => 'L',
        rNativeListPrice         => 'M',
        rNativeListPriceCurrency => 'L',
        rPurchasePrice           => 'R',
        rPurchasePriceCurrency   => 'Q',
        rDiscount                => 'X',
        rRevenue                 => 'AB',
        currencyCode             => 'AA',
        rTaxAmount               => 'W',
        isPreOrder               => 'F',
        conversionRate           => 'AC',
        rDuration                => 'D',
        rTransactionCategory     => 'E',
    };
}

sub _unverifiedFieldMap {
    {
        publisherRevenue    => 'Y',
        revenueWithTaxAUD   => 'AB',
        listPriceWithTax    => 'O',
        listPriceWithoutTax => 'P',
    };
}

sub _useIsSaleRec { 1 }
sub rPurchaseType { shift->purchaseType() }
sub rProductType  { shift->productType() }

sub rServiceName {
    return BookPub::Tracker::Service::GetDefaultServiceName( service_id => shift->serviceID );
}

sub state {
    my $self    = shift;
    my $rState  = $self->_getByFieldName('rState');
    my $country = $self->_getByFieldName('countryCode');

    # seems like the client is putting CA as the Canadian province
    # when they don't know it, we'll return no value in that case.
    return undef if ( $country eq 'CA' && $rState eq 'CA' );

    return 'QC'  if ( $country eq 'CA' && $rState eq "Qu\x{e9}bec" );
    return 'MB'  if ( $country eq 'CA' && $rState eq "Man");
    return 'BC'  if ( $country eq 'CA' && $rState eq "B.C.");

    return $self->BookPub::Import::Importer::state();
}

# leaving in variations on the purchase type string in case they're encountered
# in the future
sub purchaseType {
    my $self         = shift;
    my $purchaseType = $self->_getByFieldName('purchaseType');
    if ( $purchaseType =~ /Single Purchase/i ) {
        return BookPub::DB::Item::Sale::kPurchaseTypeDownload;
    } elsif ( $purchaseType =~ /Rental DAY_\d+/i ) {
        return BookPub::DB::Item::Sale::kPurchaseTypeLoan;
    } elsif ( $purchaseType =~ /Rental \d+.(Day|Hour)/i ) {
        return BookPub::DB::Item::Sale::kPurchaseTypeLoan;
    } else {
        $self->fail("Unrecognized purchase type: $purchaseType");
    }
}


sub rPurchasePrice {
    my $self = shift;

    my $price = $self->_getByFieldName('rPurchasePrice');
    $price =~ s/,//g;

    return $price;
}

sub rTaxAmount {
    my $self    = shift;
    my $tax     = $self->_getByFieldName('rTaxAmount');
    my $revenue = $self->_getByFieldName('rRevenue');

    $tax =~ s/,//g;

    # if the revenue is negative and tax positive, flipping the tax to match
    if ( $revenue < 0 && $tax > 0 ) {
        $tax *= -1;
    }

    return $tax;
}

sub units {
    my $self    = shift;
    my $units   = $self->_getByFieldName('rUnits');
    my $revenue = $self->_getByFieldName('rRevenue');

    $revenue =~ s/,//g;

    # flip the units if there's negative revenue and positive units
    if ( $revenue < 0 && $units > 0 ) {
        $units *= -1;
    }
    return $units;
}

sub rRevenue {
    my $self = shift;

    my $revenue = 0;
    if (
        $self->filename =~ /^HUK-Google-GBP-earnings-details-report/i ||
        $self->filename =~ /^MMUK_GoogleEarningsReport_Agency/i ) {
        $revenue = $self->_getByFieldName('rRevenue') || 0; # AB
        $revenue =~ s/,//g;
    } else {
        my $publisherRevenue = $self->_getByFieldName('publisherRevenue') || 0; # Y
        my $conversionRate   = $self->_getByFieldName('conversionRate')   || 1; # AC
        $publisherRevenue =~ s/,//g;
        $conversionRate   =~ s/,//g;
        $revenue = $publisherRevenue * $conversionRate;
    }

    # flip the revenue if it's a refund with positive revenue
    my $transactionType = $self->_getByFieldName('rSales');
    if ( $transactionType =~ /refund/i && $revenue > 0 ) {
        $revenue *= -1;
    }

    return $revenue;
}

sub rTaxUnitPrice {
    my $self = shift;

    my $listPriceWithTax    = $self->_getByFieldName('listPriceWithTax')    || 0;  # O
    my $listPriceWithoutTax = $self->_getByFieldName('listPriceWithoutTax') || 0;  # P
    $listPriceWithTax =~ s/,//g;
    $listPriceWithoutTax =~ s/,//g;

    return $listPriceWithTax - $listPriceWithoutTax;
}

sub rIsbn13 {
    my $self = shift;

    return $self->_getByFieldName('rIsbn13');
}

sub rListPriceCurrency {
    my $self = shift;

    my $listPriceCurrency = $self->_getByFieldName('rListPriceCurrency');
    my $revenueCurrency   = $self->_getByFieldName('currencyCode');
    if ( $self->listPriceRequired && $listPriceCurrency ) {
        $listPriceCurrency = $revenueCurrency;
    }

    return $listPriceCurrency;
}

sub rListPrice {
    my $self = shift;

    my $listPrice         = $self->_getByFieldName('rListPrice');
    my $listPriceCurrency = $self->_getByFieldName('rListPriceCurrency');
    my $revenueCurrency   = $self->_getByFieldName('currencyCode');
    $listPrice =~ s/,//g;

    if ( $self->listPriceRequired && $listPriceCurrency && $listPriceCurrency ne $revenueCurrency && $listPrice != 0 ) {
        my $conversionRate = $self->conversionRate;
        $listPrice *= $conversionRate;
    }

    return $listPrice;
}

sub conversionRate {
    my $self = shift;

    my $conversionRate = $self->_getByFieldName('conversionRate') || 0;      # AC
    return $conversionRate if $conversionRate;

    # If the conversion rate is missing, then calculate it!
    my $publisherRevenue = 0 + ( $self->_getByFieldName('publisherRevenue')  || 0); # Y
    my $convertedRevenue = 0 + ( $self->_getByFieldName('revenueWithTaxAUD') || 0); # AB
    $conversionRate = $publisherRevenue && $convertedRevenue ? $convertedRevenue / $publisherRevenue : 1;

    return $conversionRate || 1;
}

sub rDuration {
    my $self = shift;

    my $rDuration = $self->_getByFieldName('rDuration') || '';
    return if $rDuration =~ /^Single Purchase$/i;

    return $rDuration;
}

sub isFree {
    my $self = shift;

    return !$self->rRevenue && $self->rUnits ? 'Y' : 'N';
}


1;
