diff --git a/config/default.yml b/config/default.yml index 9d95fd4e..c3f74939 100644 --- a/config/default.yml +++ b/config/default.yml @@ -477,6 +477,14 @@ PreCommit: flags: ['--standard=PSR2', '--report=csv'] include: '**/*.php' + ProhibitedKeyword: + enabled: false + description: 'Check for prohibited keywords' + keywords: + - console.log( + - binding.pry + - eval( + Pronto: enabled: false description: 'Analyzing with pronto' diff --git a/lib/overcommit/hook/pre_commit/prohibited_keyword.rb b/lib/overcommit/hook/pre_commit/prohibited_keyword.rb new file mode 100644 index 00000000..d6ad87d4 --- /dev/null +++ b/lib/overcommit/hook/pre_commit/prohibited_keyword.rb @@ -0,0 +1,27 @@ +module Overcommit::Hook::PreCommit + class ProhibitedKeyword < Base + def run + errors = [] + + applicable_files.each do |file| + if File.read(file) =~ /(#{formatted_keywords})/ + errors << "#{file}: contains prohibited keyword.`" + end + end + + return :fail, errors.join("\n") if errors.any? + + :pass + end + + private + + def formatted_keywords + prohibited_keywords.map { |keyword| Regexp.quote(keyword) }.join('|') + end + + def prohibited_keywords + @prohibited_keywords ||= Array(config['keywords']) + end + end +end diff --git a/spec/overcommit/hook/pre_commit/prohibited_keyword_spec.rb b/spec/overcommit/hook/pre_commit/prohibited_keyword_spec.rb new file mode 100644 index 00000000..736f8899 --- /dev/null +++ b/spec/overcommit/hook/pre_commit/prohibited_keyword_spec.rb @@ -0,0 +1,49 @@ +require 'spec_helper' +require 'overcommit/hook_context/pre_push' + +describe Overcommit::Hook::PreCommit::ProhibitedKeyword do + let(:hook_config) { { keywords: ['console.log(', 'eval('] } } + let(:config) { Overcommit::ConfigurationLoader.default_configuration } + subject { described_class.new(config, context) } + + context 'with blacklisted keyword' do + let(:file) { create_file('console.log("hello")') } + + context 'with matching file' do + let(:context) { double('context', modified_files: [file.path]) } + + it { should fail_hook /contains prohibited keyword./ } + end + + context 'without matching file' do + let(:context) { double('context', modified_files: []) } + + it { should pass } + end + end + + context 'without blacklisted keyword' do + let(:file) { create_file('alert("hello")') } + + context 'with matching file' do + let(:context) { double('context', modified_files: [file.path]) } + + it { should pass } + end + + context 'without matching file' do + let(:context) { double('context', modified_files: []) } + + it { should pass } + end + end + + private + + def create_file(content) + Tempfile.new('index.html').tap do |file| + file.write(content) + file.close + end + end +end