diff options
-rw-r--r-- | app/assets/javascripts/notebook/cells/markdown.vue | 1 | ||||
-rw-r--r-- | lib/gitlab/x509/signature.rb | 10 | ||||
-rw-r--r-- | spec/frontend/notebook/cells/markdown_spec.js | 13 | ||||
-rw-r--r-- | spec/lib/gitlab/x509/signature_spec.rb | 77 | ||||
-rw-r--r-- | spec/tasks/gitlab/x509/update_rake_spec.rb | 20 |
5 files changed, 66 insertions, 55 deletions
diff --git a/app/assets/javascripts/notebook/cells/markdown.vue b/app/assets/javascripts/notebook/cells/markdown.vue index 9bf26e5a182..a7fcce02ab3 100644 --- a/app/assets/javascripts/notebook/cells/markdown.vue +++ b/app/assets/javascripts/notebook/cells/markdown.vue @@ -195,6 +195,7 @@ export default { 'var', ], ALLOWED_ATTR: ['class', 'style', 'href', 'src'], + ALLOW_DATA_ATTR: false, }); }, }, diff --git a/lib/gitlab/x509/signature.rb b/lib/gitlab/x509/signature.rb index c83213e973b..a6761e211fa 100644 --- a/lib/gitlab/x509/signature.rb +++ b/lib/gitlab/x509/signature.rb @@ -23,7 +23,7 @@ module Gitlab end def user - User.find_by_any_email(@email) + strong_memoize(:user) { User.find_by_any_email(@email) } end def verified_signature @@ -31,9 +31,13 @@ module Gitlab end def verification_status - return :unverified if x509_certificate.nil? || x509_certificate.revoked? + return :unverified if + x509_certificate.nil? || + x509_certificate.revoked? || + !verified_signature || + user.nil? - if verified_signature && certificate_email == @email + if user.verified_emails.include?(@email) && certificate_email == @email :verified else :unverified diff --git a/spec/frontend/notebook/cells/markdown_spec.js b/spec/frontend/notebook/cells/markdown_spec.js index d250ffed1a9..deeee5d6589 100644 --- a/spec/frontend/notebook/cells/markdown_spec.js +++ b/spec/frontend/notebook/cells/markdown_spec.js @@ -39,7 +39,7 @@ describe('Markdown component', () => { expect(vm.$el.querySelector('.markdown h1')).not.toBeNull(); }); - it('sanitizes output', async () => { + it('sanitizes Markdown output', async () => { Object.assign(cell, { source: [ '[XSS](data:text/html;base64,PHNjcmlwdD5hbGVydChkb2N1bWVudC5kb21haW4pPC9zY3JpcHQ+Cg==)\n', @@ -50,6 +50,17 @@ describe('Markdown component', () => { expect(vm.$el.querySelector('a').getAttribute('href')).toBeNull(); }); + it('sanitizes HTML', async () => { + const findLink = () => vm.$el.querySelector('.xss-link'); + Object.assign(cell, { + source: ['<a href="test.js" data-remote=true data-type="script" class="xss-link">XSS</a>\n'], + }); + + await vm.$nextTick(); + expect(findLink().getAttribute('data-remote')).toBe(null); + expect(findLink().getAttribute('data-type')).toBe(null); + }); + describe('tables', () => { beforeEach(() => { json = getJSONFixture('blob/notebook/markdown-table.json'); diff --git a/spec/lib/gitlab/x509/signature_spec.rb b/spec/lib/gitlab/x509/signature_spec.rb index 2ac9c1f3a3b..7ba15faf910 100644 --- a/spec/lib/gitlab/x509/signature_spec.rb +++ b/spec/lib/gitlab/x509/signature_spec.rb @@ -12,20 +12,30 @@ RSpec.describe Gitlab::X509::Signature do end shared_examples "a verified signature" do - it 'returns a verified signature if email does match' do - signature = described_class.new( + let_it_be(:user) { create(:user, email: X509Helpers::User1.certificate_email) } + + subject(:signature) do + described_class.new( X509Helpers::User1.signed_commit_signature, X509Helpers::User1.signed_commit_base_data, X509Helpers::User1.certificate_email, X509Helpers::User1.signed_commit_time ) + end + it 'returns a verified signature if email does match' do expect(signature.x509_certificate).to have_attributes(certificate_attributes) expect(signature.x509_certificate.x509_issuer).to have_attributes(issuer_attributes) expect(signature.verified_signature).to be_truthy expect(signature.verification_status).to eq(:verified) end + it "returns an unverified signature if the email matches but isn't confirmed" do + user.update!(confirmed_at: nil) + + expect(signature.verification_status).to eq(:unverified) + end + it 'returns an unverified signature if email does not match' do signature = described_class.new( X509Helpers::User1.signed_commit_signature, @@ -55,13 +65,6 @@ RSpec.describe Gitlab::X509::Signature do end it 'returns an unverified signature if certificate is revoked' do - signature = described_class.new( - X509Helpers::User1.signed_commit_signature, - X509Helpers::User1.signed_commit_base_data, - X509Helpers::User1.certificate_email, - X509Helpers::User1.signed_commit_time - ) - expect(signature.verification_status).to eq(:verified) signature.x509_certificate.revoked! @@ -253,23 +256,25 @@ RSpec.describe Gitlab::X509::Signature do end describe '#user' do - signature = described_class.new( - X509Helpers::User1.signed_tag_signature, - X509Helpers::User1.signed_tag_base_data, - X509Helpers::User1.certificate_email, - X509Helpers::User1.signed_commit_time - ) + subject do + described_class.new( + X509Helpers::User1.signed_tag_signature, + X509Helpers::User1.signed_tag_base_data, + X509Helpers::User1.certificate_email, + X509Helpers::User1.signed_commit_time + ).user + end context 'if email is assigned to a user' do let!(:user) { create(:user, email: X509Helpers::User1.certificate_email) } it 'returns user' do - expect(signature.user).to eq(user) + is_expected.to eq(user) end end it 'if email is not assigned to a user, return nil' do - expect(signature.user).to be_nil + is_expected.to be_nil end end @@ -292,6 +297,17 @@ RSpec.describe Gitlab::X509::Signature do end context 'verified signature' do + let_it_be(:user) { create(:user, email: X509Helpers::User1.certificate_email) } + + subject(:signature) do + described_class.new( + X509Helpers::User1.signed_tag_signature, + X509Helpers::User1.signed_tag_base_data, + X509Helpers::User1.certificate_email, + X509Helpers::User1.signed_commit_time + ) + end + context 'with trusted certificate store' do before do store = OpenSSL::X509::Store.new @@ -301,19 +317,18 @@ RSpec.describe Gitlab::X509::Signature do end it 'returns a verified signature if email does match' do - signature = described_class.new( - X509Helpers::User1.signed_tag_signature, - X509Helpers::User1.signed_tag_base_data, - X509Helpers::User1.certificate_email, - X509Helpers::User1.signed_commit_time - ) - expect(signature.x509_certificate).to have_attributes(certificate_attributes) expect(signature.x509_certificate.x509_issuer).to have_attributes(issuer_attributes) expect(signature.verified_signature).to be_truthy expect(signature.verification_status).to eq(:verified) end + it "returns an unverified signature if the email matches but isn't confirmed" do + user.update!(confirmed_at: nil) + + expect(signature.verification_status).to eq(:unverified) + end + it 'returns an unverified signature if email does not match' do signature = described_class.new( X509Helpers::User1.signed_tag_signature, @@ -343,13 +358,6 @@ RSpec.describe Gitlab::X509::Signature do end it 'returns an unverified signature if certificate is revoked' do - signature = described_class.new( - X509Helpers::User1.signed_tag_signature, - X509Helpers::User1.signed_tag_base_data, - X509Helpers::User1.certificate_email, - X509Helpers::User1.signed_commit_time - ) - expect(signature.verification_status).to eq(:verified) signature.x509_certificate.revoked! @@ -368,13 +376,6 @@ RSpec.describe Gitlab::X509::Signature do end it 'returns an unverified signature' do - signature = described_class.new( - X509Helpers::User1.signed_tag_signature, - X509Helpers::User1.signed_tag_base_data, - X509Helpers::User1.certificate_email, - X509Helpers::User1.signed_commit_time - ) - expect(signature.x509_certificate).to have_attributes(certificate_attributes) expect(signature.x509_certificate.x509_issuer).to have_attributes(issuer_attributes) expect(signature.verified_signature).to be_falsey diff --git a/spec/tasks/gitlab/x509/update_rake_spec.rb b/spec/tasks/gitlab/x509/update_rake_spec.rb index 93e97ab38ad..b166e73935a 100644 --- a/spec/tasks/gitlab/x509/update_rake_spec.rb +++ b/spec/tasks/gitlab/x509/update_rake_spec.rb @@ -8,12 +8,13 @@ RSpec.describe 'gitlab:x509 namespace rake task' do end describe 'update_signatures' do - subject { run_rake_task('gitlab:x509:update_signatures') } - - let(:project) { create :project, :repository, path: X509Helpers::User1.path } + let(:user) { create(:user, email: X509Helpers::User1.certificate_email) } + let(:project) { create(:project, :repository, path: X509Helpers::User1.path, creator: user) } let(:x509_signed_commit) { project.commit_by(oid: '189a6c924013fc3fe40d6f1ec1dc20214183bc97') } let(:x509_commit) { Gitlab::X509::Commit.new(x509_signed_commit).signature } + subject { run_rake_task('gitlab:x509:update_signatures') } + it 'changes from unverified to verified if the certificate store contains the root certificate' do x509_commit @@ -22,21 +23,14 @@ RSpec.describe 'gitlab:x509 namespace rake task' do store.add_cert(certificate) allow(OpenSSL::X509::Store).to receive(:new).and_return(store) - expect(x509_commit.verification_status).to eq('unverified') expect_any_instance_of(Gitlab::X509::Commit).to receive(:update_signature!).and_call_original - - subject - - x509_commit.reload - expect(x509_commit.verification_status).to eq('verified') + expect { subject }.to change { x509_commit.reload.verification_status }.from('unverified').to('verified') end it 'returns if no signature is available' do - expect_any_instance_of(Gitlab::X509::Commit) do |x509_commit| - expect(x509_commit).not_to receive(:update_signature!) + expect_any_instance_of(Gitlab::X509::Commit).not_to receive(:update_signature!) - subject - end + subject end end end |