File tree 24 files changed +80
-34
lines changed
overcommit/hook/pre_commit
24 files changed +80
-34
lines changed Original file line number Diff line number Diff line change 1
1
# Overcommit Changelog
2
2
3
+ ## master (unreleased)
4
+
5
+ * Change ` command ` hook helper signature to accept an array of arguments
6
+ instead of a shell string
7
+
3
8
## 0.6.3
4
9
5
10
* ` TextWidth ` pre-commit hook now supports customized maximum subject line
Original file line number Diff line number Diff line change @@ -29,7 +29,13 @@ about Overcommit on our [engineering blog](http://causes.github.io).
29
29
30
30
## Requirements
31
31
32
- * Ruby 1.8.7+ is supported
32
+ The following Ruby versions are supported:
33
+
34
+ * 1.8.7
35
+ * 1.9.2
36
+ * 1.9.3
37
+ * 2.0.0
38
+ * 2.1.0
33
39
34
40
### Dependencies
35
41
Original file line number Diff line number Diff line change @@ -7,7 +7,7 @@ module Overcommit::Hook::CommitMsg
7
7
# edit the message after a prepare-commit-msg hook was run.
8
8
class GerritChangeId < Base
9
9
def run
10
- result = command ( " #{ SCRIPT_LOCATION } #{ commit_message_file } " )
10
+ result = command ( [ SCRIPT_LOCATION , commit_message_file ] )
11
11
return ( result . success? ? :good : :bad ) , result . stdout
12
12
end
13
13
Original file line number Diff line number Diff line change @@ -15,15 +15,15 @@ def run
15
15
private
16
16
17
17
def dependencies_changed?
18
- result = command ( " git diff --exit-code #{ new_head } #{ previous_head } --name-only" )
18
+ result = command ( %w[ git diff --exit-code --name-only ] + [ new_head , previous_head ] )
19
19
20
20
result . stdout . split ( "\n " ) . any? do |file |
21
21
Array ( @config [ 'include' ] ) . any? { |glob | File . fnmatch ( glob , file ) }
22
22
end
23
23
end
24
24
25
25
def dependencies_satisfied?
26
- command ( ' bundle check' ) . success?
26
+ command ( %w[ bundle check ] ) . success?
27
27
end
28
28
end
29
29
end
Original file line number Diff line number Diff line change @@ -2,7 +2,7 @@ module Overcommit::Hook::PreCommit
2
2
# Checks the format of an author's email address.
3
3
class AuthorEmail < Base
4
4
def run
5
- result = command ( ' git config --get user.email' )
5
+ result = command ( %w[ git config --get user.email ] )
6
6
email = result . stdout . chomp
7
7
8
8
unless email =~ /#{ @config [ 'pattern' ] } /
Original file line number Diff line number Diff line change @@ -2,7 +2,7 @@ module Overcommit::Hook::PreCommit
2
2
# Ensures that a commit author has a name with at least first and last names.
3
3
class AuthorName < Base
4
4
def run
5
- result = command ( ' git config --get user.name' )
5
+ result = command ( %w[ git config --get user.name ] )
6
6
name = result . stdout . chomp
7
7
8
8
unless name . split ( ' ' ) . count >= 2
Original file line number Diff line number Diff line change @@ -8,14 +8,14 @@ def run
8
8
end
9
9
10
10
# Ignore if Gemfile.lock is not tracked by git
11
- return :good if command ( " git check-ignore #{ LOCK_FILE } " ) . success?
11
+ return :good if command ( %w[ git check-ignore ] + [ LOCK_FILE ] ) . success?
12
12
13
- result = command ( ' bundle check' )
13
+ result = command ( %w[ bundle check ] )
14
14
unless result . success?
15
15
return :bad , result . stdout
16
16
end
17
17
18
- result = command ( " git diff --quiet -- #{ LOCK_FILE } " )
18
+ result = command ( %w[ git diff --quiet -- ] + [ LOCK_FILE ] )
19
19
unless result . success?
20
20
return :bad , "#{ LOCK_FILE } is not up-to-date -- run `bundle check`"
21
21
end
Original file line number Diff line number Diff line change 6
6
return :warn , 'Run `npm install -g coffeelint`'
7
7
end
8
8
9
- result = command ( " coffeelint --quiet #{ applicable_files . join ( ' ' ) } " )
9
+ result = command ( %w[ coffeelint --quiet ] + applicable_files )
10
10
return :good if result . success?
11
11
return :bad , result . stdout
12
12
end
Original file line number Diff line number Diff line change 6
6
return :warn , 'csslint not installed -- run `npm install -g csslint`'
7
7
end
8
8
9
- paths = applicable_files . join ( ' ' )
10
-
11
- result = command ( "csslint --quiet --format=compact #{ paths } | grep 'Error - '" )
9
+ result = command ( %w[ csslint --quiet --format=compact ] + applicable_files )
12
10
output = result . stdout
13
11
return ( output !~ /Error - (?!Unknown @ rule)/ ? :good : :bad ) , output
14
12
end
Original file line number Diff line number Diff line change 6
6
return :warn , 'haml-lint not installed -- run `gem install haml-lint`'
7
7
end
8
8
9
- result = command ( " haml-lint #{ applicable_files . join ( ' ' ) } " )
9
+ result = command ( %w[ haml-lint ] + applicable_files )
10
10
return :good if result . success?
11
11
12
12
# Keep lines from the output for files that we actually modified
Original file line number Diff line number Diff line change @@ -2,10 +2,8 @@ module Overcommit::Hook::PreCommit
2
2
# Checks for hard tabs in files.
3
3
class HardTabs < Base
4
4
def run
5
- paths = applicable_files . join ( ' ' )
6
-
7
5
# Catches hard tabs
8
- result = command ( " grep -IHn \ "\t \" #{ paths } " )
6
+ result = command ( %w[ grep -IHn ] + [ "\t " ] + applicable_files )
9
7
unless result . stdout . empty?
10
8
return :bad , "Hard tabs detected:\n #{ result . stdout } "
11
9
end
Original file line number Diff line number Diff line change 6
6
return :warn , 'jshint not installed -- run `npm install -g jshint`'
7
7
end
8
8
9
- result = command ( " jshint #{ applicable_files . join ( ' ' ) } " )
9
+ result = command ( %w[ jshint ] + applicable_files )
10
10
output = result . stdout
11
11
12
12
return ( output . empty? ? :good : :bad ) , output
Original file line number Diff line number Diff line change 7
7
return :warn , 'jscs not installed -- run `npm install -g jscs`'
8
8
end
9
9
10
- result = command ( " jscs --reporter=inline #{ applicable_files . join ( ' ' ) } " )
10
+ result = command ( %w[ jscs --reporter=inline ] + applicable_files )
11
11
return :good if result . success?
12
12
13
13
if /Config.*not found/i =~ result . stderr
Original file line number Diff line number Diff line change 6
6
return :warn , 'flake8 not installed -- run `pip install flake8`'
7
7
end
8
8
9
- result = command ( " flake8 #{ applicable_files . join ( ' ' ) } " )
9
+ result = command ( %w[ flake8 ] + applicable_files )
10
10
11
11
return ( result . success? ? :good : :bad ) , result . stdout
12
12
end
Original file line number Diff line number Diff line change @@ -6,11 +6,13 @@ def run
6
6
return :warn , 'Rubocop not installed -- run `gem install rubocop`'
7
7
end
8
8
9
- result = command ( " rubocop --format=emacs #{ applicable_files . join ( ' ' ) } 2>&1" )
9
+ result = command ( %w[ rubocop --format=emacs ] + applicable_files )
10
10
return :good if result . success?
11
11
12
+ output = result . stdout + result . stderr
13
+
12
14
# Keep lines from the output for files that we actually modified
13
- error_lines , warning_lines = result . stdout . split ( "\n " ) . partition do |output_line |
15
+ error_lines , warning_lines = output . split ( "\n " ) . partition do |output_line |
14
16
if match = output_line . match ( /^([^:]+):(\d +)/ )
15
17
file = match [ 1 ]
16
18
line = match [ 2 ]
Original file line number Diff line number Diff line change 6
6
return :warn , 'scss-lint not installed -- run `gem install scss-lint`'
7
7
end
8
8
9
- result = command ( " scss-lint #{ applicable_files . join ( ' ' ) } " )
9
+ result = command ( %w[ scss-lint ] + applicable_files )
10
10
return :good if result . success?
11
11
12
12
# Keep lines from the output for files that we actually modified
Original file line number Diff line number Diff line change @@ -2,9 +2,7 @@ module Overcommit::Hook::PreCommit
2
2
# Checks for trailing whitespace in files.
3
3
class TrailingWhitespace < Base
4
4
def run
5
- paths = applicable_files . join ( ' ' )
6
-
7
- result = command ( "grep -IHn \" \\ s$\" #{ paths } " )
5
+ result = command ( %w[ grep -IHn \s $ ] + applicable_files )
8
6
unless result . stdout . empty?
9
7
return :bad , "Trailing whitespace detected:\n #{ result . stdout } "
10
8
end
Original file line number Diff line number Diff line change
1
+ require 'childprocess'
2
+ require 'tempfile'
3
+
4
+ module Overcommit
5
+ # Manages execution of a child process, collecting the exit status and
6
+ # standard out/error output.
7
+ class Subprocess
8
+ # Encapsulates the result of a process.
9
+ Result = Struct . new ( :status , :stderr , :stdout ) do
10
+ def success?
11
+ status == 0
12
+ end
13
+ end
14
+
15
+ # Spawns a new process using the given array of arguments (the first
16
+ # element is the command).
17
+ def self . spawn ( args )
18
+ process = ChildProcess . build ( *args )
19
+
20
+ err = ::Tempfile . new ( 'err' )
21
+ err . sync = true
22
+ out = ::Tempfile . new ( 'out' )
23
+ out . sync = true
24
+
25
+ process . io . stderr = err
26
+ process . io . stdout = out
27
+
28
+ process . start
29
+ process . wait
30
+
31
+ err . rewind
32
+ out . rewind
33
+
34
+ Result . new ( process . exit_code , err . read , out . read )
35
+ end
36
+ end
37
+ end
Original file line number Diff line number Diff line change 1
- require 'wopen3 '
1
+ require 'overcommit/subprocess '
2
2
3
3
module Overcommit
4
4
# Utility functions for general use.
@@ -62,9 +62,9 @@ def in_path?(cmd)
62
62
# Overcommit to call other Ruby executables without requiring that they be
63
63
# specified in Overcommit's Gemfile--a nasty consequence of using
64
64
# `bundle exec overcommit` while developing locally.
65
- def command ( command )
65
+ def command ( args )
66
66
with_environment 'RUBYOPT' => nil do
67
- Wopen3 . system ( command )
67
+ Subprocess . spawn ( args )
68
68
end
69
69
end
70
70
Original file line number Diff line number Diff line change @@ -26,7 +26,7 @@ Gem::Specification.new do |s|
26
26
27
27
s . required_ruby_version = '>= 1.8.7'
28
28
29
- s . add_dependency 'wopen3 '
29
+ s . add_dependency 'childprocess' , '>= 0.5.1 '
30
30
31
31
s . add_development_dependency 'rspec' , '2.14.1'
32
32
s . add_development_dependency 'image_optim' , '0.11.1'
Original file line number Diff line number Diff line change 1
1
require 'spec_helper'
2
2
3
3
describe 'commiting' do
4
- subject { shell ( ' git commit --allow-empty -m " Test"' ) }
4
+ subject { shell ( %w[ git commit --allow-empty -m Test ] ) }
5
5
6
6
let ( :config ) { <<-YML }
7
7
CommitMsg:
Original file line number Diff line number Diff line change 38
38
before do
39
39
result . stub ( :success? => success , :stdout => 'Bundler error message' )
40
40
subject . stub ( :command ) . and_call_original
41
- subject . stub ( :command ) . with ( ' bundle check' ) . and_return ( result )
41
+ subject . stub ( :command ) . with ( %w[ bundle check ] ) . and_return ( result )
42
42
end
43
43
44
44
context 'and bundle check exits unsuccessfully' do
Original file line number Diff line number Diff line change 41
41
result . stub ( :stdout ) . and_return ( [
42
42
'file1.rb:1:1: C: Missing top-level class documentation' ,
43
43
] . join ( "\n " ) )
44
+ result . stub ( :stderr ) . and_return ( '' )
44
45
45
46
subject . stub ( :modified_lines ) . and_return ( [ 2 , 3 ] )
46
47
end
53
54
result . stub ( :stdout ) . and_return ( [
54
55
'file1.rb:1:1: C: Missing top-level class documentation' ,
55
56
] . join ( "\n " ) )
57
+ result . stub ( :stderr ) . and_return ( '' )
56
58
57
59
subject . stub ( :modified_lines ) . and_return ( [ 1 , 2 ] )
58
60
end
Original file line number Diff line number Diff line change 1
- require 'wopen3 '
1
+ require 'overcommit/subprocess '
2
2
3
3
# Helpers for executing shell commands in tests.
4
4
module ShellHelpers
5
5
def shell ( command )
6
- Wopen3 . system ( command )
6
+ Overcommit :: Subprocess . spawn ( command )
7
7
end
8
8
end
You can’t perform that action at this time.
0 commit comments