<commit_before>require 'json'
# Helper methods for Testing Framework forms
module AutomatedTestsHelper
  # This is the waiting list for automated testing. Once a test is requested,
  # it is enqueued and it is waiting for execution. Resque manages this queue.
  @queue = :test_waiting_list

  def fetch_latest_tokens_for_grouping(grouping)
    if grouping.token.nil?
      grouping.create_token(remaining: nil, last_used: nil)
    end
    grouping.token.reassign_tokens
    grouping.token
  end

  def create_test_repo(assignment)
    # Create the automated test repository
    unless File.exist?(MarkusConfigurator
                           .markus_config_automated_tests_repository)
      FileUtils.mkdir(MarkusConfigurator
                          .markus_config_automated_tests_repository)
    end

    test_dir = File.join(MarkusConfigurator
                             .markus_config_automated_tests_repository,
                         assignment.short_identifier)
    unless File.exist?(test_dir)
      FileUtils.mkdir(test_dir)
    end
  end

  # Process Testing Framework form
  # - Process new and updated test files (additional validation to be done at the model level)
  def process_test_form(assignment, params, assignment_params,
                        new_script, new_support_file)

    updated_script_files = {}
    updated_support_files = {}

    testscripts = assignment_params[:test_scripts_attributes] || []
    testsupporters = assignment_params[:test_support_files_attributes] || []

    # Create/Update test scripts
    testscripts.each do |file_num, file|
      # If no new_script then form is empty and skip
      next if testscripts[file_num][:seq_num].empty? && new_script.nil?
      # Create new test script file
      if new_script
        filename = new_script.original_filename
        if TestScript.exists?(script_name: filename, assignment: assignment)
          raise I18n.t('automated_tests.duplicate_filename') + filename
        else
          # Override filename from form
          file[:script_name] = filename
          file[:seq_num] = file_num
          updated_script_files[file_num] = file.clone
        end
      else
        # Edit existing test script file
        unless params[('new_update_script_' +
            testscripts[file_num][:script_name]).to_sym].nil?
          new_update_script = params[('new_update_script_' +
              testscripts[file_num][:script_name]).to_sym]
          old_script_name = file[:script_name]
          file[:script_name] = new_update_script.original_filename
          file[:seq_num] = file_num
          updated_script_files[file_num] = file.clone

          # Uploading new script
          assignment_tests_path = File.join(
                    MarkusConfigurator.markus_config_automated_tests_repository,
                    @assignment.repository_folder,
                    new_update_script.original_filename)
          File.open(assignment_tests_path, 'w') { |f| f.write new_update_script.read }

          # Deleting old script
          old_script_path = File.join(
                    MarkusConfigurator.markus_config_automated_tests_repository,
                    @assignment.repository_folder,
                    old_script_name)
          if File.exist?(old_script_path)
            File.delete(old_script_path)
          end
        end
        updated_script_files[file_num] = file.clone
      end
      # always make sure the criterion type is correct
      updated_script_files[file_num][:criterion_type] = @assignment.criterion_class
    end

    # Create/Update test support files
    # Ignore editing files for now
    testsupporters.each do |file_num, file|
      # Empty file submission, skip
      next if testsupporters[file_num][:file_name].nil? &&
          new_support_file.nil?

      if testsupporters[file_num][:file_name].nil?
        updated_support_files[file_num] = {} || []
        filename = new_support_file.original_filename
        # Create test support file if it does not exist
        if TestSupportFile.exists?(file_name: filename,
                                   assignment: assignment)
          raise I18n.t('automated_tests.duplicate_filename') + filename
        else
          updated_support_files[file_num] = file.clone
          # Override filename from form
          updated_support_files[file_num][:file_name] = filename
        end
      else
        # Edit existing test support file
        unless params[('new_update_file_' +
            testsupporters[file_num][:file_name]).to_sym].nil?
          new_update_file = params[('new_update_file_' +
              testsupporters[file_num][:file_name]).to_sym]
          old_file_name = file[:file_name]
          updated_support_files[file_num] = file.clone
          file[:file_name] = new_update_file.original_filename

          # Uploading new file
          assignment_tests_path = File.join(
                   MarkusConfigurator.markus_config_automated_tests_repository,
                   @assignment.repository_folder,
                   new_update_file.original_filename)
          File.open(
              assignment_tests_path, 'w') { |f| f.write new_update_file.read }

          # Deleting old file
          old_file_path = File.join(
                    MarkusConfigurator.markus_config_automated_tests_repository,
                    @assignment.repository_folder,<commit_msg>automarking: Fix handling of multiple scripts and support files<commit_after>require 'json'
# Helper methods for Testing Framework forms
module AutomatedTestsHelper
  # This is the waiting list for automated testing. Once a test is requested,
  # it is enqueued and it is waiting for execution. Resque manages this queue.
  @queue = :test_waiting_list

  def fetch_latest_tokens_for_grouping(grouping)
    if grouping.token.nil?
      grouping.create_token(remaining: nil, last_used: nil)
    end
    grouping.token.reassign_tokens
    grouping.token
  end

  def create_test_repo(assignment)
    # Create the automated test repository
    unless File.exist?(MarkusConfigurator
                           .markus_config_automated_tests_repository)
      FileUtils.mkdir(MarkusConfigurator
                          .markus_config_automated_tests_repository)
    end

    test_dir = File.join(MarkusConfigurator
                             .markus_config_automated_tests_repository,
                         assignment.short_identifier)
    unless File.exist?(test_dir)
      FileUtils.mkdir(test_dir)
    end
  end

  # Process Testing Framework form
  # - Process new and updated test files (additional validation to be done at the model level)
  def process_test_form(assignment, params, assignment_params,
                        new_script, new_support_file)

    updated_script_files = {}
    updated_support_files = {}

    testscripts = assignment_params[:test_scripts_attributes] || []
    testsupporters = assignment_params[:test_support_files_attributes] || []

    # Create/Update test scripts
    testscripts.each do |file_num, file|
      # If no new_script then form is empty and skip
      next if testscripts[file_num][:seq_num].empty? && new_script.nil?
      if testscripts[file_num][:script_name].nil?
        # Create new test script file if one with the same name does not exist
        updated_script_files[file_num] = {}
        filename = new_script.original_filename
        if TestScript.exists?(script_name: filename, assignment: assignment)
          raise I18n.t('automated_tests.duplicate_filename') + filename
        end
        updated_script_files[file_num] = file.clone
        # Override filename from form
        updated_script_files[file_num][:script_name] = filename
        updated_script_files[file_num][:seq_num] = file_num
      else
        # Edit existing test script file
        unless params[('new_update_script_' + testscripts[file_num][:script_name]).to_sym].nil?
          new_update_script = params[('new_update_script_' + testscripts[file_num][:script_name]).to_sym]
          new_script_name = new_update_script.original_filename
          old_script_name = file[:script_name]
          if TestScript.exists?(script_name: new_script_name, assignment: assignment)
            raise I18n.t('automated_tests.duplicate_filename') + new_script_name
          end
          updated_script_files[file_num] = file.clone
          updated_script_files[file_num][:script_name] = new_script_name
          updated_script_files[file_num][:seq_num] = file_num

          # Uploading new script
          assignment_tests_path = File.join(
                    MarkusConfigurator.markus_config_automated_tests_repository,
                    @assignment.repository_folder,
                    new_script_name)
          File.open(assignment_tests_path, 'w') { |f| f.write new_update_script.read }

          # Deleting old script
          old_script_path = File.join(
                    MarkusConfigurator.markus_config_automated_tests_repository,
                    @assignment.repository_folder,
                    old_script_name)
          if File.exist?(old_script_path)
            File.delete(old_script_path)
          end
        end
        updated_script_files[file_num] = file.clone
      end
      # always make sure the criterion type is correct
      updated_script_files[file_num][:criterion_type] = @assignment.criterion_class
    end

    # Create/Update test support files
    # Ignore editing files for now
    testsupporters.each do |file_num, file|
      # Empty file submission, skip
      next if testsupporters[file_num][:file_name].nil? && new_support_file.nil?
      if testsupporters[file_num][:file_name].nil?
        # Create test support file if one with the same name does not exist
        updated_support_files[file_num] = {}
        filename = new_support_file.original_filename
        if TestSupportFile.exists?(file_name: filename, assignment: assignment)
          raise I18n.t('automated_tests.duplicate_filename') + filename
        end
        updated_support_files[file_num] = file.clone
        # Override filename from form
        updated_support_files[file_num][:file_name] = filename
      else
        # Edit existing test support file
        unless params[('new_update_file_' + testsupporters[file_num][:file_name]).to_sym].nil?
          new_update_file = params[('new_update_file_' + testsupporters[file_num][:file_name]).to_sym]
          new_file_name = new_update_file.original_filename
          old_file_name = file[:file_name]
          if TestSupportFile.exists?(file_name: new_file_name, assignment: assignment)
            raise I18n.t('automated_tests.duplicate_filename') + new_file_name
          end
          updated_support_files[file_num] = file.clone
          updated_support_files[file_num][:file_name] = new_file_name

          # Uploading new file
          assignment_tests_path = File.join(
                   MarkusConfigurator.markus_config_automated_tests_repository,
                   @assignment.repository_folder,
                   new_file_name)
          File.open(
              assignment_tests_path, 'w') { |f| f.write new_update_file.read }

          # Deleting old file
          old_file_path = File.join(
                    MarkusConfigurator.markus_config_automated_tests_repository,
                    @assignment.repository_folder,
{'fraction_non_alphanumeric': 0.07007825551745361, 'fraction_numerical': 0.0010551305724083356, 'mean_word_length': 2.647851186658114, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 1, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3207603', 'n_tokens_mistral': 3205, 'n_tokens_neox': 3141, 'n_words': 649}