require 'pathname' class Pathname def +@ expand_path.to_s end def chdir &exe Dir.chdir self.to_s, &exe end alias cd chdir # copies content of src in self as destination def copy src, **opts FileUtils.copy_file src.to_s, self.to_s, **opts end alias link make_link alias symlink make_symlink def replace_i &e changed = false open 'r+' do |f| old = f.readlines f.pos = 0 lines = yield f changed = lines != old if changed f.truncate 0 f.pos = 0 f.puts lines end end not changed end def sed_i **replaces, &e changed = false open 'r+' do |f| lines = f.each_line.flat_map do |l| yield( l.chomp, replaces).tap {|r| changed = true unless l == r } end changed = true unless replaces.empty? if changed f.truncate 0 f.pos = 0 f.puts lines replaces.each {|_,rls| f.puts rls } end end not changed end end class XPathname < Pathname %i[/ + join].each do |meth| define_method meth do |*n| XPathname.new "#{super *n}" end end %i[unlink read mkdir mkpath].each do |meth| define_method meth do STDERR.puts "\e[1;36m#{meth} \e[1;35m#{self}\e[0m" super() end end %i[replace_i sed_i].each do |meth| define_method meth do |*a, **o, &e| STDERR.print "\e[1;36mpatching \e[1;35m#{self}\e[0m" begin r = super *a, **o, &e STDERR.puts "\r\e[#{r ? "1;32" : "33"}mpatching \e[1;35m#{self}\e[0m" rescue Object STDERR.puts "\r\e[1;31mpatching \e[1;35m#{self}\e[0m" raise end r end end def rename dest STDERR.puts "\e[1;36mrename \e[1;35m#{self}\e[0m -> \e[1;35m#{dest}\e[0m" super dest end def move src STDERR.puts "\e[1;36mmove \e[1;35m#{self}\e[0m <- \e[1;35m#{dest}\e[0m" super src end def copy src, **opts STDERR.puts "\e[1;36mcopy \e[1;35m#{self}\e[0m <- \e[1;35m#{src}\e[0m" super src, **opts end %i[link symlink].each do |meth| define_method meth do |dest| STDERR.puts "\e[1;36m#{meth} \e[1;35m#{self}\e[0m -> \e[1;35m#{dest}\e[0m" super dest end end alias link make_link alias symlink make_symlink %i[write].each do |meth| define_method meth do |*a, **o, &e| STDERR.puts "\e[1;36m#{meth} \e[1;35m#{self}\e[0m \e[1;35m#{a[0][0...128].inspect}\e[0m" super *a, &e end end end class Symbol alias +@ to_s def -@ :"-#{self}" end end class File def reset f.truncate 0 f.pos = 0 end end