gitty 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,50 @@
1
+ class Gitty::Hook::Manager < Gitty::Runner
2
+ include ::Gitty::Helpers
3
+ def initialize(args, stdout = STDOUT, stderr = STDERR)
4
+ super
5
+ @hookname = args.shift
6
+ end
7
+
8
+ def options
9
+ @options ||= super.update(:kind => :local)
10
+ end
11
+
12
+ def src_hook_file
13
+ Gitty.find_asset("hooks/#{@hookname}")
14
+ end
15
+
16
+ def master_hook_file
17
+ @master_hook_file ||= hooks_directory + @hookname
18
+ end
19
+
20
+ def meta_data
21
+ @meta_data ||= Gitty.extract_meta_data(File.read(src_hook_file))
22
+ end
23
+
24
+ def run
25
+ raise NotImplementedError
26
+ end
27
+
28
+ def target_file(hook)
29
+ @target_file ||= file_with_existing_directory!(base_directory + "#{hook}.d/#{@hookname}")
30
+ end
31
+
32
+ def base_directory
33
+ @base_directory ||= existing_directory!(".git/hooks/#{options[:kind]}")
34
+ end
35
+
36
+ def helpers_directory
37
+ @helpers_directory ||= existing_directory!(".git/hooks/#{options[:kind]}/helpers")
38
+ end
39
+
40
+ def hooks_directory
41
+ existing_directory!(base_directory + "hooks")
42
+ end
43
+
44
+ def option_parser
45
+ @option_parser ||= super.tap do |opts|
46
+ opts.on("-l", "--local", "Local hook (default)") { |l| options[:kind] = :local }
47
+ opts.on("-s", "--shared", "Remote hook") { |l| options[:kind] = :shared }
48
+ end
49
+ end
50
+ end
@@ -0,0 +1,34 @@
1
+ class Gitty::Hook::Publish < Gitty::Runner
2
+ include ::Gitty::Helpers
3
+
4
+ def run
5
+ rev = nil
6
+ puts "Publishing with message #{options[:message].inspect}"
7
+ with_env_var("GIT_OBJECT_DIRECTORY", File.join(Dir.pwd, ".git/objects")) do
8
+ Dir.chdir(".git/hooks/shared") do
9
+ cmd(*%w[git add . -A])
10
+ cmd(*%w[git commit -m].push(options[:message]))
11
+ rev = %x{git rev-parse HEAD}.chomp
12
+ end
13
+ end
14
+ # back on the mother repo...
15
+ cmd(*%w[git push origin -f].push("#{rev}:refs/heads/--hooks--"))
16
+ end
17
+
18
+ protected
19
+ def option_parser
20
+ @option_parser ||= super.tap do |opts|
21
+ opts.banner = "Usage: git hook publish [options]"
22
+ opts.on("-m [message]", "--message [message]", "Message for commit (required)") do |m|
23
+ options[:message] = m
24
+ end
25
+ end
26
+ end
27
+
28
+ def parse_args!
29
+ super
30
+ if options[:message].nil?
31
+ puts option_parser
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,17 @@
1
+ require GITTY_PATH + "commands/manager"
2
+ class Gitty::Hook::Remove < Gitty::Hook::Manager
3
+ include FileUtils
4
+ def run
5
+ rm(master_hook_file)
6
+ meta_data["targets"].each do |target|
7
+ rm(target_file(target))
8
+ end
9
+ # TODO - cleanup helpers
10
+ end
11
+
12
+ def option_parser
13
+ @option_parser ||= super.tap do |opts|
14
+ opts.banner = "Usage: git hook remove [opts] hook-name"
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,32 @@
1
+ require 'fileutils'
2
+ class Gitty::Hook::Shell < Gitty::Runner
3
+ include ::Gitty::Helpers
4
+
5
+ def run
6
+ exec "bash --init-file #{create_init_file}"
7
+ end
8
+
9
+ def create_init_file
10
+ "/tmp/gitty-shell-init".tap do |filename|
11
+ File.open(filename, "wb") do |f|
12
+ f.puts(<<-EOF)
13
+ pushd $HOME > /dev/null
14
+ [ -f $HOME/.bashrc ] && . $HOME/.bashrc
15
+ [ -f $HOME/.bash_profile ] && . $HOME/.bash_profile
16
+ popd > /dev/null
17
+ export GIT_OBJECT_DIRECTORY="$(pwd)/.git/objects"
18
+
19
+ export PS1="Shared Hooks [$(basename $(pwd))]$ "
20
+ cd .git/hooks/shared
21
+ rm "#{filename}"
22
+ EOF
23
+ end
24
+ end
25
+ end
26
+
27
+ def option_parser
28
+ super.tap do |opts|
29
+ opts.banner = "Usage: git hook shell"
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,21 @@
1
+ module Gitty::Helpers
2
+ def existing_directory!(dir)
3
+ FileUtils.mkdir_p(dir)
4
+ Pathname.new(dir)
5
+ end
6
+
7
+ def file_with_existing_directory!(path)
8
+ FileUtils.mkdir_p(File.dirname(path))
9
+ Pathname.new(path)
10
+ end
11
+
12
+ def with_env_var(name, value, &block)
13
+ previous_value, ENV[name] = ENV[name], value
14
+ yield
15
+ ENV[name] = previous_value
16
+ end
17
+
18
+ def cmd(*args)
19
+ system(*args.flatten)
20
+ end
21
+ end
@@ -0,0 +1,42 @@
1
+ class Gitty::Hook < Gitty::Runner
2
+ COMMANDS = %w[
3
+ init
4
+ list
5
+ add
6
+ remove
7
+ publish
8
+ shell
9
+ ]
10
+ COMMANDS.each do |cmd|
11
+ autoload cmd.classify.to_sym, (GITTY_PATH + "commands/#{cmd}.rb").to_s
12
+ end
13
+
14
+ def initialize(args, stdout = STDOUT, stderr = STDERR)
15
+ @args, @stdout, @stderr = args, stdout, stderr
16
+ if COMMANDS.include?(args.first)
17
+ @target = Gitty::Hook.const_get(args.shift.classify).new(args, stdout, stderr)
18
+ else
19
+ parse_args!
20
+ end
21
+ end
22
+
23
+ def option_parser
24
+ @option_parser ||= super.tap do |opts|
25
+ opts.banner = "Usage: git hook [command]\nCommands are: #{COMMANDS.join(', ')}"
26
+ end
27
+ end
28
+
29
+ def run
30
+ unless File.directory?(".git")
31
+ stderr.puts "You must run git hook from the root of a git repository"
32
+ exit 1
33
+ end
34
+ @target && @target.run
35
+ end
36
+
37
+ def parse_args!
38
+ opt_p = option_parser
39
+ opt_p.parse!(args)
40
+ puts opt_p
41
+ end
42
+ end
@@ -0,0 +1,44 @@
1
+ require "optparse"
2
+ class Gitty::Runner
3
+ attr_reader :stdout, :stderr, :args
4
+
5
+ def initialize(args, stdout = STDOUT, stderr = STDERR)
6
+ @args, @stdout, @stderr = args, stdout, stderr
7
+ parse_args!
8
+ end
9
+
10
+ def options
11
+ @options ||= {}
12
+ end
13
+
14
+ def run
15
+ raise NotImplementedError
16
+ end
17
+
18
+ def option_parser
19
+ @option_parser ||= OptionParser.new do |opts|
20
+ opts.banner = "Usage: #{$0}"
21
+ opts.separator "Options:"
22
+ opts.on('--help', "Show help") do |h|
23
+ @show_help = opts
24
+ end
25
+ end
26
+ end
27
+
28
+ def handle_show_help
29
+ if @show_help
30
+ puts @show_help
31
+ exit(1)
32
+ end
33
+ end
34
+
35
+ def self.run(args, stdout = STDOUT, stderr = STDERR)
36
+ new(args, stdout, stderr).run
37
+ end
38
+
39
+ protected
40
+ def parse_args!
41
+ option_parser.parse!(args)
42
+ handle_show_help
43
+ end
44
+ end
@@ -0,0 +1,13 @@
1
+ class String
2
+ def constantize
3
+ Object.module_eval("::" + self)
4
+ end
5
+
6
+ def underscore
7
+ gsub(/(^|\b)[A-Z]/) { |l| l.downcase}.gsub(/[A-Z]/) { |l| "_#{l.downcase}" }.gsub("::", "/")
8
+ end
9
+
10
+ def classify
11
+ gsub(/^[a-z]/) { |l| l.upcase}.gsub(/_[a-z]/) { |l| l[1..1].upcase}.gsub(/\b[a-z]/) {|l| l.upcase}.gsub("/", "::")
12
+ end
13
+ end
@@ -0,0 +1,5 @@
1
+ require File.expand_path('../../spec_helper', File.dirname(__FILE__))
2
+ require 'stringio'
3
+
4
+ describe Gitty::Hook::Add do
5
+ end
@@ -0,0 +1,59 @@
1
+ require 'spec_helper'
2
+
3
+ describe Gitty do
4
+ describe ".asset_file" do
5
+ it "searches first in the specified $GITTY_ASSETS environment variable" do
6
+ ENV.stub!(:[]).with("GITTY_ASSETS").and_return("/tmp/assets")
7
+ File.stub!(:exist?).with("/tmp/assets/helpers/helpful").and_return(true)
8
+ File.stub!(:exist?).with(ASSETS_PATH + "helpers/helpful").and_return(true)
9
+
10
+ Gitty.find_asset("helpers/helpful").should == "/tmp/assets/helpers/helpful"
11
+ end
12
+
13
+ it "searches the core ASSETS_PATH if GITTY_ASSETS is not defined" do
14
+ ENV.stub!(:[]).with("GITTY_ASSETS").and_return(nil)
15
+ File.stub!(:exist?).with((ASSETS_PATH + "helpers/helpful").to_s).and_return(true)
16
+ Gitty.find_asset("helpers/helpful").should == (ASSETS_PATH + "helpers/helpful").to_s
17
+ end
18
+
19
+ it "returns nil if none the file is not found" do
20
+ Gitty.find_asset("willy/wonka").should be_nil
21
+ end
22
+ end
23
+
24
+ describe ".extract_meta_data" do
25
+ it "extracts meta data from a stream" do
26
+ stream = <<-EOF
27
+ #!/usr/bash
28
+
29
+ # description: hi
30
+ # targets: ["post-merge", "post-checkout"]
31
+ #
32
+
33
+ here's my hook
34
+ EOF
35
+ Gitty.extract_meta_data(stream).should == {
36
+ "description" => "hi",
37
+ "targets" => ["post-merge", "post-checkout"]
38
+ }
39
+ end
40
+
41
+ it "returns nil when no data found" do
42
+ stream = <<-EOF
43
+ #!/usr/bash
44
+ #
45
+ #
46
+ EOF
47
+ Gitty.extract_meta_data(stream).should == nil
48
+ end
49
+
50
+ it "returns the data when there's no actual content" do
51
+ stream = <<-EOF
52
+ #!/usr/bash
53
+ #
54
+ # description: hi
55
+ EOF
56
+ Gitty.extract_meta_data(stream).should == {"description" => "hi"}
57
+ end
58
+ end
59
+ end
@@ -0,0 +1,6 @@
1
+ require File.dirname(__FILE__) + "/../lib/gitty"
2
+ SPEC_PATH = GITTY_ROOT_PATH + "spec"
3
+ require 'rubygems'
4
+ require 'cucumber'
5
+ require SPEC_PATH + "support/constants.rb"
6
+ require "spec"
@@ -0,0 +1 @@
1
+ BIN_PATH = GITTY_LIB_PATH + "../bin"
metadata ADDED
@@ -0,0 +1,90 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: gitty
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Tim Harper
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2010-02-21 00:00:00 -07:00
13
+ default_executable: git-hook
14
+ dependencies: []
15
+
16
+ description: Unobtrusively extend git
17
+ email: timcharper@gmail.com
18
+ executables:
19
+ - git-hook
20
+ extensions: []
21
+
22
+ extra_rdoc_files:
23
+ - LICENSE
24
+ - README.textile
25
+ files:
26
+ - LICENSE
27
+ - README.textile
28
+ - Rakefile
29
+ - assets/helpers/git-cleanup-branches
30
+ - assets/helpers/git-strip-new-whitespace
31
+ - assets/helpers/git-submodule-helper
32
+ - assets/helpers/git-trash
33
+ - assets/helpers/git-when-introduced
34
+ - assets/helpers/hookd_wrapper
35
+ - assets/hooks/clean-patches
36
+ - assets/hooks/git-post-checkout-submodules
37
+ - assets/hooks/git-prevent-messy-rebase
38
+ - assets/hooks/prevent-nocommit-tags
39
+ - bin/git-hook
40
+ - cucumber.yml
41
+ - lib/ext.rb
42
+ - lib/gitty.rb
43
+ - lib/gitty/commands/add.rb
44
+ - lib/gitty/commands/init.rb
45
+ - lib/gitty/commands/list.rb
46
+ - lib/gitty/commands/manager.rb
47
+ - lib/gitty/commands/publish.rb
48
+ - lib/gitty/commands/remove.rb
49
+ - lib/gitty/commands/shell.rb
50
+ - lib/gitty/helpers.rb
51
+ - lib/gitty/hook.rb
52
+ - lib/gitty/runner.rb
53
+ - lib/string.rb
54
+ - spec/gitty/commands/add_spec.rb
55
+ - spec/gitty_spec.rb
56
+ - spec/spec_helper.rb
57
+ - spec/support/constants.rb
58
+ has_rdoc: true
59
+ homepage: http://github.com/timcharper/gitty
60
+ licenses: []
61
+
62
+ post_install_message:
63
+ rdoc_options:
64
+ - --charset=UTF-8
65
+ require_paths:
66
+ - lib
67
+ required_ruby_version: !ruby/object:Gem::Requirement
68
+ requirements:
69
+ - - ">="
70
+ - !ruby/object:Gem::Version
71
+ version: "0"
72
+ version:
73
+ required_rubygems_version: !ruby/object:Gem::Requirement
74
+ requirements:
75
+ - - ">="
76
+ - !ruby/object:Gem::Version
77
+ version: "0"
78
+ version:
79
+ requirements: []
80
+
81
+ rubyforge_project:
82
+ rubygems_version: 1.3.5
83
+ signing_key:
84
+ specification_version: 3
85
+ summary: Unobtrusively extend git
86
+ test_files:
87
+ - spec/gitty/commands/add_spec.rb
88
+ - spec/gitty_spec.rb
89
+ - spec/spec_helper.rb
90
+ - spec/support/constants.rb