swiftlang / swift-package-manager

The Package Manager for the Swift Programming Language
Apache License 2.0
9.7k stars 1.33k forks source link

[SR-14647] `swift build` incorrectly downgrading dependencies in Package.resolved #4418

Open CraigSiemens opened 3 years ago

CraigSiemens commented 3 years ago
Previous ID SR-14647
Radar rdar://problem/78276237
Original Reporter @CraigSiemens
Type Bug

Attachment: Download

Environment `Apple Swift version 5.4 (swiftlang-1205.0.26.9 clang-1205.0.19.55)` `Target: x86_64-apple-darwin20.4.0`
Additional Detail from JIRA | | | |------------------|-----------------| |Votes | 6 | |Component/s | Package Manager | |Labels | Bug | |Assignee | None | |Priority | Medium | md5: 3df0eb42ba22271c1e8a7b759fa20f63

is duplicated by:

Issue Description:

Introduction

swift build will not respect the versions in Package.swift and instead change Package.resolved to match the dependency versions currently checked out in the .build folder.

Seems to be related to SR-10718

Example project

SomePackage is a Swift Package with a git repo, the commits are the following.

* b6ee888 (update-dependencies) Updated dependencies
* ee23dfe (HEAD -> main) Added dependencies
* 6715449 Initial commit

main is the commit where some dependencies were added

update-dependencies is a branch that has updated the dependencies.

Steps to reproduce

  1. `cd SomePackage`

  2. `git checkout main`

  3. `swift build`

  4. `git checkout update-dependencies`

  5. `swift build`

Expected behaviour

It should build the updated dependencies based on what's in Package.resolved

Actual behaviour

The Package.resolved is updated to match the version of the dependencies that is currently checked out.

Running swift package reset before swift build uses the dependency versions from Package.resolved

Additional notes

typesanitizer commented 3 years ago

@swift-ci create

CraigSiemens commented 3 years ago

I've attached a simpler version of the sample project that reproduces that issue

package-resolved-being-reset-simpler.zip

The steps are the same to reproduce. The main difference it the package only has on dependency (Starscream from:4.0.3). The issue occurs when switching from a branch that had build 4.0.3 to a branch where Package.resolved contains 4.0.4. Between those two versions a sub-dependency was removed which seems to cause the Package.resoved to be ignored and reset to match the versions in the .build folder.

danieleformichelli commented 2 years ago

Same still doesn't work on 5.5 and it also affects other commands, like `swift package resolve`

leleoveiga commented 2 years ago

same

Kondamon commented 2 years ago

This behaviour is horrible when you try to use git bisect and have a project with multiple framework dependencies. You are waiting all the time and resetting package caches to get the correctly versions checked out. Is there any workaround for this, or how do you use git bisect respecting the Package.resolved?

neonichu commented 2 years ago

Untested, but --only-use-versions-from-resolved-file might help.

danieleformichelli commented 2 years ago

Untested, but --only-use-versions-from-resolved-file might help.

No, it doesn't. The resolve should honor the Package.resolved if possible, or use what in Package.swift otherwise. For example, if Package.resolved defines version 2.x for a dependency and it is changed in Package.swift to 3.x, the Package.resovled should update that dependency, while keeping the other the same, if possible

tomassliz commented 1 year ago

I think that #6578 fixes this issue.