Archive for the 'Scripting' Category

Rails 2.0 regex to convert old Migrations

Dec 07, 2007 in Ruby, Scripting, Web Development

Rails 2.0 is here! I’m going to try to move the app I’ve been working on (at DesignHammer) over to take advantage of it. Doesn’t seem like it should take that long? But we’ll see ;-)

While getting started on that I wanted to try the new method for Active Record DB migrations. So I decided to rewrite all my old migrations (or at least the ones adding tables). I ended up crafting this regex to allow for a quick find and replace of the old style to be like the new style:

Find:

   \.column\s+(("\w+")|(\:\w+))\s*,\s+(\:(\w+))

Replace:

   .$5 $1

Tags: , , , , ,

Ruby script to convert file(s) character encoding

Oct 24, 2007 in Ruby, Scripting

Today at work I had to take a whole set of directory upon directory of files and convert them from one character encoding to UTF-8. Of course, this was instantly a task I said a script should do. And along came the following script. It takes two options one required, defining the character encoding of the files being converted, using the flag “-f”. The other optional, defining the character encoding the files are to be converted to, using the flag “-t”. The second is optional because the default is to convert to is UTF-8. Finally, it accepts an argument list of directories or file names and processes each recurcively going through each directory processing each file and/or directory in it. It ignores all invisible files (those that start with “.”). It will most likely fail for a given file if the character encoding is off. But it will continue with the other files notifing the user that there was an issue.

#!/usr/bin/env ruby -KU

require 'optparse'
require 'ostruct'
require 'iconv'

SCRIPT_NAME = "File Character Encoding Converter"
SCRIPT_VERSION = "0.1"

class FileEncodingConverterOptionParser

   def self.parse(args)
      options = OpenStruct.new
      options.to = 'UTF-8'
      options.verbose = false

      opts = OptionParser.new do |opts|
         opts.banner = "Usage: convert_encoding.rb [options] directory|file..."

         opts.separator ""
         opts.separator "Specific options:"

         opts.on("-f", "--from ENCODING", "Character Encoding converting from") do |encoding|
            options.from = encoding
         end

         opts.on("-t", "--to ENCODING", "Character Encoding converting to") do |encoding|
            options.to = encoding
         end

         opts.separator ""
         opts.separator "Common options:"

         opts.on("-v", "--[no-]verbose", "Run verbosely") do |v|
            options.verbose = v
         end

         opts.on_tail("-h", "--help", "Show this message") do
            puts opts
            exit
         end

         opts.on_tail("-V", "--version", "Show version") do
            puts SCRIPT_NAME + ' ' + SCRIPT_VERSION
            exit
         end

      end

      opts.parse!(args)
      options
   end

end

options = FileEncodingConverterOptionParser.parse(ARGV)
VERBOSE = options.verbose ? true : false

class FileEncodingConverter

   def initialize(from, to = 'UTF-8')
      @to = to
      @from = from
   end

   def fconv(filename)
      begin
         contents = File.open(filename).read
         output = Iconv.conv(@to, @from, contents)
         file = File.open(filename, 'w')
         file.write(output)
      rescue Iconv::IllegalSequence
         puts "Could not be processed: #{filename}"
      else
         if VERBOSE
            puts "Processed successfully: #{filename}"
         end
      ensure
         if defined? file
            if file
               file.close
               file = nil
            end
         end
      end
   end

   def process_dir(dir)
      Dir.foreach(dir){ |filename| 
         if !filename.match(/^\./)
            absolute_path = dir + '/' + filename
            if File.file?(absolute_path)
               self.fconv(absolute_path)
            elsif File.directory?(absolute_path)
               self.process_dir(absolute_path)
            end
         end
      }
   end

end

converter = FileEncodingConverter.new(options.from, options.to)

ARGV.each { |arg| 
   wd = Dir.getwd
   entryname = arg.match(/^\//) ? wd + '/' + arg : arg
   if File.directory?(entryname)
      converter.process_dir(entryname)
   elsif File.file?(entryname)
      converter.fconv(entryname)
   end
}

Tags: , , , ,

Script and Droplet for forcing an app to run with the old WebKit

Jul 20, 2007 in Mac, Scripting

Thomas Aylott over at subtleGradient had a posting a little while ago about how to install Safari 2 on top of Safari 3 beta and open applications with the older version of WebKit. I was needing to do this a lot and his work around called for running a command from the shell every time. I thought wouldn’t it be nice to to have some quick way to do this from the finder. Also, some apps were spitting out some text to standard error in the terminal and while the “&” at the end prevented standard output from going to the terminal (by making the command run in the background), standard error was stilling being displayed. So, I wrote a bash script and turned it into a droplet with Platapus. I then created a Automator workflow that opened a selected finder item with the droplet, and saved it as Finder plug-in, which allows me to call it from a contextual menu in the Finder. Of course you can always add the app to the dock or use Quicksilver triggers or whatever you prefer at that point.

I’ve included the script code below and posted the app and workflow with this posting (to use them you will have to first follow the instructions over at subtleGradient to install Safari 2 on top of Safari 3).
(*the workflow should be installed in “~/Library/Workflows/Applications/Finder“)

#!/usr/bin/env bash

IFS=" "
filename=${*##/*/}
appname=${filename%%.*}
binpath="$*/Contents/MacOS/$appname"

env DYLD_FRAMEWORK_PATH="/Applications/Safari2.app/Contents/Resources" \
WEBKIT_UNSET_DYLD_FRAMEWORK_PATH=YES "$binpath" >&/dev/null &

Tags: , , , , , ,

A Shell Script for renaming an hg project and files

Apr 25, 2007 in Scripting

This semester I’ve been taking a “Web Databases” class, for a number of the assignments we’ve been progressively building up a simple digital library site. Each project we needed to change the name of the files from something like “blandau-p5-home.html” to “blandau-p6-home.html”.
I was using Mercurial for managing my version control, and needed a way to quickly manage moving over the files from one name to another. In comes the shell script! I needed to clone the Mercurial repository over, then rename all the files to the new name. Here’s the code:

#!/usr/bin/env bash

v=''
# process the option flags
while getopts ":vh" opt; do
   case $opt in
      v  ) v='-v ' ;;
      h  ) echo "usage: renameproj.sh  [-v] [-h] old new" ;;
      \? ) echo "usage: renameproj.sh  [-v] [-h] old new" ;;
   esac
done
shift $(($OPTIND - 1))

# Get the old and new project names
old=$1
new=$2

# Function to rename files
renamepfiles(){
v=''
# process the option flags
while getopts ":vo:n:" opt; do
   case $opt in
      v  ) v='-v ' ;;
      o  ) old=$OPTARG ;;
      n  ) new=$OPTARG ;;
      \? ) echo "usage: renamepfiles  [-v] [-o oldproject] [-n newproject] args..." ;;
   esac
done
shift $(($OPTIND - 1))

# Make the move
for filename do
   oldfile=${filename}
   # the next line transforms the old filename into the new one by replacing the
   # old porject name with the new one.
   newfile=${filename/$old/$new}
   # first rename it with the move command
   mv -i ${v}$oldfile $newfile
   # then rename it with the hg command
   hg ${v}rename -A $oldfile $newfile
done
}

# perform an mercurial clone of the project
hg ${v}clone $old $new
# change the working directory to our new project
cd ${new}

# call the function over all the files with the "old" project name in their name
renamepfiles ${v}-n $new -o $old $(find . -name "*$old*" -maxdepth 2 -print | xargs echo -n)
echo "- Project Moved"

Tags: , , , ,