Skip to content

Commit

Permalink
properly locate nuget.config when it's further up-directory from a …
Browse files Browse the repository at this point in the history
…project (dependabot#8722)
  • Loading branch information
brettfo authored Jan 8, 2024
1 parent a93b2b2 commit 456f424
Show file tree
Hide file tree
Showing 6 changed files with 109 additions and 23 deletions.
39 changes: 21 additions & 18 deletions nuget/lib/dependabot/nuget/file_fetcher.rb
Original file line number Diff line number Diff line change
Expand Up @@ -219,29 +219,32 @@ def find_and_fetch_with_suffix(suffix)
def nuget_config_files
return @nuget_config_files if @nuget_config_files

@nuget_config_files = []
candidate_paths = [*project_files.map { |f| File.dirname(f.name) }, "."].uniq
visited_directories = Set.new
candidate_paths.each do |dir|
search_in_directory_and_parents(dir, visited_directories)
end
@nuget_config_files = [*project_files.map do |f|
named_file_up_tree_from_project_file(f, "nuget.config")
end].compact.uniq
@nuget_config_files
end

def search_in_directory_and_parents(dir, visited_directories)
loop do
break if visited_directories.include?(dir)

visited_directories << dir
file = repo_contents(dir: dir)
.find { |f| f.name.casecmp("nuget.config").zero? }
if file
file = fetch_file_from_host(File.join(dir, file.name))
file&.tap { |f| f.support_file = true }
@nuget_config_files << file
def named_file_up_tree_from_project_file(project_file, expected_file_name)
found_expected_file = nil
directory_path = Pathname.new(directory)
full_project_dir = Pathname.new(project_file.directory).join(project_file.name).dirname
full_project_dir.ascend.each do |base|
break if found_expected_file

candidate_file_path = Pathname.new(base).join(expected_file_name).cleanpath.to_path
candidate_directory = Pathname.new(File.dirname(candidate_file_path))
relative_candidate_directory = candidate_directory.relative_path_from(directory_path)
candidate_file = repo_contents(dir: relative_candidate_directory).find do |f|
f.name.casecmp?(expected_file_name)
end
if candidate_file
found_expected_file = fetch_file_from_host(File.join(relative_candidate_directory,
candidate_file.name))
end
dir = File.dirname(dir)
end

found_expected_file
end

def global_json
Expand Down
9 changes: 4 additions & 5 deletions nuget/lib/dependabot/nuget/file_parser/project_file_parser.rb
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,10 @@ def target_frameworks(project_file:)
["net#{value[1..-1].delete('.')}"]
end

def nuget_configs
dependency_files.select { |f| f.name.match?(%r{(^|/)nuget\.config$}i) }
end

private

attr_reader :dependency_files, :credentials
Expand Down Expand Up @@ -281,7 +285,6 @@ def build_dependency(name, req, version, prop_name, project_file, dev: false)
end

def dependency_has_search_results?(dependency)
nuget_configs = dependency_files.select { |f| f.name.casecmp?("nuget.config") }
dependency_urls = UpdateChecker::RepositoryFinder.new(
dependency: dependency,
credentials: credentials,
Expand Down Expand Up @@ -490,10 +493,6 @@ def packages_config_files
end
end

def nuget_configs
dependency_files.select { |f| f.name.match?(/nuget\.config$/i) }
end

def global_json
dependency_files.find { |f| f.name.casecmp("global.json").zero? }
end
Expand Down
34 changes: 34 additions & 0 deletions nuget/spec/dependabot/nuget/file_fetcher_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -330,6 +330,40 @@
# end
end

context "NuGet.config can be found when starting in a subdirectory" do
let(:directory) { "/src/some-project/" }

before do
GitHubHelpers.stub_requests_for_directory(
->(a, b) { stub_request(a, b) },
File.join(__dir__, "..", "..", "fixtures", "github", "csproj_in_subdirectory"),
"",
url,
"token token",
"gocardless",
"bump",
"main"
)
stub_request(:get, File.join(url, "src/some-project/.config?ref=sha"))
.with(headers: { "Authorization" => "token token" })
.to_return(
status: 404,
body: "{}",
headers: { "content-type" => "application/json" }
)
end

it "fetches the NuGet.config file from several directories up" do
expect(file_fetcher_instance.files.map(&:name))
.to match_array(
%w(
../../NuGet.Config
some-project.csproj
)
)
end
end

context "with a dirs.proj" do
before do
GitHubHelpers.stub_requests_for_directory(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -831,6 +831,42 @@ def dependencies_from(dep_info)
end
end

describe "nuget.config files further up the tree are considered" do
let(:file_body) { "not relevant" }
let(:file) do
Dependabot::DependencyFile.new(directory: "src/project", name: "my.csproj", content: file_body)
end
let(:nuget_config_body) { "not relevant" }
let(:nuget_config_file) do
Dependabot::DependencyFile.new(name: "../../NuGet.Config", content: nuget_config_body)
end
let(:parser) { described_class.new(dependency_files: [file, nuget_config_file], credentials: credentials) }

it "finds the config file up several directories" do
nuget_configs = parser.nuget_configs
expect(nuget_configs.count).to eq(1)
expect(nuget_configs.first).to be_a(Dependabot::DependencyFile)
expect(nuget_configs.first.name).to eq("../../NuGet.Config")
end
end

describe "files with a `nuget.config` suffix are not considered" do
let(:file_body) { "not relevant" }
let(:file) do
Dependabot::DependencyFile.new(directory: "src/project", name: "my.csproj", content: file_body)
end
let(:nuget_config_body) { "not relevant" }
let(:nuget_config_file) do
Dependabot::DependencyFile.new(name: "../../not-NuGet.Config", content: nuget_config_body)
end
let(:parser) { described_class.new(dependency_files: [file, nuget_config_file], credentials: credentials) }

it "does not return a name with a partial match" do
nuget_configs = parser.nuget_configs
expect(nuget_configs.count).to eq(0)
end
end

describe "multiple dependencies, but each search URI is only hit once" do
let(:file_body) do
<<~XML
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<?xml version="1.0"?>
<configuration>
<packageSources>
<clear />
<add key="nuget.org" value="https://api.nuget.org/v3/index.json" />
</packageSources>
</configuration>
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>net8.0</TargetFramework>
</PropertyGroup>

</Project>

0 comments on commit 456f424

Please sign in to comment.