#!/usr/bin/perl -w
# VERSION: 1.0b2 - myth2ipod
# Get the latest version, and change log at myth2ipod.com
# Author: Chris aka Wififun - email: wififun@myth2ipod.com 
# Contributions and testing by Paul Egli
# modified to use nuvexport by starv at juniks dot org

# Includes
	use DBI;
	use Getopt::Long;
	use File::Path;
	
# User variables
	my $portable = "ipod";
	my $feedfile = "/data/media/feed.php";
	my $feedpath = "/data/media/";
	my $wwwloc = "/data/srv/httpd/htdocs/";
	my $feedurl = "http://REPLACEME/ipodfeed/";
	my $nuvoptions ="--mode=iPod --nice=19 --cutlist --nodenoise --nodeinterlace --nomultipass";
	
# Some variables
	our ($dest, $format, $usage);
	our ($db_host, $db_user, $db_name, $db_pass, $video_dir);
	our ($hostname, $db_handle, $sql, $statement, $row_ref);
    our ($chanid, $start, $nuvfile, @nuvarray);	
	my $rebuild = '0';
	my $encode = '0';
	my $debug = '0';
	my $setup = '0';
	my $cut = '0';
	my( $rightnow ) = `date`; 

GetOptions ("rebuild" => \$rebuild,
			"encode"   => \$encode,
			"debug"	=>	\$debug,
			"setup" => \$setup,
			"cut" => \$cut);

if ($setup == 1){
		system("clear");
		print "Setup will do everything needed to run this script.\n";
		print "This has only been tested on KnoppMyth R5A22.\n";
		print "make sure you have edited the variables for your conguration.\n";
		my $cksetup = &promptUser("\nAre you sure you want to procceed?","n");
			if ($cksetup =~ "y") {
				DoSetup();
				exit;
			}
			print "Setup exited. Nothing done.\n";
		exit;
}
elsif ($rebuild == 1){
		GenerateRSSFeed();
		print "Rebuilding of RSS feed is complete.\n";
		exit;
}
else {
		Encode4Portable();
		print "$title is ready for your $portable\n";
		
		# Check to see if the feed file exists; if not, create it.
		if (! -e $feedfile) { 
		print "No feed file found. I will make one for you.\n";
		GenerateRSSFeed();
		print "All done.\n";
		}
}

sub Encode4Portable{
	if ($#ARGV != 1) { 
		print "Encoding requires options.\nusage: myth2ipod <options> DIRECTORY FILE\n"; 
		exit; 
	}
	
	# Get the show information
	$directory = $ARGV[0]; 
	$file = $ARGV[1]; 
	@file = split(/_/, $file);
		$chanid = $file[0];
		$start = substr $file[1],0,14;
		if($debug == 1){ print "$chanid\n$start\n"};
	if (! -e $directory."/".$file){
		print "Opps, the file ".$directory.$file." does not exist.\n";
		exit;
	}
	
	# Connect to the database
	PrepSQLRead();
	$db_handle = DBI->connect("dbi:mysql:database=$db_name:host=$db_host", $db_user, $db_pass)
	or die "Cannot connect to database: $!\n\n";
		$sql = "SELECT title, subtitle, description, category, starttime FROM recorded WHERE chanid = $chanid AND DATE_FORMAT(starttime,'%Y%m%d%H%i%s') = $start";

		$statement = $db_handle->prepare($sql)
			or die "Couldn't prepare query '$sql': $DBI::errstr\n";
		
		$statement->execute()
		or die "Couldn't execute query '$sql': $DBI::errstr\n";
		$row_ref = $statement->fetchrow_hashref();
		if($debug == 1){ print "$row_ref->{starttime}\n"};
	$title = $row_ref->{title}; 
	$subtitle = $row_ref->{subtitle};
	$recorddate = $row_ref->{starttime}; 
	$description = $row_ref->{description};
	$category = $row_ref->{category};
	$filename = $title."-".$subtitle."-".substr $start, 0, 8;
	$filename =~ s/ /_/g;
	$filename =~ s/&/+/g;
	$filename =~ s/\047//g;
    $filename =~ s/[^+0-9a-zA-Z_-]+/_/g;
    $filename =~ s/_$//g;
		
	printf("Starting nuvexport...\n"); 
		EncodeIt(); 
	printf("Nuvexport completed, starting xml generation...\n"); 
		CreateItemXML(); 
	printf("XML file created for \"$filename\" : Yipeee\n"); 
	printf("Cleaning up temporary files\n"); 
		$cmd = "rm -f $feedpath$chanid\_$start.temp.mp4";
		print $cmd."\n";
		if(system($cmd)) { print "Removing nuvexport temp file failed\n"; }
		
		# remove the cutlist incase we added it.
		if ($cut == 1){
		printf("Generating cutlist\n"); 
		$cmd = "/usr/bin/mythcommflag --chanid $chanid --starttime $start --clearcutlist";
		print $cmd."\n"; 
		if(system($cmd)) { print "It looks like I was not able to generate a cutlist.\n"; } 
		}
	return 0;
}

#
# Encode for Portable
#
sub EncodeIt { 
	# Create cutlist from commercial flagging if -cut was passed to the script
	if ($cut == 1){
	printf("Generating cutlist\n"); 
	$cmd = "/usr/local/bin/mythcommflag --chanid $chanid --starttime $start --gencutlist";
	print $cmd."\n"; 
	if(system($cmd)) { print "It looks like I was not able to generate a cutlist.\n"; } 
	}
	
	# Use nuvexport to do the work
	$cmd = "/usr/local/bin/nuvexport --chanid=$chanid --start=$start $nuvoptions --filename=$chanid\_$start.temp --path=$feedpath";
	print $cmd."\n"; 
	if(system($cmd)) { print "Nuvexport encoding seems to have failed\n"; } 
	
	# Now clean up the output so iPods with firmware 1.1 and above can use it
	$cmd = "/usr/bin/MP4Box -add $feedpath$chanid\_$start.temp.mp4 $feedpath$chanid\_$start.$portable.mp4";
	print $cmd."\n"; 
	if(system($cmd)) { print "MP4Box cleanup seems to have failed\n"; } 
	return 0;
}

#
# Create XML with <ITEM> tag for this video file
#
sub CreateItemXML {
		open(ITEM, ">$feedpath$chanid\_$start.$portable.xml");
			print ITEM "<item>\n";  
			print ITEM "<title>".&encodeForXML($title." - ".$subtitle)."</title>\n";
			print ITEM "<itunes:author>MythTV</itunes:author>\n";  
			print ITEM "<author>MythTV</author>\n";  
			print ITEM "<itunes:category text=\"TV Shows\"></itunes:category>\n";
			print ITEM "<comments>".&encodeForXML($file)."</comments>\n";  
			print ITEM "<description>".&encodeForXML($description)."</description>\n";  
			print ITEM "<pubDate>".$recorddate."</pubDate>\n";  
			print ITEM "<enclosure url=\"".&encodeForXML("$feedurl$chanid\_$start.$portable.mp4")."\" type=\"video/quicktime\" />\n";  
			print ITEM "<itunes:duration></itunes:duration>\n";  
			print ITEM "<itunes:keywords>".&encodeForXML($title." - ".$subtitle." - ".$category)."</itunes:keywords>\n";
			print ITEM "<category>".&encodeForXML($category)."</category>\n";			
			print ITEM "</item>\n";
			print "\"$filename\" has been added to the feed.\n";
		close(ITEM);
	return 0;
}

#
# Generate the RSS feed by combining the ITEM XML Files
#
sub GenerateRSSFeed {

	open(RSS, ">$feedfile");
		print RSS "<?php\n"; 
		print RSS "header(\"Content-Type: text/xml\");\n"; 
		print RSS "echo \"<?xml version=\\\"1.0\\\" encoding=\\\"UTF-8\\\"?>\"; ?>\n"; 
		print RSS "<rss xmlns:itunes=\"http://www.itunes.com/DTDs/Podcast-1.0.dtd\" version=\"2.0\">\n"; 
		print RSS "<channel>\n"; 
		print RSS "<title>MythTV - <? if (\$_GET['title'] == \"\") { \$title = \"*\"; echo \"Recorded Programs\"; }\n";
		print RSS "else { \$title = \$_GET['title']; echo str_replace(\"_\",\" \",\$_GET['title']); } ?> </title>\n";
		print RSS "<itunes:author>MythTV - myth2ipod</itunes:author>\n"; 
		print RSS "<link>".&encodeForXML($feedurl)."</link>\n";
		print RSS "<itunes:subtitle>Transcoded recording for your iPod Video.</itunes:subtitle>\n"; 
		print RSS "<itunes:summary>Myth TV Recorded Programs for the iPod v.1</itunes:summary>\n"; 
		print RSS "<description>Myth TV Recorded Programs for the iPod v.1</description>\n"; 
		print RSS "<itunes:owner>\n"; 
		print RSS "<itunes:name>MythTV</itunes:name>\n"; 
		print RSS "<itunes:email>mythtv\@localhost</itunes:email>\n"; 
		print RSS "</itunes:owner>\n"; 
		print RSS "<itunes:explicit>No</itunes:explicit>\n"; 
		print RSS "<language>en-us</language>\n"; 
		print RSS "<copyright>Copyright 2005.</copyright>\n"; 
		print RSS "<webMaster>mythtv\@localhost</webMaster>\n"; 
		print RSS "<itunes:image href=\"http://myth2ipod.com/mythipod_200.jpg\" />\n"; 
		print RSS "<itunes:category text=\"TV Shows\"></itunes:category>\n"; 
		print RSS "<category>TV Shows</category>\n";
		print RSS "<itunes:image href=\"http://myth2ipod.com/mythipod_200.jpg\"/>";
		print RSS "<image>"; 
		print RSS "<url>http://myth2ipod.com/mythipod_200.jpg</url>\n";
		print RSS "<title>MythTV 2 iPod</title>\n";
		print RSS "<link>".&encodeForXML($feedurl)."</link>\n";	
		print RSS "<width>200</width>\n";		
		print RSS "<height>200</height>\n";		
		print RSS "</image>\n";
		print RSS "<? foreach (glob(\$title\.\"*\.$portable\.xml\") as \$file) {include \$file;} ?>\n";
		print RSS "</channel>\n"; 
		print RSS "</rss>\n";
 	close(RSS);
	if($debug == 1){ print "I created a feed file, was I supposed to?\n"};

	return 0;
}

# substitute for XML entities
sub encodeForXML {
	local $result;
	$result = $_[0];
	$result =~ s/&/&amp;/g;
	$result =~ s/</&lt;/g;
	$result =~ s/>/&gt;/g;
	$result;
}


#
# This code taken from one of the mythlink.sh scripts to get MySQL information
#
sub PrepSQLRead{
# Get the hostname of this machine
    $hostname = `hostname`;
    chomp($hostname);
    
# Read the mysql.txt file in use by MythTV.
# could be in a couple places, so try the usual suspects
    my $found = 0;
    my @mysql = ('/usr/local/share/mythtv/mysql.txt',
                 '/usr/share/mythtv/mysql.txt',
                 '/etc/mythtv/mysql.txt',
                 '/usr/local/etc/mythtv/mysql.txt',
                 "$ENV{HOME}/.mythtv/mysql.txt",
                 'mysql.txt'
                );
    foreach my $file (@mysql) {
        next unless (-e $file);
        $found = 1;
        open(CONF, $file) or die "Unable to open $file:  $!\n\n";
        while (my $line = <CONF>) {
        # Cleanup
            next if ($line =~ /^\s*#/);
            $line =~ s/^str //;
            chomp($line);
        # Split off the var=val pairs
            my ($var, $val) = split(/\=/, $line, 2);
            next unless ($var && $var =~ /\w/);
            if ($var eq 'DBHostName') {
                $db_host = $val;
            }
            elsif ($var eq 'DBUserName') {
                $db_user = $val;
            }
            elsif ($var eq 'DBName') {
                $db_name = $val;
            }
            elsif ($var eq 'DBPassword') {
                $db_pass = $val;
            }
        # Hostname override
            elsif ($var eq 'LocalHostName') {
                $hostname = $val;
            }
        }
        close CONF;
    }
    die "Unable to locate mysql.txt:  $!\n\n" unless ($found && $db_host);
    return 0;
}

sub promptUser {
   local($promptString,$defaultValue) = @_;
   if ($defaultValue) {
      print $promptString, "[", $defaultValue, "]: ";
   } else {
      print $promptString, ": ";
   }

   $| = 1;               # force a flush after our print
   $_ = <STDIN>;         # get the input from STDIN (presumably the keyboard)
   chomp;
   if ("$defaultValue") {
      return $_ ? $_ : $defaultValue;    # return $_ if it has a value
   } else {
      return $_;
   }
}

sub DoSetup {
	print "\nNot ready yet. How do you send the cd command from perl?\n";
	return 0;
}