#!/usr/bin/perl -w # # $Id: multimedia.pl,v 1.1 2007-05-15 21:30:41 keramida Exp $ # $FreeBSD$ # use strict; use XML::Parser; use Data::Dumper; use POSIX; my @months=( "","January","February","March", "April","May","June","July", "August","September","October", "November","December" ); my @createdfiles=(); my @tree=(); my @values=(); my $treeindex=-1; my @items; my $ci=-1; my %sources; my $sid=""; my %tags; sub addtags { my $tags=shift; if ($tags) { my @w=split(/,/,$tags); foreach my $w (@w) { $tags{$w}=0 if (!defined $tags{$w}); $tags{$w}++; } return; } my $array=shift; my @array=@{$array}; foreach my $w (@array) { $tags{$w}=0 if (!defined $tags{$w}); $tags{$w}++; } } sub xml_start { my $expat=shift; my $element=shift; $tree[++$treeindex]=$element; while (defined (my $attribute=shift)) { $values[$treeindex]{$attribute}=shift; } if ($element eq "item" && $treeindex==2) { $ci++; $items[$ci]=(); $items[$ci]{source}=$values[$treeindex]{source}; $items[$ci]{added}=$values[$treeindex]{added}; $items[$ci]{ci}=$ci; $items[$ci]{fc}=-1; } if ($element eq "source" && $treeindex==2) { $sid=$values[$treeindex]{id}; $sources{$values[$treeindex]{id}}=(); } } sub xml_end { my $expat=shift; my $element=shift; $values[$treeindex]=(); $treeindex--; } sub xml_char { my $expat=shift; my $value=shift; if ($tree[0] eq "multimedia") { return if ($treeindex==0); if ($tree[1] eq "items") { return if ($treeindex==1); if ($tree[2] eq "item") { return if ($treeindex==2); if ($tree[3] eq "title") { $items[$ci]{title}=$value; return; } if ($tree[3] eq "desc") { $items[$ci]{desc}="" if (!defined $items[$ci]{desc}); $items[$ci]{desc}.=$value; return; } if ($tree[3] eq "overview") { $items[$ci]{overview}=$value; return; } if ($tree[3] eq "link") { $items[$ci]{link}=$value; return; } if ($tree[3] eq "tags") { @{$items[$ci]{tags}}=split(/,/,$value); addtags($value); return; } if ($tree[3] eq "files") { return if ($treeindex==3); if ($tree[4] eq "prefix") { $items[$ci]{prefix}="" if (!defined $items[$ci]{prefix}); $items[$ci]{prefix}.=$value; return; } if ($tree[4] eq "file") { return if ($treeindex==4); if ($tree[5] eq "url") { $items[$ci]{fc}++; $items[$ci]{files}{$items[$ci]{fc}}{url}=$value; return; } if ($tree[5] eq "size") { $items[$ci]{files}{$items[$ci]{fc}}{size}=$value; return; } if ($tree[5] eq "length") { $items[$ci]{files}{$items[$ci]{fc}}{length}=$value; return; } if ($tree[5] eq "desc") { $items[$ci]{files}{$items[$ci]{fc}}{desc}=$value; return; } if ($tree[5] eq "tags") { @{$items[$ci]{files}{$items[$ci]{fc}}{tags}}=split(/,/,$value); addtags($value); addtags("",$items[$ci]{tags}); return; } goto error; } goto error; } goto error; } goto error; } if ($tree[1] eq "sources") { return if ($treeindex==1); if ($tree[2] eq "source") { return if ($treeindex==2); if ($tree[3] eq "name") { $sources{$sid}{name}=$value; return; } if ($tree[3] eq "url") { $sources{$sid}{url}=$value; return; } goto error; } goto error; } goto error; } error: print "Unknown item at depth $treeindex: $tree[$treeindex]\n"; } my $p=new XML::Parser( Handlers => { Start => \&xml_start, End => \&xml_end, Char => \&xml_char, } ); $p->parsefile("multimedia-input.xml"); my @site_order=(); { sub site_sort { my %a=%{$a}; my %b=%{$b}; return $a{source} cmp $b{source} if ($a{source} ne $b{source}); return $a{title} cmp $b{title}; } @site_order=sort site_sort @items; } my @date_order=(); { my %dates=(); foreach my $item (@items) { my %item=%{$item}; $dates{$item{ci}}=$item{added}; } my @dates=keys(%dates); @date_order=sort { $dates{$b} cmp $dates{$a} } @dates; } # # HTML overview output # sub print_htmlitem { my $item=shift; my %item=%{$item}; my $source=shift; my %source=%{$source}; print FOUT "
  • "; if (defined $item{overview}) { print FOUT "$item{title}\n"; } else { my %media=%{$item{files}{0}}; print FOUT "$item{title}\n"; if (defined $media{size} || defined $media{length}) { my $s=""; print FOUT "("; if (defined $media{size}) { print FOUT "$media{size}"; $s=", "; } if (defined $media{length}) { print FOUT "$s$media{length}"; $s=", "; } print FOUT ")"; } } print FOUT "
    Source: ",$source{name},"
    \n"; print FOUT "Tags: ",join(", ",@{$item{tags}}),"
    \n"; if (defined $item{overview} && defined $item{files}) { my $c=0; foreach my $m (keys(%{$item{files}})) { my %file=%{$item{files}{$m}}; print FOUT ", " if ($c++); if (defined $item{prefix}) { print FOUT "$file{desc}"; } else { print FOUT "$file{desc}"; } if (defined $file{size} || defined $file{length}) { my $s=""; print FOUT " ("; if (defined $file{size}) { print FOUT "$file{size}"; $s=", "; } if (defined $file{length}) { print FOUT "$s$file{length}"; $s=", "; } print FOUT ")"; } } print FOUT "
    \n"; } print FOUT "$item{desc}\n"; } { $createdfiles[$#createdfiles+1]="multimedia.html"; open(FOUT,">multimedia.html"); open(FIN,"multimedia.html.pre"); my @lines=; close(FIN); print FOUT @lines; open(FIN,"multimedia.html.intro"); @lines=; close(FIN); print FOUT @lines; print FOUT "

    Newest resources

    \n"; my $month=""; foreach my $order (@date_order) { my %item=%{$items[$order]}; my %source=%{$sources{$item{source}}}; if (substr($item{added},0,6) ne $month) { print FOUT "

    ",$months[substr($item{added},4,2)+0]," ",substr($item{added},0,4),"

    \n"; open(FIN,"multimedia.html.post"); @lines=; close(FIN); print FOUT @lines; close(FOUT); } # # HTML cloud output # { $createdfiles[$#createdfiles+1]="multimedia-tags.html"; open(FOUT,">multimedia-tags.html"); open(FIN,"multimedia.html.pre"); my @lines=; close(FIN); print FOUT @lines; open(FIN,"multimedia.html.intro"); @lines=; close(FIN); print FOUT @lines; print FOUT "

    Tags

    \n"; my $month=""; sub size { return $b cmp $a if ($tags{$b}==$tags{$a}); return $tags{$b} <=> $tags{$a}; } my $size=20; my $c=0; foreach my $tag (sort size(keys(%tags))) { my $ftag=$tag; $ftag=~s/ /_/g; print FOUT "$tag\n"; $size-- if ($c++%10==0 && $size>2); } open(FIN,"multimedia.html.post"); @lines=; close(FIN); print FOUT @lines; close(FOUT); } # # HTML per-tags output # { foreach my $tag (keys(%tags)) { my $ftag=$tag; $ftag=~s/ /_/g; $createdfiles[$#createdfiles+1]="multimedia-tag-$ftag.html"; open(FOUT,">multimedia-tag-$ftag.html"); open(FIN,"multimedia.html.pre"); my @lines=; close(FIN); print FOUT @lines; open(FIN,"multimedia.html.intro"); @lines=; close(FIN); print FOUT @lines; print FOUT "

    Tag: $tag

    \n"; print FOUT "
      \n"; foreach my $item (@items) { my %item=%{$item}; my %source=%{$sources{$item{source}}}; my $found=0; foreach my $itag (@{$item{tags}}) { if ($itag eq $tag) { $found=1; last; } } if (!$found) { foreach my $file (keys(%{$item{files}})) { my %file=%{$item{files}{$file}}; foreach my $itag (@{$file{tags}}) { if ($itag eq $tag) { $found=1; last; } } } } print_htmlitem(\%item,\%source) if ($found); } print FOUT "
    \n"; open(FIN,"multimedia.html.post"); @lines=; close(FIN); print FOUT @lines; close(FOUT); } } # # HTML all-sources output # { $createdfiles[$#createdfiles+1]="multimedia-sources.html"; open(FOUT,">multimedia-sources.html"); open(FIN,"multimedia.html.pre"); my @lines=; close(FIN); print FOUT @lines; open(FIN,"multimedia.html.intro"); @lines=; close(FIN); print FOUT @lines; print FOUT "

    Sources

    \n"; print FOUT "
      \n"; my $lastsource=""; foreach my $item (@site_order) { my %item=%{$item}; next if ($lastsource eq $item{source}); $lastsource=$item{source}; print FOUT "
    • ",$sources{$item{source}}{name},"\n"; } print FOUT "
    \n"; open(FIN,"multimedia.html.post"); @lines=; close(FIN); print FOUT @lines; close(FOUT); } # # HTML per-source output # { my $lastsource=""; foreach my $item (@site_order) { my %item=%{$item}; my %source=%{$sources{$item{source}}}; if ($lastsource ne $item{source}) { if ($lastsource) { print FOUT "\n"; open(FIN,"multimedia.html.post"); my @lines=; close(FIN); print FOUT @lines; close(FOUT); } $createdfiles[$#createdfiles+1]="multimedia-source-$item{source}.html"; open(FOUT,">multimedia-source-$item{source}.html"); open(FIN,"multimedia.html.pre"); my @lines=; close(FIN); print FOUT @lines; open(FIN,"multimedia.html.intro"); @lines=; close(FIN); print FOUT @lines; $lastsource=$item{source}; print FOUT "

    $source{name}

    \n"; print FOUT "
      \n"; } print_htmlitem(\%item,\%source); } print FOUT "
    \n"; open(FIN,"multimedia.html.post"); my @lines=; close(FIN); print FOUT @lines; close(FOUT); } # # XML output # { sub htmlentities { my $s=shift; $s=~s/&/&/g; $s=~s//>/g; return $s;; } sub printxml_multiple { my $item=shift; my %item=%{$item}; my $source=shift; my %source=%{$source}; return if ($item{fc}<0); for (my $i=0;$i<=$item{fc};$i++) { my %f=%{$item{files}{$i}}; my %tempitem=%item; $tempitem{title}.=" - $f{desc}"; $f{url}="$item{prefix}/$f{url}" if (defined $item{prefix}); printxml_single(\%tempitem,\%source,\%f); } } sub printxml_single { my $item=shift; my %item=%{$item}; my $source=shift; my %source=%{$source}; my $file=shift; my %file=%{$file}; my $date=POSIX::strftime("%a, %d %b %Y %H:%M:%S %Z", 0,0,0,substr($item{added},6,2),substr($item{added},4,2)-1,substr($item{added},0,4)-1900); my $tags=join(", ",@{$item{tags}}); for my $tag (@{$file{tags}}) { $tags.=", $tag"; } print FOUT "\n"; print FOUT "",htmlentities("$source{name} - $item{title}"),"\n"; print FOUT "",htmlentities($file{url}),"\n"; print FOUT "$date\n"; print FOUT "\n"; print FOUT ""; print FOUT htmlentities("$item{title}
    From: $source{name}
    "); print FOUT htmlentities("Tags: $tags
    \n"); print FOUT htmlentities("$item{desc}"); print FOUT "
    \n"; print FOUT "
    \n"; } $createdfiles[$#createdfiles+1]="multimedia.xml"; open(FOUT,">multimedia.xml"); my @s=stat("multimedia-input.xml"); my $date=POSIX::strftime("%a, %d %b %Y %H:%M:%S %Z",localtime($s[9])); print FOUT < FreeBSD Multimedia Resources List FreeBSD Multimedia Resources http://www.FreeBSD.org/docs/multimedia.html $date EOF foreach my $order (@date_order) { my %item=%{$items[$order]}; my %source=%{$sources{$item{source}}}; if (defined $item{overview}) { printxml_multiple(\%item,\%source); } else { printxml_single(\%item,\%source,$item{files}{0}); } } print FOUT < EOF close(FOUT); } # # Created files # { open(FOUT,">multimedia.created"); foreach my $f (@createdfiles) { print FOUT "$f\n"; } close(FOUT); }