Class: Dependabot::Python::FileFetcher

Inherits:
FileFetchers::Base
  • Object
show all
Extended by:
T::Helpers, T::Sig
Defined in:
lib/dependabot/python/file_fetcher.rb

Constant Summary collapse

CHILD_REQUIREMENT_REGEX =
/^-r\s?(?<path>.*\.(?:txt|in))/
CONSTRAINT_REGEX =
/^-c\s?(?<path>.*\.(?:txt|in))/
DEPENDENCY_TYPES =
%w(packages dev-packages).freeze

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.required_files_in?(filenames) ⇒ Boolean

Returns:

  • (Boolean)


26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
# File 'lib/dependabot/python/file_fetcher.rb', line 26

def self.required_files_in?(filenames)
  return true if filenames.any? { |name| name.end_with?(".txt", ".in") }

  # If there is a directory of requirements return true
  return true if filenames.include?("requirements")

  # If this repo is using a Pipfile return true
  return true if filenames.include?("Pipfile")

  # If this repo is using pyproject.toml return true
  return true if filenames.include?("pyproject.toml")

  return true if filenames.include?("setup.py")

  filenames.include?("setup.cfg")
end

.required_files_messageObject



43
44
45
46
# File 'lib/dependabot/python/file_fetcher.rb', line 43

def self.required_files_message
  "Repo must contain a requirements.txt, setup.py, setup.cfg, pyproject.toml, " \
    "or a Pipfile."
end

Instance Method Details

#ecosystem_versionsObject



48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# File 'lib/dependabot/python/file_fetcher.rb', line 48

def ecosystem_versions
  # Hmm... it's weird that this calls file parser methods, but here we are in the file fetcher... for all
  # ecosystems our goal is to extract the user specified versions, so we'll need to do file parsing... so should
  # we move this `ecosystem_versions` metrics method to run in the file parser for all ecosystems? Downside is if
  # file parsing blows up, this metric isn't emitted, but reality is we have to parse anyway... as we want to know
  # the user-specified range of versions, not the version Dependabot chose to run.
  python_requirement_parser = FileParser::PythonRequirementParser.new(dependency_files: files)
  language_version_manager = LanguageVersionManager.new(python_requirement_parser: python_requirement_parser)
  Dependabot.logger.info("Dependabot is using Python version '#{language_version_manager.python_major_minor}'.")
  {
    languages: {
      python: {
        # TODO: alternatively this could use `python_requirement_parser.user_specified_requirements` which
        # returns an array... which we could flip to return a hash of manifest name => version
        # string and then check for min/max versions... today it simply defaults to
        # array.first which seems rather arbitrary.
        "raw" => language_version_manager.user_specified_python_version || "unknown",
        "max" => language_version_manager.python_major_minor || "unknown"
      }
    }
  }
end

#fetch_filesObject



72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
# File 'lib/dependabot/python/file_fetcher.rb', line 72

def fetch_files
  fetched_files = []

  fetched_files += pipenv_files
  fetched_files += pyproject_files

  fetched_files += requirements_in_files
  fetched_files += requirement_files if requirements_txt_files.any?

  fetched_files << setup_file if setup_file
  fetched_files << setup_cfg_file if setup_cfg_file
  fetched_files += project_files
  fetched_files << pip_conf if pip_conf
  fetched_files << python_version_file if python_version_file

  uniq_files(fetched_files)
end