
https://svn.lrde.epita.fr/svn/lrdetools/trunk Index: ChangeLog from Nicolas Pouillard <ertai@lrde.epita.fr> Add protocol version and default commit supprt. * vcs/NEWS: Add an entry for vcs extensions files. * vcs/lib/vcs/vcs.rb: Add protocol_version and default_commit. * vcs/lib/vcs/app.rb: Create a cleaner structure. * vcs/lib/vcs/changelog.rb: Update display messages. * vcs/lib/vcs/mycommit.rb: Rename to ... * vcs/lib/vcs/common_commit.rb: ... this. * vcs/lib/vcs/message.rb: Move diff extensions ... * vcs/lib/vcs/diff.rb: ... here. And makes diffw_from_status skip deleted files like (--no-diff-deleted). * vcs/lrdetools.rb, vcs/template/prj.rb: Add protocol_version '0.1'. * vcs/test/options-suite.yml: Add a test for the vcs-svn --help. * vcs/lib/vcs/app.rb: . * vcs/lib/vcs/message.rb: . * vcs/lib/vcs/changelog.rb: . * vcs/lib/vcs/vcs.rb: . * vcs/lib/vcs/opt_parse.rb: . * vcs/lib/vcs/mycommit.rb: Remove. * vcs/lib/vcs/common_commit.rb: New. * vcs/lib/vcs/diff.rb: . * vcs/lrdetools.rb: . * vcs/template/prj.rb: . * vcs/NEWS: . NEWS | 10 ++++ lib/vcs/app.rb | 105 +++++++++++++++++++++++++++++------------------ lib/vcs/changelog.rb | 3 - lib/vcs/common_commit.rb | 2 lib/vcs/diff.rb | 14 +++++- lib/vcs/message.rb | 14 ------ lib/vcs/mycommit.rb | 87 -------------------------------------- lib/vcs/opt_parse.rb | 6 ++ lib/vcs/vcs.rb | 63 ++++++++++++++++++---------- lrdetools.rb | 3 + template/prj.rb | 3 + test/options-suite.yml | 15 ++++++ 12 files changed, 161 insertions(+), 164 deletions(-) Index: vcs/template/prj.rb --- vcs/template/prj.rb (revision 231) +++ vcs/template/prj.rb (working copy) @@ -15,6 +15,9 @@ '<' + "%= #{s} %" + '>' end %> + + protocol_version '0.1' + def <%= project %>_commit! ( *args ) common_commit!("<%= tag 'rev' %>: <%= project %>: <%= tag 'title' %>", *args) do |subject| Index: vcs/lib/vcs/app.rb --- vcs/lib/vcs/app.rb (revision 231) +++ vcs/lib/vcs/app.rb (working copy) @@ -23,68 +23,93 @@ # Vcs is a wrapper over any version control system. class VcsApp - @@vcs = Pathname.new(__FILE__).expand_path.dirname - @@dir = @@vcs.parent - require @@vcs + 'vcs' unless defined? Vcs + @@vcs_dir ||= Pathname.new(__FILE__).expand_path.dirname + @@dir ||= @@vcs_dir.parent + @@extension_dirs ||= [] + + require @@vcs_dir + 'vcs' unless defined? Vcs + @@dir.load_path! - cattr_accessor :all_vcs - cattr_accessor :by_name + cattr_accessor :vcs_dir cattr_accessor :dir + cattr_accessor :extension_dirs cattr_accessor :path - dir = Pathname.pwd - while not dir.root? and not (vcs_dir = dir + 'vcs').exist? - dir = dir + '..' - end - vcs_dir = vcs_dir.expand_path - vcs_dir.load_path! - - HOME = ENV['HOME'].to_path - vcs_user_conf = HOME/'.vcsrc' - if vcs_user_conf.exist? - Vcs.user_conf = OpenStruct.new(YAML.load(vcs_user_conf.read)) - end + class << self - Pathname.glob("{#{@@vcs},#{vcs_dir}}/*.rb") do |file| + def requirements + Pathname.glob("{#{vcs_dir},#{extension_dirs.join(',')}}/*.rb") do |file| next if file.to_s =~ /\/(app|opt_parse|vcs)\.rb$/ LOG.debug { file.basename.to_s } require file.to_s end + grab_all_vcs() + end - @@all_vcs ||= [] - @@by_name ||= {} + def grab_all_vcs + @@all_vcs ||= {} if @@all_vcs.empty? ObjectSpace.each_object(Class) do |aClass| if aClass != Vcs and aClass.ancestors.include? Vcs - name = aClass.to_s.to_sym - @@all_vcs << name - @@by_name[name.to_s.downcase] = aClass + name = aClass.to_s.demodulize.underscore.to_sym + @@all_vcs[name] = aClass + end end end end - require 'vcs/opt_parse' + def all_vcs + @@all_vcs.keys + end + end + + requirements() + require 'vcs/opt_parse' @@parser = Vcs::OptParse.new def initialize ( __file__, vcs_type=nil ) - @@path = __file__ + @@path = __file__.to_path Vcs.default ||= vcs_type end + def vcs_extensions_setup + dir = Pathname.pwd + while not dir.root? and not (vcs_dir = dir + 'vcs').exist? + dir = dir + '..' + end + vcs_dir = vcs_dir.expand_path + vcs_dir.load_path! + extension_dirs << vcs_dir + VcsApp.requirements() + end + + def user_configuration_setup + home = ENV['HOME'].to_path + vcs_user_conf = home/'.vcsrc' + if vcs_user_conf.exist? + Vcs.user_conf = OpenStruct.new(YAML.load(vcs_user_conf.read)) + end + end + def run vcs = nil begin - @@parser.parse! ARGV + vcs_extensions_setup() + user_configuration_setup() + @@parser.parse! ARGV if Vcs.default.nil? if Vcs.default.nil? STDERR.puts @@parser - STDERR.puts "\nSpecify at least a Vcs type, or use a wrapped command\n" + - 'like svn, cvs, prcs in the vcs bin directory.' + STDERR.puts " + | + |Specify at least a Vcs type, or use a wrapped command + |like svn, cvs, prcs in the vcs bin directory. + ".head_cut! exit end - vcs = @@by_name[Vcs.default.to_s.downcase].new + vcs = @@all_vcs[Vcs.default.to_s.downcase.to_sym].new if ARGV.empty? meth = :help! @@ -94,10 +119,12 @@ vcs.send(meth, *ARGV) - rescue Exception + rescue SystemExit => ex + raise ex + rescue Exception => ex vcs.call_handlers unless vcs.nil? - LOG.debug { raise } - LOG.error $!.to_s.sub(/\.$/, '') unless $!.to_s == 'exit' + LOG.debug { raise ex } + LOG.error ex.to_s.sub(/\.$/, '') end end Index: vcs/lib/vcs/common_commit.rb --- vcs/lib/vcs/common_commit.rb (revision 231) +++ vcs/lib/vcs/common_commit.rb (working copy) @@ -80,7 +80,7 @@ def commit_failed LOG.info "#{COMMITED}: Contains your ChangeLog entry" if COMMITED.exist? LOG.error 'Aborting' - LOG.info 'You can rerun the same command to continue the commit' + LOG.info 'You can rerun the same command to resume the commit' raise 'Commit failed' end Index: vcs/lib/vcs/changelog.rb --- vcs/lib/vcs/changelog.rb (revision 231) +++ vcs/lib/vcs/changelog.rb (working copy) @@ -44,7 +44,7 @@ attr_reader :file def initialize ( file ) @file = file - super("You must fill this file: `#{file.to_s}'") + super("You must fill this file: `#{file.to_s}' (and remove the first line)") end end @@ -61,6 +61,7 @@ # Already filled if ,ChangeLog.add exists and not begin by --- if cl.exist? + just_one_time { LOG.info "#{cl} already exists" } raise MustBeFilled, cl if cl.read =~ /\A---/ require 'erb' ls = [] Index: vcs/lib/vcs/diff.rb --- vcs/lib/vcs/diff.rb (revision 231) +++ vcs/lib/vcs/diff.rb (working copy) @@ -3,12 +3,24 @@ # License:: GNU General Public License (GPL). # Revision:: $Id$ +class Vcs + def diffw! ( *args ) + diff!(*args) + end +end # class Vcs + + class Svn + # A diff only for your eyes + def diffw! ( *args ) + diff! '--diff-cmd', 'diff', '-x', '-NPbuw', *args + end + def diffw_from_status! ( *args ) files = Set.new from_status(*args) do |line, file_st, prop_st, cpy, file| - next if file_st =~ /[?X\\,]/ + next if file_st =~ /[?X\\,D]/ next if file == 'ChangeLog' files << Pathname.new(file) end Index: vcs/NEWS --- vcs/NEWS (revision 231) +++ vcs/NEWS (working copy) @@ -1,5 +1,15 @@ New in 0.4 ...: + * Vcs extensions files: + - Protocol version: + You can now add `protocol_version "0.1"' in your extensions. Thus + you will be alert when the format will changes. + - Default commit: + By adding `default_commit :your_commit_method' you override the + default commit method with yours. So you can call `commit' and `ci', + but also your old aliases. Of course you can call the real commit + with `commit_' or `ci_'. + * Status & User Configuration File: >>>> ~/.vcsrc <<<< --- Index: vcs/lib/vcs/vcs.rb --- vcs/lib/vcs/vcs.rb (revision 231) +++ vcs/lib/vcs/vcs.rb (working copy) @@ -110,15 +110,19 @@ def #{m1} ( *args ) #{m2}(*args) end + unless method_defined? :#{m1} def #{m1}_ ( *args ) #{m2}_(*args) end + end def #{m1}! ( *args ) #{m2}!(*args) end + unless method_defined? :#{m1}! def #{m1}_! ( *args ) #{m2}_!(*args) end + end end_eval end @@ -275,29 +279,46 @@ @handlers.each { |meth| send(meth) } end - def self.add_conf_checker ( meth ) - @@checkers << meth - end - def call_conf_checkers @@checkers.each { |meth| send(meth) } end - def self.match ( regexps, file ) + class << self + + def add_conf_checker ( meth ) + @@checkers << meth + end + + def match ( regexps, file ) regexps.each do |re| return true if re.match(file) end return false end - def self.user_conf_global_ignore ( file ) + def user_conf_global_ignore ( file ) return false if user_conf.nil? or user_conf.global_ignore.nil? match(user_conf.global_ignore, file) end - def self.user_conf_global_unmask ( file ) + def user_conf_global_unmask ( file ) return false if user_conf.nil? or user_conf.global_unmask.nil? match(user_conf.global_unmask, file) end + # Here we can handle version conflicts with vcs extensions + def protocol_version ( aVersion ) + if aVersion != '0.1' + raise ArgumentError, "Bad protocol version #{aVersion} but 0.1 is needed" + end + end + + # Set the given method as default commit action, use commit_ for the old one + def default_commit ( meth ) + alias_command :commit, meth + alias_command :ci, meth + end + + end # class << self + end # class Vcs Index: vcs/test/options-suite.yml --- vcs/test/options-suite.yml (revision 231) +++ vcs/test/options-suite.yml (working copy) @@ -36,3 +36,18 @@ args: --mk-alias # Output will be compared to this regexp output: !re \A(^alias \w+=.* ;$)+ + + - Check the help option for svn: + command: <<pwd>>/../bin/vcs-svn + args : --help + error : "" + output : !re | + \Ausage: svn <subcommand> \[options\] \[args\] + Type 'svn help <subcommand>' for help on a specific subcommand\. + + Most subcommands take file and/or directory arguments, recursing + on the directories\. If no arguments are supplied to such a + command, it recurses on the current directory \(inclusive\) by default\. + + Available subcommands: + (^ - .*$)+ Index: vcs/lrdetools.rb --- vcs/lrdetools.rb (revision 231) +++ vcs/lrdetools.rb (working copy) @@ -1,5 +1,7 @@ class Vcs + protocol_version '0.1' + def lrdetools_commit! ( *args ) common_commit!("[LrdeTools] <%= rev %>: <%= title %>", *args) do |subject| @@ -8,5 +10,6 @@ end alias_command :ltci, :lrdetools_commit + default_commit :lrdetools_commit end # class Vcs Index: vcs/lib/vcs/opt_parse.rb --- vcs/lib/vcs/opt_parse.rb (revision 231) +++ vcs/lib/vcs/opt_parse.rb (working copy) @@ -8,6 +8,8 @@ class OptParse + attr_reader :option_parser + def initialize @option_parser = @@option_parser.dup end @@ -20,6 +22,10 @@ @option_parser.parse argv end + def to_s + @option_parser.to_s + end + @@option_parser = OptionParser.new do |o| o.banner = "Usage: vcs [options] <file>*" Index: vcs/lib/vcs/message.rb --- vcs/lib/vcs/message.rb (revision 231) +++ vcs/lib/vcs/message.rb (working copy) @@ -7,20 +7,6 @@ require 'vcs/changelog' class Vcs - def diffw! ( *args ) - diff!(*args) - end -end # class Vcs - - -class Svn - def diffw! ( *args ) - diff! '--diff-cmd', 'diff', '-x', '-NPbuw', *args - end -end # class Svn - - -class Vcs @@message = Pathname.new(',message')