#------------------------------------------------------------
# Copyright (C) 2006 RoyaltyShare, Inc.   All Rights Reserved
#------------------------------------------------------------
package RPS::Catalog::TrackAdditionalArtist;

use strict;
use warnings;

use Data::Dumper;

use lib '/app/tools/rps/lib';
use RPS::DB::Item::Artist;
use RPS::DB::Item::TrackAdditionalArtist;
use RPS::ArtistRole;
use Common::FormObject;
use Common::Assert;

use base 'RPS::Catalog::AdditionalArtist';

sub _init {
    my ( $self, %args ) = @_;

    $self->SUPER::_init(%args);

    my %properties;
    if ( $args{_dbItem} ) {
        $self->_propertiesFromDBItem( \%properties, $args{_dbItem} );
    } elsif ( $args{artistID} && $args{artistRoleID} && $args{trackID} ) {
        $self->_propertiesFromDB( \%properties, %args );
    } else {
        $self->_propertiesFromDefaults( \%properties );
    }

    $self->_initProperties( \%properties );
    $self->_initSubs( \%properties );

    return $self;
}

sub _propertiesFromDB {
    my ( $self, $hrProperties, %args ) = @_;

    my $dbItem = RPS::DB::Item::Artist->LookupWithTrackAdditionalArtist(
        artist_id      => $args{artistID},
        artist_role_id => $args{artistRoleID},
        track_id       => $args{track_id}
    );

    $self->_propertiesFromDBItem( $hrProperties, $dbItem );
}

sub _propertiesFromDBItem {
    my ( $self, $hrProperties, $dbItem ) = @_;

    $hrProperties->{track_id} = $dbItem->{track_id};

    $self->SUPER::_propertiesFromDBItem( $hrProperties, $dbItem );
}

sub _initProperties {
    my ( $self, $props ) = @_;

    $self->SUPER::_initProperties($props);

    $self->{TrackID} = Common::FormObject::Scalar->new( value => $props->{track_id} );

    return $self;
}

sub validate {
    my $self = shift;
    my %args = @_;

    return $self->SUPER::validate(%args);
}

sub save {
    my $self    = shift;
    my %args    = @_;
    my $oldInfo = $self->parseKey( $self->OriginalKey() );

    $self->TrackID( $args{trackID} ) if ( $args{trackID} );

    # Check if anything has changed.  If not, we're done.
    unless ( $self->hasChanged( $args{key} ) || $self->Delete() ) {
        Common::Log::Debug("No change detected, not updating");
        return;
    }

    my $dbObj;

    ###
    #   Delete
    ###
    if ( $self->Delete() ) {
        $self->_delete($oldInfo);

        ###
        #   Update
        ###
    } elsif ($oldInfo) {
        $self->_update($oldInfo);
    }

    ###
    #   Create
    ###
    else {
        $self->_create();
    }

}

sub _create {
    my $self = shift;

    my $artistID = $self->_getArtistID();
    assert($artistID);
    $self->ArtistID($artistID);

    # Do we need to clear our an old record?

    my $dbObj = RPS::DB::Item::TrackAdditionalArtist->Create();

    $dbObj->track_id( $self->TrackID );
    $dbObj->artist_role_id( $self->ArtistRoleID );
    $dbObj->artist_id( $self->ArtistID );

    $dbObj->save;
}

sub _update {
    my $self    = shift;
    my $oldInfo = shift;

    my $artistID = $self->_getArtistID();
    assert($artistID);
    $self->ArtistID($artistID);

    assert( $oldInfo->{artistID} && $oldInfo->{artistRoleID} && $oldInfo->{trackID} );

    my $dbObj = RPS::DB::Item::TrackAdditionalArtist->Lookup(
        artist_id      => $oldInfo->{artistID},
        track_id       => $oldInfo->{trackID},
        artist_role_id => $oldInfo->{artistRoleID},
    );

    assert($dbObj);

    $dbObj->track_id( $self->TrackID );
    $dbObj->artist_role_id( $self->ArtistRoleID );
    $dbObj->artist_id( $self->ArtistID );

    $dbObj->save;
}

sub _delete {
    my $self    = shift;
    my $oldInfo = shift;

    return unless ($oldInfo);

    assert( $oldInfo->{artistID} && $oldInfo->{artistRoleID} && $oldInfo->{trackID} );

    RPS::DB::Item::TrackAdditionalArtist->Delete(
        artist_id      => $oldInfo->{artistID},
        artist_role_id => $oldInfo->{artistRoleID},
        track_id       => $oldInfo->{trackID}
    );
}

sub hasChanged {
    my $self    = shift;
    my $key     = shift;
    my $oldInfo = $self->parseKey($key);

    if ( $oldInfo->{trackID} != $self->TrackID ) {
        return 1;
    }

    return $self->SUPER::hasChanged($key);
}

sub hashKey {
    my $self         = shift;
    my $trackID      = $self->TrackID || "";
    my $artistID     = $self->ArtistID || "";
    my $artistRoleID = $self->ArtistRoleID || "";

    return $self->OriginalKey() if ( $self->OriginalKey() );

    return "$trackID.$artistID.$artistRoleID";
}

sub parseKey {
    my $self = shift;
    my $key  = shift;

    Common::Log::Debug("Parse Key: $key") if ($key);

    return unless ( $key && $key !~ /new/i );

    my ( $trackID, $artistID, $artistRoleID ) = split( /\./, $key );

    return { trackID => $trackID, artistID => $artistID, artistRoleID => $artistRoleID };
}

1;
