github_webhook 1.1.1 → 1.4.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b600d6f9819bb2733a770802f9b7d9bf3c6ce0494f5efd5331a3c837449138e9
4
- data.tar.gz: 2508562d1d07536d4269a8d9a2887e11a5fb777d8def729e1a7874e04a818b23
3
+ metadata.gz: ec22b9a09fcb0d2833a46cffacf39ac9703b33fd0b909bfee2258f4191fdfc21
4
+ data.tar.gz: 0f0fc361b3f1ccccb93dc66baf1b75d3ebc1f34fa3ef6022a0598dd6abc20c1b
5
5
  SHA512:
6
- metadata.gz: bab9275ab482493469fff0e8b161d320626b514303e4370fff55929beb2ed30aac8f2eaf6c21410834f4c38d56c4e633e3ce7ef768a04c1cf1bae02a3f5e4413
7
- data.tar.gz: 5359dd0bc8f338a19d95ca06f2b8c0c340f02f2ccd49aebae4d8eae7cce27a85dc8f300524551ee298a3cbe49e5f6aec71ad4a87f4cebfd7dd44d6101386074e
6
+ metadata.gz: 4292322d0e533e85de5fdedf0c67efe57847114beda60ba710a3fe191d9a59ad3c61fe8ead9c68272ba8067b53f709a10980059c6cb4a37f3898a6bc6b0b1f3a
7
+ data.tar.gz: 767ce312e69c381ac91cc6bd4c9cf913b1297ca9d4ee990f38cf8e55f306c8607421dcaf1b0ab9941da41003f20674346512c53595d5d61c6a9866cdb6f5a559
@@ -0,0 +1,24 @@
1
+ name: Ruby
2
+
3
+ on:
4
+ push:
5
+ branches: [ master ]
6
+ pull_request:
7
+ branches: [ master ]
8
+
9
+ jobs:
10
+ build:
11
+
12
+ runs-on: ubuntu-latest
13
+
14
+ steps:
15
+ - uses: actions/checkout@v2
16
+ - name: Set up Ruby 2.7
17
+ uses: actions/setup-ruby@v1
18
+ with:
19
+ ruby-version: 2.7.x
20
+ - name: Build and test with Rake
21
+ run: |
22
+ gem install bundler
23
+ bundle install --jobs 4 --retry 3
24
+ bundle exec rake
data/.ruby-version CHANGED
@@ -1 +1 @@
1
- 2.4.2
1
+ 2.7.4
data/Appraisals CHANGED
@@ -9,3 +9,7 @@ end
9
9
  appraise "rails-5.1" do
10
10
  gem "rails", "~> 5.1.0"
11
11
  end
12
+
13
+ appraise "rails-6.0" do
14
+ gem "rails", "~> 6.0"
15
+ end
data/README.md CHANGED
@@ -1,19 +1,27 @@
1
- [![Build Status](https://travis-ci.org/ssaunier/github_webhook.svg?branch=master)](https://travis-ci.org/ssaunier/github_webhook)
2
- [![Code Climate](https://codeclimate.com/github/ssaunier/github_webhook/badges/gpa.svg)](https://codeclimate.com/github/ssaunier/github_webhook)
1
+
3
2
  [![Gem Version](https://badge.fury.io/rb/github_webhook.svg)](http://badge.fury.io/rb/github_webhook)
4
3
 
5
4
 
6
- # GithubWebhook
5
+ # Github Webhook for Rails
7
6
 
8
7
  This gem will help you to quickly setup a route in your Rails application which listens
9
8
  to a [GitHub webhook](https://developer.github.com/webhooks/)
10
9
 
10
+ ## Alternatives
11
+
12
+ If you want to use this logic outside of Rails, you should consider the following gems (cf [#19](https://github.com/ssaunier/github_webhook/issues/19)):
13
+
14
+ - [`sinatra-github_webhooks`](https://github.com/chrismytton/sinatra-github_webhooks)
15
+ - [`rack-github_webhooks`](https://github.com/chrismytton/rack-github_webhooks)
16
+
17
+ If you are on Rails, please read on!
18
+
11
19
  ## Installation
12
20
 
13
21
  Add this line to your application's Gemfile:
14
22
 
15
23
  ```ruby
16
- gem 'github_webhook', '~> 1.1'
24
+ gem 'github_webhook', '~> 1.4'
17
25
  ```
18
26
 
19
27
  And then execute:
@@ -22,9 +22,7 @@ Gem::Specification.new do |spec|
22
22
  spec.add_dependency "activesupport", ">= 4"
23
23
  spec.add_dependency "railties", ">= 4"
24
24
 
25
- spec.add_development_dependency "bundler", "~> 1.5"
26
- spec.add_development_dependency "rake", "~> 10.1"
27
- spec.add_development_dependency "rspec", "~> 2.14"
28
- spec.add_development_dependency "codeclimate-test-reporter", "~> 1.0"
25
+ spec.add_development_dependency "rake", "~> 12.3"
26
+ spec.add_development_dependency "rspec", "~> 3.9"
29
27
  spec.add_development_dependency "appraisal"
30
28
  end
@@ -1,44 +1,44 @@
1
1
  module GithubWebhook::Processor
2
2
  extend ActiveSupport::Concern
3
+ require 'abstract_controller'
3
4
 
4
5
  included do
5
6
  before_action :authenticate_github_request!, only: :create
6
7
  before_action :check_github_event!, only: :create
7
8
  end
8
9
 
9
- class SignatureError < StandardError; end
10
- class UnspecifiedWebhookSecretError < StandardError; end
11
- class UnsupportedGithubEventError < StandardError; end
12
- class UnsupportedContentTypeError < StandardError; end
13
-
14
10
  # To fetch list from https://developer.github.com/v3/activity/events/types
15
11
  # run this little JS code in the console:
16
- # $("h3:contains('Webhook event name')").next('p').each((_, p) => console.log(p.innerText))
12
+ # document.querySelectorAll('.list-style-none li.lh-condensed a').forEach(e => console.log(e.text))
17
13
  GITHUB_EVENTS = %w(
18
14
  check_run
19
15
  check_suite
16
+ code_scanning_alert
20
17
  commit_comment
18
+ content_reference
21
19
  create
22
20
  delete
21
+ deploy_key
23
22
  deployment
24
23
  deployment_status
25
- download
26
- follow
24
+ discussion
25
+ discussion_comment
27
26
  fork
28
- fork_apply
29
27
  github_app_authorization
30
- gist
31
28
  gollum
32
29
  installation
33
30
  installation_repositories
34
31
  issue_comment
35
32
  issues
36
33
  label
34
+ marketplace_purchase
37
35
  member
38
36
  membership
37
+ meta
39
38
  milestone
40
39
  organization
41
40
  org_block
41
+ package
42
42
  page_build
43
43
  ping
44
44
  project_card
@@ -50,13 +50,20 @@ module GithubWebhook::Processor
50
50
  pull_request_review_comment
51
51
  push
52
52
  release
53
+ repository_dispatch
53
54
  repository
54
55
  repository_import
55
56
  repository_vulnerability_alert
57
+ secret_scanning_alert
58
+ security_advisory
59
+ sponsorship
60
+ star
56
61
  status
57
62
  team
58
63
  team_add
59
64
  watch
65
+ workflow_dispatch
66
+ workflow_run
60
67
  )
61
68
 
62
69
  def create
@@ -64,7 +71,7 @@ module GithubWebhook::Processor
64
71
  self.send event_method, json_body
65
72
  head(:ok)
66
73
  else
67
- raise NoMethodError.new("GithubWebhooksController##{event_method} not implemented")
74
+ raise AbstractController::ActionNotFound.new("GithubWebhooksController##{event_method} not implemented")
68
75
  end
69
76
  end
70
77
 
@@ -75,23 +82,23 @@ module GithubWebhook::Processor
75
82
 
76
83
  private
77
84
 
78
- HMAC_DIGEST = OpenSSL::Digest.new('sha1')
85
+ HMAC_DIGEST = OpenSSL::Digest.new('sha256')
79
86
 
80
87
  def authenticate_github_request!
81
- raise UnspecifiedWebhookSecretError.new unless respond_to?(:webhook_secret, true)
88
+ raise AbstractController::ActionNotFound.new unless respond_to?(:webhook_secret, true)
82
89
  secret = webhook_secret(json_body)
83
90
 
84
- expected_signature = "sha1=#{OpenSSL::HMAC.hexdigest(HMAC_DIGEST, secret, request_body)}"
85
- if signature_header != expected_signature
91
+ expected_signature = "sha256=#{OpenSSL::HMAC.hexdigest(HMAC_DIGEST, secret, request_body)}"
92
+ unless ActiveSupport::SecurityUtils.secure_compare(signature_header, expected_signature)
86
93
  GithubWebhook.logger && GithubWebhook.logger.warn("[GithubWebhook::Processor] signature "\
87
94
  "invalid, actual: #{signature_header}, expected: #{expected_signature}")
88
- raise SignatureError
95
+ raise AbstractController::ActionNotFound
89
96
  end
90
97
  end
91
98
 
92
99
  def check_github_event!
93
100
  unless GITHUB_EVENTS.include?(request.headers['X-GitHub-Event'])
94
- raise UnsupportedGithubEventError.new("#{request.headers['X-GitHub-Event']} is not a whiltelisted GitHub event. See https://developer.github.com/v3/activity/events/types/")
101
+ raise AbstractController::ActionNotFound.new("#{request.headers['X-GitHub-Event']} is not a whitelisted GitHub event. See https://developer.github.com/v3/activity/events/types/")
95
102
  end
96
103
  end
97
104
 
@@ -112,7 +119,7 @@ module GithubWebhook::Processor
112
119
  when 'application/json'
113
120
  payload = request_body
114
121
  else
115
- raise UnsupportedContentTypeError.new(
122
+ raise AbstractController::ActionNotFound.new(
116
123
  "Content-Type #{content_type} is not supported. Use 'application/x-www-form-urlencoded' or 'application/json")
117
124
  end
118
125
  ActiveSupport::HashWithIndifferentAccess.new(JSON.load(payload))
@@ -120,7 +127,7 @@ module GithubWebhook::Processor
120
127
  end
121
128
 
122
129
  def signature_header
123
- @signature_header ||= request.headers['X-Hub-Signature']
130
+ @signature_header ||= request.headers['X-Hub-Signature-256'] || ''
124
131
  end
125
132
 
126
133
  def event_method
@@ -1,3 +1,3 @@
1
1
  module GithubWebhook
2
- VERSION = "1.1.1"
2
+ VERSION = "1.4.0"
3
3
  end
@@ -53,9 +53,9 @@ module GithubWebhook
53
53
  context 'when #webhook_secret is not defined' do
54
54
  let(:controller_class) { ControllerWithoutSecret }
55
55
 
56
- it "raises a Processor::UnspecifiedWebhookSecretError" do
56
+ it "raises a AbstractController::ActionNotFound" do
57
57
  expect { controller.send :authenticate_github_request! }
58
- .to raise_error(Processor::UnspecifiedWebhookSecretError)
58
+ .to raise_error(AbstractController::ActionNotFound)
59
59
  end
60
60
  end
61
61
 
@@ -65,7 +65,7 @@ module GithubWebhook
65
65
  it "calls the #push method in controller" do
66
66
  expect(controller).to receive(:github_push)
67
67
  controller.request.body = StringIO.new({ :foo => "bar" }.to_json.to_s)
68
- controller.request.headers['X-Hub-Signature'] = "sha1=52b582138706ac0c597c315cfc1a1bf177408a4d"
68
+ controller.request.headers['X-Hub-Signature-256'] = "sha256=3f3ab3986b656abb17af3eb1443ed6c08ef8fff9fea83915909d1b421aec89be"
69
69
  controller.request.headers['X-GitHub-Event'] = 'push'
70
70
  controller.request.headers['Content-Type'] = 'application/json'
71
71
  controller.send :authenticate_github_request! # Manually as we don't have the before_filter logic in our Mock object
@@ -75,7 +75,7 @@ module GithubWebhook
75
75
 
76
76
  it "calls the #push method in controller (json)" do
77
77
  controller.request.body = StringIO.new({ :foo => "bar" }.to_json.to_s)
78
- controller.request.headers['X-Hub-Signature'] = "sha1=52b582138706ac0c597c315cfc1a1bf177408a4d"
78
+ controller.request.headers['X-Hub-Signature-256'] = "sha256=3f3ab3986b656abb17af3eb1443ed6c08ef8fff9fea83915909d1b421aec89be"
79
79
  controller.request.headers['X-GitHub-Event'] = 'push'
80
80
  controller.request.headers['Content-Type'] = 'application/json'
81
81
  controller.send :authenticate_github_request! # Manually as we don't have the before_action logic in our Mock object
@@ -86,7 +86,7 @@ module GithubWebhook
86
86
  it "calls the #push method (x-www-form-urlencoded encoded)" do
87
87
  body = "payload=" + CGI::escape({ :foo => "bar" }.to_json.to_s)
88
88
  controller.request.body = StringIO.new(body)
89
- controller.request.headers['X-Hub-Signature'] = "sha1=6986874ecdf710b04de7ef5a040161d41687407a"
89
+ controller.request.headers['X-Hub-Signature-256'] = "sha256=cefe60b775fcb22483ceece8f20be4869868a20fb4aa79829e53c1de61b99d01"
90
90
  controller.request.headers['X-GitHub-Event'] = 'push'
91
91
  controller.request.headers['Content-Type'] = 'application/x-www-form-urlencoded'
92
92
  controller.send :authenticate_github_request! # Manually as we don't have the before_action logic in our Mock object
@@ -96,30 +96,46 @@ module GithubWebhook
96
96
 
97
97
  it "raises an error when signature does not match" do
98
98
  controller.request.body = StringIO.new({ :foo => "bar" }.to_json.to_s)
99
- controller.request.headers['X-Hub-Signature'] = "sha1=FOOBAR"
99
+ controller.request.headers['X-Hub-Signature-256'] = "sha256=FOOBAR"
100
100
  controller.request.headers['X-GitHub-Event'] = 'push'
101
101
  controller.request.headers['Content-Type'] = 'application/json'
102
- expect { controller.send :authenticate_github_request! }.to raise_error(Processor::SignatureError)
102
+ expect { controller.send :authenticate_github_request! }.to raise_error(AbstractController::ActionNotFound)
103
103
  end
104
104
 
105
105
  it "raises an error when the github event method is not implemented" do
106
106
  controller.request.headers['X-GitHub-Event'] = 'deployment'
107
107
  controller.request.headers['Content-Type'] = 'application/json'
108
- expect { controller.create }.to raise_error(NoMethodError)
108
+ expect { controller.create }.to raise_error(
109
+ AbstractController::ActionNotFound,
110
+ "GithubWebhooksController#github_deployment not implemented",
111
+ )
109
112
  end
110
113
 
111
114
  it "raises an error when the github event is not in the whitelist" do
112
115
  controller.request.headers['X-GitHub-Event'] = 'fake_event'
113
116
  controller.request.headers['Content-Type'] = 'application/json'
114
- expect { controller.send :check_github_event! }.to raise_error(Processor::UnsupportedGithubEventError)
117
+ expect { controller.send :check_github_event! }.to raise_error(
118
+ AbstractController::ActionNotFound,
119
+ "fake_event is not a whitelisted GitHub event. See https://developer.github.com/v3/activity/events/types/",
120
+ )
115
121
  end
116
122
 
117
123
  it "raises an error when the content type is not correct" do
118
124
  controller.request.body = StringIO.new({ :foo => "bar" }.to_json.to_s)
119
- controller.request.headers['X-Hub-Signature'] = "sha1=52b582138706ac0c597c315cfc1a1bf177408a4d"
125
+ controller.request.headers['X-Hub-Signature-256'] = "sha256=3f3ab3986b656abb17af3eb1443ed6c08ef8fff9fea83915909d1b421aec89be"
120
126
  controller.request.headers['X-GitHub-Event'] = 'ping'
121
127
  controller.request.headers['Content-Type'] = 'application/xml'
122
- expect { controller.send :authenticate_github_request! }.to raise_error(Processor::UnsupportedContentTypeError)
128
+ expect { controller.send :authenticate_github_request! }.to raise_error(
129
+ AbstractController::ActionNotFound,
130
+ "Content-Type application/xml is not supported. Use 'application/x-www-form-urlencoded' or 'application/json",
131
+ )
132
+ end
133
+
134
+ it 'raises SignatureError when the X-Hub-Signature header is missing' do
135
+ controller.request.body = StringIO.new('{}')
136
+ controller.request.headers['Content-Type'] = 'application/json'
137
+ controller.request.headers['X-GitHub-Event'] = 'ping'
138
+ expect { controller.send :authenticate_github_request! }.to raise_error(AbstractController::ActionNotFound)
123
139
  end
124
140
  end
125
141
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: github_webhook
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.1
4
+ version: 1.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sebastien Saunier
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-08-22 00:00:00.000000000 Z
11
+ date: 2021-12-16 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rack
@@ -52,62 +52,34 @@ dependencies:
52
52
  - - ">="
53
53
  - !ruby/object:Gem::Version
54
54
  version: '4'
55
- - !ruby/object:Gem::Dependency
56
- name: bundler
57
- requirement: !ruby/object:Gem::Requirement
58
- requirements:
59
- - - "~>"
60
- - !ruby/object:Gem::Version
61
- version: '1.5'
62
- type: :development
63
- prerelease: false
64
- version_requirements: !ruby/object:Gem::Requirement
65
- requirements:
66
- - - "~>"
67
- - !ruby/object:Gem::Version
68
- version: '1.5'
69
55
  - !ruby/object:Gem::Dependency
70
56
  name: rake
71
57
  requirement: !ruby/object:Gem::Requirement
72
58
  requirements:
73
59
  - - "~>"
74
60
  - !ruby/object:Gem::Version
75
- version: '10.1'
61
+ version: '12.3'
76
62
  type: :development
77
63
  prerelease: false
78
64
  version_requirements: !ruby/object:Gem::Requirement
79
65
  requirements:
80
66
  - - "~>"
81
67
  - !ruby/object:Gem::Version
82
- version: '10.1'
68
+ version: '12.3'
83
69
  - !ruby/object:Gem::Dependency
84
70
  name: rspec
85
71
  requirement: !ruby/object:Gem::Requirement
86
72
  requirements:
87
73
  - - "~>"
88
74
  - !ruby/object:Gem::Version
89
- version: '2.14'
90
- type: :development
91
- prerelease: false
92
- version_requirements: !ruby/object:Gem::Requirement
93
- requirements:
94
- - - "~>"
95
- - !ruby/object:Gem::Version
96
- version: '2.14'
97
- - !ruby/object:Gem::Dependency
98
- name: codeclimate-test-reporter
99
- requirement: !ruby/object:Gem::Requirement
100
- requirements:
101
- - - "~>"
102
- - !ruby/object:Gem::Version
103
- version: '1.0'
75
+ version: '3.9'
104
76
  type: :development
105
77
  prerelease: false
106
78
  version_requirements: !ruby/object:Gem::Requirement
107
79
  requirements:
108
80
  - - "~>"
109
81
  - !ruby/object:Gem::Version
110
- version: '1.0'
82
+ version: '3.9'
111
83
  - !ruby/object:Gem::Dependency
112
84
  name: appraisal
113
85
  requirement: !ruby/object:Gem::Requirement
@@ -129,9 +101,9 @@ executables: []
129
101
  extensions: []
130
102
  extra_rdoc_files: []
131
103
  files:
104
+ - ".github/workflows/ruby.yml"
132
105
  - ".gitignore"
133
106
  - ".ruby-version"
134
- - ".travis.yml"
135
107
  - Appraisals
136
108
  - Gemfile
137
109
  - LICENSE.txt
@@ -151,7 +123,7 @@ homepage: https://github.com/ssaunier/github_webhook
151
123
  licenses:
152
124
  - MIT
153
125
  metadata: {}
154
- post_install_message:
126
+ post_install_message:
155
127
  rdoc_options: []
156
128
  require_paths:
157
129
  - lib
@@ -166,9 +138,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
166
138
  - !ruby/object:Gem::Version
167
139
  version: '0'
168
140
  requirements: []
169
- rubyforge_project:
170
- rubygems_version: 2.7.6
171
- signing_key:
141
+ rubygems_version: 3.1.6
142
+ signing_key:
172
143
  specification_version: 4
173
144
  summary: Process GitHub Webhooks in your Rails app (Controller mixin)
174
145
  test_files:
data/.travis.yml DELETED
@@ -1,14 +0,0 @@
1
- language: ruby
2
- rvm:
3
- - 2.4.2
4
- - 2.3.5
5
- - 2.2.8
6
- gemfile:
7
- - gemfiles/rails_4.2.gemfile
8
- - gemfiles/rails_5.0.gemfile
9
- - gemfiles/rails_5.1.gemfile
10
- addons:
11
- code_climate:
12
- repo_token: 50425d682162d68af0b65bd9e5160da8337d2159fc3ebc00d2a5b14386548ac5
13
- after_success:
14
- - bundle exec codeclimate-test-reporter