From e4eb44b24fb62a04b7309a296ffd5813ea55bf48 Mon Sep 17 00:00:00 2001 From: Sean McGivern Date: Fri, 9 Jun 2017 12:48:25 +0100 Subject: Add table for files in merge request diffs --- app/models/merge_request_diff.rb | 38 ++++++++++++++++----- app/models/merge_request_diff_file.rb | 21 ++++++++++++ ...170608171156_create_merge_request_diff_files.rb | 31 +++++++++++++++++ db/schema.rb | 19 ++++++++++- doc/user/project/settings/import_export.md | 17 ++++----- lib/gitlab/git/diff.rb | 5 ++- lib/gitlab/import_export.rb | 2 +- lib/gitlab/import_export/import_export.yml | 7 +++- lib/gitlab/import_export/json_hash_builder.rb | 4 ++- lib/gitlab/import_export/relation_factory.rb | 5 +++ .../import_export/test_project_export.tar.gz | Bin 681478 -> 681481 bytes spec/lib/gitlab/git/diff_spec.rb | 2 +- spec/lib/gitlab/import_export/all_models.yml | 3 ++ spec/lib/gitlab/import_export/project.json | 38 +++++++++++++++------ .../import_export/project_tree_restorer_spec.rb | 7 +++- .../import_export/project_tree_saver_spec.rb | 10 ++++++ .../gitlab/import_export/safe_model_attributes.yml | 11 ++++++ spec/models/merge_request_diff_file_spec.rb | 8 +++++ spec/models/merge_request_diff_spec.rb | 7 ++-- 19 files changed, 197 insertions(+), 38 deletions(-) create mode 100644 app/models/merge_request_diff_file.rb create mode 100644 db/migrate/20170608171156_create_merge_request_diff_files.rb create mode 100644 spec/models/merge_request_diff_file_spec.rb diff --git a/app/models/merge_request_diff.rb b/app/models/merge_request_diff.rb index 99dd2130188..4eada439977 100644 --- a/app/models/merge_request_diff.rb +++ b/app/models/merge_request_diff.rb @@ -10,6 +10,7 @@ class MergeRequestDiff < ActiveRecord::Base VALID_CLASSES = [Hash, Rugged::Patch, Rugged::Diff::Delta].freeze belongs_to :merge_request + has_many :merge_request_diff_files, -> { order(:merge_request_diff_id, :relative_order) } serialize :st_commits # rubocop:disable Cop/ActiverecordSerialize serialize :st_diffs # rubocop:disable Cop/ActiverecordSerialize @@ -91,7 +92,7 @@ class MergeRequestDiff < ActiveRecord::Base head_commit_sha).diffs(options) else @raw_diffs ||= {} - @raw_diffs[options] ||= load_diffs(st_diffs, options) + @raw_diffs[options] ||= load_diffs(options) end end @@ -253,14 +254,34 @@ class MergeRequestDiff < ActiveRecord::Base update_columns_serialized(new_attributes) end - def dump_diffs(diffs) - if diffs.respond_to?(:map) - diffs.map(&:to_hash) + def create_merge_request_diff_files(diffs) + tuples = diffs.map.with_index do |diff, index| + MergeRequestDiffFile.keys.map do |key| + self.class.connection.quote(diff.public_send(key)) + end.unshift(index).unshift(self.id) end + + columns = [:merge_request_diff_id, :relative_order] + MergeRequestDiffFile.keys + + columns = columns.map do |column| + self.class.connection.quote_column_name(column) + end + + self.class.connection.execute <<-EOF.strip_heredoc + INSERT INTO merge_request_diff_files (#{columns.join(', ')}) + VALUES #{tuples.map { |tuple| "(#{tuple.join(', ')})" }.join(', ')} + EOF end - def load_diffs(raw, options) - if valid_raw_diff?(raw) + def load_diffs(options) + raw = + if st_diffs.present? && valid_raw_diff?(st_diffs) + st_diffs + elsif merge_request_diff_files.present? + merge_request_diff_files.map(&:to_hash) + end + + if raw if paths = options[:paths] raw = raw.select do |diff| paths.include?(diff[:old_path]) || paths.include?(diff[:new_path]) @@ -285,11 +306,10 @@ class MergeRequestDiff < ActiveRecord::Base new_attributes[:real_size] = diff_collection.real_size if diff_collection.any? - new_diffs = dump_diffs(diff_collection) new_attributes[:state] = :collected - end - new_attributes[:st_diffs] = new_diffs || [] + create_merge_request_diff_files(diff_collection) + end # Set our state to 'overflow' to make the #empty? and #collected? # methods (generated by StateMachine) return false. diff --git a/app/models/merge_request_diff_file.rb b/app/models/merge_request_diff_file.rb new file mode 100644 index 00000000000..0df76100174 --- /dev/null +++ b/app/models/merge_request_diff_file.rb @@ -0,0 +1,21 @@ +class MergeRequestDiffFile < ActiveRecord::Base + include Gitlab::EncodingHelper + + belongs_to :merge_request_diff + + def self.keys + @keys ||= column_names.map(&:to_sym) - [:merge_request_diff_id, :relative_order] + end + + def to_hash + self.class.keys.each_with_object({}) do |key, hash| + hash[key] = public_send(key) + end + end + + def utf8_diff + return '' if diff.blank? + + encode_utf8(diff) if diff.respond_to?(:encoding) + end +end diff --git a/db/migrate/20170608171156_create_merge_request_diff_files.rb b/db/migrate/20170608171156_create_merge_request_diff_files.rb new file mode 100644 index 00000000000..afe42fc96d4 --- /dev/null +++ b/db/migrate/20170608171156_create_merge_request_diff_files.rb @@ -0,0 +1,31 @@ +class CreateMergeRequestDiffFiles < ActiveRecord::Migration + include Gitlab::Database::MigrationHelpers + + DOWNTIME = false + + disable_ddl_transaction! + + def up + create_table :merge_request_diff_files, id: false do |t| + t.integer :merge_request_diff_id, null: false + t.integer :relative_order, null: false + t.boolean :new_file, null: false + t.boolean :renamed_file, null: false + t.boolean :deleted_file, null: false + t.boolean :too_large, null: false + t.string :new_path, null: false + t.string :old_path, null: false + t.string :a_mode, null: false + t.string :b_mode, null: false + t.text :diff, null: false + end + + add_index :merge_request_diff_files, [:merge_request_diff_id, :relative_order], name: 'index_merge_request_diff_files_on_mr_diff_id_and_order' + + add_concurrent_foreign_key :merge_request_diff_files, :merge_request_diffs, column: :merge_request_diff_id, on_delete: :cascade + end + + def down + drop_table :merge_request_diff_files + end +end diff --git a/db/schema.rb b/db/schema.rb index b93630a410d..ea336d7d8ec 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -11,7 +11,7 @@ # # It's strongly recommended that you check this file into your version control system. -ActiveRecord::Schema.define(version: 20170606202615) do +ActiveRecord::Schema.define(version: 20170608171156) do # These are extensions that must be enabled in order to support this database enable_extension "plpgsql" enable_extension "pg_trgm" @@ -690,6 +690,22 @@ ActiveRecord::Schema.define(version: 20170606202615) do add_index "members", ["source_id", "source_type"], name: "index_members_on_source_id_and_source_type", using: :btree add_index "members", ["user_id"], name: "index_members_on_user_id", using: :btree + create_table "merge_request_diff_files", id: false, force: :cascade do |t| + t.integer "merge_request_diff_id", null: false + t.integer "relative_order", null: false + t.boolean "new_file", null: false + t.boolean "renamed_file", null: false + t.boolean "deleted_file", null: false + t.boolean "too_large", null: false + t.string "new_path", null: false + t.string "old_path", null: false + t.string "a_mode", null: false + t.string "b_mode", null: false + t.text "diff", null: false + end + + add_index "merge_request_diff_files", ["merge_request_diff_id", "relative_order"], name: "index_merge_request_diff_files_on_mr_diff_id_and_order", using: :btree + create_table "merge_request_diffs", force: :cascade do |t| t.string "state" t.text "st_commits" @@ -1517,6 +1533,7 @@ ActiveRecord::Schema.define(version: 20170606202615) do add_foreign_key "labels", "namespaces", column: "group_id", on_delete: :cascade add_foreign_key "lists", "boards" add_foreign_key "lists", "labels" + add_foreign_key "merge_request_diff_files", "merge_request_diffs", name: "fk_501aa0a391", on_delete: :cascade add_foreign_key "merge_request_metrics", "ci_pipelines", column: "pipeline_id", on_delete: :cascade add_foreign_key "merge_request_metrics", "merge_requests", on_delete: :cascade add_foreign_key "merge_requests_closing_issues", "issues", on_delete: :cascade diff --git a/doc/user/project/settings/import_export.md b/doc/user/project/settings/import_export.md index 58d2fd76c61..35960ade3d4 100644 --- a/doc/user/project/settings/import_export.md +++ b/doc/user/project/settings/import_export.md @@ -27,14 +27,15 @@ with all their related data and be moved into a new GitLab instance. | GitLab version | Import/Export version | | -------- | -------- | -| 9.2.0 to current | 0.1.7 | -| 8.17.0 | 0.1.6 | -| 8.13.0 | 0.1.5 | -| 8.12.0 | 0.1.4 | -| 8.10.3 | 0.1.3 | -| 8.10.0 | 0.1.2 | -| 8.9.5 | 0.1.1 | -| 8.9.0 | 0.1.0 | +| 9.4.0 to current | 0.1.8 | +| 9.2.0 | 0.1.7 | +| 8.17.0 | 0.1.6 | +| 8.13.0 | 0.1.5 | +| 8.12.0 | 0.1.4 | +| 8.10.3 | 0.1.3 | +| 8.10.0 | 0.1.2 | +| 8.9.5 | 0.1.1 | +| 8.9.0 | 0.1.0 | > The table reflects what GitLab version we updated the Import/Export version at. > For instance, 8.10.3 and 8.11 will have the same Import/Export version (0.1.3) diff --git a/lib/gitlab/git/diff.rb b/lib/gitlab/git/diff.rb index 88ad760bea3..74e93093ad2 100644 --- a/lib/gitlab/git/diff.rb +++ b/lib/gitlab/git/diff.rb @@ -16,9 +16,7 @@ module Gitlab alias_method :renamed_file?, :renamed_file attr_accessor :expanded - - # We need this accessor because of `to_hash` and `init_from_hash` - attr_accessor :too_large + attr_writer :too_large class << self # The maximum size of a diff to display. @@ -264,6 +262,7 @@ module Gitlab @too_large end end + alias_method :too_large, :too_large? def too_large! @diff = '' diff --git a/lib/gitlab/import_export.rb b/lib/gitlab/import_export.rb index 27d5a9198b6..3470a09eaf0 100644 --- a/lib/gitlab/import_export.rb +++ b/lib/gitlab/import_export.rb @@ -3,7 +3,7 @@ module Gitlab extend self # For every version update, the version history in import_export.md has to be kept up to date. - VERSION = '0.1.7'.freeze + VERSION = '0.1.8'.freeze FILENAME_LIMIT = 50 def export_path(relative_path:) diff --git a/lib/gitlab/import_export/import_export.yml b/lib/gitlab/import_export/import_export.yml index ff2b1d08c3c..72183e8aad4 100644 --- a/lib/gitlab/import_export/import_export.yml +++ b/lib/gitlab/import_export/import_export.yml @@ -26,7 +26,8 @@ project_tree: - notes: - :author - :events - - :merge_request_diff + - merge_request_diff: + - :merge_request_diff_files - :events - :timelogs - label_links: @@ -92,6 +93,8 @@ excluded_attributes: - :expired_at merge_request_diff: - :st_diffs + merge_request_diff_files: + - :diff issues: - :milestone_id merge_requests: @@ -113,6 +116,8 @@ methods: - :type merge_request_diff: - :utf8_st_diffs + merge_request_diff_files: + - :utf8_diff merge_requests: - :diff_head_sha project: diff --git a/lib/gitlab/import_export/json_hash_builder.rb b/lib/gitlab/import_export/json_hash_builder.rb index 48c09dafcb6..b48f63bcd7e 100644 --- a/lib/gitlab/import_export/json_hash_builder.rb +++ b/lib/gitlab/import_export/json_hash_builder.rb @@ -83,7 +83,9 @@ module Gitlab # +value+ existing model to be included in the hash # +json_config_hash+ the original hash containing the root model def add_model_value(current_key, value, json_config_hash) - @attributes_finder.parse(value) { |hash| value = { value => hash } } + @attributes_finder.parse(value) do |hash| + value = { value => hash } unless value.is_a?(Hash) + end add_to_array(current_key, json_config_hash, value) end diff --git a/lib/gitlab/import_export/relation_factory.rb b/lib/gitlab/import_export/relation_factory.rb index 695852526cb..20580459046 100644 --- a/lib/gitlab/import_export/relation_factory.rb +++ b/lib/gitlab/import_export/relation_factory.rb @@ -71,6 +71,7 @@ module Gitlab @relation_hash['data'].deep_symbolize_keys! if @relation_name == :events && @relation_hash['data'] set_st_diff_commits if @relation_name == :merge_request_diff + set_diff if @relation_name == :merge_request_diff_files end def update_user_references @@ -202,6 +203,10 @@ module Gitlab HashUtil.deep_symbolize_array_with_date!(@relation_hash['st_commits']) end + def set_diff + @relation_hash['diff'] = @relation_hash.delete('utf8_diff') + end + def existing_or_new_object # Only find existing records to avoid mapping tables such as milestones # Otherwise always create the record, skipping the extra SELECT clause. diff --git a/spec/features/projects/import_export/test_project_export.tar.gz b/spec/features/projects/import_export/test_project_export.tar.gz index 4efd5a26a82..e03e7b88174 100644 Binary files a/spec/features/projects/import_export/test_project_export.tar.gz and b/spec/features/projects/import_export/test_project_export.tar.gz differ diff --git a/spec/lib/gitlab/git/diff_spec.rb b/spec/lib/gitlab/git/diff_spec.rb index da213f617cc..78d741f0110 100644 --- a/spec/lib/gitlab/git/diff_spec.rb +++ b/spec/lib/gitlab/git/diff_spec.rb @@ -90,7 +90,7 @@ EOT let(:diff) { described_class.new(@rugged_diff) } it 'initializes the diff' do - expect(diff.to_hash).to eq(@raw_diff_hash.merge(too_large: nil)) + expect(diff.to_hash).to eq(@raw_diff_hash) end it 'does not prune the diff' do diff --git a/spec/lib/gitlab/import_export/all_models.yml b/spec/lib/gitlab/import_export/all_models.yml index 412eb33b35b..a5f09f1856e 100644 --- a/spec/lib/gitlab/import_export/all_models.yml +++ b/spec/lib/gitlab/import_export/all_models.yml @@ -88,6 +88,9 @@ merge_requests: - head_pipeline merge_request_diff: - merge_request +- merge_request_diff_files +merge_request_diff_files: +- merge_request_diff pipelines: - project - user diff --git a/spec/lib/gitlab/import_export/project.json b/spec/lib/gitlab/import_export/project.json index e3599d6fe59..98c117b4cd8 100644 --- a/spec/lib/gitlab/import_export/project.json +++ b/spec/lib/gitlab/import_export/project.json @@ -2821,9 +2821,11 @@ "committer_email": "dmitriy.zaporozhets@gmail.com" } ], - "utf8_st_diffs": [ + "merge_request_diff_files": [ { - "diff": "Binary files a/.DS_Store and /dev/null differ\n", + "merge_request_diff_id": 27, + "relative_order": 0, + "utf8_diff": "Binary files a/.DS_Store and /dev/null differ\n", "new_path": ".DS_Store", "old_path": ".DS_Store", "a_mode": "100644", @@ -2834,7 +2836,9 @@ "too_large": false }, { - "diff": "--- a/.gitignore\n+++ b/.gitignore\n@@ -17,3 +17,4 @@ rerun.txt\n pickle-email-*.html\n .project\n config/initializers/secret_token.rb\n+.DS_Store\n", + "merge_request_diff_id": 27, + "relative_order": 1, + "utf8_diff": "--- a/.gitignore\n+++ b/.gitignore\n@@ -17,3 +17,4 @@ rerun.txt\n pickle-email-*.html\n .project\n config/initializers/secret_token.rb\n+.DS_Store\n", "new_path": ".gitignore", "old_path": ".gitignore", "a_mode": "100644", @@ -2845,7 +2849,9 @@ "too_large": false }, { - "diff": "--- a/.gitmodules\n+++ b/.gitmodules\n@@ -1,3 +1,9 @@\n [submodule \"six\"]\n \tpath = six\n \turl = git://github.com/randx/six.git\n+[submodule \"gitlab-shell\"]\n+\tpath = gitlab-shell\n+\turl = https://github.com/gitlabhq/gitlab-shell.git\n+[submodule \"gitlab-grack\"]\n+\tpath = gitlab-grack\n+\turl = https://gitlab.com/gitlab-org/gitlab-grack.git\n", + "merge_request_diff_id": 27, + "relative_order": 2, + "utf8_diff": "--- a/.gitmodules\n+++ b/.gitmodules\n@@ -1,3 +1,9 @@\n [submodule \"six\"]\n \tpath = six\n \turl = git://github.com/randx/six.git\n+[submodule \"gitlab-shell\"]\n+\tpath = gitlab-shell\n+\turl = https://github.com/gitlabhq/gitlab-shell.git\n+[submodule \"gitlab-grack\"]\n+\tpath = gitlab-grack\n+\turl = https://gitlab.com/gitlab-org/gitlab-grack.git\n", "new_path": ".gitmodules", "old_path": ".gitmodules", "a_mode": "100644", @@ -2856,7 +2862,9 @@ "too_large": false }, { - "diff": "Binary files a/files/.DS_Store and /dev/null differ\n", + "merge_request_diff_id": 27, + "relative_order": 3, + "utf8_diff": "Binary files a/files/.DS_Store and /dev/null differ\n", "new_path": "files/.DS_Store", "old_path": "files/.DS_Store", "a_mode": "100644", @@ -2867,7 +2875,9 @@ "too_large": false }, { - "diff": "--- /dev/null\n+++ b/files/ruby/feature.rb\n@@ -0,0 +1,4 @@\n+# This file was changed in feature branch\n+# We put different code here to make merge conflict\n+class Conflict\n+end\n", + "merge_request_diff_id": 27, + "relative_order": 4, + "utf8_diff": "--- /dev/null\n+++ b/files/ruby/feature.rb\n@@ -0,0 +1,4 @@\n+# This file was changed in feature branch\n+# We put different code here to make merge conflict\n+class Conflict\n+end\n", "new_path": "files/ruby/feature.rb", "old_path": "files/ruby/feature.rb", "a_mode": "0", @@ -2878,7 +2888,9 @@ "too_large": false }, { - "diff": "--- a/files/ruby/popen.rb\n+++ b/files/ruby/popen.rb\n@@ -6,12 +6,18 @@ module Popen\n \n def popen(cmd, path=nil)\n unless cmd.is_a?(Array)\n- raise \"System commands must be given as an array of strings\"\n+ raise RuntimeError, \"System commands must be given as an array of strings\"\n end\n \n path ||= Dir.pwd\n- vars = { \"PWD\" =\u003e path }\n- options = { chdir: path }\n+\n+ vars = {\n+ \"PWD\" =\u003e path\n+ }\n+\n+ options = {\n+ chdir: path\n+ }\n \n unless File.directory?(path)\n FileUtils.mkdir_p(path)\n@@ -19,6 +25,7 @@ module Popen\n \n @cmd_output = \"\"\n @cmd_status = 0\n+\n Open3.popen3(vars, *cmd, options) do |stdin, stdout, stderr, wait_thr|\n @cmd_output \u003c\u003c stdout.read\n @cmd_output \u003c\u003c stderr.read\n", + "merge_request_diff_id": 27, + "relative_order": 5, + "utf8_diff": "--- a/files/ruby/popen.rb\n+++ b/files/ruby/popen.rb\n@@ -6,12 +6,18 @@ module Popen\n \n def popen(cmd, path=nil)\n unless cmd.is_a?(Array)\n- raise \"System commands must be given as an array of strings\"\n+ raise RuntimeError, \"System commands must be given as an array of strings\"\n end\n \n path ||= Dir.pwd\n- vars = { \"PWD\" =\u003e path }\n- options = { chdir: path }\n+\n+ vars = {\n+ \"PWD\" =\u003e path\n+ }\n+\n+ options = {\n+ chdir: path\n+ }\n \n unless File.directory?(path)\n FileUtils.mkdir_p(path)\n@@ -19,6 +25,7 @@ module Popen\n \n @cmd_output = \"\"\n @cmd_status = 0\n+\n Open3.popen3(vars, *cmd, options) do |stdin, stdout, stderr, wait_thr|\n @cmd_output \u003c\u003c stdout.read\n @cmd_output \u003c\u003c stderr.read\n", "new_path": "files/ruby/popen.rb", "old_path": "files/ruby/popen.rb", "a_mode": "100644", @@ -2889,7 +2901,9 @@ "too_large": false }, { - "diff": "--- a/files/ruby/regex.rb\n+++ b/files/ruby/regex.rb\n@@ -19,14 +19,12 @@ module Gitlab\n end\n \n def archive_formats_regex\n- #|zip|tar| tar.gz | tar.bz2 |\n- /(zip|tar|tar\\.gz|tgz|gz|tar\\.bz2|tbz|tbz2|tb2|bz2)/\n+ /(zip|tar|7z|tar\\.gz|tgz|gz|tar\\.bz2|tbz|tbz2|tb2|bz2)/\n end\n \n def git_reference_regex\n # Valid git ref regex, see:\n # https://www.kernel.org/pub/software/scm/git/docs/git-check-ref-format.html\n-\n %r{\n (?!\n (?# doesn't begins with)\n", + "merge_request_diff_id": 27, + "relative_order": 6, + "utf8_diff": "--- a/files/ruby/regex.rb\n+++ b/files/ruby/regex.rb\n@@ -19,14 +19,12 @@ module Gitlab\n end\n \n def archive_formats_regex\n- #|zip|tar| tar.gz | tar.bz2 |\n- /(zip|tar|tar\\.gz|tgz|gz|tar\\.bz2|tbz|tbz2|tb2|bz2)/\n+ /(zip|tar|7z|tar\\.gz|tgz|gz|tar\\.bz2|tbz|tbz2|tb2|bz2)/\n end\n \n def git_reference_regex\n # Valid git ref regex, see:\n # https://www.kernel.org/pub/software/scm/git/docs/git-check-ref-format.html\n-\n %r{\n (?!\n (?# doesn't begins with)\n", "new_path": "files/ruby/regex.rb", "old_path": "files/ruby/regex.rb", "a_mode": "100644", @@ -2900,7 +2914,9 @@ "too_large": false }, { - "diff": "--- /dev/null\n+++ b/gitlab-grack\n@@ -0,0 +1 @@\n+Subproject commit 645f6c4c82fd3f5e06f67134450a570b795e55a6\n", + "merge_request_diff_id": 27, + "relative_order": 7, + "utf8_diff": "--- /dev/null\n+++ b/gitlab-grack\n@@ -0,0 +1 @@\n+Subproject commit 645f6c4c82fd3f5e06f67134450a570b795e55a6\n", "new_path": "gitlab-grack", "old_path": "gitlab-grack", "a_mode": "0", @@ -2911,7 +2927,9 @@ "too_large": false }, { - "diff": "--- /dev/null\n+++ b/gitlab-shell\n@@ -0,0 +1 @@\n+Subproject commit 79bceae69cb5750d6567b223597999bfa91cb3b9\n", + "merge_request_diff_id": 27, + "relative_order": 8, + "utf8_diff": "--- /dev/null\n+++ b/gitlab-shell\n@@ -0,0 +1 @@\n+Subproject commit 79bceae69cb5750d6567b223597999bfa91cb3b9\n", "new_path": "gitlab-shell", "old_path": "gitlab-shell", "a_mode": "0", diff --git a/spec/lib/gitlab/import_export/project_tree_restorer_spec.rb b/spec/lib/gitlab/import_export/project_tree_restorer_spec.rb index 14338515892..c11b15a811b 100644 --- a/spec/lib/gitlab/import_export/project_tree_restorer_spec.rb +++ b/spec/lib/gitlab/import_export/project_tree_restorer_spec.rb @@ -86,8 +86,13 @@ describe Gitlab::ImportExport::ProjectTreeRestorer, services: true do it 'has the correct data for merge request st_diffs' do # makes sure we are renaming the custom method +utf8_st_diffs+ into +st_diffs+ + # one MergeRequestDiff uses the new format, where st_diffs is expected to be nil - expect(MergeRequestDiff.where.not(st_diffs: nil).count).to eq(9) + expect(MergeRequestDiff.where.not(st_diffs: nil).count).to eq(8) + end + + it 'has the correct data for merge request diff files' do + expect(MergeRequestDiffFile.where.not(diff: nil).count).to eq(9) end it 'has the correct time for merge request st_commits' do diff --git a/spec/lib/gitlab/import_export/project_tree_saver_spec.rb b/spec/lib/gitlab/import_export/project_tree_saver_spec.rb index 5aeb29b7fec..e52f79513f1 100644 --- a/spec/lib/gitlab/import_export/project_tree_saver_spec.rb +++ b/spec/lib/gitlab/import_export/project_tree_saver_spec.rb @@ -83,6 +83,10 @@ describe Gitlab::ImportExport::ProjectTreeSaver, services: true do expect(saved_project_json['merge_requests'].first['merge_request_diff']['utf8_st_diffs']).not_to be_nil end + it 'has merge request diff files' do + expect(saved_project_json['merge_requests'].first['merge_request_diff']['merge_request_diff_files']).not_to be_empty + end + it 'has merge requests comments' do expect(saved_project_json['merge_requests'].first['notes']).not_to be_empty end @@ -145,6 +149,12 @@ describe Gitlab::ImportExport::ProjectTreeSaver, services: true do expect(project_tree_saver.save).to be true end + it 'does not complain about non UTF-8 characters in MR diff files' do + ActiveRecord::Base.connection.execute("UPDATE merge_request_diff_files SET diff = '---\n- :diff: !binary |-\n LS0tIC9kZXYvbnVsbAorKysgYi9pbWFnZXMvbnVjb3IucGRmCkBAIC0wLDAg\n KzEsMTY3OSBAQAorJVBERi0xLjUNJeLjz9MNCisxIDAgb2JqDTw8L01ldGFk\n YXR'") + + expect(project_tree_saver.save).to be true + end + context 'group members' do let(:user2) { create(:user, email: 'group@member.com') } let(:member_emails) do diff --git a/spec/lib/gitlab/import_export/safe_model_attributes.yml b/spec/lib/gitlab/import_export/safe_model_attributes.yml index 50ff6ecc1e0..fadd3ad1330 100644 --- a/spec/lib/gitlab/import_export/safe_model_attributes.yml +++ b/spec/lib/gitlab/import_export/safe_model_attributes.yml @@ -172,6 +172,17 @@ MergeRequestDiff: - real_size - head_commit_sha - start_commit_sha +MergeRequestDiffFile: +- merge_request_diff_id +- relative_order +- new_file +- renamed_file +- deleted_file +- new_path +- old_path +- a_mode +- b_mode +- too_large Ci::Pipeline: - id - project_id diff --git a/spec/models/merge_request_diff_file_spec.rb b/spec/models/merge_request_diff_file_spec.rb new file mode 100644 index 00000000000..73dfab41532 --- /dev/null +++ b/spec/models/merge_request_diff_file_spec.rb @@ -0,0 +1,8 @@ +require 'rails_helper' + +describe MergeRequestDiffFile, type: :model do + describe '#to_hash' do + it 'returns a hash matching Gitlab::Git::Diff#to_hash' do + end + end +end diff --git a/spec/models/merge_request_diff_spec.rb b/spec/models/merge_request_diff_spec.rb index ed9fde57bf7..42b86a6c199 100644 --- a/spec/models/merge_request_diff_spec.rb +++ b/spec/models/merge_request_diff_spec.rb @@ -36,7 +36,7 @@ describe MergeRequestDiff, models: true do end context 'when the raw diffs are empty' do - before { mr_diff.update_attributes(st_diffs: '') } + before { MergeRequestDiffFile.delete_all(merge_request_diff_id: mr_diff.id) } it 'returns an empty DiffCollection' do expect(mr_diff.raw_diffs).to be_a(Gitlab::Git::DiffCollection) @@ -45,7 +45,10 @@ describe MergeRequestDiff, models: true do end context 'when the raw diffs have invalid content' do - before { mr_diff.update_attributes(st_diffs: ["--broken-diff"]) } + before do + MergeRequestDiffFile.delete_all(merge_request_diff_id: mr_diff.id) + mr_diff.update_attributes(st_diffs: ["--broken-diff"]) + end it 'returns an empty DiffCollection' do expect(mr_diff.raw_diffs.to_a).to be_empty -- cgit v1.2.3