Skip to content

Commit 9867153

Browse files
Merge pull request from GHSA-qxmr-qxh6-2cc9
Fix ReDos vulnerability on Spree::EmailValidator::EMAIL_REGEXP
2 parents 5de0fe5 + ff33a8b commit 9867153

File tree

4 files changed

+61
-8
lines changed

4 files changed

+61
-8
lines changed

core/lib/spree/core/validators/email.rb

+1-1
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ module Spree
1212
# end
1313
#
1414
class EmailValidator < ActiveModel::EachValidator
15-
EMAIL_REGEXP = /\A([^@\.]|[^@\.]([^@\s]*)[^@\.])@([^@\s]+\.)+[^@\s]+\z/
15+
EMAIL_REGEXP = URI::MailTo::EMAIL_REGEXP
1616

1717
def validate_each(record, attribute, value)
1818
unless EMAIL_REGEXP.match? value
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# frozen_string_literal: true
2+
3+
namespace :solidus do
4+
desc 'Prints orders with invalid email (after fix for GHSA-qxmr-qxh6-2cc9)'
5+
task check_orders_with_invalid_email: :environment do
6+
matches = Spree::Order.find_each.reduce([]) do |matches, order|
7+
order.email.nil? || Spree::EmailValidator::EMAIL_REGEXP.match?(order.email) ? matches : matches + [order]
8+
end
9+
if matches.any?
10+
puts 'Email / ID / Number'
11+
puts(matches.map do |order|
12+
"#{order.email} / #{order.id} / #{order.number}"
13+
end.join("\n"))
14+
else
15+
puts 'NO MATCHES'
16+
end
17+
end
18+
end

core/spec/lib/spree/core/validators/email_spec.rb

+4-7
Original file line numberDiff line numberDiff line change
@@ -24,30 +24,27 @@ class Tester
2424
let(:invalid_emails) {
2525
[
2626
'invalid [email protected]',
27-
28-
2927
'@email.com',
30-
3128
'invalidemailemail.com',
3229
3330
'invalid@[email protected]',
3431
'invalid.email@@email.com'
3532
]
3633
}
3734

38-
it 'validates valid email addresses' do
35+
it 'validates valid email addresses', :aggregate_failures do
3936
tester = Tester.new
4037
valid_emails.each do |email|
4138
tester.email_address = email
42-
expect(tester.valid?).to be true
39+
expect(tester.valid?).to be(true), "expected #{email} to be valid"
4340
end
4441
end
4542

46-
it 'validates invalid email addresses' do
43+
it 'validates invalid email addresses', :aggregate_failures do
4744
tester = Tester.new
4845
invalid_emails.each do |email|
4946
tester.email_address = email
50-
expect(tester.valid?).to be false
47+
expect(tester.valid?).to be(false), "expected #{email} not to be valid"
5148
end
5249
end
5350
end
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
# frozen_string_literal: true
2+
3+
require 'rails_helper'
4+
5+
path = Spree::Core::Engine.root.join('lib/tasks/solidus/check_orders_with_invalid_email.rake')
6+
7+
RSpec.describe 'solidus' do
8+
describe 'check_orders_with_invalid_email' do
9+
include_context(
10+
'rake',
11+
task_path: path,
12+
task_name: 'solidus:check_orders_with_invalid_email'
13+
)
14+
15+
it 'includes orders with invalid email' do
16+
order = create(:order)
17+
order.update_column(:email, 'invalid [email protected]')
18+
19+
expect { task.invoke }.to output(/invalid [email protected] \/ #{order.id} \/ #{order.number}\n/).to_stdout
20+
end
21+
22+
it "doesn't include orders with valid email" do
23+
order = create(:order, email: '[email protected]')
24+
25+
expect { task.invoke }.not_to output(/[email protected]/).to_stdout
26+
end
27+
28+
it "doesn't include orders with no email" do
29+
order = create(:order, user: nil, email: nil, number: '123')
30+
31+
expect { task.invoke }.not_to output(/#{order.number}/).to_stdout
32+
end
33+
34+
it "prints message when no matches found" do
35+
expect { task.invoke }.to output(/NO MATCHES/).to_stdout
36+
end
37+
end
38+
end

0 commit comments

Comments
 (0)