git.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCHv2 0/2] gitweb: Syntax highlighting support
@ 2010-04-27 19:34 Jakub Narebski
  2010-04-27 19:34 ` [PATCHv1 1/2] " Jakub Narebski
                   ` (2 more replies)
  0 siblings, 3 replies; 5+ messages in thread
From: Jakub Narebski @ 2010-04-27 19:34 UTC (permalink / raw)
  To: git; +Cc: Johannes Schindelin, Jakub Narebski, Petr Baudis

This series of patches is based originally on on Daniel Svensson's and
Sham Chukoury's work in gitweb-xmms2.git

Currently only 'highlight' standalone syntax highlighter from
http://www.andre-simon.de/ is supported.  Second patch in the series
reorganizes syntax highlighting code to make it easier to add (in the
future) support for other syntax highlighters, like source-highlight from
http://www.gnu.org/software/src-highlite, or some syntax higlighting Perl
module from CPAN like Text::Highlight or Syntax::Highlight::* modules.
Unfortunately the name of syntax to be used as parameter to syntax
highlighter (syntax highlighting engine) depends on highlighter, which would
complicate code a bit.

The list of currently supported file types do not cover all types that
'highlight' supports, but it is selected a bit, with syntax highlight for
git.git taking precedence.

Table of contents:
~~~~~~~~~~~~~~~~~~
 [PATCH 1/2] gitweb: Syntax highlighting support
 [PATCH 2/2] gitweb: Refactor syntax highlighting support

Shortlog:
~~~~~~~~~
Jakub Narebski (1):
  gitweb: Refactor syntax highlighting support

Johannes Schindelin (1):
  gitweb: Syntax highlighting support

Diffstat:
~~~~~~~~~
 gitweb/gitweb.css                      |   18 +++++++
 gitweb/gitweb.perl                     |   79 ++++++++++++++++++++++++++++++-
 t/t9500-gitweb-standalone-no-errors.sh |   29 ++++++++++++
 3 files changed, 123 insertions(+), 3 deletions(-)

-- 
Jakub Narebski

^ permalink raw reply	[flat|nested] 5+ messages in thread

* [PATCHv1 1/2] gitweb: Syntax highlighting support
  2010-04-27 19:34 [PATCHv2 0/2] gitweb: Syntax highlighting support Jakub Narebski
@ 2010-04-27 19:34 ` Jakub Narebski
  2010-04-27 19:34 ` [PATCHv2 2/2] gitweb: Refactor syntax " Jakub Narebski
  2010-04-27 20:32 ` [PATCHv2 0/2] gitweb: Syntax " Petr Baudis
  2 siblings, 0 replies; 5+ messages in thread
From: Jakub Narebski @ 2010-04-27 19:34 UTC (permalink / raw)
  To: git; +Cc: Johannes Schindelin, Jakub Narebski, Petr Baudis

From: Johannes Schindelin <johannes.schindelin@gmx.de>

It requires the 'highlight' program to do all the heavy-lifting.

This is loosely based on Daniel Svensson's and Sham Chukoury's work in
gitweb-xmms2.git (it cannot be cherry-picked, as gitweb-xmms2 first forked
wildly, then not contributed back, and then went stale).

[jn: cherry picked from bc1ed6aafd9ee4937559535c66c8bddf1864bec6
 in http://repo.or.cz/w/git/dscho.git, with a few changes]

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Jakub Narebski <jnareb@gmail.com>
---
This patch is unchanged from previous version.


Compared to the version in Dscho repository, it makes gitweb do line
numbering by itself, instead of making 'highlight' do it... and then
rewriting it to conform to the rest of gitweb.  It also leaves tab
expansion to gitweb, for 'blob' view to look the same with and without
syntax highlighting enabled.

The list of supported extensions is widened, and syntax is decided
based on basename, not on whole pathname (which might be a mistake).
Also the '.in' suffix is stripped if it is present (so 'git.spec.in'
file would use 'spec' syntax).

Note that gitweb.css contains default 'highlight' style, but perhaps
other style would be better fit for default gitweb CSS.

 gitweb/gitweb.css  |   18 ++++++++++++++
 gitweb/gitweb.perl |   65 +++++++++++++++++++++++++++++++++++++++++++++++++++-
 2 files changed, 82 insertions(+), 1 deletions(-)

diff --git a/gitweb/gitweb.css b/gitweb/gitweb.css
index 50067f2..4132aab 100644
--- a/gitweb/gitweb.css
+++ b/gitweb/gitweb.css
@@ -572,3 +572,21 @@ span.match {
 div.binary {
 	font-style: italic;
 }
+
+/* Style definition generated by highlight 2.4.5, http://www.andre-simon.de/ */
+
+/* Highlighting theme definition: */
+
+.num    { color:#2928ff; }
+.esc    { color:#ff00ff; }
+.str    { color:#ff0000; }
+.dstr   { color:#818100; }
+.slc    { color:#838183; font-style:italic; }
+.com    { color:#838183; font-style:italic; }
+.dir    { color:#008200; }
+.sym    { color:#000000; }
+.line   { color:#555555; }
+.kwa    { color:#000000; font-weight:bold; }
+.kwb    { color:#830000; }
+.kwc    { color:#000000; font-weight:bold; }
+.kwd    { color:#010181; }
diff --git a/gitweb/gitweb.perl b/gitweb/gitweb.perl
index c356e95..de18ebf 100755
--- a/gitweb/gitweb.perl
+++ b/gitweb/gitweb.perl
@@ -227,6 +227,36 @@ our %avatar_size = (
 # Leave it undefined (or set to 'undef') to turn off load checking.
 our $maxload = 300;
 
+# syntax highlighting
+our %highlight_type = (
+	# match by basename
+	'SConstruct' => 'py',
+	'Program' => 'py',
+	'Library' => 'py',
+	'Makefile' => 'make',
+	# match by extension
+	'\.py$' => 'py', # Python
+	'\.c$' => 'c',
+	'\.h$' => 'c',
+	'\.cpp$' => 'cpp',
+	'\.cxx$' => 'cpp',
+	'\.rb$' => 'ruby',
+	'\.java$' => 'java',
+	'\.css$' => 'css',
+	'\.php3?$' => 'php',
+	'\.sh$' => 'sh', # Bash / shell script
+	'\.pl$' => 'pl', # Perl
+	'\.js$' => 'js', # JavaScript
+	'\.tex$' => 'tex', # TeX and LaTeX
+	'\.bib$' => 'bib', # BibTeX
+	'\.x?html$' => 'xml',
+	'\.xml$' => 'xml',
+	'\.awk$' => 'awk',
+	'\.bat$' => 'bat', # DOS Batch script
+	'\.ini$' => 'ini',
+	'\.spec$' => 'spec', # RPM Spec
+);
+
 # You define site-wide feature defaults here; override them with
 # $GITWEB_CONFIG as necessary.
 our %feature = (
@@ -445,6 +475,19 @@ our %feature = (
 	'javascript-actions' => {
 		'override' => 0,
 		'default' => [0]},
+
+	# Syntax highlighting support. This is based on Daniel Svensson's
+	# and Sham Chukoury's work in gitweb-xmms2.git.
+	# It requires the 'highlight' program, and therefore is disabled
+	# by default.
+
+	# To enable system wide have in $GITWEB_CONFIG
+	# $feature{'highlight'}{'default'} = [1];
+
+	'highlight' => {
+		'sub' => sub { feature_bool('highlight', @_) },
+		'override' => 0,
+		'default' => [0]},
 );
 
 sub gitweb_get_feature {
@@ -5346,6 +5389,7 @@ sub git_blob {
 	open my $fd, "-|", git_cmd(), "cat-file", "blob", $hash
 		or die_error(500, "Couldn't cat $file_name, $hash");
 	my $mimetype = blob_mimetype($fd, $file_name);
+	# use 'blob_plain' (aka 'raw') view for files that cannot be displayed
 	if ($mimetype !~ m!^(?:text/|image/(?:gif|png|jpeg)$)! && -B $fd) {
 		close $fd;
 		return git_blob_plain($mimetype);
@@ -5353,6 +5397,25 @@ sub git_blob {
 	# we can have blame only for text/* mimetype
 	$have_blame &&= ($mimetype =~ m!^text/!);
 
+	my $have_highlight = gitweb_check_feature('highlight');
+	my $syntax;
+	if ($have_highlight && defined($file_name)) {
+		my $basename = basename($file_name, '.in');
+		foreach my $regexp (keys %highlight_type) {
+			if ($basename =~ /$regexp/) {
+				$syntax = $highlight_type{$regexp};
+				last;
+			}
+		}
+
+		if ($syntax) {
+			close $fd;
+			open $fd, quote_command(git_cmd(), "cat-file", "blob", $hash)." | ".
+			          "highlight --xhtml --fragment -t 8 --syntax $syntax |"
+				or die_error(500, "Couldn't open file or run syntax highlighter");
+		}
+	}
+
 	git_header_html(undef, $expires);
 	my $formats_nav = '';
 	if (defined $hash_base && (my %co = parse_commit($hash_base))) {
@@ -5404,7 +5467,7 @@ sub git_blob {
 			$line = untabify($line);
 			printf "<div class=\"pre\"><a id=\"l%i\" href=\"" . href(-replay => 1)
 				. "#l%i\" class=\"linenr\">%4i</a> %s</div>\n",
-			       $nr, $nr, $nr, esc_html($line, -nbsp=>1);
+			       $nr, $nr, $nr, $syntax ? $line : esc_html($line, -nbsp=>1);
 		}
 	}
 	close $fd
-- 
1.7.0.1

^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCHv2 2/2] gitweb: Refactor syntax highlighting support
  2010-04-27 19:34 [PATCHv2 0/2] gitweb: Syntax highlighting support Jakub Narebski
  2010-04-27 19:34 ` [PATCHv1 1/2] " Jakub Narebski
@ 2010-04-27 19:34 ` Jakub Narebski
  2010-04-27 20:32 ` [PATCHv2 0/2] gitweb: Syntax " Petr Baudis
  2 siblings, 0 replies; 5+ messages in thread
From: Jakub Narebski @ 2010-04-27 19:34 UTC (permalink / raw)
  To: git; +Cc: Johannes Schindelin, Jakub Narebski, Petr Baudis

This refactoring (adding guess_file_syntax and run_highlighter
subroutines) is meant to make it easier in the future to add support
for other syntax highlighing solutions, or make it smarter by not
re-running `git cat-file` second time.

Instead of looping over list of regexps (keys of %highlight_type hash),
make use of the fact that choosing syntax is based either on full
basename (%highlight_basename), or on file extension (%highlight_ext).

Add some basic test of syntax highlighting (with 'highlight' as
prerequisite) to t/t9500-gitweb-standalone-no-errors.sh test.

While at it make git_blob Perl style prettier.

Signed-off-by: Jakub Narebski <jnareb@gmail.com>
---
Compared to previous version, blob_syntax_highlight is now named
guess_file_syntax, and blob_highlight is now named run_highlighter.

Some comments were added, and some improved. %highlight_ext is now
in larger part generated.

 gitweb/gitweb.perl                     |  116 +++++++++++++++++---------------
 t/t9500-gitweb-standalone-no-errors.sh |   29 ++++++++
 2 files changed, 92 insertions(+), 53 deletions(-)

diff --git a/gitweb/gitweb.perl b/gitweb/gitweb.perl
index de18ebf..7d9b660 100755
--- a/gitweb/gitweb.perl
+++ b/gitweb/gitweb.perl
@@ -227,36 +227,6 @@ our %avatar_size = (
 # Leave it undefined (or set to 'undef') to turn off load checking.
 our $maxload = 300;
 
-# syntax highlighting
-our %highlight_type = (
-	# match by basename
-	'SConstruct' => 'py',
-	'Program' => 'py',
-	'Library' => 'py',
-	'Makefile' => 'make',
-	# match by extension
-	'\.py$' => 'py', # Python
-	'\.c$' => 'c',
-	'\.h$' => 'c',
-	'\.cpp$' => 'cpp',
-	'\.cxx$' => 'cpp',
-	'\.rb$' => 'ruby',
-	'\.java$' => 'java',
-	'\.css$' => 'css',
-	'\.php3?$' => 'php',
-	'\.sh$' => 'sh', # Bash / shell script
-	'\.pl$' => 'pl', # Perl
-	'\.js$' => 'js', # JavaScript
-	'\.tex$' => 'tex', # TeX and LaTeX
-	'\.bib$' => 'bib', # BibTeX
-	'\.x?html$' => 'xml',
-	'\.xml$' => 'xml',
-	'\.awk$' => 'awk',
-	'\.bat$' => 'bat', # DOS Batch script
-	'\.ini$' => 'ini',
-	'\.spec$' => 'spec', # RPM Spec
-);
-
 # You define site-wide feature defaults here; override them with
 # $GITWEB_CONFIG as necessary.
 our %feature = (
@@ -478,8 +448,8 @@ our %feature = (
 
 	# Syntax highlighting support. This is based on Daniel Svensson's
 	# and Sham Chukoury's work in gitweb-xmms2.git.
-	# It requires the 'highlight' program, and therefore is disabled
-	# by default.
+	# It requires the 'highlight' program present in $PATH,
+	# and therefore is disabled by default.
 
 	# To enable system wide have in $GITWEB_CONFIG
 	# $feature{'highlight'}{'default'} = [1];
@@ -3198,6 +3168,61 @@ sub blob_contenttype {
 	return $type;
 }
 
+# guess file syntax for syntax highlighting; return undef if no highlighting
+# the name of syntax can (in the future) depend on syntax highlighter used
+sub guess_file_syntax {
+	my ($highlight, $mimetype, $file_name) = @_;
+	return undef unless ($highlight && defined $file_name);
+
+	# configuration for 'highlight' (http://www.andre-simon.de/)
+	# match by basename
+	my %highlight_basename = (
+		#'Program' => 'py',
+		#'Library' => 'py',
+		'SConstruct' => 'py', # SCons equivalent of Makefile
+		'Makefile' => 'make',
+	);
+	# match by extension
+	my %highlight_ext = (
+		# main extensions, defining name of syntax;
+		# see files in /usr/share/highlight/langDefs/ directory
+		map { $_ => $_ }
+			qw(py c cpp rb java css php sh pl js tex bib xml awk bat ini spec tcl),
+		# alternate extensions, see /etc/highlight/filetypes.conf
+		'h' => 'c',
+		map { $_ => 'cpp' } qw(cxx c++ cc),
+		map { $_ => 'php' } qw(php3 php4),
+		map { $_ => 'pl'  } qw(perl pm), # perhaps also 'cgi'
+		'mak' => 'make',
+		map { $_ => 'xml' } qw(xhtml html htm),
+	);
+
+	my $basename = basename($file_name, '.in');
+	return $highlight_basename{$basename}
+		if exists $highlight_basename{$basename};
+
+	$basename =~ /\.([^.]*)$/;
+	my $ext = $1 or return undef;
+	return $highlight_ext{$ext}
+		if exists $highlight_ext{$ext};
+
+	return undef;
+}
+
+# run highlighter and return FD of its output,
+# or return original FD if no highlighting
+sub run_highlighter {
+	my ($fd, $highlight, $syntax) = @_;
+	return $fd unless ($highlight && defined $syntax);
+
+	close $fd
+		or die_error(404, "Reading blob failed");
+	open $fd, quote_command(git_cmd(), "cat-file", "blob", $hash)." | ".
+	          "highlight --xhtml --fragment --syntax $syntax |"
+		or die_error(500, "Couldn't open file or run syntax highlighter");
+	return $fd;
+}
+
 ## ======================================================================
 ## functions printing HTML: header, footer, error page
 
@@ -5397,24 +5422,10 @@ sub git_blob {
 	# we can have blame only for text/* mimetype
 	$have_blame &&= ($mimetype =~ m!^text/!);
 
-	my $have_highlight = gitweb_check_feature('highlight');
-	my $syntax;
-	if ($have_highlight && defined($file_name)) {
-		my $basename = basename($file_name, '.in');
-		foreach my $regexp (keys %highlight_type) {
-			if ($basename =~ /$regexp/) {
-				$syntax = $highlight_type{$regexp};
-				last;
-			}
-		}
-
-		if ($syntax) {
-			close $fd;
-			open $fd, quote_command(git_cmd(), "cat-file", "blob", $hash)." | ".
-			          "highlight --xhtml --fragment -t 8 --syntax $syntax |"
-				or die_error(500, "Couldn't open file or run syntax highlighter");
-		}
-	}
+	my $highlight = gitweb_check_feature('highlight');
+	my $syntax = guess_file_syntax($highlight, $mimetype, $file_name);
+	$fd = run_highlighter($fd, $highlight, $syntax)
+		if $syntax;
 
 	git_header_html(undef, $expires);
 	my $formats_nav = '';
@@ -5465,9 +5476,8 @@ sub git_blob {
 			chomp $line;
 			$nr++;
 			$line = untabify($line);
-			printf "<div class=\"pre\"><a id=\"l%i\" href=\"" . href(-replay => 1)
-				. "#l%i\" class=\"linenr\">%4i</a> %s</div>\n",
-			       $nr, $nr, $nr, $syntax ? $line : esc_html($line, -nbsp=>1);
+			printf qq!<div class="pre"><a id="l%i" href="%s#l%i" class="linenr">%4i</a> %s</div>\n!,
+			       $nr, href(-replay => 1), $nr, $nr, $syntax ? $line : esc_html($line, -nbsp=>1);
 		}
 	}
 	close $fd
diff --git a/t/t9500-gitweb-standalone-no-errors.sh b/t/t9500-gitweb-standalone-no-errors.sh
index 63b6b06..4f2b9b0 100755
--- a/t/t9500-gitweb-standalone-no-errors.sh
+++ b/t/t9500-gitweb-standalone-no-errors.sh
@@ -647,4 +647,33 @@ test_expect_success \
 	 gitweb_run "p=.git;a=summary"'
 test_debug 'cat gitweb.log'
 
+# ----------------------------------------------------------------------
+# syntax highlighting
+
+cat >>gitweb_config.perl <<\EOF
+$feature{'highlight'}{'override'} = 1;
+EOF
+
+highlight --version >/dev/null 2>&1
+if [ $? -eq 127 ]; then
+	say "Skipping syntax highlighting test, because 'highlight' was not found"
+else
+	test_set_prereq HIGHLIGHT
+fi
+
+test_expect_success HIGHLIGHT \
+	'syntax highlighting (no highlight)' \
+	'git config gitweb.highlight yes &&
+	 gitweb_run "p=.git;a=blob;f=file"'
+test_debug 'cat gitweb.log'
+
+test_expect_success HIGHLIGHT \
+	'syntax highlighting (highlighted)' \
+	'git config gitweb.highlight yes &&
+	 echo "#!/usr/bin/sh" > test.sh &&
+	 git add test.sh &&
+	 git commit -m "Add test.sh" &&
+	 gitweb_run "p=.git;a=blob;f=test.sh"'
+test_debug 'cat gitweb.log'
+
 test_done
-- 
1.7.0.1

^ permalink raw reply related	[flat|nested] 5+ messages in thread

* Re: [PATCHv2 0/2] gitweb: Syntax highlighting support
  2010-04-27 19:34 [PATCHv2 0/2] gitweb: Syntax highlighting support Jakub Narebski
  2010-04-27 19:34 ` [PATCHv1 1/2] " Jakub Narebski
  2010-04-27 19:34 ` [PATCHv2 2/2] gitweb: Refactor syntax " Jakub Narebski
@ 2010-04-27 20:32 ` Petr Baudis
  2010-04-27 20:49   ` Jakub Narebski
  2 siblings, 1 reply; 5+ messages in thread
From: Petr Baudis @ 2010-04-27 20:32 UTC (permalink / raw)
  To: Jakub Narebski; +Cc: git, Johannes Schindelin

  Hi!

On Tue, Apr 27, 2010 at 09:34:43PM +0200, Jakub Narebski wrote:
> This series of patches is based originally on on Daniel Svensson's and
> Sham Chukoury's work in gitweb-xmms2.git

  I have no major concerns, but I think it would be much simpler to just
have a single squashed-together patch.

  Acked-by: Petr Baudis <pasky@suse.cz>

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCHv2 0/2] gitweb: Syntax highlighting support
  2010-04-27 20:32 ` [PATCHv2 0/2] gitweb: Syntax " Petr Baudis
@ 2010-04-27 20:49   ` Jakub Narebski
  0 siblings, 0 replies; 5+ messages in thread
From: Jakub Narebski @ 2010-04-27 20:49 UTC (permalink / raw)
  To: Petr Baudis; +Cc: git, Johannes Schindelin

On Tue, 27 Apr 2010, Petr Baudis napisał:
> On Tue, Apr 27, 2010 at 09:34:43PM +0200, Jakub Narebski wrote:

> > This series of patches is based originally on on Daniel Svensson's and
> > Sham Chukoury's work in gitweb-xmms2.git
> 
>   I have no major concerns, but I think it would be much simpler to just
> have a single squashed-together patch.

Note that first patch in series have different authorship.  But perhaps
that doesn't matter much...

>   Acked-by: Petr Baudis <pasky@suse.cz>

Thanks.

-- 
Jakub Narebski
Poland

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2010-04-27 20:49 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2010-04-27 19:34 [PATCHv2 0/2] gitweb: Syntax highlighting support Jakub Narebski
2010-04-27 19:34 ` [PATCHv1 1/2] " Jakub Narebski
2010-04-27 19:34 ` [PATCHv2 2/2] gitweb: Refactor syntax " Jakub Narebski
2010-04-27 20:32 ` [PATCHv2 0/2] gitweb: Syntax " Petr Baudis
2010-04-27 20:49   ` Jakub Narebski

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).