#------------------------------------------------------------
# Copyright (C) 2006 RoyaltyShare, Inc.   All Rights Reserved
#------------------------------------------------------------
package RPS::Track::TrackSimple;
use strict;
use warnings;

use Data::Dumper;

use lib '/app/tools/appuser/lib';
use AppUser::User::User;

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

use lib '/app/tools/rps/lib';
use RPS::DB::Item::Track;
use RPS::DB::Item::MediaType;
use RPS::DB::Item::Artist;

use lib '/app/tools/mediaserve/lib';
use MediaServe::DB::Item::ProductTrackFile;

use RPS::Master::Master;
use RPS::Catalog::Album;

use Common::FormObject;
use base 'Common::FormObject';


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

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

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

    $self->_initProperties(\%properties);

    return $self;
}

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

	my $dbItem = RPS::DB::Item::Track->Lookup(track_id => $trackID);

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

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

	$hrProperties->{track_id}       = $dbItem->track_id;
	$hrProperties->{album_id}       = $dbItem->album_id;
	$hrProperties->{track_order}    = $dbItem->track_order;
	$hrProperties->{title}          = $dbItem->title;
	$hrProperties->{title_clean}    = $dbItem->title_clean;
	$hrProperties->{client_track_id} = $dbItem->client_track_id;
	$hrProperties->{track_order}   = $dbItem->track_order;
	$hrProperties->{master_id}      = $dbItem->master_id;
	$hrProperties->{mechanical_exempt}      = $dbItem->mechanical_exempt;
	$hrProperties->{ca_mechanical_exempt}   = $dbItem->ca_mechanical_exempt;
	$hrProperties->{parental_advisory}      = $dbItem->parental_advisory;

	$hrProperties->{date_created}   = $dbItem->date_created;
	$hrProperties->{date_modified}  = $dbItem->date_modified;
	$hrProperties->{created_by}     = $dbItem->created_by;
	$hrProperties->{modified_by}    = $dbItem->modified_by;
	$hrProperties->{artist_id}      = $dbItem->artist_id;
	$hrProperties->{media_type}     = $dbItem->media_type;

	$hrProperties->{genre_name}      = $dbItem->genre_name;
	$hrProperties->{custom_1}       = $dbItem->custom_1;
	$hrProperties->{custom_2}       = $dbItem->custom_2;
	$hrProperties->{custom_3}       = $dbItem->custom_3;

}

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

	$self->{TrackID}        = Common::FormObject::Scalar->new(value => $props->{track_id}, readOnly => 1);
	$self->{AlbumID}        = Common::FormObject::Scalar->new(value => $props->{album_id}); # !!! had been required
	$self->{Title}          = Common::FormObject::Scalar::String->new(value => $props->{title}, required => 1);
	$self->{TitleClean}     = Common::FormObject::Scalar::String->new(value => $props->{title_clean});
	$self->{ClientTrackID}  = Common::FormObject::Scalar::String->new(value => $props->{client_track_id});
	$self->{TrackOrder}    = Common::FormObject::Scalar->new(value => $props->{track_order});
	$self->{MasterID}       = Common::FormObject::Scalar->new(value => $props->{master_id});
	$self->{MechanicalExempt} = Common::FormObject::Scalar::Boolean->new(value => $props->{mechanical_exempt});
	$self->{CAMechanicalExempt} = Common::FormObject::Scalar::Boolean->new(value => $props->{ca_mechanical_exempt});
	$self->{ParentalAdvisory} = Common::FormObject::Scalar::String->new(value => $props->{parental_advisory});
	$self->{GenreName}      = Common::FormObject::Scalar::String->new(value => $props->{genre_name});
	$self->{MediaType}      = Common::FormObject::Scalar->new(value => $props->{media_type});
	$self->{Custom1}        = Common::FormObject::Scalar::String->new(value => $props->{custom_1});
	$self->{Custom2}        = Common::FormObject::Scalar::String->new(value => $props->{custom_2});
	$self->{Custom3}        = Common::FormObject::Scalar::String->new(value => $props->{custom_3});

	$self->{CreatedDate}    = Common::FormObject::Scalar::DateTime->new(value => $props->{date_created}, readOnly => 1);
	$self->{ModifiedDate}   = Common::FormObject::Scalar::DateTime->new(value => $props->{date_modified}, readOnly => 1);
	$self->{CreatedBy}      = Common::FormObject::Scalar::UserName->new(value => $props->{created_by}, readOnly => 1);
	$self->{ModifiedBy}     = Common::FormObject::Scalar::UserName->new(value => $props->{modified_by}, readOnly => 1);


	# We need to fetch the artist name, given the artist id.
	#
	my $artistName;
	if ($props->{artist_id})
	{
		my $artistDBItem = RPS::DB::Item::Artist->Lookup(artist_id => $props->{artist_id});
		$artistName = $artistDBItem->name if($artistDBItem);
	}
	$self->{ArtistName} = Common::FormObject::Scalar::String->new(value => $artistName, required => 1);
	$self->{ArtistID} = Common::FormObject::Scalar->new(value => $props->{artist_id});


	# this is something we only do for TrackSimple and not
	# for any of its derived classes.
    # !!! Huh? What?  Why is this here?
	#
	if(ref($self) eq 'RPS::Track::TrackSimple')
	{
		my $seconds = 0;
		if($props->{master_id})
		{
			my $master = RPS::DB::Item::Master->Lookup(master_id => $props->{master_id});
			$seconds = $master->duration if($master);
		}
		$self->{Duration} = Common::FormObject::Scalar->new(value => Common::FormObject::_secondsToMMSS($seconds));
	}

	$self->{AudioPreviewURL} = $self->_getTrackAudioURL();
}


sub _propertiesFromDefaults
{
	my ($self, $hrProperties, $albumID) = @_;

	my $album = RPS::Catalog::Album->new(albumID => $albumID, loadSubs => 0);
    assert($album);


	# let's figure out the max track number
	#
	my $nextTrackNum = RPS::DB::Item::Track->GetTrackCountByAlbumID($albumID);
	$nextTrackNum++;

    $hrProperties->{album_id} = $albumID;
    $hrProperties->{track_order} = $nextTrackNum;

    # We'll get the artist id from the album as well.
    #
    $hrProperties->{artist_id} = $album->ArtistID();


    $hrProperties->{media_type} = RPS::DB::Item::MediaType::kMediaTypeAudio;
    $hrProperties->{parental_advisory} = 'N';
}

sub save
{
    my ($self) = @_;

    my $dbObj = $self->_saveTrack();
    $self->_init(_dbItem => $dbObj);
}

# jpk - broke this out into an 'inner' method to make it easier to subclass
#
sub _saveTrack
{
    my ($self) = @_;


    # !!! This assumes AlbumID gets set before we get here.
    #
    # Get the album data, so we can set the artist name if necessary.
    #
    my $artistID;
    my $albumData = RPS::DB::Item::Album->Lookup(album_id => $self->AlbumID());
    if ($albumData)
    {
        $artistID = $albumData->artist_id;
    }

	# -------------------------------
	# Handle the Track artist here
	# -------------------------------

	# Translate artist name to artist id, creating the artist if necessary.
	# Use the $artistObj to set artist_id in the dbItem.
	#
    if ($self->ArtistName())
    {
	    my $artistObj;
	    $artistObj = RPS::DB::Item::Artist->Lookup(name => $self->ArtistName());
	    if(!defined $artistObj)
	    {
		    $artistObj = RPS::DB::Item::Artist->Create(name => $self->ArtistName());
            ## only good place to set the clean name for artists atm
            $artistObj->name_clean(Common::Util::clean_name_catalog($self->ArtistName()));
		    $artistObj->save();
	    }

        $artistID = $artistObj->artist_id;
    }

	my $masterID = $self->MasterID();


	# -------------------------------
	# Save myself (Track)
	# -------------------------------
	#
	my $trackDBObj;
	if ($self->TrackID())
	{
		$trackDBObj = RPS::DB::Item::Track->Lookup(track_id => $self->TrackID());
	}
	else
	{
		$trackDBObj = RPS::DB::Item::Track->Create();
	}


    # !!! This needs to change.
    # Track order is provided 'externally'.
    # We are using a scalar reference so that we can increment it for the next guy.
    #
#	$trackDBObj->track_order($$trackOrderRef++);
	$trackDBObj->track_order($self->TrackOrder());

	$trackDBObj->album_id($self->AlbumID());
	$trackDBObj->title($self->Title());
	$trackDBObj->mechanical_exempt($self->MechanicalExempt());
	$trackDBObj->ca_mechanical_exempt($self->CAMechanicalExempt());


    # !!! These fields have not been added to the form, yet.
    #
	$trackDBObj->client_track_id($self->ClientTrackID());
	$trackDBObj->genre_name($self->GenreName());
	$trackDBObj->media_type($self->MediaType());
	$trackDBObj->parental_advisory($self->ParentalAdvisory());
	$trackDBObj->custom_1($self->Custom1());
	$trackDBObj->custom_2($self->Custom2());
	$trackDBObj->custom_3($self->Custom3());

	# foreign keys
	#
	$trackDBObj->master_id($masterID);
	$trackDBObj->artist_id($artistID);


    # Derrive clean names
    #
	$trackDBObj->title_clean(Common::Util::clean_name_catalog($self->Title()));

	$trackDBObj->save();

    return $trackDBObj;

}

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

    my $audio = MediaServe::DB::Item::ProductTrackFile->LookupByTrackID( track_id => $self->TrackID );
	#Common::Log::Debug("-------- the 'audio' obj: " . Dumper($audio));
    my $audio_file = MediaServe::Audio::AudioFile->new(
                        clientID => Common::RSApp::GetClientID(),
                        id       => $audio->media_file_id )
        if( $audio );

	#Common::Log::Debug("-------- the 'audio_file' obj: " . Dumper($audio_file));
    return $audio_file ? $audio_file->url() : undef;
}
###
1;# Play nicely.
###
