Skip Menu |

This queue is for tickets about the SVN-Web CPAN distribution.

Report information
The Basics
Id: 18169
Status: resolved
Priority: 0/
Queue: SVN-Web

People
Owner: Nobody in particular
Requestors: mikee [...] s2technologies.com
Cc:
AdminCc:

Bug Information
Severity: Wishlist
Broken in: 0.46
Fixed in: (no value)



Subject: Mods to RSS.pm
I needed a few changes to the RSS feed: (1) I wanted the author name in the title, so I added it. (2) I need to truncate any long words (I chose 22 chars as the limit) in the message text. I consume the RSS feed in a side-bar reader that is part of a portal, so long words had a way of making the side-bar take-up too much real-estate. This is a strange hack, admittedly, but I didn't have any other way to configure my reader. (3) I actually wanted a few more characters in the description, so I increased it to 80. I'm submitting a patch file for your review. Maybe you will consider putting some/all of these changes into a future release. I suppose a better solution would be to make some of these params configurable. Thanks, Mike Ellery
Subject: patch_rss_mikee.txt
diff -Naur SVN-Web-0.46/lib/SVN/Web/RSS.pm SVN-Web-0.46_mine/lib/SVN/Web/RSS.pm --- SVN-Web-0.46/lib/SVN/Web/RSS.pm 2006-03-10 06:08:16.000000000 -0800 +++ SVN-Web-0.46_mine/lib/SVN/Web/RSS.pm 2006-03-13 16:12:15.744568000 -0800 @@ -62,15 +62,22 @@ }, ); - $_ && $rss->add_item - ( title => "$_->{rev} - ".substr ((split("\n",$_->{msg}, 1))[0], - 0, 40), - link => "$url/revision/?rev=$_->{rev}", - dc => { date => $_->{date}, - creator => $_->{author}, - }, - description => $_->{msg}, - ) for @{$self->{REVS}}[0..10]; + for (@{$self->{REVS}}[0..10]) { + if ($_) { + # truncate long words + $_->{msg} =~ s/(\S{22})\S+/$1.../gs; + $rss->add_item ( + title => "$_->{rev} - [$_->{author}] " + . substr ((split("\n",$_->{msg}, 1))[0], 0, 80), + link => "$url/revision/?rev=$_->{rev}", + dc => { + date => $_->{date}, + creator => $_->{author}, + }, + description => $_->{msg}, + ); + } + } return { mimetype => 'text/xml', body => $rss->as_string }; }
Mike, Guest via RT wrote: Show quoted text
> (1) I wanted the author name in the title, so I added it. > (2) I need to truncate any long words (I chose 22 chars as the limit) in > the message text. I consume the RSS feed in a side-bar reader that is > part of a portal, so long words had a way of making the side-bar take-up > too much real-estate. This is a strange hack, admittedly, but I didn't > have any other way to configure my reader. > (3) I actually wanted a few more characters in the description, so I > increased it to 80. > > I'm submitting a patch file for your review. Maybe you will consider > putting some/all of these changes into a future release. I suppose a > better solution would be to make some of these params configurable.
Many thanks for the patch. Sitting on the train this morning I've gone for a slightly different approach which is (hopefully) even more customisable. Previously, RSS.pm used XML::RSS to generate the feed. As you've seen, any changes to the feed content meant changing the code. Since the rest of SVN::Web uses templates I've modified RSS.pm to use a template as well. The template is used instead of XML::RSS. Accordingly, any changes to the feed content can now be made by changing the template, which is less invasive (and local template changes are probably easier to maintain between different versions of SVN::Web). Attached is the patch that implements these changes. I'd be grateful if you could apply this patch to your installation, and let me know if it solves the problem. N
=== Build.PL ================================================================== --- Build.PL (revision 810) +++ Build.PL (local) @@ -46,7 +46,6 @@ script_files => [ 'bin/svnweb-install', 'bin/svnweb-server' ], requires => { 'Template' => 0, 'YAML' => 0, - 'XML::RSS' => 0, 'Text::Diff' => 0, 'Text::Diff::HTML' => 0, 'Template::Plugin::Number::Format' => 0, === CHANGES.pod ================================================================== --- CHANGES.pod (revision 810) +++ CHANGES.pod (local) @@ -14,13 +14,21 @@ =item +Generation of RSS feeds is now done using a template, instead of using +L<XML::RSS>. This removes a dependency, and should make it easier to +customise the content of the RSS feed should you desire. + +This fixes rt#18169, reported by Mike Ellery <mikee@s2technologies.com>. + +=item + The formatting of timestamps is now configurable using L<POSIX/strftime>. You can choose how timestamps are formatted, and they can be displayed in UTC (the Subversion default), the server's local timezone, or the timezone of your choice. See L<SVN::Web/"Time and date formatting"> for details. -This fixes rt#18806, reported by Mike Ellery <mikee@s2technologies.com> +This fixes rt#18806, reported by Mike Ellery <mikee@s2technologies.com>. =item === lib/SVN/Web/RSS.pm ================================================================== --- lib/SVN/Web/RSS.pm (revision 810) +++ lib/SVN/Web/RSS.pm (local) @@ -20,62 +20,32 @@ =head1 DESCRIPTION -Generates an RSS feed of commits to a file or path in the Subversion +Generates an RSS feed of commits to a file or path in the Subversion repository. =head1 OPTIONS -None. +See L<SVN::Web::Log>. =head1 TEMPLATE VARIABLES -None. This action does not use a template. +See L<SVN::Web::Log>. =head1 EXCEPTIONS -None. +See L<SVN::Web::Log>. =cut sub run { my $self = shift; - my $data = eval { $self->SUPER::run(@_)->{data}; }; + my $data = $self->SUPER::run(@_)->{data}; - if(!defined $data) { - return - "<p>RSS error -- this file does not exist in the repository.</p>"; - } - - my $rss = new XML::RSS(version => '1.0'); - my $url = "http://$ENV{HTTP_HOST}$self->{script}/$self->{reposname}"; - - $rss->channel( - title => "subversion revisions of $self->{path}", - link => "$url/log$self->{path}", - dc => { - date => $self->{REVS}[0]{date}, - creator => 'SVN::Web', - publisher => "adm\@$ENV{HTTP_HOST}", - }, - syn => { - updatePeriod => "daily", - updateFrequency => "1", - updateBase => "1901-01-01T00:00+00:00", - }, - ); - - $_ && $rss->add_item( - title => "$_->{rev} - " - . substr((split("\n", $_->{msg}, 1))[0], 0, 40), - link => "$url/revision/?rev=$_->{rev}", - dc => { - date => $_->{date}, - creator => $_->{author}, - }, - description => $_->{msg}, - ) - for @{ $self->{REVS} }[0 .. 10]; - return { mimetype => 'text/xml', body => $rss->as_string }; + return { + template => 'rss', + mimetype => 'text/xml', + data => $data, + }; } 1; === lib/SVN/Web/Template/trac/browse ================================================================== --- lib/SVN/Web/Template/trac/browse (revision 810) +++ lib/SVN/Web/Template/trac/browse (local) @@ -1,3 +1,4 @@ +[% PROCESS header %] [% USE Number.Format %] [% USE cgi = CGI %] @@ -85,3 +86,4 @@ </tbody> </table> [% END %] +[% PROCESS footer %] === lib/SVN/Web/Template/trac/diff ================================================================== --- lib/SVN/Web/Template/trac/diff (revision 810) +++ lib/SVN/Web/Template/trac/diff (local) @@ -1,3 +1,4 @@ +[% PROCESS header %] [% USE cgi = CGI %] <h1>[%|l(script, repos, rev1, rev2)%](diff range)[%END%]</h1> @@ -11,3 +12,4 @@ [% body %]</li> </ul> </div> +[% PROCESS footer %] === lib/SVN/Web/Template/trac/list ================================================================== --- lib/SVN/Web/Template/trac/list (revision 810) +++ lib/SVN/Web/Template/trac/list (local) @@ -1,3 +1,4 @@ +[% PROCESS header %] [% IF reposcount %] <p> [%|l%](choose repos)[%END%] @@ -13,3 +14,4 @@ [%|l%](no repos)[%END%] </p> [% END %] +[% PROCESS footer %] === lib/SVN/Web/Template/trac/log ================================================================== --- lib/SVN/Web/Template/trac/log (revision 810) +++ lib/SVN/Web/Template/trac/log (local) @@ -1,3 +1,4 @@ +[% PROCESS header %] [% USE cgi = CGI %] [% IF ! isdir OR at_head %] @@ -64,4 +65,5 @@ </table> [% IF ! isdir %] </form> -[% END %] \ No newline at end of file +[% END %] +[% PROCESS footer %] === lib/SVN/Web/Template/trac/revision ================================================================== --- lib/SVN/Web/Template/trac/revision (revision 810) +++ lib/SVN/Web/Template/trac/revision (local) @@ -1,3 +1,4 @@ +[% PROCESS header %] [% class_with_action = { 'A' => 'add', 'M' => 'mod', 'D' => 'rem', @@ -107,3 +108,4 @@ </ul> [% END %] </div> +[% PROCESS footer %] === lib/SVN/Web/Template/trac/view ================================================================== --- lib/SVN/Web/Template/trac/view (revision 810) +++ lib/SVN/Web/Template/trac/view (local) @@ -1,3 +1,4 @@ +[% PROCESS header %] <p><a href="[% script %]/[% repos %]/log[% path | uri | html %][% revstr %]">[%|l%](view revision log)[%END%]</a> | <a href="[% script %]/[% repos %]/checkout[% path | uri | html %][% revstr %]">[%|l%](checkout)[%END%]</a></p> <table id="info" summary="[%|l%](revision log)[%END%]"> @@ -17,3 +18,4 @@ <p>This file can not be displayed in the browser. You can <a href="[% script %]/[% repos %]/checkout[% path | uri | html %]">download it</a>.</p> [% END %] </div> +[% PROCESS footer %] === lib/SVN/Web/Template/trac/x ================================================================== --- lib/SVN/Web/Template/trac/x (revision 810) +++ lib/SVN/Web/Template/trac/x (local) @@ -1,3 +1,5 @@ +[% PROCESS header %] <h1>An error occured</h1> +[% PROCESS footer %] <p>[% error_msg | html_para %]</p> === lib/SVN/Web/Template/trac/rss ================================================================== --- lib/SVN/Web/Template/trac/rss (revision 810) +++ lib/SVN/Web/Template/trac/rss (local) @@ -0,0 +1,41 @@ +<?xml version="1.0" encoding="UTF-8"?> + +<rdf:RDF + xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" + xmlns="http://purl.org/rss/1.0/" + xmlns:taxo="http://purl.org/rss/1.0/modules/taxonomy/" + xmlns:dc="http://purl.org/dc/elements/1.1/" + xmlns:syn="http://purl.org/rss/1.0/modules/syndication/" + xmlns:admin="http://webns.net/mvcb/" +> + +<channel rdf:about="[% script %]/[% repos %]/log[% path | uri | html %]"> + <title>Revision log of [% path | uri | html %]</title> + <link>[% script %]/[% repos %]/log[% path | uri | html %]</link> + <description></description> + <dc:date>[% revs.0.date %]</dc:date> + <dc:publisher>adm@localhost</dc:publisher> <!-- XXX Change this --> + <dc:creator>SVN::Web</dc:creator> + <syn:updatePeriod>daily</syn:updatePeriod> + <syn:updateFrequency>1</syn:updateFrequency> + <syn:updateBase>1901-01-01T00:00+00:00</syn:updateBase> + <items> + <rdf:Seq> + [%- FOREACH revs %] + <rdf:li rdf:resource="[% script %]/[% repos %]/revision?rev=[% rev %]" /> + [%- END %] + </rdf:Seq> + </items> +</channel> + +[% FOREACH revs %] +<item rdf:about="[% script %]/[% repos %]/revision?rev=[% rev %]"> + <title>[% rev %] - [% msg | truncate(80) | html %]</title> + <link>[% script %]/[% repos %]/revision?rev=[% rev %]></link> + <description>[% msg | log_msg %]</description> + <dc:creator>[% author %]</dc:creator> + <dc:date>[% date %]</dc:date> +</item> +[% END %] + +</rdf:RDF> === lib/SVN/Web.pm ================================================================== --- lib/SVN/Web.pm (revision 810) +++ lib/SVN/Web.pm (local) @@ -968,8 +968,6 @@ sub get_template { Template->new( { INCLUDE_PATH => $config->{templatedirs}, - PRE_PROCESS => 'header', - POST_PROCESS => 'footer', COMPILE_DIR => $config->{tt_compile_dir}, FILTERS => { l => ([\&loc_filter, 1]), === t/2basic.t ================================================================== --- t/2basic.t (revision 810) +++ t/2basic.t (local) @@ -6,7 +6,7 @@ use File::Spec; my $repospath; -my($can_tidy, $tidy); +my($can_tidy, $can_parse_rss, $tidy, $rss); BEGIN { plan skip_all => "Test::WWW::Mechanize not installed" @@ -16,6 +16,7 @@ unless `svnadmin --version` =~ /version/; $can_tidy = eval { require Test::HTML::Tidy; 1 }; + $can_parse_rss = eval { require XML::RSS::Parser; 1 }; plan 'no_plan'; $repospath = File::Spec->rel2abs("t/repos"); @@ -33,6 +34,10 @@ $tidy->ignore(text => qr/trimming empty <span>/); } +if($can_parse_rss) { + $rss = XML::RSS::Parser->new(); +} + my $url = 'http://localhost/svnweb'; use SVN::Web::Test ('http://localhost', '/svnweb', repos => $repospath); my $mech = SVN::Web::Test->new; @@ -70,6 +75,12 @@ or diag($mech->content()); } + if(($mech->uri() =~ m{/rss/}) and $can_parse_rss) { + my $parse_result = $rss->parse_string($mech->content()); + ok(defined $parse_result, 'RSS parsed successfully') + or diag $rss->errstr(), diag $mech->content(); + } + # diag $mech->content() if $mech->uri() !~ m{ /(?:rss|checkout)/ }x; my @links = $mech->links; diag 'Found ' . (scalar @links) . ' links' if $ENV{TEST_VERBOSE};
Templated RSS generation (along with tests for its validity) will be in 0.48, hopefully released by the end of the week. Thanks for the suggestion.