Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/spec
diff options
context:
space:
mode:
authorGitLab Bot <gitlab-bot@gitlab.com>2022-01-11 12:14:09 +0300
committerGitLab Bot <gitlab-bot@gitlab.com>2022-01-11 12:14:09 +0300
commit1b5a83917d2ee58d168745fd5ca516a772316ce7 (patch)
tree67c09c6102241da102423fd984e6213bbcd1a01c /spec
parentf31ef3fd5548f9ffd5740b6aaca8672c27e34b42 (diff)
Add latest changes from gitlab-org/gitlab@master
Diffstat (limited to 'spec')
-rw-r--r--spec/lib/gitlab/background_migration/fix_vulnerability_occurrences_with_hashes_as_raw_metadata_spec.rb232
1 files changed, 232 insertions, 0 deletions
diff --git a/spec/lib/gitlab/background_migration/fix_vulnerability_occurrences_with_hashes_as_raw_metadata_spec.rb b/spec/lib/gitlab/background_migration/fix_vulnerability_occurrences_with_hashes_as_raw_metadata_spec.rb
new file mode 100644
index 00000000000..af551861d47
--- /dev/null
+++ b/spec/lib/gitlab/background_migration/fix_vulnerability_occurrences_with_hashes_as_raw_metadata_spec.rb
@@ -0,0 +1,232 @@
+# frozen_string_literal: true
+
+require 'spec_helper'
+
+RSpec.describe Gitlab::BackgroundMigration::FixVulnerabilityOccurrencesWithHashesAsRawMetadata, schema: 20211209203821 do
+ let(:users) { table(:users) }
+ let(:namespaces) { table(:namespaces) }
+ let(:projects) { table(:projects) }
+ let(:scanners) { table(:vulnerability_scanners) }
+ let(:identifiers) { table(:vulnerability_identifiers) }
+ let(:findings) { table(:vulnerability_occurrences) }
+
+ let(:user) { users.create!(name: 'Test User', projects_limit: 10, username: 'test-user', email: '1') }
+
+ let(:namespace) do
+ namespaces.create!(
+ owner_id: user.id,
+ name: user.name,
+ path: user.username
+ )
+ end
+
+ let(:project) do
+ projects.create!(namespace_id: namespace.id, name: 'Test Project')
+ end
+
+ let(:scanner) do
+ scanners.create!(
+ project_id: project.id,
+ external_id: 'test-scanner',
+ name: 'Test Scanner',
+ vendor: 'GitLab'
+ )
+ end
+
+ let(:primary_identifier) do
+ identifiers.create!(
+ project_id: project.id,
+ external_type: 'cve',
+ name: 'CVE-2021-1234',
+ external_id: 'CVE-2021-1234',
+ fingerprint: '4c0fe491999f94701ee437588554ef56322ae276'
+ )
+ end
+
+ let(:finding) do
+ findings.create!(
+ raw_metadata: raw_metadata,
+ project_id: project.id,
+ scanner_id: scanner.id,
+ primary_identifier_id: primary_identifier.id,
+ uuid: '4deb090a-bedf-5ccc-aa9a-ac8055a1ea81',
+ project_fingerprint: '1caa750a6dad769a18ad6f40b413b3b6ab1c8d77',
+ location_fingerprint: '6d1f35f53b065238abfcadc01336ce65d112a2bd',
+ name: 'name',
+ report_type: 7,
+ severity: 0,
+ confidence: 0,
+ detection_method: 'gitlab_security_report',
+ metadata_version: 'cluster_image_scanning:1.0',
+ created_at: "2021-12-10 14:27:42 -0600",
+ updated_at: "2021-12-10 14:27:42 -0600"
+ )
+ end
+
+ subject(:perform) { described_class.new.perform(finding.id, finding.id) }
+
+ context 'with stringified hash as raw_metadata' do
+ let(:raw_metadata) do
+ '{:location=>{"image"=>"index.docker.io/library/nginx:latest", "kubernetes_resource"=>{"namespace"=>"production", "kind"=>"deployment", "name"=>"nginx", "container_name"=>"nginx", "agent_id"=>"2"}, "dependency"=>{"package"=>{"name"=>"libc"}, "version"=>"v1.2.3"}}}'
+ end
+
+ it 'converts stringified hash to JSON' do
+ expect { perform }.not_to raise_error
+
+ result = finding.reload.raw_metadata
+ metadata = Oj.load(result)
+ expect(metadata).to eq(
+ {
+ 'location' => {
+ 'image' => 'index.docker.io/library/nginx:latest',
+ 'kubernetes_resource' => {
+ 'namespace' => 'production',
+ 'kind' => 'deployment',
+ 'name' => 'nginx',
+ 'container_name' => 'nginx',
+ 'agent_id' => '2'
+ },
+ 'dependency' => {
+ 'package' => { 'name' => 'libc' },
+ 'version' => 'v1.2.3'
+ }
+ }
+ }
+ )
+ end
+ end
+
+ context 'with valid raw_metadata' do
+ where(:raw_metadata) do
+ [
+ '{}',
+ '{"location":null}',
+ '{"location":{"image":"index.docker.io/library/nginx:latest","kubernetes_resource":{"namespace":"production","kind":"deployment","name":"nginx","container_name":"nginx","agent_id":"2"},"dependency":{"package":{"name":"libc"},"version":"v1.2.3"}}}'
+ ]
+ end
+
+ with_them do
+ it 'does not change the raw_metadata' do
+ expect { perform }.not_to raise_error
+
+ result = finding.reload.raw_metadata
+ expect(result).to eq(raw_metadata)
+ end
+ end
+ end
+
+ context 'when raw_metadata contains forbidden types' do
+ using RSpec::Parameterized::TableSyntax
+
+ where(:raw_metadata, :type) do
+ 'def foo; "bar"; end' | :def
+ '`cat somefile`' | :xstr
+ 'exec("cat /etc/passwd")' | :send
+ end
+
+ with_them do
+ it 'does not change the raw_metadata' do
+ expect(Gitlab::AppLogger).to receive(:error).with(message: "expected raw_metadata to be a hash", type: type)
+
+ expect { perform }.not_to raise_error
+
+ result = finding.reload.raw_metadata
+ expect(result).to eq(raw_metadata)
+ end
+ end
+ end
+
+ context 'when forbidden types are nested inside a hash' do
+ using RSpec::Parameterized::TableSyntax
+
+ where(:raw_metadata, :type) do
+ '{:location=>Env.fetch("SOME_VAR")}' | :send
+ '{:location=>{:image=>Env.fetch("SOME_VAR")}}' | :send
+ # rubocop:disable Lint/InterpolationCheck
+ '{"key"=>"value: #{send}"}' | :dstr
+ # rubocop:enable Lint/InterpolationCheck
+ end
+
+ with_them do
+ it 'does not change the raw_metadata' do
+ expect(Gitlab::AppLogger).to receive(:error).with(
+ message: "error parsing raw_metadata",
+ error: "value of a pair was an unexpected type",
+ type: type
+ )
+
+ expect { perform }.not_to raise_error
+
+ result = finding.reload.raw_metadata
+ expect(result).to eq(raw_metadata)
+ end
+ end
+ end
+
+ context 'when key is an unexpected type' do
+ let(:raw_metadata) { "{nil=>nil}" }
+
+ it 'logs error' do
+ expect(Gitlab::AppLogger).to receive(:error).with(
+ message: "error parsing raw_metadata",
+ error: "expected key to be either symbol, string, or integer",
+ type: :nil
+ )
+
+ expect { perform }.not_to raise_error
+ end
+ end
+
+ context 'when raw_metadata cannot be parsed' do
+ let(:raw_metadata) { "{" }
+
+ it 'logs error' do
+ expect(Gitlab::AppLogger).to receive(:error).with(message: "error parsing raw_metadata", error: "unexpected token $end")
+
+ expect { perform }.not_to raise_error
+ end
+ end
+
+ describe '#hash_from_s' do
+ subject { described_class.new.hash_from_s(input) }
+
+ context 'with valid input' do
+ let(:input) { '{:location=>{"image"=>"index.docker.io/library/nginx:latest", "kubernetes_resource"=>{"namespace"=>"production", "kind"=>"deployment", "name"=>"nginx", "container_name"=>"nginx", "agent_id"=>2}, "dependency"=>{"package"=>{"name"=>"libc"}, "version"=>"v1.2.3"}}}' }
+
+ it 'converts string to a hash' do
+ expect(subject).to eq({
+ location: {
+ 'image' => 'index.docker.io/library/nginx:latest',
+ 'kubernetes_resource' => {
+ 'namespace' => 'production',
+ 'kind' => 'deployment',
+ 'name' => 'nginx',
+ 'container_name' => 'nginx',
+ 'agent_id' => 2
+ },
+ 'dependency' => {
+ 'package' => { 'name' => 'libc' },
+ 'version' => 'v1.2.3'
+ }
+ }
+ })
+ end
+ end
+
+ using RSpec::Parameterized::TableSyntax
+
+ where(:input, :expected) do
+ '{}' | {}
+ '{"bool"=>true}' | { 'bool' => true }
+ '{"bool"=>false}' | { 'bool' => false }
+ '{"nil"=>nil}' | { 'nil' => nil }
+ '{"array"=>[1, "foo", nil]}' | { 'array' => [1, "foo", nil] }
+ '{foo: :bar}' | { foo: :bar }
+ '{foo: {bar: "bin"}}' | { foo: { bar: "bin" } }
+ end
+
+ with_them do
+ specify { expect(subject).to eq(expected) }
+ end
+ end
+end