From: voipfc Date: 2006-10-11T23:58:54+09:00 Subject: My First Almost Serious Ruby Program - Critique it This is a follow up on what I this posting http://groups.google.co.uk/group/ruby-talk-google/browse_frm/thread/b58ab3c4876da743/d70309f2a864ed85?lnk=st&q=voipfc&rnum=9&hl=en#d70309f2a864ed85 It is based on info from here http://freshmeat.net/articles/view/447/ and http://www.oreillynet.com/onjava/blog/2006/03/recursive_directory_list_with.html It is a templating program that takes a source directory, reads the files there and outputs them to a destination directory, adjusting both values and file paths alike. Main Program ============== # templatefiller.rb require 'find' class Template # Construct the template object with the template and the # replacement values. "values" can be a hash, a function, # or a method. def initialize(replaceStr, values, fileReplaceStr, fileValues) @replaceStrs = {} if values.kind_of?( Hash ) @replaceStrs[ replaceStr ] = values.method( :fetch ) else @replaceStrs[ replaceStr ] = values.clone() end @fileReplaceStrs = {} if fileValues.kind_of?( Hash ) @fileReplaceStrs[ fileReplaceStr ] = fileValues.method( :fetch ) else @fileReplaceStrs[ fileReplaceStr ] = fileValues.clone() end end def run(inStream) outStream = inStream.clone() @replaceStrs.keys.each { |fileReplaceStr| outStream.gsub!( /#{fileReplaceStr}(.*?)#{fileReplaceStr}/ ) { @replaceStrs[ fileReplaceStr ].call( $1 ).to_s } } outStream end def runFile(inStream) outStream = inStream.clone() @fileReplaceStrs.keys.each { |fileReplaceStr| outStream.gsub!( /#{fileReplaceStr}(.*?)#{fileReplaceStr}/ ) { @fileReplaceStrs[fileReplaceStr ].call( $1 ).to_s } } outStream end def to_s() run(); end end if File.exists?(ARGV[0]) inputFile = ARGV[0]; else puts "File #{ARGV[0]} does not exist.\n" exit end ini_hash = {} ini_hash[""] = section_hash = {} # default unnamed section data = File.read(inputFile) data.each do |line| if /^\[.+\]$/ =~ line # section headers are surrounded by brackets ini_hash[line.chomp.gsub(/[\[\]]/, '')] = section_hash = {} else key,value = line.chomp.split("=",2) if value section_hash[key] = value #puts " #{key} is #{value} " else #puts "key is #{key} nil? How about value? #{value} and section_hash[#{key}] = " if key.nil? end end end # example of walking through the whole thing ini_hash.each do |k, v| unless k.empty? # v.each {|sk, sv| puts " #{sk}=#{sv}"} v.each do |sk, sv| unless sk.nil? # end end end end $matchesTemplate = Template.new(ini_hash["Directories"]["escape"], ini_hash["TemplateValues"], ini_hash["Directories"]["outEscape"], ini_hash["PathTemplates"]) inDir = ini_hash["Directories"]["input_directory"] outDir = ini_hash["Directories"]["output_directory"] puts "Input Directory is - #{inDir}" puts "Output Directory is - #{outDir}" dirs = [inDir] excludes = ["CVS","classes","images","lib","tlds"] for dir in dirs Find.find(dir) do |path| if FileTest.directory?(path) if excludes.include?(File.basename(path)) Find.prune # Don't look any further into this directory. else next end else if FileTest.file?(path) if excludes.include?(File.basename(path)) == true next end data = File.read(path) outFileName = outDir + path[inDir.length, path.length - inDir.length] zFileName = $matchesTemplate.runFile(outFileName) f = File::open( zFileName, "w" ) f << $matchesTemplate.run(data) f.close() end end end end ============== sample template settings. #template.ini [Directories] input_directory=.\templateSource output_directory=.\templateDestination escape=::: outEscape=___ [TemplateValues] aaaa=Mary bbbb=Had cccc=a dddd=Little eeee=Lamb [PathTemplates] template=workdone