diff --git a/app/controllers/concerns/file_import_actions.rb b/app/controllers/concerns/file_import_actions.rb index c7e416df9b..5b37370c5b 100644 --- a/app/controllers/concerns/file_import_actions.rb +++ b/app/controllers/concerns/file_import_actions.rb @@ -34,6 +34,6 @@ def create # rubocop:disable Metrics/AbcSize private def file_import_params - params.require(:file_import).permit(:file, :sample_id_column, :ignore_empty_values) + params.require(:file_import).permit(:file, :sample_id_column, :ignore_empty_values, metadata_columns: []) end end diff --git a/app/javascript/controllers/metadata/file_import_controller.js b/app/javascript/controllers/metadata/file_import_controller.js index 2abd75af52..f624058e63 100644 --- a/app/javascript/controllers/metadata/file_import_controller.js +++ b/app/javascript/controllers/metadata/file_import_controller.js @@ -2,11 +2,12 @@ import { Controller } from "@hotwired/stimulus"; import * as XLSX from "xlsx"; export default class extends Controller { - static targets = ["selectInput", "submitButton"]; + static targets = ["sampleIdColumn", "metadataColumns", "submitButton"]; static values = { - loaded: Boolean + loaded: Boolean, }; + #headers = []; #disabled_classes = [ "bg-slate-50", "border", @@ -28,12 +29,26 @@ export default class extends Controller { ]; connect() { - this.#disableSelectInput(); + this.#disableTarget(this.sampleIdColumnTarget); + if (this.hasMetadataColumnsTarget) { + this.#disableTarget(this.metadataColumnsTarget); + } this.submitButtonTarget.disabled = true; this.loadedValue = true; } - toggleSubmitButton(event) { + changeSampleIDInput() { + if (this.hasMetadataColumnsTarget) { + this.#removeInputOptions(this.metadataColumnsTarget); + this.#addMetadataInputOptions(); + this.#enableTarget(this.metadataColumnsTarget); + this.submitButtonTarget.disabled = true; + } else { + this.submitButtonTarget.disabled = false; + } + } + + changeMetadataInput(event) { const { value } = event.target; this.submitButtonTarget.disabled = !value; } @@ -42,7 +57,7 @@ export default class extends Controller { const { files } = event.target; if (!files.length) { - this.#removeSelectOptions(); + this.#removeInputsOptions(); return; } @@ -53,33 +68,75 @@ export default class extends Controller { const workbook = XLSX.read(reader.result, { sheetRows: 1 }); const worksheetName = workbook.SheetNames[0]; const worksheet = workbook.Sheets[worksheetName]; - const headers = XLSX.utils.sheet_to_json(worksheet, { header: 1 })[0]; - this.#removeSelectOptions(); - this.#addSelectOptions(headers); + this.#headers = XLSX.utils.sheet_to_json(worksheet, { header: 1 })[0]; + this.#removeInputsOptions(); + this.#addSampleIDInputOptions(); + this.#enableTarget(this.sampleIdColumnTarget); + if (this.hasMetadataColumnsTarget) { + this.#disableTarget(this.metadataColumnsTarget); + } }; } - #removeSelectOptions() { - while (this.selectInputTarget.options.length > 1) { - this.selectInputTarget.remove(this.selectInputTarget.options.length - 1); + #removeInputsOptions() { + this.#removeInputOptions(this.sampleIdColumnTarget); + this.#disableTarget(this.sampleIdColumnTarget); + if (this.hasMetadataColumnsTarget) { + this.#removeInputOptions(this.metadataColumnsTarget); + this.#disableTarget(this.metadataColumnsTarget); } - this.#disableSelectInput(); this.submitButtonTarget.disabled = true; } - #addSelectOptions(headers) { - for (let header of headers) { + #addSampleIDInputOptions() { + for (let header of this.#headers) { const option = document.createElement("option"); option.value = header; option.text = header; - this.selectInputTarget.append(option); + this.sampleIdColumnTarget.append(option); } - this.selectInputTarget.disabled = false; - this.selectInputTarget.classList.remove(...this.#disabled_classes); } - #disableSelectInput() { - this.selectInputTarget.disabled = true; - this.selectInputTarget.classList.add(...this.#disabled_classes); + #addMetadataInputOptions() { + const ignoreList = [ + "sample id", + "sample name", + "project id", + "created_at", + "updated_at", + "last_updated_at", + ]; + + let columns = this.#headers.filter( + (header) => + !ignoreList.includes(header.toLowerCase()) && + header.toLowerCase() != this.sampleIdColumnTarget.value.toLowerCase(), + ); + + for (let column of columns) { + const option = document.createElement("option"); + option.value = column; + option.text = column; + this.metadataColumnsTarget.append(option); + } + } + + #removeInputOptions(target) { + for (let index = target.options.length - 1; index >= 0; index--) { + //do not remove the placeholder + if (target.options[index].value) { + target.remove(index); + } + } + } + + #disableTarget(target) { + target.disabled = true; + target.classList.add(...this.#disabled_classes); + } + + #enableTarget(target) { + target.disabled = false; + target.classList.remove(...this.#disabled_classes); } } diff --git a/app/services/samples/metadata/file_import_service.rb b/app/services/samples/metadata/file_import_service.rb index 7e8e321950..e10aec21e9 100644 --- a/app/services/samples/metadata/file_import_service.rb +++ b/app/services/samples/metadata/file_import_service.rb @@ -8,9 +8,9 @@ module Metadata class FileImportService < BaseSpreadsheetImportService def initialize(namespace, user = nil, blob_id = nil, params = {}) @sample_id_column = params[:sample_id_column] - required_headers = [@sample_id_column] + @selected_headers = params[:metadata_columns] || [] @ignore_empty_values = params[:ignore_empty_values] - super(namespace, user, blob_id, required_headers, 1, params) + super(namespace, user, blob_id, [@sample_id_column], 1, params) end def execute @@ -24,9 +24,14 @@ def execute protected - def perform_file_import + def perform_file_import # rubocop:disable Metrics/MethodLength response = {} - parse_settings = @headers.zip(@headers).to_h + headers = if Flipper.enabled?(:metadata_import_field_selection) + @selected_headers << @sample_id_column + else + @headers + end + parse_settings = headers.zip(headers).to_h @spreadsheet.each_with_index(parse_settings) do |metadata, index| next unless index.positive? diff --git a/app/views/shared/samples/metadata/file_imports/_dialog.html.erb b/app/views/shared/samples/metadata/file_imports/_dialog.html.erb index b8973cfc35..9f1032b9ce 100644 --- a/app/views/shared/samples/metadata/file_imports/_dialog.html.erb +++ b/app/views/shared/samples/metadata/file_imports/_dialog.html.erb @@ -47,10 +47,26 @@ { prompt: t(".select_sample_id_column") }, required: true, data: { - "metadata--file-import-target": "selectInput", - action: "change->metadata--file-import#toggleSubmitButton", + "metadata--file-import-target": "sampleIdColumn", + action: "change->metadata--file-import#changeSampleIDInput", } %> + <% if Flipper.enabled?(:metadata_import_field_selection) %> +
+ <%= form.label :metadata_columns, + t(".metadata_columns"), + class: + "block mb-2 text-sm font-medium text-slate-900 dark:text-white" %> + <%= form.select :metadata_columns, + {}, + { multiple: true, include_hidden: false }, + required: true, + data: { + "metadata--file-import-target": "metadataColumns", + action: "change->metadata--file-import#changeMetadataInput", + } %> +
+ <% end %>
<%= form.check_box :ignore_empty_values, { diff --git a/config/locales/en.yml b/config/locales/en.yml index df2ecba18d..415e6ce428 100644 --- a/config/locales/en.yml +++ b/config/locales/en.yml @@ -1819,8 +1819,9 @@ en: file_help: CSV, TSV, XLS or XLSX. ignore_empty_values: description: If selected, any metadata fields without an associated value will be ignored and those metadata keys will not be removed from the sample if present. However, if this not selected, any samples with the metadata key and empty value will be deleted. + metadata_columns: Metadata Columns namespace: - description: 'The spreadsheet is required to have a column that contains a sample identifier. ' + description: The spreadsheet is required to have a column that contains a sample identifier. group: description_html: The identifier is case-sensitive and must contain the sample ID. project: diff --git a/config/locales/fr.yml b/config/locales/fr.yml index ea6f7d4dc4..61db93549b 100644 --- a/config/locales/fr.yml +++ b/config/locales/fr.yml @@ -1819,8 +1819,9 @@ fr: file_help: CSV, TSV, XLS or XLSX. ignore_empty_values: description: If selected, any metadata fields without an associated value will be ignored and those metadata keys will not be removed from the sample if present. However, if this not selected, any samples with the metadata key and empty value will be deleted. + metadata_columns: Metadata Columns namespace: - description: 'The spreadsheet is required to have a column that contains a sample identifier. ' + description: The spreadsheet is required to have a column that contains a sample identifier. group: description_html: The identifier is case-sensitive and must contain the sample ID. project: diff --git a/db/seeds.rb b/db/seeds.rb index e246bc1c8a..1c761269aa 100644 --- a/db/seeds.rb +++ b/db/seeds.rb @@ -5,6 +5,7 @@ Faker::Config.locale = 'en' Flipper.enable(:workflow_execution_sharing) +Flipper.enable(:metadata_import_field_selection) @namespace_group_link_expiry_date = (Time.zone.today + 14).strftime('%Y-%m-%d') diff --git a/docs-site/docs/extend/grapgql_sample_filter.md b/docs-site/docs/extend/graphql_sample_filter.md similarity index 100% rename from docs-site/docs/extend/grapgql_sample_filter.md rename to docs-site/docs/extend/graphql_sample_filter.md diff --git a/test/fixtures/files/metadata/duplicate_headers.csv b/test/fixtures/files/metadata/duplicate_headers.csv index c7b2dfc6f1..fa5bef3539 100644 --- a/test/fixtures/files/metadata/duplicate_headers.csv +++ b/test/fixtures/files/metadata/duplicate_headers.csv @@ -1,3 +1,3 @@ -sample_name,metadatafield1,metadatafield2,sample_name,metadatafield3 -Project 1 Sample 1,10,20,Project 1 Sample 1,30 -Project 1 Sample 2,15,25,Project 1 Sample 2,35 +sample_name,metadatafield1,metadatafield2,metadatafield3,metadatafield3 +Project 1 Sample 1,10,20,30,30 +Project 1 Sample 2,15,25,35,35 diff --git a/test/fixtures/files/metadata/invalid.txt b/test/fixtures/files/metadata/invalid.txt index addbfb8ede..afca8bc76b 100644 --- a/test/fixtures/files/metadata/invalid.txt +++ b/test/fixtures/files/metadata/invalid.txt @@ -1 +1 @@ -invalid file extension +invalid file extension,header diff --git a/test/services/samples/metadata/file_import_service_test.rb b/test/services/samples/metadata/file_import_service_test.rb index 4534147b0f..4051ed3408 100644 --- a/test/services/samples/metadata/file_import_service_test.rb +++ b/test/services/samples/metadata/file_import_service_test.rb @@ -6,6 +6,8 @@ module Samples module Metadata class FileImportServiceTest < ActiveSupport::TestCase def setup + Flipper.enable(:metadata_import_field_selection) + @john_doe = users(:john_doe) @jane_doe = users(:jane_doe) @group = groups(:group_one) @@ -79,7 +81,7 @@ def setup test 'import sample metadata via csv file using sample names for project namespace' do assert_equal({}, @sample1.metadata) assert_equal({}, @sample2.metadata) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, @blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield2 metadatafield3], @@ -104,7 +106,7 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_puid' } + params = { sample_id_column: 'sample_puid', metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.puid => { added: %w[metadatafield1 metadatafield2 metadatafield3], @@ -142,7 +144,8 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_puid' } + params = { sample_id_column: 'sample_puid', + metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3] } response = Samples::Metadata::FileImportService.new(@group, @john_doe, blob.id, params).execute assert_equal({ @sample1.puid => { added: %w[metadatafield1 metadatafield2 metadatafield3], @@ -167,7 +170,8 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', + metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3 metadatafield4] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield2 metadatafield3 metadatafield4], updated: [], deleted: [], not_updated: [], unchanged: [] }, @@ -192,7 +196,8 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', + metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3 metadatafield4] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield2 metadatafield3 metadatafield4], updated: [], deleted: [], not_updated: [], unchanged: [] }, @@ -216,7 +221,7 @@ def setup filename: file.original_filename, content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield2 metadatafield3], @@ -320,7 +325,7 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield3] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield3], @@ -343,7 +348,7 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield3] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield3], @@ -367,7 +372,8 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name', ignore_empty_values: true } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3], + ignore_empty_values: true } response = Samples::Metadata::FileImportService.new(project29.namespace, @john_doe, blob.id, params).execute assert_equal({ sample32.name => { added: ['metadatafield3'], updated: ['metadatafield2'], deleted: [], not_updated: [], unchanged: [] } }, response) @@ -394,7 +400,7 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield3] } response = Samples::Metadata::FileImportService.new(project31.namespace, @john_doe, blob.id, params).execute assert_empty response assert_equal("Sample 'Sample 34' with field(s) 'metadatafield1' cannot be updated.", @@ -416,7 +422,8 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name', ignore_empty_values: false } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3], + ignore_empty_values: false } response = Samples::Metadata::FileImportService.new(project29.namespace, @john_doe, blob.id, params).execute assert_equal({ sample32.name => { added: ['metadatafield3'], updated: ['metadatafield2'], deleted: ['metadatafield1'], not_updated: [], unchanged: [] } }, response) @@ -437,7 +444,8 @@ def setup content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', + metadata_columns: ['sample_name', 'metadatafield1', ' metadatafield2 ', 'metadatafield3'] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield2 metadatafield3], @@ -461,7 +469,7 @@ def setup filename: file.original_filename, content_type: file.content_type ) - params = { sample_id_column: 'sample_name' } + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1 metadatafield2 metadatafield3] } response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, blob.id, params).execute assert_equal({ @sample1.name => { added: %w[metadatafield1 metadatafield2 metadatafield3], updated: [], deleted: [], not_updated: [], unchanged: [] } }, response) @@ -475,6 +483,22 @@ def setup @sample1.reload.metadata) assert_equal({}, @sample2.reload.metadata) end + + test 'import sample metadata selecting a column' do + assert_equal({}, @sample1.metadata) + assert_equal({}, @sample2.metadata) + params = { sample_id_column: 'sample_name', metadata_columns: %w[metadatafield1] } + response = Samples::Metadata::FileImportService.new(@project.namespace, @john_doe, @blob.id, + params).execute + assert_equal({ @sample1.name => { added: %w[metadatafield1], + updated: [], deleted: [], not_updated: [], unchanged: [] }, + @sample2.name => { added: %w[metadatafield1], + updated: [], deleted: [], not_updated: [], unchanged: [] } }, response) + assert_equal({ 'metadatafield1' => '10' }, + @sample1.reload.metadata) + assert_equal({ 'metadatafield1' => '15' }, + @sample2.reload.metadata) + end end end end diff --git a/test/system/groups/samples_test.rb b/test/system/groups/samples_test.rb index 59485d457a..4d74b45dbc 100644 --- a/test/system/groups/samples_test.rb +++ b/test/system/groups/samples_test.rb @@ -7,6 +7,8 @@ class SamplesTest < ApplicationSystemTestCase include ActionView::Helpers::SanitizeHelper def setup + Flipper.enable(:metadata_import_field_selection) + @user = users(:john_doe) login_as @user @group = groups(:group_one) @@ -793,6 +795,9 @@ def retrieve_puids within('div[data-metadata--file-import-loaded-value="true"]') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/valid_with_puid.csv') find('#file_import_sample_id_column', wait: 1).find("option[value='sample_puid']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') @@ -811,12 +816,11 @@ def retrieve_puids within('div[data-metadata--file-import-loaded-value="true"]') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/invalid.txt') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='header']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') - end - assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') - - perform_enqueued_jobs only: [::Samples::MetadataImportJob] + perform_enqueued_jobs only: [::Samples::MetadataImportJob] + end within %(turbo-frame[id="samples_dialog"]) do assert_text I18n.t('services.spreadsheet_import.invalid_file_extension') end @@ -832,6 +836,9 @@ def retrieve_puids attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/contains_empty_values_with_puid.csv') find('#file_import_sample_id_column', wait: 1).find("option[value='sample_puid']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option check 'Ignore empty values' click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end @@ -868,6 +875,9 @@ def retrieve_puids attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/contains_empty_values_with_puid.csv') find('#file_import_sample_id_column', wait: 1).find("option[value='sample_puid']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option assert_not find_field('Ignore empty values').checked? click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end @@ -895,6 +905,10 @@ def retrieve_puids within('div[data-metadata--file-import-loaded-value="true"]') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/duplicate_headers.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find(:xpath, 'option[1]').select_option + find('#file_import_metadata_columns', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find(:xpath, 'option[3]').select_option + find('#file_import_metadata_columns', wait: 1).find(:xpath, 'option[4]').select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') @@ -912,6 +926,9 @@ def retrieve_puids within('div[data-metadata--file-import-loaded-value="true"]') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/missing_metadata_rows.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') @@ -929,14 +946,7 @@ def retrieve_puids within('div[data-metadata--file-import-loaded-value="true"]') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/missing_metadata_columns.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option - click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') - end - assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') - - perform_enqueued_jobs only: [::Samples::MetadataImportJob] - - within %(turbo-frame[id="samples_dialog"]) do - assert_text I18n.t('services.spreadsheet_import.missing_data_columns') + assert find("input[value='#{I18n.t('shared.samples.metadata.file_imports.dialog.submit_button')}'").disabled? end end @@ -955,6 +965,9 @@ def retrieve_puids attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/mixed_project_samples_with_puid.csv') find('#file_import_sample_id_column', wait: 1).find("option[value='sample_puid']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') @@ -976,6 +989,8 @@ def retrieve_puids attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/contains_analysis_values_with_puid.csv') find('#file_import_sample_id_column', wait: 1).find("option[value='sample_puid']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') diff --git a/test/system/projects/samples_test.rb b/test/system/projects/samples_test.rb index 4f9ca3997e..9d1a9c2748 100644 --- a/test/system/projects/samples_test.rb +++ b/test/system/projects/samples_test.rb @@ -7,6 +7,8 @@ class SamplesTest < ApplicationSystemTestCase include ActionView::Helpers::SanitizeHelper setup do + Flipper.enable(:metadata_import_field_selection) + @user = users(:john_doe) login_as @user @sample1 = samples(:sample1) @@ -1171,6 +1173,9 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/valid.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') ### ACTIONS END ### end @@ -1247,6 +1252,10 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/valid.xls') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield4']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end ### ACTIONS END ### @@ -1323,6 +1332,10 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/valid.xlsx') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield4']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') ### ACTIONS END ### end @@ -1374,6 +1387,7 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/invalid.txt') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='header']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end ### ACTIONS END ### @@ -1415,6 +1429,9 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/contains_empty_values.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option # enable ignore empty values find('input#file_import_ignore_empty_values').click click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') @@ -1465,6 +1482,9 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/contains_empty_values.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option # leave ignore empty values disabled assert_not find('input#file_import_ignore_empty_values').checked? click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') @@ -1499,6 +1519,9 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/duplicate_headers.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find(:xpath, 'option[1]').select_option + find('#file_import_metadata_columns', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find(:xpath, 'option[3]').select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end ### ACTIONS END ### @@ -1526,6 +1549,9 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/missing_metadata_rows.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end ### ACTIONS END ### @@ -1553,18 +1579,12 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/missing_metadata_columns.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option - click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') - end - ### ACTIONS END ### - - ### VERIFY START ### - assert_text I18n.t('shared.samples.metadata.file_imports.dialog.spinner_message') - - perform_enqueued_jobs only: [::Samples::MetadataImportJob] + ### ACTIONS END ### - # error msg - assert_text I18n.t('services.spreadsheet_import.missing_data_columns') - ### VERIFY END ### + ### VERIFY START ### + assert find("input[value='#{I18n.t('shared.samples.metadata.file_imports.dialog.submit_button')}'").disabled? + ### VERIFY END ### + end end test 'should partially import metadata with missing sample errors' do @@ -1599,6 +1619,9 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/mixed_project_samples.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield2']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end ### ACTIONS END ### @@ -1658,6 +1681,8 @@ class SamplesTest < ApplicationSystemTestCase within('#dialog') do attach_file 'file_import[file]', Rails.root.join('test/fixtures/files/metadata/contains_analysis_values.csv') find('#file_import_sample_id_column', wait: 1).find(:xpath, 'option[2]').select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield1']").select_option + find('#file_import_metadata_columns', wait: 1).find("option[value='metadatafield3']").select_option click_on I18n.t('shared.samples.metadata.file_imports.dialog.submit_button') end ### ACTIONS END ###