Created
November 2, 2012 19:50
-
-
Save isao/4003924 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/perl | |
# Copyright (c) William Uther ([email protected]) 2001 | |
# All rights reserved. | |
# | |
# Redistribution and use in source and binary forms, with or without | |
# modification, are permitted provided that the following conditions are met: | |
# | |
# * Redistributions of source code must retain the above copyright notice, | |
# this list of conditions and the following disclaimer. | |
# * Redistributions in binary form must reproduce the above copyright notice, | |
# this list of conditions and the following disclaimer in the documentation | |
# and/or other materials provided with the distribution. | |
# * Neither the name of the copyright holders nor the names of its contributors | |
# may be used to endorse or promote products derived from this software | |
# without specific prior written permission. | |
# | |
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" | |
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | |
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |
# DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY | |
# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | |
# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | |
# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON | |
# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | |
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | |
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |
# This is a script for parsing the errors of a command line application | |
# and generating an applescript that will display those errors in a | |
# BBEdit Results Window. | |
# Expected use is something like the following: (tcsh) | |
# % jikes +E myFile.java |& BBErr.pl | osascript | |
# Customization: | |
# At the moment, this file is set up to read the "emacs format" err output of | |
# jikes. Search for the comment "match this line of the error" to find the | |
# regular expression that matches each line of output. It should be fairly easy | |
# to update for other result formats. | |
# The applescript generated has the name of the BBEdit app embedded in it. | |
# If you need to alter this, look for where the variable "$BBEditAppName" | |
# is set. | |
# KNOWN ISSUES: | |
# - There are some details I don't understand about how BBEdit uses the file | |
# offsets. This leads to the selection being off by one character in some | |
# cases. sigh. | |
# - It seems that BBEdit calls perl synchronously, and will not accept appleevents | |
# while doing so. This means you use this script entirely from within BBEdit. | |
# BBEdit takes its input in terms of character offset. Jikes' output is in | |
# terms of laid out output, with tabs being expanded to 8 spaces. This | |
# function takes that expansion into account for a single line. | |
sub handleTabs { | |
my ($line, $offset) = @_; | |
$tabSize = 8; | |
#print "\r Handle: '",$line,"', ", $offset, "\r"; | |
#$offset--; | |
while ($line =~ m/\t/g) { | |
if (pos $line < $offset) { | |
$offset -= $tabSize-1; | |
} else { | |
last; | |
} | |
} | |
#print " result: ", $offset, "\r"; | |
return $offset; | |
} | |
# Jikes outputs the selection as four numbers: | |
# - The line of the start of the selection | |
# - The character on that line of the start of the selectio | |
# - The line of the end of the selection | |
# - The character on that line of the end of the selection | |
# | |
# BBEdit takes just two numbers - the start and end offset in the | |
# file of the selection. | |
# | |
# This function converts from the former format to the latter. | |
# To do this it opens the file and reads through it. No caching is | |
# currently performed, so the file will be scanned separately for each error | |
# message. | |
# | |
# This function uses handleTabs. | |
# | |
# BUG: There are some details I don't understand about how BBEdit uses the file | |
# offsets. This leads to the selection being off by one character in some | |
# cases. sigh. | |
sub translateSelection { | |
my ($filename, $startLine, $startChar, $endLine, $endChar) = @_; | |
#$startPosn = $startChar; | |
#$endPosn = $endChar; | |
open(TESTSTREAM, $filename) or die "Couldn't convert selection data"; | |
$chCount = 0; | |
$startPosn = 0; | |
# some brief sanity checks on the input selection | |
if ($startLine == 0) { | |
$startLine = 1; | |
$startChar = 0; | |
} | |
if ($endLine == 0) { | |
$endLine = $startLine; | |
$endChar = $startChar; | |
} | |
if ($startLine > $endLine) { | |
($startLine, $startChar, $endLine, $endChar) = ($endLine, $endChar, $startLine, $startChar); | |
} elsif ($startLine == $endLine) { | |
if ($startChar > $endChar) { | |
($startChar, $endChar) = ($endChar, $startChar); | |
} | |
} | |
$gotEndPosn = 0; | |
# look through the file for the appropriate lines | |
while($line = <TESTSTREAM>) { | |
$lineLength = length($line); | |
$lineNum = $.; | |
if ($lineNum == $startLine) { | |
$startChar = handleTabs($line, $startChar); | |
if ($startChar > $lineLength) { | |
$startChar = 0; | |
} | |
$startPosn = $chCount+$startChar; | |
} | |
if ($lineNum == $endLine) { | |
$endChar = handleTabs($line, $endChar); | |
#$endChar--; | |
if ($endChar > $lineLength) { | |
$endChar = $lineLength; | |
} | |
$endPosn = $chCount+$endChar; | |
$gotEndPosn = 1; | |
last; | |
} | |
$chCount += $lineLength; | |
} | |
close(TESTSTREAM); | |
if (! $gotEndPosn) { | |
$endPosn = $startPosn; | |
} | |
$line = $startLine; | |
return ($line, $startPosn, $endPosn); | |
} | |
# This is the start of the main script | |
open(INPUT,"-") or die "Can't get input stream"; | |
open(APPLESCRIPT,">-") or die "Can't get output stream"; | |
# NOTE: these lines fail from within BBEdit. | |
# it seems BBEdit calls perl synchronously and doesn't accept appleevents in the meantime. | |
#open(INPUT,"jikes +E DummyApp.java |& cat"); | |
#open(APPLESCRIPT,"| osascript"); | |
$le = "\r"; | |
$BBEditAppName="BBEdit 6.5"; | |
print APPLESCRIPT "tell application \"",$BBEditAppName,"\"", $le; | |
print APPLESCRIPT "set theData to {"; | |
$needComma = 0; | |
while (<INPUT>) { | |
#match this line of the error | |
#if the regular expression doesn't match then ignore the line | |
next if !/^([^:]+):([0-9]+):([0-9]+):([0-9]+):([0-9]+): *([^:]+): *(.*)$/; | |
$filename = $1; | |
$startLine = $2; | |
$startChar = $3; | |
$endLine = $4; | |
$endChar = $5; | |
if ($6 eq "Warning") { | |
$warning = "Warning"; | |
} elsif ($6 eq "Caution") { | |
$warning = "Note"; | |
} else { | |
$warning = "Error"; | |
} | |
$message = $7; | |
#start generating this property entry | |
if ($needComma) { | |
print APPLESCRIPT ", "; | |
} | |
$needComma = 1; | |
print APPLESCRIPT "{"; | |
$unixFileName = $filename; | |
$quotedUnixFileName = $filename; | |
$quotedUnixFileName =~ s/\"/\\\"/g; | |
# add the Error/Warning label | |
if ($warning eq "Warning") { | |
print APPLESCRIPT "result_kind:warning_kind"; | |
} elsif ($warning eq "Note") { | |
print APPLESCRIPT "result_kind:note_kind"; | |
} else { | |
print APPLESCRIPT "result_kind:error_kind"; | |
} | |
# set the file name | |
print APPLESCRIPT ", result_file: POSIX file \""; | |
print APPLESCRIPT $quotedUnixFileName; | |
print APPLESCRIPT "\""; | |
($lineOut, $startOffset, $endOffset) = translateSelection($unixFileName, $startLine, $startChar, $endLine, $endChar); | |
#set the result line | |
print APPLESCRIPT ", result_line:"; | |
print APPLESCRIPT $lineOut; | |
#set the result start char | |
print APPLESCRIPT ", start_offset:"; | |
print APPLESCRIPT $startOffset; | |
#set the result end char | |
print APPLESCRIPT ", end_offset:"; | |
print APPLESCRIPT $endOffset; | |
#set the error message | |
#first, quote any quote marks in the message | |
$message =~ s/\"/\\\"/g; | |
print APPLESCRIPT ", message:\""; | |
print APPLESCRIPT $message; | |
print APPLESCRIPT "\""; | |
print APPLESCRIPT "}"; | |
} | |
print APPLESCRIPT "}", $le; | |
print APPLESCRIPT "make new results browser with data theData with properties {name:\"Results Browser\"}", $le; | |
print APPLESCRIPT "end tell", $le; | |
close(APPLESCRIPT); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment