Class: Dependabot::Gradle::FileUpdater::WrapperUpdater

Inherits:
Object
  • Object
show all
Extended by:
T::Sig
Includes:
Distributions
Defined in:
lib/dependabot/gradle/file_updater/wrapper_updater.rb

Constant Summary

Constants included from Distributions

Distributions::DISTRIBUTION_DEPENDENCY_TYPE, Distributions::DISTRIBUTION_REPOSITORY_URL

Instance Method Summary collapse

Methods included from Distributions

distribution_requirements?

Constructor Details

#initialize(dependency_files:, dependency:) ⇒ WrapperUpdater

Returns a new instance of WrapperUpdater.



17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
# File 'lib/dependabot/gradle/file_updater/wrapper_updater.rb', line 17

def initialize(dependency_files:, dependency:)
  @dependency_files = dependency_files
  @dependency = dependency
  @target_files = T.let(
    %w(
      /gradlew
      /gradlew.bat
      /gradle/wrapper/gradle-wrapper.properties
      /gradle/wrapper/gradle-wrapper.jar
    ),
    T::Array[String]
  )
  @build_files = T.let(
    %w(
      build.gradle
      build.gradle.kts
      settings.gradle
      settings.gradle.kts
    ),
    T::Array[String]
  )
end

Instance Method Details

#update_files(build_file) ⇒ Object



44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
# File 'lib/dependabot/gradle/file_updater/wrapper_updater.rb', line 44

def update_files(build_file)
  # We only run this updater if it's a distribution dependency
  return [] unless Distributions.distribution_requirements?(dependency.requirements)

  local_files = dependency_files.select do |file|
    file.directory == build_file.directory && target_file?(file)
  end

  # If we don't have any files in the build files don't generate one
  return [] unless local_files.any?

  # we only run this updater if the build file has a requirement for this dependency
  target_requirements = dependency.requirements.select do |req|
    T.let(req[:file], String) == build_file.name
  end
  return [] unless target_requirements.any?

  updated_files = dependency_files.dup
  SharedHelpers.in_a_temporary_directory do |temp_dir|
    populate_temp_directory(temp_dir)
    cwd = File.join(temp_dir, base_path(build_file))

    has_local_script = File.exist?(File.join(cwd, "./gradlew"))
    command_parts = %w(--no-daemon --stacktrace) + command_args(target_requirements)
    command = Shellwords.join([has_local_script ? "./gradlew" : "gradle"] + command_parts)

    Dir.chdir(cwd) do
      FileUtils.chmod("+x", "./gradlew") if has_local_script

      properties_file = File.join(cwd, "gradle/wrapper/gradle-wrapper.properties")
      validate_option = get_validate_distribution_url_option(properties_file)
      env = { "JAVA_OPTS" => proxy_args.join(" ") } # set proxy for gradle execution

      begin
        # first attempt: run the wrapper task via the local gradle wrapper (if present)
        # `gradle-wrapper.jar` might be too old to run on host's Java version
        SharedHelpers.run_shell_command(command, cwd: cwd, env: env)
      rescue SharedHelpers::HelperSubprocessFailed => e
        raise e unless has_local_script # already field with system one, there is no point to retry

        Dependabot.logger.warn("Running #{command} failed, retrying first with system Gradle: #{e.message}")

        # second attempt: run the wrapper task via system gradle and then retry via local wrapper
        system_command = Shellwords.join(["gradle"] + command_parts)
        SharedHelpers.run_shell_command(system_command, cwd: cwd, env: env) # run via system gradle
        SharedHelpers.run_shell_command(command, cwd: cwd, env: env) # retry via local wrapper
      end

      # Restore previous validateDistributionUrl option if it existed
      override_validate_distribution_url_option(properties_file, validate_option)

      update_files_content(temp_dir, local_files, updated_files)
    rescue SharedHelpers::HelperSubprocessFailed => e
      Dependabot.logger.error("Failed to update files: #{e.message}")
      return updated_files
    end
  end
  updated_files
end