Convert diff output to colorized HTML
If you search the web you can find a number of references to programs/scripts that convert diff output to HTML. This is a bash version.
The script expects "unified" diff output (diff -u) on its standard input and produces a self-contained colorized HTML page on its standard output. Consider the two files:
#include <stdio.h>
// main
main()
{
printf("Hello world\n");
}
#include <stdio.h>
main()
{
printf("Hello World\n");
printf("Goodbye cruel world\n");
}
$ diff -u v1.c v2.c | diff2html >v1-v2.htmlThe resulting page is:
--- v1.c 2008-08-27 13:04:40.000000000 -0500
+++ v2.c 2008-08-27 13:04:29.000000000 -0500
@@ -1,8 +1,8 @@
#include <stdio.h>
-// main
main()
{
- printf("Hello world\n");
+ printf("Hello World\n");
+ printf("Goodbye cruel world\n");
}
The script follows:
#!/bin/bash
#
# Convert diff output to colorized HTML.
cat <<XX
<html>
<head>
<title>Colorized Diff</title>
</head>
<style>
.diffdiv { border: solid 1px black; }
.comment { color: gray; }
.diff { color: #8A2BE2; }
.minus3 { color: blue; }
.plus3 { color: maroon; }
.at2 { color: lime; }
.plus { color: green; background: #E7E7E7; }
.minus { color: red; background: #D7D7D7; }
.only { color: purple; }
</style>
<body>
<pre>
XX
echo -n '<span class="comment">'
first=1
diffseen=0
lastonly=0
OIFS=$IFS
IFS='
'
# The -r option keeps the backslash from being an escape char.
read -r s
while [[ $? -eq 0 ]]
do
# Get beginning of line to determine what type
# of diff line it is.
t1=${s:0:1}
t2=${s:0:2}
t3=${s:0:3}
t4=${s:0:4}
t7=${s:0:7}
# Determine HTML class to use.
if [[ "$t7" == 'Only in' ]]; then
cls='only'
if [[ $diffseen -eq 0 ]]; then
diffseen=1
echo -n '</span>'
else
if [[ $lastonly -eq 0 ]]; then
echo "</div>"
fi
fi
if [[ $lastonly -eq 0 ]]; then
echo "<div class='diffdiv'>"
fi
lastonly=1
elif [[ "$t4" == 'diff' ]]; then
cls='diff'
if [[ $diffseen -eq 0 ]]; then
diffseen=1
echo -n '</span>'
else
echo "</div>"
fi
echo "<div class='diffdiv'>"
lastonly=0
elif [[ "$t3" == '+++' ]]; then
cls='plus3'
lastonly=0
elif [[ "$t3" == '---' ]]; then
cls='minus3'
lastonly=0
elif [[ "$t2" == '@@' ]]; then
cls='at2'
lastonly=0
elif [[ "$t1" == '+' ]]; then
cls='plus'
lastonly=0
elif [[ "$t1" == '-' ]]; then
cls='minus'
lastonly=0
else
cls=
lastonly=0
fi
# Convert &, <, > to HTML entities.
s=$(sed -e 's/\&/\&/g' -e 's/</\</g' -e 's/>/\>/g' <<<"$s")
if [[ $first -eq 1 ]]; then
first=0
else
echo
fi
# Output the line.
if [[ "$cls" ]]; then
echo -n '<span class="'${cls}'">'${s}'</span>'
else
echo -n ${s}
fi
read -r s
done
IFS=$OIFS
if [[ $diffseen -eq 0 && $onlyseen -eq 0 ]]; then
echo -n '</span>'
else
echo "</div>"
fi
echo
cat <<XX
</pre>
</body>
</html>
XX
# vim: tabstop=4: shiftwidth=4: noexpandtab:
# kate: tab-width 4; indent-width 4; replace-tabs false;
Mitch Frazier is an Associate Editor for Linux Journal.
Trending Topics
| Blender for Visual Effects | Aug 10, 2016 |
| New Version of GParted | Aug 09, 2016 |
| Snapchat, for Hoarders | Aug 08, 2016 |
| Tor 0.2.8.6 Is Released | Aug 05, 2016 |
| A New Project for Linux at 25 | Aug 04, 2016 |
| SUSE Enterprise Storage | Aug 03, 2016 |
- New Version of GParted
- Blender for Visual Effects
- Tor 0.2.8.6 Is Released
- Snapchat, for Hoarders
- A New Project for Linux at 25
- Murat Yener and Onur Dundar's Expert Android Studio (Wrox)
- Better Cloud Storage with ownCloud 9.1
- SUSE Enterprise Storage
- SUSE LLC's SUSE Manager
- Stunnel Security for Oracle
Geek Guides
With all the industry talk about the benefits of Linux on Power and all the performance advantages offered by its open architecture, you may be considering a move in that direction. If you are thinking about analytics, big data and cloud computing, you would be right to evaluate Power. The idea of using commodity x86 hardware and replacing it every three years is an outdated cost model. It doesn’t consider the total cost of ownership, and it doesn’t consider the advantage of real processing power, high-availability and multithreading like a demon.
This ebook takes a look at some of the practical applications of the Linux on Power platform and ways you might bring all the performance power of this open architecture to bear for your organization. There are no smoke and mirrors here—just hard, cold, empirical evidence provided by independent sources. I also consider some innovative ways Linux on Power will be used in the future.
Get the Guide




Comments
Thanks Richie
Your script was useful. The IFS should be set to newline though so that tabs are not collapsed.
It is also nice to additionally accept diff input on stdin as in Mitch's original script so one can colorize output from svn/hg/cvs diff via a pipe. Just replace your "diff -u $@" with a variable called $CMD, and set $CMD to "cat" when no args are provided.
Interesting post,thanks.Good
Interesting post,thanks.Good website.
Or use vim
You can also open the diff in Vim, choose your preferred colorscheme, and then use :TOhtml.
Not another one!
I first thought this was going to be a pure output colorizer for diff. When I read on and realized it was yet another converter to generate HTML from diff output, I was disappointed. "Never mind", I thought, "I'll just write my own." Based heavily on the above program this produces pretty much the same output, but in the console, using ANSI color control sequences.
Tinker with the "style color definitions" to change colors to suit your environment.
In the course of messing with this, I made a couple of improvements that could be rolled back into the original version: 1. only one call to "read", and 2. "diff -u" is now called internally.
I tried not changing IFS, and it seemed to work, so I left those lines out, too. The other thing the original could benefit from is properly named CSS classes! (What on earth do "plus3" and "at2" mean?) As you can see, I've given more meaningful names to my ANSI equivalents.
colordiff
Hey Richie,
you could just use an existing tool colordiff
sudo apt-get colordiff
great script though.
Cheers.
tkdiff
Perhaps more interactively helpful is a graphical diff viewer such as tkdiff.