diff --git a/bundler/lib/bundler/definition.rb b/bundler/lib/bundler/definition.rb index 639740e46b6b..3cf9fbe8bf03 100644 --- a/bundler/lib/bundler/definition.rb +++ b/bundler/lib/bundler/definition.rb @@ -1077,7 +1077,7 @@ def converge_specs(specs) end end - if parent_dep && parent_dep.source.is_a?(Source::Path) + if parent_dep && parent_dep.source.is_a?(Source::Path) && parent_dep.source.specs[s]&.any? replacement_source = parent_dep.source else replacement_source = sources.get(lockfile_source) diff --git a/bundler/spec/install/gemfile/sources_spec.rb b/bundler/spec/install/gemfile/sources_spec.rb index 69b0816a1899..c72a2b982a99 100644 --- a/bundler/spec/install/gemfile/sources_spec.rb +++ b/bundler/spec/install/gemfile/sources_spec.rb @@ -1236,4 +1236,78 @@ expect(the_bundle).to include_gems("fallback_dep 1.0.0", source: "remote2") end end + + context "when a path gem has a transitive dependency that does not exist in the path source" do + before do + build_repo2 do + build_gem "missing_dep", "1.0.0" + build_gem "foo", "1.0.0" + end + + build_lib "parent_gem", "1.0.0", path: lib_path("parent_gem") do |s| + s.add_dependency "missing_dep" + end + + gemfile <<-G + source "https://gem.repo2" + + gem "foo" + + gem "parent_gem", path: "#{lib_path("parent_gem")}" + G + + bundle :install, artifice: "compact_index" + end + + it "falls back to the default rubygems source for that dependency when updating" do + build_repo2 do + build_gem "foo", "2.0.0" + end + + system_gems [] + + bundle "update foo", artifice: "compact_index" + + expect(the_bundle).to include_gems("parent_gem 1.0.0", "missing_dep 1.0.0", "foo 2.0.0") + expect(the_bundle).to include_gems("parent_gem 1.0.0", source: "path@#{lib_path("parent_gem")}") + expect(the_bundle).to include_gems("missing_dep 1.0.0", source: "remote2") + end + end + + context "when a git gem has a transitive dependency that does not exist in the git source" do + before do + build_repo2 do + build_gem "missing_dep", "1.0.0" + build_gem "foo", "1.0.0" + end + + build_git "parent_gem", "1.0.0", path: lib_path("parent_gem") do |s| + s.add_dependency "missing_dep" + end + + gemfile <<-G + source "https://gem.repo2" + + gem "foo" + + gem "parent_gem", git: "#{lib_path("parent_gem")}" + G + + bundle :install, artifice: "compact_index" + end + + it "falls back to the default rubygems source for that dependency when updating" do + build_repo2 do + build_gem "foo", "2.0.0" + end + + system_gems [] + + bundle "update foo", artifice: "compact_index" + + expect(the_bundle).to include_gems("parent_gem 1.0.0", "missing_dep 1.0.0", "foo 2.0.0") + expect(the_bundle).to include_gems("parent_gem 1.0.0", source: "git@#{lib_path("parent_gem")}") + expect(the_bundle).to include_gems("missing_dep 1.0.0", source: "remote2") + end + end end