2 # -*- coding: ascii -*-
5 # Copyright (C) 2010-2011 Toni Gundogdu <legatvs@gmail.com>
7 # This program is free software: you can redistribute it and/or modify
8 # it under the terms of the GNU General Public License as published by
9 # the Free Software Foundation, either version 3 of the License, or
10 # (at your option) any later version.
12 # This program is distributed in the hope that it will be useful,
13 # but WITHOUT ANY WARRANTY; without even the implied warranty of
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 # GNU General Public License for more details.
17 # You should have received a copy of the GNU General Public License
18 # along with this program. If not, see <http://www.gnu.org/licenses/>.
24 use version
0.77 (); our $VERSION = version
->declare("2.3.3");
26 binmode STDOUT
, ":utf8";
27 binmode STDERR
, ":utf8";
29 use Getopt
::ArgvFile
qw(argvFile);
31 use Getopt
::Long
qw(:config bundling);
32 use Encode
qw(decode_utf8);
35 my $depr_msg = "Warning:
36 '--format list' is deprecated and will be removed in the later
37 versions. Use --query-formats instead.";
39 my $quvi_quiet_switch = '-q';
49 return process_queue
();
54 if (grep {$_ eq "--config-file"} @ARGV)
56 argvFile
(fileOption
=> '--config-file');
63 "@/usr/local/share/clive/cliverc",
64 "@/usr/share/clive/cliverc",
66 "@/etc/xdg/clive/clive.conf",
67 "@/etc/xdg/clive.conf"
76 '@' . "$ENV{HOME}/.cliverc",
77 '@' . "$ENV{HOME}/.clive/config",
78 '@' . "$ENV{HOME}/.config/clive/config"
83 push @ARGV, '@' . "$ENV{CLIVE_CONFIG}" if $ENV{CLIVE_CONFIG
};
90 'help' => \
&print_help
,
91 'version' => sub {print "clive version $VERSION\n"; exit 0},
92 'license' => \
&print_license
,
94 'query_formats|query-formats|F',
96 'output_file|output-file|O=s',
97 'no_download|no-download|n',
101 'get_with|get-with=s',
102 'filename_format|filename-format=s',
107 $config{format
} ||= 'default';
108 $config{filename_format
} ||= '%t.%s';
109 $config{regexp
} ||= '/(\\w|\\s)/g';
112 unless ($config{quvi
})
114 print "Detect quvi from \$PATH\n" unless $config{quiet
};
116 my $s = detect_cmd
('quvi');
119 $config{quvi
} = "quvi %u";
123 croak
"error: specify path to quvi(1) command with --quvi\n";
130 unless ($config{get_with
})
133 print "Detect a download command from \$PATH\n"
134 unless $config{quiet
};
137 curl
=> "-L -C - -o %f %u --user-agent Mozilla/5.0",
139 # Add new ones below.
144 my $s = detect_cmd
($k);
147 $config{get_with
} = "$k $h{$k}";
152 croak
"error: specify path to a download command with --get-with\n"
153 unless $config{get_with
};
162 if (scalar @ARGV == 0)
164 append_queue
($_) while <STDIN
>;
173 or print STDERR
"$_: $!\n" and next;
174 append_queue
($_) while <$fh>;
184 @queue = uniq2
(@queue); # Remove duplicate URLs.
186 print STDERR
"error: no input urls\n" and exit 0x3 # QUVI_INVARG
187 unless scalar @queue;
190 $| = 1; # Go unbuffered.
197 print " Check for $cmd ..." unless $config{quiet
};
198 my $o = join '', qx|$cmd --version
2>/dev/null
|;
203 # TODO: Use more a elegant regexp combining all three.
205 (qr
|(\d
+.\d
+.\d
+-\w
+-\w
+)|, qr
|(\d
+.\d
+.\d
+)|, qr
|(\d
+.\d
+)|);
210 print "$1\n" unless $config{quiet
};
217 print "no\n" unless $config{quiet
};
224 return $_ =~ /^\w+\:\/\
//;
229 my $ln = trim
(shift);
232 return if $ln =~ /^$/;
233 return if $ln =~ /^#/;
239 { # http://is.gd/g8jQU
257 my $n = scalar @queue;
264 print_checking
(++$i, $n);
266 my $q = $config{quvi
};
268 $q .= " $quvi_quiet_switch"
269 if $q !~ /$quvi_quiet_switch/; # Force quiet.
270 $q .= " -f $config{format}";
271 $q .= " -F" if $config{query_formats
};
273 my $o = join '', qx/$q/;
278 print "done.\n" unless $config{quiet
};
279 print $o and next if $config{query_formats
};
281 $media = JSON
::XS
::decode_json
($o);
282 ($r, $fpath) = get_media
();
285 $r = invoke_exec
($fpath) if $config{exec};
293 return if $config{quiet
};
297 print "($i of $n) " if $n > 1;
298 print "Checking ...";
303 require File
::Basename
;
305 my $fpath = get_filename
();
306 my $fname = File
::Basename
::basename
($fpath);
308 if ($config{no_download
}) {print_media
($fname); return 0;}
310 write_media
($fpath, $fname);
317 my $e = $config{exec};
318 $e =~ s/%f/"$fpath"/g;
325 sub to_mb
{(shift) / (1024 * 1024);}
329 printf "%s %.2fM [%s]\n",
331 to_mb
($media->{link}[0]->{length_bytes
}),
332 $media->{link}[0]->{content_type
};
337 my ($fpath, $fname) = @_;
339 my $g = $config{get_with
};
340 $g =~ s/%u/"$media->{link}[0]->{url}"/g;
341 $g =~ s/%f/"$fpath"/g;
342 $g =~ s/%n/"$fname"/g;
353 if ($config{output_file
}) {$fpath = $config{output_file
};}
354 else {$fpath = apply_output_path
(apply_filename_format
());}
359 sub apply_output_path
364 my $cwd = decode_utf8
(Cwd
::getcwd
);
367 require File
::Spec
::Functions
;
369 File
::Spec
::Functions
::catfile
($cwd, $fname);
372 sub apply_filename_format
374 return $config{output_filename
}
375 if $config{output_filename
};
377 my $title = trim
(apply_regexp
($media->{page_title
}));
378 my $fname = $config{filename_format
};
380 $fname =~ s/%s/$media->{link}[0]->{file_suffix}/g;
381 $fname =~ s/%h/$media->{host}/g if $media->{host
}; # quvi 0.2.8+
382 $fname =~ s/%i/$media->{id}/g;
383 $fname =~ s/%t/$title/g;
399 my ($title, $rq) = (shift, qr
|^/(.*)/(.*)$|);
401 if ($config{regexp
} =~ /$rq/)
403 return unless $title; # Must be a syntax check.
405 $title = decode_utf8
($title); # Do not touch.
407 my ($pat, $flags, $g, $i) = ($1, $2);
411 $g = ($flags =~ /g/);
412 $i = ($flags =~ /i/);
415 $rq = $i ? qr
|$pat|i
: qr
|$pat|;
418 ?
join '', $title =~ /$rq/g
419 : join '', $title =~ /$rq/;
422 croak
"error: --regexp: expects "
423 . "`/pattern/flags', for example: `/(\\w)/g'\n";
426 sub detect_quvi_version
428 my $q = (split /\s+/, $config{quvi
})[0]; # Improve this.
429 my $o = qx|$q --version
|;
432 return ($1, $2, $3) if (split /\n/, $o)[0] =~ /(\d+).(\d+).(\d+)/;
434 print "warning: unable to detect quvi version\n"
435 unless $config{quiet
};
441 my @v = detect_quvi_version
();
442 $quvi_quiet_switch = '-vq' if $v[0] >= 0 && $v[1] >= 4 && $v[2] >= 1;
447 if ($config{format
} eq "help")
450 --format arg get format arg of media
451 --format list print domains with formats
452 --format list arg match arg to supported domain names
454 --format list youtube print youtube formats
455 --format fmt34_360p get format fmt34_360p of media
460 elsif ($config{format
} eq "list")
462 my $q = (split /\s+/, $config{quvi
})[0]; # Improve this.
465 foreach (qx/$q --support/)
467 my ($k, $v) = split /\s+/, $_;
472 if (scalar @ARGV > 0)
475 foreach (sort keys %h)
477 print "$_:\n $h{$_}\n" if $_ =~ /$ARGV[0]/;
484 print "$_:\n $h{$_}\n\n" foreach sort keys %h;
487 printf "%s\n", $depr_msg;
496 Pod
::Usage
::pod2usage
(-exitstatus
=> 0, -verbose
=> 1);
502 # Copyright (C) 2010-2011 Toni Gundogdu <legatvs\@gmail.com>
504 # This program is free software: you can redistribute it and/or modify
505 # it under the terms of the GNU General Public License as published by
506 # the Free Software Foundation, either version 3 of the License, or
507 # (at your option) any later version.
509 # This program is distributed in the hope that it will be useful,
510 # but WITHOUT ANY WARRANTY; without even the implied warranty of
511 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
512 # GNU General Public License for more details.
514 # You should have received a copy of the GNU General Public License
515 # along with this program. If not, see <http://www.gnu.org/licenses/>.
524 clive [-F] [-n] [--format=E<lt>value<gt>] [--output-file=E<lt>value<gt>]
525 [--filename-format=E<lt>valueE<gt>] [--config-file=E<lt>value<gt>]
526 [--quvi=E<lt>valueE<gt>] [--get-with=E<lt>valueE<gt>]
527 [--regexp=E<lt>valueE<gt>] [--exec=E<lt>valueE<gt>]
528 [--help] [--version] [--license] [--quiet]
529 [E<lt>urlE<gt> | E<lt>fileE<gt>]
533 --help Print help and exit
534 --version Print version and exit
535 --license Print license and exit
536 --quiet Turn off all output excl. errors
537 -F, --query-formats Query available formats to URL
538 -f, --format arg (=default) Download media format
539 -O, --output-file arg Write media to arg
540 -n, --no-download Do not download media, print details
541 --config-file arg File to read clive arguments from
543 --quvi arg Path to quvi(1) with additional args
544 --get-with arg Path to download command with args
545 --filename-format arg (=%t.%s) Downloaded media filename format
546 --regexp arg (=/(\w|\s)/g) Regexp to cleanup media title
547 --exec arg Invoke arg after each finished download
551 # vim: set ts=2 sw=2 tw=72 expandtab: